PostgreSQL Source Code git master
Loading...
Searching...
No Matches
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 & 0xFFFFFFFF)
 
#define ACLITEM_GET_GOPTIONS(item)   (((item).ai_privs >> 32) & 0xFFFFFFFF)
 
#define ACLITEM_GET_RIGHTS(item)   ((item).ai_privs)
 
#define ACL_GRANT_OPTION_FOR(privs)   (((AclMode) (privs) & 0xFFFFFFFF) << 32)
 
#define ACL_OPTION_TO_PRIVS(privs)   (((AclMode) (privs) >> 32) & 0xFFFFFFFF)
 
#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) 0xFFFFFFFF)
 
#define ACLITEM_ALL_GOPTION_BITS   ((AclMode) 0xFFFFFFFF << 32)
 
#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_MAINTAIN_CHR   'm'
 
#define ACL_ALL_RIGHTS_STR   "arwdDxtXUCTcsAm"
 
#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|ACL_MAINTAIN)
 
#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 member_can_set_role (Oid member, Oid role)
 
void check_can_set_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)
 
Oid select_best_admin (Oid member, Oid role)
 
Oid get_role_oid (const char *rolname, bool missing_ok)
 
Oid get_role_oid_or_public (const char *rolname)
 
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)
 
charget_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_class_aclmask (Oid table_oid, Oid roleid, AclMode mask, AclMaskHow how)
 
AclResult object_aclcheck (Oid classid, Oid objectid, Oid roleid, AclMode mode)
 
AclResult object_aclcheck_ext (Oid classid, Oid objectid, Oid roleid, AclMode mode, bool *is_missing)
 
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_attribute_aclcheck_all_ext (Oid table_oid, Oid roleid, AclMode mode, AclMaskHow how, bool *is_missing)
 
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_parameter_aclcheck (const char *name, Oid roleid, AclMode mode)
 
AclResult pg_largeobject_aclcheck_snapshot (Oid lobj_oid, Oid roleid, AclMode mode, Snapshot snapshot)
 
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)
 
void ReplaceRoleInInitPriv (Oid oldroleid, Oid newroleid, Oid classid, Oid objid, int32 objsubid)
 
void RemoveRoleFromInitPriv (Oid roleid, Oid classid, Oid objid, int32 objsubid)
 
bool object_ownercheck (Oid classid, Oid objectid, 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 159 of file acl.h.

◆ ACL_ALL_RIGHTS_DATABASE

#define ACL_ALL_RIGHTS_DATABASE   (ACL_CREATE|ACL_CREATE_TEMP|ACL_CONNECT)

Definition at line 162 of file acl.h.

◆ ACL_ALL_RIGHTS_FDW

#define ACL_ALL_RIGHTS_FDW   (ACL_USAGE)

Definition at line 163 of file acl.h.

◆ ACL_ALL_RIGHTS_FOREIGN_SERVER

#define ACL_ALL_RIGHTS_FOREIGN_SERVER   (ACL_USAGE)

Definition at line 164 of file acl.h.

◆ ACL_ALL_RIGHTS_FUNCTION

#define ACL_ALL_RIGHTS_FUNCTION   (ACL_EXECUTE)

Definition at line 165 of file acl.h.

◆ ACL_ALL_RIGHTS_LANGUAGE

#define ACL_ALL_RIGHTS_LANGUAGE   (ACL_USAGE)

Definition at line 166 of file acl.h.

◆ ACL_ALL_RIGHTS_LARGEOBJECT

#define ACL_ALL_RIGHTS_LARGEOBJECT   (ACL_SELECT|ACL_UPDATE)

Definition at line 167 of file acl.h.

◆ ACL_ALL_RIGHTS_PARAMETER_ACL

#define ACL_ALL_RIGHTS_PARAMETER_ACL   (ACL_SET|ACL_ALTER_SYSTEM)

Definition at line 168 of file acl.h.

◆ ACL_ALL_RIGHTS_RELATION

Definition at line 160 of file acl.h.

◆ ACL_ALL_RIGHTS_SCHEMA

#define ACL_ALL_RIGHTS_SCHEMA   (ACL_USAGE|ACL_CREATE)

Definition at line 169 of file acl.h.

◆ ACL_ALL_RIGHTS_SEQUENCE

#define ACL_ALL_RIGHTS_SEQUENCE   (ACL_USAGE|ACL_SELECT|ACL_UPDATE)

Definition at line 161 of file acl.h.

◆ ACL_ALL_RIGHTS_STR

#define ACL_ALL_RIGHTS_STR   "arwdDxtXUCTcsAm"

Definition at line 154 of file acl.h.

◆ ACL_ALL_RIGHTS_TABLESPACE

#define ACL_ALL_RIGHTS_TABLESPACE   (ACL_CREATE)

Definition at line 170 of file acl.h.

◆ ACL_ALL_RIGHTS_TYPE

#define ACL_ALL_RIGHTS_TYPE   (ACL_USAGE)

Definition at line 171 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) & 0xFFFFFFFF) << 32)

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_MAINTAIN_CHR

#define ACL_MAINTAIN_CHR   'm'

Definition at line 151 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) >> 32) & 0xFFFFFFFF)

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) 0xFFFFFFFF << 32)

Definition at line 88 of file acl.h.

◆ ACLITEM_ALL_PRIV_BITS

#define ACLITEM_ALL_PRIV_BITS   ((AclMode) 0xFFFFFFFF)

Definition at line 87 of file acl.h.

◆ ACLITEM_GET_GOPTIONS

#define ACLITEM_GET_GOPTIONS (   item)    (((item).ai_privs >> 32) & 0xFFFFFFFF)

Definition at line 67 of file acl.h.

◆ ACLITEM_GET_PRIVS

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

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) 0xFFFFFFFF) << 32)) | \
(((AclMode) (goptions) & 0xFFFFFFFF) << 32))
uint64 AclMode
Definition parsenodes.h:74
static int fb(int x)

Definition at line 76 of file acl.h.

175{
176 ACLMASK_ALL, /* normal case: compute all bits */
177 ACLMASK_ANY, /* return when result is known nonzero */
178} AclMaskHow;
179
180/* result codes for pg_*_aclcheck */
181typedef enum
182{
183 ACLCHECK_OK = 0,
186} AclResult;
187
188
189/*
190 * routines used internally
191 */
192extern Acl *acldefault(ObjectType objtype, Oid ownerId);
193extern Acl *get_user_default_acl(ObjectType objtype, Oid ownerId,
194 Oid nsp_oid);
195extern void recordDependencyOnNewAcl(Oid classId, Oid objectId, int32 objsubId,
196 Oid ownerId, Acl *acl);
197
198extern Acl *aclupdate(const Acl *old_acl, const AclItem *mod_aip,
199 int modechg, Oid ownerId, DropBehavior behavior);
201extern Acl *make_empty_acl(void);
202extern Acl *aclcopy(const Acl *orig_acl);
203extern Acl *aclconcat(const Acl *left_acl, const Acl *right_acl);
204extern Acl *aclmerge(const Acl *left_acl, const Acl *right_acl, Oid ownerId);
205extern void aclitemsort(Acl *acl);
206extern bool aclequal(const Acl *left_acl, const Acl *right_acl);
207
208extern AclMode aclmask(const Acl *acl, Oid roleid, Oid ownerId,
209 AclMode mask, AclMaskHow how);
210extern int aclmembers(const Acl *acl, Oid **roleids);
211
212extern bool has_privs_of_role(Oid member, Oid role);
213extern bool member_can_set_role(Oid member, Oid role);
214extern void check_can_set_role(Oid member, Oid role);
215extern bool is_member_of_role(Oid member, Oid role);
216extern bool is_member_of_role_nosuper(Oid member, Oid role);
217extern bool is_admin_of_role(Oid member, Oid role);
218extern Oid select_best_admin(Oid member, Oid role);
219extern Oid get_role_oid(const char *rolname, bool missing_ok);
220extern Oid get_role_oid_or_public(const char *rolname);
221extern Oid get_rolespec_oid(const RoleSpec *role, bool missing_ok);
222extern void check_rolespec_name(const RoleSpec *role, const char *detail_msg);
223extern HeapTuple get_rolespec_tuple(const RoleSpec *role);
224extern char *get_rolespec_name(const RoleSpec *role);
225
226extern void select_best_grantor(Oid roleId, AclMode privileges,
227 const Acl *acl, Oid ownerId,
229
230extern void initialize_acl(void);
231
232/*
233 * prototypes for functions in aclchk.c
234 */
235extern void ExecuteGrantStmt(GrantStmt *stmt);
237
238extern void RemoveRoleFromObjectACL(Oid roleid, Oid classid, Oid objid);
239
241 AclMode mask, AclMaskHow how);
242
243/* generic functions */
245 Oid roleid, AclMode mode);
247 Oid roleid, AclMode mode,
248 bool *is_missing);
249
250/* special cases */
252 Oid roleid, AclMode mode);
254 Oid roleid, AclMode mode,
255 bool *is_missing);
260 bool *is_missing);
263 AclMode mode, bool *is_missing);
264extern AclResult pg_parameter_aclcheck(const char *name, Oid roleid,
265 AclMode mode);
267 AclMode mode, Snapshot snapshot);
268
269extern void aclcheck_error(AclResult aclerr, ObjectType objtype,
270 const char *objectname);
271
272extern void aclcheck_error_col(AclResult aclerr, ObjectType objtype,
273 const char *objectname, const char *colname);
274
275extern void aclcheck_error_type(AclResult aclerr, Oid typeOid);
276
277extern void recordExtObjInitPriv(Oid objoid, Oid classoid);
278extern void removeExtObjInitPriv(Oid objoid, Oid classoid);
280 Oid classid, Oid objid, int32 objsubid);
281extern void RemoveRoleFromInitPriv(Oid roleid,
282 Oid classid, Oid objid, int32 objsubid);
283
284
285/* ownercheck routines just return true (owner) or false (not) */
286extern bool object_ownercheck(Oid classid, Oid objectid, Oid roleid);
287extern bool has_createrole_privilege(Oid roleid);
288extern bool has_bypassrls_privilege(Oid roleid);
289
290#endif /* ACL_H */
AclResult object_aclcheck_ext(Oid classid, Oid objectid, Oid roleid, AclMode mode, bool *is_missing)
Definition aclchk.c:3846
void initialize_acl(void)
Definition acl.c:5041
void ExecuteGrantStmt(GrantStmt *stmt)
Definition aclchk.c:391
AclResult pg_largeobject_aclcheck_snapshot(Oid lobj_oid, Oid roleid, AclMode mode, Snapshot snapshot)
Definition aclchk.c:4076
void RemoveRoleFromInitPriv(Oid roleid, Oid classid, Oid objid, int32 objsubid)
Definition aclchk.c:4867
bool is_admin_of_role(Oid member, Oid role)
Definition acl.c:5416
Acl * aclconcat(const Acl *left_acl, const Acl *right_acl)
Definition acl.c:478
Acl * aclmerge(const Acl *left_acl, const Acl *right_acl, Oid ownerId)
Definition acl.c:502
bool has_bypassrls_privilege(Oid roleid)
Definition aclchk.c:4188
AclResult pg_class_aclcheck_ext(Oid table_oid, Oid roleid, AclMode mode, bool *is_missing)
Definition aclchk.c:4049
void aclcheck_error_col(AclResult aclerr, ObjectType objtype, const char *objectname, const char *colname)
Definition aclchk.c:2943
AclResult pg_attribute_aclcheck_all_ext(Oid table_oid, Oid roleid, AclMode mode, AclMaskHow how, bool *is_missing)
Definition aclchk.c:3921
void recordDependencyOnNewAcl(Oid classId, Oid objectId, int32 objsubId, Oid ownerId, Acl *acl)
Definition aclchk.c:4327
Oid select_best_admin(Oid member, Oid role)
Definition acl.c:5441
Acl * acldefault(ObjectType objtype, Oid ownerId)
Definition acl.c:804
Oid get_role_oid_or_public(const char *rolname)
Definition acl.c:5572
void ExecAlterDefaultPrivilegesStmt(ParseState *pstate, AlterDefaultPrivilegesStmt *stmt)
Definition aclchk.c:916
bool aclequal(const Acl *left_acl, const Acl *right_acl)
Definition acl.c:560
AclResult
Definition acl.h:182
@ ACLCHECK_NO_PRIV
Definition acl.h:184
@ ACLCHECK_OK
Definition acl.h:183
@ ACLCHECK_NOT_OWNER
Definition acl.h:185
AclResult pg_attribute_aclcheck_all(Oid table_oid, Oid roleid, AclMode mode, AclMaskHow how)
Definition aclchk.c:3910
Acl * aclupdate(const Acl *old_acl, const AclItem *mod_aip, int modechg, Oid ownerId, DropBehavior behavior)
Definition acl.c:993
bool is_member_of_role(Oid member, Oid role)
Definition acl.c:5366
AclResult pg_parameter_aclcheck(const char *name, Oid roleid, AclMode mode)
Definition aclchk.c:4064
void ReplaceRoleInInitPriv(Oid oldroleid, Oid newroleid, Oid classid, Oid objid, int32 objsubid)
Definition aclchk.c:4758
void select_best_grantor(Oid roleId, AclMode privileges, const Acl *acl, Oid ownerId, Oid *grantorId, AclMode *grantOptions)
Definition acl.c:5478
bool is_member_of_role_nosuper(Oid member, Oid role)
Definition acl.c:5394
bool has_privs_of_role(Oid member, Oid role)
Definition acl.c:5286
Acl * make_empty_acl(void)
Definition acl.c:449
void recordExtObjInitPriv(Oid objoid, Oid classoid)
Definition aclchk.c:4354
int aclmembers(const Acl *acl, Oid **roleids)
Definition acl.c:1541
Acl * aclnewowner(const Acl *old_acl, Oid oldOwnerId, Oid newOwnerId)
Definition acl.c:1120
bool member_can_set_role(Oid member, Oid role)
Definition acl.c:5320
Acl * aclcopy(const Acl *orig_acl)
Definition acl.c:458
void aclitemsort(Acl *acl)
Definition acl.c:546
AclMode aclmask(const Acl *acl, Oid roleid, Oid ownerId, AclMode mask, AclMaskHow how)
Definition acl.c:1389
void aclcheck_error(AclResult aclerr, ObjectType objtype, const char *objectname)
Definition aclchk.c:2654
AclResult pg_attribute_aclcheck(Oid table_oid, AttrNumber attnum, Oid roleid, AclMode mode)
Definition aclchk.c:3868
Oid get_role_oid(const char *rolname, bool missing_ok)
Definition acl.c:5554
AclResult object_aclcheck(Oid classid, Oid objectid, Oid roleid, AclMode mode)
Definition aclchk.c:3836
bool object_ownercheck(Oid classid, Oid objectid, Oid roleid)
Definition aclchk.c:4090
AclResult pg_attribute_aclcheck_ext(Oid table_oid, AttrNumber attnum, Oid roleid, AclMode mode, bool *is_missing)
Definition aclchk.c:3880
char * get_rolespec_name(const RoleSpec *role)
Definition acl.c:5673
void check_can_set_role(Oid member, Oid role)
Definition acl.c:5343
AclMode pg_class_aclmask(Oid table_oid, Oid roleid, AclMode mask, AclMaskHow how)
Definition aclchk.c:3272
void check_rolespec_name(const RoleSpec *role, const char *detail_msg)
Definition acl.c:5695
void aclcheck_error_type(AclResult aclerr, Oid typeOid)
Definition aclchk.c:2973
bool has_createrole_privilege(Oid roleid)
Definition aclchk.c:4169
AclMaskHow
Definition acl.h:175
@ ACLMASK_ANY
Definition acl.h:177
@ ACLMASK_ALL
Definition acl.h:176
Oid get_rolespec_oid(const RoleSpec *role, bool missing_ok)
Definition acl.c:5588
Acl * get_user_default_acl(ObjectType objtype, Oid ownerId, Oid nsp_oid)
Definition aclchk.c:4247
void RemoveRoleFromObjectACL(Oid roleid, Oid classid, Oid objid)
Definition aclchk.c:1422
AclResult pg_class_aclcheck(Oid table_oid, Oid roleid, AclMode mode)
Definition aclchk.c:4039
HeapTuple get_rolespec_tuple(const RoleSpec *role)
Definition acl.c:5627
void removeExtObjInitPriv(Oid objoid, Oid classoid)
Definition aclchk.c:4518
int16 AttrNumber
Definition attnum.h:21
int32_t int32
Definition c.h:542
#define stmt
DropBehavior
ObjectType
int16 attnum
NameData rolname
Definition pg_authid.h:34
static PgChecksumMode mode
unsigned int Oid
Definition acl.h:55
const char * name

