Как обнаружить несвободное размещение, используя valgrind GDB или любой другой вариант? - PullRequest
2 голосов
/ 09 июня 2019

Я пишу код, связанный с потоками.компиляция с -Wall не дала мне ошибок.но при использовании valgrind с флагами я вижу некоторое несвободное распределение памяти.

Я пытался использовать vgdb и valgrind, это довольно ново для меня.поэтому я сделал несколько контрольных точек и следовал за кодом, но не нашел никаких проблем, только когда программа завершает работу, он показывает сводку утечек.

#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <valgrind/memcheck.h>
#include <valgrind/valgrind.h>


typedef struct Matrix{
    int **mat1;  
    int **mat2;
    int dim;
    int index;
}Matrix;

int **res;

void multMatrix(int** mat1, int** mat2, int** res, int dim, int col);
int resSpot(int** mat1, int** mat2, int row, int col, int matDim);
void matrixScan(int** mtrx, int size);
void matrixPrint(int** mtrx, int dim);
void* dealThread(void* column);
int ** allocArray(int dim);

/* function to calculate the position of the result(i,j) position */
int resSpot(int** mat1, int** mat2, int row, int col, int matDim){
    int sum=0, i;
    for (i=0; i<matDim; i++)
        sum+=mat1[row][i]*mat2[i][col];
    return sum;
}

/* Function to multiply matrix by column */
void multMatrix(int** mat1, int** mat2, int** result, int dim, int col){
    int i;
    for (i=0; i<dim; i++)
        result[i][col]= resSpot(mat1,mat2,i,col,dim);

}

//scan numbers for the matrix
void matrixScan(int** mtrx, int size){
    int i,j;
    for(i=0;i<size;i++)
        for(j=0;j<size;j++)
            scanf("%d",&mtrx[i][j]);
}

//print the matrix
void matrixPrint(int** mtrx, int dim){
    int i,j;
    for(i=0;i<dim;i++){
        for(j=0;j<dim;j++)
            printf("%d\t",mtrx[i][j]);
        printf("\n");
    }
}

//function for each thread to call mult matrix
void* dealThread(void* matPtr){

    Matrix* m=(Matrix*) matPtr;
    printf("index changes? %d \n", (*m).index);
    multMatrix((*m).mat1,(*m).mat2,res,(*m).dim,(*m).index);
    m=NULL;
    pthread_exit(0);

}

int ** allocArray( int dim){
    int i;//,j;
    int size=dim;
    int ** mat = malloc( size * sizeof(*mat));
    if (mat==NULL){
        perror("fail to malloc");
        exit(1);
    }
    for (i = 0; i < size; i++){
        mat[i] = malloc(size * sizeof(*(mat[i])));
        //mat[i]=realloc(mat[i], size*sizeof(int));
        if (mat[i]==NULL){
            perror("fail to malloc");
            exit(1);
        }   
      }
    return mat;
}

int main(){

    int **arr1, **arr2;
    int i,size; 

    printf("Enter MATRIX_DIM (number between 1 and 10)\n");
    scanf("%d",&size);

    pthread_t *thread;
    thread=malloc(sizeof(pthread_t)*size);

    arr1 = allocArray(size);
    arr2 = allocArray(size);
    res = allocArray(size);

    printf("Enter elements of first matrix\n");
    matrixScan(arr1,size);
    printf("Enter elements of second matrix\n");
    matrixScan(arr2,size);

    Matrix *matPtr;
    matPtr=(Matrix*)malloc(sizeof(Matrix)*size);
    if (matPtr==NULL){
        perror("fail to malloc\n");
        exit(1);
    }

    for(i=0;i<size ;i++){
        /* initialize the Matrix struct members to point the array
            and get the indexes */
        matPtr[i].mat1=arr1;
        matPtr[i].mat2=arr2;
        matPtr[i].dim=size;
        matPtr[i].index=i;

        if(pthread_create(&thread[i], NULL, dealThread , (void*) &matPtr[i]) <0){
            fputs("pthread create failed",stderr);
            exit(1);
        }

    }
    /*function to make it multi thread, wait till every thread finish  */
    for(i=0; i< size ; i++){
        pthread_join(thread[i], NULL);
    }

    printf("Product of the matrices:\n");
    matrixPrint(res,size);

    /*free the allocating */
    for( i = 0; i < size; i++){
        matPtr[i].mat1=NULL;
        matPtr[i].mat2=NULL;
        //matPtr[i].dim=NULL;
        //matPtr[i].index=NULL;
        free(arr1[i]);
        arr1[i]=NULL;
        free(arr1[i]);
        arr2[i]=NULL;
        free(res[i]);
        res[i]=NULL;


    }
    free(arr1);
    arr1=NULL;
    free(arr2);
    free(res);
    free(matPtr);
    matPtr=NULL;
    free(thread);
    thread=NULL;

    return 0;
}

