PostgreSQL Source Code  git master
acl.h File Reference
#include "access/htup.h"
#include "nodes/parsenodes.h"
#include "parser/parse_node.h"
#include "utils/snapshot.h"
Include dependency graph for acl.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Data Structures

struct  AclItem
 

Macros

#define ACL_ID_PUBLIC   0 /* placeholder for id in a PUBLIC acl item */
 
#define ACLITEM_GET_PRIVS(item)   ((item).ai_privs & 0xFFFF)
 
#define ACLITEM_GET_GOPTIONS(item)   (((item).ai_privs >> 16) & 0xFFFF)
 
#define ACLITEM_GET_RIGHTS(item)   ((item).ai_privs)
 
#define ACL_GRANT_OPTION_FOR(privs)   (((AclMode) (privs) & 0xFFFF) << 16)
 
#define ACL_OPTION_TO_PRIVS(privs)   (((AclMode) (privs) >> 16) & 0xFFFF)
 
#define ACLITEM_SET_PRIVS(item, privs)
 
#define ACLITEM_SET_GOPTIONS(item, goptions)
 
#define ACLITEM_SET_RIGHTS(item, rights)    ((item).ai_privs = (AclMode) (rights))
 
#define ACLITEM_SET_PRIVS_GOPTIONS(item, privs, goptions)
 
#define ACLITEM_ALL_PRIV_BITS   ((AclMode) 0xFFFF)
 
#define ACLITEM_ALL_GOPTION_BITS   ((AclMode) 0xFFFF << 16)
 
#define ACL_NUM(ACL)   (ARR_DIMS(ACL)[0])
 
#define ACL_DAT(ACL)   ((AclItem *) ARR_DATA_PTR(ACL))
 
#define ACL_N_SIZE(N)   (ARR_OVERHEAD_NONULLS(1) + ((N) * sizeof(AclItem)))
 
#define ACL_SIZE(ACL)   ARR_SIZE(ACL)
 
#define DatumGetAclItemP(X)   ((AclItem *) DatumGetPointer(X))
 
#define PG_GETARG_ACLITEM_P(n)   DatumGetAclItemP(PG_GETARG_DATUM(n))
 
#define PG_RETURN_ACLITEM_P(x)   PG_RETURN_POINTER(x)
 
#define DatumGetAclP(X)   ((Acl *) PG_DETOAST_DATUM(X))
 
#define DatumGetAclPCopy(X)   ((Acl *) PG_DETOAST_DATUM_COPY(X))
 
#define PG_GETARG_ACL_P(n)   DatumGetAclP(PG_GETARG_DATUM(n))
 
#define PG_GETARG_ACL_P_COPY(n)   DatumGetAclPCopy(PG_GETARG_DATUM(n))
 
#define PG_RETURN_ACL_P(x)   PG_RETURN_POINTER(x)
 
#define ACL_MODECHG_ADD   1
 
#define ACL_MODECHG_DEL   2
 
#define ACL_MODECHG_EQL   3
 
#define ACL_INSERT_CHR   'a' /* formerly known as "append" */
 
#define ACL_SELECT_CHR   'r' /* formerly known as "read" */
 
#define ACL_UPDATE_CHR   'w' /* formerly known as "write" */
 
#define ACL_DELETE_CHR   'd'
 
#define ACL_TRUNCATE_CHR   'D' /* super-delete, as it were */
 
#define ACL_REFERENCES_CHR   'x'
 
#define ACL_TRIGGER_CHR   't'
 
#define ACL_EXECUTE_CHR   'X'
 
#define ACL_USAGE_CHR   'U'
 
#define ACL_CREATE_CHR   'C'
 
#define ACL_CREATE_TEMP_CHR   'T'
 
#define ACL_CONNECT_CHR   'c'
 
#define ACL_SET_CHR   's'
 
#define ACL_ALTER_SYSTEM_CHR   'A'
 
#define ACL_ALL_RIGHTS_STR   "arwdDxtXUCTcsA"
 
#define ACL_ALL_RIGHTS_COLUMN   (ACL_INSERT|ACL_SELECT|ACL_UPDATE|ACL_REFERENCES)
 
#define ACL_ALL_RIGHTS_RELATION   (ACL_INSERT|ACL_SELECT|ACL_UPDATE|ACL_DELETE|ACL_TRUNCATE|ACL_REFERENCES|ACL_TRIGGER)
 
#define ACL_ALL_RIGHTS_SEQUENCE   (ACL_USAGE|ACL_SELECT|ACL_UPDATE)
 
#define ACL_ALL_RIGHTS_DATABASE   (ACL_CREATE|ACL_CREATE_TEMP|ACL_CONNECT)
 
#define ACL_ALL_RIGHTS_FDW   (ACL_USAGE)
 
#define ACL_ALL_RIGHTS_FOREIGN_SERVER   (ACL_USAGE)
 
#define ACL_ALL_RIGHTS_FUNCTION   (ACL_EXECUTE)
 
#define ACL_ALL_RIGHTS_LANGUAGE   (ACL_USAGE)
 
#define ACL_ALL_RIGHTS_LARGEOBJECT   (ACL_SELECT|ACL_UPDATE)
 
#define ACL_ALL_RIGHTS_PARAMETER_ACL   (ACL_SET|ACL_ALTER_SYSTEM)
 
#define ACL_ALL_RIGHTS_SCHEMA   (ACL_USAGE|ACL_CREATE)
 
#define ACL_ALL_RIGHTS_TABLESPACE   (ACL_CREATE)
 
#define ACL_ALL_RIGHTS_TYPE   (ACL_USAGE)
 

Typedefs

typedef struct AclItem AclItem
 
typedef struct ArrayType Acl
 

Enumerations

enum  AclMaskHow { ACLMASK_ALL , ACLMASK_ANY }
 
enum  AclResult { ACLCHECK_OK = 0 , ACLCHECK_NO_PRIV , ACLCHECK_NOT_OWNER }
 

Functions

Aclacldefault (ObjectType objtype, Oid ownerId)
 
Aclget_user_default_acl (ObjectType objtype, Oid ownerId, Oid nsp_oid)
 
void recordDependencyOnNewAcl (Oid classId, Oid objectId, int32 objsubId, Oid ownerId, Acl *acl)
 
Aclaclupdate (const Acl *old_acl, const AclItem *mod_aip, int modechg, Oid ownerId, DropBehavior behavior)
 
Aclaclnewowner (const Acl *old_acl, Oid oldOwnerId, Oid newOwnerId)
 
Aclmake_empty_acl (void)
 
Aclaclcopy (const Acl *orig_acl)
 
Aclaclconcat (const Acl *left_acl, const Acl *right_acl)
 
Aclaclmerge (const Acl *left_acl, const Acl *right_acl, Oid ownerId)
 
void aclitemsort (Acl *acl)
 
bool aclequal (const Acl *left_acl, const Acl *right_acl)
 
AclMode aclmask (const Acl *acl, Oid roleid, Oid ownerId, AclMode mask, AclMaskHow how)
 
int aclmembers (const Acl *acl, Oid **roleids)
 
bool has_privs_of_role (Oid member, Oid role)
 
bool is_member_of_role (Oid member, Oid role)
 
bool is_member_of_role_nosuper (Oid member, Oid role)
 
bool is_admin_of_role (Oid member, Oid role)
 
void check_is_member_of_role (Oid member, Oid role)
 
Oid get_role_oid (const char *rolename, bool missing_ok)
 
Oid get_role_oid_or_public (const char *rolename)
 
Oid get_rolespec_oid (const RoleSpec *role, bool missing_ok)
 
void check_rolespec_name (const RoleSpec *role, const char *detail_msg)
 
HeapTuple get_rolespec_tuple (const RoleSpec *role)
 
char * get_rolespec_name (const RoleSpec *role)
 
void select_best_grantor (Oid roleId, AclMode privileges, const Acl *acl, Oid ownerId, Oid *grantorId, AclMode *grantOptions)
 
void initialize_acl (void)
 
void ExecuteGrantStmt (GrantStmt *stmt)
 
void ExecAlterDefaultPrivilegesStmt (ParseState *pstate, AlterDefaultPrivilegesStmt *stmt)
 
void RemoveRoleFromObjectACL (Oid roleid, Oid classid, Oid objid)
 
AclMode pg_attribute_aclmask (Oid table_oid, AttrNumber attnum, Oid roleid, AclMode mask, AclMaskHow how)
 
AclMode pg_attribute_aclmask_ext (Oid table_oid, AttrNumber attnum, Oid roleid, AclMode mask, AclMaskHow how, bool *is_missing)
 
AclMode pg_class_aclmask (Oid table_oid, Oid roleid, AclMode mask, AclMaskHow how)
 
AclMode pg_class_aclmask_ext (Oid table_oid, Oid roleid, AclMode mask, AclMaskHow how, bool *is_missing)
 
AclMode pg_database_aclmask (Oid db_oid, Oid roleid, AclMode mask, AclMaskHow how)
 
AclMode pg_parameter_aclmask (const char *name, Oid roleid, AclMode mask, AclMaskHow how)
 
AclMode pg_parameter_acl_aclmask (Oid acl_oid, Oid roleid, AclMode mask, AclMaskHow how)
 
AclMode pg_proc_aclmask (Oid proc_oid, Oid roleid, AclMode mask, AclMaskHow how)
 
AclMode pg_language_aclmask (Oid lang_oid, Oid roleid, AclMode mask, AclMaskHow how)
 
AclMode pg_largeobject_aclmask_snapshot (Oid lobj_oid, Oid roleid, AclMode mask, AclMaskHow how, Snapshot snapshot)
 
AclMode pg_namespace_aclmask (Oid nsp_oid, Oid roleid, AclMode mask, AclMaskHow how)
 
AclMode pg_tablespace_aclmask (Oid spc_oid, Oid roleid, AclMode mask, AclMaskHow how)
 
AclMode pg_foreign_data_wrapper_aclmask (Oid fdw_oid, Oid roleid, AclMode mask, AclMaskHow how)
 
AclMode pg_foreign_server_aclmask (Oid srv_oid, Oid roleid, AclMode mask, AclMaskHow how)
 
AclMode pg_type_aclmask (Oid type_oid, Oid roleid, AclMode mask, AclMaskHow how)
 
AclResult pg_attribute_aclcheck (Oid table_oid, AttrNumber attnum, Oid roleid, AclMode mode)
 
AclResult pg_attribute_aclcheck_ext (Oid table_oid, AttrNumber attnum, Oid roleid, AclMode mode, bool *is_missing)
 
AclResult pg_attribute_aclcheck_all (Oid table_oid, Oid roleid, AclMode mode, AclMaskHow how)
 
AclResult pg_class_aclcheck (Oid table_oid, Oid roleid, AclMode mode)
 
AclResult pg_class_aclcheck_ext (Oid table_oid, Oid roleid, AclMode mode, bool *is_missing)
 
AclResult pg_database_aclcheck (Oid db_oid, Oid roleid, AclMode mode)
 
AclResult pg_parameter_aclcheck (const char *name, Oid roleid, AclMode mode)
 
AclResult pg_parameter_acl_aclcheck (Oid acl_oid, Oid roleid, AclMode mode)
 
AclResult pg_proc_aclcheck (Oid proc_oid, Oid roleid, AclMode mode)
 
AclResult pg_language_aclcheck (Oid lang_oid, Oid roleid, AclMode mode)
 
AclResult pg_largeobject_aclcheck_snapshot (Oid lang_oid, Oid roleid, AclMode mode, Snapshot snapshot)
 
AclResult pg_namespace_aclcheck (Oid nsp_oid, Oid roleid, AclMode mode)
 
AclResult pg_tablespace_aclcheck (Oid spc_oid, Oid roleid, AclMode mode)
 
AclResult pg_foreign_data_wrapper_aclcheck (Oid fdw_oid, Oid roleid, AclMode mode)
 
AclResult pg_foreign_server_aclcheck (Oid srv_oid, Oid roleid, AclMode mode)
 
AclResult pg_type_aclcheck (Oid type_oid, Oid roleid, AclMode mode)
 
void aclcheck_error (AclResult aclerr, ObjectType objtype, const char *objectname)
 
void aclcheck_error_col (AclResult aclerr, ObjectType objtype, const char *objectname, const char *colname)
 
void aclcheck_error_type (AclResult aclerr, Oid typeOid)
 
void recordExtObjInitPriv (Oid objoid, Oid classoid)
 
void removeExtObjInitPriv (Oid objoid, Oid classoid)
 
bool pg_class_ownercheck (Oid class_oid, Oid roleid)
 
bool pg_type_ownercheck (Oid type_oid, Oid roleid)
 
bool pg_oper_ownercheck (Oid oper_oid, Oid roleid)
 
bool pg_proc_ownercheck (Oid proc_oid, Oid roleid)
 
bool pg_language_ownercheck (Oid lan_oid, Oid roleid)
 
bool pg_largeobject_ownercheck (Oid lobj_oid, Oid roleid)
 
bool pg_namespace_ownercheck (Oid nsp_oid, Oid roleid)
 
bool pg_tablespace_ownercheck (Oid spc_oid, Oid roleid)
 
bool pg_opclass_ownercheck (Oid opc_oid, Oid roleid)
 
bool pg_opfamily_ownercheck (Oid opf_oid, Oid roleid)
 
bool pg_database_ownercheck (Oid db_oid, Oid roleid)
 
bool pg_collation_ownercheck (Oid coll_oid, Oid roleid)
 
bool pg_conversion_ownercheck (Oid conv_oid, Oid roleid)
 
bool pg_ts_dict_ownercheck (Oid dict_oid, Oid roleid)
 
bool pg_ts_config_ownercheck (Oid cfg_oid, Oid roleid)
 
bool pg_foreign_data_wrapper_ownercheck (Oid srv_oid, Oid roleid)
 
bool pg_foreign_server_ownercheck (Oid srv_oid, Oid roleid)
 
bool pg_event_trigger_ownercheck (Oid et_oid, Oid roleid)
 
bool pg_extension_ownercheck (Oid ext_oid, Oid roleid)
 
bool pg_publication_ownercheck (Oid pub_oid, Oid roleid)
 
bool pg_subscription_ownercheck (Oid sub_oid, Oid roleid)
 
bool pg_statistics_object_ownercheck (Oid stat_oid, Oid roleid)
 
bool has_createrole_privilege (Oid roleid)
 
bool has_bypassrls_privilege (Oid roleid)
 

Macro Definition Documentation

◆ ACL_ALL_RIGHTS_COLUMN

#define ACL_ALL_RIGHTS_COLUMN   (ACL_INSERT|ACL_SELECT|ACL_UPDATE|ACL_REFERENCES)

Definition at line 158 of file acl.h.

◆ ACL_ALL_RIGHTS_DATABASE

#define ACL_ALL_RIGHTS_DATABASE   (ACL_CREATE|ACL_CREATE_TEMP|ACL_CONNECT)

Definition at line 161 of file acl.h.

◆ ACL_ALL_RIGHTS_FDW

#define ACL_ALL_RIGHTS_FDW   (ACL_USAGE)

Definition at line 162 of file acl.h.

◆ ACL_ALL_RIGHTS_FOREIGN_SERVER

#define ACL_ALL_RIGHTS_FOREIGN_SERVER   (ACL_USAGE)

Definition at line 163 of file acl.h.

◆ ACL_ALL_RIGHTS_FUNCTION

#define ACL_ALL_RIGHTS_FUNCTION   (ACL_EXECUTE)

Definition at line 164 of file acl.h.

◆ ACL_ALL_RIGHTS_LANGUAGE

#define ACL_ALL_RIGHTS_LANGUAGE   (ACL_USAGE)

Definition at line 165 of file acl.h.

◆ ACL_ALL_RIGHTS_LARGEOBJECT

#define ACL_ALL_RIGHTS_LARGEOBJECT   (ACL_SELECT|ACL_UPDATE)

Definition at line 166 of file acl.h.

◆ ACL_ALL_RIGHTS_PARAMETER_ACL

#define ACL_ALL_RIGHTS_PARAMETER_ACL   (ACL_SET|ACL_ALTER_SYSTEM)

Definition at line 167 of file acl.h.

◆ ACL_ALL_RIGHTS_RELATION

Definition at line 159 of file acl.h.

◆ ACL_ALL_RIGHTS_SCHEMA

#define ACL_ALL_RIGHTS_SCHEMA   (ACL_USAGE|ACL_CREATE)

Definition at line 168 of file acl.h.

◆ ACL_ALL_RIGHTS_SEQUENCE

#define ACL_ALL_RIGHTS_SEQUENCE   (ACL_USAGE|ACL_SELECT|ACL_UPDATE)

Definition at line 160 of file acl.h.

◆ ACL_ALL_RIGHTS_STR

#define ACL_ALL_RIGHTS_STR   "arwdDxtXUCTcsA"

Definition at line 153 of file acl.h.

◆ ACL_ALL_RIGHTS_TABLESPACE

#define ACL_ALL_RIGHTS_TABLESPACE   (ACL_CREATE)

Definition at line 169 of file acl.h.

◆ ACL_ALL_RIGHTS_TYPE

#define ACL_ALL_RIGHTS_TYPE   (ACL_USAGE)

Definition at line 170 of file acl.h.

◆ ACL_ALTER_SYSTEM_CHR

#define ACL_ALTER_SYSTEM_CHR   'A'

Definition at line 150 of file acl.h.

◆ ACL_CONNECT_CHR

#define ACL_CONNECT_CHR   'c'

Definition at line 148 of file acl.h.

◆ ACL_CREATE_CHR

#define ACL_CREATE_CHR   'C'

Definition at line 146 of file acl.h.

◆ ACL_CREATE_TEMP_CHR

#define ACL_CREATE_TEMP_CHR   'T'

Definition at line 147 of file acl.h.

◆ ACL_DAT

#define ACL_DAT (   ACL)    ((AclItem *) ARR_DATA_PTR(ACL))

Definition at line 109 of file acl.h.

◆ ACL_DELETE_CHR

#define ACL_DELETE_CHR   'd'

Definition at line 140 of file acl.h.

◆ ACL_EXECUTE_CHR

#define ACL_EXECUTE_CHR   'X'

Definition at line 144 of file acl.h.

◆ ACL_GRANT_OPTION_FOR

#define ACL_GRANT_OPTION_FOR (   privs)    (((AclMode) (privs) & 0xFFFF) << 16)

Definition at line 70 of file acl.h.

◆ ACL_ID_PUBLIC

#define ACL_ID_PUBLIC   0 /* placeholder for id in a PUBLIC acl item */

Definition at line 46 of file acl.h.

◆ ACL_INSERT_CHR

#define ACL_INSERT_CHR   'a' /* formerly known as "append" */

Definition at line 137 of file acl.h.

◆ ACL_MODECHG_ADD

#define ACL_MODECHG_ADD   1

Definition at line 129 of file acl.h.

◆ ACL_MODECHG_DEL

#define ACL_MODECHG_DEL   2

Definition at line 130 of file acl.h.

◆ ACL_MODECHG_EQL

#define ACL_MODECHG_EQL   3

Definition at line 131 of file acl.h.

◆ ACL_N_SIZE

#define ACL_N_SIZE (   N)    (ARR_OVERHEAD_NONULLS(1) + ((N) * sizeof(AclItem)))

Definition at line 110 of file acl.h.

◆ ACL_NUM

#define ACL_NUM (   ACL)    (ARR_DIMS(ACL)[0])

Definition at line 108 of file acl.h.

◆ ACL_OPTION_TO_PRIVS

#define ACL_OPTION_TO_PRIVS (   privs)    (((AclMode) (privs) >> 16) & 0xFFFF)

Definition at line 71 of file acl.h.

◆ ACL_REFERENCES_CHR

#define ACL_REFERENCES_CHR   'x'

Definition at line 142 of file acl.h.

◆ ACL_SELECT_CHR

#define ACL_SELECT_CHR   'r' /* formerly known as "read" */

Definition at line 138 of file acl.h.

◆ ACL_SET_CHR

#define ACL_SET_CHR   's'

Definition at line 149 of file acl.h.

◆ ACL_SIZE

#define ACL_SIZE (   ACL)    ARR_SIZE(ACL)

Definition at line 111 of file acl.h.

◆ ACL_TRIGGER_CHR

#define ACL_TRIGGER_CHR   't'

Definition at line 143 of file acl.h.

◆ ACL_TRUNCATE_CHR

#define ACL_TRUNCATE_CHR   'D' /* super-delete, as it were */

Definition at line 141 of file acl.h.

◆ ACL_UPDATE_CHR

#define ACL_UPDATE_CHR   'w' /* formerly known as "write" */

Definition at line 139 of file acl.h.

◆ ACL_USAGE_CHR

#define ACL_USAGE_CHR   'U'

Definition at line 145 of file acl.h.

◆ ACLITEM_ALL_GOPTION_BITS

#define ACLITEM_ALL_GOPTION_BITS   ((AclMode) 0xFFFF << 16)

Definition at line 88 of file acl.h.

◆ ACLITEM_ALL_PRIV_BITS

#define ACLITEM_ALL_PRIV_BITS   ((AclMode) 0xFFFF)

Definition at line 87 of file acl.h.

◆ ACLITEM_GET_GOPTIONS

#define ACLITEM_GET_GOPTIONS (   item)    (((item).ai_privs >> 16) & 0xFFFF)

Definition at line 67 of file acl.h.

◆ ACLITEM_GET_PRIVS

#define ACLITEM_GET_PRIVS (   item)    ((item).ai_privs & 0xFFFF)

Definition at line 66 of file acl.h.

◆ ACLITEM_GET_RIGHTS

#define ACLITEM_GET_RIGHTS (   item)    ((item).ai_privs)

Definition at line 68 of file acl.h.

◆ ACLITEM_SET_GOPTIONS

#define ACLITEM_SET_GOPTIONS (   item,
  goptions 
)
Value:
((item).ai_privs = ((item).ai_privs & ~(((AclMode) 0xFFFF) << 16)) | \
(((AclMode) (goptions) & 0xFFFF) << 16))
uint32 AclMode
Definition: parsenodes.h:80

Definition at line 76 of file acl.h.

◆ ACLITEM_SET_PRIVS

#define ACLITEM_SET_PRIVS (   item,
  privs 
)
Value:
((item).ai_privs = ((item).ai_privs & ~((AclMode) 0xFFFF)) | \
((AclMode) (privs) & 0xFFFF))

Definition at line 73 of file acl.h.

◆ ACLITEM_SET_PRIVS_GOPTIONS

#define ACLITEM_SET_PRIVS_GOPTIONS (   item,
  privs,
  goptions 
)
Value:
((item).ai_privs = ((AclMode) (privs) & 0xFFFF) | \
(((AclMode) (goptions) & 0xFFFF) << 16))

Definition at line 82 of file acl.h.

◆ ACLITEM_SET_RIGHTS

#define ACLITEM_SET_RIGHTS (   item,
  rights 
)     ((item).ai_privs = (AclMode) (rights))

Definition at line 79 of file acl.h.

◆ DatumGetAclItemP

#define DatumGetAclItemP (   X)    ((AclItem *) DatumGetPointer(X))

Definition at line 116 of file acl.h.

◆ DatumGetAclP

#define DatumGetAclP (   X)    ((Acl *) PG_DETOAST_DATUM(X))

Definition at line 120 of file acl.h.

◆ DatumGetAclPCopy

#define DatumGetAclPCopy (   X)    ((Acl *) PG_DETOAST_DATUM_COPY(X))

Definition at line 121 of file acl.h.

◆ PG_GETARG_ACL_P

#define PG_GETARG_ACL_P (   n)    DatumGetAclP(PG_GETARG_DATUM(n))

Definition at line 122 of file acl.h.

◆ PG_GETARG_ACL_P_COPY

#define PG_GETARG_ACL_P_COPY (   n)    DatumGetAclPCopy(PG_GETARG_DATUM(n))

Definition at line 123 of file acl.h.

◆ PG_GETARG_ACLITEM_P

#define PG_GETARG_ACLITEM_P (   n)    DatumGetAclItemP(PG_GETARG_DATUM(n))

Definition at line 117 of file acl.h.

◆ PG_RETURN_ACL_P

#define PG_RETURN_ACL_P (   x)    PG_RETURN_POINTER(x)

Definition at line 124 of file acl.h.

◆ PG_RETURN_ACLITEM_P

#define PG_RETURN_ACLITEM_P (   x)    PG_RETURN_POINTER(x)

Definition at line 118 of file acl.h.

Typedef Documentation

◆ Acl

