[PATCH] Release a replication slot leaked by a caught subtransaction error

From: Bryan Green <dbryan(dot)green(at)gmail(dot)com>
To: pgsql-hackers(at)lists(dot)postgresql(dot)org
Subject: [PATCH] Release a replication slot leaked by a caught subtransaction error
Date: 2026-08-09 03:33:30
Message-ID: 758d3e96-984e-4abe-abcc-b145e757906d@gmail.com
Views: Whole Thread | Raw Message | Download mbox | Resend email
Thread:
Lists: pgsql-hackers

Greetings,

A SQL slot function that errors after acquiring MyReplicationSlot leaks the
slot when the error is caught by a PL/pgSQL EXCEPTION handler: the
subtransaction aborts without releasing it, MyReplicationSlot stays set, and
the next slot operation in the session trips Assert(!MyReplicationSlot).

Releasing on error is done at the top level, in PostgresMain(), and the
comment there is explicit that AbortTransaction() must not do it:

    /*
     * We can't release replication slots inside AbortTransaction() as we
     * need to be able to start and abort transactions while having a slot
     * acquired. ...
     */

A caught error never reaches that top-level path, so the slot is never let
go.

Reproduction --

    DO $$
    BEGIN
        PERFORM pg_create_physical_replication_slot('s', false);
        BEGIN
            PERFORM pg_replication_slot_advance('s', '0/1');
        EXCEPTION WHEN object_not_in_prerequisite_state THEN
            NULL;
        END;
        PERFORM pg_create_physical_replication_slot('s2');
    END $$;

    TRAP: failed Assert("!MyReplicationSlot"), slotfuncs.c:51

The fix releases the slot in AbortSubTransaction(), but only when it was
acquired at or below the aborting subtransaction, tracked by a new
MyReplicationSlotSubid.  That preserves the property the comment above
depends on: a slot acquired outside the current subtransaction survives its
abort, which is what logical apply workers and REPACK rely on.

The patch adds a TAP test for the two paths that actually leak: the acquire
path (pg_replication_slot_advance) and the create path
(pg_create_logical_replication_slot with a missing plugin, which errors
after the slot is acquired).  The test fails without the fix and passes with
it; the regression suite passes.

--
Bryan Green
EDB: https://www.enterprisedb.com

Attachment Content-Type Size
0001-Release-a-replication-slot-leaked-by-a-caught-subtra.patch text/plain 7.2 KB

Responses

Browse pgsql-hackers by date

  From Date Subject
Next Message Bryan Green 2026-08-09 03:39:01 [PATCH]Fix pg_xact corruption from subtransaction abort after subcommit
Previous Message Bryan Green 2026-08-09 03:26:40 [PATCH] Fix SIGSEGV in GrantLockLocal when OOM leaves LOCALLOCK.lockOwners NULL