희망을 포기하기 시작했습니다. 숙제 때문에 머리를 숙이세요. 어째서 어리석은 짓일까요?다중 포크(), 파이프() 및 선택()에서 길을 잃었습니다.
컨텍스트 : 쉘과 같은 실행됩니다 어떤 프로그램 유무 :
logn [--tick N] cmd를 [인수] 기본적으로
... [[인수] cmd를]를, 그것의 프로그램을 여러 개 동시에 사용할 수 있습니다.
구속 : 각 출력 라인 형식의 printf 전면에서의 명령 번호로 시작하는 "%의 D %의" 예 : 0 : 첫 번째 명령의 첫 번째 줄.
0 : 첫 번째 명령의 두 번째 줄.
1 : 두 번째 명령의 첫 번째 줄.
0 : 첫 번째 명령의 세 번째 줄.
1 : 두 번째 명령 줄.
틱이 지정된 경우 시스템은 n 초 동안 출력이 보내지지 않으면 마침표를 인쇄합니다.
Select()를 사용해야 함
마지막 출력이 마침표 인 경우 시스템에서 다른 마침표를 인쇄하지 않습니다.
이제 내 문제가 있습니다. 나는 그것을 하나의 명령으로 작동시킬 수 있었다. 여러 명령을 만들려고 할 때 실패하는 것 같습니다. 나는 그것이 내 접근일지도 모른다라고 생각한다. 어쩌면 당신 중 일부는 나를 도울 수있을 것입니다.
다음은 Multiple Cmd에서 시도한 것입니다.
당신은 루프의 모든 아이를 포크 할 필요가#include <string.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/time.h>
#include "readline.h"
// Reference: http://www.gnu.org/s/libc/manual/html_node/Waiting-for-I_002fO.html
int input_timeout (int filedes, unsigned int seconds)
{
fd_set set;
struct timeval timeout;
/* Initialize the file descriptor set. */
FD_ZERO (&set);
FD_SET (filedes, &set);
/* Initialize the timeout data structure. */
timeout.tv_sec = seconds;
timeout.tv_usec = 0;
/* select returns 0 if timeout, 1 if input available, -1 if error. */
return (select (FD_SETSIZE,&set, NULL, NULL, &timeout));
}
/* Fetches the number of commands in parameters. Number of Commas + 1 */
int getNbCmd(char ** argv)
{
int nbCmd = 1;
int i;
while(argv[i] != '\0')
{
if(strcmp(argv[i], ",") == 0)
nbCmd++;
i++;
}
return nbCmd;
}
/* Fills the Command Array */
void getCommandes(char *** tbCmd, int argc, char ** argv)
{
int indexArgv = 1;
int indexCmd = 0;
int indexTbCmd = 0;
char ** cmd = (char **)malloc(argc*sizeof(char *));
if(strcmp(argv[indexArgv], "--tick") == 0)
indexArgv = 3;
while (indexArgv < argc)
{
if(strcmp(argv[indexArgv], ",") == 0)
{
cmd[indexCmd] = (char *) 0;
tbCmd[indexTbCmd] = cmd;
free(cmd);
cmd = (char **)malloc(argc*sizeof(char *));
indexTbCmd++;
indexCmd = 0;
}
else
{
char * arg;
arg = argv[indexArgv];
cmd[indexCmd] = arg;
indexCmd++;
}
indexArgv++;
}
cmd[indexCmd] = (char *) 0;
tbCmd[indexTbCmd] = cmd;
free(cmd);
}
int main (int argc, char ** argv)
{
int nbCmds = getNbCmd(argv);
int tick = -1;
char *** tbCmd = (char ***) malloc (nbCmds*sizeof(char **));
if(strcmp(argv[1], "--tick") == 0)
tick = atoi(argv[2]);
getCommandes(tbCmd, argc, argv);
int i;
pid_t pidM[nbCmds];
int p[nbCmds][2];
for (i = 0;i < nbCmds;i++)
{
if (pipe(p[i]) != 0){ perror("pipe()"); exit(1); }
// fork() to get child process
pidM[i] = fork();
if (pidM[i] < 0){ perror("fork()"); exit(1); }
else if (pidM[i] == 0)
{
close(p[i][0]);
dup2(p[i][1], STDOUT_FILENO);
int ret;
ret = execvp(tbCmd[i][0], tbCmd[i]);
}
else
{
close(p[i][1]);
char * buffer;
int retval = 1;
int pntAfficher = 0; //Boolean for Period Printing
/* select returns 0 if timeout, 1 if input available, -1 if error. */
if(tick >= 0)
retval = input_timeout(p[i][0], tick);
if (retval == 0 && pntAfficher == 0)
{
printf(".\n");
pntAfficher = 1;
}
buffer = readline(p[i][0]);
while(buffer[0] != '\0')
{
printf("%d: %s",i, buffer);
free(buffer);
/* select returns 0 if timeout, 1 if input available, -1 if error. */
if(tick >= 0)
retval = input_timeout(p[i][0], tick);
if (retval == 0 && pntAfficher == 0)
{
printf(".\n");
pntAfficher = 1;
}
buffer = readline(p[i][0]);
pntAfficher = 0;
free(buffer);
}
}
}
free(tbCmd);
}
문제와 관련이 없습니다 (아래 답변하는 사람들이 문제를 정확히 지적 했음). select() 대신 poll()을 사용합니다. 그것은 더 좋은 인터페이스를 가지고 있으며 일반적으로 fd_set보다 더 많은 파일 기술자를 지원합니다. – asveikau