◆ ACLITEM_SET_PRIVS

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

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) & 0xFFFFFFFF) | \
(((AclMode) (goptions) & 0xFFFFFFFF) << 32))

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

Definition at line 106 of file acl.h.

◆ AclItem

Enumeration Type Documentation

◆ AclMaskHow

Enumerator
ACLMASK_ALL 
ACLMASK_ANY 

Definition at line 174 of file acl.h.

175{
176 ACLMASK_ALL, /* normal case: compute all bits */
177 ACLMASK_ANY, /* return when result is known nonzero */
178} AclMaskHow;

◆ AclResult

Enumerator
ACLCHECK_OK 
ACLCHECK_NO_PRIV 
ACLCHECK_NOT_OWNER 

Definition at line 181 of file acl.h.

Function Documentation

◆ aclcheck_error()

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

Definition at line 2654 of file aclchk.c.

2656{
2657 switch (aclerr)
2658 {
2659 case ACLCHECK_OK:
2660 /* no error, so return to caller */
2661 break;
2662 case ACLCHECK_NO_PRIV:
2663 {
2664 const char *msg = "???";
2665
2666 switch (objtype)
2667 {
2668 case OBJECT_AGGREGATE:
2669 msg = gettext_noop("permission denied for aggregate %s");
2670 break;
2671 case OBJECT_COLLATION:
2672 msg = gettext_noop("permission denied for collation %s");
2673 break;
2674 case OBJECT_COLUMN:
2675 msg = gettext_noop("permission denied for column %s");
2676 break;
2677 case OBJECT_CONVERSION:
2678 msg = gettext_noop("permission denied for conversion %s");
2679 break;
2680 case OBJECT_DATABASE:
2681 msg = gettext_noop("permission denied for database %s");
2682 break;
2683 case OBJECT_DOMAIN:
2684 msg = gettext_noop("permission denied for domain %s");
2685 break;
2687 msg = gettext_noop("permission denied for event trigger %s");
2688 break;
2689 case OBJECT_EXTENSION:
2690 msg = gettext_noop("permission denied for extension %s");
2691 break;
2692 case OBJECT_FDW:
2693 msg = gettext_noop("permission denied for foreign-data wrapper %s");
2694 break;
2696 msg = gettext_noop("permission denied for foreign server %s");
2697 break;
2699 msg = gettext_noop("permission denied for foreign table %s");
2700 break;
2701 case OBJECT_FUNCTION:
2702 msg = gettext_noop("permission denied for function %s");
2703 break;
2704 case OBJECT_INDEX:
2705 msg = gettext_noop("permission denied for index %s");
2706 break;
2707 case OBJECT_LANGUAGE:
2708 msg = gettext_noop("permission denied for language %s");
2709 break;
2710 case OBJECT_LARGEOBJECT:
2711 msg = gettext_noop("permission denied for large object %s");
2712 break;
2713 case OBJECT_MATVIEW:
2714 msg = gettext_noop("permission denied for materialized view %s");
2715 break;
2716 case OBJECT_OPCLASS:
2717 msg = gettext_noop("permission denied for operator class %s");
2718 break;
2719 case OBJECT_OPERATOR:
2720 msg = gettext_noop("permission denied for operator %s");
2721 break;
2722 case OBJECT_OPFAMILY:
2723 msg = gettext_noop("permission denied for operator family %s");
2724 break;
2726 msg = gettext_noop("permission denied for parameter %s");
2727 break;
2728 case OBJECT_POLICY:
2729 msg = gettext_noop("permission denied for policy %s");
2730 break;
2731 case OBJECT_PROCEDURE:
2732 msg = gettext_noop("permission denied for procedure %s");
2733 break;
2734 case OBJECT_PUBLICATION:
2735 msg = gettext_noop("permission denied for publication %s");
2736 break;
2737 case OBJECT_ROUTINE:
2738 msg = gettext_noop("permission denied for routine %s");
2739 break;
2740 case OBJECT_SCHEMA:
2741 msg = gettext_noop("permission denied for schema %s");
2742 break;
2743 case OBJECT_SEQUENCE:
2744 msg = gettext_noop("permission denied for sequence %s");
2745 break;
2747 msg = gettext_noop("permission denied for statistics object %s");
2748 break;
2750 msg = gettext_noop("permission denied for subscription %s");
2751 break;
2752 case OBJECT_TABLE:
2753 msg = gettext_noop("permission denied for table %s");
2754 break;
2755 case OBJECT_TABLESPACE:
2756 msg = gettext_noop("permission denied for tablespace %s");
2757 break;
2759 msg = gettext_noop("permission denied for text search configuration %s");
2760 break;
2762 msg = gettext_noop("permission denied for text search dictionary %s");
2763 break;
2764 case OBJECT_TYPE:
2765 msg = gettext_noop("permission denied for type %s");
2766 break;
2767 case OBJECT_VIEW:
2768 msg = gettext_noop("permission denied for view %s");
2769 break;
2770 /* these currently aren't used */
2772 case OBJECT_AMOP:
2773 case OBJECT_AMPROC:
2774 case OBJECT_ATTRIBUTE:
2775 case OBJECT_CAST:
2776 case OBJECT_DEFAULT:
2777 case OBJECT_DEFACL:
2781 case OBJECT_ROLE:
2782 case OBJECT_RULE:
2784 case OBJECT_TRANSFORM:
2785 case OBJECT_TRIGGER:
2786 case OBJECT_TSPARSER:
2787 case OBJECT_TSTEMPLATE:
2789 elog(ERROR, "unsupported object type: %d", objtype);
2790 }
2791
2792 ereport(ERROR,
2794 errmsg(msg, objectname)));
2795 break;
2796 }
2797 case ACLCHECK_NOT_OWNER:
2798 {
2799 const char *msg = "???";
2800
2801 switch (objtype)
2802 {
2803 case OBJECT_AGGREGATE:
2804 msg = gettext_noop("must be owner of aggregate %s");
2805 break;
2806 case OBJECT_COLLATION:
2807 msg = gettext_noop("must be owner of collation %s");
2808 break;
2809 case OBJECT_CONVERSION:
2810 msg = gettext_noop("must be owner of conversion %s");
2811 break;
2812 case OBJECT_DATABASE:
2813 msg = gettext_noop("must be owner of database %s");
2814 break;
2815 case OBJECT_DOMAIN:
2816 msg = gettext_noop("must be owner of domain %s");
2817 break;
2819 msg = gettext_noop("must be owner of event trigger %s");
2820 break;
2821 case OBJECT_EXTENSION:
2822 msg = gettext_noop("must be owner of extension %s");
2823 break;
2824 case OBJECT_FDW:
2825 msg = gettext_noop("must be owner of foreign-data wrapper %s");
2826 break;
2828 msg = gettext_noop("must be owner of foreign server %s");
2829 break;
2831 msg = gettext_noop("must be owner of foreign table %s");
2832 break;
2833 case OBJECT_FUNCTION:
2834 msg = gettext_noop("must be owner of function %s");
2835 break;
2836 case OBJECT_INDEX:
2837 msg = gettext_noop("must be owner of index %s");
2838 break;
2839 case OBJECT_LANGUAGE:
2840 msg = gettext_noop("must be owner of language %s");
2841 break;
2842 case OBJECT_LARGEOBJECT:
2843 msg = gettext_noop("must be owner of large object %s");
2844 break;
2845 case OBJECT_MATVIEW:
2846 msg = gettext_noop("must be owner of materialized view %s");
2847 break;
2848 case OBJECT_OPCLASS:
2849 msg = gettext_noop("must be owner of operator class %s");
2850 break;
2851 case OBJECT_OPERATOR:
2852 msg = gettext_noop("must be owner of operator %s");
2853 break;
2854 case OBJECT_OPFAMILY:
2855 msg = gettext_noop("must be owner of operator family %s");
2856 break;
2857 case OBJECT_PROCEDURE:
2858 msg = gettext_noop("must be owner of procedure %s");
2859 break;
2860 case OBJECT_PUBLICATION:
2861 msg = gettext_noop("must be owner of publication %s");
2862 break;
2863 case OBJECT_ROUTINE:
2864 msg = gettext_noop("must be owner of routine %s");
2865 break;
2866 case OBJECT_SEQUENCE:
2867 msg = gettext_noop("must be owner of sequence %s");
2868 break;
2870 msg = gettext_noop("must be owner of subscription %s");
2871 break;
2872 case OBJECT_TABLE:
2873 msg = gettext_noop("must be owner of table %s");
2874 break;
2875 case OBJECT_TYPE:
2876 msg = gettext_noop("must be owner of type %s");
2877 break;
2878 case OBJECT_VIEW:
2879 msg = gettext_noop("must be owner of view %s");
2880 break;
2881 case OBJECT_SCHEMA:
2882 msg = gettext_noop("must be owner of schema %s");
2883 break;
2885 msg = gettext_noop("must be owner of statistics object %s");
2886 break;
2887 case OBJECT_TABLESPACE:
2888 msg = gettext_noop("must be owner of tablespace %s");
2889 break;
2891 msg = gettext_noop("must be owner of text search configuration %s");
2892 break;
2894 msg = gettext_noop("must be owner of text search dictionary %s");
2895 break;
2896
2897 /*
2898 * Special cases: For these, the error message talks
2899 * about "relation", because that's where the
2900 * ownership is attached. See also
2901 * check_object_ownership().
2902 */
2903 case OBJECT_COLUMN:
2904 case OBJECT_POLICY:
2905 case OBJECT_RULE:
2907 case OBJECT_TRIGGER:
2908 msg = gettext_noop("must be owner of relation %s");
2909 break;
2910 /* these currently aren't used */
2912 case OBJECT_AMOP:
2913 case OBJECT_AMPROC:
2914 case OBJECT_ATTRIBUTE:
2915 case OBJECT_CAST:
2916 case OBJECT_DEFAULT:
2917 case OBJECT_DEFACL:
2922 case OBJECT_ROLE:
2923 case OBJECT_TRANSFORM:
2924 case OBJECT_TSPARSER:
2925 case OBJECT_TSTEMPLATE:
2927 elog(ERROR, "unsupported object type: %d", objtype);
2928 }
2929
2930 ereport(ERROR,
2932 errmsg(msg, objectname)));
2933 break;
2934 }
2935 default:
2936 elog(ERROR, "unrecognized AclResult: %d", (int) aclerr);
2937 break;
2938 }
2939}
#define gettext_noop(x)
Definition c.h:1201
int errcode(int sqlerrcode)
Definition elog.c:864
int errmsg(const char *fmt,...)
Definition elog.c:1081
#define ERROR
Definition elog.h:39
#define elog(elevel,...)
Definition elog.h:226
#define ereport(elevel,...)
Definition elog.h:150
@ OBJECT_EVENT_TRIGGER
@ OBJECT_FDW
@ OBJECT_TSPARSER
@ OBJECT_COLLATION
@ OBJECT_USER_MAPPING
@ OBJECT_ACCESS_METHOD
@ OBJECT_OPCLASS
@ OBJECT_DEFACL
@ OBJECT_AGGREGATE
@ OBJECT_MATVIEW
@ OBJECT_SCHEMA
@ OBJECT_POLICY
@ OBJECT_OPERATOR
@ OBJECT_FOREIGN_TABLE
@ OBJECT_TSCONFIGURATION
@ OBJECT_OPFAMILY
@ OBJECT_DOMAIN
@ OBJECT_COLUMN
@ OBJECT_TABLESPACE
@ OBJECT_ROLE
@ OBJECT_ROUTINE
@ OBJECT_LARGEOBJECT
@ OBJECT_PUBLICATION_NAMESPACE
@ OBJECT_PROCEDURE
@ OBJECT_EXTENSION
@ OBJECT_INDEX
@ OBJECT_DEFAULT
@ OBJECT_DATABASE
@ OBJECT_SEQUENCE
@ OBJECT_TSTEMPLATE
@ OBJECT_LANGUAGE
@ OBJECT_AMOP
@ OBJECT_PUBLICATION_REL
@ OBJECT_FOREIGN_SERVER
@ OBJECT_TSDICTIONARY
@ OBJECT_ATTRIBUTE
@ OBJECT_PUBLICATION
@ OBJECT_RULE
@ OBJECT_CONVERSION
@ OBJECT_AMPROC
@ OBJECT_TABLE
@ OBJECT_VIEW
@ OBJECT_PARAMETER_ACL
@ OBJECT_TYPE
@ OBJECT_FUNCTION
@ OBJECT_TABCONSTRAINT
@ OBJECT_DOMCONSTRAINT
@ OBJECT_SUBSCRIPTION
@ OBJECT_STATISTIC_EXT
@ OBJECT_CAST
@ OBJECT_TRIGGER
@ OBJECT_TRANSFORM

References ACLCHECK_NO_PRIV, ACLCHECK_NOT_OWNER, ACLCHECK_OK, elog, ereport, errcode(), errmsg(), ERROR, fb(), 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(), CreateSubscription(), 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(), ExecCheckPermissions(), ExecInitAgg(), ExecInitExprRec(), ExecInitFunc(), ExecInitWindowAgg(), ExecReindex(), ExecuteCallStmt(), ExecuteDoStmt(), ExecuteTruncateGuts(), findRangeCanonicalFunction(), findRangeSubtypeDiffFunction(), get_connect_string(), get_other_operator(), 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(), RangeVarCallbackForDblink(), RangeVarCallbackForDropRelation(), RangeVarCallbackForLockTable(), RangeVarCallbackForPolicy(), RangeVarCallbackForReindexIndex(), RangeVarCallbackForRenameRule(), RangeVarCallbackForRenameTrigger(), RangeVarCallbackForStats(), RangeVarCallbackMaintainsTable(), RangeVarCallbackOwnsRelation(), RangeVarGetAndCheckCreationNamespace(), ReindexMultipleInternal(), ReindexMultipleTables(), renameatt_check(), RenameDatabase(), RenameSchema(), RenameTableSpace(), restrict_and_check_grant(), subquery_planner(), TargetPrivilegesCheck(), transformTableLikeClause(), truncate_check_perms(), TypeCreate(), user_mapping_ddl_aclcheck(), ValidateJoinEstimator(), ValidateOperatorReference(), and ValidateRestrictionEstimator().

◆ aclcheck_error_col()

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

Definition at line 2943 of file aclchk.c.