typedef struct ArrayType Acl

Definition at line 1 of file acl.h.

◆ AclItem

typedef struct AclItem AclItem

Enumeration Type Documentation

◆ AclMaskHow

enum AclMaskHow
Enumerator
ACLMASK_ALL 
ACLMASK_ANY 

Definition at line 173 of file acl.h.

174 {
175  ACLMASK_ALL, /* normal case: compute all bits */
176  ACLMASK_ANY /* return when result is known nonzero */
177 } AclMaskHow;
AclMaskHow
Definition: acl.h:174
@ ACLMASK_ANY
Definition: acl.h:176
@ ACLMASK_ALL
Definition: acl.h:175

◆ AclResult

enum AclResult
Enumerator
ACLCHECK_OK 
ACLCHECK_NO_PRIV 
ACLCHECK_NOT_OWNER 

Definition at line 180 of file acl.h.

181 {
182  ACLCHECK_OK = 0,
185 } AclResult;
AclResult
Definition: acl.h:181
@ ACLCHECK_NO_PRIV
Definition: acl.h:183
@ ACLCHECK_OK
Definition: acl.h:182
@ ACLCHECK_NOT_OWNER
Definition: acl.h:184

Function Documentation

◆ aclcheck_error()

void aclcheck_error ( AclResult  aclerr,
ObjectType  objtype,
const char *  objectname 
)

Definition at line 3512 of file aclchk.c.

3514 {
3515  switch (aclerr)
3516  {
3517  case ACLCHECK_OK:
3518  /* no error, so return to caller */
3519  break;
3520  case ACLCHECK_NO_PRIV:
3521  {
3522  const char *msg = "???";
3523 
3524  switch (objtype)
3525  {
3526  case OBJECT_AGGREGATE:
3527  msg = gettext_noop("permission denied for aggregate %s");
3528  break;
3529  case OBJECT_COLLATION:
3530  msg = gettext_noop("permission denied for collation %s");
3531  break;
3532  case OBJECT_COLUMN:
3533  msg = gettext_noop("permission denied for column %s");
3534  break;
3535  case OBJECT_CONVERSION:
3536  msg = gettext_noop("permission denied for conversion %s");
3537  break;
3538  case OBJECT_DATABASE:
3539  msg = gettext_noop("permission denied for database %s");
3540  break;
3541  case OBJECT_DOMAIN:
3542  msg = gettext_noop("permission denied for domain %s");
3543  break;
3544  case OBJECT_EVENT_TRIGGER:
3545  msg = gettext_noop("permission denied for event trigger %s");
3546  break;
3547  case OBJECT_EXTENSION:
3548  msg = gettext_noop("permission denied for extension %s");
3549  break;
3550  case OBJECT_FDW:
3551  msg = gettext_noop("permission denied for foreign-data wrapper %s");
3552  break;
3553  case OBJECT_FOREIGN_SERVER:
3554  msg = gettext_noop("permission denied for foreign server %s");
3555  break;
3556  case OBJECT_FOREIGN_TABLE:
3557  msg = gettext_noop("permission denied for foreign table %s");
3558  break;
3559  case OBJECT_FUNCTION:
3560  msg = gettext_noop("permission denied for function %s");
3561  break;
3562  case OBJECT_INDEX:
3563  msg = gettext_noop("permission denied for index %s");
3564  break;
3565  case OBJECT_LANGUAGE:
3566  msg = gettext_noop("permission denied for language %s");
3567  break;
3568  case OBJECT_LARGEOBJECT:
3569  msg = gettext_noop("permission denied for large object %s");
3570  break;
3571  case OBJECT_MATVIEW:
3572  msg = gettext_noop("permission denied for materialized view %s");
3573  break;
3574  case OBJECT_OPCLASS:
3575  msg = gettext_noop("permission denied for operator class %s");
3576  break;
3577  case OBJECT_OPERATOR:
3578  msg = gettext_noop("permission denied for operator %s");
3579  break;
3580  case OBJECT_OPFAMILY:
3581  msg = gettext_noop("permission denied for operator family %s");
3582  break;
3583  case OBJECT_PARAMETER_ACL:
3584  msg = gettext_noop("permission denied for parameter %s");
3585  break;
3586  case OBJECT_POLICY:
3587  msg = gettext_noop("permission denied for policy %s");
3588  break;
3589  case OBJECT_PROCEDURE:
3590  msg = gettext_noop("permission denied for procedure %s");
3591  break;
3592  case OBJECT_PUBLICATION:
3593  msg = gettext_noop("permission denied for publication %s");
3594  break;
3595  case OBJECT_ROUTINE:
3596  msg = gettext_noop("permission denied for routine %s");
3597  break;
3598  case OBJECT_SCHEMA:
3599  msg = gettext_noop("permission denied for schema %s");
3600  break;
3601  case OBJECT_SEQUENCE:
3602  msg = gettext_noop("permission denied for sequence %s");
3603  break;
3604  case OBJECT_STATISTIC_EXT:
3605  msg = gettext_noop("permission denied for statistics object %s");
3606  break;
3607  case OBJECT_SUBSCRIPTION:
3608  msg = gettext_noop("permission denied for subscription %s");
3609  break;
3610  case OBJECT_TABLE:
3611  msg = gettext_noop("permission denied for table %s");
3612  break;
3613  case OBJECT_TABLESPACE:
3614  msg = gettext_noop("permission denied for tablespace %s");
3615  break;
3617  msg = gettext_noop("permission denied for text search configuration %s");
3618  break;
3619  case OBJECT_TSDICTIONARY:
3620  msg = gettext_noop("permission denied for text search dictionary %s");
3621  break;
3622  case OBJECT_TYPE:
3623  msg = gettext_noop("permission denied for type %s");
3624  break;
3625  case OBJECT_VIEW:
3626  msg = gettext_noop("permission denied for view %s");
3627  break;
3628  /* these currently aren't used */
3629  case OBJECT_ACCESS_METHOD:
3630  case OBJECT_AMOP:
3631  case OBJECT_AMPROC:
3632  case OBJECT_ATTRIBUTE:
3633  case OBJECT_CAST:
3634  case OBJECT_DEFAULT:
3635  case OBJECT_DEFACL:
3636  case OBJECT_DOMCONSTRAINT:
3639  case OBJECT_ROLE:
3640  case OBJECT_RULE:
3641  case OBJECT_TABCONSTRAINT:
3642  case OBJECT_TRANSFORM:
3643  case OBJECT_TRIGGER:
3644  case OBJECT_TSPARSER:
3645  case OBJECT_TSTEMPLATE:
3646  case OBJECT_USER_MAPPING:
3647  elog(ERROR, "unsupported object type %d", objtype);
3648  }
3649 
3650  ereport(ERROR,
3651  (errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
3652  errmsg(msg, objectname)));
3653  break;
3654  }
3655  case ACLCHECK_NOT_OWNER:
3656  {
3657  const char *msg = "???";
3658 
3659  switch (objtype)
3660  {
3661  case OBJECT_AGGREGATE:
3662  msg = gettext_noop("must be owner of aggregate %s");
3663  break;
3664  case OBJECT_COLLATION:
3665  msg = gettext_noop("must be owner of collation %s");
3666  break;
3667  case OBJECT_CONVERSION:
3668  msg = gettext_noop("must be owner of conversion %s");
3669  break;
3670  case OBJECT_DATABASE:
3671  msg = gettext_noop("must be owner of database %s");
3672  break;
3673  case OBJECT_DOMAIN:
3674  msg = gettext_noop("must be owner of domain %s");
3675  break;
3676  case OBJECT_EVENT_TRIGGER:
3677  msg = gettext_noop("must be owner of event trigger %s");
3678  break;
3679  case OBJECT_EXTENSION:
3680  msg = gettext_noop("must be owner of extension %s");
3681  break;
3682  case OBJECT_FDW:
3683  msg = gettext_noop("must be owner of foreign-data wrapper %s");
3684  break;
3685  case OBJECT_FOREIGN_SERVER:
3686  msg = gettext_noop("must be owner of foreign server %s");
3687  break;
3688  case OBJECT_FOREIGN_TABLE:
3689  msg = gettext_noop("must be owner of foreign table %s");
3690  break;
3691  case OBJECT_FUNCTION:
3692  msg = gettext_noop("must be owner of function %s");
3693  break;
3694  case OBJECT_INDEX:
3695  msg = gettext_noop("must be owner of index %s");
3696  break;
3697  case OBJECT_LANGUAGE:
3698  msg = gettext_noop("must be owner of language %s");
3699  break;
3700  case OBJECT_LARGEOBJECT:
3701  msg = gettext_noop("must be owner of large object %s");
3702  break;
3703  case OBJECT_MATVIEW:
3704  msg = gettext_noop("must be owner of materialized view %s");
3705  break;
3706  case OBJECT_OPCLASS:
3707  msg = gettext_noop("must be owner of operator class %s");
3708  break;
3709  case OBJECT_OPERATOR:
3710  msg = gettext_noop("must be owner of operator %s");
3711  break;
3712  case OBJECT_OPFAMILY:
3713  msg = gettext_noop("must be owner of operator family %s");
3714  break;
3715  case OBJECT_PROCEDURE:
3716  msg = gettext_noop("must be owner of procedure %s");
3717  break;
3718  case OBJECT_PUBLICATION:
3719  msg = gettext_noop("must be owner of publication %s");
3720  break;
3721  case OBJECT_ROUTINE:
3722  msg = gettext_noop("must be owner of routine %s");
3723  break;
3724  case OBJECT_SEQUENCE:
3725  msg = gettext_noop("must be owner of sequence %s");
3726  break;
3727  case OBJECT_SUBSCRIPTION:
3728  msg = gettext_noop("must be owner of subscription %s");
3729  break;
3730  case OBJECT_TABLE:
3731  msg = gettext_noop("must be owner of table %s");
3732  break;
3733  case OBJECT_TYPE:
3734  msg = gettext_noop("must be owner of type %s");
3735  break;
3736  case OBJECT_VIEW:
3737  msg = gettext_noop("must be owner of view %s");
3738  break;
3739  case OBJECT_SCHEMA:
3740  msg = gettext_noop("must be owner of schema %s");
3741  break;
3742  case OBJECT_STATISTIC_EXT:
3743  msg = gettext_noop("must be owner of statistics object %s");
3744  break;
3745  case OBJECT_TABLESPACE:
3746  msg = gettext_noop("must be owner of tablespace %s");
3747  break;
3749  msg = gettext_noop("must be owner of text search configuration %s");
3750  break;
3751  case OBJECT_TSDICTIONARY:
3752  msg = gettext_noop("must be owner of text search dictionary %s");
3753  break;
3754 
3755  /*
3756  * Special cases: For these, the error message talks
3757  * about "relation", because that's where the
3758  * ownership is attached. See also
3759  * check_object_ownership().
3760  */
3761  case OBJECT_COLUMN:
3762  case OBJECT_POLICY:
3763  case OBJECT_RULE:
3764  case OBJECT_TABCONSTRAINT:
3765  case OBJECT_TRIGGER:
3766  msg = gettext_noop("must be owner of relation %s");
3767  break;
3768  /* these currently aren't used */
3769  case OBJECT_ACCESS_METHOD:
3770  case OBJECT_AMOP:
3771  case OBJECT_AMPROC:
3772  case OBJECT_ATTRIBUTE:
3773  case OBJECT_CAST:
3774  case OBJECT_DEFAULT:
3775  case OBJECT_DEFACL:
3776  case OBJECT_DOMCONSTRAINT:
3777  case OBJECT_PARAMETER_ACL:
3780  case OBJECT_ROLE:
3781  case OBJECT_TRANSFORM:
3782  case OBJECT_TSPARSER:
3783  case OBJECT_TSTEMPLATE:
3784  case OBJECT_USER_MAPPING:
3785  elog(ERROR, "unsupported object type %d", objtype);
3786  }
3787 
3788  ereport(ERROR,
3789  (errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
3790  errmsg(msg, objectname)));
3791  break;
3792  }
3793  default:
3794  elog(ERROR, "unrecognized AclResult: %d", (int) aclerr);
3795  break;
3796  }
3797 }
#define gettext_noop(x)
Definition: c.h:1205
int errcode(int sqlerrcode)
Definition: elog.c:693
int errmsg(const char *fmt,...)
Definition: elog.c:904
#define ERROR
Definition: elog.h:33
#define ereport(elevel,...)
Definition: elog.h:143
@ OBJECT_EVENT_TRIGGER
Definition: parsenodes.h:2149
@ OBJECT_FDW
Definition: parsenodes.h:2151
@ OBJECT_TSPARSER
Definition: parsenodes.h:2182
@ OBJECT_COLLATION
Definition: parsenodes.h:2142
@ OBJECT_USER_MAPPING
Definition: parsenodes.h:2185
@ OBJECT_ACCESS_METHOD
Definition: parsenodes.h:2135
@ OBJECT_OPCLASS
Definition: parsenodes.h:2159
@ OBJECT_DEFACL
Definition: parsenodes.h:2146
@ OBJECT_AGGREGATE
Definition: parsenodes.h:2136
@ OBJECT_MATVIEW
Definition: parsenodes.h:2158
@ OBJECT_SCHEMA
Definition: parsenodes.h:2171
@ OBJECT_POLICY
Definition: parsenodes.h:2163
@ OBJECT_OPERATOR
Definition: parsenodes.h:2160
@ OBJECT_FOREIGN_TABLE
Definition: parsenodes.h:2153
@ OBJECT_TSCONFIGURATION
Definition: parsenodes.h:2180
@ OBJECT_OPFAMILY
Definition: parsenodes.h:2161
@ OBJECT_DOMAIN
Definition: parsenodes.h:2147
@ OBJECT_COLUMN
Definition: parsenodes.h:2141
@ OBJECT_TABLESPACE
Definition: parsenodes.h:2177
@ OBJECT_ROLE
Definition: parsenodes.h:2168
@ OBJECT_ROUTINE
Definition: parsenodes.h:2169
@ OBJECT_LARGEOBJECT
Definition: parsenodes.h:2157
@ OBJECT_PUBLICATION_NAMESPACE
Definition: parsenodes.h:2166
@ OBJECT_PROCEDURE
Definition: parsenodes.h:2164
@ OBJECT_EXTENSION
Definition: parsenodes.h:2150
@ OBJECT_INDEX
Definition: parsenodes.h:2155
@ OBJECT_DEFAULT
Definition: parsenodes.h:2145
@ OBJECT_DATABASE
Definition: parsenodes.h:2144
@ OBJECT_SEQUENCE
Definition: parsenodes.h:2172
@ OBJECT_TSTEMPLATE
Definition: parsenodes.h:2183
@ OBJECT_LANGUAGE
Definition: parsenodes.h:2156
@ OBJECT_AMOP
Definition: parsenodes.h:2137
@ OBJECT_PUBLICATION_REL
Definition: parsenodes.h:2167
@ OBJECT_FOREIGN_SERVER
Definition: parsenodes.h:2152
@ OBJECT_TSDICTIONARY
Definition: parsenodes.h:2181
@ OBJECT_ATTRIBUTE
Definition: parsenodes.h:2139
@ OBJECT_PUBLICATION
Definition: parsenodes.h:2165
@ OBJECT_RULE
Definition: parsenodes.h:2170
@ OBJECT_CONVERSION
Definition: parsenodes.h:2143
@ OBJECT_AMPROC
Definition: parsenodes.h:2138
@ OBJECT_TABLE
Definition: parsenodes.h:2176
@ OBJECT_VIEW
Definition: parsenodes.h:2186
@ OBJECT_PARAMETER_ACL
Definition: parsenodes.h:2162
@ OBJECT_TYPE
Definition: parsenodes.h:2184
@ OBJECT_FUNCTION
Definition: parsenodes.h:2154
@ OBJECT_TABCONSTRAINT
Definition: parsenodes.h:2175
@ OBJECT_DOMCONSTRAINT
Definition: parsenodes.h:2148
@ OBJECT_SUBSCRIPTION
Definition: parsenodes.h:2173
@ OBJECT_STATISTIC_EXT
Definition: parsenodes.h:2174
@ OBJECT_CAST
Definition: parsenodes.h:2140
@ OBJECT_TRIGGER
Definition: parsenodes.h:2179
@ OBJECT_TRANSFORM
Definition: parsenodes.h:2178

References ACLCHECK_NO_PRIV, ACLCHECK_NOT_OWNER, ACLCHECK_OK, elog(), ereport, errcode(), errmsg(), ERROR, gettext_noop, OBJECT_ACCESS_METHOD, OBJECT_AGGREGATE, OBJECT_AMOP, OBJECT_AMPROC, OBJECT_ATTRIBUTE, OBJECT_CAST, OBJECT_COLLATION, OBJECT_COLUMN, OBJECT_CONVERSION, OBJECT_DATABASE, OBJECT_DEFACL, OBJECT_DEFAULT, OBJECT_DOMAIN, OBJECT_DOMCONSTRAINT, OBJECT_EVENT_TRIGGER, OBJECT_EXTENSION, OBJECT_FDW, OBJECT_FOREIGN_SERVER, OBJECT_FOREIGN_TABLE, OBJECT_FUNCTION, OBJECT_INDEX, OBJECT_LANGUAGE, OBJECT_LARGEOBJECT, OBJECT_MATVIEW, OBJECT_OPCLASS, OBJECT_OPERATOR, OBJECT_OPFAMILY, OBJECT_PARAMETER_ACL, OBJECT_POLICY, OBJECT_PROCEDURE, OBJECT_PUBLICATION, OBJECT_PUBLICATION_NAMESPACE, OBJECT_PUBLICATION_REL, OBJECT_ROLE, OBJECT_ROUTINE, OBJECT_RULE, OBJECT_SCHEMA, OBJECT_SEQUENCE, OBJECT_STATISTIC_EXT, OBJECT_SUBSCRIPTION, OBJECT_TABCONSTRAINT, OBJECT_TABLE, OBJECT_TABLESPACE, OBJECT_TRANSFORM, OBJECT_TRIGGER, OBJECT_TSCONFIGURATION, OBJECT_TSDICTIONARY, OBJECT_TSPARSER, OBJECT_TSTEMPLATE, OBJECT_TYPE, OBJECT_USER_MAPPING, and OBJECT_VIEW.

Referenced by aclcheck_error_col(), aclcheck_error_type(), AlterCollation(), AlterDatabase(), AlterDatabaseOwner(), AlterDatabaseRefreshColl(), AlterDatabaseSet(), AlterEventTrigger(), AlterEventTriggerOwner_internal(), AlterExtensionNamespace(), AlterForeignServer(), AlterForeignServerOwner_internal(), AlterFunction(), AlterObjectNamespace_internal(), AlterObjectOwner_internal(), AlterObjectRename_internal(), AlterOperator(), AlterOpFamilyAdd(), AlterPublication(), AlterPublicationOwner_internal(), AlterRoleSet(), AlterSchemaOwner_internal(), AlterStatistics(), AlterSubscription(), AlterSubscriptionOwner_internal(), AlterTableMoveAll(), AlterTableSpaceOptions(), AlterTSConfiguration(), AlterTSDictionary(), AlterTypeOwner(), ATExecChangeOwner(), ATPrepSetTableSpace(), ATSimplePermissions(), brin_desummarize_range(), brin_summarize_range(), calculate_database_size(), calculate_tablespace_size(), call_pltcl_start_proc(), check_object_ownership(), check_temp_tablespaces(), checkFkeyPermissions(), CheckFunctionValidatorAccess(), compute_return_type(), CreateConversionCommand(), createdb(), CreateForeignServer(), CreateForeignTable(), CreateFunction(), CreateProceduralLanguage(), CreatePublication(), CreateSchemaCommand(), CreateStatistics(), CreateTransform(), CreateTriggerFiringOn(), currtid_internal(), DefineAggregate(), DefineCollation(), DefineDomain(), DefineEnum(), DefineIndex(), DefineOpClass(), DefineOperator(), DefineOpFamily(), DefineQueryRewrite(), DefineRange(), DefineRelation(), DefineTSConfiguration(), DefineTSDictionary(), DefineType(), dropdb(), DropSubscription(), DropTableSpace(), EnableDisableRule(), ExecAlterExtensionContentsStmt(), ExecAlterExtensionStmt(), ExecBuildGroupingEqual(), ExecBuildParamSetEqual(), ExecCheckRTPerms(), ExecInitAgg(), ExecInitExprRec(), ExecInitFunc(), ExecInitWindowAgg(), ExecReindex(), ExecuteCallStmt(), ExecuteDoStmt(), ExecuteTruncateGuts(), findRangeCanonicalFunction(), findRangeSubtypeDiffFunction(), get_connect_string(), get_other_operator(), get_rel_from_relname(), gin_clean_pending_list(), HandleFunctionRequest(), heap_force_common(), ImportForeignSchema(), init_sexpr(), initialize_peragg(), LockViewRecurse_walker(), LogicalRepSyncTableStart(), lookup_agg_function(), LookupCreationNamespace(), LookupExplicitNamespace(), MergeAttributes(), movedb(), OperatorCreate(), pg_prewarm(), pgrowlocks(), ProcedureCreate(), PublicationAddTables(), RangeVarCallbackForAlterRelation(), RangeVarCallbackForDropRelation(), RangeVarCallbackForLockTable(), RangeVarCallbackForPolicy(), RangeVarCallbackForReindexIndex(), RangeVarCallbackForRenameRule(), RangeVarCallbackForRenameTrigger(), RangeVarCallbackOwnsRelation(), RangeVarCallbackOwnsTable(), RangeVarGetAndCheckCreationNamespace(), ReindexMultipleInternal(), ReindexMultipleTables(), renameatt_check(), RenameDatabase(), RenameSchema(), RenameTableSpace(), restrict_and_check_grant(), TargetPrivilegesCheck(), transformTableLikeClause(), truncate_check_perms(), TypeCreate(), user_mapping_ddl_aclcheck(), ValidateJoinEstimator(), and ValidateRestrictionEstimator().

◆ aclcheck_error_col()

void aclcheck_error_col ( AclResult  aclerr,
ObjectType  objtype,
const char *  objectname,
const char *  colname 
)

Definition at line 3801 of file aclchk.c.

3803 {
3804  switch (aclerr)
3805  {
3806  case ACLCHECK_OK:
3807  /* no error, so return to caller */
3808  break;
3809  case ACLCHECK_NO_PRIV:
3810  ereport(ERROR,
3811  (errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
3812  errmsg("permission denied for column \"%s\" of relation \"%s\"",
3813  colname, objectname)));
3814  break;
3815  case ACLCHECK_NOT_OWNER:
3816  /* relation msg is OK since columns don't have separate owners */
3817  aclcheck_error(aclerr, objtype, objectname);
3818  break;
3819  default:
3820  elog(ERROR, "unrecognized AclResult: %d", (int) aclerr);
3821  break;
3822  }
3823 }
void aclcheck_error(AclResult aclerr, ObjectType objtype, const char *objectname)
Definition: aclchk.c:3512

References aclcheck_error(), ACLCHECK_NO_PRIV, ACLCHECK_NOT_OWNER, ACLCHECK_OK, elog(), ereport, errcode(), errmsg(), and ERROR.

Referenced by restrict_and_check_grant().

◆ aclcheck_error_type()

void aclcheck_error_type ( AclResult  aclerr,
Oid  typeOid 
)

◆ aclconcat()

Acl* aclconcat ( const Acl left_acl,
const Acl right_acl 
)

Definition at line 421 of file acl.c.

422 {
423  Acl *result_acl;
424 
425  result_acl = allocacl(ACL_NUM(left_acl) + ACL_NUM(right_acl));
426 
427  memcpy(ACL_DAT(result_acl),
428  ACL_DAT(left_acl),
429  ACL_NUM(left_acl) * sizeof(AclItem));
430 
431  memcpy(ACL_DAT(result_acl) + ACL_NUM(left_acl),
432  ACL_DAT(right_acl),
433  ACL_NUM(right_acl) * sizeof(AclItem));
434 
435  return result_acl;
436 }
static Acl * allocacl(int n)
Definition: acl.c:370
#define ACL_DAT(ACL)
Definition: acl.h:109
#define ACL_NUM(ACL)
Definition: acl.h:108
Definition: acl.h:55

References ACL_DAT, ACL_NUM, and allocacl().

Referenced by ExecGrant_Attribute().

◆ aclcopy()

Acl* aclcopy ( const Acl orig_acl)

Definition at line 401 of file acl.c.