==1298== HEAP SUMMARY:
==1298==     in use at exit: 1,714 bytes in 9 blocks
==1298==   total heap usage: 30 allocs, 21 frees, 3,610 bytes allocated
==1298== 
==1298== Searching for pointers to 9 not-freed blocks
==1298== Checked 112,600 bytes
==1298== 
==1298== 36 bytes in 1 blocks are still reachable in loss record 1 of 5
==1298==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==1298==    by 0x4009123: local_strdup (dl-load.c:162)
==1298==    by 0x4009123: _dl_map_object (dl-load.c:2509)
==1298==    by 0x4014A53: dl_open_worker (dl-open.c:235)
==1298==    by 0x400FFF3: _dl_catch_error (dl-error.c:187)
==1298==    by 0x40143BA: _dl_open (dl-open.c:661)
==1298==    by 0x518B0F1: do_dlopen (dl-libc.c:87)
==1298==    by 0x400FFF3: _dl_catch_error (dl-error.c:187)
==1298==    by 0x518B1B1: dlerror_run (dl-libc.c:46)
==1298==    by 0x518B1B1: __libc_dlopen_mode (dl-libc.c:163)
==1298==    by 0x4E47A42: pthread_cancel_init (unwind-forcedunwind.c:52)
==1298==    by 0x4E47C0B: _Unwind_ForcedUnwind (unwind-forcedunwind.c:129)
==1298==    by 0x4E45D3F: __pthread_unwind (unwind.c:129)
==1298==    by 0x4E40534: __do_cancel (pthreadP.h:280)
==1298==    by 0x4E40534: pthread_exit (pthread_exit.c:29)
==1298== 
==1298== 36 bytes in 1 blocks are still reachable in loss record 2 of 5
==1298==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==1298==    by 0x400BDC3: _dl_new_object (dl-object.c:165)
==1298==    by 0x4006783: _dl_map_object_from_fd (dl-load.c:1059)
==1298==    by 0x4008DFF: _dl_map_object (dl-load.c:2605)
==1298==    by 0x4014A53: dl_open_worker (dl-open.c:235)
==1298==    by 0x400FFF3: _dl_catch_error (dl-error.c:187)
==1298==    by 0x40143BA: _dl_open (dl-open.c:661)
==1298==    by 0x518B0F1: do_dlopen (dl-libc.c:87)
==1298==    by 0x400FFF3: _dl_catch_error (dl-error.c:187)
==1298==    by 0x518B1B1: dlerror_run (dl-libc.c:46)
==1298==    by 0x518B1B1: __libc_dlopen_mode (dl-libc.c:163)
==1298==    by 0x4E47A42: pthread_cancel_init (unwind-forcedunwind.c:52)
==1298==    by 0x4E47C0B: _Unwind_ForcedUnwind (unwind-forcedunwind.c:129)
==1298== 
==1298== 100 bytes in 5 blocks are definitely lost in loss record 3 of 5
==1298==    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==1298==    by 0x400E93: allocArray (ex4.c:78)
==1298==    by 0x400F32: main (ex4.c:99)
==1298== 
==1298== 360 bytes in 1 blocks are still reachable in loss record 4 of 5
==1298==    at 0x4C2CC70: calloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==1298==    by 0x40118A2: _dl_check_map_versions (dl-version.c:293)
==1298==    by 0x4014EEC: dl_open_worker (dl-open.c:278)
==1298==    by 0x400FFF3: _dl_catch_error (dl-error.c:187)
==1298==    by 0x40143BA: _dl_open (dl-open.c:661)
==1298==    by 0x518B0F1: do_dlopen (dl-libc.c:87)
==1298==    by 0x400FFF3: _dl_catch_error (dl-error.c:187)
==1298==    by 0x518B1B1: dlerror_run (dl-libc.c:46)
==1298==    by 0x518B1B1: __libc_dlopen_mode (dl-libc.c:163)
==1298==    by 0x4E47A42: pthread_cancel_init (unwind-forcedunwind.c:52)
==1298==    by 0x4E47C0B: _Unwind_ForcedUnwind (unwind-forcedunwind.c:129)
==1298==    by 0x4E45D3F: __pthread_unwind (unwind.c:129)
==1298==    by 0x4E40534: __do_cancel (pthreadP.h:280)
==1298==    by 0x4E40534: pthread_exit (pthread_exit.c:29)
==1298== 
==1298== 1,182 bytes in 1 blocks are still reachable in loss record 5 of 5
==1298==    at 0x4C2CC70: calloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
==1298==    by 0x400BB23: _dl_new_object (dl-object.c:75)
==1298==    by 0x4006783: _dl_map_object_from_fd (dl-load.c:1059)
==1298==    by 0x4008DFF: _dl_map_object (dl-load.c:2605)
==1298==    by 0x4014A53: dl_open_worker (dl-open.c:235)
==1298==    by 0x400FFF3: _dl_catch_error (dl-error.c:187)
==1298==    by 0x40143BA: _dl_open (dl-open.c:661)
==1298==    by 0x518B0F1: do_dlopen (dl-libc.c:87)
==1298==    by 0x400FFF3: _dl_catch_error (dl-error.c:187)
==1298==    by 0x518B1B1: dlerror_run (dl-libc.c:46)
==1298==    by 0x518B1B1: __libc_dlopen_mode (dl-libc.c:163)
==1298==    by 0x4E47A42: pthread_cancel_init (unwind-forcedunwind.c:52)
==1298==    by 0x4E47C0B: _Unwind_ForcedUnwind (unwind-forcedunwind.c:129)
==1298== 