2945{
2946 switch (aclerr)
2947 {
2948 case ACLCHECK_OK:
2949 /* no error, so return to caller */
2950 break;
2951 case ACLCHECK_NO_PRIV:
2952 ereport(ERROR,
2954 errmsg("permission denied for column \"%s\" of relation \"%s\"",
2955 colname, objectname)));
2956 break;
2957 case ACLCHECK_NOT_OWNER:
2958 /* relation msg is OK since columns don't have separate owners */
2959 aclcheck_error(aclerr, objtype, objectname);
2960 break;
2961 default:
2962 elog(ERROR, "unrecognized AclResult: %d", (int) aclerr);
2963 break;
2964 }
2965}
void aclcheck_error(AclResult aclerr, ObjectType objtype, const char *objectname)
Definition aclchk.c:2654

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

Referenced by restrict_and_check_grant().

◆ aclcheck_error_type()

◆ aclconcat()

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

Definition at line 478 of file acl.c.

479{
481
483
486 ACL_NUM(left_acl) * sizeof(AclItem));
487
490 ACL_NUM(right_acl) * sizeof(AclItem));
491
492 return result_acl;
493}
static Acl * allocacl(int n)
Definition acl.c:427
#define ACL_DAT(ACL)
Definition acl.h:109
#define ACL_NUM(ACL)
Definition acl.h:108

References ACL_DAT, ACL_NUM, allocacl(), and fb().

Referenced by ExecGrant_Attribute().

◆ aclcopy()

Acl * aclcopy ( const Acl orig_acl)
extern

Definition at line 458 of file acl.c.

459{
461
463
466 ACL_NUM(orig_acl) * sizeof(AclItem));
467
468 return result_acl;
469}

References ACL_DAT, ACL_NUM, allocacl(), and fb().

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

◆ acldefault()

Acl * acldefault ( ObjectType  objtype,
Oid  ownerId 
)
extern

Definition at line 804 of file acl.c.

805{
808 int nacl;
809 Acl *acl;
810 AclItem *aip;
811
812 switch (objtype)
813 {
814 case OBJECT_COLUMN:
815 /* by default, columns have no extra privileges */
818 break;
819 case OBJECT_TABLE:
822 break;
823 case OBJECT_SEQUENCE:
826 break;
827 case OBJECT_DATABASE:
828 /* for backwards compatibility, grant some rights by default */
831 break;
832 case OBJECT_FUNCTION:
833 /* Grant EXECUTE by default, for now */
836 break;
837 case OBJECT_LANGUAGE:
838 /* Grant USAGE by default, for now */
841 break;
845 break;
846 case OBJECT_SCHEMA:
849 break;
853 break;
854 case OBJECT_FDW:
857 break;
861 break;
862 case OBJECT_DOMAIN:
863 case OBJECT_TYPE:
866 break;
870 break;
871 default:
872 elog(ERROR, "unrecognized object type: %d", (int) objtype);
873 world_default = ACL_NO_RIGHTS; /* keep compiler quiet */
875 break;
876 }
877
878 nacl = 0;
880 nacl++;
882 nacl++;
883
884 acl = allocacl(nacl);
885 aip = ACL_DAT(acl);
886
888 {
889 aip->ai_grantee = ACL_ID_PUBLIC;
890 aip->ai_grantor = ownerId;
892 aip++;
893 }
894
895 /*
896 * Note that the owner's entry shows all ordinary privileges but no grant
897 * options. This is because his grant options come "from the system" and
898 * not from his own efforts. (The SQL spec says that the owner's rights
899 * come from a "_SYSTEM" authid.) However, we do consider that the
900 * owner's ordinary privileges are self-granted; this lets him revoke
901 * them. We implement the owner's grant options without any explicit
902 * "_SYSTEM"-like ACL entry, by internally special-casing the owner
903 * wherever we are testing grant options.
904 */
906 {
907 aip->ai_grantee = ownerId;
908 aip->ai_grantor = ownerId;
910 }
911
912 return acl;
913}
#define ACL_ALL_RIGHTS_FOREIGN_SERVER
Definition acl.h:164
#define ACL_ALL_RIGHTS_TABLESPACE
Definition acl.h:170
#define ACL_ALL_RIGHTS_PARAMETER_ACL
Definition acl.h:168
#define ACL_ALL_RIGHTS_SCHEMA
Definition acl.h:169
#define ACL_ALL_RIGHTS_SEQUENCE
Definition acl.h:161
#define ACL_ALL_RIGHTS_DATABASE
Definition acl.h:162
#define ACL_ALL_RIGHTS_FUNCTION
Definition acl.h:165
#define ACL_ALL_RIGHTS_LANGUAGE
Definition acl.h:166
#define ACL_ALL_RIGHTS_TYPE
Definition acl.h:171
#define ACL_ALL_RIGHTS_FDW
Definition acl.h:163
#define ACLITEM_SET_PRIVS_GOPTIONS(item, privs, goptions)
Definition acl.h:82
#define ACL_ALL_RIGHTS_RELATION
Definition acl.h:160
#define ACL_ID_PUBLIC
Definition acl.h:46
#define ACL_ALL_RIGHTS_LARGEOBJECT
Definition acl.h:167
#define ACL_CREATE_TEMP
Definition parsenodes.h:86
#define ACL_USAGE
Definition parsenodes.h:84
#define ACL_NO_RIGHTS
Definition parsenodes.h:92
#define ACL_CONNECT
Definition parsenodes.h:87
#define ACL_EXECUTE
Definition parsenodes.h:83

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, allocacl(), elog, ERROR, fb(), 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_common(), ExecGrant_Largeobject(), ExecGrant_Parameter(), ExecGrant_Relation(), get_user_default_acl(), object_aclmask_ext(), pg_class_aclmask_ext(), pg_largeobject_aclmask_snapshot(), pg_namespace_aclmask_ext(), pg_parameter_acl_aclmask(), pg_parameter_aclmask(), pg_type_aclmask_ext(), and SetDefaultACL().

◆ aclequal()

bool aclequal ( const Acl left_acl,
const Acl right_acl 
)
extern

Definition at line 560 of file acl.c.

561{
562 /* Check for cases where one or both are empty/null */
563 if (left_acl == NULL || ACL_NUM(left_acl) == 0)
564 {
565 if (right_acl == NULL || ACL_NUM(right_acl) == 0)
566 return true;
567 else
568 return false;
569 }
570 else
571 {
572 if (right_acl == NULL || ACL_NUM(right_acl) == 0)
573 return false;
574 }
575
577 return false;
578
581 ACL_NUM(left_acl) * sizeof(AclItem)) == 0)
582 return true;
583
584 return false;
585}

References ACL_DAT, ACL_NUM, and fb().

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

◆ aclitemsort()

void aclitemsort ( Acl acl)
extern

Definition at line 546 of file acl.c.

547{
548 if (acl != NULL && ACL_NUM(acl) > 1)
549 qsort(ACL_DAT(acl), ACL_NUM(acl), sizeof(AclItem), aclitemComparator);
550}
static int aclitemComparator(const void *arg1, const void *arg2)
Definition acl.c:725
#define qsort(a, b, c, d)
Definition port.h:495

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

Referenced by get_user_default_acl(), and SetDefaultACL().

◆ aclmask()

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

Definition at line 1389 of file acl.c.

1391{
1392 AclMode result;
1394 AclItem *aidat;
1395 int i,
1396 num;
1397
1398 /*
1399 * Null ACL should not happen, since caller should have inserted
1400 * appropriate default
1401 */
1402 if (acl == NULL)
1403 elog(ERROR, "null ACL");
1404
1405 check_acl(acl);
1406
1407 /* Quick exit for mask == 0 */
1408 if (mask == 0)
1409 return 0;
1410
1411 result = 0;
1412
1413 /* Owner always implicitly has all grant options */
1414 if ((mask & ACLITEM_ALL_GOPTION_BITS) &&
1415 has_privs_of_role(roleid, ownerId))
1416 {
1417 result = mask & ACLITEM_ALL_GOPTION_BITS;
1418 if ((how == ACLMASK_ALL) ? (result == mask) : (result != 0))
1419 return result;
1420 }
1421
1422 num = ACL_NUM(acl);
1423 aidat = ACL_DAT(acl);
1424
1425 /*
1426 * Check privileges granted directly to roleid or to public
1427 */
1428 for (i = 0; i < num; i++)
1429 {
1430 AclItem *aidata = &aidat[i];
1431
1432 if (aidata->ai_grantee == ACL_ID_PUBLIC ||
1433 aidata->ai_grantee == roleid)
1434 {
1435 result |= aidata->ai_privs & mask;
1436 if ((how == ACLMASK_ALL) ? (result == mask) : (result != 0))
1437 return result;
1438 }
1439 }
1440
1441 /*
1442 * Check privileges granted indirectly via role memberships. We do this in
1443 * a separate pass to minimize expensive indirect membership tests. In
1444 * particular, it's worth testing whether a given ACL entry grants any
1445 * privileges still of interest before we perform the has_privs_of_role
1446 * test.
1447 */
1448 remaining = mask & ~result;
1449 for (i = 0; i < num; i++)
1450 {
1451 AclItem *aidata = &aidat[i];
1452
1453 if (aidata->ai_grantee == ACL_ID_PUBLIC ||
1454 aidata->ai_grantee == roleid)
1455 continue; /* already checked it */
1456
1457 if ((aidata->ai_privs & remaining) &&
1458 has_privs_of_role(roleid, aidata->ai_grantee))
1459 {
1460 result |= aidata->ai_privs & mask;
1461 if ((how == ACLMASK_ALL) ? (result == mask) : (result != 0))
1462 return result;
1463 remaining = mask & ~result;
1464 }
1465 }
1466
1467 return result;
1468}
static void check_acl(const Acl *acl)
Definition acl.c:591
bool has_privs_of_role(Oid member, Oid role)
Definition acl.c:5286
#define ACLITEM_ALL_GOPTION_BITS
Definition acl.h:88
int remaining
Definition informix.c:692
int i
Definition isn.c:77
AclMode ai_privs
Definition acl.h:58

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

Referenced by check_circularity(), LockTableAclCheck(), object_aclmask_ext(), pg_attribute_aclcheck_all_ext(), pg_attribute_aclmask_ext(), pg_class_aclmask_ext(), pg_largeobject_aclmask_snapshot(), pg_namespace_aclmask_ext(), pg_parameter_acl_aclmask(), pg_parameter_aclmask(), pg_type_aclmask_ext(), and recursive_revoke().

◆ aclmembers()

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

Definition at line 1541 of file acl.c.

1542{
1543 Oid *list;
1544 const AclItem *acldat;
1545 int i,
1546 j;
1547
1548 if (acl == NULL || ACL_NUM(acl) == 0)
1549 {
1550 *roleids = NULL;
1551 return 0;
1552 }
1553
1554 check_acl(acl);
1555
1556 /* Allocate the worst-case space requirement */
1557 list = palloc(ACL_NUM(acl) * 2 * sizeof(Oid));
1558 acldat = ACL_DAT(acl);
1559
1560 /*
1561 * Walk the ACL collecting mentioned RoleIds.
1562 */
1563 j = 0;
1564 for (i = 0; i < ACL_NUM(acl); i++)
1565 {
1566 const AclItem *ai = &acldat[i];
1567
1568 if (ai->ai_grantee != ACL_ID_PUBLIC)
1569 list[j++] = ai->ai_grantee;
1570 /* grantor is currently never PUBLIC, but let's check anyway */
1571 if (ai->ai_grantor != ACL_ID_PUBLIC)
1572 list[j++] = ai->ai_grantor;
1573 }
1574
1575 /* Sort the array */
1576 qsort(list, j, sizeof(Oid), oid_cmp);
1577
1578 /*
1579 * We could repalloc the array down to minimum size, but it's hardly worth
1580 * it since it's only transient memory.
1581 */
1582 *roleids = list;
1583
1584 /* Remove duplicates from the array */
1585 return qunique(list, j, sizeof(Oid), oid_cmp);
1586}
int j
Definition isn.c:78
void * palloc(Size size)
Definition mcxt.c:1387
int oid_cmp(const void *p1, const void *p2)
Definition oid.c:287
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, check_acl(), fb(), i, j, oid_cmp(), palloc(), qsort, and qunique().

Referenced by ExecGrant_Attribute(), ExecGrant_common(), ExecGrant_Largeobject(), ExecGrant_Parameter(), ExecGrant_Relation(), recordDependencyOnNewAcl(), recordExtensionInitPrivWorker(), RemoveRoleFromInitPriv(), ReplaceRoleInInitPriv(), and SetDefaultACL().

◆ aclmerge()

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

Definition at line 502 of file acl.c.

503{
505 AclItem *aip;
506 int i,
507 num;
508
509 /* Check for cases where one or both are empty/null */
510 if (left_acl == NULL || ACL_NUM(left_acl) == 0)
511 {
512 if (right_acl == NULL || ACL_NUM(right_acl) == 0)
513 return NULL;
514 else
515 return aclcopy(right_acl);
516 }
517 else
518 {
519 if (right_acl == NULL || ACL_NUM(right_acl) == 0)
520 return aclcopy(left_acl);
521 }
522
523 /* Merge them the hard way, one item at a time */
525
527 num = ACL_NUM(right_acl);
528
529 for (i = 0; i < num; i++, aip++)
530 {
531 Acl *tmp_acl;
532
534 ownerId, DROP_RESTRICT);
537 }
538
539 return result_acl;
540}
Acl * aclupdate(const Acl *old_acl, const AclItem *mod_aip, int modechg, Oid ownerId, DropBehavior behavior)
Definition acl.c:993
Acl * aclcopy(const Acl *orig_acl)
Definition acl.c:458
#define ACL_MODECHG_ADD
Definition acl.h:129
void pfree(void *pointer)
Definition mcxt.c:1616
@ DROP_RESTRICT

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

Referenced by get_user_default_acl().

◆ aclnewowner()

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

Definition at line 1120 of file acl.c.

1121{
1122 Acl *new_acl;
1128 bool newpresent = false;
1129 int dst,
1130 src,
1131 targ,
1132 num;
1133
1135
1136 /*
1137 * Make a copy of the given ACL, substituting new owner ID for old
1138 * wherever it appears as either grantor or grantee. Also note if the new
1139 * owner ID is already present.
1140 */
1141 num = ACL_NUM(old_acl);
1143 new_acl = allocacl(num);
1145 memcpy(new_aip, old_aip, num * sizeof(AclItem));
1146 for (dst = 0, dst_aip = new_aip; dst < num; dst++, dst_aip++)
1147 {
1148 if (dst_aip->ai_grantor == oldOwnerId)
1149 dst_aip->ai_grantor = newOwnerId;
1150 else if (dst_aip->ai_grantor == newOwnerId)
1151 newpresent = true;
1152 if (dst_aip->ai_grantee == oldOwnerId)
1153 dst_aip->ai_grantee = newOwnerId;
1154 else if (dst_aip->ai_grantee == newOwnerId)
1155 newpresent = true;
1156 }
1157
1158 /*
1159 * If the old ACL contained any references to the new owner, then we may
1160 * now have generated an ACL containing duplicate entries. Find them and
1161 * merge them so that there are not duplicates. (This is relatively
1162 * expensive since we use a stupid O(N^2) algorithm, but it's unlikely to
1163 * be the normal case.)
1164 *
1165 * To simplify deletion of duplicate entries, we temporarily leave them in
1166 * the array but set their privilege masks to zero; when we reach such an
1167 * entry it's just skipped. (Thus, a side effect of this code will be to
1168 * remove privilege-free entries, should there be any in the input.) dst
1169 * is the next output slot, targ is the currently considered input slot
1170 * (always >= dst), and src scans entries to the right of targ looking for
1171 * duplicates. Once an entry has been emitted to dst it is known
1172 * duplicate-free and need not be considered anymore.
1173 */
1174 if (newpresent)
1175 {
1176 dst = 0;
1177 for (targ = 0, targ_aip = new_aip; targ < num; targ++, targ_aip++)
1178 {
1179 /* ignore if deleted in an earlier pass */
1181 continue;
1182 /* find and merge any duplicates */
1183 for (src = targ + 1, src_aip = targ_aip + 1; src < num;
1184 src++, src_aip++)
1185 {
1187 continue;
1189 {
1193 /* mark the duplicate deleted */
1195 }
1196 }
1197 /* and emit to output */
1198 new_aip[dst] = *targ_aip;
1199 dst++;
1200 }
1201 /* Adjust array size to be 'dst' items */
1202 ARR_DIMS(new_acl)[0] = dst;
1204 }
1205
1206 return new_acl;
1207}
static bool aclitem_match(const AclItem *a1, const AclItem *a2)
Definition acl.c:714
#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:294
static void SET_VARSIZE(void *PTR, Size len)
Definition varatt.h:432