402 {
403  Acl *result_acl;
404 
405  result_acl = allocacl(ACL_NUM(orig_acl));
406 
407  memcpy(ACL_DAT(result_acl),
408  ACL_DAT(orig_acl),
409  ACL_NUM(orig_acl) * sizeof(AclItem));
410 
411  return result_acl;
412 }

References ACL_DAT, ACL_NUM, and allocacl().

Referenced by aclmerge(), ExecGrant_Relation(), and SetDefaultACL().

◆ acldefault()

Acl* acldefault ( ObjectType  objtype,
Oid  ownerId 
)

Definition at line 742 of file acl.c.

743 {
744  AclMode world_default;
745  AclMode owner_default;
746  int nacl;
747  Acl *acl;
748  AclItem *aip;
749 
750  switch (objtype)
751  {
752  case OBJECT_COLUMN:
753  /* by default, columns have no extra privileges */
754  world_default = ACL_NO_RIGHTS;
755  owner_default = ACL_NO_RIGHTS;
756  break;
757  case OBJECT_TABLE:
758  world_default = ACL_NO_RIGHTS;
759  owner_default = ACL_ALL_RIGHTS_RELATION;
760  break;
761  case OBJECT_SEQUENCE:
762  world_default = ACL_NO_RIGHTS;
763  owner_default = ACL_ALL_RIGHTS_SEQUENCE;
764  break;
765  case OBJECT_DATABASE:
766  /* for backwards compatibility, grant some rights by default */
767  world_default = ACL_CREATE_TEMP | ACL_CONNECT;
768  owner_default = ACL_ALL_RIGHTS_DATABASE;
769  break;
770  case OBJECT_FUNCTION:
771  /* Grant EXECUTE by default, for now */
772  world_default = ACL_EXECUTE;
773  owner_default = ACL_ALL_RIGHTS_FUNCTION;
774  break;
775  case OBJECT_LANGUAGE:
776  /* Grant USAGE by default, for now */
777  world_default = ACL_USAGE;
778  owner_default = ACL_ALL_RIGHTS_LANGUAGE;
779  break;
780  case OBJECT_LARGEOBJECT:
781  world_default = ACL_NO_RIGHTS;
782  owner_default = ACL_ALL_RIGHTS_LARGEOBJECT;
783  break;
784  case OBJECT_SCHEMA:
785  world_default = ACL_NO_RIGHTS;
786  owner_default = ACL_ALL_RIGHTS_SCHEMA;
787  break;
788  case OBJECT_TABLESPACE:
789  world_default = ACL_NO_RIGHTS;
790  owner_default = ACL_ALL_RIGHTS_TABLESPACE;
791  break;
792  case OBJECT_FDW:
793  world_default = ACL_NO_RIGHTS;
794  owner_default = ACL_ALL_RIGHTS_FDW;
795  break;
797  world_default = ACL_NO_RIGHTS;
798  owner_default = ACL_ALL_RIGHTS_FOREIGN_SERVER;
799  break;
800  case OBJECT_DOMAIN:
801  case OBJECT_TYPE:
802  world_default = ACL_USAGE;
803  owner_default = ACL_ALL_RIGHTS_TYPE;
804  break;
806  world_default = ACL_NO_RIGHTS;
807  owner_default = ACL_ALL_RIGHTS_PARAMETER_ACL;
808  break;
809  default:
810  elog(ERROR, "unrecognized objtype: %d", (int) objtype);
811  world_default = ACL_NO_RIGHTS; /* keep compiler quiet */
812  owner_default = ACL_NO_RIGHTS;
813  break;
814  }
815 
816  nacl = 0;
817  if (world_default != ACL_NO_RIGHTS)
818  nacl++;
819  if (owner_default != ACL_NO_RIGHTS)
820  nacl++;
821 
822  acl = allocacl(nacl);
823  aip = ACL_DAT(acl);
824 
825  if (world_default != ACL_NO_RIGHTS)
826  {
827  aip->ai_grantee = ACL_ID_PUBLIC;
828  aip->ai_grantor = ownerId;
829  ACLITEM_SET_PRIVS_GOPTIONS(*aip, world_default, ACL_NO_RIGHTS);
830  aip++;
831  }
832 
833  /*
834  * Note that the owner's entry shows all ordinary privileges but no grant
835  * options. This is because his grant options come "from the system" and
836  * not from his own efforts. (The SQL spec says that the owner's rights
837  * come from a "_SYSTEM" authid.) However, we do consider that the
838  * owner's ordinary privileges are self-granted; this lets him revoke
839  * them. We implement the owner's grant options without any explicit
840  * "_SYSTEM"-like ACL entry, by internally special-casing the owner
841  * wherever we are testing grant options.
842  */
843  if (owner_default != ACL_NO_RIGHTS)
844  {
845  aip->ai_grantee = ownerId;
846  aip->ai_grantor = ownerId;
847  ACLITEM_SET_PRIVS_GOPTIONS(*aip, owner_default, ACL_NO_RIGHTS);
848  }
849 
850  return acl;
851 }
#define ACL_ALL_RIGHTS_FOREIGN_SERVER
Definition: acl.h:163
#define ACL_ALL_RIGHTS_TABLESPACE
Definition: acl.h:169
#define ACL_ALL_RIGHTS_PARAMETER_ACL
Definition: acl.h:167
#define ACL_ALL_RIGHTS_SCHEMA
Definition: acl.h:168
#define ACL_ALL_RIGHTS_SEQUENCE
Definition: acl.h:160
#define ACL_ALL_RIGHTS_DATABASE
Definition: acl.h:161
#define ACL_ALL_RIGHTS_FUNCTION
Definition: acl.h:164
#define ACL_ALL_RIGHTS_LANGUAGE
Definition: acl.h:165
#define ACL_ALL_RIGHTS_TYPE
Definition: acl.h:170
#define ACL_ALL_RIGHTS_FDW
Definition: acl.h:162
#define ACLITEM_SET_PRIVS_GOPTIONS(item, privs, goptions)
Definition: acl.h:82
#define ACL_ALL_RIGHTS_RELATION
Definition: acl.h:159
#define ACL_ID_PUBLIC
Definition: acl.h:46
#define ACL_ALL_RIGHTS_LARGEOBJECT
Definition: acl.h:166
#define ACL_CREATE_TEMP
Definition: parsenodes.h:92
#define ACL_USAGE
Definition: parsenodes.h:90
#define ACL_NO_RIGHTS
Definition: parsenodes.h:97
#define ACL_CONNECT
Definition: parsenodes.h:93
#define ACL_EXECUTE
Definition: parsenodes.h:89
Oid ai_grantee
Definition: acl.h:56
Oid ai_grantor
Definition: acl.h:57

References ACL_ALL_RIGHTS_DATABASE, ACL_ALL_RIGHTS_FDW, ACL_ALL_RIGHTS_FOREIGN_SERVER, ACL_ALL_RIGHTS_FUNCTION, ACL_ALL_RIGHTS_LANGUAGE, ACL_ALL_RIGHTS_LARGEOBJECT, ACL_ALL_RIGHTS_PARAMETER_ACL, ACL_ALL_RIGHTS_RELATION, ACL_ALL_RIGHTS_SCHEMA, ACL_ALL_RIGHTS_SEQUENCE, ACL_ALL_RIGHTS_TABLESPACE, ACL_ALL_RIGHTS_TYPE, ACL_CONNECT, ACL_CREATE_TEMP, ACL_DAT, ACL_EXECUTE, ACL_ID_PUBLIC, ACL_NO_RIGHTS, ACL_USAGE, ACLITEM_SET_PRIVS_GOPTIONS, AclItem::ai_grantee, AclItem::ai_grantor, allocacl(), elog(), ERROR, OBJECT_COLUMN, OBJECT_DATABASE, OBJECT_DOMAIN, OBJECT_FDW, OBJECT_FOREIGN_SERVER, OBJECT_FUNCTION, OBJECT_LANGUAGE, OBJECT_LARGEOBJECT, OBJECT_PARAMETER_ACL, OBJECT_SCHEMA, OBJECT_SEQUENCE, OBJECT_TABLE, OBJECT_TABLESPACE, and OBJECT_TYPE.

Referenced by acldefault_sql(), buildDefaultACLCommands(), dumpACL(), dumpRoleGUCPrivs(), dumpTable(), dumpTablespaces(), ExecGrant_Attribute(), ExecGrant_Database(), ExecGrant_Fdw(), ExecGrant_ForeignServer(), ExecGrant_Function(), ExecGrant_Language(), ExecGrant_Largeobject(), ExecGrant_Namespace(), ExecGrant_Parameter(), ExecGrant_Relation(), ExecGrant_Tablespace(), ExecGrant_Type(), get_user_default_acl(), pg_class_aclmask_ext(), pg_database_aclmask(), pg_foreign_data_wrapper_aclmask(), pg_foreign_server_aclmask(), pg_language_aclmask(), pg_largeobject_aclmask_snapshot(), pg_namespace_aclmask(), pg_parameter_acl_aclmask(), pg_parameter_aclmask(), pg_proc_aclmask(), pg_tablespace_aclmask(), pg_type_aclmask(), and SetDefaultACL().

◆ aclequal()

bool aclequal ( const Acl left_acl,
const Acl right_acl 
)

Definition at line 503 of file acl.c.

504 {
505  /* Check for cases where one or both are empty/null */
506  if (left_acl == NULL || ACL_NUM(left_acl) == 0)
507  {
508  if (right_acl == NULL || ACL_NUM(right_acl) == 0)
509  return true;
510  else
511  return false;
512  }
513  else
514  {
515  if (right_acl == NULL || ACL_NUM(right_acl) == 0)
516  return false;
517  }
518 
519  if (ACL_NUM(left_acl) != ACL_NUM(right_acl))
520  return false;
521 
522  if (memcmp(ACL_DAT(left_acl),
523  ACL_DAT(right_acl),
524  ACL_NUM(left_acl) * sizeof(AclItem)) == 0)
525  return true;
526 
527  return false;
528 }

References ACL_DAT, and ACL_NUM.

Referenced by ExecGrant_Parameter(), get_user_default_acl(), and SetDefaultACL().

◆ aclitemsort()

void aclitemsort ( Acl acl)

Definition at line 489 of file acl.c.

490 {
491  if (acl != NULL && ACL_NUM(acl) > 1)
492  qsort(ACL_DAT(acl), ACL_NUM(acl), sizeof(AclItem), aclitemComparator);
493 }
static int aclitemComparator(const void *arg1, const void *arg2)
Definition: acl.c:663
#define qsort(a, b, c, d)
Definition: port.h:495

References ACL_DAT, ACL_NUM, aclitemComparator(), and qsort.

Referenced by get_user_default_acl(), and SetDefaultACL().

◆ aclmask()

