Я работаю над заданием для своего класса операционной системы (Posix & C), создаю мини-оболочку и не знаю, как решить следующую проблему:
Моя мини-оболочка должна принимать две команды, например ls | grep a
. Для этого я создаю трубу второго размера и ребенка. Ребенок закрывает все, что он должен закрыть, и открывает все, что он должен открыть (стандарт / труба входит и выходит). Затем он выполняет «ls», используя execvp. Я уверен, что это работает хорошо. После этого родитель закрывает и открывает входы и выходы (я уверен, что я делаю это хорошо), а затем выполняет grep a
.
Теперь проблема в том, что процесс grep a
никогда не заканчивается. То же самое для tail -1
, например. Но оно работает для head -1
. Я думаю, что это происходит потому, что grep
и tail
, которые выполняются родителем, ожидают большего ввода, даже если дочерний процесс завершил свою работу. ls | grep a
производит правильный вывод, отображаемый на консоли (вывод канала устанавливается как вывод по умолчанию), но, как я уже сказал, grep a
не завершается.
Итак, мой вопрос: как я могу сообщить родителю, что канал завершил запись, чтобы он мог, например, завершить выполнение grep a
?
Спасибо.
Вот код:
[fd - это канал, он был инициализирован ранее в коде. Если вы видите какую-то неуместную вещь, пожалуйста, дайте мне знать; Я немного очистил код, и это только проблемная часть, как вы можете видеть.]
int fd[2];
pipe(fd);
if ((pid = fork()) != -1){
if(pid == 0){ /*Child executing */
close(fd[0]);
close(1);
dup(fd[1]);
close(fd[1]);
execvp(argvv[0][0], argvv[0]); /* Here's stored the first instruction */
} else{ /* Parent executing */
wait(&status);
close(fd[1]);
close(0);
dup(fd[0]);
close(fd[0]);
execvp(argvv[1][0], argvv[1]); /* Here's stored the second instruction */
}
}