postgres.git / summary / log / commit / refs

commit    2455ab48844c90419714e27eafd235a85de23232
Author:   Robert Haas <rhaas@postgresql.org>
Date:     Thu Mar 14 16:03:31 2019 +0000

    Defend against leaks into RelationBuildPartitionDesc.
    
    In normal builds, this isn't very important, because the leaks go
    into fairly short-lived contexts, but under CLOBBER_CACHE_ALWAYS,
    this can result in leaking hundreds of megabytes into MessageContext,
    which probably explains recent failures on hyrax.
    
    This may or may not be the best long-term strategy for dealing
    with this leak, but we can change it later if we come up with
    something better.  For now, do this to make the buildfarm green
    again (hopefully).  Commit 898e5e3290a72d288923260143930fb32036c00c
    seems to have exacerbated this problem for reasons that are not
    quite clear, but I don't believe it's actually the cause.
    
    Discussion: http://postgr.es/m/CA+TgmoY3bRmGB6-DUnoVy5fJoreiBJ43rwMrQRCdPXuKt4Ykaw@mail.gmail.com


src/backend/partitioning/partdesc.c | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/src/backend/partitioning/partdesc.c b/src/backend/partitioning/partdesc.c index a4494aca7aa..0593f044c22 100644 --- a/src/backend/partitioning/partdesc.c +++ b/src/backend/partitioning/partdesc.c @@ -68,6 +68,17 @@ RelationBuildPartitionDesc(Relation rel) PartitionKey key = RelationGetPartitionKey(rel); MemoryContext oldcxt; int *mapping; + MemoryContext rbcontext = NULL; + + /* + * While building the partition descriptor, we create various temporary + * data structures; in CLOBBER_CACHE_ALWAYS mode, at least, it's important + * not to leak them, since this can get called a lot. + */ + rbcontext = AllocSetContextCreate(CurrentMemoryContext, + "RelationBuildPartitionDesc", + ALLOCSET_DEFAULT_SIZES); + oldcxt = MemoryContextSwitchTo(rbcontext); /* * Get partition oids from pg_inherits. This uses a single snapshot to @@ -180,7 +191,7 @@ RelationBuildPartitionDesc(Relation rel) MemoryContextCopyAndSetIdentifier(rel->rd_pdcxt, RelationGetRelationName(rel)); - oldcxt = MemoryContextSwitchTo(rel->rd_pdcxt); + MemoryContextSwitchTo(rel->rd_pdcxt); partdesc = (PartitionDescData *) palloc0(sizeof(PartitionDescData)); partdesc->nparts = nparts; /* oids and boundinfo are allocated below. */ @@ -189,7 +200,11 @@ RelationBuildPartitionDesc(Relation rel) if (nparts == 0) { + /* We can exit early in this case. */ rel->rd_partdesc = partdesc; + + /* Blow away the temporary context. */ + MemoryContextDelete(rbcontext); return; } @@ -220,6 +235,9 @@ RelationBuildPartitionDesc(Relation rel) MemoryContextSwitchTo(oldcxt); rel->rd_partdesc = partdesc; + + /* Blow away the temporary context. */ + MemoryContextDelete(rbcontext); } /* [parent: c6ff0b892c30]