Memory Leak in GiDpost

Moderator: GiD Team

Post Reply
mvscheven
Posts: 16
Joined: Thu Dec 04, 2014 4:26 pm
Location: Stuttgart, Germany

Memory Leak in GiDpost

Post by mvscheven »

Hello,

we assume that there is a small memory leak in the GiDpost library in the context of opening and closing the ASCII files.

Valgrind's leak-check reports two lost blocks:

Code: Select all

48 bytes in 1 blocks are definitely lost in loss record 1 of 2
    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
    by 0x408EB2: CPostAscii_Create (in /src/GiDpost)
    by 0x402B6E: GiD_fOpenPostMeshFile (in src/GiDpost)
    by 0x401330: main (GiDpost.cpp:72)
 
48 bytes in 1 blocks are definitely lost in loss record 2 of 2
    at 0x4C2AB80: malloc (in /usr/lib/valgrind/vgpreload_memcheck-amd64-linux.so)
    by 0x408EB2: CPostAscii_Create (in src/GiDpost)
    by 0x402A8A: GiD_fOpenPostResultFile (in src/GiDpost)
    by 0x401342: main (GiDpost.cpp:73)
The memory is allocated when calling GiD_fOpenPostResultFile to open the mesh and res file (lines 72 and 73) of the example program below.