References ACL_DAT, ACL_N_SIZE, ACL_NO_RIGHTS, ACL_NUM, ACLITEM_GET_RIGHTS, aclitem_match(), ACLITEM_SET_RIGHTS, allocacl(), ARR_DIMS, check_acl(), fb(), and SET_VARSIZE().

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

◆ aclupdate()

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

Definition at line 993 of file acl.c.

995{
996 Acl *new_acl = NULL;
998 *new_aip = NULL;
1001 new_rights,
1003 int dst,
1004 num;
1005
1006 /* Caller probably already checked old_acl, but be safe */
1008
1009 /* If granting grant options, check for circularity */
1010 if (modechg != ACL_MODECHG_DEL &&
1013
1014 num = ACL_NUM(old_acl);
1016
1017 /*
1018 * Search the ACL for an existing entry for this grantee and grantor. If
1019 * one exists, just modify the entry in-place (well, in the same position,
1020 * since we actually return a copy); otherwise, insert the new entry at
1021 * the end.
1022 */
1023
1024 for (dst = 0; dst < num; ++dst)
1025 {
1027 {
1028 /* found a match, so modify existing item */
1029 new_acl = allocacl(num);
1032 break;
1033 }
1034 }
1035
1036 if (dst == num)
1037 {
1038 /* need to append a new item */
1039 new_acl = allocacl(num + 1);
1041 memcpy(new_aip, old_aip, num * sizeof(AclItem));
1042
1043 /* initialize the new entry with no permissions */
1044 new_aip[dst].ai_grantee = mod_aip->ai_grantee;
1045 new_aip[dst].ai_grantor = mod_aip->ai_grantor;
1048 num++; /* set num to the size of new_acl */
1049 }
1050
1053
1054 /* apply the specified permissions change */
1055 switch (modechg)
1056 {
1057 case ACL_MODECHG_ADD:
1060 break;
1061 case ACL_MODECHG_DEL:
1064 break;
1065 case ACL_MODECHG_EQL:
1068 break;
1069 }
1070
1073
1074 /*
1075 * If the adjusted entry has no permissions, delete it from the list.
1076 */
1078 {
1080 new_aip + dst + 1,
1081 (num - dst - 1) * sizeof(AclItem));
1082 /* Adjust array size to be 'num - 1' items */
1083 ARR_DIMS(new_acl)[0] = num - 1;
1084 SET_VARSIZE(new_acl, ACL_N_SIZE(num - 1));
1085 }
1086
1087 /*
1088 * Remove abandoned privileges (cascading revoke). Currently we can only
1089 * handle this when the grantee is not PUBLIC.
1090 */
1091 if ((old_goptions & ~new_goptions) != 0)
1092 {
1093 Assert(mod_aip->ai_grantee != ACL_ID_PUBLIC);
1094 new_acl = recursive_revoke(new_acl, mod_aip->ai_grantee,
1096 ownerId, behavior);
1097 }
1098
1099 return new_acl;
1100}
static Acl * recursive_revoke(Acl *acl, Oid grantee, AclMode revoke_privs, Oid ownerId, DropBehavior behavior)
Definition acl.c:1303
static void check_circularity(const Acl *old_acl, const AclItem *mod_aip, Oid ownerId)
Definition acl.c:1223
#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
#define Assert(condition)
Definition c.h:873

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, allocacl(), ARR_DIMS, Assert, check_acl(), check_circularity(), fb(), recursive_revoke(), and SET_VARSIZE().

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

◆ check_can_set_role()

void check_can_set_role ( Oid  member,
Oid  role 
)
extern

Definition at line 5343 of file acl.c.

5344{
5345 if (!member_can_set_role(member, role))
5346 ereport(ERROR,
5348 errmsg("must be able to SET ROLE \"%s\"",
5349 GetUserNameFromId(role, false))));
5350}
bool member_can_set_role(Oid member, Oid role)
Definition acl.c:5320
char * GetUserNameFromId(Oid roleid, bool noerr)
Definition miscinit.c:988

References ereport, errcode(), errmsg(), ERROR, fb(), GetUserNameFromId(), and member_can_set_role().

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

◆ check_rolespec_name()

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

Definition at line 5695 of file acl.c.

5696{
5697 if (!role)
5698 return;
5699
5700 if (role->roletype != ROLESPEC_CSTRING)
5701 return;
5702
5703 if (IsReservedName(role->rolename))
5704 {
5705 if (detail_msg)
5706 ereport(ERROR,
5708 errmsg("role name \"%s\" is reserved",
5709 role->rolename),
5711 else
5712 ereport(ERROR,
5714 errmsg("role name \"%s\" is reserved",
5715 role->rolename)));
5716 }
5717}
bool IsReservedName(const char *name)
Definition catalog.c:278
int errdetail_internal(const char *fmt,...)
Definition elog.c:1244
@ ROLESPEC_CSTRING
Definition parsenodes.h:419
RoleSpecType roletype
Definition parsenodes.h:429
char * rolename
Definition parsenodes.h:430

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

Referenced by AlterRole(), and AlterRoleSet().

◆ ExecAlterDefaultPrivilegesStmt()

void ExecAlterDefaultPrivilegesStmt ( ParseState pstate,
AlterDefaultPrivilegesStmt stmt 
)
extern

Definition at line 916 of file aclchk.c.

917{
918 GrantStmt *action = stmt->action;
920 ListCell *cell;
921 List *rolespecs = NIL;
922 List *nspnames = NIL;
926 const char *errormsg;
927
928 /* Deconstruct the "options" part of the statement */
929 foreach(cell, stmt->options)
930 {
931 DefElem *defel = (DefElem *) lfirst(cell);
932
933 if (strcmp(defel->defname, "schemas") == 0)
934 {
935 if (dnspnames)
938 }
939 else if (strcmp(defel->defname, "roles") == 0)
940 {
941 if (drolespecs)
944 }
945 else
946 elog(ERROR, "option \"%s\" not recognized", defel->defname);
947 }
948
949 if (dnspnames)
950 nspnames = (List *) dnspnames->arg;
951 if (drolespecs)
952 rolespecs = (List *) drolespecs->arg;
953
954 /* Prepare the InternalDefaultACL representation of the statement */
955 /* roleid to be filled below */
956 /* nspid to be filled in SetDefaultACLsInSchemas */
957 iacls.is_grant = action->is_grant;
958 iacls.objtype = action->objtype;
959 /* all_privs to be filled below */
960 /* privileges to be filled below */
961 iacls.grantees = NIL; /* filled below */
962 iacls.grant_option = action->grant_option;
963 iacls.behavior = action->behavior;
964
965 /*
966 * Convert the RoleSpec list into an Oid list. Note that at this point we
967 * insert an ACL_ID_PUBLIC into the list if appropriate, so downstream
968 * there shouldn't be any additional work needed to support this case.
969 */
970 foreach(cell, action->grantees)
971 {
972 RoleSpec *grantee = (RoleSpec *) lfirst(cell);
974
975 switch (grantee->roletype)
976 {
977 case ROLESPEC_PUBLIC:
979 break;
980 default:
982 break;
983 }
984 iacls.grantees = lappend_oid(iacls.grantees, grantee_uid);
985 }
986
987 /*
988 * Convert action->privileges, a list of privilege strings, into an
989 * AclMode bitmask.
990 */
991 switch (action->objtype)
992 {
993 case OBJECT_TABLE:
995 errormsg = gettext_noop("invalid privilege type %s for relation");
996 break;
997 case OBJECT_SEQUENCE:
999 errormsg = gettext_noop("invalid privilege type %s for sequence");
1000 break;
1001 case OBJECT_FUNCTION:
1003 errormsg = gettext_noop("invalid privilege type %s for function");
1004 break;
1005 case OBJECT_PROCEDURE:
1007 errormsg = gettext_noop("invalid privilege type %s for procedure");
1008 break;
1009 case OBJECT_ROUTINE:
1011 errormsg = gettext_noop("invalid privilege type %s for routine");
1012 break;
1013 case OBJECT_TYPE:
1015 errormsg = gettext_noop("invalid privilege type %s for type");
1016 break;
1017 case OBJECT_SCHEMA:
1019 errormsg = gettext_noop("invalid privilege type %s for schema");
1020 break;
1021 case OBJECT_LARGEOBJECT:
1023 errormsg = gettext_noop("invalid privilege type %s for large object");
1024 break;
1025 default:
1026 elog(ERROR, "unrecognized GrantStmt.objtype: %d",
1027 (int) action->objtype);
1028 /* keep compiler quiet */
1030 errormsg = NULL;
1031 }
1032
1033 if (action->privileges == NIL)
1034 {
1035 iacls.all_privs = true;
1036
1037 /*
1038 * will be turned into ACL_ALL_RIGHTS_* by the internal routines
1039 * depending on the object type
1040 */
1041 iacls.privileges = ACL_NO_RIGHTS;
1042 }
1043 else
1044 {
1045 iacls.all_privs = false;
1046 iacls.privileges = ACL_NO_RIGHTS;
1047
1048 foreach(cell, action->privileges)
1049 {
1050 AccessPriv *privnode = (AccessPriv *) lfirst(cell);
1051 AclMode priv;
1052
1053 if (privnode->cols)
1054 ereport(ERROR,
1056 errmsg("default privileges cannot be set for columns")));
1057
1058 if (privnode->priv_name == NULL) /* parser mistake? */
1059 elog(ERROR, "AccessPriv node must specify privilege");
1060 priv = string_to_privilege(privnode->priv_name);
1061
1062 if (priv & ~all_privileges)
1063 ereport(ERROR,
1065 errmsg(errormsg, privilege_to_string(priv))));
1066
1067 iacls.privileges |= priv;
1068 }
1069 }
1070
1071 if (rolespecs == NIL)
1072 {
1073 /* Set permissions for myself */
1074 iacls.roleid = GetUserId();
1075
1077 }
1078 else
1079 {
1080 /* Look up the role OIDs and do permissions checks */
1082
1083 foreach(rolecell, rolespecs)
1084 {
1086
1087 iacls.roleid = get_rolespec_oid(rolespec, false);
1088
1089 if (!has_privs_of_role(GetUserId(), iacls.roleid))
1090 ereport(ERROR,
1092 errmsg("permission denied to change default privileges")));
1093
1095 }
1096 }
1097}
Oid get_rolespec_oid(const RoleSpec *role, bool missing_ok)
Definition acl.c:5588
static AclMode string_to_privilege(const char *privname)
Definition aclchk.c:2566
static void SetDefaultACLsInSchemas(InternalDefaultACL *iacls, List *nspnames)
Definition aclchk.c:1105
static const char * privilege_to_string(AclMode privilege)
Definition aclchk.c:2607
void errorConflictingDefElem(DefElem *defel, ParseState *pstate)
Definition define.c:370
List * lappend_oid(List *list, Oid datum)
Definition list.c:375
Oid GetUserId(void)
Definition miscinit.c:469
@ ROLESPEC_PUBLIC
Definition parsenodes.h:423
#define lfirst(lc)
Definition pg_list.h:172
#define NIL
Definition pg_list.h:68
Definition pg_list.h:54

References ACL_ALL_RIGHTS_FUNCTION, ACL_ALL_RIGHTS_LARGEOBJECT, ACL_ALL_RIGHTS_RELATION, ACL_ALL_RIGHTS_SCHEMA, ACL_ALL_RIGHTS_SEQUENCE, ACL_ALL_RIGHTS_TYPE, ACL_ID_PUBLIC, ACL_NO_RIGHTS, elog, ereport, errcode(), errmsg(), ERROR, errorConflictingDefElem(), fb(), get_rolespec_oid(), gettext_noop, GetUserId(), has_privs_of_role(), lappend_oid(), lfirst, NIL, OBJECT_FUNCTION, OBJECT_LARGEOBJECT, OBJECT_PROCEDURE, OBJECT_ROUTINE, OBJECT_SCHEMA, OBJECT_SEQUENCE, OBJECT_TABLE, OBJECT_TYPE, privilege_to_string(), ROLESPEC_PUBLIC, SetDefaultACLsInSchemas(), stmt, and string_to_privilege().

Referenced by ProcessUtilitySlow().

◆ ExecuteGrantStmt()

void ExecuteGrantStmt ( GrantStmt stmt)
extern

Definition at line 391 of file aclchk.c.

