From: Michael Paquier Date: Mon, 22 Jun 2026 22:59:02 +0000 (+0900) Subject: Re-introduce pgstat_drop_entry(), keeping ABI compatibility X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=e34b1ff5d89494810a870861505f1b29a731f1ce;p=thirdparty%2Fpostgresql.git Re-introduce pgstat_drop_entry(), keeping ABI compatibility This routine acts as a wrapper of a new pgstat_drop_entry_ext(), used in the core code with a missing_ok argument. This includes an update of .abi-compliance-history, removing the latest entry that has documented the change of pgstat_drop_entry(). This change is applied across v15~v18. HEAD keeps pgstat_drop_entry() as single entry point, with the new missing_ok. Per discussion with Álvaro Herrera and Lukas Fittl. This is a follow-up of 850b9218c8e4. Discussion: https://postgr.es/m/ajZz_sVJVX7pmPHo@alvherre.pgsql Backpatch-through: 15-18 --- diff --git a/.abi-compliance-history b/.abi-compliance-history index 50b244b34d4..42dc8be1a41 100644 --- a/.abi-compliance-history +++ b/.abi-compliance-history @@ -18,15 +18,6 @@ # Be sure to replace "" with details of your change and # why it is deemed acceptable. -bf4616b598a36bfb606c7bd81c0991d895577cb3 -# -# Fix PANIC with track_functions due to concurrent drop of pgstats entries -# 2026-06-18 11:49:39 +0900 -# -# This commit has added a "missing_ok" argument to pgstat_drop_entry(). All -# the callers of this routine are in core for v15-v17. One custom stats kinds -# available in the public since v18 is impacted (maintainer informed). - e37b598028469d260650e5e1671c8275d30e22b6 # # Add file_extend_method=posix_fallocate,write_zeros. diff --git a/src/backend/utils/activity/pgstat_function.c b/src/backend/utils/activity/pgstat_function.c index 75f3dc31eb8..be1daf8925d 100644 --- a/src/backend/utils/activity/pgstat_function.c +++ b/src/backend/utils/activity/pgstat_function.c @@ -112,8 +112,8 @@ pgstat_init_function_usage(FunctionCallInfo fcinfo, AcceptInvalidationMessages(); if (!SearchSysCacheExists1(PROCOID, ObjectIdGetDatum(fcinfo->flinfo->fn_oid))) { - pgstat_drop_entry(PGSTAT_KIND_FUNCTION, MyDatabaseId, - fcinfo->flinfo->fn_oid, true); + pgstat_drop_entry_ext(PGSTAT_KIND_FUNCTION, MyDatabaseId, + fcinfo->flinfo->fn_oid, true); ereport(ERROR, errcode(ERRCODE_UNDEFINED_FUNCTION), errmsg("function call to dropped function")); } diff --git a/src/backend/utils/activity/pgstat_replslot.c b/src/backend/utils/activity/pgstat_replslot.c index 1fb3ffeedc6..48d6c50d951 100644 --- a/src/backend/utils/activity/pgstat_replslot.c +++ b/src/backend/utils/activity/pgstat_replslot.c @@ -153,8 +153,8 @@ pgstat_acquire_replslot(ReplicationSlot *slot) void pgstat_drop_replslot(ReplicationSlot *slot) { - if (!pgstat_drop_entry(PGSTAT_KIND_REPLSLOT, InvalidOid, - ReplicationSlotIndex(slot), false)) + if (!pgstat_drop_entry_ext(PGSTAT_KIND_REPLSLOT, InvalidOid, + ReplicationSlotIndex(slot), false)) pgstat_request_entry_refs_gc(); } diff --git a/src/backend/utils/activity/pgstat_shmem.c b/src/backend/utils/activity/pgstat_shmem.c index 181f9fc701b..31f8646a8fd 100644 --- a/src/backend/utils/activity/pgstat_shmem.c +++ b/src/backend/utils/activity/pgstat_shmem.c @@ -843,7 +843,7 @@ pgstat_free_entry(PgStatShared_HashEntry *shent, dshash_seq_status *hstat) /* * Helper for both pgstat_drop_database_and_contents() and - * pgstat_drop_entry(). If hstat is non-null delete the shared entry using + * pgstat_drop_entry_ext(). If hstat is non-null delete the shared entry using * dshash_delete_current(), otherwise use dshash_delete_entry(). In either * case the entry needs to be already locked. */ @@ -931,6 +931,17 @@ pgstat_drop_database_and_contents(Oid dboid) pgstat_request_entry_refs_gc(); } +/* + * ABI-preserving wrapper around pgstat_drop_entry_ext(). + * + * The original routine introduced in v15 did not include "missing_ok". + */ +bool +pgstat_drop_entry(PgStat_Kind kind, Oid dboid, Oid objoid) +{ + return pgstat_drop_entry_ext(kind, dboid, objoid, false); +} + /* * Drop a single stats entry. * @@ -945,8 +956,8 @@ pgstat_drop_database_and_contents(Oid dboid) * pgstat_gc_entry_refs(). */ bool -pgstat_drop_entry(PgStat_Kind kind, Oid dboid, Oid objoid, - bool missing_ok) +pgstat_drop_entry_ext(PgStat_Kind kind, Oid dboid, Oid objoid, + bool missing_ok) { PgStat_HashKey key; PgStatShared_HashEntry *shent; diff --git a/src/backend/utils/activity/pgstat_xact.c b/src/backend/utils/activity/pgstat_xact.c index 8f5a90153cf..186e5d5383e 100644 --- a/src/backend/utils/activity/pgstat_xact.c +++ b/src/backend/utils/activity/pgstat_xact.c @@ -85,7 +85,7 @@ AtEOXact_PgStat_DroppedStats(PgStat_SubXactStatus *xact_state, bool isCommit) * Transaction that dropped an object committed. Drop the stats * too. */ - if (!pgstat_drop_entry(it->kind, it->dboid, it->objoid, true)) + if (!pgstat_drop_entry_ext(it->kind, it->dboid, it->objoid, true)) not_freed_count++; } else if (!isCommit && pending->is_create) @@ -94,7 +94,7 @@ AtEOXact_PgStat_DroppedStats(PgStat_SubXactStatus *xact_state, bool isCommit) * Transaction that created an object aborted. Drop the stats * associated with the object. */ - if (!pgstat_drop_entry(it->kind, it->dboid, it->objoid, true)) + if (!pgstat_drop_entry_ext(it->kind, it->dboid, it->objoid, true)) not_freed_count++; } @@ -159,7 +159,7 @@ AtEOSubXact_PgStat_DroppedStats(PgStat_SubXactStatus *xact_state, * Subtransaction creating a new stats object aborted. Drop the * stats object. */ - if (!pgstat_drop_entry(it->kind, it->dboid, it->objoid, true)) + if (!pgstat_drop_entry_ext(it->kind, it->dboid, it->objoid, true)) not_freed_count++; pfree(pending); } @@ -321,7 +321,7 @@ pgstat_execute_transactional_drops(int ndrops, struct xl_xact_stats_item *items, { xl_xact_stats_item *it = &items[i]; - if (!pgstat_drop_entry(it->kind, it->dboid, it->objoid, true)) + if (!pgstat_drop_entry_ext(it->kind, it->dboid, it->objoid, true)) not_freed_count++; } diff --git a/src/include/utils/pgstat_internal.h b/src/include/utils/pgstat_internal.h index b856fbc6ab0..4ed814170dc 100644 --- a/src/include/utils/pgstat_internal.h +++ b/src/include/utils/pgstat_internal.h @@ -625,8 +625,9 @@ extern PgStat_EntryRef *pgstat_get_entry_ref(PgStat_Kind kind, Oid dboid, Oid ob extern bool pgstat_lock_entry(PgStat_EntryRef *entry_ref, bool nowait); extern bool pgstat_lock_entry_shared(PgStat_EntryRef *entry_ref, bool nowait); extern void pgstat_unlock_entry(PgStat_EntryRef *entry_ref); -extern bool pgstat_drop_entry(PgStat_Kind kind, Oid dboid, Oid objoid, - bool missing_ok); +extern bool pgstat_drop_entry(PgStat_Kind kind, Oid dboid, Oid objoid); +extern bool pgstat_drop_entry_ext(PgStat_Kind kind, Oid dboid, Oid objoid, + bool missing_ok); extern void pgstat_drop_all_entries(void); extern PgStat_EntryRef *pgstat_get_entry_ref_locked(PgStat_Kind kind, Oid dboid, Oid objoid, bool nowait);