static bool publications_valid;
+/*
+ * Private memory context for publication data, created in
+ * PGOutputData->context when starting pgoutput, and set to NULL when its
+ * parent context is reset via a dedicated MemoryContextCallback.
+ */
+static MemoryContext pubctx = NULL;
+
static List *LoadPublications(List *pubnames);
static void publication_invalidation_cb(Datum arg, int cacheid,
uint32 hashvalue);
}
}
+/*
+ * Callback of PGOutputData->context in charge of cleaning pubctx.
+ */
+static void
+pgoutput_pubctx_reset_callback(void *arg)
+{
+ pubctx = NULL;
+}
+
/*
* Initialize this plugin
*/
{
PGOutputData *data = palloc0(sizeof(PGOutputData));
static bool publication_callback_registered = false;
+ MemoryContextCallback *mcallback;
/* Create our memory context for private allocations. */
data->context = AllocSetContextCreate(ctx->context,
"logical replication output context",
ALLOCSET_DEFAULT_SIZES);
+ Assert(pubctx == NULL);
+ pubctx = AllocSetContextCreate(ctx->context,
+ "logical replication publication list context",
+ ALLOCSET_SMALL_SIZES);
+
+ mcallback = palloc0(sizeof(MemoryContextCallback));
+ mcallback->func = pgoutput_pubctx_reset_callback;
+ MemoryContextRegisterResetCallback(ctx->context, mcallback);
+
ctx->output_plugin_private = data;
/* This plugin uses binary protocol. */
/*
* Shutdown the output plugin.
*
- * Note, we don't need to clean the data->context as it's child context
- * of the ctx->context so it will be cleaned up by logical decoding machinery.
+ * Note, we don't need to clean the data->context and pubctx as they are
+ * child contexts of the ctx->context so they will be cleaned up by logical
+ * decoding machinery.
*/
static void
pgoutput_shutdown(LogicalDecodingContext *ctx)
hash_destroy(RelationSyncCache);
RelationSyncCache = NULL;
}
+
+ /* Better safe than sorry */
+ pubctx = NULL;
}
/*
/* Reload publications if needed before use. */
if (!publications_valid)
{
- oldctx = MemoryContextSwitchTo(CacheMemoryContext);
- if (data->publications)
- list_free_deep(data->publications);
+ Assert(pubctx);
+
+ MemoryContextReset(pubctx);
+ oldctx = MemoryContextSwitchTo(pubctx);
data->publications = LoadPublications(data->publication_names);
MemoryContextSwitchTo(oldctx);