392{
393 InternalGrant istmt;
394 ListCell *cell;
395 const char *errormsg;
397
398 if (stmt->grantor)
399 {
400 Oid grantor;
401
402 grantor = get_rolespec_oid(stmt->grantor, false);
403
404 /*
405 * Currently, this clause is only for SQL compatibility, not very
406 * interesting otherwise.
407 */
408 if (grantor != GetUserId())
411 errmsg("grantor must be current user")));
412 }
413
414 /*
415 * Turn the regular GrantStmt into the InternalGrant form.
416 */
417 istmt.is_grant = stmt->is_grant;
418 istmt.objtype = stmt->objtype;
419
420 /* Collect the OIDs of the target objects */
421 switch (stmt->targtype)
422 {
424 istmt.objects = objectNamesToOids(stmt->objtype, stmt->objects,
425 stmt->is_grant);
426 break;
428 istmt.objects = objectsInSchemaToOids(stmt->objtype, stmt->objects);
429 break;
430 /* ACL_TARGET_DEFAULTS should not be seen here */
431 default:
432 elog(ERROR, "unrecognized GrantStmt.targtype: %d",
433 (int) stmt->targtype);
434 }
435
436 /* all_privs to be filled below */
437 /* privileges to be filled below */
438 istmt.col_privs = NIL; /* may get filled below */
439 istmt.grantees = NIL; /* filled below */
440 istmt.grant_option = stmt->grant_option;
441 istmt.behavior = stmt->behavior;
442
443 /*
444 * Convert the RoleSpec list into an Oid list. Note that at this point we
445 * insert an ACL_ID_PUBLIC into the list if appropriate, so downstream
446 * there shouldn't be any additional work needed to support this case.
447 */
448 foreach(cell, stmt->grantees)
449 {
450 RoleSpec *grantee = (RoleSpec *) lfirst(cell);
452
453 switch (grantee->roletype)
454 {
455 case ROLESPEC_PUBLIC:
457 break;
458 default:
460 break;
461 }
463 }
464
465 /*
466 * Convert stmt->privileges, a list of AccessPriv nodes, into an AclMode
467 * bitmask. Note: objtype can't be OBJECT_COLUMN.
468 */
469 switch (stmt->objtype)
470 {
471 case OBJECT_TABLE:
472
473 /*
474 * Because this might be a sequence, we test both relation and
475 * sequence bits, and later do a more limited test when we know
476 * the object type.
477 */
479 errormsg = gettext_noop("invalid privilege type %s for relation");
480 break;
481 case OBJECT_SEQUENCE:
483 errormsg = gettext_noop("invalid privilege type %s for sequence");
484 break;
485 case OBJECT_DATABASE:
487 errormsg = gettext_noop("invalid privilege type %s for database");
488 break;
489 case OBJECT_DOMAIN:
491 errormsg = gettext_noop("invalid privilege type %s for domain");
492 break;
493 case OBJECT_FUNCTION:
495 errormsg = gettext_noop("invalid privilege type %s for function");
496 break;
497 case OBJECT_LANGUAGE:
499 errormsg = gettext_noop("invalid privilege type %s for language");
500 break;
503 errormsg = gettext_noop("invalid privilege type %s for large object");
504 break;
505 case OBJECT_SCHEMA:
507 errormsg = gettext_noop("invalid privilege type %s for schema");
508 break;
509 case OBJECT_PROCEDURE:
511 errormsg = gettext_noop("invalid privilege type %s for procedure");
512 break;
513 case OBJECT_ROUTINE:
515 errormsg = gettext_noop("invalid privilege type %s for routine");
516 break;
519 errormsg = gettext_noop("invalid privilege type %s for tablespace");
520 break;
521 case OBJECT_TYPE:
523 errormsg = gettext_noop("invalid privilege type %s for type");
524 break;
525 case OBJECT_FDW:
527 errormsg = gettext_noop("invalid privilege type %s for foreign-data wrapper");
528 break;
531 errormsg = gettext_noop("invalid privilege type %s for foreign server");
532 break;
535 errormsg = gettext_noop("invalid privilege type %s for parameter");
536 break;
537 default:
538 elog(ERROR, "unrecognized GrantStmt.objtype: %d",
539 (int) stmt->objtype);
540 /* keep compiler quiet */
542 errormsg = NULL;
543 }
544
545 if (stmt->privileges == NIL)
546 {
547 istmt.all_privs = true;
548
549 /*
550 * will be turned into ACL_ALL_RIGHTS_* by the internal routines
551 * depending on the object type
552 */
554 }
555 else
556 {
557 istmt.all_privs = false;
559
560 foreach(cell, stmt->privileges)
561 {
563 AclMode priv;
564
565 /*
566 * If it's a column-level specification, we just set it aside in
567 * col_privs for the moment; but insist it's for a relation.
568 */
569 if (privnode->cols)
570 {
571 if (stmt->objtype != OBJECT_TABLE)
574 errmsg("column privileges are only valid for relations")));
575 istmt.col_privs = lappend(istmt.col_privs, privnode);
576 continue;
577 }
578
579 if (privnode->priv_name == NULL) /* parser mistake? */
580 elog(ERROR, "AccessPriv node must specify privilege or columns");
581 priv = string_to_privilege(privnode->priv_name);
582
583 if (priv & ~all_privileges)
586 errmsg(errormsg, privilege_to_string(priv))));
587
588 istmt.privileges |= priv;
589 }
590 }
591
592 ExecGrantStmt_oids(&istmt);
593}
static void ExecGrantStmt_oids(InternalGrant *istmt)
Definition aclchk.c:601
static List * objectNamesToOids(ObjectType objtype, List *objnames, bool is_grant)
Definition aclchk.c:677
static List * objectsInSchemaToOids(ObjectType objtype, List *nspnames)
Definition aclchk.c:789
List * lappend(List *list, void *datum)
Definition list.c:339
@ ACL_TARGET_OBJECT
@ ACL_TARGET_ALL_IN_SCHEMA
DropBehavior behavior
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, InternalGrant::behavior, InternalGrant::col_privs, elog, ereport, errcode(), errmsg(), ERROR, ExecGrantStmt_oids(), fb(), get_rolespec_oid(), gettext_noop, GetUserId(), InternalGrant::grant_option, InternalGrant::grantees, 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(), InternalGrant::objects, objectsInSchemaToOids(), InternalGrant::objtype, privilege_to_string(), InternalGrant::privileges, ROLESPEC_PUBLIC, stmt, and string_to_privilege().

Referenced by ProcessUtilitySlow(), and standard_ProcessUtility().

◆ get_role_oid()

Oid get_role_oid ( const char rolname,
bool  missing_ok 
)
extern

Definition at line 5554 of file acl.c.

5555{
5556 Oid oid;
5557
5560 if (!OidIsValid(oid) && !missing_ok)
5561 ereport(ERROR,
5563 errmsg("role \"%s\" does not exist", rolname)));
5564 return oid;
5565}
#define OidIsValid(objectId)
Definition c.h:788
static Datum CStringGetDatum(const char *X)
Definition postgres.h:380
#define GetSysCacheOid1(cacheId, oidcol, key1)
Definition syscache.h:109

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

Referenced by aclparse(), check_hba(), check_ident_usermap(), 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 worker_spi_launch().

◆ get_role_oid_or_public()

◆ get_rolespec_name()

char * get_rolespec_name ( const RoleSpec role)
extern

Definition at line 5673 of file acl.c.

5674{
5675 HeapTuple tp;
5677 char *rolename;
5678
5679 tp = get_rolespec_tuple(role);
5681 rolename = pstrdup(NameStr(authForm->rolname));
5682 ReleaseSysCache(tp);
5683
5684 return rolename;
5685}
HeapTuple get_rolespec_tuple(const RoleSpec *role)
Definition acl.c:5627
#define NameStr(name)
Definition c.h:765
static void * GETSTRUCT(const HeapTupleData *tuple)
char * pstrdup(const char *in)
Definition mcxt.c:1781
FormData_pg_authid * Form_pg_authid
Definition pg_authid.h:56
void ReleaseSysCache(HeapTuple tuple)
Definition syscache.c:264

References fb(), 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 
)
extern

Definition at line 5588 of file acl.c.

5589{
5590 Oid oid;
5591
5592 switch (role->roletype)
5593 {
5594 case ROLESPEC_CSTRING:
5595 Assert(role->rolename);
5596 oid = get_role_oid(role->rolename, missing_ok);
5597 break;
5598
5601 oid = GetUserId();
5602 break;
5603
5605 oid = GetSessionUserId();
5606 break;
5607
5608 case ROLESPEC_PUBLIC:
5609 ereport(ERROR,
5611 errmsg("role \"%s\" does not exist", "public")));
5612 oid = InvalidOid; /* make compiler happy */
5613 break;
5614
5615 default:
5616 elog(ERROR, "unexpected role type %d", role->roletype);
5617 }
5618
5619 return oid;
5620}
Oid GetSessionUserId(void)
Definition miscinit.c:508
@ ROLESPEC_CURRENT_USER
Definition parsenodes.h:421
@ ROLESPEC_SESSION_USER
Definition parsenodes.h:422
@ ROLESPEC_CURRENT_ROLE
Definition parsenodes.h:420
#define InvalidOid

References Assert, elog, ereport, errcode(), errmsg(), ERROR, fb(), 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)
extern

Definition at line 5627 of file acl.c.

5628{
5629 HeapTuple tuple;
5630
5631 switch (role->roletype)
5632 {
5633 case ROLESPEC_CSTRING:
5634 Assert(role->rolename);
5636 if (!HeapTupleIsValid(tuple))
5637 ereport(ERROR,
5639 errmsg("role \"%s\" does not exist", role->rolename)));
5640 break;
5641
5645 if (!HeapTupleIsValid(tuple))
5646 elog(ERROR, "cache lookup failed for role %u", GetUserId());
5647 break;
5648
5651 if (!HeapTupleIsValid(tuple))
5652 elog(ERROR, "cache lookup failed for role %u", GetSessionUserId());
5653 break;
5654
5655 case ROLESPEC_PUBLIC:
5656 ereport(ERROR,
5658 errmsg("role \"%s\" does not exist", "public")));
5659 tuple = NULL; /* make compiler happy */
5660 break;
5661
5662 default:
5663 elog(ERROR, "unexpected role type %d", role->roletype);
5664 }
5665
5666 return tuple;
5667}
#define HeapTupleIsValid(tuple)
Definition htup.h:78
static Datum ObjectIdGetDatum(Oid X)
Definition postgres.h:262
HeapTuple SearchSysCache1(SysCacheIdentifier cacheId, Datum key1)
Definition syscache.c:220

References Assert, CStringGetDatum(), elog, ereport, errcode(), errmsg(), ERROR, fb(), GetSessionUserId(), GetUserId(), HeapTupleIsValid, ObjectIdGetDatum(), 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 
)
extern

Definition at line 4247 of file aclchk.c.

4248{
4249 Acl *result;
4250 Acl *glob_acl;
4251 Acl *schema_acl;
4252 Acl *def_acl;
4253 char defaclobjtype;
4254
4255 /*
4256 * Use NULL during bootstrap, since pg_default_acl probably isn't there
4257 * yet.
4258 */
4260 return NULL;
4261
4262 /* Check if object type is supported in pg_default_acl */
4263 switch (objtype)
4264 {
4265 case OBJECT_TABLE:
4266 defaclobjtype = DEFACLOBJ_RELATION;
4267 break;
4268
4269 case OBJECT_SEQUENCE:
4270 defaclobjtype = DEFACLOBJ_SEQUENCE;
4271 break;
4272
4273 case OBJECT_FUNCTION:
4274 defaclobjtype = DEFACLOBJ_FUNCTION;
4275 break;
4276
4277 case OBJECT_TYPE:
4278 defaclobjtype = DEFACLOBJ_TYPE;
4279 break;
4280
4281 case OBJECT_SCHEMA:
4282 defaclobjtype = DEFACLOBJ_NAMESPACE;
4283 break;
4284
4285 case OBJECT_LARGEOBJECT:
4286 defaclobjtype = DEFACLOBJ_LARGEOBJECT;
4287 break;
4288
4289 default:
4290 return NULL;
4291 }
4292
4293 /* Look up the relevant pg_default_acl entries */
4294 glob_acl = get_default_acl_internal(ownerId, InvalidOid, defaclobjtype);
4295 schema_acl = get_default_acl_internal(ownerId, nsp_oid, defaclobjtype);
4296
4297 /* Quick out if neither entry exists */
4298 if (glob_acl == NULL && schema_acl == NULL)
4299 return NULL;
4300
4301 /* We need to know the hard-wired default value, too */
4302 def_acl = acldefault(objtype, ownerId);
4303
4304 /* If there's no global entry, substitute the hard-wired default */
4305 if (glob_acl == NULL)
4306 glob_acl = def_acl;
4307
4308 /* Merge in any per-schema privileges */
4309 result = aclmerge(glob_acl, schema_acl, ownerId);
4310
4311 /*
4312 * For efficiency, we want to return NULL if the result equals default.
4313 * This requires sorting both arrays to get an accurate comparison.
4314 */
4315 aclitemsort(result);
4317 if (aclequal(result, def_acl))
4318 result = NULL;
4319
4320 return result;
4321}
Acl * aclmerge(const Acl *left_acl, const Acl *right_acl, Oid ownerId)
Definition acl.c:502
Acl * acldefault(ObjectType objtype, Oid ownerId)
Definition acl.c:804
bool aclequal(const Acl *left_acl, const Acl *right_acl)
Definition acl.c:560
void aclitemsort(Acl *acl)
Definition acl.c:546
static Acl * get_default_acl_internal(Oid roleId, Oid nsp_oid, char objtype)
Definition aclchk.c:4212
#define IsBootstrapProcessingMode()
Definition miscadmin.h:477

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

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

◆ has_bypassrls_privilege()

bool has_bypassrls_privilege ( Oid  roleid)
extern

Definition at line 4188 of file aclchk.c.

4189{
4190 bool result = false;
4192
4193 /* Superusers bypass all permission checking. */
4194 if (superuser_arg(roleid))
4195 return true;
4196
4199 {
4202 }
4203 return result;
4204}
bool rolbypassrls
Definition pg_authid.h:41
bool superuser_arg(Oid roleid)
Definition superuser.c:57

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

Referenced by AlterRole(), check_enable_rls(), CreateRole(), and RI_Initial_Check().

◆ has_createrole_privilege()

bool has_createrole_privilege ( Oid  roleid)
extern

Definition at line 4169 of file aclchk.c.

4170{
4171 bool result = false;
4173
4174 /* Superusers bypass all permission checking. */
4175 if (superuser_arg(roleid))
4176 return true;
4177
4180 {
4183 }
4184 return result;
4185}
bool rolcreaterole
Definition pg_authid.h:37

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

Referenced by check_object_ownership(), CreateRole(), and have_createrole_privilege().

◆ has_privs_of_role()

bool has_privs_of_role ( Oid  member,
Oid  role 
)
extern

Definition at line 5286 of file acl.c.

5287{
5288 /* Fast path for simple case */
5289 if (member == role)
5290 return true;
5291
5292 /* Superusers have every privilege, so are part of every role */
5293 if (superuser_arg(member))
5294 return true;
5295
5296 /*
5297 * Find all the roles that member has the privileges of, including
5298 * multi-level recursion, then see if target role is any one of them.
5299 */
5301 InvalidOid, NULL),
5302 role);
5303}
static List * roles_is_member_of(Oid roleid, enum RoleRecurseType type, Oid admin_of, Oid *admin_role)
Definition acl.c:5154
@ ROLERECURSE_PRIVS
Definition acl.c:77
bool list_member_oid(const List *list, Oid datum)
Definition list.c:722

References fb(), 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(), check_role_grantor(), ConfigOptionIsVisible(), convert_and_check_filename(), CreateSubscription(), DoCopy(), DropOwnedObjects(), ExecAlterDefaultPrivilegesStmt(), ExecCheckpoint(), file_fdw_validator(), GetConfigOptionValues(), InitPostgres(), object_ownercheck(), pg_class_aclmask_ext(), pg_get_multixact_stats(), pg_namespace_aclmask_ext(), pg_role_aclcheck(), pg_signal_backend(), pg_stat_get_wal_receiver(), pg_stat_get_wal_senders(), pg_stat_statements_internal(), pgrowlocks(), ReassignOwnedObjects(), ReindexMultipleTables(), shell_check_detail(), and TerminateOtherDBBackends().

◆ initialize_acl()

void initialize_acl ( void  )
extern

Definition at line 5041 of file acl.c.

5042{
5044 {
5048
5049 /*
5050 * In normal mode, set a callback on any syscache invalidation of rows
5051 * of pg_auth_members (for roles_is_member_of()) pg_database (for
5052 * roles_is_member_of())
5053 */
5056 (Datum) 0);
5059 (Datum) 0);
5062 (Datum) 0);
5063 }
5064}
static uint32 cached_db_hash
Definition acl.c:82
static void RoleMembershipCacheCallback(Datum arg, SysCacheIdentifier cacheid, uint32 hashvalue)
Definition acl.c:5071
Oid MyDatabaseId
Definition globals.c:94
void CacheRegisterSyscacheCallback(SysCacheIdentifier cacheid, SyscacheCallbackFunction func, Datum arg)
Definition inval.c:1816
uint64_t Datum
Definition postgres.h:70
#define GetSysCacheHashValue1(cacheId, key1)
Definition syscache.h:118

References cached_db_hash, CacheRegisterSyscacheCallback(), fb(), GetSysCacheHashValue1, IsBootstrapProcessingMode, MyDatabaseId, ObjectIdGetDatum(), and RoleMembershipCacheCallback().

Referenced by InitPostgres().