AclMode aclmask ( const Acl acl,
Oid  roleid,
Oid  ownerId,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 1321 of file acl.c.

1323 {
1324  AclMode result;
1326  AclItem *aidat;
1327  int i,
1328  num;
1329 
1330  /*
1331  * Null ACL should not happen, since caller should have inserted
1332  * appropriate default
1333  */
1334  if (acl == NULL)
1335  elog(ERROR, "null ACL");
1336 
1337  check_acl(acl);
1338 
1339  /* Quick exit for mask == 0 */
1340  if (mask == 0)
1341  return 0;
1342 
1343  result = 0;
1344 
1345  /* Owner always implicitly has all grant options */
1346  if ((mask & ACLITEM_ALL_GOPTION_BITS) &&
1347  has_privs_of_role(roleid, ownerId))
1348  {
1349  result = mask & ACLITEM_ALL_GOPTION_BITS;
1350  if ((how == ACLMASK_ALL) ? (result == mask) : (result != 0))
1351  return result;
1352  }
1353 
1354  num = ACL_NUM(acl);
1355  aidat = ACL_DAT(acl);
1356 
1357  /*
1358  * Check privileges granted directly to roleid or to public
1359  */
1360  for (i = 0; i < num; i++)
1361  {
1362  AclItem *aidata = &aidat[i];
1363 
1364  if (aidata->ai_grantee == ACL_ID_PUBLIC ||
1365  aidata->ai_grantee == roleid)
1366  {
1367  result |= aidata->ai_privs & mask;
1368  if ((how == ACLMASK_ALL) ? (result == mask) : (result != 0))
1369  return result;
1370  }
1371  }
1372 
1373  /*
1374  * Check privileges granted indirectly via role memberships. We do this in
1375  * a separate pass to minimize expensive indirect membership tests. In
1376  * particular, it's worth testing whether a given ACL entry grants any
1377  * privileges still of interest before we perform the has_privs_of_role
1378  * test.
1379  */
1380  remaining = mask & ~result;
1381  for (i = 0; i < num; i++)
1382  {
1383  AclItem *aidata = &aidat[i];
1384 
1385  if (aidata->ai_grantee == ACL_ID_PUBLIC ||
1386  aidata->ai_grantee == roleid)
1387  continue; /* already checked it */
1388 
1389  if ((aidata->ai_privs & remaining) &&
1390  has_privs_of_role(roleid, aidata->ai_grantee))
1391  {
1392  result |= aidata->ai_privs & mask;
1393  if ((how == ACLMASK_ALL) ? (result == mask) : (result != 0))
1394  return result;
1395  remaining = mask & ~result;
1396  }
1397  }
1398 
1399  return result;
1400 }
static void check_acl(const Acl *acl)
Definition: acl.c:534
bool has_privs_of_role(Oid member, Oid role)
Definition: acl.c:4925
#define ACLITEM_ALL_GOPTION_BITS
Definition: acl.h:88
int remaining
Definition: informix.c:667
int i
Definition: isn.c:73
AclMode ai_privs
Definition: acl.h:58

References ACL_DAT, ACL_ID_PUBLIC, ACL_NUM, ACLITEM_ALL_GOPTION_BITS, ACLMASK_ALL, AclItem::ai_grantee, AclItem::ai_privs, check_acl(), elog(), ERROR, has_privs_of_role(), i, and remaining.

Referenced by check_circularity(), LockTableAclCheck(), pg_attribute_aclmask_ext(), pg_class_aclmask_ext(), pg_database_aclmask(), pg_foreign_data_wrapper_aclmask(), pg_foreign_server_aclmask(), pg_language_aclmask(), pg_largeobject_aclmask_snapshot(), pg_namespace_aclmask(), pg_parameter_acl_aclmask(), pg_parameter_aclmask(), pg_proc_aclmask(), pg_tablespace_aclmask(), pg_type_aclmask(), and recursive_revoke().

◆ aclmembers()

int aclmembers ( const Acl acl,
Oid **  roleids 
)

Definition at line 1473 of file acl.c.

1474 {
1475  Oid *list;
1476  const AclItem *acldat;
1477  int i,
1478  j;
1479 
1480  if (acl == NULL || ACL_NUM(acl) == 0)
1481  {
1482  *roleids = NULL;
1483  return 0;
1484  }
1485 
1486  check_acl(acl);
1487 
1488  /* Allocate the worst-case space requirement */
1489  list = palloc(ACL_NUM(acl) * 2 * sizeof(Oid));
1490  acldat = ACL_DAT(acl);
1491 
1492  /*
1493  * Walk the ACL collecting mentioned RoleIds.
1494  */
1495  j = 0;
1496  for (i = 0; i < ACL_NUM(acl); i++)
1497  {
1498  const AclItem *ai = &acldat[i];
1499 
1500  if (ai->ai_grantee != ACL_ID_PUBLIC)
1501  list[j++] = ai->ai_grantee;
1502  /* grantor is currently never PUBLIC, but let's check anyway */
1503  if (ai->ai_grantor != ACL_ID_PUBLIC)
1504  list[j++] = ai->ai_grantor;
1505  }
1506 
1507  /* Sort the array */
1508  qsort(list, j, sizeof(Oid), oid_cmp);
1509 
1510  /*
1511  * We could repalloc the array down to minimum size, but it's hardly worth
1512  * it since it's only transient memory.
1513  */
1514  *roleids = list;
1515 
1516  /* Remove duplicates from the array */
1517  return qunique(list, j, sizeof(Oid), oid_cmp);
1518 }
int j
Definition: isn.c:74
void * palloc(Size size)
Definition: mcxt.c:1068
int oid_cmp(const void *p1, const void *p2)
Definition: oid.c:336
static size_t qunique(void *array, size_t elements, size_t width, int(*compare)(const void *, const void *))
Definition: qunique.h:21

References ACL_DAT, ACL_ID_PUBLIC, ACL_NUM, AclItem::ai_grantee, AclItem::ai_grantor, check_acl(), i, j, sort-test::list, oid_cmp(), palloc(), qsort, and qunique().

Referenced by ExecGrant_Attribute(), ExecGrant_Database(), ExecGrant_Fdw(), ExecGrant_ForeignServer(), ExecGrant_Function(), ExecGrant_Language(), ExecGrant_Largeobject(), ExecGrant_Namespace(), ExecGrant_Parameter(), ExecGrant_Relation(), ExecGrant_Tablespace(), ExecGrant_Type(), recordDependencyOnNewAcl(), and SetDefaultACL().

◆ aclmerge()

Acl* aclmerge ( const Acl left_acl,
const Acl right_acl,
Oid  ownerId 
)

Definition at line 445 of file acl.c.

446 {
447  Acl *result_acl;
448  AclItem *aip;
449  int i,
450  num;
451 
452  /* Check for cases where one or both are empty/null */
453  if (left_acl == NULL || ACL_NUM(left_acl) == 0)
454  {
455  if (right_acl == NULL || ACL_NUM(right_acl) == 0)
456  return NULL;
457  else
458  return aclcopy(right_acl);
459  }
460  else
461  {
462  if (right_acl == NULL || ACL_NUM(right_acl) == 0)
463  return aclcopy(left_acl);
464  }
465 
466  /* Merge them the hard way, one item at a time */
467  result_acl = aclcopy(left_acl);
468 
469  aip = ACL_DAT(right_acl);
470  num = ACL_NUM(right_acl);
471 
472  for (i = 0; i < num; i++, aip++)
473  {
474  Acl *tmp_acl;
475 
476  tmp_acl = aclupdate(result_acl, aip, ACL_MODECHG_ADD,
477  ownerId, DROP_RESTRICT);
478  pfree(result_acl);
479  result_acl = tmp_acl;
480  }
481 
482  return result_acl;
483 }
Acl * aclupdate(const Acl *old_acl, const AclItem *mod_aip, int modechg, Oid ownerId, DropBehavior behavior)
Definition: acl.c:931
Acl * aclcopy(const Acl *orig_acl)
Definition: acl.c:401
#define ACL_MODECHG_ADD
Definition: acl.h:129
void pfree(void *pointer)
Definition: mcxt.c:1175
@ DROP_RESTRICT
Definition: parsenodes.h:2208

References ACL_DAT, ACL_MODECHG_ADD, ACL_NUM, aclcopy(), aclupdate(), DROP_RESTRICT, i, and pfree().

Referenced by get_user_default_acl().

◆ aclnewowner()

Acl* aclnewowner ( const Acl old_acl,
Oid  oldOwnerId,
Oid  newOwnerId 
)

Definition at line 1052 of file acl.c.

1053 {
1054  Acl *new_acl;
1055  AclItem *new_aip;
1056  AclItem *old_aip;
1057  AclItem *dst_aip;
1058  AclItem *src_aip;
1059  AclItem *targ_aip;
1060  bool newpresent = false;
1061  int dst,
1062  src,
1063  targ,
1064  num;
1065 
1066  check_acl(old_acl);
1067 
1068  /*
1069  * Make a copy of the given ACL, substituting new owner ID for old
1070  * wherever it appears as either grantor or grantee. Also note if the new
1071  * owner ID is already present.
1072  */
1073  num = ACL_NUM(old_acl);
1074  old_aip = ACL_DAT(old_acl);
1075  new_acl = allocacl(num);
1076  new_aip = ACL_DAT(new_acl);
1077  memcpy(new_aip, old_aip, num * sizeof(AclItem));
1078  for (dst = 0, dst_aip = new_aip; dst < num; dst++, dst_aip++)
1079  {
1080  if (dst_aip->ai_grantor == oldOwnerId)
1081  dst_aip->ai_grantor = newOwnerId;
1082  else if (dst_aip->ai_grantor == newOwnerId)
1083  newpresent = true;
1084  if (dst_aip->ai_grantee == oldOwnerId)
1085  dst_aip->ai_grantee = newOwnerId;
1086  else if (dst_aip->ai_grantee == newOwnerId)
1087  newpresent = true;
1088  }
1089 
1090  /*
1091  * If the old ACL contained any references to the new owner, then we may
1092  * now have generated an ACL containing duplicate entries. Find them and
1093  * merge them so that there are not duplicates. (This is relatively
1094  * expensive since we use a stupid O(N^2) algorithm, but it's unlikely to
1095  * be the normal case.)
1096  *
1097  * To simplify deletion of duplicate entries, we temporarily leave them in
1098  * the array but set their privilege masks to zero; when we reach such an
1099  * entry it's just skipped. (Thus, a side effect of this code will be to
1100  * remove privilege-free entries, should there be any in the input.) dst
1101  * is the next output slot, targ is the currently considered input slot
1102  * (always >= dst), and src scans entries to the right of targ looking for
1103  * duplicates. Once an entry has been emitted to dst it is known
1104  * duplicate-free and need not be considered anymore.
1105  */
1106  if (newpresent)
1107  {
1108  dst = 0;
1109  for (targ = 0, targ_aip = new_aip; targ < num; targ++, targ_aip++)
1110  {
1111  /* ignore if deleted in an earlier pass */
1112  if (ACLITEM_GET_RIGHTS(*targ_aip) == ACL_NO_RIGHTS)
1113  continue;
1114  /* find and merge any duplicates */
1115  for (src = targ + 1, src_aip = targ_aip + 1; src < num;
1116  src++, src_aip++)
1117  {
1118  if (ACLITEM_GET_RIGHTS(*src_aip) == ACL_NO_RIGHTS)
1119  continue;
1120  if (aclitem_match(targ_aip, src_aip))
1121  {
1122  ACLITEM_SET_RIGHTS(*targ_aip,
1123  ACLITEM_GET_RIGHTS(*targ_aip) |
1124  ACLITEM_GET_RIGHTS(*src_aip));
1125  /* mark the duplicate deleted */
1126  ACLITEM_SET_RIGHTS(*src_aip, ACL_NO_RIGHTS);
1127  }
1128  }
1129  /* and emit to output */
1130  new_aip[dst] = *targ_aip;
1131  dst++;
1132  }
1133  /* Adjust array size to be 'dst' items */
1134  ARR_DIMS(new_acl)[0] = dst;
1135  SET_VARSIZE(new_acl, ACL_N_SIZE(dst));
1136  }
1137 
1138  return new_acl;
1139 }
static bool aclitem_match(const AclItem *a1, const AclItem *a2)
Definition: acl.c:652
#define ACL_N_SIZE(N)
Definition: acl.h:110
#define ACLITEM_GET_RIGHTS(item)
Definition: acl.h:68
#define ACLITEM_SET_RIGHTS(item, rights)
Definition: acl.h:79
#define ARR_DIMS(a)
Definition: array.h:287
#define SET_VARSIZE(PTR, len)
Definition: postgres.h:342

References ACL_DAT, ACL_N_SIZE, ACL_NO_RIGHTS, ACL_NUM, ACLITEM_GET_RIGHTS, aclitem_match(), ACLITEM_SET_RIGHTS, AclItem::ai_grantee, AclItem::ai_grantor, allocacl(), ARR_DIMS, check_acl(), and SET_VARSIZE.

Referenced by AlterDatabaseOwner(), AlterForeignDataWrapperOwner_internal(), AlterForeignServerOwner_internal(), AlterObjectOwner_internal(), AlterSchemaOwner_internal(), AlterTypeOwnerInternal(), ATExecChangeOwner(), and change_owner_fix_column_acls().

◆ aclupdate()

Acl* aclupdate ( const Acl old_acl,
const AclItem mod_aip,
int  modechg,
Oid  ownerId,
DropBehavior  behavior 
)

Definition at line 931 of file acl.c.

933 {
934  Acl *new_acl = NULL;
935  AclItem *old_aip,
936  *new_aip = NULL;
937  AclMode old_rights,
938  old_goptions,
939  new_rights,
940  new_goptions;
941  int dst,
942  num;
943 
944  /* Caller probably already checked old_acl, but be safe */
945  check_acl(old_acl);
946 
947  /* If granting grant options, check for circularity */
948  if (modechg != ACL_MODECHG_DEL &&
949  ACLITEM_GET_GOPTIONS(*mod_aip) != ACL_NO_RIGHTS)
950  check_circularity(old_acl, mod_aip, ownerId);
951 
952  num = ACL_NUM(old_acl);
953  old_aip = ACL_DAT(old_acl);
954 
955  /*
956  * Search the ACL for an existing entry for this grantee and grantor. If
957  * one exists, just modify the entry in-place (well, in the same position,
958  * since we actually return a copy); otherwise, insert the new entry at
959  * the end.
960  */
961 
962  for (dst = 0; dst < num; ++dst)
963  {
964  if (aclitem_match(mod_aip, old_aip + dst))
965  {
966  /* found a match, so modify existing item */
967  new_acl = allocacl(num);
968  new_aip = ACL_DAT(new_acl);
969  memcpy(new_acl, old_acl, ACL_SIZE(old_acl));
970  break;
971  }
972  }
973 
974  if (dst == num)
975  {
976  /* need to append a new item */
977  new_acl = allocacl(num + 1);
978  new_aip = ACL_DAT(new_acl);
979  memcpy(new_aip, old_aip, num * sizeof(AclItem));
980 
981  /* initialize the new entry with no permissions */
982  new_aip[dst].ai_grantee = mod_aip->ai_grantee;
983  new_aip[dst].ai_grantor = mod_aip->ai_grantor;
984  ACLITEM_SET_PRIVS_GOPTIONS(new_aip[dst],
986  num++; /* set num to the size of new_acl */
987  }
988 
989  old_rights = ACLITEM_GET_RIGHTS(new_aip[dst]);
990  old_goptions = ACLITEM_GET_GOPTIONS(new_aip[dst]);
991 
992  /* apply the specified permissions change */
993  switch (modechg)
994  {
995  case ACL_MODECHG_ADD:
996  ACLITEM_SET_RIGHTS(new_aip[dst],
997  old_rights | ACLITEM_GET_RIGHTS(*mod_aip));
998  break;
999  case ACL_MODECHG_DEL:
1000  ACLITEM_SET_RIGHTS(new_aip[dst],
1001  old_rights & ~ACLITEM_GET_RIGHTS(*mod_aip));
1002  break;
1003  case ACL_MODECHG_EQL:
1004  ACLITEM_SET_RIGHTS(new_aip[dst],
1005  ACLITEM_GET_RIGHTS(*mod_aip));
1006  break;
1007  }
1008 
1009  new_rights = ACLITEM_GET_RIGHTS(new_aip[dst]);
1010  new_goptions = ACLITEM_GET_GOPTIONS(new_aip[dst]);
1011 
1012  /*
1013  * If the adjusted entry has no permissions, delete it from the list.
1014  */
1015  if (new_rights == ACL_NO_RIGHTS)
1016  {
1017  memmove(new_aip + dst,
1018  new_aip + dst + 1,
1019  (num - dst - 1) * sizeof(AclItem));
1020  /* Adjust array size to be 'num - 1' items */
1021  ARR_DIMS(new_acl)[0] = num - 1;
1022  SET_VARSIZE(new_acl, ACL_N_SIZE(num - 1));
1023  }
1024 
1025  /*
1026  * Remove abandoned privileges (cascading revoke). Currently we can only
1027  * handle this when the grantee is not PUBLIC.
1028  */
1029  if ((old_goptions & ~new_goptions) != 0)
1030  {
1031  Assert(mod_aip->ai_grantee != ACL_ID_PUBLIC);
1032  new_acl = recursive_revoke(new_acl, mod_aip->ai_grantee,
1033  (old_goptions & ~new_goptions),
1034  ownerId, behavior);
1035  }
1036 
1037  return new_acl;
1038 }
static Acl * recursive_revoke(Acl *acl, Oid grantee, AclMode revoke_privs, Oid ownerId, DropBehavior behavior)
Definition: acl.c:1235
static void check_circularity(const Acl *old_acl, const AclItem *mod_aip, Oid ownerId)
Definition: acl.c:1155
#define ACL_SIZE(ACL)
Definition: acl.h:111
#define ACL_MODECHG_DEL
Definition: acl.h:130
#define ACLITEM_GET_GOPTIONS(item)
Definition: acl.h:67
#define ACL_MODECHG_EQL
Definition: acl.h:131
Assert(fmt[strlen(fmt) - 1] !='\n')

References ACL_DAT, ACL_ID_PUBLIC, ACL_MODECHG_ADD, ACL_MODECHG_DEL, ACL_MODECHG_EQL, ACL_N_SIZE, ACL_NO_RIGHTS, ACL_NUM, ACL_SIZE, ACLITEM_GET_GOPTIONS, ACLITEM_GET_RIGHTS, aclitem_match(), ACLITEM_SET_PRIVS_GOPTIONS, ACLITEM_SET_RIGHTS, AclItem::ai_grantee, AclItem::ai_grantor, allocacl(), ARR_DIMS, Assert(), check_acl(), check_circularity(), recursive_revoke(), and SET_VARSIZE.

Referenced by aclmerge(), check_circularity(), merge_acl_with_grant(), and recursive_revoke().

◆ check_is_member_of_role()

void check_is_member_of_role ( Oid  member,
Oid  role 
)

Definition at line 4977 of file acl.c.

4978 {
4979  if (!is_member_of_role(member, role))
4980  ereport(ERROR,
4981  (errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
4982  errmsg("must be member of role \"%s\"",
4983  GetUserNameFromId(role, false))));
4984 }
bool is_member_of_role(Oid member, Oid role)
Definition: acl.c:4953
char * GetUserNameFromId(Oid roleid, bool noerr)
Definition: miscinit.c:912

References ereport, errcode(), errmsg(), ERROR, GetUserNameFromId(), and is_member_of_role().

Referenced by AlterDatabaseOwner(), AlterForeignServerOwner_internal(), AlterObjectOwner_internal(), AlterPublicationOwner_internal(), AlterSchemaOwner_internal(), AlterTypeOwner(), ATExecChangeOwner(), createdb(), CreateSchemaCommand(), and ExecAlterDefaultPrivilegesStmt().

◆ check_rolespec_name()

void check_rolespec_name ( const RoleSpec role,
const char *  detail_msg 
)

Definition at line 5292 of file acl.c.

5293 {
5294  if (!role)
5295  return;
5296 
5297  if (role->roletype != ROLESPEC_CSTRING)
5298  return;
5299 
5300  if (IsReservedName(role->rolename))
5301  {
5302  if (detail_msg)
5303  ereport(ERROR,
5304  (errcode(ERRCODE_RESERVED_NAME),
5305  errmsg("role name \"%s\" is reserved",
5306  role->rolename),
5307  errdetail("%s", detail_msg)));
5308  else
5309  ereport(ERROR,
5310  (errcode(ERRCODE_RESERVED_NAME),
5311  errmsg("role name \"%s\" is reserved",
5312  role->rolename)));
5313  }
5314 }
bool IsReservedName(const char *name)
Definition: catalog.c:219
int errdetail(const char *fmt,...)
Definition: elog.c:1037
@ ROLESPEC_CSTRING
Definition: parsenodes.h:349
RoleSpecType roletype
Definition: parsenodes.h:359
char * rolename
Definition: parsenodes.h:360

References ereport, errcode(), errdetail(), errmsg(), ERROR, IsReservedName(), RoleSpec::rolename, ROLESPEC_CSTRING, and RoleSpec::roletype.

Referenced by AlterRole(), and AlterRoleSet().

◆ ExecAlterDefaultPrivilegesStmt()

void ExecAlterDefaultPrivilegesStmt ( ParseState pstate,
AlterDefaultPrivilegesStmt stmt 
)

Definition at line 950 of file aclchk.c.

951 {
952  GrantStmt *action = stmt->action;
953  InternalDefaultACL iacls;
954  ListCell *cell;
955  List *rolespecs = NIL;
956  List *nspnames = NIL;
957  DefElem *drolespecs = NULL;
958  DefElem *dnspnames = NULL;
959  AclMode all_privileges;
960  const char *errormsg;
961 
962  /* Deconstruct the "options" part of the statement */
963  foreach(cell, stmt->options)
964  {
965  DefElem *defel = (DefElem *) lfirst(cell);
966 
967  if (strcmp(defel->defname, "schemas") == 0)
968  {
969  if (dnspnames)
970  errorConflictingDefElem(defel, pstate);
971  dnspnames = defel;
972  }
973  else if (strcmp(defel->defname, "roles") == 0)
974  {
975  if (drolespecs)
976  errorConflictingDefElem(defel, pstate);
977  drolespecs = defel;
978  }
979  else
980  elog(ERROR, "option \"%s\" not recognized", defel->defname);
981  }
982 
983  if (dnspnames)
984  nspnames = (List *) dnspnames->arg;
985  if (drolespecs)
986  rolespecs = (List *) drolespecs->arg;
987 
988  /* Prepare the InternalDefaultACL representation of the statement */
989  /* roleid to be filled below */
990  /* nspid to be filled in SetDefaultACLsInSchemas */
991  iacls.is_grant = action->is_grant;
992  iacls.objtype = action->objtype;
993  /* all_privs to be filled below */
994  /* privileges to be filled below */
995  iacls.grantees = NIL; /* filled below */
996  iacls.grant_option = action->grant_option;
997  iacls.behavior = action->behavior;
998 
999  /*
1000  * Convert the RoleSpec list into an Oid list. Note that at this point we
1001  * insert an ACL_ID_PUBLIC into the list if appropriate, so downstream
1002  * there shouldn't be any additional work needed to support this case.
1003  */
1004  foreach(cell, action->grantees)
1005  {
1006  RoleSpec *grantee = (RoleSpec *) lfirst(cell);
1007  Oid grantee_uid;
1008 
1009  switch (grantee->roletype)
1010  {
1011  case ROLESPEC_PUBLIC:
1012  grantee_uid = ACL_ID_PUBLIC;
1013  break;
1014  default:
1015  grantee_uid = get_rolespec_oid(grantee, false);
1016  break;
1017  }
1018  iacls.grantees = lappend_oid(iacls.grantees, grantee_uid);
1019  }
1020 
1021  /*
1022  * Convert action->privileges, a list of privilege strings, into an
1023  * AclMode bitmask.
1024  */
1025  switch (action->objtype)
1026  {
1027  case OBJECT_TABLE:
1028  all_privileges = ACL_ALL_RIGHTS_RELATION;
1029  errormsg = gettext_noop("invalid privilege type %s for relation");
1030  break;
1031  case OBJECT_SEQUENCE:
1032  all_privileges = ACL_ALL_RIGHTS_SEQUENCE;
1033  errormsg = gettext_noop("invalid privilege type %s for sequence");
1034  break;
1035  case OBJECT_FUNCTION:
1036  all_privileges = ACL_ALL_RIGHTS_FUNCTION;
1037  errormsg = gettext_noop("invalid privilege type %s for function");
1038  break;
1039  case OBJECT_PROCEDURE:
1040  all_privileges = ACL_ALL_RIGHTS_FUNCTION;
1041  errormsg = gettext_noop("invalid privilege type %s for procedure");
1042  break;
1043  case OBJECT_ROUTINE:
1044  all_privileges = ACL_ALL_RIGHTS_FUNCTION;
1045  errormsg = gettext_noop("invalid privilege type %s for routine");
1046  break;
1047  case OBJECT_TYPE:
1048  all_privileges = ACL_ALL_RIGHTS_TYPE;
1049  errormsg = gettext_noop("invalid privilege type %s for type");
1050  break;
1051  case OBJECT_SCHEMA:
1052  all_privileges = ACL_ALL_RIGHTS_SCHEMA;
1053  errormsg = gettext_noop("invalid privilege type %s for schema");
1054  break;
1055  default:
1056  elog(ERROR, "unrecognized GrantStmt.objtype: %d",
1057  (int) action->objtype);
1058  /* keep compiler quiet */
1059  all_privileges = ACL_NO_RIGHTS;
1060  errormsg = NULL;
1061  }
1062 
1063  if (action->privileges == NIL)
1064  {
1065  iacls.all_privs = true;
1066 
1067  /*
1068  * will be turned into ACL_ALL_RIGHTS_* by the internal routines
1069  * depending on the object type
1070  */
1071  iacls.privileges = ACL_NO_RIGHTS;
1072  }
1073  else
1074  {
1075  iacls.all_privs = false;
1076  iacls.privileges = ACL_NO_RIGHTS;
1077 
1078  foreach(cell, action->privileges)
1079  {
1080  AccessPriv *privnode = (AccessPriv *) lfirst(cell);
1081  AclMode priv;
1082 
1083  if (privnode->cols)
1084  ereport(ERROR,
1085  (errcode(ERRCODE_INVALID_GRANT_OPERATION),
1086  errmsg("default privileges cannot be set for columns")));
1087 
1088  if (privnode->priv_name == NULL) /* parser mistake? */
1089  elog(ERROR, "AccessPriv node must specify privilege");
1090  priv = string_to_privilege(privnode->priv_name);
1091 
1092  if (priv & ~((AclMode) all_privileges))
1093  ereport(ERROR,
1094  (errcode(ERRCODE_INVALID_GRANT_OPERATION),
1095  errmsg(errormsg, privilege_to_string(priv))));
1096 
1097  iacls.privileges |= priv;
1098  }
1099  }
1100 
1101  if (rolespecs == NIL)
1102  {
1103  /* Set permissions for myself */
1104  iacls.roleid = GetUserId();
1105 
1106  SetDefaultACLsInSchemas(&iacls, nspnames);
1107  }
1108  else
1109  {
1110  /* Look up the role OIDs and do permissions checks */
1111  ListCell *rolecell;
1112 
1113  foreach(rolecell, rolespecs)
1114  {
1115  RoleSpec *rolespec = lfirst(rolecell);
1116 
1117  iacls.roleid = get_rolespec_oid(rolespec, false);
1118 
1119  /*
1120  * We insist that calling user be a member of each target role. If
1121  * he has that, he could become that role anyway via SET ROLE, so
1122  * FOR ROLE is just a syntactic convenience and doesn't give any
1123  * special privileges.
1124  */
1126 
1127  SetDefaultACLsInSchemas(&iacls, nspnames);
1128  }
1129  }
1130 }
void check_is_member_of_role(Oid member, Oid role)
Definition: acl.c:4977
Oid get_rolespec_oid(const RoleSpec *role, bool missing_ok)
Definition: acl.c:5185
static AclMode string_to_privilege(const char *privname)
Definition: aclchk.c:3426
static void SetDefaultACLsInSchemas(InternalDefaultACL *iacls, List *nspnames)
Definition: aclchk.c:1138
static const char * privilege_to_string(AclMode privilege)
Definition: aclchk.c:3467
void errorConflictingDefElem(DefElem *defel, ParseState *pstate)
Definition: define.c:352
if(TABLE==NULL||TABLE_index==NULL)
Definition: isn.c:77
List * lappend_oid(List *list, Oid datum)
Definition: list.c:374
Oid GetUserId(void)
Definition: miscinit.c:491
@ ROLESPEC_PUBLIC
Definition: parsenodes.h:353
#define lfirst(lc)
Definition: pg_list.h:170
#define NIL
Definition: pg_list.h:66
char * priv_name
Definition: parsenodes.h:2423
List * cols
Definition: parsenodes.h:2424
char * defname
Definition: parsenodes.h:766
Node * arg
Definition: parsenodes.h:767
bool grant_option
Definition: aclchk.c:94
AclMode privileges
Definition: aclchk.c:92
List * grantees
Definition: aclchk.c:93
DropBehavior behavior
Definition: aclchk.c:95
ObjectType objtype
Definition: aclchk.c:90
Definition: pg_list.h:52

References ACL_ALL_RIGHTS_FUNCTION, ACL_ALL_RIGHTS_RELATION, ACL_ALL_RIGHTS_SCHEMA, ACL_ALL_RIGHTS_SEQUENCE, ACL_ALL_RIGHTS_TYPE, ACL_ID_PUBLIC, ACL_NO_RIGHTS, generate_unaccent_rules::action, AlterDefaultPrivilegesStmt::action, InternalDefaultACL::all_privs, DefElem::arg, InternalDefaultACL::behavior, check_is_member_of_role(), AccessPriv::cols, DefElem::defname, elog(), ereport, errcode(), errmsg(), ERROR, errorConflictingDefElem(), get_rolespec_oid(), gettext_noop, GetUserId(), InternalDefaultACL::grant_option, InternalDefaultACL::grantees, if(), InternalDefaultACL::is_grant, lappend_oid(), lfirst, NIL, OBJECT_FUNCTION, OBJECT_PROCEDURE, OBJECT_ROUTINE, OBJECT_SCHEMA, OBJECT_SEQUENCE, OBJECT_TABLE, OBJECT_TYPE, InternalDefaultACL::objtype, AlterDefaultPrivilegesStmt::options, AccessPriv::priv_name, privilege_to_string(), InternalDefaultACL::privileges, InternalDefaultACL::roleid, ROLESPEC_PUBLIC, RoleSpec::roletype, SetDefaultACLsInSchemas(), and string_to_privilege().

Referenced by ProcessUtilitySlow().

◆ ExecuteGrantStmt()

void ExecuteGrantStmt ( GrantStmt stmt)

Definition at line 366 of file aclchk.c.

367 {
368  InternalGrant istmt;
369  ListCell *cell;
370  const char *errormsg;
371  AclMode all_privileges;
372 
373  if (stmt->grantor)
374  {
375  Oid grantor;
376 
377  grantor = get_rolespec_oid(stmt->grantor, false);
378 
379  /*
380  * Currently, this clause is only for SQL compatibility, not very
381  * interesting otherwise.
382  */
383  if (grantor != GetUserId())
384  ereport(ERROR,
385  (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
386  errmsg("grantor must be current user")));
387  }
388 
389  /*
390  * Turn the regular GrantStmt into the InternalGrant form.
391  */
392  istmt.is_grant = stmt->is_grant;
393  istmt.objtype = stmt->objtype;
394 
395  /* Collect the OIDs of the target objects */
396  switch (stmt->targtype)
397  {
398  case ACL_TARGET_OBJECT:
399  istmt.objects = objectNamesToOids(stmt->objtype, stmt->objects,
400  stmt->is_grant);
401  break;
403  istmt.objects = objectsInSchemaToOids(stmt->objtype, stmt->objects);
404  break;
405  /* ACL_TARGET_DEFAULTS should not be seen here */
406  default:
407  elog(ERROR, "unrecognized GrantStmt.targtype: %d",
408  (int) stmt->targtype);
409  }
410 
411  /* all_privs to be filled below */
412  /* privileges to be filled below */
413  istmt.col_privs = NIL; /* may get filled below */
414  istmt.grantees = NIL; /* filled below */
415  istmt.grant_option = stmt->grant_option;
416  istmt.behavior = stmt->behavior;
417 
418  /*
419  * Convert the RoleSpec list into an Oid list. Note that at this point we
420  * insert an ACL_ID_PUBLIC into the list if appropriate, so downstream
421  * there shouldn't be any additional work needed to support this case.
422  */
423  foreach(cell, stmt->grantees)
424  {
425  RoleSpec *grantee = (RoleSpec *) lfirst(cell);
426  Oid grantee_uid;
427 
428  switch (grantee->roletype)
429  {
430  case ROLESPEC_PUBLIC:
431  grantee_uid = ACL_ID_PUBLIC;
432  break;
433  default:
434  grantee_uid = get_rolespec_oid(grantee, false);
435  break;
436  }
437  istmt.grantees = lappend_oid(istmt.grantees, grantee_uid);
438  }
439 
440  /*
441  * Convert stmt->privileges, a list of AccessPriv nodes, into an AclMode
442  * bitmask. Note: objtype can't be OBJECT_COLUMN.
443  */
444  switch (stmt->objtype)
445  {
446  case OBJECT_TABLE:
447 
448  /*
449  * Because this might be a sequence, we test both relation and
450  * sequence bits, and later do a more limited test when we know
451  * the object type.
452  */
454  errormsg = gettext_noop("invalid privilege type %s for relation");
455  break;
456  case OBJECT_SEQUENCE:
457  all_privileges = ACL_ALL_RIGHTS_SEQUENCE;
458  errormsg = gettext_noop("invalid privilege type %s for sequence");
459  break;
460  case OBJECT_DATABASE:
461  all_privileges = ACL_ALL_RIGHTS_DATABASE;
462  errormsg = gettext_noop("invalid privilege type %s for database");
463  break;
464  case OBJECT_DOMAIN:
465  all_privileges = ACL_ALL_RIGHTS_TYPE;
466  errormsg = gettext_noop("invalid privilege type %s for domain");
467  break;
468  case OBJECT_FUNCTION:
469  all_privileges = ACL_ALL_RIGHTS_FUNCTION;
470  errormsg = gettext_noop("invalid privilege type %s for function");
471  break;
472  case OBJECT_LANGUAGE:
473  all_privileges = ACL_ALL_RIGHTS_LANGUAGE;
474  errormsg = gettext_noop("invalid privilege type %s for language");
475  break;
476  case OBJECT_LARGEOBJECT:
477  all_privileges = ACL_ALL_RIGHTS_LARGEOBJECT;
478  errormsg = gettext_noop("invalid privilege type %s for large object");
479  break;
480  case OBJECT_SCHEMA:
481  all_privileges = ACL_ALL_RIGHTS_SCHEMA;
482  errormsg = gettext_noop("invalid privilege type %s for schema");
483  break;
484  case OBJECT_PROCEDURE:
485  all_privileges = ACL_ALL_RIGHTS_FUNCTION;
486  errormsg = gettext_noop("invalid privilege type %s for procedure");
487  break;
488  case OBJECT_ROUTINE:
489  all_privileges = ACL_ALL_RIGHTS_FUNCTION;
490  errormsg = gettext_noop("invalid privilege type %s for routine");
491  break;
492  case OBJECT_TABLESPACE:
493  all_privileges = ACL_ALL_RIGHTS_TABLESPACE;
494  errormsg = gettext_noop("invalid privilege type %s for tablespace");
495  break;
496  case OBJECT_TYPE:
497  all_privileges = ACL_ALL_RIGHTS_TYPE;
498  errormsg = gettext_noop("invalid privilege type %s for type");
499  break;
500  case OBJECT_FDW:
501  all_privileges = ACL_ALL_RIGHTS_FDW;
502  errormsg = gettext_noop("invalid privilege type %s for foreign-data wrapper");
503  break;
505  all_privileges = ACL_ALL_RIGHTS_FOREIGN_SERVER;
506  errormsg = gettext_noop("invalid privilege type %s for foreign server");
507  break;
509  all_privileges = ACL_ALL_RIGHTS_PARAMETER_ACL;
510  errormsg = gettext_noop("invalid privilege type %s for parameter");
511  break;
512  default:
513  elog(ERROR, "unrecognized GrantStmt.objtype: %d",
514  (int) stmt->objtype);
515  /* keep compiler quiet */
516  all_privileges = ACL_NO_RIGHTS;
517  errormsg = NULL;
518  }
519 
520  if (stmt->privileges == NIL)
521  {
522  istmt.all_privs = true;
523 
524  /*
525  * will be turned into ACL_ALL_RIGHTS_* by the internal routines
526  * depending on the object type
527  */
528  istmt.privileges = ACL_NO_RIGHTS;
529  }
530  else
531  {
532  istmt.all_privs = false;
533  istmt.privileges = ACL_NO_RIGHTS;
534 
535  foreach(cell, stmt->privileges)
536  {
537  AccessPriv *privnode = (AccessPriv *) lfirst(cell);
538  AclMode priv;
539 
540  /*
541  * If it's a column-level specification, we just set it aside in
542  * col_privs for the moment; but insist it's for a relation.
543  */
544  if (privnode->cols)
545  {
546  if (stmt->objtype != OBJECT_TABLE)
547  ereport(ERROR,
548  (errcode(ERRCODE_INVALID_GRANT_OPERATION),
549  errmsg("column privileges are only valid for relations")));
550  istmt.col_privs = lappend(istmt.col_privs, privnode);
551  continue;
552  }
553 
554  if (privnode->priv_name == NULL) /* parser mistake? */
555  elog(ERROR, "AccessPriv node must specify privilege or columns");
556  priv = string_to_privilege(privnode->priv_name);
557 
558  if (priv & ~((AclMode) all_privileges))
559  ereport(ERROR,
560  (errcode(ERRCODE_INVALID_GRANT_OPERATION),
561  errmsg(errormsg, privilege_to_string(priv))));
562 
563  istmt.privileges |= priv;
564  }
565  }
566 
567  ExecGrantStmt_oids(&istmt);
568 }
static void ExecGrantStmt_oids(InternalGrant *istmt)
Definition: aclchk.c:576
static List * objectNamesToOids(ObjectType objtype, List *objnames, bool is_grant)
Definition: aclchk.c:643
static List * objectsInSchemaToOids(ObjectType objtype, List *nspnames)
Definition: aclchk.c:823
List * lappend(List *list, void *datum)
Definition: list.c:338
@ ACL_TARGET_OBJECT
Definition: parsenodes.h:2366
@ ACL_TARGET_ALL_IN_SCHEMA
Definition: parsenodes.h:2367
ObjectType objtype
Definition: parsenodes.h:2376
bool is_grant
Definition: parsenodes.h:2374
List * objects
Definition: parsenodes.h:2377
bool grant_option
Definition: parsenodes.h:2382
List * grantees
Definition: parsenodes.h:2381
List * privileges
Definition: parsenodes.h:2379
GrantTargetType targtype
Definition: parsenodes.h:2375
DropBehavior behavior
Definition: parsenodes.h:2384
RoleSpec * grantor
Definition: parsenodes.h:2383
DropBehavior behavior
AclMode privileges
ObjectType objtype

References ACL_ALL_RIGHTS_DATABASE, ACL_ALL_RIGHTS_FDW, ACL_ALL_RIGHTS_FOREIGN_SERVER, ACL_ALL_RIGHTS_FUNCTION, ACL_ALL_RIGHTS_LANGUAGE, ACL_ALL_RIGHTS_LARGEOBJECT, ACL_ALL_RIGHTS_PARAMETER_ACL, ACL_ALL_RIGHTS_RELATION, ACL_ALL_RIGHTS_SCHEMA, ACL_ALL_RIGHTS_SEQUENCE, ACL_ALL_RIGHTS_TABLESPACE, ACL_ALL_RIGHTS_TYPE, ACL_ID_PUBLIC, ACL_NO_RIGHTS, ACL_TARGET_ALL_IN_SCHEMA, ACL_TARGET_OBJECT, InternalGrant::all_privs, GrantStmt::behavior, InternalGrant::behavior, InternalGrant::col_privs, AccessPriv::cols, elog(), ereport, errcode(), errmsg(), ERROR, ExecGrantStmt_oids(), get_rolespec_oid(), gettext_noop, GetUserId(), GrantStmt::grant_option, InternalGrant::grant_option, GrantStmt::grantees, InternalGrant::grantees, GrantStmt::grantor, GrantStmt::is_grant, InternalGrant::is_grant, lappend(), lappend_oid(), lfirst, NIL, OBJECT_DATABASE, OBJECT_DOMAIN, OBJECT_FDW, OBJECT_FOREIGN_SERVER, OBJECT_FUNCTION, OBJECT_LANGUAGE, OBJECT_LARGEOBJECT, OBJECT_PARAMETER_ACL, OBJECT_PROCEDURE, OBJECT_ROUTINE, OBJECT_SCHEMA, OBJECT_SEQUENCE, OBJECT_TABLE, OBJECT_TABLESPACE, OBJECT_TYPE, objectNamesToOids(), GrantStmt::objects, InternalGrant::objects, objectsInSchemaToOids(), GrantStmt::objtype, InternalGrant::objtype, AccessPriv::priv_name, privilege_to_string(), GrantStmt::privileges, InternalGrant::privileges, ROLESPEC_PUBLIC, RoleSpec::roletype, string_to_privilege(), and GrantStmt::targtype.

Referenced by ProcessUtilitySlow(), and standard_ProcessUtility().

◆ get_role_oid()

Oid get_role_oid ( const char *  rolename,
bool  missing_ok 
)

Definition at line 5151 of file acl.c.

5152 {
5153  Oid oid;
5154 
5155  oid = GetSysCacheOid1(AUTHNAME, Anum_pg_authid_oid,
5157  if (!OidIsValid(oid) && !missing_ok)
5158  ereport(ERROR,
5159  (errcode(ERRCODE_UNDEFINED_OBJECT),
5160  errmsg("role \"%s\" does not exist", rolname)));
5161  return oid;
5162 }
#define OidIsValid(objectId)
Definition: c.h:721
NameData rolname
Definition: pg_authid.h:34
#define CStringGetDatum(X)
Definition: postgres.h:622
@ AUTHNAME
Definition: syscache.h:44
#define GetSysCacheOid1(cacheId, oidcol, key1)
Definition: syscache.h:197

References AUTHNAME, CStringGetDatum, ereport, errcode(), errmsg(), ERROR, GetSysCacheOid1, OidIsValid, and rolname.

Referenced by aclparse(), check_hba(), createdb(), CreateRole(), get_object_address_unqualified(), get_role_oid_or_public(), get_rolespec_oid(), GrantRole(), is_member(), pg_has_role_id_name(), pg_has_role_name(), pg_has_role_name_id(), pg_has_role_name_name(), regrolein(), shell_check_detail(), and to_regrole().

◆ get_role_oid_or_public()

◆ get_rolespec_name()

char* get_rolespec_name ( const RoleSpec role)

Definition at line 5270 of file acl.c.

5271 {
5272  HeapTuple tp;
5273  Form_pg_authid authForm;
5274  char *rolename;
5275 
5276  tp = get_rolespec_tuple(role);
5277  authForm = (Form_pg_authid) GETSTRUCT(tp);
5278  rolename = pstrdup(NameStr(authForm->rolname));
5279  ReleaseSysCache(tp);
5280 
5281  return rolename;
5282 }
HeapTuple get_rolespec_tuple(const RoleSpec *role)
Definition: acl.c:5224
#define NameStr(name)
Definition: c.h:692
#define GETSTRUCT(TUP)
Definition: htup_details.h:649
char * pstrdup(const char *in)
Definition: mcxt.c:1305
FormData_pg_authid * Form_pg_authid
Definition: pg_authid.h:56
void ReleaseSysCache(HeapTuple tuple)
Definition: syscache.c:1221

References get_rolespec_tuple(), GETSTRUCT, NameStr, pstrdup(), and ReleaseSysCache().

Referenced by AddRoleMems(), and DelRoleMems().

◆ get_rolespec_oid()

Oid get_rolespec_oid ( const RoleSpec role,
bool  missing_ok 
)

Definition at line 5185 of file acl.c.

5186 {
5187  Oid oid;
5188 
5189  switch (role->roletype)
5190  {
5191  case ROLESPEC_CSTRING:
5192  Assert(role->rolename);
5193  oid = get_role_oid(role->rolename, missing_ok);
5194  break;
5195 
5196  case ROLESPEC_CURRENT_ROLE:
5197  case ROLESPEC_CURRENT_USER:
5198  oid = GetUserId();
5199  break;
5200 
5201  case ROLESPEC_SESSION_USER:
5202  oid = GetSessionUserId();
5203  break;
5204 
5205  case ROLESPEC_PUBLIC:
5206  ereport(ERROR,
5207  (errcode(ERRCODE_UNDEFINED_OBJECT),
5208  errmsg("role \"%s\" does not exist", "public")));
5209  oid = InvalidOid; /* make compiler happy */
5210  break;
5211 
5212  default:
5213  elog(ERROR, "unexpected role type %d", role->roletype);
5214  }
5215 
5216  return oid;
5217 }
Oid GetSessionUserId(void)
Definition: miscinit.c:525
@ ROLESPEC_CURRENT_USER
Definition: parsenodes.h:351
@ ROLESPEC_SESSION_USER
Definition: parsenodes.h:352
@ ROLESPEC_CURRENT_ROLE
Definition: parsenodes.h:350
#define InvalidOid
Definition: postgres_ext.h:36

References Assert(), elog(), ereport, errcode(), errmsg(), ERROR, get_role_oid(), GetSessionUserId(), GetUserId(), InvalidOid, RoleSpec::rolename, ROLESPEC_CSTRING, ROLESPEC_CURRENT_ROLE, ROLESPEC_CURRENT_USER, ROLESPEC_PUBLIC, ROLESPEC_SESSION_USER, and RoleSpec::roletype.

Referenced by AlterUserMapping(), ATExecCmd(), CreateSchemaCommand(), CreateTableSpace(), CreateUserMapping(), ExecAlterDefaultPrivilegesStmt(), ExecAlterOwnerStmt(), ExecuteGrantStmt(), GrantRole(), policy_role_list_to_array(), ReassignOwnedObjects(), RemoveUserMapping(), and roleSpecsToIds().

◆ get_rolespec_tuple()

HeapTuple get_rolespec_tuple ( const RoleSpec role)

Definition at line 5224 of file acl.c.

5225 {
5226  HeapTuple tuple;
5227 
5228  switch (role->roletype)
5229  {
5230  case ROLESPEC_CSTRING:
5231  Assert(role->rolename);
5233  if (!HeapTupleIsValid(tuple))
5234  ereport(ERROR,
5235  (errcode(ERRCODE_UNDEFINED_OBJECT),
5236  errmsg("role \"%s\" does not exist", role->rolename)));
5237  break;
5238 
5239  case ROLESPEC_CURRENT_ROLE:
5240  case ROLESPEC_CURRENT_USER:
5241  tuple = SearchSysCache1(AUTHOID, GetUserId());
5242  if (!HeapTupleIsValid(tuple))
5243  elog(ERROR, "cache lookup failed for role %u", GetUserId());
5244  break;
5245 
5246  case ROLESPEC_SESSION_USER:
5248  if (!HeapTupleIsValid(tuple))
5249  elog(ERROR, "cache lookup failed for role %u", GetSessionUserId());
5250  break;
5251 
5252  case ROLESPEC_PUBLIC:
5253  ereport(ERROR,
5254  (errcode(ERRCODE_UNDEFINED_OBJECT),
5255  errmsg("role \"%s\" does not exist", "public")));
5256  tuple = NULL; /* make compiler happy */
5257  break;
5258 
5259  default:
5260  elog(ERROR, "unexpected role type %d", role->roletype);
5261  }
5262 
5263  return tuple;
5264 }
#define HeapTupleIsValid(tuple)
Definition: htup.h:78
HeapTuple SearchSysCache1(int cacheId, Datum key1)
Definition: syscache.c:1173
@ AUTHOID
Definition: syscache.h:45

References Assert(), AUTHNAME, AUTHOID, CStringGetDatum, elog(), ereport, errcode(), errmsg(), ERROR, GetSessionUserId(), GetUserId(), HeapTupleIsValid, RoleSpec::rolename, ROLESPEC_CSTRING, ROLESPEC_CURRENT_ROLE, ROLESPEC_CURRENT_USER, ROLESPEC_PUBLIC, ROLESPEC_SESSION_USER, RoleSpec::roletype, and SearchSysCache1().

Referenced by AlterRole(), AlterRoleSet(), CreateRole(), and get_rolespec_name().

◆ get_user_default_acl()

Acl* get_user_default_acl ( ObjectType  objtype,
Oid  ownerId,
Oid  nsp_oid 
)

Definition at line 5874 of file aclchk.c.

5875 {
5876  Acl *result;
5877  Acl *glob_acl;
5878  Acl *schema_acl;
5879  Acl *def_acl;
5880  char defaclobjtype;
5881 
5882  /*
5883  * Use NULL during bootstrap, since pg_default_acl probably isn't there
5884  * yet.
5885  */
5887  return NULL;
5888 
5889  /* Check if object type is supported in pg_default_acl */
5890  switch (objtype)
5891  {
5892  case OBJECT_TABLE:
5893  defaclobjtype = DEFACLOBJ_RELATION;
5894  break;
5895 
5896  case OBJECT_SEQUENCE:
5897  defaclobjtype = DEFACLOBJ_SEQUENCE;
5898  break;
5899 
5900  case OBJECT_FUNCTION:
5901  defaclobjtype = DEFACLOBJ_FUNCTION;
5902  break;
5903 
5904  case OBJECT_TYPE:
5905  defaclobjtype = DEFACLOBJ_TYPE;
5906  break;
5907 
5908  case OBJECT_SCHEMA:
5909  defaclobjtype = DEFACLOBJ_NAMESPACE;
5910  break;
5911 
5912  default:
5913  return NULL;
5914  }
5915 
5916  /* Look up the relevant pg_default_acl entries */
5917  glob_acl = get_default_acl_internal(ownerId, InvalidOid, defaclobjtype);
5918  schema_acl = get_default_acl_internal(ownerId, nsp_oid, defaclobjtype);
5919 
5920  /* Quick out if neither entry exists */
5921  if (glob_acl == NULL && schema_acl == NULL)
5922  return NULL;
5923 
5924  /* We need to know the hard-wired default value, too */
5925  def_acl = acldefault(objtype, ownerId);
5926 
5927  /* If there's no global entry, substitute the hard-wired default */
5928  if (glob_acl == NULL)
5929  glob_acl = def_acl;
5930 
5931  /* Merge in any per-schema privileges */
5932  result = aclmerge(glob_acl, schema_acl, ownerId);
5933 
5934  /*
5935  * For efficiency, we want to return NULL if the result equals default.
5936  * This requires sorting both arrays to get an accurate comparison.
5937  */
5938  aclitemsort(result);
5939  aclitemsort(def_acl);
5940  if (aclequal(result, def_acl))
5941  result = NULL;
5942 
5943  return result;
5944 }
bool aclequal(const Acl *left_acl, const Acl *right_acl)
Definition: acl.c:503
void aclitemsort(Acl *acl)
Definition: acl.c:489
Acl * acldefault(ObjectType objtype, Oid ownerId)
Definition: acl.c:742
Acl * aclmerge(const Acl *left_acl, const Acl *right_acl, Oid ownerId)
Definition: acl.c:445
static Acl * get_default_acl_internal(Oid roleId, Oid nsp_oid, char objtype)
Definition: aclchk.c:5839
#define IsBootstrapProcessingMode()
Definition: miscadmin.h:406

References acldefault(), aclequal(), aclitemsort(), aclmerge(), get_default_acl_internal(), InvalidOid, IsBootstrapProcessingMode, OBJECT_FUNCTION, OBJECT_SCHEMA, OBJECT_SEQUENCE, OBJECT_TABLE, and OBJECT_TYPE.

Referenced by heap_create_with_catalog(), NamespaceCreate(), ProcedureCreate(), and TypeCreate().

◆ has_bypassrls_privilege()

bool has_bypassrls_privilege ( Oid  roleid)

Definition at line 5815 of file aclchk.c.

5816 {
5817  bool result = false;
5818  HeapTuple utup;
5819 
5820  /* Superusers bypass all permission checking. */
5821  if (superuser_arg(roleid))
5822  return true;
5823 
5824  utup = SearchSysCache1(AUTHOID, ObjectIdGetDatum(roleid));
5825  if (HeapTupleIsValid(utup))
5826  {
5827  result = ((Form_pg_authid) GETSTRUCT(utup))->rolbypassrls;
5828  ReleaseSysCache(utup);
5829  }
5830  return result;
5831 }
bool rolbypassrls
Definition: pg_authid.h:41
#define ObjectIdGetDatum(X)
Definition: postgres.h:551
bool superuser_arg(Oid roleid)
Definition: superuser.c:56

References AUTHOID, GETSTRUCT, HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), rolbypassrls, SearchSysCache1(), and superuser_arg().

Referenced by check_enable_rls(), and RI_Initial_Check().

◆ has_createrole_privilege()

bool has_createrole_privilege ( Oid  roleid)

Definition at line 5796 of file aclchk.c.

5797 {
5798  bool result = false;
5799  HeapTuple utup;
5800 
5801  /* Superusers bypass all permission checking. */
5802  if (superuser_arg(roleid))
5803  return true;
5804 
5805  utup = SearchSysCache1(AUTHOID, ObjectIdGetDatum(roleid));
5806  if (HeapTupleIsValid(utup))
5807  {
5808  result = ((Form_pg_authid) GETSTRUCT(utup))->rolcreaterole;
5809  ReleaseSysCache(utup);
5810  }
5811  return result;
5812 }
bool rolcreaterole
Definition: pg_authid.h:37

References AUTHOID, GETSTRUCT, HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), rolcreaterole, SearchSysCache1(), and superuser_arg().

Referenced by check_object_ownership(), and have_createrole_privilege().

◆ has_privs_of_role()

bool has_privs_of_role ( Oid  member,
Oid  role 
)

Definition at line 4925 of file acl.c.

4926 {
4927  /* Fast path for simple case */
4928  if (member == role)
4929  return true;
4930 
4931  /* Superusers have every privilege, so are part of every role */
4932  if (superuser_arg(member))
4933  return true;
4934 
4935  /*
4936  * Find all the roles that member has the privileges of, including
4937  * multi-level recursion, then see if target role is any one of them.
4938  */
4940  InvalidOid, NULL),
4941  role);
4942 }
@ ROLERECURSE_PRIVS
Definition: acl.c:69
static List * roles_is_member_of(Oid roleid, enum RoleRecurseType type, Oid admin_of, bool *is_admin)
Definition: acl.c:4808
bool list_member_oid(const List *list, Oid datum)
Definition: list.c:721

