【问题标题】:Malloc Memory corruption in CC 中的 Malloc 内存损坏
【发布时间】:2011-06-04 17:29:33
【问题描述】:

我在使用 malloc 时遇到问题。

我有一个名为 jacobi_gpu 的函数,它被多次调用:

int main(int argc, char* argv[]){

    /* ... */

    int totalrot=0;
    while(nrot>0){
        iter++;
        nrot=jacobi_gpu(a,q, tol, dimmat);
        totalrot+=nrot;

        printf("iter =%3d  nrot=%3d\n",iter, nrot);
    }

    /* ... */
}

参数 a,q,tol 和 dimmat 已正确初始化。 A 和 Q 是 2 个方阵,而 dimmat 是它们的维度。

这是我的代码:

int jacobi_gpu(double A[], double Q[], double tol, long int dim){
    int nrot, p, q, k, tid;
    double c, s;
    double *mc, *vc;

    printf("jacobi begins \n");

    mc   = (double *)malloc(2 * dim * sizeof(double));
    vc   = (double *)malloc(2 * dim * sizeof(double));

    if( mc == NULL || vc == NULL){
        fprintf(stderr, "pb allocation matricre\n");
        exit(1);
    }

    nrot = 0;

    for(k = 0; k < dim - 1; k++){
        eye(mc, dim);
        eye(vc, dim);

        for(tid = 0; tid < floor(dim /2); tid++){
            p = (tid + k)%(dim - 1);
            if(tid != 0)
                q = (dim - tid + k - 1)%(dim - 1);
            else
                q = dim - 1;

            //printf("p = %d | q = %d\n", p, q);
            if(fabs(A[p + q*dim]) > tol){

                nrot++;
                symschur2(A, dim, p, q, &c, &s);

                mc[2*tid] = p;        vc[2 * tid] = c;
                mc[2*tid + 1] = q;    vc[2*tid + 1] = -s;

                mc[2*tid + 2*(dim - 2*tid) - 2] = p;
                vc[2*tid + 2*(dim - 2*tid)   - 2 ] = s;

                mc[2*tid + 2*(dim - 2*tid) - 1] = q;
                vc[2 * tid + 2*(dim - 2*tid) - 1 ] = c;     
            }
        }

        affiche(mc,dim,2,"Matrice creuse");
        affiche(vc,dim,2,"Valeur creuse");

    }
    printf("end\n");
    free(mc);
    free(vc);
    return nrot;
}

我的问题在于 mc 变量的 malloc 调用:

*** glibc detected *** ./jacobi_gpu: double free or corruption (!prev): 0x00000000022944a0 ***
    *** glibc detected *** ./jacobi_gpu: malloc(): memory corruption: 0x0000000002294580 ***

有什么建议吗?

[编辑]

  • 函数eye初始化一个单位矩阵
  • affiche 函数显示带有行和列的矩阵。第一个参数是矩阵,第二个是行数,第三个是列数。

更多解释

矩阵 mc 的目的是存储变量 p 和 q。这些变量包含列索引。 矩阵 vc 的目的是存储那些列中包含的值。 例如,如果矩阵 mc 的第一行是 0 和 5(p = 0,q = 5),这意味着矩阵 vc 中的值将在第 0 和第 5 列中。 如果矩阵 mc 中的矩阵第五行是 2 3 ( p = 2, q = 3),则表示 vc 中第五行的值将在第 2 列和第 3 列中。

希望这一次,我更清楚。

感谢您的帮助

【问题讨论】:

  • 使用调试器单步调试代码会发生什么?
  • eye() 是做什么的,什么时候发生故障?即它是在第一次调用malloc() 时发生还是在多次调用后发生?
  • 就此而言,affiche() 是做什么的?
  • @james affiche() 翻译成海报,所以我猜是输出包装器。

标签: c malloc cuda gpu


【解决方案1】:

恒等矩阵总是正方形的,但 mc 不是。当您致电eye(mc, dim) 时,我怀疑 eye 将 mc 视为一个暗矩阵,而实际上它是一个 2 矩阵,并写入未分配的内存。

【讨论】:

  • 啊,eye() 有它:)
【解决方案2】:

在调用malloc() 时,您没有为方阵分配足够的内存。正确的大小应该是dim 的平方,而不仅仅是2*dim

这应该可以解决问题:

mc   = (double *)malloc(dim * dim * sizeof(double));
vc   = (double *)malloc(dim * dim * sizeof(double)); 

【讨论】:

  • ... 所以矩阵运算可能会覆盖malloc 簿记信息。
  • 不,这是我矩阵的正确维度。该矩阵包含 2 列和 N 行。此矩阵的目的是存储值 p 和 q。
  • @larsmans:这是有道理的。当然,一旦您开始写入未分配的内存,就无法保证。
  • @Dimitri:嗯,然后回到第一格。
  • @Dimitri:你说你的矩阵在问题中是正方形的。
【解决方案3】:

据我所知,double free or corruption (!prev) 是您在同一个指针上多次调用 free(),您的其他函数可能正在执行此操作(我怀疑 affiche(). 也许尝试在你的 shell 上 export MALLOC_CHECK_=0 之后运行它?

【讨论】:

    【解决方案4】:

    您的代码中一定有堆栈损坏。使用调试选项编译并通过 valgrind 运行您的代码,它会告诉您。

    顺便说一句,在 C 中,malloc 的结果是一个坏主意。不要这样做,它可能会隐藏缺少包含正确头文件的诊断。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2023-03-16
      • 1970-01-01
      • 2019-11-04
      相关资源
      最近更新 更多