◆ is_admin_of_role()

bool is_admin_of_role ( Oid  member,
Oid  role 
)
extern

Definition at line 5416 of file acl.c.

5417{
5419
5420 if (superuser_arg(member))
5421 return true;
5422
5423 /* By policy, a role cannot have WITH ADMIN OPTION on itself. */
5424 if (member == role)
5425 return false;
5426
5428 return OidIsValid(admin_role);
5429}
@ ROLERECURSE_MEMBERS
Definition acl.c:76

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

Referenced by AlterRole(), AlterRoleSet(), check_object_ownership(), check_role_membership_authorization(), DropRole(), pg_role_aclcheck(), and RenameRole().

◆ is_member_of_role()

bool is_member_of_role ( Oid  member,
Oid  role 
)
extern

Definition at line 5366 of file acl.c.

5367{
5368 /* Fast path for simple case */
5369 if (member == role)
5370 return true;
5371
5372 /* Superusers have every privilege, so are part of every role */
5373 if (superuser_arg(member))
5374 return true;
5375
5376 /*
5377 * Find all the roles that member is a member of, including multi-level
5378 * recursion, then see if target role is any one of them.
5379 */
5381 InvalidOid, NULL),
5382 role);
5383}

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

Referenced by pg_role_aclcheck().

◆ is_member_of_role_nosuper()

bool is_member_of_role_nosuper ( Oid  member,
Oid  role 
)
extern

Definition at line 5394 of file acl.c.

5395{
5396 /* Fast path for simple case */
5397 if (member == role)
5398 return true;
5399
5400 /*
5401 * Find all the roles that member is a member of, including multi-level
5402 * recursion, then see if target role is any one of them.
5403 */
5405 InvalidOid, NULL),
5406 role);
5407}

References fb(), 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  )
extern

Definition at line 449 of file acl.c.

450{
451 return allocacl(0);
452}

References allocacl().

Referenced by SetDefaultACL().

◆ member_can_set_role()

bool member_can_set_role ( Oid  member,
Oid  role 
)
extern

Definition at line 5320 of file acl.c.

5321{
5322 /* Fast path for simple case */
5323 if (member == role)
5324 return true;
5325
5326 /* Superusers have every privilege, so can always SET ROLE */
5327 if (superuser_arg(member))
5328 return true;
5329
5330 /*
5331 * Find all the roles that member can access via SET ROLE, including
5332 * multi-level recursion, then see if target role is any one of them.
5333 */
5335 InvalidOid, NULL),
5336 role);
5337}
@ ROLERECURSE_SETROLE
Definition acl.c:78

References fb(), InvalidOid, list_member_oid(), ROLERECURSE_SETROLE, roles_is_member_of(), and superuser_arg().

Referenced by check_can_set_role(), check_role(), pg_role_aclcheck(), and SwitchToUntrustedUser().

◆ object_aclcheck()

AclResult object_aclcheck ( Oid  classid,
Oid  objectid,
Oid  roleid,
AclMode  mode 
)
extern

Definition at line 3836 of file aclchk.c.

3837{
3838 return object_aclcheck_ext(classid, objectid, roleid, mode, NULL);
3839}
AclResult object_aclcheck_ext(Oid classid, Oid objectid, Oid roleid, AclMode mode, bool *is_missing)
Definition aclchk.c:3846

References fb(), mode, and object_aclcheck_ext().

Referenced by AggregateCreate(), AlterExtensionNamespace(), AlterForeignServerOwner_internal(), AlterObjectNamespace_internal(), AlterObjectOwner_internal(), AlterObjectRename_internal(), AlterPublicationOwner_internal(), AlterSchemaOwner_internal(), AlterSubscriptionOwner_internal(), AlterTableMoveAll(), AlterTypeOwner(), ATExecChangeOwner(), ATPrepAlterColumnType(), ATPrepSetTableSpace(), BuildDescForRelation(), calculate_database_size(), calculate_tablespace_size(), call_pltcl_start_proc(), check_temp_tablespaces(), CheckFunctionValidatorAccess(), CheckMyDatabase(), compute_return_type(), CreateCast(), CreateConversionCommand(), createdb(), CreateForeignServer(), CreateForeignTable(), CreateFunction(), CreatePublication(), CreateSchemaCommand(), CreateStatistics(), CreateSubscription(), CreateTransform(), CreateTriggerFiringOn(), DefineAggregate(), DefineCollation(), DefineDomain(), DefineEnum(), DefineIndex(), DefineOpClass(), DefineOperator(), DefineOpFamily(), DefineRange(), DefineRelation(), DefineTSConfiguration(), DefineTSDictionary(), DefineType(), ExecBuildGroupingEqual(), ExecBuildParamSetEqual(), ExecInitAgg(), ExecInitExprRec(), ExecInitFunc(), ExecInitWindowAgg(), ExecReindex(), ExecuteCallStmt(), ExecuteDoStmt(), extension_is_trusted(), findRangeCanonicalFunction(), findRangeSubtypeDiffFunction(), get_connect_string(), get_other_operator(), HandleFunctionRequest(), has_database_privilege_id_name(), has_database_privilege_name(), has_database_privilege_name_name(), has_foreign_data_wrapper_privilege_id_name(), has_foreign_data_wrapper_privilege_name(), has_foreign_data_wrapper_privilege_name_name(), has_function_privilege_id_name(), has_function_privilege_name(), has_function_privilege_name_name(), has_language_privilege_id_name(), has_language_privilege_name(), has_language_privilege_name_name(), has_schema_privilege_id_name(), has_schema_privilege_name(), has_schema_privilege_name_name(), has_server_privilege_id_name(), has_server_privilege_name(), has_server_privilege_name_name(), has_tablespace_privilege_id_name(), has_tablespace_privilege_name(), has_tablespace_privilege_name_name(), has_type_privilege_id_name(), has_type_privilege_name(), has_type_privilege_name_name(), ImportForeignSchema(), init_sexpr(), initialize_peragg(), InitTempTableNamespace(), inline_function(), inline_function_in_from(), interpret_function_parameter_list(), lookup_agg_function(), LookupCreationNamespace(), LookupExplicitNamespace(), movedb(), PrepareTempTablespaces(), preprocessNamespacePath(), RangeVarCallbackForAlterRelation(), RangeVarGetAndCheckCreationNamespace(), ReindexMultipleInternal(), RenameSchema(), transformTableLikeClause(), user_mapping_ddl_aclcheck(), ValidateJoinEstimator(), and ValidateRestrictionEstimator().

◆ object_aclcheck_ext()

◆ object_ownercheck()

bool object_ownercheck ( Oid  classid,
Oid  objectid,
Oid  roleid 
)
extern

Definition at line 4090 of file aclchk.c.

4091{
4093 Oid ownerId;
4094
4095 /* Superusers bypass all permission checking. */
4096 if (superuser_arg(roleid))
4097 return true;
4098
4099 /* For large objects, the catalog to consult is pg_largeobject_metadata */
4100 if (classid == LargeObjectRelationId)
4102
4105 {
4106 /* we can get the object's tuple from the syscache */
4107 HeapTuple tuple;
4108
4110 if (!HeapTupleIsValid(tuple))
4111 elog(ERROR, "cache lookup failed for %s %u",
4113
4115 tuple,
4116 get_object_attnum_owner(classid)));
4117 ReleaseSysCache(tuple);
4118 }
4119 else
4120 {
4121 /* for catalogs without an appropriate syscache */
4122 Relation rel;
4123 ScanKeyData entry[1];
4124 SysScanDesc scan;
4125 HeapTuple tuple;
4126 bool isnull;
4127
4128 rel = table_open(classid, AccessShareLock);
4129
4130 ScanKeyInit(&entry[0],
4131 get_object_attnum_oid(classid),
4134
4135 scan = systable_beginscan(rel,
4136 get_object_oid_index(classid), true,
4137 NULL, 1, entry);
4138
4139 tuple = systable_getnext(scan);
4140 if (!HeapTupleIsValid(tuple))
4141 elog(ERROR, "could not find tuple for %s %u",
4143
4144 ownerId = DatumGetObjectId(heap_getattr(tuple,
4145 get_object_attnum_owner(classid),
4146 RelationGetDescr(rel),
4147 &isnull));
4148 Assert(!isnull);
4149
4150 systable_endscan(scan);
4152 }
4153
4154 return has_privs_of_role(roleid, ownerId);
4155}
void systable_endscan(SysScanDesc sysscan)
Definition genam.c:603
HeapTuple systable_getnext(SysScanDesc sysscan)
Definition genam.c:514
SysScanDesc systable_beginscan(Relation heapRelation, Oid indexId, bool indexOK, Snapshot snapshot, int nkeys, ScanKey key)
Definition genam.c:388
static Datum heap_getattr(HeapTuple tup, int attnum, TupleDesc tupleDesc, bool *isnull)
#define AccessShareLock
Definition lockdefs.h:36
AttrNumber get_object_attnum_owner(Oid class_id)
AttrNumber get_object_attnum_oid(Oid class_id)
const char * get_object_class_descr(Oid class_id)
Oid get_object_oid_index(Oid class_id)
SysCacheIdentifier get_object_catcache_oid(Oid class_id)
static Oid DatumGetObjectId(Datum X)
Definition postgres.h:252
#define RelationGetDescr(relation)
Definition rel.h:540
void ScanKeyInit(ScanKey entry, AttrNumber attributeNumber, StrategyNumber strategy, RegProcedure procedure, Datum argument)
Definition scankey.c:76
#define BTEqualStrategyNumber
Definition stratnum.h:31
Datum SysCacheGetAttrNotNull(SysCacheIdentifier cacheId, HeapTuple tup, AttrNumber attributeNumber)
Definition syscache.c:625
void table_close(Relation relation, LOCKMODE lockmode)
Definition table.c:126
Relation table_open(Oid relationId, LOCKMODE lockmode)
Definition table.c:40

References AccessShareLock, Assert, BTEqualStrategyNumber, DatumGetObjectId(), elog, ERROR, fb(), get_object_attnum_oid(), get_object_attnum_owner(), get_object_catcache_oid(), get_object_class_descr(), get_object_oid_index(), has_privs_of_role(), heap_getattr(), HeapTupleIsValid, ObjectIdGetDatum(), RelationGetDescr, ReleaseSysCache(), ScanKeyInit(), SearchSysCache1(), superuser_arg(), SysCacheGetAttrNotNull(), systable_beginscan(), systable_endscan(), systable_getnext(), table_close(), and table_open().

Referenced by AlterCollation(), AlterDatabase(), AlterDatabaseOwner(), AlterDatabaseRefreshColl(), AlterDatabaseSet(), AlterEventTrigger(), AlterEventTriggerOwner_internal(), AlterExtensionNamespace(), AlterForeignServer(), AlterForeignServerOwner_internal(), AlterFunction(), AlterOperator(), AlterOpFamilyAdd(), AlterPublication(), AlterPublicationOwner_internal(), AlterRoleSet(), AlterSchemaOwner_internal(), AlterStatistics(), AlterSubscription(), AlterSubscriptionOwner_internal(), AlterTableMoveAll(), AlterTableSpaceOptions(), AlterTSConfiguration(), AlterTSDictionary(), AlterType(), AlterTypeNamespace_oid(), AlterTypeOwner(), ATExecChangeOwner(), ATSimplePermissions(), be_lo_unlink(), brin_desummarize_range(), brin_summarize_range(), check_enable_rls(), check_object_ownership(), checkDomainOwner(), checkEnumOwner(), CreateCast(), createdb(), CreateProceduralLanguage(), CreateStatistics(), CreateTransform(), DefineOpClass(), DefineQueryRewrite(), DefineType(), dropdb(), DropSubscription(), DropTableSpace(), EnableDisableRule(), ExecAlterExtensionContentsStmt(), ExecAlterExtensionStmt(), ExecuteTruncateGuts(), gin_clean_pending_list(), heap_force_common(), MergeAttributes(), movedb(), OperatorCreate(), ProcedureCreate(), PublicationAddTables(), RangeVarCallbackForAlterRelation(), RangeVarCallbackForDropRelation(), RangeVarCallbackForPolicy(), RangeVarCallbackForRenameRule(), RangeVarCallbackForRenameTrigger(), RangeVarCallbackForStats(), RangeVarCallbackOwnsRelation(), RangeVarGetAndCheckCreationNamespace(), ReindexMultipleTables(), RemoveObjects(), renameatt_check(), RenameDatabase(), RenameSchema(), RenameTableSpace(), RenameType(), RI_Initial_Check(), user_mapping_ddl_aclcheck(), vacuum_is_permitted_for_relation(), and ValidateOperatorReference().

◆ pg_attribute_aclcheck()

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

Definition at line 3868 of file aclchk.c.

3870{
3872}
AclResult pg_attribute_aclcheck_ext(Oid table_oid, AttrNumber attnum, Oid roleid, AclMode mode, bool *is_missing)
Definition aclchk.c:3880

References attnum, fb(), mode, and pg_attribute_aclcheck_ext().

Referenced by all_rows_selectable(), BuildIndexValueDescription(), checkFkeyPermissions(), ExecBuildSlotPartitionKeyDescription(), ExecBuildSlotValueDescription(), ExecCheckOneRelPerms(), ExecCheckPermissionsModified(), and ri_ReportViolation().

◆ pg_attribute_aclcheck_all()

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

Definition at line 3910 of file aclchk.c.

3912{
3914}
AclResult pg_attribute_aclcheck_all_ext(Oid table_oid, Oid roleid, AclMode mode, AclMaskHow how, bool *is_missing)
Definition aclchk.c:3921

References fb(), mode, and pg_attribute_aclcheck_all_ext().

Referenced by all_rows_selectable(), ExecCheckOneRelPerms(), ExecCheckPermissionsModified(), has_any_column_privilege_id_name(), has_any_column_privilege_name(), and has_any_column_privilege_name_name().

◆ pg_attribute_aclcheck_all_ext()

AclResult pg_attribute_aclcheck_all_ext ( Oid  table_oid,
Oid  roleid,
AclMode  mode,
AclMaskHow  how,
bool is_missing 
)
extern

Definition at line 3921 of file aclchk.c.

3924{
3925 AclResult result;
3928 Oid ownerId;
3929 AttrNumber nattrs;
3931
3932 /*
3933 * Must fetch pg_class row to get owner ID and number of attributes.
3934 */
3937 {
3938 if (is_missing != NULL)
3939 {
3940 /* return "no privileges" instead of throwing an error */
3941 *is_missing = true;
3942 return ACLCHECK_NO_PRIV;
3943 }
3944 else
3945 ereport(ERROR,
3947 errmsg("relation with OID %u does not exist",
3948 table_oid)));
3949 }
3951
3952 ownerId = classForm->relowner;
3953 nattrs = classForm->relnatts;
3954
3956
3957 /*
3958 * Initialize result in case there are no non-dropped columns. We want to
3959 * report failure in such cases for either value of 'how'.
3960 */
3961 result = ACLCHECK_NO_PRIV;
3962
3963 for (curr_att = 1; curr_att <= nattrs; curr_att++)
3964 {
3967 bool isNull;
3968 Acl *acl;
3970
3974
3975 /*
3976 * Lookup failure probably indicates that the table was just dropped,
3977 * but we'll treat it the same as a dropped column rather than
3978 * throwing error.
3979 */
3981 continue;
3982
3983 /* ignore dropped columns */
3984 if (((Form_pg_attribute) GETSTRUCT(attTuple))->attisdropped)
3985 {
3987 continue;
3988 }
3989
3991 &isNull);
3992
3993 /*
3994 * Here we hard-wire knowledge that the default ACL for a column
3995 * grants no privileges, so that we can fall out quickly in the very
3996 * common case where attacl is null.
3997 */
3998 if (isNull)
3999 attmask = 0;
4000 else
4001 {
4002 /* detoast column's ACL if necessary */
4003 acl = DatumGetAclP(aclDatum);
4004
4005 attmask = aclmask(acl, roleid, ownerId, mode, ACLMASK_ANY);
4006
4007 /* if we have a detoasted copy, free it */
4008 if (acl != DatumGetPointer(aclDatum))
4009 pfree(acl);
4010 }
4011
4013
4014 if (attmask != 0)
4015 {
4016 result = ACLCHECK_OK;
4017 if (how == ACLMASK_ANY)
4018 break; /* succeed on any success */
4019 }
4020 else
4021 {
4022 result = ACLCHECK_NO_PRIV;
4023 if (how == ACLMASK_ALL)
4024 break; /* fail on any failure */
4025 }
4026 }
4027
4028 return result;
4029}
AclMode aclmask(const Acl *acl, Oid roleid, Oid ownerId, AclMode mask, AclMaskHow how)
Definition acl.c:1389
#define DatumGetAclP(X)
Definition acl.h:120
FormData_pg_attribute * Form_pg_attribute
FormData_pg_class * Form_pg_class
Definition pg_class.h:156
#define ERRCODE_UNDEFINED_TABLE
Definition pgbench.c:79
static Datum Int16GetDatum(int16 X)
Definition postgres.h:182
static Pointer DatumGetPointer(Datum X)
Definition postgres.h:342
HeapTuple SearchSysCache2(SysCacheIdentifier cacheId, Datum key1, Datum key2)
Definition syscache.c:230
Datum SysCacheGetAttr(SysCacheIdentifier cacheId, HeapTuple tup, AttrNumber attributeNumber, bool *isNull)
Definition syscache.c:595

