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:5040
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:5414
Acl * aclconcat(const Acl *left_acl, const Acl *right_acl)
Definition acl.c:477
Acl * aclmerge(const Acl *left_acl, const Acl *right_acl, Oid ownerId)
Definition acl.c:501
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:5439
Acl * acldefault(ObjectType objtype, Oid ownerId)
Definition acl.c:803
Oid get_role_oid_or_public(const char *rolname)
Definition acl.c:5570
void ExecAlterDefaultPrivilegesStmt(ParseState *pstate, AlterDefaultPrivilegesStmt *stmt)
Definition aclchk.c:916
bool aclequal(const Acl *left_acl, const Acl *right_acl)
Definition acl.c:559
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:992
bool is_member_of_role(Oid member, Oid role)
Definition acl.c:5364
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:5476
bool is_member_of_role_nosuper(Oid member, Oid role)
Definition acl.c:5392
bool has_privs_of_role(Oid member, Oid role)
Definition acl.c:5284
Acl * make_empty_acl(void)
Definition acl.c:448
void recordExtObjInitPriv(Oid objoid, Oid classoid)
Definition aclchk.c:4354
int aclmembers(const Acl *acl, Oid **roleids)
Definition acl.c:1540
Acl * aclnewowner(const Acl *old_acl, Oid oldOwnerId, Oid newOwnerId)
Definition acl.c:1119
bool member_can_set_role(Oid member, Oid role)
Definition acl.c:5318
Acl * aclcopy(const Acl *orig_acl)
Definition acl.c:457
void aclitemsort(Acl *acl)
Definition acl.c:545
AclMode aclmask(const Acl *acl, Oid roleid, Oid ownerId, AclMode mask, AclMaskHow how)
Definition acl.c:1388
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:5552
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:5671
void check_can_set_role(Oid member, Oid role)
Definition acl.c:5341
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:5693
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:5586
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:5625
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:1185
int errcode(int sqlerrcode)
Definition elog.c:863
int errmsg(const char *fmt,...)
Definition elog.c:1080
#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 477 of file acl.c.

478{
480
482
485 ACL_NUM(left_acl) * sizeof(AclItem));
486
489 ACL_NUM(right_acl) * sizeof(AclItem));
490
491 return result_acl;
492}
static Acl * allocacl(int n)
Definition acl.c:426
#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 457 of file acl.c.

458{
460
462
465 ACL_NUM(orig_acl) * sizeof(AclItem));
466
467 return result_acl;
468}

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 803 of file acl.c.

804{
807 int nacl;
808 Acl *acl;
809 AclItem *aip;
810
811 switch (objtype)
812 {
813 case OBJECT_COLUMN:
814 /* by default, columns have no extra privileges */
817 break;
818 case OBJECT_TABLE:
821 break;
822 case OBJECT_SEQUENCE:
825 break;
826 case OBJECT_DATABASE:
827 /* for backwards compatibility, grant some rights by default */
830 break;
831 case OBJECT_FUNCTION:
832 /* Grant EXECUTE by default, for now */
835 break;
836 case OBJECT_LANGUAGE:
837 /* Grant USAGE by default, for now */
840 break;
844 break;
845 case OBJECT_SCHEMA:
848 break;
852 break;
853 case OBJECT_FDW:
856 break;
860 break;
861 case OBJECT_DOMAIN:
862 case OBJECT_TYPE:
865 break;
869 break;
870 default:
871 elog(ERROR, "unrecognized object type: %d", (int) objtype);
872 world_default = ACL_NO_RIGHTS; /* keep compiler quiet */
874 break;
875 }
876
877 nacl = 0;
879 nacl++;
881 nacl++;
882
883 acl = allocacl(nacl);
884 aip = ACL_DAT(acl);
885
887 {
888 aip->ai_grantee = ACL_ID_PUBLIC;
889 aip->ai_grantor = ownerId;
891 aip++;
892 }
893
894 /*
895 * Note that the owner's entry shows all ordinary privileges but no grant
896 * options. This is because his grant options come "from the system" and
897 * not from his own efforts. (The SQL spec says that the owner's rights
898 * come from a "_SYSTEM" authid.) However, we do consider that the
899 * owner's ordinary privileges are self-granted; this lets him revoke
900 * them. We implement the owner's grant options without any explicit
901 * "_SYSTEM"-like ACL entry, by internally special-casing the owner
902 * wherever we are testing grant options.
903 */
905 {
906 aip->ai_grantee = ownerId;
907 aip->ai_grantor = ownerId;
909 }
910
911 return acl;
912}
#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 559 of file acl.c.

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

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 545 of file acl.c.

546{
547 if (acl != NULL && ACL_NUM(acl) > 1)
548 qsort(ACL_DAT(acl), ACL_NUM(acl), sizeof(AclItem), aclitemComparator);
549}
static int aclitemComparator(const void *arg1, const void *arg2)
Definition acl.c:724
#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 1388 of file acl.c.

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

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

