简体   繁体   中英

Creating and joining pthreads in a loop

I am having a weird issue with creating threads via a loop. I have a thread array and the user can specify the number of threads from 1 to 25. A specific issue I ran across is getting a seg fault when looping through and joining the separate threads in the thread array. I debugged it and saw that the thread values in the array are spread sporadically. For instance, if the user specified 9 threads and the array holds 25 possible threads total, then the array would look something like this:

{0, 0, 12332342, 0, 0, 123212313, ...}

Basically, the populated indices are not from index 0 to 9 as expected, but rather spread across the entire array.

My code is a bit messy so I've only included the relevant section, please let me know if more context is needed:

int max_chld_threads = p_args->num_threads - 1;
int chld_threads_delay = p_args->cons_chld_delay;
pthread_t chld_threads[25];
consargs chld_c_args[25];
char chld_name[2] = {'B', 0};
int thd_cnt = 0;
size_t max_char = MAX_CHAR_PER_LINE - 1;
char term_sentinel[] = "@$%#";
int i;
char *cur_file;
char *line;
void *retval;

if ((line = (char *) malloc(max_char * sizeof(char))) == NULL) {
    perror("Malloc failed");
    exit(1);
}

//Opening files in file array
for (i = 0; i < num_files; i++) {
    cur_file = *(file_path_lst + i);
    if ((fp = fopen(cur_file, "r")) == NULL) {
        perror("Cannot open");
        continue;
    }
    while (getline(&line, &max_char, fp) != -1) {
        put (&buffer, line);

        //Creates new child thread if buffer is full
        if (thd_cnt < max_chld_threads && buffer.full == 1) {

            //Copies the argument which contains a thread's name
            strncpy(chld_c_args[thd_cnt].name, chld_name, sizeof(chld_c_args));
            chld_c_args[thd_cnt].delay = chld_threads_delay;

            if (pthread_create (&chld_threads[thd_cnt], NULL, consumer,
                                (void *) &chld_c_args[thd_cnt]) != 0) {
                perror("Child consumer thread creation failed");
                continue;
            }

            //Increment the letter for next child thread
            chld_name[0]++;
            thd_cnt++;
        }
    }
    fclose(fp);
}
put (&buffer, term_sentinel);
/* Join here */
for (i = 0; i < thd_cnt; i++) { //SEGFAULTS here
    pthread_join (chld_threads[i], &retval);
}

consargs:

struct consargs
{
    int delay;
    char name[2];
};

Not sure if this is causing your specific problem but you likely have a buffer overflow in this line:

strncpy(chld_c_args[thd_cnt].name, chld_name, sizeof(chld_c_args));

That should be:

strncpy(chld_c_args[thd_cnt].name, chld_name, 
        sizeof(chld_c_args[thd_cnt].name));

strncpy will pad the dest with zeroes. So you are likely overwriting thd_cnt (and other variables as well).

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM