Програмирам UNIX shell и трябва да използвам execv()
системен разговор за създаване на процес. Един от параметрите за execv()
е pathpath за изпълнимия файл. Така че, ако някой влезе /bin/ls
, той ще стартира ls
изпълним. Но това, от което се нуждая, е такава функция, че когато ls
е натиснат, той ще търси пътя на файла ls
(като which
команда). Има ли функция, която ми позволява да направя това?
За съжаление, това е училищен проект, който не ми е позволено да използвам execvp()
, Трябва да внедря някаква функция за търсене на път и след това да добави, че filepath към execv()
параметър.
Отговори:
4 за отговор № 1употреба PATH = getenv("PATH")
за да получите низ от пътя от околната среда, след това използвайте последователни повиквания strtok(PATH,":")
тогава strtok(NULL,":")
да разберем пътеките от PATH
низ в масив от char **path
, с които ще трябва да разпределите malloc()
, място path[x]
+ "/"
+ argv[0]
в буфер и използване access(buffer, X_OK)
за да видите дали можете да изпълнявате файла си на това място на пътя, ако е така, изпълнете своя execv(buffer,argv)
.
3 за отговор № 2
Ако не можете да използвате execvp, можете да получите променливата PATH от char** environ
от <unistd.h> или char* getenv(const char* name)
от <stdlib.h> след това използвайте int access(const char* filename, int mode)
за да видите дали файлът съществува и е изпълним. Аз ще оставя изпълнението на вас, тъй като това е училищен проект.
2 за отговор № 3
Искате execvp (), той ще търси в пътя, посочен в променливата PATH, освен ако името на файла не съдържа "/".
2 за отговор № 4
Няколко души са ви предложили да се обадите access()
или stat()
преди да се опитате да изпълните програмата с execv()
, Не е нужно да правиш това. execv()
ще върне грешка, ако не може да изпълни заявения файл.
1 за отговор № 5
употреба execvp
.
char *args[] = {"ls", (char *) NULL};
execvp("ls", args);
например този пример ще се изпълни /bin/echo
(приемайки /bin
е на вашия PATH).
#include <unistd.h>
int main()
{
char *args[] = {"echo", "hello world", (char *) NULL};
execvp("echo", args);
return 0;
}
1 за отговор № 6
Мисля, че execvp () прави това, от което се нуждаете.
Редактиране: Така че всъщност питате как да направите това ръчно? В този случай ...
- Намерете PATH в envp (трети аргумент към main ())
- Разделете това на отделни пътеки
- Проверете за съществуването на вашата програма във всяка от тях със stat ()
- Изпълнете първата, която откриете, че съществува
Или ако искате наистина ли солидна реализация, използване това, Може и да изгасне детекторите на плагаризма :)
0 за отговор № 7
От страницата man execvp:
The functions execlp() and execvp() will duplicate the actions of the
shell in searching for an executable file if the specified filename
does not contain a slash (/) character. The search path is the path
specified in the environment by the PATH variable. If this variable
isn’t specified, the default path ‘‘:/bin:/usr/bin’’ is used. In addi-
tion, certain errors are treated specially.
Възможно ли е да използвате execlp ()? Ако трябва да използвате execv, ще трябва да получите стойността на променливата за PATH средата, да анализирате това с помощта на strtok (), за да получите отделните пътища, да добавите името на файла към всеки път и да опитате да го изпълните с execv ().
Аз дадох код, но не правя домашното ти за теб.
0 за отговор № 8
execvp
:-)
Редактиране: Добре. Тук е версия на Perl, която може да служи като псевдокод за вашия проблем.
use List::Util qw(first);
my @path = split /:/, $ENV{PATH};
my $dir = first {$_ ||= "."; -x "$_/$name"} @path
or die "Can"t find program $namen";
exec "$dir/$name", @args;
split
разделя низ в масив от низове, използвайки дадения разделител. first
намира първия елемент, който отговаря на критерий; тук, че свързването на директорията и търсеното име е изпълнима (-x
). Тогава тече това.
Надявам се, че помага!
-1 за отговор № 9
О, училищен проект ...
Е, ако искате нещо "като кой" защо не просто exec, което "сам (/ usr / bin / which on linux, а не bash alias или tcsh builtin), за да стигнете до това, което търсите ...
:-)