502{
504 AclItem *aip;
505 int i,
506 num;
507
508 /* Check for cases where one or both are empty/null */
509 if (left_acl == NULL || ACL_NUM(left_acl) == 0)
510 {
511 if (right_acl == NULL || ACL_NUM(right_acl) == 0)
512 return NULL;
513 else
514 return aclcopy(right_acl);
515 }
516 else
517 {
518 if (right_acl == NULL || ACL_NUM(right_acl) == 0)
519 return aclcopy(left_acl);
520 }
521
522 /* Merge them the hard way, one item at a time */
524
526 num = ACL_NUM(right_acl);
527
528 for (i = 0; i < num; i++, aip++)
529 {
530 Acl *tmp_acl;
531
533 ownerId, DROP_RESTRICT);
536 }
537
538 return result_acl;
539}
Acl * aclupdate(const Acl *old_acl, const AclItem *mod_aip, int modechg, Oid ownerId, DropBehavior behavior)
Definition acl.c:992
Acl * aclcopy(const Acl *orig_acl)
Definition acl.c:457
#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 1119 of file acl.c.

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

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

5342{
5343 if (!member_can_set_role(member, role))
5344 ereport(ERROR,
5346 errmsg("must be able to SET ROLE \"%s\"",
5347 GetUserNameFromId(role, false))));
5348}
bool member_can_set_role(Oid member, Oid role)
Definition acl.c:5318
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 5693 of file acl.c.

5694{
5695 if (!role)
5696 return;
5697
5698 if (role->roletype != ROLESPEC_CSTRING)
5699 return;
5700
5701 if (IsReservedName(role->rolename))
5702 {
5703 if (detail_msg)
5704 ereport(ERROR,
5706 errmsg("role name \"%s\" is reserved",
5707 role->rolename),
5709 else
5710 ereport(ERROR,
5712 errmsg("role name \"%s\" is reserved",
5713 role->rolename)));
5714 }
5715}
bool IsReservedName(const char *name)
Definition catalog.c:278
int errdetail_internal(const char *fmt,...)
Definition elog.c:1243
@ 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:5586
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 5552 of file acl.c.

5553{
5554 Oid oid;
5555
5558 if (!OidIsValid(oid) && !missing_ok)
5559 ereport(ERROR,
5561 errmsg("role \"%s\" does not exist", rolname)));
5562 return oid;
5563}
#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 5671 of file acl.c.

5672{
5673 HeapTuple tp;
5675 char *rolename;
5676
5677 tp = get_rolespec_tuple(role);
5679 rolename = pstrdup(NameStr(authForm->rolname));
5680 ReleaseSysCache(tp);
5681
5682 return rolename;
5683}
HeapTuple get_rolespec_tuple(const RoleSpec *role)
Definition acl.c:5625
#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 5586 of file acl.c.

5587{
5588 Oid oid;
5589
5590 switch (role->roletype)
5591 {
5592 case ROLESPEC_CSTRING:
5593 Assert(role->rolename);
5594 oid = get_role_oid(role->rolename, missing_ok);
5595 break;
5596
5599 oid = GetUserId();
5600 break;
5601
5603 oid = GetSessionUserId();
5604 break;
5605
5606 case ROLESPEC_PUBLIC:
5607 ereport(ERROR,
5609 errmsg("role \"%s\" does not exist", "public")));
5610 oid = InvalidOid; /* make compiler happy */
5611 break;
5612
5613 default:
5614 elog(ERROR, "unexpected role type %d", role->roletype);
5615 }
5616
5617 return oid;
5618}
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 5625 of file acl.c.

5626{
5627 HeapTuple tuple;
5628
5629 switch (role->roletype)
5630 {
5631 case ROLESPEC_CSTRING:
5632 Assert(role->rolename);
5634 if (!HeapTupleIsValid(tuple))
5635 ereport(ERROR,
5637 errmsg("role \"%s\" does not exist", role->rolename)));
5638 break;
5639
5643 if (!HeapTupleIsValid(tuple))
5644 elog(ERROR, "cache lookup failed for role %u", GetUserId());
5645 break;
5646
5649 if (!HeapTupleIsValid(tuple))
5650 elog(ERROR, "cache lookup failed for role %u", GetSessionUserId());
5651 break;
5652
5653 case ROLESPEC_PUBLIC:
5654 ereport(ERROR,
5656 errmsg("role \"%s\" does not exist", "public")));
5657 tuple = NULL; /* make compiler happy */
5658 break;
5659
5660 default:
5661 elog(ERROR, "unexpected role type %d", role->roletype);
5662 }
5663
5664 return tuple;
5665}
#define HeapTupleIsValid(tuple)
Definition htup.h:78
static Datum ObjectIdGetDatum(Oid X)
Definition postgres.h:262
HeapTuple SearchSysCache1(int 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:501
Acl * acldefault(ObjectType objtype, Oid ownerId)
Definition acl.c:803
bool aclequal(const Acl *left_acl, const Acl *right_acl)
Definition acl.c:559
void aclitemsort(Acl *acl)
Definition acl.c:545
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:56

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 5284 of file acl.c.

5285{
5286 /* Fast path for simple case */
5287 if (member == role)
5288 return true;
5289
5290 /* Superusers have every privilege, so are part of every role */
5291 if (superuser_arg(member))
5292 return true;
5293
5294 /*
5295 * Find all the roles that member has the privileges of, including
5296 * multi-level recursion, then see if target role is any one of them.
5297 */
5299 InvalidOid, NULL),
5300 role);
5301}
static List * roles_is_member_of(Oid roleid, enum RoleRecurseType type, Oid admin_of, Oid *admin_role)
Definition acl.c:5152
@ 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 5040 of file acl.c.

