Thread: Report a potential memory leak in PostgresSQL 14.1

Report a potential memory leak in PostgresSQL 14.1

From
wliang@stu.xidian.edu.cn
Date:
Hi all,

I find a potential memory leak in PostgresSQL 14.1, which is in the function getPublicationTables (./src/bin/pg_dump/pg_dump.c).

Specifically, at line 4079, a memory chunk is allocated with pg_malloc() and assigned to 'pubrinfo' by employing the pg_malloc(). However, the function returns without freeing the memory and does not pass 'pubrinfo' to other functions. As a result, a memory leak problem is caused.

 4045 void
 4046 getPublicationTables(Archive *fout, TableInfo tblinfo[], int numTables)
 4047 {
 4048     PQExpBuffer query;
 4049     PGresult   *res;
 4050     PublicationRelInfo *pubrinfo;
 4051     DumpOptions *dopt = fout->dopt;
 4052     int         i_tableoid;
 4053     int         i_oid;
 4054     int         i_prpubid;
 4055     int         i_prrelid;
 4056     int         i,
 4057                 j,
 4058                 ntups;
 4059 
 4060     if (dopt->no_publications || fout->remoteVersion < 100000)
 4061         return;
 4062 
 4063     query = createPQExpBuffer();
 4064 
 4065     /* Collect all publication membership info. */
 4066     appendPQExpBufferStr(query,
 4067                          "SELECT tableoid, oid, prpubid, prrelid "

 4068                          "FROM pg_catalog.pg_publication_rel");

 4069     res = ExecuteSqlQuery(fout, query->data, PGRES_TUPLES_OK);
 4070 
 4071     ntups = PQntuples(res);
 4072 
 4073     i_tableoid = PQfnumber(res, "tableoid");
 4074     i_oid = PQfnumber(res, "oid");
 4075     i_prpubid = PQfnumber(res, "prpubid");
 4076     i_prrelid = PQfnumber(res, "prrelid");
 4077 
 4078     /* this allocation may be more than we need */
 4079     pubrinfo = pg_malloc(ntups * sizeof(PublicationRelInfo));
 4080     j = 0;
 4081 
 4082     for (i = 0; i < ntups; i++)
 4083     {
 4084         Oid         prpubid = atooid(PQgetvalue(res, i, i_prpubid));
 4085         Oid         prrelid = atooid(PQgetvalue(res, i, i_prrelid));

 4086         PublicationInfo *pubinfo;
 4087         TableInfo  *tbinfo;
 4088 
 4089         /*
 4090          * Ignore any entries for which we aren't interested in either the
 4091          * publication or the rel.
 4092          */
 4093         pubinfo = findPublicationByOid(prpubid);
 4094         if (pubinfo == NULL)
 4095             continue;
 4096         tbinfo = findTableByOid(prrelid);
 4097         if (tbinfo == NULL)
 4098             continue;
 4099 
 4100         /*
 4101          * Ignore publication membership of tables whose definitions are not
 4102          * to be dumped.
 4103          */
 4104         if (!(tbinfo->dobj.dump & DUMP_COMPONENT_DEFINITION))
 4105             continue;
 4106 

 4107         /* OK, make a DumpableObject for this relationship */
 4108         pubrinfo[j].dobj.objType = DO_PUBLICATION_REL;
 4109         pubrinfo[j].dobj.catId.tableoid =
 4110             atooid(PQgetvalue(res, i, i_tableoid));
 4111         pubrinfo[j].dobj.catId.oid = atooid(PQgetvalue(res, i, i_oid));
 4112         AssignDumpId(&pubrinfo[j].dobj);
 4113         pubrinfo[j].dobj.namespace = tbinfo->dobj.namespace;
 4114         pubrinfo[j].dobj.name = tbinfo->dobj.name;
 4115         pubrinfo[j].publication = pubinfo;
 4116         pubrinfo[j].pubtable = tbinfo;
 4117 
 4118         /* Decide whether we want to dump it */
 4119         selectDumpablePublicationObject(&(pubrinfo[j].dobj), fout);
 4120 
 4121         j++;
 4122     }
 4123 
 4124     PQclear(res);
 4125     destroyPQExpBuffer(query);
 4126 }

I'm looking forward to your confirmation.

Best,

Wentao



Re: Report a potential memory leak in PostgresSQL 14.1

From
Daniel Gustafsson
Date:
> On 14 Feb 2022, at 11:02, wliang@stu.xidian.edu.cn wrote:

Thanks for you report.

>  4112         AssignDumpId(&pubrinfo[j].dobj);

AssignDumpId records the DumpableObject and keeps a reference to this memory,
have a read of that function and I think you'll see how the memory is managed.

--
Daniel Gustafsson        https://vmware.com/