/* wordcount-incomplete.c */ #include #include #include #include #include #include #include #include /* function prototypes */ int child( char * word, int fd ); void parent( int children, int child_pids[], char *argv[] ); int main( int argc, char *argv[] ) { int i, children; if ( argc < 3 ) { fprintf( stderr, "USAGE: %s ...\n", argv[0] ); return EXIT_FAILURE; } printf( "PARENT: opening %s....\n", argv[1] ); int fd = open( argv[1], O_RDONLY ); /* maybe use fopen() instead here... */ if ( fd < 0 ) /* if ( fd == -1 ) */ { fprintf( stderr, "ERROR: errno is %d\n", errno ); perror( "error opening file" ); return EXIT_FAILURE; } int child_pids[100]; /* TO DO: use calloc() and argc */ /* cycle through argv[2] thru the end argv[argc-1] */ for ( i = 2 ; i < argc ; i++ ) { pid_t z = fork(); if ( z < 0 ) { perror( "fork() failed" ); return EXIT_FAILURE; } if ( z == 0 ) { int word_count = child( argv[i], fd ); exit( word_count ); /* return result to parent */ } child_pids[i-2] = z; /* parent stores each child's pid */ } parent( argc - 2, child_pids, argv ); /* child_pids[0] <==> argv[2] */ /* child_pids[1] <==> argv[3] etc. */ return EXIT_SUCCESS; } /* each child process counts its word */ int child( char * word, int fd ) { int count = 0; printf( "CHILD: I'm counting \"%s\" occurrences\n", word ); /* TO DO: read through the file specified by fd and count */ return count; } void parent( int children, int child_pids[], char *argv[] ) { int status; /* return status from a child process */ pid_t child_pid; printf( "PARENT: I'm waiting for my children to report results.\n" ); int size_of_array = children; while ( children > 0 ) { /* wait until a child process exits */ child_pid = wait( &status ); /* BLOCK */ children--; printf( "PARENT: child %d terminated...", child_pid ); if ( WIFSIGNALED( status ) ) /* core dump or kill or kill -9 */ { printf( "abnormally\n" ); } else if ( WIFEXITED( status ) ) /* child called return or exit() */ { int rc = WEXITSTATUS( status ); printf( "successfully with exit status %d\n", rc ); /* find child_pid in the array: */ int j = 0; while ( j < size_of_array ) { if ( child_pid == child_pids[j] ) { break; } j++; } printf( "PARENT: child counted \"%s\"\n", argv[j+2] ); } printf( "PARENT: %d children to go...\n", children ); } printf( "PARENT: All of my children are awake!\n" ); }