References InvalidOid, list_member_oid(), ROLERECURSE_PRIVS, roles_is_member_of(), and superuser_arg().

Referenced by aclmask(), AlterObjectNamespace_internal(), AlterObjectOwner_internal(), AlterObjectRename_internal(), bbsink_server_new(), calculate_database_size(), calculate_tablespace_size(), check_role_for_policy(), convert_and_check_filename(), DoCopy(), DropOwnedObjects(), file_fdw_validator(), get_explain_guc_options(), GetConfigOption(), GetConfigOptionByName(), GetConfigOptionByNum(), GetConfigOptionResetString(), pg_class_aclmask_ext(), pg_class_ownercheck(), pg_collation_ownercheck(), pg_conversion_ownercheck(), pg_database_ownercheck(), pg_event_trigger_ownercheck(), pg_extension_ownercheck(), pg_foreign_data_wrapper_ownercheck(), pg_foreign_server_ownercheck(), pg_language_ownercheck(), pg_largeobject_ownercheck(), pg_namespace_aclmask(), pg_namespace_ownercheck(), pg_opclass_ownercheck(), pg_oper_ownercheck(), pg_opfamily_ownercheck(), pg_proc_ownercheck(), pg_publication_ownercheck(), pg_role_aclcheck(), pg_signal_backend(), pg_stat_get_wal_receiver(), pg_stat_get_wal_senders(), pg_stat_statements_internal(), pg_statistics_object_ownercheck(), pg_subscription_ownercheck(), pg_tablespace_ownercheck(), pg_ts_config_ownercheck(), pg_ts_dict_ownercheck(), pg_type_ownercheck(), pgrowlocks(), ReassignOwnedObjects(), shell_check_detail(), ShowAllGUCConfig(), standard_ProcessUtility(), and TerminateOtherDBBackends().

◆ initialize_acl()

void initialize_acl ( void  )

Definition at line 4730 of file acl.c.

4731 {
4733  {
4734  cached_db_hash =
4737 
4738  /*
4739  * In normal mode, set a callback on any syscache invalidation of rows
4740  * of pg_auth_members (for roles_is_member_of()), pg_authid (for
4741  * has_rolinherit()), or pg_database (for roles_is_member_of())
4742  */
4745  (Datum) 0);
4748  (Datum) 0);
4751  (Datum) 0);
4752  }
4753 }
static uint32 cached_db_hash
Definition: acl.c:74
static void RoleMembershipCacheCallback(Datum arg, int cacheid, uint32 hashvalue)
Definition: acl.c:4760
Oid MyDatabaseId
Definition: globals.c:89
void CacheRegisterSyscacheCallback(int cacheid, SyscacheCallbackFunction func, Datum arg)
Definition: inval.c:1519
uintptr_t Datum
Definition: postgres.h:411
@ AUTHMEMROLEMEM
Definition: syscache.h:43
@ DATABASEOID
Definition: syscache.h:55
#define GetSysCacheHashValue1(cacheId, key1)
Definition: syscache.h:206

References AUTHMEMROLEMEM, AUTHOID, cached_db_hash, CacheRegisterSyscacheCallback(), DATABASEOID, GetSysCacheHashValue1, IsBootstrapProcessingMode, MyDatabaseId, ObjectIdGetDatum, and RoleMembershipCacheCallback().

Referenced by InitPostgres().

◆ is_admin_of_role()

bool is_admin_of_role ( Oid  member,
Oid  role 
)

Definition at line 5017 of file acl.c.

5018 {
5019  bool result = false;
5020 
5021  if (superuser_arg(member))
5022  return true;
5023 
5024  /* By policy, a role cannot have WITH ADMIN OPTION on itself. */
5025  if (member == role)
5026  return false;
5027 
5028  (void) roles_is_member_of(member, ROLERECURSE_MEMBERS, role, &result);
5029  return result;
5030 }
@ ROLERECURSE_MEMBERS
Definition: acl.c:70

References ROLERECURSE_MEMBERS, roles_is_member_of(), and superuser_arg().

Referenced by AddRoleMems(), DelRoleMems(), and pg_role_aclcheck().

◆ is_member_of_role()

bool is_member_of_role ( Oid  member,
Oid  role 
)

Definition at line 4953 of file acl.c.

4954 {
4955  /* Fast path for simple case */
4956  if (member == role)
4957  return true;
4958 
4959  /* Superusers have every privilege, so are part of every role */
4960  if (superuser_arg(member))
4961  return true;
4962 
4963  /*
4964  * Find all the roles that member is a member of, including multi-level
4965  * recursion, then see if target role is any one of them.
4966  */
4968  InvalidOid, NULL),
4969  role);
4970 }

References InvalidOid, list_member_oid(), ROLERECURSE_MEMBERS, roles_is_member_of(), and superuser_arg().

Referenced by check_is_member_of_role(), check_role(), and pg_role_aclcheck().

◆ is_member_of_role_nosuper()

bool is_member_of_role_nosuper ( Oid  member,
Oid  role 
)

Definition at line 4995 of file acl.c.

4996 {
4997  /* Fast path for simple case */
4998  if (member == role)
4999  return true;
5000 
5001  /*
5002  * Find all the roles that member is a member of, including multi-level
5003  * recursion, then see if target role is any one of them.
5004  */
5006  InvalidOid, NULL),
5007  role);
5008 }

References InvalidOid, list_member_oid(), ROLERECURSE_MEMBERS, and roles_is_member_of().

Referenced by AddRoleMems(), and is_member().

◆ make_empty_acl()

Acl* make_empty_acl ( void  )

Definition at line 392 of file acl.c.

393 {
394  return allocacl(0);
395 }

References allocacl().

Referenced by SetDefaultACL().

◆ pg_attribute_aclcheck()

AclResult pg_attribute_aclcheck ( Oid  table_oid,
AttrNumber  attnum,
Oid  roleid,
AclMode  mode 
)

Definition at line 4878 of file aclchk.c.

4880 {
4881  return pg_attribute_aclcheck_ext(table_oid, attnum, roleid, mode, NULL);
4882 }
AclResult pg_attribute_aclcheck_ext(Oid table_oid, AttrNumber attnum, Oid roleid, AclMode mode, bool *is_missing)
Definition: aclchk.c:4892
int16 attnum
Definition: pg_attribute.h:83
static PgChecksumMode mode
Definition: pg_checksums.c:65

References attnum, mode, and pg_attribute_aclcheck_ext().

Referenced by BuildIndexValueDescription(), checkFkeyPermissions(), examine_simple_variable(), ExecBuildSlotPartitionKeyDescription(), ExecBuildSlotValueDescription(), ExecCheckRTEPerms(), ExecCheckRTEPermsModified(), ri_ReportViolation(), and statext_is_compatible_clause().

◆ pg_attribute_aclcheck_all()

AclResult pg_attribute_aclcheck_all ( Oid  table_oid,
Oid  roleid,
AclMode  mode,
AclMaskHow  how 
)

Definition at line 4922 of file aclchk.c.

