LinuxQuestions.org
Visit Jeremy's Blog.
Home Forums Tutorials Articles Register
Go Back   LinuxQuestions.org > Forums > Non-*NIX Forums > Programming
User Name
Password
Programming This forum is for all programming questions.
The question does not have to be directly related to Linux and any language is fair game.

Notices


Reply
  Search this Thread
Old 08-11-2011, 02:03 PM   #1
trist007
Senior Member
 
Registered: May 2008
Distribution: Slackware
Posts: 1,052

Rep: Reputation: 70
Assembly for execve passing args...


I'm trying to figure out how to save a pointer to a list of arguments in assembly. I'm just starting to learn assembly.
In C it would be like this:
Code:
int main()
{
char *args[] = { "/usr/bin/ps", "a", NULL };
execve( "/usr/bin/ps", args, NULL );
exit(-1);
}
Code:
BITS 32
xor eax,eax                         // zeroing out eax register
cdq                                      // zeroing out edx register (3rd arg)
push eax                             // pushing zero or NULL onto the stack
push long 0x73702f2f        // pushing "//ps" onto the stack
push long 0x6e69622f       // pushing "/bin" onto the stack
push long 0x7273752f       // pushing "/usr" onto the stack
mov ebx,esp                       // saving the pointer to the string in ebx register (1st arg)
push eax                             // pushing zero or NULL onto the stack
push long 0x20202061      // pushing "a   " onto the stack
push ebx                             // pushing the pointer to the string "/usr/bin/ps0" onto the stack
mov ecx, esp                       // saving the pointer of the string in the ecx register (2nd arg)
mov al,0x0b                        // moving decimal 11 into the al register, 11 syscall for execve
int 0x80                               // executing, no need to call exit
Please be as detailed as possible. Thanks.
 
Old 08-11-2011, 08:17 PM   #2
paulsm4
LQ Guru
 
Registered: Mar 2004
Distribution: SusE 8.2
Posts: 5,863
Blog Entries: 1

Rep: Reputation: Disabled
Not even close. I'm not sure if the comments are off, or the actual code is wrong ... or both ...

... but ...

Suggestions:
1. Write a 5-line C program that does your execve, compile with "-S" to generate an assembly listing and see how it works.

2. I don't recall if "execve" is an OS call (which would use "int 0x80"), or a standard library call (which wouldn't).
In either case, "gcc -S" would tell you.

3. Declare local variables for your string and use variable names. DON'T use big hairy hexadecimal constants

... and ...

4. Check out this tutorial. It's free, and it's a really, really good introduction to assembly programming in general (and assembly programming on Linux in particular):

Programming from the Ground Up, Jonathan Bartlett

PS:
NASM syntax might be appealing if you're looking at DOS examples, or if you're only ever programming Intel CPUs.

But you SHOULDN'T be looking at DOS examples - they'll give you some nasty bad habits you'll have to unlearn

And Gnu Assembler syntax really shines the moment you try your hand at OTHER assembly languages, BESIDES Intel (like MIPS, ARM or Power PC, for example).

IMHO...
 
Old 08-11-2011, 08:34 PM   #3
trist007
Senior Member
 
Registered: May 2008
Distribution: Slackware
Posts: 1,052

Original Poster
Rep: Reputation: 70
Fantastic, thank you for pointing me in the right direction. I also figured it out, let me post a working build.
Code:
[bits 32]

xor eax, eax             ; zeroing out registers
xor ebx, ebx
xor ecx, ecx
xor edx, edx            ; 3rd arg done
xor esi, esi
xor edi, edi

push eax
push long 0x73702f2f    ; "//ps"
push long 0x6e69622f		; "/bin"
push long 0x7273752f		; "/usr"
mov ebx, esp		; 1st arg done

; working on args array
; eax, ebx, ecx, edx, esi, edi, ebp

push eax
push byte 0x61			; "a"
mov esi, esp

; assemble the args array
push eax
push esi
push ebx
mov ecx, esp            ; 2nd arg done

; give to the kernel
mov eax, 0x0b
int 0x80

; execve("/usr/bin/ps", NULL)
; args[] = {"/usr/bin/ps0", "a", NULL}

Last edited by trist007; 08-11-2011 at 08:47 PM.
 
Old 08-12-2011, 01:05 AM   #4
paulsm4
LQ Guru
 
Registered: Mar 2004
Distribution: SusE 8.2
Posts: 5,863
Blog Entries: 1

Rep: Reputation: Disabled
Glad you got it working. A few additional points:

1. When I compiled with "-S", my execve did indeed resolve to a standard library call (*not* directly to the underlying syscall). But invoking the syscall directly is equally valid. They're all defined here, in "asm/unistd.h":

http://linux.die.net/include/asm/unistd.h
#define __NR_execve 11

2. The comments are still wrong. Here's the API call:
Code:
 int execve(const char *filename, char *const argv [], char *const envp[]);
3. This means you're passing the following:

eax // Syscall#: NR_execve == 11 == 0x0b
ebx // Arg#1: pointer to the program string ("/usr/bin/ps")
ecx // Arg#2: pointer to the arguments array (*args[] = { "/usr/bin/ps", "a", NULL }
edx // Arg#3: pointer to the environment array (NULL)

'Hope that helps .. PSM
 
  


Reply



Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is Off
HTML code is Off



Similar Threads
Thread Thread Starter Forum Replies Last Post
[SOLVED] python passing multiple args to bash gary_in_springhill Programming 6 01-16-2011 05:14 AM
Passing args in terminal window is OK. but isn't when passing in GNOME launcher why? majrys1962 Debian 0 11-18-2008 06:00 PM
Passing args to port / make and apache rob0t *BSD 4 08-27-2008 10:34 AM
Passing args in an IOCTL neerajb Linux - Software 0 04-20-2006 05:51 AM
assembly execve (syscall 11) rblampain Programming 2 07-03-2005 09:23 AM

LinuxQuestions.org > Forums > Non-*NIX Forums > Programming

All times are GMT -5. The time now is 05:45 PM.

Main Menu
Advertisement
My LQ
Write for LQ
LinuxQuestions.org is looking for people interested in writing Editorials, Articles, Reviews, and more. If you'd like to contribute content, let us know.
Main Menu
Syndicate
RSS1  Latest Threads
RSS1  LQ News
Twitter: @linuxquestions
Open Source Consulting | Domain Registration