This is an automated email from the ASF dual-hosted git repository.

reshke pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/cloudberry.git

commit 08910980be7268e77c21b81aa1eef1060f7e9b97
Author: Nathan Bossart <[email protected]>
AuthorDate: Mon Aug 10 06:38:25 2026 -0700

    Check for USAGE privilege on the composite type in ALTER TABLE OF.
    
    This omission allowed roles without USAGE on a type to create
    tables that depend on it, which could prevent the owner from
    changing the type later.
    
    Reported-by: Nathan Bossart <[email protected]>
    Author: Nathan Bossart <[email protected]>
    Reviewed-by: Robert Haas <[email protected]>
    Security: CVE-2026-6470
    Backpatch-through: 14
---
 src/backend/commands/tablecmds.c         | 5 +++++
 src/test/regress/expected/privileges.out | 6 ++++++
 src/test/regress/sql/privileges.sql      | 5 +++++
 3 files changed, 16 insertions(+)

diff --git a/src/backend/commands/tablecmds.c b/src/backend/commands/tablecmds.c
index b8b69336b89..53adcd73021 100644
--- a/src/backend/commands/tablecmds.c
+++ b/src/backend/commands/tablecmds.c
@@ -20376,6 +20376,7 @@ ATExecAddOf(Relation rel, const TypeName *ofTypename, 
LOCKMODE lockmode)
        ObjectAddress tableobj,
                                typeobj;
        HeapTuple       classtuple;
+       AclResult       aclresult;
 
        /* Validate the type. */
        typetuple = typenameType(NULL, ofTypename, NULL);
@@ -20383,6 +20384,10 @@ ATExecAddOf(Relation rel, const TypeName *ofTypename, 
LOCKMODE lockmode)
        typeform = (Form_pg_type) GETSTRUCT(typetuple);
        typeid = typeform->oid;
 
+       aclresult = object_aclcheck(TypeRelationId, typeid, GetUserId(), 
ACL_USAGE);
+       if (aclresult != ACLCHECK_OK)
+               aclcheck_error_type(aclresult, typeid);
+
        /* Fail if the table has any inheritance parents. */
        inheritsRelation = table_open(InheritsRelationId, AccessShareLock);
        ScanKeyInit(&key,
diff --git a/src/test/regress/expected/privileges.out 
b/src/test/regress/expected/privileges.out
index 82c4805d49b..b26f447b99e 100644
--- a/src/test/regress/expected/privileges.out
+++ b/src/test/regress/expected/privileges.out
@@ -1395,6 +1395,9 @@ CREATE TABLE test5a (a int, b priv_testdomain1);
 ERROR:  permission denied for type priv_testdomain1
 CREATE TABLE test6a OF priv_testtype1;
 ERROR:  permission denied for type priv_testtype1
+CREATE TABLE test6a2 (a int, b text);
+ALTER TABLE test6a2 OF priv_testtype1;
+ERROR:  permission denied for type priv_testtype1
 CREATE TABLE test10a (a int[], b priv_testtype1[]);
 ERROR:  permission denied for type priv_testtype1
 CREATE TABLE test9a (a int, b int);
@@ -1426,6 +1429,8 @@ CREATE FUNCTION priv_testfunc6b(b int) RETURNS 
priv_testdomain1 LANGUAGE SQL AS
 CREATE OPERATOR !! (PROCEDURE = priv_testfunc5b, RIGHTARG = priv_testdomain1);
 CREATE TABLE test5b (a int, b priv_testdomain1);
 CREATE TABLE test6b OF priv_testtype1;
+CREATE TABLE test6b2 (a int, b text);
+ALTER TABLE test6b2 OF priv_testtype1;
 CREATE TABLE test10b (a int[], b priv_testtype1[]);
 CREATE TABLE test9b (a int, b int);
 ALTER TABLE test9b ADD COLUMN c priv_testdomain1;
@@ -1446,6 +1451,7 @@ DROP FUNCTION priv_testfunc5b(a priv_testdomain1);
 DROP FUNCTION priv_testfunc6b(b int);
 DROP TABLE test5b;
 DROP TABLE test6b;
+DROP TABLE test6b2;
 DROP TABLE test9b;
 DROP TABLE test10b;
 DROP TYPE test7b;
diff --git a/src/test/regress/sql/privileges.sql 
b/src/test/regress/sql/privileges.sql
index d530d14fd8b..89a01ed421e 100644
--- a/src/test/regress/sql/privileges.sql
+++ b/src/test/regress/sql/privileges.sql
@@ -966,6 +966,8 @@ CREATE OPERATOR !+! (PROCEDURE = int4pl, LEFTARG = 
priv_testdomain1, RIGHTARG =
 
 CREATE TABLE test5a (a int, b priv_testdomain1);
 CREATE TABLE test6a OF priv_testtype1;
+CREATE TABLE test6a2 (a int, b text);
+ALTER TABLE test6a2 OF priv_testtype1;
 CREATE TABLE test10a (a int[], b priv_testtype1[]);
 
 CREATE TABLE test9a (a int, b int);
@@ -1001,6 +1003,8 @@ CREATE OPERATOR !! (PROCEDURE = priv_testfunc5b, RIGHTARG 
= priv_testdomain1);
 
 CREATE TABLE test5b (a int, b priv_testdomain1);
 CREATE TABLE test6b OF priv_testtype1;
+CREATE TABLE test6b2 (a int, b text);
+ALTER TABLE test6b2 OF priv_testtype1;
 CREATE TABLE test10b (a int[], b priv_testtype1[]);
 
 CREATE TABLE test9b (a int, b int);
@@ -1025,6 +1029,7 @@ DROP FUNCTION priv_testfunc5b(a priv_testdomain1);
 DROP FUNCTION priv_testfunc6b(b int);
 DROP TABLE test5b;
 DROP TABLE test6b;
+DROP TABLE test6b2;
 DROP TABLE test9b;
 DROP TABLE test10b;
 DROP TYPE test7b;


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to