Thread: Using execvp

  1. #1
    Registered User
    Join Date
    Apr 2008
    Posts
    101

    Using execvp

    In my code I try to remove the contents of a folder using this
    Code:
    if((nTokens = makeargv("rm /tmp/.tmp_cache/*.*", " ", &tokens)) == -1 ){
    	printf("Ocorreu um erro ao separar o comando em tokens.\n");
    }
    else{
    	if(execvp("rm", "rm", "/tmp/.tmp_cache/*.*", NULL) == -1){
    		perror("Error executing execvp : ");
    	}
    }
    (makargv is a function that tokenizes the string - let me know if you wanna see it)

    The output for it is
    Code:
    rm: cannot remove `/tmp/.tmp_cache/*.*': No such file or directory
    but if I try
    Code:
    rm /tmp/.tmp_cache/*.*
    on the same shell just after the program ends it wirks fine.

    I have no idea of what can be wrong. Please help.

  2. #2
    and the hat of int overfl Salem's Avatar
    Join Date
    Aug 2001
    Location
    The edge of the known universe
    Posts
    39,659
    Wildcards are expanded by the shell, not by execv or the process which ultimately receives the command line.
    If you dance barefoot on the broken glass of undefined behaviour, you've got to expect the occasional cut.
    If at first you don't succeed, try writing your phone number on the exam paper.

  3. #3
    Registered User
    Join Date
    Apr 2008
    Posts
    101
    So how can I run that command?

    Or any command that allows me to delete all content of a file (without knowing what could be there in advance)

  4. #4
    Registered User
    Join Date
    Apr 2008
    Posts
    396
    either call the shell exec...("/bin/sh -e rm /tmp/something/*"...); or walk the entire directory (readdir()) to delete each file one by one.

  5. #5
    Registered User
    Join Date
    Apr 2008
    Posts
    101
    How would I go about calling the shell exec?

    it's ok to run in execvp ("/bin/sh", "/bin/sh", "-e", "rm", "/tmp/cenas/*.*", NULL );

  6. #6
    Registered User
    Join Date
    Apr 2008
    Posts
    396
    sorry, I missed a word: "either call the shell *from* exec", there is no "shell exec"
    and yes your example seems right.

  7. #7
    Registered User
    Join Date
    Apr 2008
    Posts
    101
    now I get
    Code:
    /bin/sh: Can't open rm

  8. #8
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Quote Originally Posted by kotoko View Post
    now I get
    Code:
    /bin/sh: Can't open rm
    You may need to pass the path to rm (or pass in the environment from your exisitng process by calling execve instead).

    http://www.manpagez.com/man/2/execve/

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  9. #9
    Registered User
    Join Date
    Apr 2008
    Posts
    101
    I far as I understood the execve needs to specify the environment. I'm not that sure of what this means exactly but it seems to me that it's the kind of thing that isn't very portable. My problem with that is that the code must run on my machine, my colleague and on a server.

    It really isn't any simpler way of deleting the contents of a directory?

  10. #10
    Registered User
    Join Date
    Apr 2008
    Posts
    396
    what matsp meant, was to add the path to rm: execvp(..."/bin/rm"...), that's all (or provide the appropriate PATH env. var. to exec)

  11. #11
    Registered User
    Join Date
    Apr 2008
    Posts
    101
    Hmm It's just that I saw this example
    Code:
    #include <unistd.h>
    
    
    int ret;
    char *cmd[] = { "ls", "-l", (char *)0 };
    char *env[] = { "HOME=/usr/home", "LOGNAME=home", (char *)0 };
    ...
    ret = execve ("/bin/ls", cmd, env);
    The man pages says
    Code:
    int execve(const char *path, char *const argv[], char *const envp[]);
    So the correct use for me would be

    Code:
    char *cmd[] = { "rm", "/tmp/cenas/*.*", (char *)0 };
    char *env[] = { "HOME=/usr/home", "LOGNAME=home", (char *)0 };
    execve("/bin/sh", cmd, env);
    I'm confused about the env part

  12. #12
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    You can obviously write a function that deletes all files in a directory.

    You can also do
    Code:
    extern char **environ;
    char *argv[] =
    {
       "/bin/sh", "-e", "rm", "/tmp/cenas/*.*", NULL
    };
    execve(argv[0], argv, environ);
    execvp in itself is specific to Unix OS's, so it's not VERY portable. But if all the machines you need to run this on are Unix/Linux, then you should be fine with this.

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  13. #13
    Registered User
    Join Date
    Apr 2008
    Posts
    101
    I'm still getting
    Code:
    /bin/sh: Can't open rm

  14. #14
    Kernel hacker
    Join Date
    Jul 2007
    Location
    Farncombe, Surrey, England
    Posts
    15,677
    Is that with the code I posted or your code?

    --
    Mats
    Compilers can produce warnings - make the compiler programmers happy: Use them!
    Please don't PM me for help - and no, I don't do help over instant messengers.

  15. #15
    Registered User
    Join Date
    Apr 2008
    Posts
    101
    Yup. I get

    Code:
    /bin/sh: Can't open rm
    using

    Code:
    extern char **environ;
    char *argv[] = {"/bin/sh", "-e", "rm", "/tmp/cenas/*.*", NULL};
    execve(argv[0], argv, environ);

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Storing the result of execvp to a char array in C
    By kponenation in forum C Programming
    Replies: 1
    Last Post: 12-14-2005, 11:43 PM
  2. Replies: 1
    Last Post: 10-27-2005, 10:24 AM
  3. execvp not working right
    By Nessarose in forum C Programming
    Replies: 5
    Last Post: 07-18-2005, 05:51 AM
  4. execvp and ampersand?
    By slevytam in forum C Programming
    Replies: 16
    Last Post: 02-02-2005, 08:36 PM
  5. getting input from keyboard, passing to execvp
    By jumpyg in forum C++ Programming
    Replies: 4
    Last Post: 11-02-2003, 08:49 PM