diff options
author | Tom Lane <tgl@sss.pgh.pa.us> | 2024-06-14 16:20:35 -0400 |
---|---|---|
committer | Tom Lane <tgl@sss.pgh.pa.us> | 2024-06-14 16:20:35 -0400 |
commit | 198de79612f04f45320781d0a57ee77d9043d0c2 (patch) | |
tree | 6aacfdcb2781643439df270c017bbc8ad09fd6c0 | |
parent | c7de5a654567ffbd0eef1d6d2fb8d3fa2b5c5dee (diff) | |
download | postgresql-198de79612f04f45320781d0a57ee77d9043d0c2.tar.gz postgresql-198de79612f04f45320781d0a57ee77d9043d0c2.zip |
Clean out column-level pg_init_privs entries when dropping tables.
DeleteInitPrivs did not get the memo about how, when dropping a
whole object (with subid == 0), you should drop entries relating
to its sub-objects too. This is visible in the test_pg_dump test
case if one drops the extension at the end: the entry for
GRANT SELECT(col1) ON regress_pg_dump_table TO public;
was still present in pg_init_privs afterwards, although it was
pointing to a dangling table OID.
Noted while fooling with a fix for REASSIGN OWNED for pg_init_privs
entries. This bug is aboriginal in the pg_init_privs feature
though, and there seems no reason not to back-patch the fix.
-rw-r--r-- | src/backend/catalog/dependency.c | 21 | ||||
-rw-r--r-- | src/test/modules/test_pg_dump/expected/test_pg_dump.out | 7 | ||||
-rw-r--r-- | src/test/modules/test_pg_dump/sql/test_pg_dump.sql | 5 |
3 files changed, 27 insertions, 6 deletions
diff --git a/src/backend/catalog/dependency.c b/src/backend/catalog/dependency.c index 3d67525c7e0..ef7be47212a 100644 --- a/src/backend/catalog/dependency.c +++ b/src/backend/catalog/dependency.c @@ -1328,7 +1328,9 @@ deleteOneObject(const ObjectAddress *object, Relation *depRel, int flags) /* * Delete any comments, security labels, or initial privileges associated * with this object. (This is a convenient place to do these things, - * rather than having every object type know to do it.) + * rather than having every object type know to do it.) As above, all + * these functions must remove records for sub-objects too if the subid is + * zero. */ DeleteComments(object->objectId, object->classId, object->objectSubId); DeleteSecurityLabel(object); @@ -2887,6 +2889,7 @@ DeleteInitPrivs(const ObjectAddress *object) { Relation relation; ScanKeyData key[3]; + int nkeys; SysScanDesc scan; HeapTuple oldtuple; @@ -2900,13 +2903,19 @@ DeleteInitPrivs(const ObjectAddress *object) Anum_pg_init_privs_classoid, BTEqualStrategyNumber, F_OIDEQ, ObjectIdGetDatum(object->classId)); - ScanKeyInit(&key[2], - Anum_pg_init_privs_objsubid, - BTEqualStrategyNumber, F_INT4EQ, - Int32GetDatum(object->objectSubId)); + if (object->objectSubId != 0) + { + ScanKeyInit(&key[2], + Anum_pg_init_privs_objsubid, + BTEqualStrategyNumber, F_INT4EQ, + Int32GetDatum(object->objectSubId)); + nkeys = 3; + } + else + nkeys = 2; scan = systable_beginscan(relation, InitPrivsObjIndexId, true, - NULL, 3, key); + NULL, nkeys, key); while (HeapTupleIsValid(oldtuple = systable_getnext(scan))) CatalogTupleDelete(relation, &oldtuple->t_self); diff --git a/src/test/modules/test_pg_dump/expected/test_pg_dump.out b/src/test/modules/test_pg_dump/expected/test_pg_dump.out index a50eaf6125d..d53a60385c8 100644 --- a/src/test/modules/test_pg_dump/expected/test_pg_dump.out +++ b/src/test/modules/test_pg_dump/expected/test_pg_dump.out @@ -93,3 +93,10 @@ ALTER EXTENSION test_pg_dump DROP SERVER s0; ALTER EXTENSION test_pg_dump DROP TABLE test_pg_dump_t1; ALTER EXTENSION test_pg_dump DROP TYPE test_pg_dump_e1; ALTER EXTENSION test_pg_dump DROP VIEW test_pg_dump_v1; +DROP EXTENSION test_pg_dump; +-- shouldn't be anything left in pg_init_privs +SELECT * FROM pg_init_privs WHERE privtype = 'e'; + objoid | classoid | objsubid | privtype | initprivs +--------+----------+----------+----------+----------- +(0 rows) + diff --git a/src/test/modules/test_pg_dump/sql/test_pg_dump.sql b/src/test/modules/test_pg_dump/sql/test_pg_dump.sql index a61a7c8c4ce..7f2e7d32f6d 100644 --- a/src/test/modules/test_pg_dump/sql/test_pg_dump.sql +++ b/src/test/modules/test_pg_dump/sql/test_pg_dump.sql @@ -106,3 +106,8 @@ ALTER EXTENSION test_pg_dump DROP SERVER s0; ALTER EXTENSION test_pg_dump DROP TABLE test_pg_dump_t1; ALTER EXTENSION test_pg_dump DROP TYPE test_pg_dump_e1; ALTER EXTENSION test_pg_dump DROP VIEW test_pg_dump_v1; + +DROP EXTENSION test_pg_dump; + +-- shouldn't be anything left in pg_init_privs +SELECT * FROM pg_init_privs WHERE privtype = 'e'; |