Code: Select all

    #include <stdlib.h>
    #include <stdio.h>
    #include "gidpost.h"

    #define ASCII_FORMAT

    typedef struct {
      int id;
      float x, y, z;
    } SCoord;

    typedef struct {
      int id;
      int n1, n2, n3;
    } SElem;

    SCoord nodes[9];
    SElem elems[8];

    void GenMesh()
    {
      int i, j, idx;
      SCoord * node;
      SElem * elm1, * elm2;

      idx = 1;
      for ( i = 0; i < 3; i++ ) {
        for ( j = 0; j < 3; j++, idx++ ) {
          node = nodes + idx -1;
          node->id = idx;
          node->x = (float)(i);
          node->y = (float)(j);
          node->z = 0;
        }
      }
      idx = 0;
      for ( i = 0; i < 2; i++ ) {
        for ( j = 0; j < 2; j++, idx+=2 ) {
          elm1 = elems + idx;
          elm2 = elm1 + 1;
          elm1->id = idx+1;
          elm1->n1 = i*3 + j + 1;
          elm1->n3 = i*3 + j + 1 + 3 ;
          elm1->n2 = elm1->n3 + 1;
          elm2->id = idx+2;
          elm2->n1 = elm1->n1;
          elm2->n2 = elm1->n1 + 1;
          elm2->n3 = elm1->n2;
        }
      }
    }

    float Random()
    {
      return rand()/(float)(RAND_MAX);
    }

    int main()
    {
      int i;
      SCoord * node;
      SElem * elm;
      int elmi[4];
      int elmi2[10];
      GiD_FILE fdm, fdr;

      GenMesh();

      GiD_PostInit();

    #if defined(ASCII_FORMAT)
      fdm = GiD_fOpenPostMeshFile( "test_fd.post.msh", GiD_PostAscii);
      fdr = GiD_fOpenPostResultFile( "test_fd.post.res", GiD_PostAscii);
    #else
      fdm = fdr = GiD_fOpenPostResultFile( "test_fd.post.bin", GiD_PostBinary);
    #endif



      /* write mesh for first time step */
      GiD_fBeginMeshGroup(fdm, "Mesh 1");

      GiD_fBeginMeshColor(fdm, "TestMsh", GiD_2D, GiD_Triangle, 3, 0, 0.99, 0);
      /* coordinates */
      GiD_fBeginCoordinates(fdm);
      for ( i = 0; i < 9; i++ ) {
        node = nodes + i;
        GiD_fWriteCoordinates(fdm, node->id, node->x, node->y, node->z );
      }
      GiD_fEndCoordinates(fdm);
      /* elements */
      GiD_fBeginElements(fdm);
      for ( i = 0; i < 8; i++ ) {
        elm = elems + i;
        elmi[0] = elm->n1;
        elmi[1] = elm->n2;
        elmi[2] = elm->n3;
        elmi[3] = 2;
        GiD_fWriteElementMat(fdm, elm->id, elmi);
      }
      GiD_fEndElements(fdm);
      GiD_fEndMesh(fdm);

      GiD_fEndMeshGroup(fdm);


      // A: outside group
      //GiD_fBeginGaussPoint(fdr, "GPTri", GiD_Triangle, "TestMsh", 1, 0, 1);
      //GiD_fEndGaussPoint(fdr);

      /* now results for first time step */
      GiD_fBeginOnMeshGroup(fdr, "Mesh 1");

      // B: inside group
      GiD_fBeginGaussPoint(fdr, "GPTri", GiD_Triangle, "TestMsh", 1, 0, 1);
      GiD_fEndGaussPoint(fdr);

       // Result
      GiD_fBeginResult(fdr, "Scalar on GP", "Analysis", 1.0, GiD_Scalar, GiD_OnGaussPoints, "GPTri", NULL, 0, NULL);
      for ( i = 0; i < 8; i++ ) {
        GiD_fWriteScalar(fdr, i+1, Random());
      }
      GiD_fEndResult(fdr);

      GiD_fEndOnMeshGroup(fdr);




      /* write mesh for second time step */
      GiD_fBeginMeshGroup(fdm, "Mesh 2");

      GiD_fBeginMeshColor(fdm, "TestMsh", GiD_2D, GiD_Quadrilateral, 9, 0, 0.99, 0);
      /* coordinates */
      GiD_fBeginCoordinates(fdm);
      for ( i = 0; i < 9; i++ ) {
        node = nodes + i;
        GiD_fWriteCoordinates(fdm, node->id, node->x, node->y, node->z );
      }
      GiD_fEndCoordinates(fdm);
      /* elements */
      GiD_fBeginElements(fdm);

        elmi2[0] = 1;
        elmi2[1] = 7;
        elmi2[2] = 9;
        elmi2[3] = 3;
        elmi2[4] = 4;
        elmi2[5] = 8;
        elmi2[6] = 6;
        elmi2[7] = 2;
        elmi2[8] = 5;
        elmi2[9] = 2;
        GiD_fWriteElementMat(fdm, 1, elmi2);

      GiD_fEndElements(fdm);
      GiD_fEndMesh(fdm);

      GiD_fEndMeshGroup(fdm);


      // A: outside group
      //GiD_fBeginGaussPoint(fdr, "GPQuad", GiD_Quadrilateral, "TestMsh", 1, 0, 1);
      //GiD_fEndGaussPoint(fdr);

      /* now results for second time step */
      GiD_fBeginOnMeshGroup(fdr, "Mesh 2");

      // B: inside group
      GiD_fBeginGaussPoint(fdr, "GPQuad", GiD_Quadrilateral, "TestMsh", 1, 0, 1);
      GiD_fEndGaussPoint(fdr);



      // Result
      GiD_fBeginResult(fdr, "Scalar on GP", "Analysis", 1.0, GiD_Scalar, GiD_OnGaussPoints, "GPQuad", NULL, 0, NULL);
      GiD_fWriteScalar(fdr, 1, Random());
      GiD_fEndResult(fdr);

      GiD_fEndOnMeshGroup(fdr);


      // Close file(s)
    #ifdef ASCII_FORMAT
      GiD_fClosePostMeshFile(fdm);
    #endif
      GiD_fClosePostResultFile(fdr);

      GiD_PostDone();

      printf("Finished normally!!");
      return 0;
    }
Regards
Malte
User avatar
escolano
Posts: 1922
Joined: Sun Sep 05, 1982 10:51 pm

Re: Memory Leak in GiDpost

Post by escolano »

I think that this memory leak has been fixed a week ago, but there is not available publicly until next gidpost release.

In any case, to use free the allocated resources properly it is necessary before to use any library procedure call

Code: Select all

GiD_PostInit();
and when finishing the use call

Code: Select all

GiD_PostDone();
But don't worry about this memory leak, it is only few bytes that are not properly freed, and when the process finish the operating system will release all its memory.
mvscheven
Posts: 16
Joined: Thu Dec 04, 2014 4:26 pm
Location: Stuttgart, Germany

Re: Memory Leak in GiDpost

Post by mvscheven »

We know that the memory lost is only a few bytes, but we are trying to get a clean valgrind output for our own code to be able to detect memory problems more easily. Doing so we found the small leak in GiDpost.

Thanks a lot for fixing this. Looking forward to the new version.
Malte
Post Reply