diff --git a/src/backend/catalog/aclchk.c b/src/backend/catalog/aclchk.c index 6ff89eb0425b52c87eed91aa6cc7fbfb1fe781ca..f095ef24d6bf604c3cd1f3986e2faf80da88fae0 100644 --- a/src/backend/catalog/aclchk.c +++ b/src/backend/catalog/aclchk.c @@ -8,7 +8,7 @@ * * * IDENTIFICATION - * $PostgreSQL: pgsql/src/backend/catalog/aclchk.c,v 1.113 2005/06/28 05:08:52 tgl Exp $ + * $PostgreSQL: pgsql/src/backend/catalog/aclchk.c,v 1.114 2005/06/28 19:51:21 tgl Exp $ * * NOTES * See acl.h. @@ -47,6 +47,7 @@ static void ExecuteGrantStmt_Language(GrantStmt *stmt); static void ExecuteGrantStmt_Namespace(GrantStmt *stmt); static void ExecuteGrantStmt_Tablespace(GrantStmt *stmt); +static AclMode string_to_privilege(const char *privname); static const char *privilege_to_string(AclMode privilege); @@ -209,7 +210,7 @@ ExecuteGrantStmt_Relation(GrantStmt *stmt) bool all_privs; ListCell *i; - if (linitial_int(stmt->privileges) == ACL_ALL_RIGHTS) + if (stmt->privileges == NIL) { all_privs = true; privileges = ACL_ALL_RIGHTS_RELATION; @@ -220,7 +221,8 @@ ExecuteGrantStmt_Relation(GrantStmt *stmt) privileges = ACL_NO_RIGHTS; foreach(i, stmt->privileges) { - AclMode priv = lfirst_int(i); + char *privname = strVal(lfirst(i)); + AclMode priv = string_to_privilege(privname); if (priv & ~((AclMode) ACL_ALL_RIGHTS_RELATION)) ereport(ERROR, @@ -377,7 +379,7 @@ ExecuteGrantStmt_Database(GrantStmt *stmt) bool all_privs; ListCell *i; - if (linitial_int(stmt->privileges) == ACL_ALL_RIGHTS) + if (stmt->privileges == NIL) { all_privs = true; privileges = ACL_ALL_RIGHTS_DATABASE; @@ -388,7 +390,8 @@ ExecuteGrantStmt_Database(GrantStmt *stmt) privileges = ACL_NO_RIGHTS; foreach(i, stmt->privileges) { - AclMode priv = lfirst_int(i); + char *privname = strVal(lfirst(i)); + AclMode priv = string_to_privilege(privname); if (priv & ~((AclMode) ACL_ALL_RIGHTS_DATABASE)) ereport(ERROR, @@ -535,7 +538,7 @@ ExecuteGrantStmt_Function(GrantStmt *stmt) bool all_privs; ListCell *i; - if (linitial_int(stmt->privileges) == ACL_ALL_RIGHTS) + if (stmt->privileges == NIL) { all_privs = true; privileges = ACL_ALL_RIGHTS_FUNCTION; @@ -546,7 +549,8 @@ ExecuteGrantStmt_Function(GrantStmt *stmt) privileges = ACL_NO_RIGHTS; foreach(i, stmt->privileges) { - AclMode priv = lfirst_int(i); + char *privname = strVal(lfirst(i)); + AclMode priv = string_to_privilege(privname); if (priv & ~((AclMode) ACL_ALL_RIGHTS_FUNCTION)) ereport(ERROR, @@ -689,7 +693,7 @@ ExecuteGrantStmt_Language(GrantStmt *stmt) bool all_privs; ListCell *i; - if (linitial_int(stmt->privileges) == ACL_ALL_RIGHTS) + if (stmt->privileges == NIL) { all_privs = true; privileges = ACL_ALL_RIGHTS_LANGUAGE; @@ -700,7 +704,8 @@ ExecuteGrantStmt_Language(GrantStmt *stmt) privileges = ACL_NO_RIGHTS; foreach(i, stmt->privileges) { - AclMode priv = lfirst_int(i); + char *privname = strVal(lfirst(i)); + AclMode priv = string_to_privilege(privname); if (priv & ~((AclMode) ACL_ALL_RIGHTS_LANGUAGE)) ereport(ERROR, @@ -852,7 +857,7 @@ ExecuteGrantStmt_Namespace(GrantStmt *stmt) bool all_privs; ListCell *i; - if (linitial_int(stmt->privileges) == ACL_ALL_RIGHTS) + if (stmt->privileges == NIL) { all_privs = true; privileges = ACL_ALL_RIGHTS_NAMESPACE; @@ -863,7 +868,8 @@ ExecuteGrantStmt_Namespace(GrantStmt *stmt) privileges = ACL_NO_RIGHTS; foreach(i, stmt->privileges) { - AclMode priv = lfirst_int(i); + char *privname = strVal(lfirst(i)); + AclMode priv = string_to_privilege(privname); if (priv & ~((AclMode) ACL_ALL_RIGHTS_NAMESPACE)) ereport(ERROR, @@ -1006,7 +1012,7 @@ ExecuteGrantStmt_Tablespace(GrantStmt *stmt) bool all_privs; ListCell *i; - if (linitial_int(stmt->privileges) == ACL_ALL_RIGHTS) + if (stmt->privileges == NIL) { all_privs = true; privileges = ACL_ALL_RIGHTS_TABLESPACE; @@ -1017,7 +1023,8 @@ ExecuteGrantStmt_Tablespace(GrantStmt *stmt) privileges = ACL_NO_RIGHTS; foreach(i, stmt->privileges) { - AclMode priv = lfirst_int(i); + char *privname = strVal(lfirst(i)); + AclMode priv = string_to_privilege(privname); if (priv & ~((AclMode) ACL_ALL_RIGHTS_TABLESPACE)) ereport(ERROR, @@ -1157,6 +1164,39 @@ ExecuteGrantStmt_Tablespace(GrantStmt *stmt) } +static AclMode +string_to_privilege(const char *privname) +{ + if (strcmp(privname, "insert") == 0) + return ACL_INSERT; + if (strcmp(privname, "select") == 0) + return ACL_SELECT; + if (strcmp(privname, "update") == 0) + return ACL_UPDATE; + if (strcmp(privname, "delete") == 0) + return ACL_DELETE; + if (strcmp(privname, "rule") == 0) + return ACL_RULE; + if (strcmp(privname, "references") == 0) + return ACL_REFERENCES; + if (strcmp(privname, "trigger") == 0) + return ACL_TRIGGER; + if (strcmp(privname, "execute") == 0) + return ACL_EXECUTE; + if (strcmp(privname, "usage") == 0) + return ACL_USAGE; + if (strcmp(privname, "create") == 0) + return ACL_CREATE; + if (strcmp(privname, "temporary") == 0) + return ACL_CREATE_TEMP; + if (strcmp(privname, "temp") == 0) + return ACL_CREATE_TEMP; + ereport(ERROR, + (errcode(ERRCODE_SYNTAX_ERROR), + errmsg("unrecognized privilege type \"%s\"", privname))); + return 0; /* appease compiler */ +} + static const char * privilege_to_string(AclMode privilege) { diff --git a/src/backend/catalog/pg_proc.c b/src/backend/catalog/pg_proc.c index 7d1384ed382be8530fb1e9a3fa66073e1edab905..f8ed892ebfe3f02bdb1e07f5cca1b7d9cb517639 100644 --- a/src/backend/catalog/pg_proc.c +++ b/src/backend/catalog/pg_proc.c @@ -8,7 +8,7 @@ * * * IDENTIFICATION - * $PostgreSQL: pgsql/src/backend/catalog/pg_proc.c,v 1.130 2005/06/28 05:08:52 tgl Exp $ + * $PostgreSQL: pgsql/src/backend/catalog/pg_proc.c,v 1.131 2005/06/28 19:51:21 tgl Exp $ * *------------------------------------------------------------------------- */ @@ -266,7 +266,7 @@ ProcedureCreate(const char *procedureName, (errcode(ERRCODE_DUPLICATE_FUNCTION), errmsg("function \"%s\" already exists with same argument types", procedureName))); - if (GetUserId() != oldproc->proowner && !superuser()) + if (!pg_proc_ownercheck(HeapTupleGetOid(oldtup), GetUserId())) aclcheck_error(ACLCHECK_NOT_OWNER, ACL_KIND_PROC, procedureName); diff --git a/src/backend/commands/user.c b/src/backend/commands/user.c index 131f1896f928c563d39e4ddae58693eff2803799..0d34e57b258fc2225a1816aea24c115aa03711bb 100644 --- a/src/backend/commands/user.c +++ b/src/backend/commands/user.c @@ -6,7 +6,7 @@ * Portions Copyright (c) 1996-2005, PostgreSQL Global Development Group * Portions Copyright (c) 1994, Regents of the University of California * - * $PostgreSQL: pgsql/src/backend/commands/user.c,v 1.152 2005/06/28 05:08:55 tgl Exp $ + * $PostgreSQL: pgsql/src/backend/commands/user.c,v 1.153 2005/06/28 19:51:22 tgl Exp $ * *------------------------------------------------------------------------- */ @@ -61,16 +61,17 @@ CreateRole(CreateRoleStmt *stmt) bool createrole = false; /* Can this user create roles? */ bool createdb = false; /* Can the user create databases? */ bool canlogin = false; /* Can this user login? */ - List *roleElts = NIL; /* roles the user is a member of */ - List *rolememElts = NIL; /* roles which will be members of this role */ - char *validUntil = NULL; /* The time the login is valid - * until */ + List *addroleto = NIL; /* roles to make this a member of */ + List *rolemembers = NIL; /* roles to be members of this role */ + List *adminmembers = NIL; /* roles to be admins of this role */ + char *validUntil = NULL; /* time the login is valid until */ DefElem *dpassword = NULL; DefElem *dcreatedb = NULL; DefElem *dcreaterole = NULL; DefElem *dcanlogin = NULL; - DefElem *droleElts = NULL; - DefElem *drolememElts = NULL; + DefElem *daddroleto = NULL; + DefElem *drolemembers = NULL; + DefElem *dadminmembers = NULL; DefElem *dvalidUntil = NULL; /* Extract options from the statement node tree */ @@ -121,21 +122,29 @@ CreateRole(CreateRoleStmt *stmt) errmsg("conflicting or redundant options"))); dcanlogin = defel; } - else if (strcmp(defel->defname, "roleElts") == 0) + else if (strcmp(defel->defname, "addroleto") == 0) { - if (droleElts) + if (daddroleto) ereport(ERROR, (errcode(ERRCODE_SYNTAX_ERROR), errmsg("conflicting or redundant options"))); - droleElts = defel; + daddroleto = defel; } - else if (strcmp(defel->defname, "rolememElts") == 0) + else if (strcmp(defel->defname, "rolemembers") == 0) { - if (drolememElts) + if (drolemembers) ereport(ERROR, (errcode(ERRCODE_SYNTAX_ERROR), errmsg("conflicting or redundant options"))); - drolememElts = defel; + drolemembers = defel; + } + else if (strcmp(defel->defname, "adminmembers") == 0) + { + if (dadminmembers) + ereport(ERROR, + (errcode(ERRCODE_SYNTAX_ERROR), + errmsg("conflicting or redundant options"))); + dadminmembers = defel; } else if (strcmp(defel->defname, "validUntil") == 0) { @@ -164,10 +173,12 @@ CreateRole(CreateRoleStmt *stmt) validUntil = strVal(dvalidUntil->arg); if (dpassword) password = strVal(dpassword->arg); - if (droleElts) - roleElts = (List *) droleElts->arg; - if (drolememElts) - rolememElts = (List *) drolememElts->arg; + if (daddroleto) + addroleto = (List *) daddroleto->arg; + if (drolemembers) + rolemembers = (List *) drolemembers->arg; + if (dadminmembers) + adminmembers = (List *) dadminmembers->arg; /* Check some permissions first */ if (!superuser()) @@ -257,7 +268,7 @@ CreateRole(CreateRoleStmt *stmt) /* * Add the new role to the specified existing roles. */ - foreach(item, roleElts) + foreach(item, addroleto) { char *oldrolename = strVal(lfirst(item)); Oid oldroleid = get_roleid_checked(oldrolename); @@ -269,10 +280,14 @@ CreateRole(CreateRoleStmt *stmt) } /* - * Add the specified members to this new role. + * Add the specified members to this new role. adminmembers get the + * admin option, rolemembers don't. */ AddRoleMems(stmt->role, roleid, - rolememElts, roleNamesToIds(rolememElts), + adminmembers, roleNamesToIds(adminmembers), + GetUserId(), true); + AddRoleMems(stmt->role, roleid, + rolemembers, roleNamesToIds(rolemembers), GetUserId(), false); /* @@ -309,17 +324,14 @@ AlterRole(AlterRoleStmt *stmt) int createrole = -1; /* Can this user create roles? */ int createdb = -1; /* Can the user create databases? */ int canlogin = -1; /* Can this user login? */ - int adminopt = 0; /* Can this user grant this role to others? */ - List *rolememElts = NIL; /* The roles which will be added/removed to this role */ - char *validUntil = NULL; /* The time the login is valid - * until */ + List *rolemembers = NIL; /* roles to be added/removed */ + char *validUntil = NULL; /* time the login is valid until */ DefElem *dpassword = NULL; DefElem *dcreatedb = NULL; DefElem *dcreaterole = NULL; DefElem *dcanlogin = NULL; - DefElem *dadminopt = NULL; DefElem *dvalidUntil = NULL; - DefElem *drolememElts = NULL; + DefElem *drolemembers = NULL; Oid roleid; /* Extract options from the statement node tree */ @@ -365,14 +377,6 @@ AlterRole(AlterRoleStmt *stmt) errmsg("conflicting or redundant options"))); dcanlogin = defel; } - else if (strcmp(defel->defname, "adminopt") == 0) - { - if (dadminopt) - ereport(ERROR, - (errcode(ERRCODE_SYNTAX_ERROR), - errmsg("conflicting or redundant options"))); - dadminopt = defel; - } else if (strcmp(defel->defname, "validUntil") == 0) { if (dvalidUntil) @@ -381,13 +385,14 @@ AlterRole(AlterRoleStmt *stmt) errmsg("conflicting or redundant options"))); dvalidUntil = defel; } - else if (strcmp(defel->defname, "rolememElts") == 0 && stmt->action != 0) + else if (strcmp(defel->defname, "rolemembers") == 0 && + stmt->action != 0) { - if (drolememElts) + if (drolemembers) ereport(ERROR, (errcode(ERRCODE_SYNTAX_ERROR), errmsg("conflicting or redundant options"))); - drolememElts = defel; + drolemembers = defel; } else elog(ERROR, "option \"%s\" not recognized", @@ -404,14 +409,12 @@ AlterRole(AlterRoleStmt *stmt) } if (dcanlogin) canlogin = intVal(dcanlogin->arg); - if (dadminopt) - adminopt = intVal(dadminopt->arg); if (dvalidUntil) validUntil = strVal(dvalidUntil->arg); if (dpassword) password = strVal(dpassword->arg); - if (drolememElts) - rolememElts = (List *) drolememElts->arg; + if (drolemembers) + rolemembers = (List *) drolemembers->arg; /* must be superuser or just want to change your own password */ if (!superuser() && @@ -420,8 +423,7 @@ AlterRole(AlterRoleStmt *stmt) createdb < 0 && canlogin < 0 && !validUntil && - !rolememElts && - !adminopt && + !rolemembers && password && strcmp(GetUserNameFromId(GetUserId()), stmt->role) == 0)) ereport(ERROR, @@ -537,12 +539,12 @@ AlterRole(AlterRoleStmt *stmt) if (stmt->action == +1) /* add members to role */ AddRoleMems(stmt->role, roleid, - rolememElts, roleNamesToIds(rolememElts), - GetUserId(), adminopt); + rolemembers, roleNamesToIds(rolemembers), + GetUserId(), false); else if (stmt->action == -1) /* drop members from role */ DelRoleMems(stmt->role, roleid, - rolememElts, roleNamesToIds(rolememElts), - adminopt); + rolemembers, roleNamesToIds(rolemembers), + false); /* * Set flag to update flat auth file at commit. diff --git a/src/backend/parser/gram.y b/src/backend/parser/gram.y index d822a7176a72cc9a32af4d9ac1e2cab5564a35b0..7f18b12b92b0308536bf7a2bb80958dadcf47b8b 100644 --- a/src/backend/parser/gram.y +++ b/src/backend/parser/gram.y @@ -11,7 +11,7 @@ * * * IDENTIFICATION - * $PostgreSQL: pgsql/src/backend/parser/gram.y,v 2.499 2005/06/28 05:08:57 tgl Exp $ + * $PostgreSQL: pgsql/src/backend/parser/gram.y,v 2.500 2005/06/28 19:51:22 tgl Exp $ * * HISTORY * AUTHOR DATE MAJOR EVENT @@ -143,10 +143,10 @@ static void doNegateFloat(Value *v); DropGroupStmt DropOpClassStmt DropPLangStmt DropStmt DropAssertStmt DropTrigStmt DropRuleStmt DropCastStmt DropRoleStmt DropUserStmt DropdbStmt DropTableSpaceStmt ExplainStmt FetchStmt - GrantRoleStmt GrantStmt IndexStmt InsertStmt ListenStmt LoadStmt + GrantStmt GrantRoleStmt IndexStmt InsertStmt ListenStmt LoadStmt LockStmt NotifyStmt ExplainableStmt PreparableStmt CreateFunctionStmt AlterFunctionStmt ReindexStmt RemoveAggrStmt - RemoveFuncStmt RemoveOperStmt RenameStmt RevokeRoleStmt RevokeStmt + RemoveFuncStmt RemoveOperStmt RenameStmt RevokeStmt RevokeRoleStmt RuleActionStmt RuleActionStmtOrEmpty RuleStmt SelectStmt TransactionStmt TruncateStmt UnlistenStmt UpdateStmt VacuumStmt @@ -170,15 +170,11 @@ static void doNegateFloat(Value *v); %type <ival> opt_lock lock_type cast_context %type <boolean> opt_force opt_or_replace - opt_grant_grant_option opt_revoke_grant_option - opt_alter_admin_option - opt_grant_admin_option opt_revoke_admin_option + opt_grant_grant_option opt_grant_admin_option opt_nowait %type <boolean> like_including_defaults -%type <list> role_list - %type <list> OptRoleList %type <defelt> OptRoleElem @@ -205,7 +201,7 @@ static void doNegateFloat(Value *v); %type <str> iso_level opt_encoding %type <node> grantee %type <list> grantee_list -%type <ival> privilege +%type <str> privilege %type <list> privileges privilege_list %type <privtarget> privilege_target %type <funwithargs> function_with_argtypes @@ -347,8 +343,8 @@ static void doNegateFloat(Value *v); CHARACTER CHARACTERISTICS CHECK CHECKPOINT CLASS CLOSE CLUSTER COALESCE COLLATE COLUMN COMMENT COMMIT COMMITTED CONSTRAINT CONSTRAINTS CONVERSION_P CONVERT COPY CREATE CREATEDB - CREATEROLE CREATEUSER CROSS CSV CURRENT_DATE CURRENT_TIME - CURRENT_TIMESTAMP CURRENT_ROLE CURRENT_USER CURSOR CYCLE + CREATEROLE CREATEUSER CROSS CSV CURRENT_DATE CURRENT_ROLE CURRENT_TIME + CURRENT_TIMESTAMP CURRENT_USER CURSOR CYCLE DATABASE DAY_P DEALLOCATE DEC DECIMAL_P DECLARE DEFAULT DEFAULTS DEFERRABLE DEFERRED DEFINER DELETE_P DELIMITER DELIMITERS @@ -375,13 +371,13 @@ static void doNegateFloat(Value *v); LANCOMPILER LANGUAGE LARGE_P LAST_P LEADING LEAST LEFT LEVEL LIKE LIMIT LISTEN LOAD LOCAL LOCALTIME LOCALTIMESTAMP LOCATION - LOCK_P LOGIN + LOCK_P LOGIN_P MATCH MAXVALUE MINUTE_P MINVALUE MODE MONTH_P MOVE NAMES NATIONAL NATURAL NCHAR NEW NEXT NO NOCREATEDB - NOCREATEROLE NOCREATEUSER NONE NOT NOTHING NOTIFY NOTNULL NOWAIT NULL_P - NULLIF NUMERIC NOLOGIN + NOCREATEROLE NOCREATEUSER NOLOGIN_P NONE NOT NOTHING NOTIFY + NOTNULL NOWAIT NULL_P NULLIF NUMERIC OBJECT_P OF OFF OFFSET OIDS OLD ON ONLY OPERATOR OPTION OR ORDER OUT_P OUTER_P OVERLAPS OVERLAY OWNER @@ -397,7 +393,7 @@ static void doNegateFloat(Value *v); ROLE ROLLBACK ROW ROWS RULE SAVEPOINT SCHEMA SCROLL SECOND_P SECURITY SELECT SEQUENCE - SERIALIZABLE SESSION SESSION_ROLE SESSION_USER SET SETOF SHARE + SERIALIZABLE SESSION SESSION_USER SET SETOF SHARE SHOW SIMILAR SIMPLE SMALLINT SOME STABLE START STATEMENT STATISTICS STDIN STDOUT STORAGE STRICT_P SUBSTRING SYMMETRIC SYSID SYSTEM_P @@ -407,7 +403,7 @@ static void doNegateFloat(Value *v); TRUNCATE TRUSTED TYPE_P UNCOMMITTED UNENCRYPTED UNION UNIQUE UNKNOWN UNLISTEN UNTIL - UPDATE USAGE USER USING + UPDATE USER USING VACUUM VALID VALIDATOR VALUES VARCHAR VARYING VERBOSE VIEW VOLATILE @@ -544,8 +540,8 @@ stmt : | ExecuteStmt | ExplainStmt | FetchStmt - | GrantRoleStmt | GrantStmt + | GrantRoleStmt | IndexStmt | InsertStmt | ListenStmt @@ -558,8 +554,8 @@ stmt : | RemoveFuncStmt | RemoveOperStmt | RenameStmt - | RevokeRoleStmt | RevokeStmt + | RevokeRoleStmt | RuleStmt | SelectStmt | TransactionStmt @@ -579,7 +575,6 @@ stmt : * * Create a new Postgres DBMS role * - * *****************************************************************************/ CreateRoleStmt: @@ -597,11 +592,99 @@ opt_with: WITH {} | /*EMPTY*/ {} ; +/* + * Options for CREATE ROLE and ALTER ROLE (also used by CREATE/ALTER USER + * for backwards compatibility). Note: the only option required by SQL99 + * is "WITH ADMIN name". + */ +OptRoleList: + OptRoleList OptRoleElem { $$ = lappend($1, $2); } + | /* EMPTY */ { $$ = NIL; } + ; + +OptRoleElem: + PASSWORD Sconst + { + $$ = makeDefElem("password", + (Node *)makeString($2)); + } + | ENCRYPTED PASSWORD Sconst + { + $$ = makeDefElem("encryptedPassword", + (Node *)makeString($3)); + } + | UNENCRYPTED PASSWORD Sconst + { + $$ = makeDefElem("unencryptedPassword", + (Node *)makeString($3)); + } + | SYSID Iconst + { + $$ = makeDefElem("sysid", (Node *)makeInteger($2)); + } + | CREATEDB + { + $$ = makeDefElem("createdb", (Node *)makeInteger(TRUE)); + } + | NOCREATEDB + { + $$ = makeDefElem("createdb", (Node *)makeInteger(FALSE)); + } + | CREATEROLE + { + $$ = makeDefElem("createrole", (Node *)makeInteger(TRUE)); + } + | CREATEUSER + { + $$ = makeDefElem("createrole", (Node *)makeInteger(TRUE)); + } + | LOGIN_P + { + $$ = makeDefElem("canlogin", (Node *)makeInteger(TRUE)); + } + | NOCREATEROLE + { + $$ = makeDefElem("createrole", (Node *)makeInteger(FALSE)); + } + | NOCREATEUSER + { + $$ = makeDefElem("createrole", (Node *)makeInteger(FALSE)); + } + | NOLOGIN_P + { + $$ = makeDefElem("canlogin", (Node *)makeInteger(FALSE)); + } + | IN_P ROLE name_list + { + $$ = makeDefElem("addroleto", (Node *)$3); + } + | IN_P GROUP_P name_list + { + $$ = makeDefElem("addroleto", (Node *)$3); + } + | VALID UNTIL Sconst + { + $$ = makeDefElem("validUntil", (Node *)makeString($3)); + } + | ADMIN name_list + { + $$ = makeDefElem("adminmembers", (Node *)$2); + } + | ROLE name_list + { + $$ = makeDefElem("rolemembers", (Node *)$2); + } + | USER name_list + { + $$ = makeDefElem("rolemembers", (Node *)$2); + } + ; + + /***************************************************************************** * * Create a new Postgres DBMS user (role with implied login ability) * - * *****************************************************************************/ CreateUserStmt: @@ -609,8 +692,9 @@ CreateUserStmt: { CreateRoleStmt *n = makeNode(CreateRoleStmt); n->role = $3; - n->options = $5; - n->options = lappend(n->options,makeDefElem("canlogin", (Node *)makeInteger(TRUE))); + n->options = lappend($5, + makeDefElem("canlogin", + (Node *)makeInteger(TRUE))); $$ = (Node *)n; } ; @@ -620,7 +704,6 @@ CreateUserStmt: * * Alter a postgresql DBMS role * - * *****************************************************************************/ AlterRoleStmt: @@ -631,24 +714,6 @@ AlterRoleStmt: n->options = $5; $$ = (Node *)n; } - | ALTER ROLE RoleId add_drop ROLE role_list opt_alter_admin_option - { - AlterRoleStmt *n = makeNode(AlterRoleStmt); - n->role = $3; - n->action = $4; - n->options = lappend(n->options,makeDefElem("rolememElts", (Node *)$6)); - n->options = lappend(n->options,makeDefElem("adminopt", (Node *)makeInteger($7))); - $$ = (Node *)n; - } - ; - -add_drop: ADD { $$ = +1; } - | DROP { $$ = -1; } - ; - -opt_alter_admin_option: - ADMIN OPTION { $$ = TRUE; } - | /*EMPTY*/ { $$ = FALSE; } ; AlterRoleSetStmt: @@ -668,14 +733,13 @@ AlterRoleSetStmt: n->value = NIL; $$ = (Node *)n; } - ; + ; /***************************************************************************** * * Alter a postgresql DBMS user * - * *****************************************************************************/ AlterUserStmt: @@ -719,7 +783,7 @@ AlterUserSetStmt: *****************************************************************************/ DropRoleStmt: - DROP ROLE role_list + DROP ROLE name_list { DropRoleStmt *n = makeNode(DropRoleStmt); n->roles = $3; @@ -737,7 +801,7 @@ DropRoleStmt: *****************************************************************************/ DropUserStmt: - DROP USER role_list + DROP USER name_list { DropRoleStmt *n = makeNode(DropRoleStmt); n->roles = $3; @@ -745,96 +809,11 @@ DropUserStmt: } ; -/* - * Options for CREATE ROLE and ALTER ROLE (also used by CREATE/ALTER USER for backwards compat) - */ -OptRoleList: - OptRoleList OptRoleElem { $$ = lappend($1, $2); } - | /* EMPTY */ { $$ = NIL; } - ; - -OptRoleElem: - PASSWORD Sconst - { - $$ = makeDefElem("password", (Node *)makeString($2)); - } - | ENCRYPTED PASSWORD Sconst - { - $$ = makeDefElem("encryptedPassword", (Node *)makeString($3)); - } - | UNENCRYPTED PASSWORD Sconst - { - $$ = makeDefElem("unencryptedPassword", (Node *)makeString($3)); - } - | SYSID Iconst - { - $$ = makeDefElem("sysid", (Node *)makeInteger($2)); - } - | CREATEDB - { - $$ = makeDefElem("createdb", (Node *)makeInteger(TRUE)); - } - | NOCREATEDB - { - $$ = makeDefElem("createdb", (Node *)makeInteger(FALSE)); - } - | CREATEROLE - { - $$ = makeDefElem("createrole", (Node *)makeInteger(TRUE)); - } - | CREATEUSER - { - $$ = makeDefElem("createrole", (Node *)makeInteger(TRUE)); - } - | LOGIN - { - $$ = makeDefElem("canlogin", (Node *)makeInteger(TRUE)); - } - | NOCREATEROLE - { - $$ = makeDefElem("createrole", (Node *)makeInteger(FALSE)); - } - | NOCREATEUSER - { - $$ = makeDefElem("createrole", (Node *)makeInteger(FALSE)); - } - | NOLOGIN - { - $$ = makeDefElem("canlogin", (Node *)makeInteger(FALSE)); - } - | IN_P ROLE role_list - { - $$ = makeDefElem("roleElts", (Node *)$3); - } - | IN_P GROUP_P role_list - { - $$ = makeDefElem("roleElts", (Node *)$3); - } - | VALID UNTIL Sconst - { - $$ = makeDefElem("validUntil", (Node *)makeString($3)); - } - | ROLE role_list - { - $$ = makeDefElem("rolememElts", (Node *)$2); - } - | USER role_list - { - $$ = makeDefElem("rolememElts", (Node *)$2); - } - ; - -role_list: role_list ',' RoleId { $$ = lappend($1, makeString($3)); } - | RoleId { $$ = list_make1(makeString($1)); } - ; - - /***************************************************************************** * * Create a postgresql group (role without login ability) * - * *****************************************************************************/ CreateGroupStmt: @@ -852,20 +831,24 @@ CreateGroupStmt: * * Alter a postgresql group * - * *****************************************************************************/ AlterGroupStmt: - ALTER GROUP_P RoleId add_drop USER role_list + ALTER GROUP_P RoleId add_drop USER name_list { AlterRoleStmt *n = makeNode(AlterRoleStmt); n->role = $3; n->action = $4; - n->options = lappend(n->options,makeDefElem("rolememElts", (Node *)$6)); + n->options = list_make1(makeDefElem("rolemembers", + (Node *)$6)); $$ = (Node *)n; } ; +add_drop: ADD { $$ = +1; } + | DROP { $$ = -1; } + ; + /***************************************************************************** * @@ -875,7 +858,7 @@ AlterGroupStmt: *****************************************************************************/ DropGroupStmt: - DROP GROUP_P role_list + DROP GROUP_P name_list { DropRoleStmt *n = makeNode(DropRoleStmt); n->roles = $3; @@ -3116,36 +3099,6 @@ from_in: FROM {} ; -/***************************************************************************** - * - * GRANT and REVOKE ROLE statements - * - *****************************************************************************/ - -GrantRoleStmt: GRANT ROLE role_list TO role_list opt_grant_admin_option - opt_granted_by - { - GrantRoleStmt *n = makeNode(GrantRoleStmt); - n->granted_roles = $3; - n->grantee_roles = $5; - n->is_grant = true; - n->admin_opt = $6; - n->grantor = $7; - $$ = (Node*)n; - } - -RevokeRoleStmt: REVOKE ROLE opt_revoke_admin_option role_list FROM role_list - opt_drop_behavior - { - GrantRoleStmt *n = makeNode(GrantRoleStmt); - n->granted_roles = $4; - n->grantee_roles = $6; - n->is_grant = false; - n->admin_opt = $3; - n->behavior = $7; - $$ = (Node*)n; - } - /***************************************************************************** * * GRANT and REVOKE statements @@ -3166,54 +3119,70 @@ GrantStmt: GRANT privileges ON privilege_target TO grantee_list } ; -RevokeStmt: REVOKE opt_revoke_grant_option privileges ON privilege_target +RevokeStmt: + REVOKE privileges ON privilege_target FROM grantee_list opt_drop_behavior { GrantStmt *n = makeNode(GrantStmt); n->is_grant = false; - n->privileges = $3; - n->objtype = ($5)->objtype; - n->objects = ($5)->objs; - n->grantees = $7; - n->grant_option = $2; - n->behavior = $8; - + n->grant_option = false; + n->privileges = $2; + n->objtype = ($4)->objtype; + n->objects = ($4)->objs; + n->grantees = $6; + n->behavior = $7; + $$ = (Node *)n; + } + | REVOKE GRANT OPTION FOR privileges ON privilege_target + FROM grantee_list opt_drop_behavior + { + GrantStmt *n = makeNode(GrantStmt); + n->is_grant = false; + n->grant_option = true; + n->privileges = $5; + n->objtype = ($7)->objtype; + n->objects = ($7)->objs; + n->grantees = $9; + n->behavior = $10; $$ = (Node *)n; } ; +/* + * A privilege list is represented as a list of strings; the validity of + * the privilege names gets checked at execution. This is a bit annoying + * but we have little choice because of the syntactic conflict with lists + * of role names in GRANT/REVOKE. What's more, we have to call out in + * the "privilege" production any reserved keywords that need to be usable + * as privilege names. + */ + /* either ALL [PRIVILEGES] or a list of individual privileges */ -privileges: privilege_list { $$ = $1; } - | ALL { $$ = list_make1_int(ACL_ALL_RIGHTS); } - | ALL PRIVILEGES { $$ = list_make1_int(ACL_ALL_RIGHTS); } +privileges: privilege_list + { $$ = $1; } + | ALL + { $$ = NIL; } + | ALL PRIVILEGES + { $$ = NIL; } ; -privilege_list: - privilege { $$ = list_make1_int($1); } - | privilege_list ',' privilege { $$ = lappend_int($1, $3); } +privilege_list: privilege + { $$ = list_make1(makeString($1)); } + | privilege_list ',' privilege + { $$ = lappend($1, makeString($3)); } ; -/* Not all of these privilege types apply to all objects, but that - * gets sorted out later. - */ -privilege: SELECT { $$ = ACL_SELECT; } - | INSERT { $$ = ACL_INSERT; } - | UPDATE { $$ = ACL_UPDATE; } - | DELETE_P { $$ = ACL_DELETE; } - | RULE { $$ = ACL_RULE; } - | REFERENCES { $$ = ACL_REFERENCES; } - | TRIGGER { $$ = ACL_TRIGGER; } - | EXECUTE { $$ = ACL_EXECUTE; } - | USAGE { $$ = ACL_USAGE; } - | CREATE { $$ = ACL_CREATE; } - | TEMPORARY { $$ = ACL_CREATE_TEMP; } - | TEMP { $$ = ACL_CREATE_TEMP; } +privilege: SELECT { $$ = pstrdup($1); } + | REFERENCES { $$ = pstrdup($1); } + | CREATE { $$ = pstrdup($1); } + | ColId { $$ = $1; } ; /* Don't bother trying to fold the first two rules into one using - opt_table. You're going to get conflicts. */ + * opt_table. You're going to get conflicts. + */ privilege_target: qualified_name_list { @@ -3300,27 +3269,6 @@ opt_grant_grant_option: | /*EMPTY*/ { $$ = FALSE; } ; -opt_grant_admin_option: - WITH ADMIN OPTION { $$ = TRUE; } - | /*EMPTY*/ { $$ = FALSE; } - ; - -opt_granted_by: - GRANTED BY RoleId { $$ = $3; } - | /*EMPTY*/ { $$ = NULL; } - ; - -opt_revoke_grant_option: - GRANT OPTION FOR { $$ = TRUE; } - | /*EMPTY*/ { $$ = FALSE; } - ; - -opt_revoke_admin_option: - ADMIN OPTION FOR { $$ = TRUE; } - | /*EMPTY*/ { $$ = FALSE; } - ; - - function_with_argtypes_list: function_with_argtypes { $$ = list_make1($1); } | function_with_argtypes_list ',' function_with_argtypes @@ -3337,6 +3285,56 @@ function_with_argtypes: } ; +/***************************************************************************** + * + * GRANT and REVOKE ROLE statements + * + *****************************************************************************/ + +GrantRoleStmt: + GRANT privilege_list TO name_list opt_grant_admin_option opt_granted_by + { + GrantRoleStmt *n = makeNode(GrantRoleStmt); + n->is_grant = true; + n->granted_roles = $2; + n->grantee_roles = $4; + n->admin_opt = $5; + n->grantor = $6; + $$ = (Node*)n; + } + ; + +RevokeRoleStmt: + REVOKE privilege_list FROM name_list opt_granted_by opt_drop_behavior + { + GrantRoleStmt *n = makeNode(GrantRoleStmt); + n->is_grant = false; + n->admin_opt = false; + n->granted_roles = $2; + n->grantee_roles = $4; + n->behavior = $6; + $$ = (Node*)n; + } + | REVOKE ADMIN OPTION FOR privilege_list FROM name_list opt_granted_by opt_drop_behavior + { + GrantRoleStmt *n = makeNode(GrantRoleStmt); + n->is_grant = false; + n->admin_opt = true; + n->granted_roles = $5; + n->grantee_roles = $7; + n->behavior = $9; + $$ = (Node*)n; + } + ; + +opt_grant_admin_option: WITH ADMIN OPTION { $$ = TRUE; } + | /*EMPTY*/ { $$ = FALSE; } + ; + +opt_granted_by: GRANTED BY RoleId { $$ = $3; } + | /*EMPTY*/ { $$ = NULL; } + ; + /***************************************************************************** * @@ -7066,24 +7064,6 @@ func_expr: func_name '(' ')' n->agg_distinct = FALSE; $$ = (Node *)n; } - | SESSION_ROLE - { - FuncCall *n = makeNode(FuncCall); - n->funcname = SystemFuncName("session_user"); - n->args = NIL; - n->agg_star = FALSE; - n->agg_distinct = FALSE; - $$ = (Node *)n; - } - | ROLE - { - FuncCall *n = makeNode(FuncCall); - n->funcname = SystemFuncName("current_user"); - n->args = NIL; - n->agg_star = FALSE; - n->agg_distinct = FALSE; - $$ = (Node *)n; - } | CURRENT_USER { FuncCall *n = makeNode(FuncCall); @@ -7928,6 +7908,7 @@ unreserved_keyword: | ACCESS | ACTION | ADD + | ADMIN | AFTER | AGGREGATE | ALSO @@ -7988,6 +7969,7 @@ unreserved_keyword: | FORWARD | FUNCTION | GLOBAL + | GRANTED | HANDLER | HEADER | HOLD @@ -8016,7 +7998,7 @@ unreserved_keyword: | LOCAL | LOCATION | LOCK_P - | LOGIN + | LOGIN_P | MATCH | MAXVALUE | MINUTE_P @@ -8030,7 +8012,7 @@ unreserved_keyword: | NOCREATEDB | NOCREATEROLE | NOCREATEUSER - | NOLOGIN + | NOLOGIN_P | NOTHING | NOTIFY | NOWAIT @@ -8063,6 +8045,7 @@ unreserved_keyword: | RESTRICT | RETURNS | REVOKE + | ROLE | ROLLBACK | ROWS | RULE @@ -8104,7 +8087,6 @@ unreserved_keyword: | UNLISTEN | UNTIL | UPDATE - | USAGE | VACUUM | VALID | VALIDATOR @@ -8228,9 +8210,9 @@ reserved_keyword: | CONSTRAINT | CREATE | CURRENT_DATE + | CURRENT_ROLE | CURRENT_TIME | CURRENT_TIMESTAMP - | CURRENT_ROLE | CURRENT_USER | DEFAULT | DEFERRABLE @@ -8269,7 +8251,6 @@ reserved_keyword: | PRIMARY | REFERENCES | SELECT - | SESSION_ROLE | SESSION_USER | SOME | SYMMETRIC @@ -8280,7 +8261,6 @@ reserved_keyword: | TRUE_P | UNION | UNIQUE - | ROLE | USER | USING | WHEN diff --git a/src/backend/parser/keywords.c b/src/backend/parser/keywords.c index a11d4affc1df3ea385f0e476d6d8b06353589d6a..6fcb97675f629f98c40c791c83811b190cee07d3 100644 --- a/src/backend/parser/keywords.c +++ b/src/backend/parser/keywords.c @@ -8,7 +8,7 @@ * * * IDENTIFICATION - * $PostgreSQL: pgsql/src/backend/parser/keywords.c,v 1.160 2005/06/28 05:08:58 tgl Exp $ + * $PostgreSQL: pgsql/src/backend/parser/keywords.c,v 1.161 2005/06/28 19:51:22 tgl Exp $ * *------------------------------------------------------------------------- */ @@ -35,6 +35,7 @@ static const ScanKeyword ScanKeywords[] = { {"access", ACCESS}, {"action", ACTION}, {"add", ADD}, + {"admin", ADMIN}, {"after", AFTER}, {"aggregate", AGGREGATE}, {"all", ALL}, @@ -89,10 +90,12 @@ static const ScanKeyword ScanKeywords[] = { {"copy", COPY}, {"create", CREATE}, {"createdb", CREATEDB}, + {"createrole", CREATEROLE}, {"createuser", CREATEUSER}, {"cross", CROSS}, {"csv", CSV}, {"current_date", CURRENT_DATE}, + {"current_role", CURRENT_ROLE}, {"current_time", CURRENT_TIME}, {"current_timestamp", CURRENT_TIMESTAMP}, {"current_user", CURRENT_USER}, @@ -146,6 +149,7 @@ static const ScanKeyword ScanKeywords[] = { {"function", FUNCTION}, {"global", GLOBAL}, {"grant", GRANT}, + {"granted", GRANTED}, {"greatest", GREATEST}, {"group", GROUP_P}, {"handler", HANDLER}, @@ -197,6 +201,7 @@ static const ScanKeyword ScanKeywords[] = { {"localtimestamp", LOCALTIMESTAMP}, {"location", LOCATION}, {"lock", LOCK_P}, + {"login", LOGIN_P}, {"match", MATCH}, {"maxvalue", MAXVALUE}, {"minute", MINUTE_P}, @@ -212,7 +217,9 @@ static const ScanKeyword ScanKeywords[] = { {"next", NEXT}, {"no", NO}, {"nocreatedb", NOCREATEDB}, + {"nocreaterole", NOCREATEROLE}, {"nocreateuser", NOCREATEUSER}, + {"nologin", NOLOGIN_P}, {"none", NONE}, {"not", NOT}, {"nothing", NOTHING}, @@ -331,7 +338,6 @@ static const ScanKeyword ScanKeywords[] = { {"unlisten", UNLISTEN}, {"until", UNTIL}, {"update", UPDATE}, - {"usage", USAGE}, {"user", USER}, {"using", USING}, {"vacuum", VACUUM}, diff --git a/src/backend/utils/adt/acl.c b/src/backend/utils/adt/acl.c index 4d5904b76901dc4526a9d88feff36291ad1a7f63..2fe7fd39bcac787135d3c34fc7fefc620d890039 100644 --- a/src/backend/utils/adt/acl.c +++ b/src/backend/utils/adt/acl.c @@ -8,7 +8,7 @@ * * * IDENTIFICATION - * $PostgreSQL: pgsql/src/backend/utils/adt/acl.c,v 1.115 2005/06/28 05:09:00 tgl Exp $ + * $PostgreSQL: pgsql/src/backend/utils/adt/acl.c,v 1.116 2005/06/28 19:51:23 tgl Exp $ * *------------------------------------------------------------------------- */ @@ -2414,7 +2414,7 @@ convert_tablespace_priv_string(text *priv_type_text) } void -InitializeAcl(void) +initialize_acl(void) { if (!IsBootstrapProcessingMode()) { diff --git a/src/backend/utils/init/postinit.c b/src/backend/utils/init/postinit.c index 9baacacfffd9400341ead1dbb5869bcab58f23c5..21b0650e8278458a6cf457b4c6643a4359d4c937 100644 --- a/src/backend/utils/init/postinit.c +++ b/src/backend/utils/init/postinit.c @@ -8,7 +8,7 @@ * * * IDENTIFICATION - * $PostgreSQL: pgsql/src/backend/utils/init/postinit.c,v 1.150 2005/06/28 05:09:02 tgl Exp $ + * $PostgreSQL: pgsql/src/backend/utils/init/postinit.c,v 1.151 2005/06/28 19:51:23 tgl Exp $ * * *------------------------------------------------------------------------- @@ -471,7 +471,7 @@ InitPostgres(const char *dbname, const char *username) InitializeSearchPath(); /* set up ACL framework (currently just sets RolMemCache callback) */ - InitializeAcl(); + initialize_acl(); /* initialize client encoding */ InitializeClientEncoding(); diff --git a/src/include/nodes/parsenodes.h b/src/include/nodes/parsenodes.h index 64acaa72e57f5e169a7a0bcd395637c2dc649f82..32f9b03c585a243dd43651389f3ef86bc8299d3f 100644 --- a/src/include/nodes/parsenodes.h +++ b/src/include/nodes/parsenodes.h @@ -7,7 +7,7 @@ * Portions Copyright (c) 1996-2005, PostgreSQL Global Development Group * Portions Copyright (c) 1994, Regents of the University of California * - * $PostgreSQL: pgsql/src/include/nodes/parsenodes.h,v 1.284 2005/06/28 05:09:13 tgl Exp $ + * $PostgreSQL: pgsql/src/include/nodes/parsenodes.h,v 1.285 2005/06/28 19:51:24 tgl Exp $ * *------------------------------------------------------------------------- */ @@ -29,7 +29,7 @@ typedef enum QuerySource /* * Grantable rights are encoded so that we can OR them together in a bitmask. - * The present representation of AclItem limits us to 15 distinct rights, + * The present representation of AclItem limits us to 16 distinct rights, * even though AclMode is defined as uint32. See utils/acl.h. * * Caution: changing these codes breaks stored ACLs, hence forces initdb. @@ -48,7 +48,6 @@ typedef uint32 AclMode; /* a bitmask of privilege bits */ #define ACL_CREATE (1<<9) /* for namespaces and databases */ #define ACL_CREATE_TEMP (1<<10) /* for databases */ #define N_ACL_RIGHTS 11 /* 1 plus the last 1<<x */ -#define ACL_ALL_RIGHTS (-1) /* all-privileges marker in GRANT list */ #define ACL_NO_RIGHTS 0 /* Currently, SELECT ... FOR UPDATE/FOR SHARE requires UPDATE privileges */ #define ACL_SELECT_FOR_UPDATE ACL_UPDATE @@ -886,7 +885,8 @@ typedef struct GrantStmt List *objects; /* list of RangeVar nodes, FuncWithArgs * nodes, or plain names (as Value * strings) */ - List *privileges; /* integer list of privilege codes */ + List *privileges; /* list of privilege names (as Strings) */ + /* privileges == NIL denotes "all privileges" */ List *grantees; /* list of PrivGrantee nodes */ bool grant_option; /* grant or revoke grant option */ DropBehavior behavior; /* drop behavior (for REVOKE) */ diff --git a/src/include/storage/pmsignal.h b/src/include/storage/pmsignal.h index f82630ae2421c6960e7facad7b558c7294da8c39..d7956d94105153ac02ce6a53a76f5d1253b6955c 100644 --- a/src/include/storage/pmsignal.h +++ b/src/include/storage/pmsignal.h @@ -7,7 +7,7 @@ * Portions Copyright (c) 1996-2005, PostgreSQL Global Development Group * Portions Copyright (c) 1994, Regents of the University of California * - * $PostgreSQL: pgsql/src/include/storage/pmsignal.h,v 1.11 2004/12/31 22:03:42 pgsql Exp $ + * $PostgreSQL: pgsql/src/include/storage/pmsignal.h,v 1.12 2005/06/28 19:51:25 tgl Exp $ * *------------------------------------------------------------------------- */ @@ -22,7 +22,7 @@ */ typedef enum { - PMSIGNAL_PASSWORD_CHANGE, /* pg_pwd file has changed */ + PMSIGNAL_PASSWORD_CHANGE, /* pg_auth file has changed */ PMSIGNAL_WAKEN_CHILDREN, /* send a SIGUSR1 signal to all backends */ PMSIGNAL_WAKEN_ARCHIVER, /* send a NOTIFY signal to xlog archiver */ diff --git a/src/include/utils/acl.h b/src/include/utils/acl.h index f055ac93aa30c64650232c1777affda4676e1af1..82e004794bcfd380bad4a9f66fa5b316580d932b 100644 --- a/src/include/utils/acl.h +++ b/src/include/utils/acl.h @@ -7,7 +7,7 @@ * Portions Copyright (c) 1996-2005, PostgreSQL Global Development Group * Portions Copyright (c) 1994, Regents of the University of California * - * $PostgreSQL: pgsql/src/include/utils/acl.h,v 1.78 2005/06/28 05:09:13 tgl Exp $ + * $PostgreSQL: pgsql/src/include/utils/acl.h,v 1.79 2005/06/28 19:51:25 tgl Exp $ * * NOTES * An ACL array is simply an array of AclItems, representing the union @@ -211,7 +211,7 @@ extern AclMode aclmask(const Acl *acl, Oid roleid, Oid ownerId, extern bool is_member_of_role(Oid member, Oid role); -extern void InitializeAcl(void); +extern void initialize_acl(void); /* * SQL functions (from acl.c) diff --git a/src/test/regress/expected/rules.out b/src/test/regress/expected/rules.out index 47fc262c31569a4bc8898ac3f3e27ea10ba67ce4..41cc113b6dd7006584a752fc87fa9fa806899cd4 100644 --- a/src/test/regress/expected/rules.out +++ b/src/test/regress/expected/rules.out @@ -1279,7 +1279,7 @@ SELECT viewname, definition FROM pg_views WHERE schemaname <> 'information_schem iexit | SELECT ih.name, ih.thepath, interpt_pp(ih.thepath, r.thepath) AS exit FROM ihighway ih, ramp r WHERE (ih.thepath ## r.thepath); pg_group | SELECT pg_authid.rolname AS groname, pg_authid.oid AS grosysid, ARRAY(SELECT pg_auth_members.member FROM pg_auth_members WHERE (pg_auth_members.roleid = pg_authid.oid)) AS grolist FROM pg_authid WHERE (NOT pg_authid.rolcanlogin); pg_indexes | SELECT n.nspname AS schemaname, c.relname AS tablename, i.relname AS indexname, t.spcname AS "tablespace", pg_get_indexdef(i.oid) AS indexdef FROM ((((pg_index x JOIN pg_class c ON ((c.oid = x.indrelid))) JOIN pg_class i ON ((i.oid = x.indexrelid))) LEFT JOIN pg_namespace n ON ((n.oid = c.relnamespace))) LEFT JOIN pg_tablespace t ON ((t.oid = i.reltablespace))) WHERE ((c.relkind = 'r'::"char") AND (i.relkind = 'i'::"char")); - pg_locks | SELECT l.locktype, l."database", l.relation, l.page, l.tuple, l.transactionid, l.classid, l.objid, l.objsubid, l."transaction", l.pid, l."mode", l.granted FROM pg_lock_status() l(locktype text, "database" oid, relation oid, page integer, tuple smallint, transactionid xid, classid oid, objid oid, objsubid smallint, "transaction" xid, pid integer, "mode" text, granted boolean); + pg_locks | SELECT l.locktype, l."database", l.relation, l.page, l.tuple, l.transactionid, l.classid, l.objid, l.objsubid, l."transaction", l.pid, l."mode", l."granted" FROM pg_lock_status() l(locktype text, "database" oid, relation oid, page integer, tuple smallint, transactionid xid, classid oid, objid oid, objsubid smallint, "transaction" xid, pid integer, "mode" text, "granted" boolean); pg_prepared_xacts | SELECT p."transaction", p.gid, p."prepared", u.rolname AS "owner", d.datname AS "database" FROM ((pg_prepared_xact() p("transaction" xid, gid text, "prepared" timestamp with time zone, ownerid oid, dbid oid) LEFT JOIN pg_authid u ON ((p.ownerid = u.oid))) LEFT JOIN pg_database d ON ((p.dbid = d.oid))); pg_roles | SELECT pg_authid.rolname, pg_authid.rolsuper, pg_authid.rolcreaterole, pg_authid.rolcreatedb, pg_authid.rolcatupdate, pg_authid.rolcanlogin, '********'::text AS rolpassword, pg_authid.rolvaliduntil, pg_authid.rolconfig FROM pg_authid; pg_rules | SELECT n.nspname AS schemaname, c.relname AS tablename, r.rulename, pg_get_ruledef(r.oid) AS definition FROM ((pg_rewrite r JOIN pg_class c ON ((c.oid = r.ev_class))) LEFT JOIN pg_namespace n ON ((n.oid = c.relnamespace))) WHERE (r.rulename <> '_RETURN'::name);