由于MIC上的数据对齐问题导致的分段错误

时间:2014-12-31 10:01:35

标签: memory-alignment intel-mic

我有两个阵列说'fa'和'tempxyz'。我需要从另一个中减去一个并将其存储在另一个数组中。我正在使用流媒体商店。所以我需要对齐访问。我对齐了这两个数组以及第三个数组。我仍然得到一个段。故障。对于流式存储,数组应该是64字节对齐的。这是否意味着数组的每个元素应该相隔64个字节,以便每个元素的地址是64的倍数?我在下面给出了我的代码片段。请帮助我。

main()
{
 double *force = ( double * ) _mm_malloc ( (nd * np )* sizeof ( double ),64);  
                  // np can be any number (np=1000, 2000, etc.)
                  // nd = 3
 __declspec(align(64)) double array[np*nd];
 compute (force, array);
}

void compute (double *f double array[np*nd])
{
  __declspec(align(64)) double fa[8], tempxyz[8];

   for(k=0;k<np;k++)
   {   

   __assume_aligned(f,64);
   __assume((k*nd) % 8 == 0);

   for ( i = 0; i < nd; i++ )
   {
    f[i+k*nd] = 0.0;      
   }

   // Doing some computation on array and storing it in fa.

   fa[0] = array[k*nd+0];
   fa[1] = array[k*nd+1];
   fa[2] = array[k*nd+2];

   __m512d y1, y2, y3;

   __assume_aligned(&fa,64);
   __assume_aligned(&tempxyz,64);

   // Want to load 3 elements at a time, subtract all the three 
   // and store it at a memory location.

   y1 = _mm512_load_pd(fa);
   y2 = _mm512_load_pd(tempxyz);
   y3 = _mm512_sub_pd(y1,y2); 

   __assume_aligned(f,64);
   __assume((k*nd) % 8 == 0);    // Here nd=3 and k is loop index variable.    
   _mm512_storenr_pd((f+k*nd), y3);  // streaming store instruction 
                                     //   --- GIVING SEG. FAULT !!!

  } // end of k loop

}// end of compute function

1 个答案:

答案 0 :(得分:1)

数组&#39;力量&#39;是64字节对齐。因此,对force数组的每次访问都应该是64字节对齐的,即访问的元素的地址应该是64的倍数。一次使用load_pd指令,加载8个双精度数。 (f + k * nd)当k = 1时访问第3个元素,当k = 2时访问第6个元素,依此类推。但是第3个元素的开头对应于第25个字节,它不是64的倍数,这就是发生段错误的原因(类似于其他k值)。所以应该改变公式(f + k * nd)本身,以便使用公式的每次访问都是64的倍数。