и вот утечка

==1298== LEAK SUMMARY:
==1298==    definitely lost: 100 bytes in 5 blocks
==1298==    indirectly lost: 0 bytes in 0 blocks
==1298==      possibly lost: 0 bytes in 0 blocks
==1298==    still reachable: 1,614 bytes in 4 blocks
==1298==         suppressed: 0 bytes in 0 blocks
==1298== 
==1298== ERROR SUMMARY: 1 errors from 1 contexts (suppressed: 0 from 0)
==1298== ERROR SUMMARY: 1 errors from 1 contexts (suppressed: 0 from 0)

Я действительно хочу узнать, как найти место утечки.

Спасибо и ценим ваше время.

1 Ответ

2 голосов
/ 09 июня 2019
    free(arr1[i]);
    arr1[i]=NULL;
    free(arr1[i]);
    arr2[i]=NULL;
    free(res[i]);
    res[i]=NULL;

В этом коде вы освобождаете arr1 [i] дважды, когда я думаю, что вы хотите освободить arr2 [i].Вот откуда строка '0x400E93: allocArray (ex4.c: 78)' взята из valgrind.В общем, когда вы видите это, посмотрите, где, по вашему мнению, вы освобождаете память, занимаемую malloc, в строке 78 и убедитесь, что код действительно выполняется и выполняет то, что вы думаете.

...