简体   繁体   中英

ls: cannot access 'PATH=./': No such file or directory

I'm new to using linux and the bash command line but I was trying to see whether I could execute basic bash commands (or program) from a c file. My code is really simple and I could've sworn that it was working but suddenly it is not acknowledging that the path even exists.

char* arg[] = {"ls", "-l"};
char* environ[] = {"PATH=./", (char*)0};
execve("/bin/ls", arg, environ);/*execute the command 'ls -l' in curdir*/

I've tried to set as PATH=/bin but it's not even executing the command in that directory. it just returns a similar error.

NOTE: I have tried

char* environ[] = {"PATH=./", NULL};

I've even tried using the envp from main() and that STILL doesn't work.

Put NULL in the end of arg array.

char* arg[] = {"ls", "-l", NULL};

The NULL is used to mark the end of the array.

This error message...

 ls: cannot access 'PATH=./': No such file or directory

... indicates that the ls utility is attempting to access a file named "PATH=./", which it does not find. That is a manifestation of the undefined behavior arising from your code...

 char* arg[] = {"ls", "-l"}; char* environ[] = {"PATH=./", (char*)0}; execve("/bin/ls", arg, environ);/*execute the command 'ls -l' in curdir*/

... on account of execve() expecting and relying upon the argument list to which arg points being terminated by a null pointer.

Although it is somewhat fraught to try to rationalize or interpret undefined behavior, you can imagine that the contents of arrays arg and environ are laid out one immediately after the other in memory, so that the combined representation of these two is the same as the representation of a four-element array of char * . This view is perhaps useful for understanding why the arg and env arrays must be terminated by null pointers in the first place.

The fix is to append a null pointer to the value of arg :

char* arg[] = {"ls", "-l", NULL};

Note also that in this particular case there is no apparent advantage to specifying an environment, so you could simplify by using execv() instead.

Note, too, that path elements other than / itself should not contain a trailing / character. This is not part of a correct name for a directory, and although you can often get away with it, it is poor form.

Please always post a complete program.

As said in the man page, and as said in the comments above, you need a NULL at the end of the arguments list.

You do not need to pass anything in envp[] since you are running just ls

By convention you should pass the full path of the executable in argv[0]

In short, this works

#include <stdio.h>
#include <unistd.h>

int main(void)
{
    char* arg[] = { "/bin/ls", "-l", NULL };
    execve("/bin/ls", arg, NULL);
    return 0;
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM