OpenMP Segfault

我试图将OpenMP并行化添加到一个工作代码(只是一个for循环),但我无法摆脱分段错误。 问题来自这条线:

 pos += sprintf(com + pos, "%d ", i); 

com是一个字符数组,我尝试将它定义为char com[255]char *com = malloc(255*sizeof(char)) ,在for循环内部和之前。 当我在循环之前定义com时,我将private(com)添加到#pragma omp parallel for directive。 我也尝试初始化它并使用firstprivate 。 ( pos是一个整数,初始化为0

当我不添加-fopenmp一切正常,但是使用-fopenmp它会产生段错误。 我错过了什么?

分段错误来自多个线程同时更新pos的值,因此将其设置为某个值,将com + pos转换为指向com的已分配内存之外或之前的指针。 并行化这种循环的正确方法是将私有字符串中的值连接起来,然后以有序的方式连接私有字符串:

 char com[255]; int pos = 0; #pragma omp parallel { char mycom[255]; int mypos = 0; #pragma omp for schedule(static) nowait for (int i = 0; i < N; i++) mypos += sprintf(mycom + mypos, "%d ", i); // Concatenate the strings in an ordered fashion #pragma omp for schedule(static) ordered for (int i = 0; i < omp_get_num_threads(); i++) { #pragma omp ordered pos += sprintf(com + pos, "%s", mycom); } } 

ordered构造确保了正确的同步,因此不需要critical 。 为了保证每个线程处理迭代空间的单个连续部分,使用schedule(static)很重要。