References ACLCHECK_NO_PRIV, ACLCHECK_OK, aclmask(), ACLMASK_ALL, ACLMASK_ANY, DatumGetAclP, DatumGetPointer(), ereport, errcode(), ERRCODE_UNDEFINED_TABLE, errmsg(), ERROR, fb(), GETSTRUCT(), HeapTupleIsValid, Int16GetDatum(), mode, ObjectIdGetDatum(), pfree(), ReleaseSysCache(), SearchSysCache1(), SearchSysCache2(), and SysCacheGetAttr().

Referenced by has_any_column_privilege_id(), has_any_column_privilege_id_id(), has_any_column_privilege_name_id(), and pg_attribute_aclcheck_all().

◆ pg_attribute_aclcheck_ext()

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

Definition at line 3880 of file aclchk.c.

3882{
3884 ACLMASK_ANY, is_missing) != 0)
3885 return ACLCHECK_OK;
3886 else
3887 return ACLCHECK_NO_PRIV;
3888}
static AclMode pg_attribute_aclmask_ext(Oid table_oid, AttrNumber attnum, Oid roleid, AclMode mask, AclMaskHow how, bool *is_missing)
Definition aclchk.c:3158

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

Referenced by column_privilege_check(), and pg_attribute_aclcheck().

◆ pg_class_aclcheck()

◆ pg_class_aclcheck_ext()

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

◆ pg_class_aclmask()

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

Definition at line 3272 of file aclchk.c.

3274{
3275 return pg_class_aclmask_ext(table_oid, roleid, mask, how, NULL);
3276}

References fb(), and pg_class_aclmask_ext().

Referenced by ExecCheckOneRelPerms(), and pg_aclmask().

◆ pg_largeobject_aclcheck_snapshot()

AclResult pg_largeobject_aclcheck_snapshot ( Oid  lobj_oid,
Oid  roleid,
AclMode  mode,
Snapshot  snapshot 
)
extern

Definition at line 4076 of file aclchk.c.

4078{
4080 ACLMASK_ANY, snapshot) != 0)
4081 return ACLCHECK_OK;
4082 else
4083 return ACLCHECK_NO_PRIV;
4084}
static AclMode pg_largeobject_aclmask_snapshot(Oid lobj_oid, Oid roleid, AclMode mask, AclMaskHow how, Snapshot snapshot)
Definition aclchk.c:3535

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

Referenced by has_lo_priv_byid(), and inv_open().

◆ pg_parameter_aclcheck()

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

Definition at line 4064 of file aclchk.c.

4065{
4066 if (pg_parameter_aclmask(name, roleid, mode, ACLMASK_ANY) != 0)
4067 return ACLCHECK_OK;
4068 else
4069 return ACLCHECK_NO_PRIV;
4070}
static AclMode pg_parameter_aclmask(const char *name, Oid roleid, AclMode mask, AclMaskHow how)
Definition aclchk.c:3412

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

Referenced by AlterSystemSetConfigFile(), has_param_priv_byname(), set_config_with_handle(), and validate_option_array_item().

◆ recordDependencyOnNewAcl()

void recordDependencyOnNewAcl ( Oid  classId,
Oid  objectId,
int32  objsubId,
Oid  ownerId,
Acl acl 
)
extern

Definition at line 4327 of file aclchk.c.

4329{
4330 int nmembers;
4331 Oid *members;
4332
4333 /* Nothing to do if ACL is defaulted */
4334 if (acl == NULL)
4335 return;
4336
4337 /* Extract roles mentioned in ACL */
4338 nmembers = aclmembers(acl, &members);
4339
4340 /* Update the shared dependency ACL info */
4341 updateAclDependencies(classId, objectId, objsubId,
4342 ownerId,
4343 0, NULL,
4344 nmembers, members);
4345}
int aclmembers(const Acl *acl, Oid **roleids)
Definition acl.c:1541
void updateAclDependencies(Oid classId, Oid objectId, int32 objsubId, Oid ownerId, int noldmembers, Oid *oldmembers, int nnewmembers, Oid *newmembers)

References aclmembers(), fb(), and updateAclDependencies().

Referenced by GenerateTypeDependencies(), heap_create_with_catalog(), LargeObjectCreate(), NamespaceCreate(), and ProcedureCreate().

◆ recordExtObjInitPriv()

void recordExtObjInitPriv ( Oid  objoid,
Oid  classoid 
)
extern

Definition at line 4354 of file aclchk.c.

4355{
4356 /*
4357 * pg_class / pg_attribute
4358 *
4359 * If this is a relation then we need to see if there are any sub-objects
4360 * (eg: columns) for it and, if so, be sure to call
4361 * recordExtensionInitPrivWorker() for each one.
4362 */
4363 if (classoid == RelationRelationId)
4364 {
4367 bool isNull;
4368 HeapTuple tuple;
4369
4370 tuple = SearchSysCache1(RELOID, ObjectIdGetDatum(objoid));
4371 if (!HeapTupleIsValid(tuple))
4372 elog(ERROR, "cache lookup failed for relation %u", objoid);
4374
4375 /*
4376 * Indexes don't have permissions, neither do the pg_class rows for
4377 * composite types. (These cases are unreachable given the
4378 * restrictions in ALTER EXTENSION ADD, but let's check anyway.)
4379 */
4380 if (pg_class_tuple->relkind == RELKIND_INDEX ||
4383 {
4384 ReleaseSysCache(tuple);
4385 return;
4386 }
4387
4388 /*
4389 * If this isn't a sequence then it's possibly going to have
4390 * column-level ACLs associated with it.
4391 */
4392 if (pg_class_tuple->relkind != RELKIND_SEQUENCE)
4393 {
4395 AttrNumber nattrs = pg_class_tuple->relnatts;
4396
4397 for (curr_att = 1; curr_att <= nattrs; curr_att++)
4398 {
4401
4403 ObjectIdGetDatum(objoid),
4405
4407 continue;
4408
4409 /* ignore dropped columns */
4410 if (((Form_pg_attribute) GETSTRUCT(attTuple))->attisdropped)
4411 {
4413 continue;
4414 }
4415
4418 &isNull);
4419
4420 /* no need to do anything for a NULL ACL */
4421 if (isNull)
4422 {
4424 continue;
4425 }
4426
4427 recordExtensionInitPrivWorker(objoid, classoid, curr_att,
4429
4431 }
4432 }
4433
4435 &isNull);
4436
4437 /* Add the record, if any, for the top-level object */
4438 if (!isNull)
4439 recordExtensionInitPrivWorker(objoid, classoid, 0,
4441
4442 ReleaseSysCache(tuple);
4443 }
4444 else if (classoid == LargeObjectRelationId)
4445 {
4446 /* For large objects, we must consult pg_largeobject_metadata */
4448 bool isNull;
4449 HeapTuple tuple;
4450 ScanKeyData entry[1];
4451 SysScanDesc scan;
4452 Relation relation;
4453
4454 /*
4455 * Note: this is dead code, given that we don't allow large objects to
4456 * be made extension members. But it seems worth carrying in case
4457 * some future caller of this function has need for it.
4458 */
4460
4461 /* There's no syscache for pg_largeobject_metadata */
4462 ScanKeyInit(&entry[0],
4465 ObjectIdGetDatum(objoid));
4466
4467 scan = systable_beginscan(relation,
4469 NULL, 1, entry);
4470
4471 tuple = systable_getnext(scan);
4472 if (!HeapTupleIsValid(tuple))
4473 elog(ERROR, "could not find tuple for large object %u", objoid);
4474
4475 aclDatum = heap_getattr(tuple,
4477 RelationGetDescr(relation), &isNull);
4478
4479 /* Add the record, if any, for the top-level object */
4480 if (!isNull)
4481 recordExtensionInitPrivWorker(objoid, classoid, 0,
4483
4484 systable_endscan(scan);
4485 }
4486 /* This will error on unsupported classoid. */
4487 else if (get_object_attnum_acl(classoid) != InvalidAttrNumber)
4488 {
4491 bool isNull;
4492 HeapTuple tuple;
4493
4494 cacheid = get_object_catcache_oid(classoid);
4495 tuple = SearchSysCache1(cacheid, ObjectIdGetDatum(objoid));
4496 if (!HeapTupleIsValid(tuple))
4497 elog(ERROR, "cache lookup failed for %s %u",
4498 get_object_class_descr(classoid), objoid);
4499
4501 get_object_attnum_acl(classoid),
4502 &isNull);
4503
4504 /* Add the record, if any, for the top-level object */
4505 if (!isNull)
4506 recordExtensionInitPrivWorker(objoid, classoid, 0,
4508
4509 ReleaseSysCache(tuple);
4510 }
4511}
static void recordExtensionInitPrivWorker(Oid objoid, Oid classoid, int objsubid, Acl *new_acl)
Definition aclchk.c:4630
#define InvalidAttrNumber
Definition attnum.h:23
#define RowExclusiveLock
Definition lockdefs.h:38
AttrNumber get_object_attnum_acl(Oid class_id)

References BTEqualStrategyNumber, DatumGetAclP, elog, ERROR, fb(), get_object_attnum_acl(), get_object_catcache_oid(), get_object_class_descr(), GETSTRUCT(), heap_getattr(), HeapTupleIsValid, Int16GetDatum(), InvalidAttrNumber, ObjectIdGetDatum(), recordExtensionInitPrivWorker(), RelationGetDescr, ReleaseSysCache(), RowExclusiveLock, ScanKeyInit(), SearchSysCache1(), SearchSysCache2(), SysCacheGetAttr(), systable_beginscan(), systable_endscan(), systable_getnext(), and table_open().

Referenced by ExecAlterExtensionContentsRecurse().

◆ removeExtObjInitPriv()

void removeExtObjInitPriv ( Oid  objoid,
Oid  classoid 
)
extern

Definition at line 4518 of file aclchk.c.

4519{
4520 /*
4521 * If this is a relation then we need to see if there are any sub-objects
4522 * (eg: columns) for it and, if so, be sure to call
4523 * recordExtensionInitPrivWorker() for each one.
4524 */
4525 if (classoid == RelationRelationId)
4526 {
4528 HeapTuple tuple;
4529
4530 tuple = SearchSysCache1(RELOID, ObjectIdGetDatum(objoid));
4531 if (!HeapTupleIsValid(tuple))
4532 elog(ERROR, "cache lookup failed for relation %u", objoid);
4534
4535 /*
4536 * Indexes don't have permissions, neither do the pg_class rows for
4537 * composite types. (These cases are unreachable given the
4538 * restrictions in ALTER EXTENSION DROP, but let's check anyway.)
4539 */
4540 if (pg_class_tuple->relkind == RELKIND_INDEX ||
4543 {
4544 ReleaseSysCache(tuple);
4545 return;
4546 }
4547
4548 /*
4549 * If this isn't a sequence then it's possibly going to have
4550 * column-level ACLs associated with it.
4551 */
4552 if (pg_class_tuple->relkind != RELKIND_SEQUENCE)
4553 {
4555 AttrNumber nattrs = pg_class_tuple->relnatts;
4556
4557 for (curr_att = 1; curr_att <= nattrs; curr_att++)
4558 {
4560
4562 ObjectIdGetDatum(objoid),
4564
4566 continue;
4567
4568 /* when removing, remove all entries, even dropped columns */
4569
4570 recordExtensionInitPrivWorker(objoid, classoid, curr_att, NULL);
4571
4573 }
4574 }
4575
4576 ReleaseSysCache(tuple);
4577 }
4578
4579 /* Remove the record, if any, for the top-level object */
4580 recordExtensionInitPrivWorker(objoid, classoid, 0, NULL);
4581}

References elog, ERROR, fb(), GETSTRUCT(), HeapTupleIsValid, Int16GetDatum(), ObjectIdGetDatum(), recordExtensionInitPrivWorker(), ReleaseSysCache(), SearchSysCache1(), and SearchSysCache2().

Referenced by ExecAlterExtensionContentsRecurse().

◆ RemoveRoleFromInitPriv()

void RemoveRoleFromInitPriv ( Oid  roleid,
Oid  classid,
Oid  objid,
int32  objsubid 
)
extern

Definition at line 4867 of file aclchk.c.

4868{
4869 Relation rel;
4870 ScanKeyData key[3];
4871 SysScanDesc scan;
4872 HeapTuple oldtuple;
4875 Oid ownerId;
4877 bool isNull;
4878 Acl *old_acl;
4879 Acl *new_acl;
4880 HeapTuple newtuple;
4881 int noldmembers;
4882 int nnewmembers;
4883 Oid *oldmembers;
4884 Oid *newmembers;
4885
4886 /* Search for existing pg_init_privs entry for the target object. */
4888
4889 ScanKeyInit(&key[0],
4892 ObjectIdGetDatum(objid));
4893 ScanKeyInit(&key[1],
4896 ObjectIdGetDatum(classid));
4897 ScanKeyInit(&key[2],
4900 Int32GetDatum(objsubid));
4901
4902 scan = systable_beginscan(rel, InitPrivsObjIndexId, true,
4903 NULL, 3, key);
4904
4905 /* There should exist only one entry or none. */
4906 oldtuple = systable_getnext(scan);
4907
4908 if (!HeapTupleIsValid(oldtuple))
4909 {
4910 /*
4911 * Hmm, why are we here if there's no entry? But pack up and go away
4912 * quietly.
4913 */
4914 systable_endscan(scan);
4916 return;
4917 }
4918
4919 /* Get a writable copy of the existing ACL. */
4921 RelationGetDescr(rel), &isNull);
4922 Assert(!isNull);
4924
4925 /*
4926 * We need the members of both old and new ACLs so we can correct the
4927 * shared dependency information. Collect data before
4928 * merge_acl_with_grant throws away old_acl.
4929 */
4931
4932 /* Must find out the owner's OID the hard way. */
4936 elog(ERROR, "cache lookup failed for %s %u",
4937 get_object_class_descr(classid), objid);
4938
4940 objtuple,
4941 get_object_attnum_owner(classid)));
4943
4944 /*
4945 * Generate new ACL. Grantor of rights is always the same as the owner.
4946 */
4947 if (old_acl != NULL)
4949 false, /* is_grant */
4950 false, /* grant_option */
4952 list_make1_oid(roleid),
4954 ownerId,
4955 ownerId);
4956 else
4957 new_acl = NULL; /* this case shouldn't happen, probably */
4958
4959 /* If we end with an empty ACL, delete the pg_init_privs entry. */
4960 if (new_acl == NULL || ACL_NUM(new_acl) == 0)
4961 {
4962 CatalogTupleDelete(rel, &oldtuple->t_self);
4963 }
4964 else
4965 {
4967 bool nulls[Natts_pg_init_privs] = {0};
4968 bool replaces[Natts_pg_init_privs] = {0};
4969
4970 /* Update existing entry. */
4973
4974 newtuple = heap_modify_tuple(oldtuple, RelationGetDescr(rel),
4975 values, nulls, replaces);
4976 CatalogTupleUpdate(rel, &newtuple->t_self, newtuple);
4977 }
4978
4979 /*
4980 * Update the shared dependency ACL info.
4981 */
4983
4984 updateInitAclDependencies(classid, objid, objsubid,
4987
4988 systable_endscan(scan);
4989
4990 /* prevent error when processing objects multiple times */
4992
4994}
#define ACLITEM_ALL_PRIV_BITS
Definition acl.h:87
#define DatumGetAclPCopy(X)
Definition acl.h:121
static Acl * merge_acl_with_grant(Acl *old_acl, bool is_grant, bool grant_option, DropBehavior behavior, List *grantees, AclMode privileges, Oid grantorId, Oid ownerId)
Definition aclchk.c:181
static Datum values[MAXATTR]
Definition bootstrap.c:155
HeapTuple heap_modify_tuple(HeapTuple tuple, TupleDesc tupleDesc, const Datum *replValues, const bool *replIsnull, const bool *doReplace)
Definition heaptuple.c:1210
void CatalogTupleUpdate(Relation heapRel, const ItemPointerData *otid, HeapTuple tup)
Definition indexing.c:313
void CatalogTupleDelete(Relation heapRel, const ItemPointerData *tid)
Definition indexing.c:365
#define list_make1_oid(x1)
Definition pg_list.h:242
void updateInitAclDependencies(Oid classId, Oid objectId, int32 objsubId, int noldmembers, Oid *oldmembers, int nnewmembers, Oid *newmembers)
static Datum PointerGetDatum(const void *X)
Definition postgres.h:352
static Datum Int32GetDatum(int32 X)
Definition postgres.h:222
ItemPointerData t_self
Definition htup.h:65
void CommandCounterIncrement(void)
Definition xact.c:1101

