Pasar argumentos de línea de comando a un proceso hijo y contarlos.

Quiero que el proceso principal lleve los argumentos a main () y envíe los caracteres uno por uno al proceso secundario a través de un conducto que comienza con argv [1] y continúa por el rest de los argumentos. para cada personaje).

Quiero que el proceso hijo cuente los caracteres enviados por el proceso padre e imprima la cantidad de caracteres que recibió del padre. El proceso hijo no debe usar los argumentos para main () de ninguna manera.

¿Qué estoy haciendo mal? ¿Necesito usar exec ()?

salida que no es correcta:

~ $ gc a03 gcc -Wall -g a03.c -o a03 ~ $ ./a03 abcd ef ghi child: counted 12 characters ~ $ 

Aquí está el progtwig ..

 #include  #include  #include  #include  #include  int main(int argc, char *argv[]) { int length = 0; int i, count; int fdest[2]; // for pipe pid_t pid; //process IDs char buffer[BUFSIZ]; if (pipe(fdest) < 0) /* attempt to create pipe */ printf("pipe error"); if ((pid = fork())  0) { close(fdest[0]); for(i = 1; i < argc; i++) /* write to pipe */ { write(fdest[1], argv[i], strlen(argv[1])); } wait(0); } else { /* child Process */ close(fdest[1]); for(i = 0; i < argc; i++) { length +=( strlen(argv[i])); /* get length of arguments */ } count = read(fdest[0], buffer, length); printf("\nchild: counted %d characters\n", count); } exit(0); } 

Usted dijo que “el proceso hijo no debe usar los argumentos para main () de ninguna manera”. Sin embargo, veo que su proceso hijo está usando argc . ¿No derrota esto a tu restricción?

También dices que quieres “una llamada para escribir para cada personaje”. Su implementación actual utiliza una llamada para escribir para cada argumento, no para cada carácter. Fue este un error tipográfico? Si no, querrás usar algo más como esto:

 char nul='\0', endl='\n'; for (a=1; a < argc; ++a) { for (c=0; c < strlen(argv[a]); ++c) { write(fdest[1], &argv[a][c], 1); } write(fdest[1], &nul, 1); } write(fdest[1], &endl, 1); 

Esto escribirá un carácter a la vez, con cada argumento como una cadena terminada en NULL y un carácter de nueva línea al final. La nueva línea solo sirve como marcador para indicar que no hay más datos para enviar (y es seguro de usar, ya que no pasará una nueva línea en un argumento de la CLI).

El proceso hijo solo tendrá que ser un bucle que lea los bytes entrantes uno por uno e incremente el contador si el byte no es '\0' o '\n' . Cuando lee el carácter de nueva línea, se sale del bucle de procesamiento de entrada e informa el valor del contador.

Usted tiene un error aquí:

 write(fdest[1], argv[i], strlen(argv[1])); 

Debería tomar strlen(argv[i]) , o le está diciendo a write() que lea más allá del espacio de argv [i] e invoque un comportamiento indefinido.

Tenga en cuenta que solo está llamando a read () una vez. Cuando llama a read (), tal vez solo uno de los argumentos [] haya sido escrito por el padre. O 2. O cualquier número de ellos.

El problema esta aqui

 write(fdest[1], argv[i], strlen(argv[1])); 

Tenga en cuenta que este es strlen de argv[1] , debe ser argv[i] . En realidad estás haciendo referencia al final de argv[2] y argv[3] en este bucle

Está escribiendo efectivamente strlen (“abcd”) * 3 caracteres que son 12 caracteres

Aquí dentro

 for(i = 1; i < argc; i++) /* write to pipe */ { write(fdest[1], argv[i], strlen(argv[1])); } 

strlen(argv[1]) debe ser de hecho strlen(argv[i])