печать дочерних пидов на стандартный вывод в C - PullRequest
0 голосов
/ 15 октября 2018

В настоящее время я пытаюсь отсортировать несколько файлов в каталогах и подкаталогах и вывести отсортированные файлы в другой указанный каталог.Я должен использовать разветвленные процессы для каждой подкаталоги, с которой я сталкиваюсь, и для каждой фактической сортировки.Я также должен следить за тем, сколько дочерних процессов я создал, и печатать PID (ID процесса) каждого из них.

void iterate_dir(char* current_path, char* new_dir, char* column_name){

DIR *dd = opendir(current_path);
struct dirent *curr;
int status = -1;

while((curr = readdir(dd))!=NULL){

    if((strcmp(curr->d_name,".")==0 || strcmp(curr->d_name,"..")==0 || strcmp(curr->d_name,new_dir)==0) && curr->d_type==DT_DIR){

        continue;

    }
    //Just formating stuff, I'm only supposed to sort files ending with .csv
    if(curr->d_type!=DT_DIR){

        if(strlen(curr->d_name)<4){

            continue;

        }

        char* extension = strrchr(curr->d_name,'.');
        if(extension==NULL){

            continue;

        }

        if(strcmp(extension,".csv")!=0){

            continue;

        }

    }

    int pid = fork();

    if(pid==0){


        (*num_of_child_procs)++;

        //child process
        if(curr->d_type==DT_DIR){

            char new_path[strlen(curr->d_name)+strlen(current_path)+2];
            sprintf(new_path,"%s/%s",current_path,curr->d_name);
            iterate_dir(new_path, new_dir, column_name);
            exit(getpid());


        }else{

            //more formatting stuff, I'm supposed to output a new sorted file to the specified output directory
            char file_name[strlen(curr->d_name)-3];
            memcpy(file_name,curr->d_name,strlen(curr->d_name)-4);
            file_name[strlen(curr->d_name)-4] = '\0';
            char new_path[strlen(file_name)+strlen(column_name)+strlen(new_dir)+12+1+1];
            sprintf(new_path,"%s/%s%s%s%s",new_dir,file_name,"-sorted-",column_name,".csv");
            char old_path[strlen(curr->d_name)+strlen(current_path)+2];
            sprintf(old_path,"%s/%s",current_path,curr->d_name);
            int output = open(new_path, O_WRONLY|O_CREAT, 0666);
            int input = open(old_path, O_RDONLY);
            sort(input,output)

            if(ret==-1){

                _exit(-1);

            }

            if(ret==-2){

                remove(new_path);

            }

            exit(getpid());

        }


    }


}


//This is where I print the pids for each process, by using the return status from each child process exit()
while(wait(&status)>0){

    printf("%d,",status);

}

closedir(dd);

}

В основном я вызываю функциюкак таковой

printf("Initial PID:%d\n",getpid());

printf("PIDS of all child processes:");

//mmap is only used for obtaining the number of processes, not printing their pids
num_of_child_procs = mmap(NULL, sizeof *num_of_child_procs, PROT_READ | 
PROT_WRITE,MAP_SHARED | MAP_ANONYMOUS, -1, 0);
*num_of_child_procs = 0;
iterate_dir(dir_name, new_dir_name, column_name);
printf("\nTotal number of processes:%d\n", *num_of_child_procs);
munmap(num_of_child_procs, sizeof *num_of_child_procs);

И все работает нормально, кроме вывода.Выполнение кода в каталоге с 2 файлами .csv, подкаталогом с 2 файлами .csv и подкаталогом этого подкаталога с 1 файлом .csv (всего 7 процессов) выводит

Initial PID:9773
PIDS of all child processes:PIDS of all child processes:PIDS of all child 
processes:PIDS of all child processes:PIDS of all child processes:PIDS of 
all child processes:13312,PIDS of all child processes:13056,12800,12544,PIDS 
of all child processes:12032,12288,11776,
Total number of processes:7

Как видите, по какой-то причине он печатает «PIDS всех дочерних процессов:» несколько раз, несмотря на то, что он вызывается только в моем основном процессе.Кто-нибудь может объяснить, почему он это делает?

1 Ответ

0 голосов
/ 15 октября 2018

printf("PIDS of all child processes:"); не имеет новой строки и, скорее всего, не очищается, а просто находится в буфере stdout.Этот буфер наследуется каждым дочерним процессом;каждый дочерний элемент получает свою собственную копию и сбрасывает ее, когда завершает свою работу.

Решение: fflush(stdout) явно перед разветвлением дочерних элементов.

...