References ACL_NUM, ACLITEM_ALL_PRIV_BITS, aclmembers(), Assert, BTEqualStrategyNumber, CatalogTupleDelete(), CatalogTupleUpdate(), CommandCounterIncrement(), DatumGetAclPCopy, DatumGetObjectId(), DROP_RESTRICT, elog, ERROR, fb(), get_object_attnum_owner(), get_object_catcache_oid(), get_object_class_descr(), heap_getattr(), heap_modify_tuple(), HeapTupleIsValid, Int32GetDatum(), list_make1_oid, merge_acl_with_grant(), ObjectIdGetDatum(), PointerGetDatum(), RelationGetDescr, ReleaseSysCache(), RowExclusiveLock, ScanKeyInit(), SearchSysCache1(), SysCacheGetAttrNotNull(), systable_beginscan(), systable_endscan(), systable_getnext(), HeapTupleData::t_self, table_close(), table_open(), updateInitAclDependencies(), and values.

Referenced by shdepDropOwned().

◆ RemoveRoleFromObjectACL()

void RemoveRoleFromObjectACL ( Oid  roleid,
Oid  classid,
Oid  objid 
)
extern

Definition at line 1422 of file aclchk.c.

1423{
1424 if (classid == DefaultAclRelationId)
1425 {
1428 Relation rel;
1429 ScanKeyData skey[1];
1430 SysScanDesc scan;
1431 HeapTuple tuple;
1432
1433 /* first fetch info needed by SetDefaultACL */
1435
1436 ScanKeyInit(&skey[0],
1439 ObjectIdGetDatum(objid));
1440
1441 scan = systable_beginscan(rel, DefaultAclOidIndexId, true,
1442 NULL, 1, skey);
1443
1444 tuple = systable_getnext(scan);
1445
1446 if (!HeapTupleIsValid(tuple))
1447 elog(ERROR, "could not find tuple for default ACL %u", objid);
1448
1450
1451 iacls.roleid = pg_default_acl_tuple->defaclrole;
1452 iacls.nspid = pg_default_acl_tuple->defaclnamespace;
1453
1454 switch (pg_default_acl_tuple->defaclobjtype)
1455 {
1456 case DEFACLOBJ_RELATION:
1457 iacls.objtype = OBJECT_TABLE;
1458 break;
1459 case DEFACLOBJ_SEQUENCE:
1460 iacls.objtype = OBJECT_SEQUENCE;
1461 break;
1462 case DEFACLOBJ_FUNCTION:
1463 iacls.objtype = OBJECT_FUNCTION;
1464 break;
1465 case DEFACLOBJ_TYPE:
1466 iacls.objtype = OBJECT_TYPE;
1467 break;
1469 iacls.objtype = OBJECT_SCHEMA;
1470 break;
1472 iacls.objtype = OBJECT_LARGEOBJECT;
1473 break;
1474 default:
1475 /* Shouldn't get here */
1476 elog(ERROR, "unexpected default ACL type: %d",
1477 (int) pg_default_acl_tuple->defaclobjtype);
1478 break;
1479 }
1480
1481 systable_endscan(scan);
1483
1484 iacls.is_grant = false;
1485 iacls.all_privs = true;
1486 iacls.privileges = ACL_NO_RIGHTS;
1487 iacls.grantees = list_make1_oid(roleid);
1488 iacls.grant_option = false;
1489 iacls.behavior = DROP_CASCADE;
1490
1491 /* Do it */
1493 }
1494 else
1495 {
1496 InternalGrant istmt;
1497
1498 switch (classid)
1499 {
1500 case RelationRelationId:
1501 /* it's OK to use TABLE for a sequence */
1502 istmt.objtype = OBJECT_TABLE;
1503 break;
1504 case DatabaseRelationId:
1505 istmt.objtype = OBJECT_DATABASE;
1506 break;
1507 case TypeRelationId:
1508 istmt.objtype = OBJECT_TYPE;
1509 break;
1511 istmt.objtype = OBJECT_ROUTINE;
1512 break;
1513 case LanguageRelationId:
1514 istmt.objtype = OBJECT_LANGUAGE;
1515 break;
1518 break;
1520 istmt.objtype = OBJECT_SCHEMA;
1521 break;
1523 istmt.objtype = OBJECT_TABLESPACE;
1524 break;
1527 break;
1529 istmt.objtype = OBJECT_FDW;
1530 break;
1533 break;
1534 default:
1535 elog(ERROR, "unexpected object class %u", classid);
1536 break;
1537 }
1538 istmt.is_grant = false;
1539 istmt.objects = list_make1_oid(objid);
1540 istmt.all_privs = true;
1541 istmt.privileges = ACL_NO_RIGHTS;
1542 istmt.col_privs = NIL;
1543 istmt.grantees = list_make1_oid(roleid);
1544 istmt.grant_option = false;
1545 istmt.behavior = DROP_CASCADE;
1546
1547 ExecGrantStmt_oids(&istmt);
1548 }
1549}
static void SetDefaultACL(InternalDefaultACL *iacls)
Definition aclchk.c:1147
@ DROP_CASCADE
FormData_pg_default_acl * Form_pg_default_acl

References AccessShareLock, ACL_NO_RIGHTS, InternalGrant::all_privs, InternalGrant::behavior, BTEqualStrategyNumber, InternalGrant::col_privs, DROP_CASCADE, elog, ERROR, ExecGrantStmt_oids(), fb(), GETSTRUCT(), InternalGrant::grant_option, InternalGrant::grantees, HeapTupleIsValid, InternalGrant::is_grant, list_make1_oid, NIL, OBJECT_DATABASE, OBJECT_FDW, OBJECT_FOREIGN_SERVER, OBJECT_FUNCTION, OBJECT_LANGUAGE, OBJECT_LARGEOBJECT, OBJECT_PARAMETER_ACL, OBJECT_ROUTINE, OBJECT_SCHEMA, OBJECT_SEQUENCE, OBJECT_TABLE, OBJECT_TABLESPACE, OBJECT_TYPE, ObjectIdGetDatum(), InternalGrant::objects, InternalGrant::objtype, InternalGrant::privileges, ScanKeyInit(), SetDefaultACL(), systable_beginscan(), systable_endscan(), systable_getnext(), table_close(), and table_open().

Referenced by shdepDropOwned().

◆ ReplaceRoleInInitPriv()

void ReplaceRoleInInitPriv ( Oid  oldroleid,
Oid  newroleid,
Oid  classid,
Oid  objid,
int32  objsubid 
)
extern

Definition at line 4758 of file aclchk.c.

4760{
4761 Relation rel;
4762 ScanKeyData key[3];
4763 SysScanDesc scan;
4764 HeapTuple oldtuple;
4766 bool isNull;
4767 Acl *old_acl;
4768 Acl *new_acl;
4769 HeapTuple newtuple;
4770 int noldmembers;
4771 int nnewmembers;
4772 Oid *oldmembers;
4773 Oid *newmembers;
4774
4775 /* Search for existing pg_init_privs entry for the target object. */
4777
4778 ScanKeyInit(&key[0],
4781 ObjectIdGetDatum(objid));
4782 ScanKeyInit(&key[1],
4785 ObjectIdGetDatum(classid));
4786 ScanKeyInit(&key[2],
4789 Int32GetDatum(objsubid));
4790
4791 scan = systable_beginscan(rel, InitPrivsObjIndexId, true,
4792 NULL, 3, key);
4793
4794 /* There should exist only one entry or none. */
4795 oldtuple = systable_getnext(scan);
4796
4797 if (!HeapTupleIsValid(oldtuple))
4798 {
4799 /*
4800 * Hmm, why are we here if there's no entry? But pack up and go away
4801 * quietly.
4802 */
4803 systable_endscan(scan);
4805 return;
4806 }
4807
4808 /* Get a writable copy of the existing ACL. */
4810 RelationGetDescr(rel), &isNull);
4811 Assert(!isNull);
4813
4814 /*
4815 * Generate new ACL. This usage of aclnewowner is a bit off-label when
4816 * oldroleid isn't the owner; but it does the job fine.
4817 */
4819
4820 /*
4821 * If we end with an empty ACL, delete the pg_init_privs entry. (That
4822 * probably can't happen here, but we may as well cover the case.)
4823 */
4824 if (new_acl == NULL || ACL_NUM(new_acl) == 0)
4825 {
4826 CatalogTupleDelete(rel, &oldtuple->t_self);
4827 }
4828 else
4829 {
4831 bool nulls[Natts_pg_init_privs] = {0};
4832 bool replaces[Natts_pg_init_privs] = {0};
4833
4834 /* Update existing entry. */
4837
4838 newtuple = heap_modify_tuple(oldtuple, RelationGetDescr(rel),
4839 values, nulls, replaces);
4840 CatalogTupleUpdate(rel, &newtuple->t_self, newtuple);
4841 }
4842
4843 /*
4844 * Update the shared dependency ACL info.
4845 */
4848
4849 updateInitAclDependencies(classid, objid, objsubid,
4852
4853 systable_endscan(scan);
4854
4855 /* prevent error when processing objects multiple times */
4857
4859}
Acl * aclnewowner(const Acl *old_acl, Oid oldOwnerId, Oid newOwnerId)
Definition acl.c:1120

References ACL_NUM, aclmembers(), aclnewowner(), Assert, BTEqualStrategyNumber, CatalogTupleDelete(), CatalogTupleUpdate(), CommandCounterIncrement(), DatumGetAclPCopy, fb(), heap_getattr(), heap_modify_tuple(), HeapTupleIsValid, Int32GetDatum(), ObjectIdGetDatum(), PointerGetDatum(), RelationGetDescr, RowExclusiveLock, ScanKeyInit(), systable_beginscan(), systable_endscan(), systable_getnext(), HeapTupleData::t_self, table_close(), table_open(), updateInitAclDependencies(), and values.

Referenced by shdepReassignOwned_InitAcl().

◆ select_best_admin()

Oid select_best_admin ( Oid  member,
Oid  role 
)
extern

Definition at line 5441 of file acl.c.

5442{
5444
5445 /* By policy, a role cannot have WITH ADMIN OPTION on itself. */
5446 if (member == role)
5447 return InvalidOid;
5448
5450 return admin_role;
5451}

References fb(), InvalidOid, ROLERECURSE_PRIVS, and roles_is_member_of().

Referenced by check_role_grantor().

◆ select_best_grantor()

void select_best_grantor ( Oid  roleId,
AclMode  privileges,
const Acl acl,
Oid  ownerId,
Oid grantorId,
AclMode grantOptions 
)
extern

Definition at line 5478 of file acl.c.

5481{
5484 int nrights;
5485 ListCell *l;
5486
5487 /*
5488 * The object owner is always treated as having all grant options, so if
5489 * roleId is the owner it's easy. Also, if roleId is a superuser it's
5490 * easy: superusers are implicitly members of every role, so they act as
5491 * the object owner.
5492 */
5493 if (roleId == ownerId || superuser_arg(roleId))
5494 {
5495 *grantorId = ownerId;
5497 return;
5498 }
5499
5500 /*
5501 * Otherwise we have to do a careful search to see if roleId has the
5502 * privileges of any suitable role. Note: we can hang onto the result of
5503 * roles_is_member_of() throughout this loop, because aclmask_direct()
5504 * doesn't query any role memberships.
5505 */
5507 InvalidOid, NULL);
5508
5509 /* initialize candidate result as default */
5510 *grantorId = roleId;
5512 nrights = 0;
5513
5514 foreach(l, roles_list)
5515 {
5518
5519 otherprivs = aclmask_direct(acl, otherrole, ownerId,
5522 {
5523 /* Found a suitable grantor */
5526 return;
5527 }
5528
5529 /*
5530 * If it has just some of the needed privileges, remember best
5531 * candidate.
5532 */
5534 {
5536
5537 if (nnewrights > nrights)
5538 {
5542 }
5543 }
5544 }
5545}
static AclMode aclmask_direct(const Acl *acl, Oid roleid, Oid ownerId, AclMode mask, AclMaskHow how)
Definition acl.c:1478
#define ACL_GRANT_OPTION_FOR(privs)
Definition acl.h:70
static int pg_popcount64(uint64 word)
#define lfirst_oid(lc)
Definition pg_list.h:174

References ACL_GRANT_OPTION_FOR, ACL_NO_RIGHTS, ACLMASK_ALL, aclmask_direct(), fb(), InvalidOid, lfirst_oid, pg_popcount64(), ROLERECURSE_PRIVS, roles_is_member_of(), and superuser_arg().

Referenced by ExecGrant_Attribute(), ExecGrant_common(), ExecGrant_Largeobject(), ExecGrant_Parameter(), and ExecGrant_Relation().