4924 {
4925  AclResult result;
4926  HeapTuple classTuple;
4927  Form_pg_class classForm;
4928  AttrNumber nattrs;
4929  AttrNumber curr_att;
4930 
4931  /*
4932  * Must fetch pg_class row to check number of attributes. As in
4933  * pg_attribute_aclmask, we prefer to return "no privileges" instead of
4934  * throwing an error if we get any unexpected lookup errors.
4935  */
4936  classTuple = SearchSysCache1(RELOID, ObjectIdGetDatum(table_oid));
4937  if (!HeapTupleIsValid(classTuple))
4938  return ACLCHECK_NO_PRIV;
4939  classForm = (Form_pg_class) GETSTRUCT(classTuple);
4940 
4941  nattrs = classForm->relnatts;
4942 
4943  ReleaseSysCache(classTuple);
4944 
4945  /*
4946  * Initialize result in case there are no non-dropped columns. We want to
4947  * report failure in such cases for either value of 'how'.
4948  */
4949  result = ACLCHECK_NO_PRIV;
4950 
4951  for (curr_att = 1; curr_att <= nattrs; curr_att++)
4952  {
4953  HeapTuple attTuple;
4954  AclMode attmask;
4955 
4956  attTuple = SearchSysCache2(ATTNUM,
4957  ObjectIdGetDatum(table_oid),
4958  Int16GetDatum(curr_att));
4959  if (!HeapTupleIsValid(attTuple))
4960  continue;
4961 
4962  /* ignore dropped columns */
4963  if (((Form_pg_attribute) GETSTRUCT(attTuple))->attisdropped)
4964  {
4965  ReleaseSysCache(attTuple);
4966  continue;
4967  }
4968 
4969  /*
4970  * Here we hard-wire knowledge that the default ACL for a column
4971  * grants no privileges, so that we can fall out quickly in the very
4972  * common case where attacl is null.
4973  */
4974  if (heap_attisnull(attTuple, Anum_pg_attribute_attacl, NULL))
4975  attmask = 0;
4976  else
4977  attmask = pg_attribute_aclmask(table_oid, curr_att, roleid,
4978  mode, ACLMASK_ANY);
4979 
4980  ReleaseSysCache(attTuple);
4981 
4982  if (attmask != 0)
4983  {
4984  result = ACLCHECK_OK;
4985  if (how == ACLMASK_ANY)
4986  break; /* succeed on any success */
4987  }
4988  else
4989  {
4990  result = ACLCHECK_NO_PRIV;
4991  if (how == ACLMASK_ALL)
4992  break; /* fail on any failure */
4993  }
4994  }
4995 
4996  return result;
4997 }
AclMode pg_attribute_aclmask(Oid table_oid, AttrNumber attnum, Oid roleid, AclMode mask, AclMaskHow how)
Definition: aclchk.c:3913
int16 AttrNumber
Definition: attnum.h:21
bool heap_attisnull(HeapTuple tup, int attnum, TupleDesc tupleDesc)
Definition: heaptuple.c:359
FormData_pg_attribute * Form_pg_attribute
Definition: pg_attribute.h:207
FormData_pg_class * Form_pg_class
Definition: pg_class.h:153
#define Int16GetDatum(X)
Definition: postgres.h:495
HeapTuple SearchSysCache2(int cacheId, Datum key1, Datum key2)
Definition: syscache.c:1184
@ ATTNUM
Definition: syscache.h:41
@ RELOID
Definition: syscache.h:89

References ACLCHECK_NO_PRIV, ACLCHECK_OK, ACLMASK_ALL, ACLMASK_ANY, ATTNUM, GETSTRUCT, heap_attisnull(), HeapTupleIsValid, Int16GetDatum, mode, ObjectIdGetDatum, pg_attribute_aclmask(), ReleaseSysCache(), RELOID, SearchSysCache1(), and SearchSysCache2().

Referenced by ExecCheckRTEPerms(), ExecCheckRTEPermsModified(), has_any_column_privilege_id(), has_any_column_privilege_id_id(), has_any_column_privilege_id_name(), has_any_column_privilege_name(), has_any_column_privilege_name_id(), has_any_column_privilege_name_name(), and statext_is_compatible_clause().

◆ pg_attribute_aclcheck_ext()

AclResult pg_attribute_aclcheck_ext ( Oid  table_oid,
AttrNumber  attnum,
Oid  roleid,
AclMode  mode,
bool is_missing 
)

Definition at line 4892 of file aclchk.c.

4894 {
4895  if (pg_attribute_aclmask_ext(table_oid, attnum, roleid, mode,
4896  ACLMASK_ANY, is_missing) != 0)
4897  return ACLCHECK_OK;
4898  else
4899  return ACLCHECK_NO_PRIV;
4900 }
AclMode pg_attribute_aclmask_ext(Oid table_oid, AttrNumber attnum, Oid roleid, AclMode mask, AclMaskHow how, bool *is_missing)
Definition: aclchk.c:3927

References ACLCHECK_NO_PRIV, ACLCHECK_OK, ACLMASK_ANY, attnum, mode, and pg_attribute_aclmask_ext().

Referenced by column_privilege_check(), and pg_attribute_aclcheck().

◆ pg_attribute_aclmask()

AclMode pg_attribute_aclmask ( Oid  table_oid,
AttrNumber  attnum,
Oid  roleid,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 3913 of file aclchk.c.

3915 {
3916  return pg_attribute_aclmask_ext(table_oid, attnum, roleid,
3917  mask, how, NULL);
3918 }

References attnum, and pg_attribute_aclmask_ext().

Referenced by pg_aclmask(), and pg_attribute_aclcheck_all().

◆ pg_attribute_aclmask_ext()

AclMode pg_attribute_aclmask_ext ( Oid  table_oid,
AttrNumber  attnum,
Oid  roleid,
AclMode  mask,
AclMaskHow  how,
bool is_missing 
)

Definition at line 3927 of file aclchk.c.

3929 {
3930  AclMode result;
3931  HeapTuple classTuple;
3932  HeapTuple attTuple;
3933  Form_pg_class classForm;
3934  Form_pg_attribute attributeForm;
3935  Datum aclDatum;
3936  bool isNull;
3937  Acl *acl;
3938  Oid ownerId;
3939 
3940  /*
3941  * First, get the column's ACL from its pg_attribute entry
3942  */
3943  attTuple = SearchSysCache2(ATTNUM,
3944  ObjectIdGetDatum(table_oid),
3946  if (!HeapTupleIsValid(attTuple))
3947  {
3948  if (is_missing != NULL)
3949  {
3950  /* return "no privileges" instead of throwing an error */
3951  *is_missing = true;
3952  return 0;
3953  }
3954  else
3955  ereport(ERROR,
3956  (errcode(ERRCODE_UNDEFINED_COLUMN),
3957  errmsg("attribute %d of relation with OID %u does not exist",
3958  attnum, table_oid)));
3959  }
3960 
3961  attributeForm = (Form_pg_attribute) GETSTRUCT(attTuple);
3962 
3963  /* Check dropped columns, too */
3964  if (attributeForm->attisdropped)
3965  {
3966  if (is_missing != NULL)
3967  {
3968  /* return "no privileges" instead of throwing an error */
3969  *is_missing = true;
3970  ReleaseSysCache(attTuple);
3971  return 0;
3972  }
3973  else
3974  ereport(ERROR,
3975  (errcode(ERRCODE_UNDEFINED_COLUMN),
3976  errmsg("attribute %d of relation with OID %u does not exist",
3977  attnum, table_oid)));
3978  }
3979 
3980  aclDatum = SysCacheGetAttr(ATTNUM, attTuple, Anum_pg_attribute_attacl,
3981  &isNull);
3982 
3983  /*
3984  * Here we hard-wire knowledge that the default ACL for a column grants no
3985  * privileges, so that we can fall out quickly in the very common case
3986  * where attacl is null.
3987  */
3988  if (isNull)
3989  {
3990  ReleaseSysCache(attTuple);
3991  return 0;
3992  }
3993 
3994  /*
3995  * Must get the relation's ownerId from pg_class. Since we already found
3996  * a pg_attribute entry, the only likely reason for this to fail is that a
3997  * concurrent DROP of the relation committed since then (which could only
3998  * happen if we don't have lock on the relation). We prefer to report "no
3999  * privileges" rather than failing in such a case, so as to avoid unwanted
4000  * failures in has_column_privilege() tests.
4001  */
4002  classTuple = SearchSysCache1(RELOID, ObjectIdGetDatum(table_oid));
4003  if (!HeapTupleIsValid(classTuple))
4004  {
4005  ReleaseSysCache(attTuple);
4006  return 0;
4007  }
4008  classForm = (Form_pg_class) GETSTRUCT(classTuple);
4009 
4010  ownerId = classForm->relowner;
4011 
4012  ReleaseSysCache(classTuple);
4013 
4014  /* detoast column's ACL if necessary */
4015  acl = DatumGetAclP(aclDatum);
4016 
4017  result = aclmask(acl, roleid, ownerId, mask, how);
4018 
4019  /* if we have a detoasted copy, free it */
4020  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4021  pfree(acl);
4022 
4023  ReleaseSysCache(attTuple);
4024 
4025  return result;
4026 }
AclMode aclmask(const Acl *acl, Oid roleid, Oid ownerId, AclMode mask, AclMaskHow how)
Definition: acl.c:1321
#define DatumGetAclP(X)
Definition: acl.h:120
char * Pointer
Definition: c.h:429
#define DatumGetPointer(X)
Definition: postgres.h:593
Datum SysCacheGetAttr(int cacheId, HeapTuple tup, AttrNumber attributeNumber, bool *isNull)
Definition: syscache.c:1434

References aclmask(), attnum, ATTNUM, DatumGetAclP, DatumGetPointer, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, HeapTupleIsValid, Int16GetDatum, ObjectIdGetDatum, pfree(), ReleaseSysCache(), RELOID, SearchSysCache1(), SearchSysCache2(), and SysCacheGetAttr().

Referenced by pg_attribute_aclcheck_ext(), and pg_attribute_aclmask().

◆ pg_class_aclcheck()

AclResult pg_class_aclcheck ( Oid  table_oid,
Oid  roleid,
AclMode  mode 
)

◆ pg_class_aclcheck_ext()

AclResult pg_class_aclcheck_ext ( Oid  table_oid,
Oid  roleid,
AclMode  mode,
bool is_missing 
)

Definition at line 5019 of file aclchk.c.

5021 {
5022  if (pg_class_aclmask_ext(table_oid, roleid, mode,
5023  ACLMASK_ANY, is_missing) != 0)
5024  return ACLCHECK_OK;
5025  else
5026  return ACLCHECK_NO_PRIV;
5027 }
AclMode pg_class_aclmask_ext(Oid table_oid, Oid roleid, AclMode mask, AclMaskHow how, bool *is_missing)
Definition: aclchk.c:4045

References ACLCHECK_NO_PRIV, ACLCHECK_OK, ACLMASK_ANY, mode, and pg_class_aclmask_ext().

Referenced by column_privilege_check(), and pg_class_aclcheck().

◆ pg_class_aclmask()

AclMode pg_class_aclmask ( Oid  table_oid,
Oid  roleid,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 4032 of file aclchk.c.

4034 {
4035  return pg_class_aclmask_ext(table_oid, roleid, mask, how, NULL);
4036 }

References pg_class_aclmask_ext().

Referenced by ExecCheckRTEPerms(), and pg_aclmask().

◆ pg_class_aclmask_ext()

AclMode pg_class_aclmask_ext ( Oid  table_oid,
Oid  roleid,
AclMode  mask,
AclMaskHow  how,
bool is_missing 
)

Definition at line 4045 of file aclchk.c.

4047 {
4048  AclMode result;
4049  HeapTuple tuple;
4050  Form_pg_class classForm;
4051  Datum aclDatum;
4052  bool isNull;
4053  Acl *acl;
4054  Oid ownerId;
4055 
4056  /*
4057  * Must get the relation's tuple from pg_class
4058  */
4059  tuple = SearchSysCache1(RELOID, ObjectIdGetDatum(table_oid));
4060  if (!HeapTupleIsValid(tuple))
4061  {
4062  if (is_missing != NULL)
4063  {
4064  /* return "no privileges" instead of throwing an error */
4065  *is_missing = true;
4066  return 0;
4067  }
4068  else
4069  ereport(ERROR,
4071  errmsg("relation with OID %u does not exist",
4072  table_oid)));
4073  }
4074 
4075  classForm = (Form_pg_class) GETSTRUCT(tuple);
4076 
4077  /*
4078  * Deny anyone permission to update a system catalog unless
4079  * pg_authid.rolsuper is set.
4080  *
4081  * As of 7.4 we have some updatable system views; those shouldn't be
4082  * protected in this way. Assume the view rules can take care of
4083  * themselves. ACL_USAGE is if we ever have system sequences.
4084  */
4085  if ((mask & (ACL_INSERT | ACL_UPDATE | ACL_DELETE | ACL_TRUNCATE | ACL_USAGE)) &&
4086  IsSystemClass(table_oid, classForm) &&
4087  classForm->relkind != RELKIND_VIEW &&
4088  !superuser_arg(roleid))
4090 
4091  /*
4092  * Otherwise, superusers bypass all permission-checking.
4093  */
4094  if (superuser_arg(roleid))
4095  {
4096  ReleaseSysCache(tuple);
4097  return mask;
4098  }
4099 
4100  /*
4101  * Normal case: get the relation's ACL from pg_class
4102  */
4103  ownerId = classForm->relowner;
4104 
4105  aclDatum = SysCacheGetAttr(RELOID, tuple, Anum_pg_class_relacl,
4106  &isNull);
4107  if (isNull)
4108  {
4109  /* No ACL, so build default ACL */
4110  switch (classForm->relkind)
4111  {
4112  case RELKIND_SEQUENCE:
4113  acl = acldefault(OBJECT_SEQUENCE, ownerId);
4114  break;
4115  default:
4116  acl = acldefault(OBJECT_TABLE, ownerId);
4117  break;
4118  }
4119  aclDatum = (Datum) 0;
4120  }
4121  else
4122  {
4123  /* detoast rel's ACL if necessary */
4124  acl = DatumGetAclP(aclDatum);
4125  }
4126 
4127  result = aclmask(acl, roleid, ownerId, mask, how);
4128 
4129  /* if we have a detoasted copy, free it */
4130  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4131  pfree(acl);
4132 
4133  ReleaseSysCache(tuple);
4134 
4135  /*
4136  * Check if ACL_SELECT is being checked and, if so, and not set already as
4137  * part of the result, then check if the user is a member of the
4138  * pg_read_all_data role, which allows read access to all relations.
4139  */
4140  if (mask & ACL_SELECT && !(result & ACL_SELECT) &&
4141  has_privs_of_role(roleid, ROLE_PG_READ_ALL_DATA))
4142  result |= ACL_SELECT;
4143 
4144  /*
4145  * Check if ACL_INSERT, ACL_UPDATE, or ACL_DELETE is being checked and, if
4146  * so, and not set already as part of the result, then check if the user
4147  * is a member of the pg_write_all_data role, which allows
4148  * INSERT/UPDATE/DELETE access to all relations (except system catalogs,
4149  * which requires superuser, see above).
4150  */
4151  if (mask & (ACL_INSERT | ACL_UPDATE | ACL_DELETE) &&
4152  !(result & (ACL_INSERT | ACL_UPDATE | ACL_DELETE)) &&
4153  has_privs_of_role(roleid, ROLE_PG_WRITE_ALL_DATA))
4154  result |= (mask & (ACL_INSERT | ACL_UPDATE | ACL_DELETE));
4155 
4156  return result;
4157 }
bool IsSystemClass(Oid relid, Form_pg_class reltuple)
Definition: catalog.c:87
#define ACL_DELETE
Definition: parsenodes.h:85
#define ACL_INSERT
Definition: parsenodes.h:82
#define ACL_UPDATE
Definition: parsenodes.h:84
#define ACL_SELECT
Definition: parsenodes.h:83
#define ACL_TRUNCATE
Definition: parsenodes.h:86
#define ERRCODE_UNDEFINED_TABLE
Definition: pgbench.c:81

References ACL_DELETE, ACL_INSERT, ACL_SELECT, ACL_TRUNCATE, ACL_UPDATE, ACL_USAGE, acldefault(), aclmask(), DatumGetAclP, DatumGetPointer, ereport, errcode(), ERRCODE_UNDEFINED_TABLE, errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, IsSystemClass(), OBJECT_SEQUENCE, OBJECT_TABLE, ObjectIdGetDatum, pfree(), ReleaseSysCache(), RELOID, SearchSysCache1(), superuser_arg(), and SysCacheGetAttr().

Referenced by pg_class_aclcheck_ext(), and pg_class_aclmask().

◆ pg_class_ownercheck()

bool pg_class_ownercheck ( Oid  class_oid,
Oid  roleid 
)

Definition at line 5171 of file aclchk.c.

5172 {
5173  HeapTuple tuple;
5174  Oid ownerId;
5175 
5176  /* Superusers bypass all permission checking. */
5177  if (superuser_arg(roleid))
5178  return true;
5179 
5180  tuple = SearchSysCache1(RELOID, ObjectIdGetDatum(class_oid));
5181  if (!HeapTupleIsValid(tuple))
5182  ereport(ERROR,
5184  errmsg("relation with OID %u does not exist", class_oid)));
5185 
5186  ownerId = ((Form_pg_class) GETSTRUCT(tuple))->relowner;
5187 
5188  ReleaseSysCache(tuple);
5189 
5190  return has_privs_of_role(roleid, ownerId);
5191 }

References ereport, errcode(), ERRCODE_UNDEFINED_TABLE, errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), RELOID, SearchSysCache1(), and superuser_arg().

Referenced by AlterTableMoveAll(), ATExecChangeOwner(), ATSimplePermissions(), brin_desummarize_range(), brin_summarize_range(), check_enable_rls(), check_object_ownership(), cluster_rel(), CreateStatistics(), DefineQueryRewrite(), EnableDisableRule(), ExecuteTruncateGuts(), get_tables_to_cluster(), get_tables_to_cluster_partitioned(), gin_clean_pending_list(), heap_force_common(), MergeAttributes(), PublicationAddTables(), RangeVarCallbackForAlterRelation(), RangeVarCallbackForDropRelation(), RangeVarCallbackForPolicy(), RangeVarCallbackForReindexIndex(), RangeVarCallbackForRenameRule(), RangeVarCallbackForRenameTrigger(), RangeVarCallbackOwnsRelation(), RangeVarCallbackOwnsTable(), RangeVarGetAndCheckCreationNamespace(), ReindexMultipleTables(), renameatt_check(), RI_Initial_Check(), and vacuum_is_relation_owner().

◆ pg_collation_ownercheck()

bool pg_collation_ownercheck ( Oid  coll_oid,
Oid  roleid 
)

Definition at line 5615 of file aclchk.c.

5616 {
5617  HeapTuple tuple;
5618  Oid ownerId;
5619 
5620  /* Superusers bypass all permission checking. */
5621  if (superuser_arg(roleid))
5622  return true;
5623 
5624  tuple = SearchSysCache1(COLLOID, ObjectIdGetDatum(coll_oid));
5625  if (!HeapTupleIsValid(tuple))
5626  ereport(ERROR,
5627  (errcode(ERRCODE_UNDEFINED_OBJECT),
5628  errmsg("collation with OID %u does not exist", coll_oid)));
5629 
5630  ownerId = ((Form_pg_collation) GETSTRUCT(tuple))->collowner;
5631 
5632  ReleaseSysCache(tuple);
5633 
5634  return has_privs_of_role(roleid, ownerId);
5635 }
FormData_pg_collation * Form_pg_collation
Definition: pg_collation.h:57
@ COLLOID
Definition: syscache.h:50

References COLLOID, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by AlterCollation(), and check_object_ownership().

◆ pg_conversion_ownercheck()

bool pg_conversion_ownercheck ( Oid  conv_oid,
Oid  roleid 
)

Definition at line 5641 of file aclchk.c.

5642 {
5643  HeapTuple tuple;
5644  Oid ownerId;
5645 
5646  /* Superusers bypass all permission checking. */
5647  if (superuser_arg(roleid))
5648  return true;
5649 
5650  tuple = SearchSysCache1(CONVOID, ObjectIdGetDatum(conv_oid));
5651  if (!HeapTupleIsValid(tuple))
5652  ereport(ERROR,
5653  (errcode(ERRCODE_UNDEFINED_OBJECT),
5654  errmsg("conversion with OID %u does not exist", conv_oid)));
5655 
5656  ownerId = ((Form_pg_conversion) GETSTRUCT(tuple))->conowner;
5657 
5658  ReleaseSysCache(tuple);
5659 
5660  return has_privs_of_role(roleid, ownerId);
5661 }
FormData_pg_conversion * Form_pg_conversion
Definition: pg_conversion.h:61
@ CONVOID
Definition: syscache.h:54

References CONVOID, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by check_object_ownership().

◆ pg_database_aclcheck()

◆ pg_database_aclmask()