5041{
5043 {
5047
5048 /*
5049 * In normal mode, set a callback on any syscache invalidation of rows
5050 * of pg_auth_members (for roles_is_member_of()) pg_database (for
5051 * roles_is_member_of())
5052 */
5055 (Datum) 0);
5058 (Datum) 0);
5061 (Datum) 0);
5062 }
5063}
static uint32 cached_db_hash
Definition acl.c:82
static void RoleMembershipCacheCallback(Datum arg, int cacheid, uint32 hashvalue)
Definition acl.c:5070
Oid MyDatabaseId
Definition globals.c:94
void CacheRegisterSyscacheCallback(int 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 5414 of file acl.c.

5415{
5417
5418 if (superuser_arg(member))
5419 return true;
5420
5421 /* By policy, a role cannot have WITH ADMIN OPTION on itself. */
5422 if (member == role)
5423 return false;
5424
5426 return OidIsValid(admin_role);
5427}
@ 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 5364 of file acl.c.

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

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 5392 of file acl.c.

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

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 448 of file acl.c.

449{
450 return allocacl(0);
451}

References allocacl().

Referenced by SetDefaultACL().

◆ member_can_set_role()

bool member_can_set_role ( Oid  member,
Oid  role 
)
extern

Definition at line 5318 of file acl.c.

5319{
5320 /* Fast path for simple case */
5321 if (member == role)
5322 return true;
5323
5324 /* Superusers have every privilege, so can always SET ROLE */
5325 if (superuser_arg(member))
5326 return true;
5327
5328 /*
5329 * Find all the roles that member can access via SET ROLE, including
5330 * multi-level recursion, then see if target role is any one of them.
5331 */
5333 InvalidOid, NULL),
5334 role);
5335}
@ 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{
4092 int cacheid;
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
4104 if (cacheid != -1)
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)
int get_object_catcache_oid(Oid class_id)
Oid get_object_oid_index(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(int 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:1388
#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
Datum SysCacheGetAttr(int cacheId, HeapTuple tup, AttrNumber attributeNumber, bool *isNull)
Definition syscache.c:595
HeapTuple SearchSysCache2(int cacheId, Datum key1, Datum key2)
Definition syscache.c:230

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:1540
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 {
4489 int cacheid;
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;
4873 int cacheid;
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:1119

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 5439 of file acl.c.

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

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 5476 of file acl.c.

5479{
5482 int nrights;
5483 ListCell *l;
5484
5485 /*
5486 * The object owner is always treated as having all grant options, so if
5487 * roleId is the owner it's easy. Also, if roleId is a superuser it's
5488 * easy: superusers are implicitly members of every role, so they act as
5489 * the object owner.
5490 */
5491 if (roleId == ownerId || superuser_arg(roleId))
5492 {
5493 *grantorId = ownerId;
5495 return;
5496 }
5497
5498 /*
5499 * Otherwise we have to do a careful search to see if roleId has the
5500 * privileges of any suitable role. Note: we can hang onto the result of
5501 * roles_is_member_of() throughout this loop, because aclmask_direct()
5502 * doesn't query any role memberships.
5503 */
5505 InvalidOid, NULL);
5506
5507 /* initialize candidate result as default */
5508 *grantorId = roleId;
5510 nrights = 0;
5511
5512 foreach(l, roles_list)
5513 {
5516
5517 otherprivs = aclmask_direct(acl, otherrole, ownerId,
5520 {
5521 /* Found a suitable grantor */
5524 return;
5525 }
5526
5527 /*
5528 * If it has just some of the needed privileges, remember best
5529 * candidate.
5530 */
5532 {
5534
5535 if (nnewrights > nrights)
5536 {
5540 }
5541 }
5542 }
5543}
static AclMode aclmask_direct(const Acl *acl, Oid roleid, Oid ownerId, AclMode mask, AclMaskHow how)
Definition acl.c:1477
#define ACL_GRANT_OPTION_FOR(privs)
Definition acl.h:70
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().