2014-01-12 2 views
0

Я в настоящее время реализует функцию & & в оболочке с использованием C. Например, если вход cmd1 & & Cmd2, то cmd2 выполняет только тогда, когда cmd1 успешно завершается. Я думаю о:ли функция возвращается в дочернем процессе могут быть захвачены в родительском процессе

int main() { 
    int i; 
    char **args; 

    while(1) { 
     printf("yongfeng's shell:~$ "); 
     args = get_line(); 
     if (strcmp(args[0], "exit") == 0) exit(0);  /* if it's built-in command exit, exit the shell */ 
     if('&&') parse_out_two_commands: cmd1, cmd2; 
     if (execute(cmd1) != -1) /* if cmd1 successfully executed */ 
      execute(cmd2);  /* then execute the second cmd */ 
    } 
} 

int execute(char **args){ 
    int pid; 
    int status; /* location to store the termination status of the terminated process */ 
    char **cmd; /* pure command without special charactors */ 

    if(pid=fork() < 0){ //fork a child process, if pid<0, fork fails 
     perror("Error: forking failed"); 
     return -1; 
    } 

    /* child */ 
    else if(pid==0){    /* child process, in which command is going to be executed */ 
     cmd = parse_out(args); 
     /* codes handleing I/O redirection */ 

     if(execvp(*cmd, cmd) < 0){ /* execute command */ 
      perror("execution error"); 
      return -1; 
     } 
     return 0; 
    } 
    /* parent */ 
    else{   /* parent process is going to wait for child or not, depends on whether there's '&' at the end of the command */ 
     if(strcmp(args[sizeof(args)],'&') == 0){ 
      /* handle signals */ 
     } 
     else if (pid = waitpid(pid, &status, 0) == -1) perror("wait error"); 
    } 
} 

Так что я использую другую функцию int execute (char ** args), чтобы выполнить фактическую работу. Его тип возврата - int, потому что я хочу знать, успешно ли завершена команда. Но я не уверен здесь, может ли родительский процесс получить возвращаемое значение от ребенка, поскольку это два разных процесса.

Или мне нужно решить, следует ли выполнять вторую команду в дочернем процессе, путем форматирования другого процесса для его запуска? Большое спасибо.

+0

Не имеет отношения к вашему вопросу, но есть проблемы с 'strcmp (args [sizeof (args)], '&'), но есть меньше.' –

+0

Прочитайте [Расширенное программирование на Linux] (http://advancedlinuxprogramming.com/) –

ответ

3

Изменение:

if(pid=fork() < 0){ //fork a child process, if pid<0, fork fails 

к:

if((pid=fork()) < 0){ //fork a child process, if pid<0, fork fails 

Вы установки pid в результате fork() < 0, не устанавливая его на PID ребенка. Поэтому, если в fork() нет ошибки, это устанавливает pid в 0 как в родительском, так и в дочернем, поэтому оба они считают, что они являются дочерними.

Что касается возвращаемого значения функции execute(): оно будет возвращаться как в родительском, так и в дочернем. В каждом процессе он вернет все, что было указано в инструкции return в соответствующей ветке if в execute(). Обратите внимание, что он execve() успешно, ребенок никогда не возвращается, потому что он больше не запускает эту программу, он запускает программу, которая была выполнена.

Если ребенок хочет отправить родительскому сообщению информацию о успехе или неудаче, он делает это, используя свой статус выхода, путем вызова exit(0) для указания успеха и exit(some-nonzero-value) для указания отказа. Родитель может получить статус выхода с помощью waitpid, а затем вернуть показатель успеха или отказа от execute().

+0

о, да, я вижу. Спасибо. но на самом деле мой вопрос заключается в том, можно ли зафиксировать значение, возвращаемое в дочернем процессе, в родительском процессе. То есть, могу ли я написать if (execute (cmd1)! = -1)? Благодарю. –

+1

Ничего, что происходит в дочернем процессе, не отображается родительскому объекту, кроме его статуса выхода, который вы можете использовать с помощью 'waitpid()'. – Barmar

+0

Большое спасибо. но здесь я все еще не могу понять, почему функция execute вернется как в родительском, так и в дочернем процессах? Если я хочу реализовать функцию &&, должен ли я запускать один cmd в дочернем элементе, а другой - в родительском, если дочерний элемент успешно завершен? В настоящее время я делаю это для двух детей. –

Смежные вопросы