AclMode pg_database_aclmask ( Oid  db_oid,
Oid  roleid,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 4163 of file aclchk.c.

4165 {
4166  AclMode result;
4167  HeapTuple tuple;
4168  Datum aclDatum;
4169  bool isNull;
4170  Acl *acl;
4171  Oid ownerId;
4172 
4173  /* Superusers bypass all permission checking. */
4174  if (superuser_arg(roleid))
4175  return mask;
4176 
4177  /*
4178  * Get the database's ACL from pg_database
4179  */
4180  tuple = SearchSysCache1(DATABASEOID, ObjectIdGetDatum(db_oid));
4181  if (!HeapTupleIsValid(tuple))
4182  ereport(ERROR,
4183  (errcode(ERRCODE_UNDEFINED_DATABASE),
4184  errmsg("database with OID %u does not exist", db_oid)));
4185 
4186  ownerId = ((Form_pg_database) GETSTRUCT(tuple))->datdba;
4187 
4188  aclDatum = SysCacheGetAttr(DATABASEOID, tuple, Anum_pg_database_datacl,
4189  &isNull);
4190  if (isNull)
4191  {
4192  /* No ACL, so build default ACL */
4193  acl = acldefault(OBJECT_DATABASE, ownerId);
4194  aclDatum = (Datum) 0;
4195  }
4196  else
4197  {
4198  /* detoast ACL if necessary */
4199  acl = DatumGetAclP(aclDatum);
4200  }
4201 
4202  result = aclmask(acl, roleid, ownerId, mask, how);
4203 
4204  /* if we have a detoasted copy, free it */
4205  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4206  pfree(acl);
4207 
4208  ReleaseSysCache(tuple);
4209 
4210  return result;
4211 }
FormData_pg_database * Form_pg_database
Definition: pg_database.h:87

References acldefault(), aclmask(), DATABASEOID, DatumGetAclP, DatumGetPointer, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, HeapTupleIsValid, OBJECT_DATABASE, ObjectIdGetDatum, pfree(), ReleaseSysCache(), SearchSysCache1(), superuser_arg(), and SysCacheGetAttr().

Referenced by pg_aclmask(), and pg_database_aclcheck().

◆ pg_database_ownercheck()

bool pg_database_ownercheck ( Oid  db_oid,
Oid  roleid 
)

Definition at line 5589 of file aclchk.c.

5590 {
5591  HeapTuple tuple;
5592  Oid dba;
5593 
5594  /* Superusers bypass all permission checking. */
5595  if (superuser_arg(roleid))
5596  return true;
5597 
5598  tuple = SearchSysCache1(DATABASEOID, ObjectIdGetDatum(db_oid));
5599  if (!HeapTupleIsValid(tuple))
5600  ereport(ERROR,
5601  (errcode(ERRCODE_UNDEFINED_DATABASE),
5602  errmsg("database with OID %u does not exist", db_oid)));
5603 
5604  dba = ((Form_pg_database) GETSTRUCT(tuple))->datdba;
5605 
5606  ReleaseSysCache(tuple);
5607 
5608  return has_privs_of_role(roleid, dba);
5609 }

References DATABASEOID, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by AlterDatabase(), AlterDatabaseOwner(), AlterDatabaseRefreshColl(), AlterDatabaseSet(), AlterRoleSet(), check_object_ownership(), createdb(), dropdb(), get_tables_to_cluster_partitioned(), movedb(), ReindexMultipleTables(), RenameDatabase(), and vacuum_is_relation_owner().

◆ pg_event_trigger_ownercheck()

bool pg_event_trigger_ownercheck ( Oid  et_oid,
Oid  roleid 
)

Definition at line 5562 of file aclchk.c.

5563 {
5564  HeapTuple tuple;
5565  Oid ownerId;
5566 
5567  /* Superusers bypass all permission checking. */
5568  if (superuser_arg(roleid))
5569  return true;
5570 
5572  if (!HeapTupleIsValid(tuple))
5573  ereport(ERROR,
5574  (errcode(ERRCODE_UNDEFINED_OBJECT),
5575  errmsg("event trigger with OID %u does not exist",
5576  et_oid)));
5577 
5578  ownerId = ((Form_pg_event_trigger) GETSTRUCT(tuple))->evtowner;
5579 
5580  ReleaseSysCache(tuple);
5581 
5582  return has_privs_of_role(roleid, ownerId);
5583 }
FormData_pg_event_trigger * Form_pg_event_trigger
@ EVENTTRIGGEROID
Definition: syscache.h:60

References ereport, errcode(), errmsg(), ERROR, EVENTTRIGGEROID, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by AlterEventTrigger(), AlterEventTriggerOwner_internal(), and check_object_ownership().

◆ pg_extension_ownercheck()

bool pg_extension_ownercheck ( Oid  ext_oid,
Oid  roleid 
)

Definition at line 5667 of file aclchk.c.

5668 {
5669  Relation pg_extension;
5670  ScanKeyData entry[1];
5671  SysScanDesc scan;
5672  HeapTuple tuple;
5673  Oid ownerId;
5674 
5675  /* Superusers bypass all permission checking. */
5676  if (superuser_arg(roleid))
5677  return true;
5678 
5679  /* There's no syscache for pg_extension, so do it the hard way */
5680  pg_extension = table_open(ExtensionRelationId, AccessShareLock);
5681 
5682  ScanKeyInit(&entry[0],
5683  Anum_pg_extension_oid,
5684  BTEqualStrategyNumber, F_OIDEQ,
5685  ObjectIdGetDatum(ext_oid));
5686 
5687  scan = systable_beginscan(pg_extension,
5688  ExtensionOidIndexId, true,
5689  NULL, 1, entry);
5690 
5691  tuple = systable_getnext(scan);
5692  if (!HeapTupleIsValid(tuple))
5693  ereport(ERROR,
5694  (errcode(ERRCODE_UNDEFINED_OBJECT),
5695  errmsg("extension with OID %u does not exist", ext_oid)));
5696 
5697  ownerId = ((Form_pg_extension) GETSTRUCT(tuple))->extowner;
5698 
5699  systable_endscan(scan);
5700  table_close(pg_extension, AccessShareLock);
5701 
5702  return has_privs_of_role(roleid, ownerId);
5703 }
void systable_endscan(SysScanDesc sysscan)
Definition: genam.c:598
HeapTuple systable_getnext(SysScanDesc sysscan)
Definition: genam.c:505
SysScanDesc systable_beginscan(Relation heapRelation, Oid indexId, bool indexOK, Snapshot snapshot, int nkeys, ScanKey key)
Definition: genam.c:386
#define AccessShareLock
Definition: lockdefs.h:36
FormData_pg_extension * Form_pg_extension
Definition: pg_extension.h:52
void ScanKeyInit(ScanKey entry, AttrNumber attributeNumber, StrategyNumber strategy, RegProcedure procedure, Datum argument)
Definition: scankey.c:76
#define BTEqualStrategyNumber
Definition: stratnum.h:31
void table_close(Relation relation, LOCKMODE lockmode)
Definition: table.c:167
Relation table_open(Oid relationId, LOCKMODE lockmode)
Definition: table.c:39

References AccessShareLock, BTEqualStrategyNumber, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ScanKeyInit(), superuser_arg(), systable_beginscan(), systable_endscan(), systable_getnext(), table_close(), and table_open().

Referenced by AlterExtensionNamespace(), check_object_ownership(), ExecAlterExtensionContentsStmt(), and ExecAlterExtensionStmt().

◆ pg_foreign_data_wrapper_aclcheck()

AclResult pg_foreign_data_wrapper_aclcheck ( Oid  fdw_oid,
Oid  roleid,
AclMode  mode 
)

◆ pg_foreign_data_wrapper_aclmask()

AclMode pg_foreign_data_wrapper_aclmask ( Oid  fdw_oid,
Oid  roleid,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 4671 of file aclchk.c.

4673 {
4674  AclMode result;
4675  HeapTuple tuple;
4676  Datum aclDatum;
4677  bool isNull;
4678  Acl *acl;
4679  Oid ownerId;
4680 
4682 
4683  /* Bypass permission checks for superusers */
4684  if (superuser_arg(roleid))
4685  return mask;
4686 
4687  /*
4688  * Must get the FDW's tuple from pg_foreign_data_wrapper
4689  */
4691  if (!HeapTupleIsValid(tuple))
4692  ereport(ERROR,
4693  (errcode(ERRCODE_UNDEFINED_OBJECT),
4694  errmsg("foreign-data wrapper with OID %u does not exist",
4695  fdw_oid)));
4696  fdwForm = (Form_pg_foreign_data_wrapper) GETSTRUCT(tuple);
4697 
4698  /*
4699  * Normal case: get the FDW's ACL from pg_foreign_data_wrapper
4700  */
4701  ownerId = fdwForm->fdwowner;
4702 
4703  aclDatum = SysCacheGetAttr(FOREIGNDATAWRAPPEROID, tuple,
4704  Anum_pg_foreign_data_wrapper_fdwacl, &isNull);
4705  if (isNull)
4706  {
4707  /* No ACL, so build default ACL */
4708  acl = acldefault(OBJECT_FDW, ownerId);
4709  aclDatum = (Datum) 0;
4710  }
4711  else
4712  {
4713  /* detoast rel's ACL if necessary */
4714  acl = DatumGetAclP(aclDatum);
4715  }
4716 
4717  result = aclmask(acl, roleid, ownerId, mask, how);
4718 
4719  /* if we have a detoasted copy, free it */
4720  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4721  pfree(acl);
4722 
4723  ReleaseSysCache(tuple);
4724 
4725  return result;
4726 }
FormData_pg_foreign_data_wrapper * Form_pg_foreign_data_wrapper
@ FOREIGNDATAWRAPPEROID
Definition: syscache.h:62

References acldefault(), aclmask(), DatumGetAclP, DatumGetPointer, ereport, errcode(), errmsg(), ERROR, FOREIGNDATAWRAPPEROID, GETSTRUCT, HeapTupleIsValid, OBJECT_FDW, ObjectIdGetDatum, pfree(), ReleaseSysCache(), SearchSysCache1(), superuser_arg(), and SysCacheGetAttr().

Referenced by pg_aclmask(), and pg_foreign_data_wrapper_aclcheck().

◆ pg_foreign_data_wrapper_ownercheck()

bool pg_foreign_data_wrapper_ownercheck ( Oid  srv_oid,
Oid  roleid 
)

Definition at line 5508 of file aclchk.c.

5509 {
5510  HeapTuple tuple;
5511  Oid ownerId;
5512 
5513  /* Superusers bypass all permission checking. */
5514  if (superuser_arg(roleid))
5515  return true;
5516 
5518  if (!HeapTupleIsValid(tuple))
5519  ereport(ERROR,
5520  (errcode(ERRCODE_UNDEFINED_OBJECT),
5521  errmsg("foreign-data wrapper with OID %u does not exist",
5522  srv_oid)));
5523 
5524  ownerId = ((Form_pg_foreign_data_wrapper) GETSTRUCT(tuple))->fdwowner;
5525 
5526  ReleaseSysCache(tuple);
5527 
5528  return has_privs_of_role(roleid, ownerId);
5529 }

References ereport, errcode(), errmsg(), ERROR, FOREIGNDATAWRAPPEROID, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by check_object_ownership().

◆ pg_foreign_server_aclcheck()

AclResult pg_foreign_server_aclcheck ( Oid  srv_oid,
Oid  roleid,
AclMode  mode 
)

◆ pg_foreign_server_aclmask()

AclMode pg_foreign_server_aclmask ( Oid  srv_oid,
Oid  roleid,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 4733 of file aclchk.c.

4735 {
4736  AclMode result;
4737  HeapTuple tuple;
4738  Datum aclDatum;
4739  bool isNull;
4740  Acl *acl;
4741  Oid ownerId;
4742 
4743  Form_pg_foreign_server srvForm;
4744 
4745  /* Bypass permission checks for superusers */
4746  if (superuser_arg(roleid))
4747  return mask;
4748 
4749  /*
4750  * Must get the FDW's tuple from pg_foreign_data_wrapper
4751  */
4753  if (!HeapTupleIsValid(tuple))
4754  ereport(ERROR,
4755  (errcode(ERRCODE_UNDEFINED_OBJECT),
4756  errmsg("foreign server with OID %u does not exist",
4757  srv_oid)));
4758  srvForm = (Form_pg_foreign_server) GETSTRUCT(tuple);
4759 
4760  /*
4761  * Normal case: get the foreign server's ACL from pg_foreign_server
4762  */
4763  ownerId = srvForm->srvowner;
4764 
4765  aclDatum = SysCacheGetAttr(FOREIGNSERVEROID, tuple,
4766  Anum_pg_foreign_server_srvacl, &isNull);
4767  if (isNull)
4768  {
4769  /* No ACL, so build default ACL */
4770  acl = acldefault(OBJECT_FOREIGN_SERVER, ownerId);
4771  aclDatum = (Datum) 0;
4772  }
4773  else
4774  {
4775  /* detoast rel's ACL if necessary */
4776  acl = DatumGetAclP(aclDatum);
4777  }
4778 
4779  result = aclmask(acl, roleid, ownerId, mask, how);
4780 
4781  /* if we have a detoasted copy, free it */
4782  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4783  pfree(acl);
4784 
4785  ReleaseSysCache(tuple);
4786 
4787  return result;
4788 }
FormData_pg_foreign_server * Form_pg_foreign_server
@ FOREIGNSERVEROID
Definition: syscache.h:64

References acldefault(), aclmask(), DatumGetAclP, DatumGetPointer, ereport, errcode(), errmsg(), ERROR, FOREIGNSERVEROID, GETSTRUCT, HeapTupleIsValid, OBJECT_FOREIGN_SERVER, ObjectIdGetDatum, pfree(), ReleaseSysCache(), SearchSysCache1(), superuser_arg(), and SysCacheGetAttr().

Referenced by pg_aclmask(), and pg_foreign_server_aclcheck().

◆ pg_foreign_server_ownercheck()

bool pg_foreign_server_ownercheck ( Oid  srv_oid,
Oid  roleid 
)

Definition at line 5535 of file aclchk.c.

5536 {
5537  HeapTuple tuple;
5538  Oid ownerId;
5539 
5540  /* Superusers bypass all permission checking. */
5541  if (superuser_arg(roleid))
5542  return true;
5543 
5545  if (!HeapTupleIsValid(tuple))
5546  ereport(ERROR,
5547  (errcode(ERRCODE_UNDEFINED_OBJECT),
5548  errmsg("foreign server with OID %u does not exist",
5549  srv_oid)));
5550 
5551  ownerId = ((Form_pg_foreign_server) GETSTRUCT(tuple))->srvowner;
5552 
5553  ReleaseSysCache(tuple);
5554 
5555  return has_privs_of_role(roleid, ownerId);
5556 }

References ereport, errcode(), errmsg(), ERROR, FOREIGNSERVEROID, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by AlterForeignServer(), AlterForeignServerOwner_internal(), check_object_ownership(), and user_mapping_ddl_aclcheck().

◆ pg_language_aclcheck()

AclResult pg_language_aclcheck ( Oid  lang_oid,
Oid  roleid,
AclMode  mode 
)

Definition at line 5083 of file aclchk.c.

5084 {
5085  if (pg_language_aclmask(lang_oid, roleid, mode, ACLMASK_ANY) != 0)
5086  return ACLCHECK_OK;
5087  else
5088  return ACLCHECK_NO_PRIV;
5089 }
AclMode pg_language_aclmask(Oid lang_oid, Oid roleid, AclMode mask, AclMaskHow how)
Definition: aclchk.c:4386

References ACLCHECK_NO_PRIV, ACLCHECK_OK, ACLMASK_ANY, mode, and pg_language_aclmask().

Referenced by CheckFunctionValidatorAccess(), CreateFunction(), CreateTransform(), ExecuteDoStmt(), has_language_privilege_id(), has_language_privilege_id_id(), has_language_privilege_id_name(), has_language_privilege_name(), has_language_privilege_name_id(), and has_language_privilege_name_name().

◆ pg_language_aclmask()

AclMode pg_language_aclmask ( Oid  lang_oid,
Oid  roleid,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 4386 of file aclchk.c.

4388 {
4389  AclMode result;
4390  HeapTuple tuple;
4391  Datum aclDatum;
4392  bool isNull;
4393  Acl *acl;
4394  Oid ownerId;
4395 
4396  /* Superusers bypass all permission checking. */
4397  if (superuser_arg(roleid))
4398  return mask;
4399 
4400  /*
4401  * Get the language's ACL from pg_language
4402  */
4403  tuple = SearchSysCache1(LANGOID, ObjectIdGetDatum(lang_oid));
4404  if (!HeapTupleIsValid(tuple))
4405  ereport(ERROR,
4406  (errcode(ERRCODE_UNDEFINED_OBJECT),
4407  errmsg("language with OID %u does not exist", lang_oid)));
4408 
4409  ownerId = ((Form_pg_language) GETSTRUCT(tuple))->lanowner;
4410 
4411  aclDatum = SysCacheGetAttr(LANGOID, tuple, Anum_pg_language_lanacl,
4412  &isNull);
4413  if (isNull)
4414  {
4415  /* No ACL, so build default ACL */
4416  acl = acldefault(OBJECT_LANGUAGE, ownerId);
4417  aclDatum = (Datum) 0;
4418  }
4419  else
4420  {
4421  /* detoast ACL if necessary */
4422  acl = DatumGetAclP(aclDatum);
4423  }
4424 
4425  result = aclmask(acl, roleid, ownerId, mask, how);
4426 
4427  /* if we have a detoasted copy, free it */
4428  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4429  pfree(acl);
4430 
4431  ReleaseSysCache(tuple);
4432 
4433  return result;
4434 }
FormData_pg_language * Form_pg_language
Definition: pg_language.h:65
@ LANGOID
Definition: syscache.h:68

References acldefault(), aclmask(), DatumGetAclP, DatumGetPointer, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, HeapTupleIsValid, LANGOID, OBJECT_LANGUAGE, ObjectIdGetDatum, pfree(), ReleaseSysCache(), SearchSysCache1(), superuser_arg(), and SysCacheGetAttr().

Referenced by pg_aclmask(), and pg_language_aclcheck().

◆ pg_language_ownercheck()

bool pg_language_ownercheck ( Oid  lan_oid,
Oid  roleid 
)

Definition at line 5275 of file aclchk.c.

5276 {
5277  HeapTuple tuple;
5278  Oid ownerId;
5279 
5280  /* Superusers bypass all permission checking. */
5281  if (superuser_arg(roleid))
5282  return true;
5283 
5284  tuple = SearchSysCache1(LANGOID, ObjectIdGetDatum(lan_oid));
5285  if (!HeapTupleIsValid(tuple))
5286  ereport(ERROR,
5287  (errcode(ERRCODE_UNDEFINED_FUNCTION),
5288  errmsg("language with OID %u does not exist", lan_oid)));
5289 
5290  ownerId = ((Form_pg_language) GETSTRUCT(tuple))->lanowner;
5291 
5292  ReleaseSysCache(tuple);
5293 
5294  return has_privs_of_role(roleid, ownerId);
5295 }

References ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, LANGOID, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by check_object_ownership(), and CreateProceduralLanguage().

◆ pg_largeobject_aclcheck_snapshot()

AclResult pg_largeobject_aclcheck_snapshot ( Oid  lang_oid,
Oid  roleid,
AclMode  mode,
Snapshot  snapshot 
)

Definition at line 5095 of file aclchk.c.

5097 {
5098  if (pg_largeobject_aclmask_snapshot(lobj_oid, roleid, mode,
5099  ACLMASK_ANY, snapshot) != 0)
5100  return ACLCHECK_OK;
5101  else
5102  return ACLCHECK_NO_PRIV;
5103 }
AclMode pg_largeobject_aclmask_snapshot(Oid lobj_oid, Oid roleid, AclMode mask, AclMaskHow how, Snapshot snapshot)
Definition: aclchk.c:4449

References ACLCHECK_NO_PRIV, ACLCHECK_OK, ACLMASK_ANY, mode, and pg_largeobject_aclmask_snapshot().

Referenced by be_lo_put(), and inv_open().

◆ pg_largeobject_aclmask_snapshot()

AclMode pg_largeobject_aclmask_snapshot ( Oid  lobj_oid,
Oid  roleid,
AclMode  mask,
AclMaskHow  how,
Snapshot  snapshot 
)

Definition at line 4449 of file aclchk.c.

4452 {
4453  AclMode result;
4454  Relation pg_lo_meta;
4455  ScanKeyData entry[1];
4456  SysScanDesc scan;
4457  HeapTuple tuple;
4458  Datum aclDatum;
4459  bool isNull;
4460  Acl *acl;
4461  Oid ownerId;
4462 
4463  /* Superusers bypass all permission checking. */
4464  if (superuser_arg(roleid))
4465  return mask;
4466 
4467  /*
4468  * Get the largeobject's ACL from pg_largeobject_metadata
4469  */
4470  pg_lo_meta = table_open(LargeObjectMetadataRelationId,
4471  AccessShareLock);
4472 
4473  ScanKeyInit(&entry[0],
4474  Anum_pg_largeobject_metadata_oid,
4475  BTEqualStrategyNumber, F_OIDEQ,
4476  ObjectIdGetDatum(lobj_oid));
4477 
4478  scan = systable_beginscan(pg_lo_meta,
4479  LargeObjectMetadataOidIndexId, true,
4480  snapshot, 1, entry);
4481 
4482  tuple = systable_getnext(scan);
4483  if (!HeapTupleIsValid(tuple))
4484  ereport(ERROR,
4485  (errcode(ERRCODE_UNDEFINED_OBJECT),
4486  errmsg("large object %u does not exist", lobj_oid)));
4487 
4488  ownerId = ((Form_pg_largeobject_metadata) GETSTRUCT(tuple))->lomowner;
4489 
4490  aclDatum = heap_getattr(tuple, Anum_pg_largeobject_metadata_lomacl,
4491  RelationGetDescr(pg_lo_meta), &isNull);
4492 
4493  if (isNull)
4494  {
4495  /* No ACL, so build default ACL */
4496  acl = acldefault(OBJECT_LARGEOBJECT, ownerId);
4497  aclDatum = (Datum) 0;
4498  }
4499  else
4500  {
4501  /* detoast ACL if necessary */
4502  acl = DatumGetAclP(aclDatum);
4503  }
4504 
4505  result = aclmask(acl, roleid, ownerId, mask, how);
4506 
4507  /* if we have a detoasted copy, free it */
4508  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4509  pfree(acl);
4510 
4511  systable_endscan(scan);
4512 
4513  table_close(pg_lo_meta, AccessShareLock);
4514 
4515  return result;
4516 }
static Datum heap_getattr(HeapTuple tup, int attnum, TupleDesc tupleDesc, bool *isnull)
Definition: htup_details.h:788
FormData_pg_largeobject_metadata * Form_pg_largeobject_metadata
#define RelationGetDescr(relation)
Definition: rel.h:514

References AccessShareLock, acldefault(), aclmask(), BTEqualStrategyNumber, DatumGetAclP, DatumGetPointer, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, heap_getattr(), HeapTupleIsValid, OBJECT_LARGEOBJECT, ObjectIdGetDatum, pfree(), RelationGetDescr, ScanKeyInit(), superuser_arg(), systable_beginscan(), systable_endscan(), systable_getnext(), table_close(), and table_open().

Referenced by pg_aclmask(), and pg_largeobject_aclcheck_snapshot().

◆ pg_largeobject_ownercheck()

bool pg_largeobject_ownercheck ( Oid  lobj_oid,
Oid  roleid 
)

Definition at line 5304 of file aclchk.c.

5305 {
5306  Relation pg_lo_meta;
5307  ScanKeyData entry[1];
5308  SysScanDesc scan;
5309  HeapTuple tuple;
5310  Oid ownerId;
5311 
5312  /* Superusers bypass all permission checking. */
5313  if (superuser_arg(roleid))
5314  return true;
5315 
5316  /* There's no syscache for pg_largeobject_metadata */
5317  pg_lo_meta = table_open(LargeObjectMetadataRelationId,
5318  AccessShareLock);
5319 
5320  ScanKeyInit(&entry[0],
5321  Anum_pg_largeobject_metadata_oid,
5322  BTEqualStrategyNumber, F_OIDEQ,
5323  ObjectIdGetDatum(lobj_oid));
5324 
5325  scan = systable_beginscan(pg_lo_meta,
5326  LargeObjectMetadataOidIndexId, true,
5327  NULL, 1, entry);
5328 
5329  tuple = systable_getnext(scan);
5330  if (!HeapTupleIsValid(tuple))
5331  ereport(ERROR,
5332  (errcode(ERRCODE_UNDEFINED_OBJECT),
5333  errmsg("large object %u does not exist", lobj_oid)));
5334 
5335  ownerId = ((Form_pg_largeobject_metadata) GETSTRUCT(tuple))->lomowner;
5336 
5337  systable_endscan(scan);
5338  table_close(pg_lo_meta, AccessShareLock);
5339 
5340  return has_privs_of_role(roleid, ownerId);
5341 }

References AccessShareLock, BTEqualStrategyNumber, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ScanKeyInit(), superuser_arg(), systable_beginscan(), systable_endscan(), systable_getnext(), table_close(), and table_open().

Referenced by be_lo_unlink(), and check_object_ownership().

◆ pg_namespace_aclcheck()

◆ pg_namespace_aclmask()

AclMode pg_namespace_aclmask ( Oid  nsp_oid,
Oid  roleid,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 4522 of file aclchk.c.

4524 {
4525  AclMode result;
4526  HeapTuple tuple;
4527  Datum aclDatum;
4528  bool isNull;
4529  Acl *acl;
4530  Oid ownerId;
4531 
4532  /* Superusers bypass all permission checking. */
4533  if (superuser_arg(roleid))
4534  return mask;
4535 
4536  /*
4537  * If we have been assigned this namespace as a temp namespace, check to
4538  * make sure we have CREATE TEMP permission on the database, and if so act
4539  * as though we have all standard (but not GRANT OPTION) permissions on
4540  * the namespace. If we don't have CREATE TEMP, act as though we have
4541  * only USAGE (and not CREATE) rights.
4542  *
4543  * This may seem redundant given the check in InitTempTableNamespace, but
4544  * it really isn't since current user ID may have changed since then. The
4545  * upshot of this behavior is that a SECURITY DEFINER function can create
4546  * temp tables that can then be accessed (if permission is granted) by
4547  * code in the same session that doesn't have permissions to create temp
4548  * tables.
4549  *
4550  * XXX Would it be safe to ereport a special error message as
4551  * InitTempTableNamespace does? Returning zero here means we'll get a
4552  * generic "permission denied for schema pg_temp_N" message, which is not
4553  * remarkably user-friendly.
4554  */
4555  if (isTempNamespace(nsp_oid))
4556  {
4557  if (pg_database_aclcheck(MyDatabaseId, roleid,
4559  return mask & ACL_ALL_RIGHTS_SCHEMA;
4560  else
4561  return mask & ACL_USAGE;
4562  }
4563 
4564  /*
4565  * Get the schema's ACL from pg_namespace
4566  */
4567  tuple = SearchSysCache1(NAMESPACEOID, ObjectIdGetDatum(nsp_oid));
4568  if (!HeapTupleIsValid(tuple))
4569  ereport(ERROR,
4570  (errcode(ERRCODE_UNDEFINED_SCHEMA),
4571  errmsg("schema with OID %u does not exist", nsp_oid)));
4572 
4573  ownerId = ((Form_pg_namespace) GETSTRUCT(tuple))->nspowner;
4574 
4575  aclDatum = SysCacheGetAttr(NAMESPACEOID, tuple, Anum_pg_namespace_nspacl,
4576  &isNull);
4577  if (isNull)
4578  {
4579  /* No ACL, so build default ACL */
4580  acl = acldefault(OBJECT_SCHEMA, ownerId);
4581  aclDatum = (Datum) 0;
4582  }
4583  else
4584  {
4585  /* detoast ACL if necessary */
4586  acl = DatumGetAclP(aclDatum);
4587  }
4588 
4589  result = aclmask(acl, roleid, ownerId, mask, how);
4590 
4591  /* if we have a detoasted copy, free it */
4592  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4593  pfree(acl);
4594 
4595  ReleaseSysCache(tuple);
4596 
4597  /*
4598  * Check if ACL_USAGE is being checked and, if so, and not set already as
4599  * part of the result, then check if the user is a member of the
4600  * pg_read_all_data or pg_write_all_data roles, which allow usage access
4601  * to all schemas.
4602  */
4603  if (mask & ACL_USAGE && !(result & ACL_USAGE) &&
4604  (has_privs_of_role(roleid, ROLE_PG_READ_ALL_DATA) ||
4605  has_privs_of_role(roleid, ROLE_PG_WRITE_ALL_DATA)))
4606  result |= ACL_USAGE;
4607  return result;
4608 }
AclResult pg_database_aclcheck(Oid db_oid, Oid roleid, AclMode mode)
Definition: aclchk.c:5033
bool isTempNamespace(Oid namespaceId)
Definition: namespace.c:3203
FormData_pg_namespace * Form_pg_namespace
Definition: pg_namespace.h:52
@ NAMESPACEOID
Definition: syscache.h:70

References ACL_ALL_RIGHTS_SCHEMA, ACL_CREATE_TEMP, ACL_USAGE, ACLCHECK_OK, acldefault(), aclmask(), DatumGetAclP, DatumGetPointer, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, isTempNamespace(), MyDatabaseId, NAMESPACEOID, OBJECT_SCHEMA, ObjectIdGetDatum, pfree(), pg_database_aclcheck(), ReleaseSysCache(), SearchSysCache1(), superuser_arg(), and SysCacheGetAttr().

Referenced by pg_aclmask(), and pg_namespace_aclcheck().

◆ pg_namespace_ownercheck()

bool pg_namespace_ownercheck ( Oid  nsp_oid,
Oid  roleid 
)

Definition at line 5347 of file aclchk.c.

5348 {
5349  HeapTuple tuple;
5350  Oid ownerId;
5351 
5352  /* Superusers bypass all permission checking. */
5353  if (superuser_arg(roleid))
5354  return true;
5355 
5356  tuple = SearchSysCache1(NAMESPACEOID, ObjectIdGetDatum(nsp_oid));
5357  if (!HeapTupleIsValid(tuple))
5358  ereport(ERROR,
5359  (errcode(ERRCODE_UNDEFINED_SCHEMA),
5360  errmsg("schema with OID %u does not exist", nsp_oid)));
5361 
5362  ownerId = ((Form_pg_namespace) GETSTRUCT(tuple))->nspowner;
5363 
5364  ReleaseSysCache(tuple);
5365 
5366  return has_privs_of_role(roleid, ownerId);
5367 }

References ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, NAMESPACEOID, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by AlterSchemaOwner_internal(), check_object_ownership(), RangeVarCallbackForDropRelation(), ReindexMultipleTables(), RemoveObjects(), and RenameSchema().

◆ pg_opclass_ownercheck()

bool pg_opclass_ownercheck ( Oid  opc_oid,
Oid  roleid 
)

Definition at line 5400 of file aclchk.c.

5401 {
5402  HeapTuple tuple;
5403  Oid ownerId;
5404 
5405  /* Superusers bypass all permission checking. */
5406  if (superuser_arg(roleid))
5407  return true;
5408 
5409  tuple = SearchSysCache1(CLAOID, ObjectIdGetDatum(opc_oid));
5410  if (!HeapTupleIsValid(tuple))
5411  ereport(ERROR,
5412  (errcode(ERRCODE_UNDEFINED_OBJECT),
5413  errmsg("operator class with OID %u does not exist",
5414  opc_oid)));
5415 
5416  ownerId = ((Form_pg_opclass) GETSTRUCT(tuple))->opcowner;
5417 
5418  ReleaseSysCache(tuple);
5419 
5420  return has_privs_of_role(roleid, ownerId);
5421 }
FormData_pg_opclass * Form_pg_opclass
Definition: pg_opclass.h:83
@ CLAOID
Definition: syscache.h:48

References CLAOID, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by check_object_ownership().

◆ pg_oper_ownercheck()

bool pg_oper_ownercheck ( Oid  oper_oid,
Oid  roleid 
)

Definition at line 5223 of file aclchk.c.

5224 {
5225  HeapTuple tuple;
5226  Oid ownerId;
5227 
5228  /* Superusers bypass all permission checking. */
5229  if (superuser_arg(roleid))
5230  return true;
5231 
5232  tuple = SearchSysCache1(OPEROID, ObjectIdGetDatum(oper_oid));
5233  if (!HeapTupleIsValid(tuple))
5234  ereport(ERROR,
5235  (errcode(ERRCODE_UNDEFINED_FUNCTION),
5236  errmsg("operator with OID %u does not exist", oper_oid)));
5237 
5238  ownerId = ((Form_pg_operator) GETSTRUCT(tuple))->oprowner;
5239 
5240  ReleaseSysCache(tuple);
5241 
5242  return has_privs_of_role(roleid, ownerId);
5243 }
FormData_pg_operator * Form_pg_operator
Definition: pg_operator.h:83
@ OPEROID
Definition: syscache.h:72

References ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, OPEROID, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by AlterOperator(), AlterOpFamilyAdd(), check_object_ownership(), DefineOpClass(), and OperatorCreate().

◆ pg_opfamily_ownercheck()

bool pg_opfamily_ownercheck ( Oid  opf_oid,
Oid  roleid 
)

Definition at line 5427 of file aclchk.c.

5428 {
5429  HeapTuple tuple;
5430  Oid ownerId;
5431 
5432  /* Superusers bypass all permission checking. */
5433  if (superuser_arg(roleid))
5434  return true;
5435 
5436  tuple = SearchSysCache1(OPFAMILYOID, ObjectIdGetDatum(opf_oid));
5437  if (!HeapTupleIsValid(tuple))
5438  ereport(ERROR,
5439  (errcode(ERRCODE_UNDEFINED_OBJECT),
5440  errmsg("operator family with OID %u does not exist",
5441  opf_oid)));
5442 
5443  ownerId = ((Form_pg_opfamily) GETSTRUCT(tuple))->opfowner;
5444 
5445  ReleaseSysCache(tuple);
5446 
5447  return has_privs_of_role(roleid, ownerId);
5448 }
FormData_pg_opfamily * Form_pg_opfamily
Definition: pg_opfamily.h:51
@ OPFAMILYOID
Definition: syscache.h:74

References ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, OPFAMILYOID, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by check_object_ownership().

◆ pg_parameter_acl_aclcheck()

AclResult pg_parameter_acl_aclcheck ( Oid  acl_oid,
Oid  roleid,
AclMode  mode 
)

Definition at line 5059 of file aclchk.c.

5060 {
5061  if (pg_parameter_acl_aclmask(acl_oid, roleid, mode, ACLMASK_ANY) != 0)
5062  return ACLCHECK_OK;
5063  else
5064  return ACLCHECK_NO_PRIV;
5065 }
AclMode pg_parameter_acl_aclmask(Oid acl_oid, Oid roleid, AclMode mask, AclMaskHow how)
Definition: aclchk.c:4282

References ACLCHECK_NO_PRIV, ACLCHECK_OK, ACLMASK_ANY, mode, and pg_parameter_acl_aclmask().

◆ pg_parameter_acl_aclmask()

AclMode pg_parameter_acl_aclmask ( Oid  acl_oid,
Oid  roleid,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 4282 of file aclchk.c.

4283 {
4284  AclMode result;
4285  HeapTuple tuple;
4286  Datum aclDatum;
4287  bool isNull;
4288  Acl *acl;
4289 
4290  /* Superusers bypass all permission checking. */
4291  if (superuser_arg(roleid))
4292  return mask;
4293 
4294  /* Get the ACL from pg_parameter_acl */
4296  if (!HeapTupleIsValid(tuple))
4297  ereport(ERROR,
4298  (errcode(ERRCODE_UNDEFINED_OBJECT),
4299  errmsg("parameter ACL with OID %u does not exist",
4300  acl_oid)));
4301 
4302  aclDatum = SysCacheGetAttr(PARAMETERACLOID, tuple,
4303  Anum_pg_parameter_acl_paracl,
4304  &isNull);
4305  if (isNull)
4306  {
4307  /* No ACL, so build default ACL */
4308  acl = acldefault(OBJECT_PARAMETER_ACL, BOOTSTRAP_SUPERUSERID);
4309  aclDatum = (Datum) 0;
4310  }
4311  else
4312  {
4313  /* detoast ACL if necessary */
4314  acl = DatumGetAclP(aclDatum);
4315  }
4316 
4317  result = aclmask(acl, roleid, BOOTSTRAP_SUPERUSERID, mask, how);
4318 
4319  /* if we have a detoasted copy, free it */
4320  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4321  pfree(acl);
4322 
4323  ReleaseSysCache(tuple);
4324 
4325  return result;
4326 }
@ PARAMETERACLOID
Definition: syscache.h:76

References acldefault(), aclmask(), DatumGetAclP, DatumGetPointer, ereport, errcode(), errmsg(), ERROR, HeapTupleIsValid, OBJECT_PARAMETER_ACL, ObjectIdGetDatum, PARAMETERACLOID, pfree(), ReleaseSysCache(), SearchSysCache1(), superuser_arg(), and SysCacheGetAttr().

Referenced by pg_aclmask(), and pg_parameter_acl_aclcheck().

◆ pg_parameter_aclcheck()

AclResult pg_parameter_aclcheck ( const char *  name,
Oid  roleid,
AclMode  mode 
)

Definition at line 5046 of file aclchk.c.

5047 {
5048  if (pg_parameter_aclmask(name, roleid, mode, ACLMASK_ANY) != 0)
5049  return ACLCHECK_OK;
5050  else
5051  return ACLCHECK_NO_PRIV;
5052 }
AclMode pg_parameter_aclmask(const char *name, Oid roleid, AclMode mask, AclMaskHow how)
Definition: aclchk.c:4218
const char * name
Definition: encode.c:561

References ACLCHECK_NO_PRIV, ACLCHECK_OK, ACLMASK_ANY, mode, name, and pg_parameter_aclmask().

Referenced by AlterSystemSetConfigFile(), has_param_priv_byname(), and set_config_option().

◆ pg_parameter_aclmask()

AclMode pg_parameter_aclmask ( const char *  name,
Oid  roleid,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 4218 of file aclchk.c.

4219 {
4220  AclMode result;
4221  char *parname;
4222  text *partext;
4223  HeapTuple tuple;
4224 
4225  /* Superusers bypass all permission checking. */
4226  if (superuser_arg(roleid))
4227  return mask;
4228 
4229  /* Convert name to the form it should have in pg_parameter_acl... */
4231  partext = cstring_to_text(parname);
4232 
4233  /* ... and look it up */
4235 
4236  if (!HeapTupleIsValid(tuple))
4237  {
4238  /* If no entry, GUC has no permissions for non-superusers */
4239  result = ACL_NO_RIGHTS;
4240  }
4241  else
4242  {
4243  Datum aclDatum;
4244  bool isNull;
4245  Acl *acl;
4246 
4247  aclDatum = SysCacheGetAttr(PARAMETERACLNAME, tuple,
4248  Anum_pg_parameter_acl_paracl,
4249  &isNull);
4250  if (isNull)
4251  {
4252  /* No ACL, so build default ACL */
4253  acl = acldefault(OBJECT_PARAMETER_ACL, BOOTSTRAP_SUPERUSERID);
4254  aclDatum = (Datum) 0;
4255  }
4256  else
4257  {
4258  /* detoast ACL if necessary */
4259  acl = DatumGetAclP(aclDatum);
4260  }
4261 
4262  result = aclmask(acl, roleid, BOOTSTRAP_SUPERUSERID, mask, how);
4263 
4264  /* if we have a detoasted copy, free it */
4265  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4266  pfree(acl);
4267 
4268  ReleaseSysCache(tuple);
4269  }
4270 
4271  pfree(parname);
4272  pfree(partext);
4273 
4274  return result;
4275 }
char * convert_GUC_name_for_parameter_acl(const char *name)
Definition: guc.c:5780
#define PointerGetDatum(X)
Definition: postgres.h:600
Definition: c.h:633
@ PARAMETERACLNAME
Definition: syscache.h:75
text * cstring_to_text(const char *s)
Definition: varlena.c:188

References ACL_NO_RIGHTS, acldefault(), aclmask(), convert_GUC_name_for_parameter_acl(), cstring_to_text(), DatumGetAclP, DatumGetPointer, HeapTupleIsValid, name, OBJECT_PARAMETER_ACL, PARAMETERACLNAME, pfree(), PointerGetDatum, ReleaseSysCache(), SearchSysCache1(), superuser_arg(), and SysCacheGetAttr().

Referenced by pg_parameter_aclcheck().

◆ pg_proc_aclcheck()

◆ pg_proc_aclmask()

AclMode pg_proc_aclmask ( Oid  proc_oid,
Oid  roleid,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 4332 of file aclchk.c.

4334 {
4335  AclMode result;
4336  HeapTuple tuple;
4337  Datum aclDatum;
4338  bool isNull;
4339  Acl *acl;
4340  Oid ownerId;
4341 
4342  /* Superusers bypass all permission checking. */
4343  if (superuser_arg(roleid))
4344  return mask;
4345 
4346  /*
4347  * Get the function's ACL from pg_proc
4348  */
4349  tuple = SearchSysCache1(PROCOID, ObjectIdGetDatum(proc_oid));
4350  if (!HeapTupleIsValid(tuple))
4351  ereport(ERROR,
4352  (errcode(ERRCODE_UNDEFINED_FUNCTION),
4353  errmsg("function with OID %u does not exist", proc_oid)));
4354 
4355  ownerId = ((Form_pg_proc) GETSTRUCT(tuple))->proowner;
4356 
4357  aclDatum = SysCacheGetAttr(PROCOID, tuple, Anum_pg_proc_proacl,
4358  &isNull);
4359  if (isNull)
4360  {
4361  /* No ACL, so build default ACL */
4362  acl = acldefault(OBJECT_FUNCTION, ownerId);
4363  aclDatum = (Datum) 0;
4364  }
4365  else
4366  {
4367  /* detoast ACL if necessary */
4368  acl = DatumGetAclP(aclDatum);
4369  }
4370 
4371  result = aclmask(acl, roleid, ownerId, mask, how);
4372 
4373  /* if we have a detoasted copy, free it */
4374  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4375  pfree(acl);
4376 
4377  ReleaseSysCache(tuple);
4378 
4379  return result;
4380 }
FormData_pg_proc * Form_pg_proc
Definition: pg_proc.h:136
@ PROCOID
Definition: syscache.h:79

References acldefault(), aclmask(), DatumGetAclP, DatumGetPointer, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, HeapTupleIsValid, OBJECT_FUNCTION, ObjectIdGetDatum, pfree(), PROCOID, ReleaseSysCache(), SearchSysCache1(), superuser_arg(), and SysCacheGetAttr().

Referenced by pg_aclmask(), and pg_proc_aclcheck().

◆ pg_proc_ownercheck()

bool pg_proc_ownercheck ( Oid  proc_oid,
Oid  roleid 
)

Definition at line 5249 of file aclchk.c.

5250 {
5251  HeapTuple tuple;
5252  Oid ownerId;
5253 
5254  /* Superusers bypass all permission checking. */
5255  if (superuser_arg(roleid))
5256  return true;
5257 
5258  tuple = SearchSysCache1(PROCOID, ObjectIdGetDatum(proc_oid));
5259  if (!HeapTupleIsValid(tuple))
5260  ereport(ERROR,
5261  (errcode(ERRCODE_UNDEFINED_FUNCTION),
5262  errmsg("function with OID %u does not exist", proc_oid)));
5263 
5264  ownerId = ((Form_pg_proc) GETSTRUCT(tuple))->proowner;
5265 
5266  ReleaseSysCache(tuple);
5267 
5268  return has_privs_of_role(roleid, ownerId);
5269 }

References ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, PROCOID, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by AlterFunction(), AlterOpFamilyAdd(), check_object_ownership(), CreateTransform(), DefineOpClass(), DefineType(), and ProcedureCreate().

◆ pg_publication_ownercheck()

bool pg_publication_ownercheck ( Oid  pub_oid,
Oid  roleid 
)

Definition at line 5709 of file aclchk.c.

5710 {
5711  HeapTuple tuple;
5712  Oid ownerId;
5713 
5714  /* Superusers bypass all permission checking. */
5715  if (superuser_arg(roleid))
5716  return true;
5717 
5718  tuple = SearchSysCache1(PUBLICATIONOID, ObjectIdGetDatum(pub_oid));
5719  if (!HeapTupleIsValid(tuple))
5720  ereport(ERROR,
5721  (errcode(ERRCODE_UNDEFINED_OBJECT),
5722  errmsg("publication with OID %u does not exist", pub_oid)));
5723 
5724  ownerId = ((Form_pg_publication) GETSTRUCT(tuple))->pubowner;
5725 
5726  ReleaseSysCache(tuple);
5727 
5728  return has_privs_of_role(roleid, ownerId);
5729 }
FormData_pg_publication * Form_pg_publication
@ PUBLICATIONOID
Definition: syscache.h:83

References ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, PUBLICATIONOID, ReleaseSysCache(), SearchSysCache1(), and superuser_arg().

Referenced by AlterPublication(), AlterPublicationOwner_internal(), and check_object_ownership().

◆ pg_statistics_object_ownercheck()

bool pg_statistics_object_ownercheck ( Oid  stat_oid,
Oid  roleid 
)

Definition at line 5761 of file aclchk.c.

5762 {
5763  HeapTuple tuple;
5764  Oid ownerId;
5765 
5766  /* Superusers bypass all permission checking. */
5767  if (superuser_arg(roleid))
5768  return true;
5769 
5770  tuple = SearchSysCache1(STATEXTOID, ObjectIdGetDatum(stat_oid));
5771  if (!HeapTupleIsValid(tuple))
5772  ereport(ERROR,
5773  (errcode(ERRCODE_UNDEFINED_OBJECT),
5774  errmsg("statistics object with OID %u does not exist",
5775  stat_oid)));
5776 
5777  ownerId = ((Form_pg_statistic_ext) GETSTRUCT(tuple))->stxowner;
5778 
5779  ReleaseSysCache(tuple);
5780 
5781  return has_privs_of_role(roleid, ownerId);
5782 }
FormData_pg_statistic_ext * Form_pg_statistic_ext
@ STATEXTOID
Definition: syscache.h:96

References ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), STATEXTOID, and superuser_arg().

Referenced by AlterStatistics(), and check_object_ownership().

◆ pg_subscription_ownercheck()

bool pg_subscription_ownercheck ( Oid  sub_oid,
Oid  roleid 
)

Definition at line 5735 of file aclchk.c.

5736 {
5737  HeapTuple tuple;
5738  Oid ownerId;
5739 
5740  /* Superusers bypass all permission checking. */
5741  if (superuser_arg(roleid))
5742  return true;
5743 
5745  if (!HeapTupleIsValid(tuple))
5746  ereport(ERROR,
5747  (errcode(ERRCODE_UNDEFINED_OBJECT),
5748  errmsg("subscription with OID %u does not exist", sub_oid)));
5749 
5750  ownerId = ((Form_pg_subscription) GETSTRUCT(tuple))->subowner;
5751 
5752  ReleaseSysCache(tuple);
5753 
5754  return has_privs_of_role(roleid, ownerId);
5755 }
FormData_pg_subscription * Form_pg_subscription
@ SUBSCRIPTIONOID
Definition: syscache.h:99

References ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), SUBSCRIPTIONOID, and superuser_arg().

Referenced by AlterSubscription(), AlterSubscriptionOwner_internal(), check_object_ownership(), and DropSubscription().

◆ pg_tablespace_aclcheck()

◆ pg_tablespace_aclmask()

AclMode pg_tablespace_aclmask ( Oid  spc_oid,
Oid  roleid,
AclMode  mask,
AclMaskHow  how 
)

Definition at line 4614 of file aclchk.c.

4616 {
4617  AclMode result;
4618  HeapTuple tuple;
4619  Datum aclDatum;
4620  bool isNull;
4621  Acl *acl;
4622  Oid ownerId;
4623 
4624  /* Superusers bypass all permission checking. */
4625  if (superuser_arg(roleid))
4626  return mask;
4627 
4628  /*
4629  * Get the tablespace's ACL from pg_tablespace
4630  */
4631  tuple = SearchSysCache1(TABLESPACEOID, ObjectIdGetDatum(spc_oid));
4632  if (!HeapTupleIsValid(tuple))
4633  ereport(ERROR,
4634  (errcode(ERRCODE_UNDEFINED_OBJECT),
4635  errmsg("tablespace with OID %u does not exist", spc_oid)));
4636 
4637  ownerId = ((Form_pg_tablespace) GETSTRUCT(tuple))->spcowner;
4638 
4639  aclDatum = SysCacheGetAttr(TABLESPACEOID, tuple,
4640  Anum_pg_tablespace_spcacl,
4641  &isNull);
4642 
4643  if (isNull)
4644  {
4645  /* No ACL, so build default ACL */
4646  acl = acldefault(OBJECT_TABLESPACE, ownerId);
4647  aclDatum = (Datum) 0;
4648  }
4649  else
4650  {
4651  /* detoast ACL if necessary */
4652  acl = DatumGetAclP(aclDatum);
4653  }
4654 
4655  result = aclmask(acl, roleid, ownerId, mask, how);
4656 
4657  /* if we have a detoasted copy, free it */
4658  if (acl && (Pointer) acl != DatumGetPointer(aclDatum))
4659  pfree(acl);
4660 
4661  ReleaseSysCache(tuple);
4662 
4663  return result;
4664 }
FormData_pg_tablespace * Form_pg_tablespace
Definition: pg_tablespace.h:48
@ TABLESPACEOID
Definition: syscache.h:101

References acldefault(), aclmask(), DatumGetAclP, DatumGetPointer, ereport, errcode(), errmsg(), ERROR, GETSTRUCT, HeapTupleIsValid, OBJECT_TABLESPACE, ObjectIdGetDatum, pfree(), ReleaseSysCache(), SearchSysCache1(), superuser_arg(), SysCacheGetAttr(), and TABLESPACEOID.

Referenced by pg_aclmask(), and pg_tablespace_aclcheck().

◆ pg_tablespace_ownercheck()

bool pg_tablespace_ownercheck ( Oid  spc_oid,
Oid  roleid 
)

Definition at line 5373 of file aclchk.c.

5374 {
5375  HeapTuple spctuple;
5376  Oid spcowner;
5377 
5378  /* Superusers bypass all permission checking. */
5379  if (superuser_arg(roleid))
5380  return true;
5381 
5382  /* Search syscache for pg_tablespace */
5383  spctuple = SearchSysCache1(TABLESPACEOID, ObjectIdGetDatum(spc_oid));
5384  if (!HeapTupleIsValid(spctuple))
5385  ereport(ERROR,
5386  (errcode(ERRCODE_UNDEFINED_OBJECT),
5387  errmsg("tablespace with OID %u does not exist", spc_oid)));
5388 
5389  spcowner = ((Form_pg_tablespace) GETSTRUCT(spctuple))->spcowner;
5390 
5391  ReleaseSysCache(spctuple);
5392 
5393  return has_privs_of_role(roleid, spcowner);
5394 }

References ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), superuser_arg(), and TABLESPACEOID.

Referenced by AlterTableSpaceOptions(), check_object_ownership(), DropTableSpace(), and RenameTableSpace().

◆ pg_ts_config_ownercheck()

bool pg_ts_config_ownercheck ( Oid  cfg_oid,
Oid  roleid 
)

Definition at line 5481 of file aclchk.c.

5482 {
5483  HeapTuple tuple;
5484  Oid ownerId;
5485 
5486  /* Superusers bypass all permission checking. */
5487  if (superuser_arg(roleid))
5488  return true;
5489 
5490  tuple = SearchSysCache1(TSCONFIGOID, ObjectIdGetDatum(cfg_oid));
5491  if (!HeapTupleIsValid(tuple))
5492  ereport(ERROR,
5493  (errcode(ERRCODE_UNDEFINED_OBJECT),
5494  errmsg("text search configuration with OID %u does not exist",
5495  cfg_oid)));
5496 
5497  ownerId = ((Form_pg_ts_config) GETSTRUCT(tuple))->cfgowner;
5498 
5499  ReleaseSysCache(tuple);
5500 
5501  return has_privs_of_role(roleid, ownerId);
5502 }
FormData_pg_ts_config * Form_pg_ts_config
Definition: pg_ts_config.h:48
@ TSCONFIGOID
Definition: syscache.h:106

References ereport, errcode(), errmsg(), ERROR, GETSTRUCT, has_privs_of_role(), HeapTupleIsValid, ObjectIdGetDatum, ReleaseSysCache(), SearchSysCache1(), superu