From 6dc249610a87aa8b9dcc8baf4e64d2e14d02f548 Mon Sep 17 00:00:00 2001
From: Peter Eisentraut <peter_e@gmx.net>
Date: Wed, 6 Sep 2000 14:15:31 +0000
Subject: [PATCH] Code cleanup of user name and user id handling in the
 backend. The current user is now defined in terms of the user id, the user
 name is only computed upon request (for display purposes). This is kind of
 the opposite of the previous state, which would maintain the user name and
 compute the user id for permission checks.

Besides perhaps saving a few cycles (integer vs string), this now creates a
single point of attack for changing the user id during a connection, for
purposes of "setuid" functions, etc.
---
 src/backend/bootstrap/bootstrap.c    |  4 +-
 src/backend/catalog/aclchk.c         | 77 ++++++++++++++--------------
 src/backend/commands/analyze.c       |  4 +-
 src/backend/commands/command.c       | 16 +++---
 src/backend/commands/comment.c       | 44 ++++++----------
 src/backend/commands/copy.c          |  5 +-
 src/backend/commands/dbcommands.c    | 25 ++++-----
 src/backend/commands/indexcmds.c     | 20 ++------
 src/backend/commands/remove.c        | 18 ++-----
 src/backend/commands/rename.c        |  7 ++-
 src/backend/commands/sequence.c      |  6 +--
 src/backend/commands/trigger.c       |  6 +--
 src/backend/commands/vacuum.c        |  4 +-
 src/backend/executor/execMain.c      | 12 ++---
 src/backend/main/main.c              | 18 +++++--
 src/backend/postmaster/postmaster.c  | 18 +++----
 src/backend/rewrite/locks.c          |  6 +--
 src/backend/rewrite/rewriteHandler.c |  4 +-
 src/backend/tcop/postgres.c          | 39 ++++++--------
 src/backend/tcop/utility.c           | 26 ++++------
 src/backend/utils/init/globals.c     |  3 +-
 src/backend/utils/init/miscinit.c    | 74 ++++++++++----------------
 src/backend/utils/init/postinit.c    | 23 +++++----
 src/backend/utils/misc/superuser.c   |  6 +--
 src/include/commands/rename.h        |  4 +-
 src/include/miscadmin.h              | 12 ++---
 src/include/tcop/tcopprot.h          |  4 +-
 src/include/utils/acl.h              | 10 ++--
 28 files changed, 217 insertions(+), 278 deletions(-)

diff --git a/src/backend/bootstrap/bootstrap.c b/src/backend/bootstrap/bootstrap.c
index 2eacad23dc3..1620839e9ac 100644
--- a/src/backend/bootstrap/bootstrap.c
+++ b/src/backend/bootstrap/bootstrap.c
@@ -8,7 +8,7 @@
  * Portions Copyright (c) 1994, Regents of the University of California
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/bootstrap/bootstrap.c,v 1.92 2000/08/03 19:19:06 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/bootstrap/bootstrap.c,v 1.93 2000/09/06 14:15:14 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -355,7 +355,7 @@ BootstrapMain(int argc, char *argv[])
 	/*
 	 * backend initialization
 	 */
-	InitPostgres(dbName);
+	InitPostgres(dbName, NULL);
 	LockDisable(true);
 
 	if (IsUnderPostmaster && !xloginit)
diff --git a/src/backend/catalog/aclchk.c b/src/backend/catalog/aclchk.c
index 6be489a0c74..b5c9cf51a1b 100644
--- a/src/backend/catalog/aclchk.c
+++ b/src/backend/catalog/aclchk.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/catalog/aclchk.c,v 1.39 2000/07/31 22:39:13 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/catalog/aclchk.c,v 1.40 2000/09/06 14:15:15 petere Exp $
  *
  * NOTES
  *	  See acl.h.
@@ -355,21 +355,22 @@ aclcheck(char *relname, Acl *acl, AclId id, AclIdType idtype, AclMode mode)
 }
 
 int32
-pg_aclcheck(char *relname, char *usename, AclMode mode)
+pg_aclcheck(char *relname, Oid userid, AclMode mode)
 {
 	HeapTuple	tuple;
-	AclId		id;
 	Acl		   *acl = (Acl *) NULL;
 	int32		result;
+	char       *usename;
 	Relation	relation;
 
-	tuple = SearchSysCacheTuple(SHADOWNAME,
-								PointerGetDatum(usename),
+	tuple = SearchSysCacheTuple(SHADOWSYSID,
+								ObjectIdGetDatum(userid),
 								0, 0, 0);
 	if (!HeapTupleIsValid(tuple))
-		elog(ERROR, "pg_aclcheck: user \"%s\" not found",
-			 usename);
-	id = (AclId) ((Form_pg_shadow) GETSTRUCT(tuple))->usesysid;
+		elog(ERROR, "pg_aclcheck: invalid user id %u",
+			 (unsigned) userid);
+
+	usename = NameStr(((Form_pg_shadow) GETSTRUCT(tuple))->usename);
 
 	/*
 	 * Deny anyone permission to update a system catalog unless
@@ -445,28 +446,28 @@ pg_aclcheck(char *relname, char *usename, AclMode mode)
 	}
 	heap_close(relation, RowExclusiveLock);
 #endif
-	result = aclcheck(relname, acl, id, (AclIdType) ACL_IDTYPE_UID, mode);
+	result = aclcheck(relname, acl, userid, (AclIdType) ACL_IDTYPE_UID, mode);
 	if (acl)
 		pfree(acl);
 	return result;
 }
 
 int32
-pg_ownercheck(const char *usename,
+pg_ownercheck(Oid userid,
 			  const char *value,
 			  int cacheid)
 {
 	HeapTuple	tuple;
-	AclId		user_id,
-				owner_id = 0;
+	AclId		owner_id = 0;
+	char       *usename;
 
-	tuple = SearchSysCacheTuple(SHADOWNAME,
-								PointerGetDatum(usename),
+	tuple = SearchSysCacheTuple(SHADOWSYSID,
+								ObjectIdGetDatum(userid),
 								0, 0, 0);
 	if (!HeapTupleIsValid(tuple))
-		elog(ERROR, "pg_ownercheck: user \"%s\" not found",
-			 usename);
-	user_id = (AclId) ((Form_pg_shadow) GETSTRUCT(tuple))->usesysid;
+		elog(ERROR, "pg_ownercheck: invalid user id %u",
+			 (unsigned) userid);
+	usename = NameStr(((Form_pg_shadow) GETSTRUCT(tuple))->usename);
 
 	/*
 	 * Superusers bypass all permission-checking.
@@ -513,26 +514,26 @@ pg_ownercheck(const char *usename,
 			break;
 	}
 
-	return user_id == owner_id;
+	return userid == owner_id;
 }
 
 int32
-pg_func_ownercheck(char *usename,
+pg_func_ownercheck(Oid userid,
 				   char *funcname,
 				   int nargs,
 				   Oid *arglist)
 {
 	HeapTuple	tuple;
-	AclId		user_id,
-				owner_id;
+	AclId		owner_id;
+	char *username;
 
-	tuple = SearchSysCacheTuple(SHADOWNAME,
-								PointerGetDatum(usename),
+	tuple = SearchSysCacheTuple(SHADOWSYSID,
+								ObjectIdGetDatum(userid),
 								0, 0, 0);
 	if (!HeapTupleIsValid(tuple))
-		elog(ERROR, "pg_func_ownercheck: user \"%s\" not found",
-			 usename);
-	user_id = (AclId) ((Form_pg_shadow) GETSTRUCT(tuple))->usesysid;
+		elog(ERROR, "pg_func_ownercheck: invalid user id %u",
+			 (unsigned) userid);
+	username = NameStr(((Form_pg_shadow) GETSTRUCT(tuple))->usename);
 
 	/*
 	 * Superusers bypass all permission-checking.
@@ -541,7 +542,7 @@ pg_func_ownercheck(char *usename,
 	{
 #ifdef ACLDEBUG_TRACE
 		elog(DEBUG, "pg_ownercheck: user \"%s\" is superuser",
-			 usename);
+			 username);
 #endif
 		return 1;
 	}
@@ -556,25 +557,25 @@ pg_func_ownercheck(char *usename,
 
 	owner_id = ((Form_pg_proc) GETSTRUCT(tuple))->proowner;
 
-	return user_id == owner_id;
+	return userid == owner_id;
 }
 
 int32
-pg_aggr_ownercheck(char *usename,
+pg_aggr_ownercheck(Oid userid,
 				   char *aggname,
 				   Oid basetypeID)
 {
 	HeapTuple	tuple;
-	AclId		user_id,
-				owner_id;
+	AclId		owner_id;
+	char *username;
 
-	tuple = SearchSysCacheTuple(SHADOWNAME,
-								PointerGetDatum(usename),
+	tuple = SearchSysCacheTuple(SHADOWSYSID,
+								PointerGetDatum(userid),
 								0, 0, 0);
 	if (!HeapTupleIsValid(tuple))
-		elog(ERROR, "pg_aggr_ownercheck: user \"%s\" not found",
-			 usename);
-	user_id = (AclId) ((Form_pg_shadow) GETSTRUCT(tuple))->usesysid;
+		elog(ERROR, "pg_aggr_ownercheck: invalid user id %u",
+			 (unsigned) userid);
+	username = NameStr(((Form_pg_shadow) GETSTRUCT(tuple))->usename);
 
 	/*
 	 * Superusers bypass all permission-checking.
@@ -583,7 +584,7 @@ pg_aggr_ownercheck(char *usename,
 	{
 #ifdef ACLDEBUG_TRACE
 		elog(DEBUG, "pg_aggr_ownercheck: user \"%s\" is superuser",
-			 usename);
+			 username);
 #endif
 		return 1;
 	}
@@ -598,5 +599,5 @@ pg_aggr_ownercheck(char *usename,
 
 	owner_id = ((Form_pg_aggregate) GETSTRUCT(tuple))->aggowner;
 
-	return user_id == owner_id;
+	return userid == owner_id;
 }
diff --git a/src/backend/commands/analyze.c b/src/backend/commands/analyze.c
index 1747132f8a7..048d4b1df9d 100644
--- a/src/backend/commands/analyze.c
+++ b/src/backend/commands/analyze.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/commands/analyze.c,v 1.5 2000/08/21 17:22:32 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/commands/analyze.c,v 1.6 2000/09/06 14:15:16 petere Exp $
  *
 
  *-------------------------------------------------------------------------
@@ -99,7 +99,7 @@ analyze_rel(Oid relid, List *anal_cols2, int MESSAGE_LEVEL)
 	onerel = heap_open(relid, AccessShareLock);
 
 #ifndef NO_SECURITY
-	if (!pg_ownercheck(GetPgUserName(), RelationGetRelationName(onerel),
+	if (!pg_ownercheck(GetUserId(), RelationGetRelationName(onerel),
 					   RELNAME))
 	{
 		/* we already did an elog during vacuum
diff --git a/src/backend/commands/command.c b/src/backend/commands/command.c
index 97b3563d9fc..054b76e480d 100644
--- a/src/backend/commands/command.c
+++ b/src/backend/commands/command.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/commands/Attic/command.c,v 1.97 2000/08/29 04:20:43 momjian Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/commands/Attic/command.c,v 1.98 2000/09/06 14:15:16 petere Exp $
  *
  * NOTES
  *	  The PerformAddAttribute() code, like most of the relation
@@ -308,7 +308,7 @@ AlterTableAddColumn(const char *relationName,
 		elog(ERROR, "ALTER TABLE: relation \"%s\" is a system catalog",
 			 relationName);
 #ifndef NO_SECURITY
-	if (!pg_ownercheck(UserName, relationName, RELNAME))
+	if (!pg_ownercheck(GetUserId(), relationName, RELNAME))
 		elog(ERROR, "ALTER TABLE: permission denied");
 #endif
 
@@ -523,7 +523,7 @@ AlterTableAlterColumn(const char *relationName,
 		elog(ERROR, "ALTER TABLE: relation \"%s\" is a system catalog",
 			 relationName);
 #ifndef NO_SECURITY
-	if (!pg_ownercheck(UserName, relationName, RELNAME))
+	if (!pg_ownercheck(GetUserId(), relationName, RELNAME))
 		elog(ERROR, "ALTER TABLE: permission denied");
 #endif
 
@@ -935,7 +935,7 @@ AlterTableDropColumn(const char *relationName,
 		elog(ERROR, "ALTER TABLE: relation \"%s\" is a system catalog",
 			 relationName);
 #ifndef NO_SECURITY
-	if (!pg_ownercheck(UserName, relationName, RELNAME))
+	if (!pg_ownercheck(GetUserId(), relationName, RELNAME))
 		elog(ERROR, "ALTER TABLE: permission denied");
 #endif
 
@@ -1095,7 +1095,7 @@ AlterTableAddConstraint(char *relationName,
 		elog(ERROR, "ALTER TABLE / ADD CONSTRAINT passed invalid constraint.");
 
 #ifndef NO_SECURITY
-	if (!pg_ownercheck(UserName, relationName, RELNAME))
+	if (!pg_ownercheck(GetUserId(), relationName, RELNAME))
 		elog(ERROR, "ALTER TABLE: permission denied");
 #endif
 
@@ -1484,7 +1484,7 @@ AlterTableCreateToastTable(const char *relationName, bool silent)
 	 * permissions checking.  XXX exactly what is appropriate here?
 	 */
 #ifndef NO_SECURITY
-	if (!pg_ownercheck(UserName, relationName, RELNAME))
+	if (!pg_ownercheck(GetUserId(), relationName, RELNAME))
 		elog(ERROR, "ALTER TABLE: permission denied");
 #endif
 
@@ -1723,9 +1723,9 @@ LockTableCommand(LockStmt *lockstmt)
 	rel = heap_openr(lockstmt->relname, NoLock);
 
 	if (lockstmt->mode == AccessShareLock)
-		aclresult = pg_aclcheck(lockstmt->relname, GetPgUserName(), ACL_RD);
+		aclresult = pg_aclcheck(lockstmt->relname, GetUserId(), ACL_RD);
 	else
-		aclresult = pg_aclcheck(lockstmt->relname, GetPgUserName(), ACL_WR);
+		aclresult = pg_aclcheck(lockstmt->relname, GetUserId(), ACL_WR);
 
 	if (aclresult != ACLCHECK_OK)
 		elog(ERROR, "LOCK TABLE: permission denied");
diff --git a/src/backend/commands/comment.c b/src/backend/commands/comment.c
index c76912f332a..87c7d84727d 100644
--- a/src/backend/commands/comment.c
+++ b/src/backend/commands/comment.c
@@ -281,7 +281,7 @@ CommentRelation(int reltype, char *relname, char *comment)
 	/*** First, check object security ***/
 
 #ifndef NO_SECURITY
-	if (!pg_ownercheck(GetPgUserName(), relname, RELNAME))
+	if (!pg_ownercheck(GetUserId(), relname, RELNAME))
 		elog(ERROR, "you are not permitted to comment on class '%s'", relname);
 #endif
 
@@ -347,7 +347,7 @@ CommentAttribute(char *relname, char *attrname, char *comment)
 	/*** First, check object security ***/
 
 #ifndef NO_SECURITY
-	if (!pg_ownercheck(GetPgUserName(), relname, RELNAME))
+	if (!pg_ownercheck(GetUserId(), relname, RELNAME))
 		elog(ERROR, "you are not permitted to comment on class '%s\'", relname);
 #endif
 
@@ -395,9 +395,8 @@ CommentDatabase(char *database, char *comment)
 	HeapScanDesc scan;
 	Oid			oid;
 	bool		superuser;
-	int4		dba,
-				userid;
-	char	   *username;
+	int4		dba;
+	Oid		userid;
 
 	/*** First find the tuple in pg_database for the database ***/
 
@@ -416,12 +415,11 @@ CommentDatabase(char *database, char *comment)
 
 	/*** Now, fetch user information ***/
 
-	username = GetPgUserName();
-	usertuple = SearchSysCacheTuple(SHADOWNAME, PointerGetDatum(username),
+	userid = GetUserId();
+	usertuple = SearchSysCacheTuple(SHADOWSYSID, ObjectIdGetDatum(userid),
 									0, 0, 0);
 	if (!HeapTupleIsValid(usertuple))
-		elog(ERROR, "current user '%s' does not exist", username);
-	userid = ((Form_pg_shadow) GETSTRUCT(usertuple))->usesysid;
+		elog(ERROR, "invalid user id %u", (unsigned) userid);
 	superuser = ((Form_pg_shadow) GETSTRUCT(usertuple))->usesuper;
 
 	/*** Allow if the userid matches the database dba or is a superuser ***/
@@ -461,16 +459,14 @@ CommentRewrite(char *rule, char *comment)
 
 	HeapTuple	rewritetuple;
 	Oid			oid;
-	char	   *user,
-			   *relation;
+	char	   *relation;
 	int			aclcheck;
 
 	/*** First, validate user ***/
 
 #ifndef NO_SECURITY
-	user = GetPgUserName();
 	relation = RewriteGetRuleEventRel(rule);
-	aclcheck = pg_aclcheck(relation, user, ACL_RU);
+	aclcheck = pg_aclcheck(relation, GetUserId(), ACL_RU);
 	if (aclcheck != ACLCHECK_OK)
 	{
 		elog(ERROR, "you are not permitted to comment on rule '%s'",
@@ -510,13 +506,11 @@ CommentType(char *type, char *comment)
 
 	HeapTuple	typetuple;
 	Oid			oid;
-	char	   *user;
 
 	/*** First, validate user ***/
 
 #ifndef NO_SECURITY
-	user = GetPgUserName();
-	if (!pg_ownercheck(user, type, TYPENAME))
+	if (!pg_ownercheck(GetUserId(), type, TYPENAME))
 	{
 		elog(ERROR, "you are not permitted to comment on type '%s'",
 			 type);
@@ -556,7 +550,6 @@ CommentAggregate(char *aggregate, char *argument, char *comment)
 	Oid			baseoid,
 				oid;
 	bool		defined;
-	char	   *user;
 
 	/*** First, attempt to determine the base aggregate oid ***/
 
@@ -572,8 +565,7 @@ CommentAggregate(char *aggregate, char *argument, char *comment)
 	/*** Next, validate the user's attempt to comment ***/
 
 #ifndef NO_SECURITY
-	user = GetPgUserName();
-	if (!pg_aggr_ownercheck(user, aggregate, baseoid))
+	if (!pg_aggr_ownercheck(GetUserId(), aggregate, baseoid))
 	{
 		if (argument)
 		{
@@ -629,8 +621,7 @@ CommentProc(char *function, List *arguments, char *comment)
 				functuple;
 	Oid			oid,
 				argoids[FUNC_MAX_ARGS];
-	char	   *user,
-			   *argument;
+	char	   *argument;
 	int			i,
 				argcount;
 
@@ -662,8 +653,7 @@ CommentProc(char *function, List *arguments, char *comment)
 	/*** Now, validate the user's ability to comment on this function ***/
 
 #ifndef NO_SECURITY
-	user = GetPgUserName();
-	if (!pg_func_ownercheck(user, function, argcount, argoids))
+	if (!pg_func_ownercheck(GetUserId(), function, argcount, argoids))
 		elog(ERROR, "you are not permitted to comment on function '%s'",
 			 function);
 #endif
@@ -708,7 +698,6 @@ CommentOperator(char *opername, List *arguments, char *comment)
 				rightoid = InvalidOid;
 	bool		defined;
 	char		oprtype = 0,
-			   *user,
 			   *lefttype = NULL,
 			   *righttype = NULL;
 
@@ -762,8 +751,7 @@ CommentOperator(char *opername, List *arguments, char *comment)
 	/*** Valid user's ability to comment on this operator ***/
 
 #ifndef NO_SECURITY
-	user = GetPgUserName();
-	if (!pg_ownercheck(user, (char *) ObjectIdGetDatum(oid), OPEROID))
+	if (!pg_ownercheck(GetUserId(), (char *) ObjectIdGetDatum(oid), OPEROID))
 	{
 		elog(ERROR, "you are not permitted to comment on operator '%s'",
 			 opername);
@@ -805,13 +793,11 @@ CommentTrigger(char *trigger, char *relname, char *comment)
 	HeapScanDesc scan;
 	ScanKeyData entry;
 	Oid			oid = InvalidOid;
-	char	   *user;
 
 	/*** First, validate the user's action ***/
 
 #ifndef NO_SECURITY
-	user = GetPgUserName();
-	if (!pg_ownercheck(user, relname, RELNAME))
+	if (!pg_ownercheck(GetUserId(), relname, RELNAME))
 	{
 		elog(ERROR, "you are not permitted to comment on trigger '%s' %s '%s'",
 			 trigger, "defined for relation", relname);
diff --git a/src/backend/commands/copy.c b/src/backend/commands/copy.c
index 4b81a35c122..ea90e0f2e04 100644
--- a/src/backend/commands/copy.c
+++ b/src/backend/commands/copy.c
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/commands/copy.c,v 1.121 2000/08/22 04:06:21 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/commands/copy.c,v 1.122 2000/09/06 14:15:16 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -272,7 +272,6 @@ DoCopy(char *relname, bool binary, bool oids, bool from, bool pipe,
 
 	FILE	   *fp;
 	Relation	rel;
-	extern char *UserName;		/* defined in global.c */
 	const AclMode required_access = from ? ACL_WR : ACL_RD;
 	int			result;
 
@@ -281,7 +280,7 @@ DoCopy(char *relname, bool binary, bool oids, bool from, bool pipe,
 	 */
 	rel = heap_openr(relname, (from ? RowExclusiveLock : AccessShareLock));
 
-	result = pg_aclcheck(relname, UserName, required_access);
+	result = pg_aclcheck(relname, GetUserId(), required_access);
 	if (result != ACLCHECK_OK)
 		elog(ERROR, "%s: %s", relname, aclcheck_error_strings[result]);
 	if (!pipe && !superuser())
diff --git a/src/backend/commands/dbcommands.c b/src/backend/commands/dbcommands.c
index 1c2df9c5eb8..f320979af99 100644
--- a/src/backend/commands/dbcommands.c
+++ b/src/backend/commands/dbcommands.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/commands/dbcommands.c,v 1.59 2000/08/03 16:34:01 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/commands/dbcommands.c,v 1.60 2000/09/06 14:15:16 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -37,7 +37,7 @@
 
 /* non-export function prototypes */
 static bool
-			get_user_info(const char *name, int4 *use_sysid, bool *use_super, bool *use_createdb);
+			get_user_info(Oid use_sysid, bool *use_super, bool *use_createdb);
 
 static bool
 			get_db_info(const char *name, char *dbpath, Oid *dbIdP, int4 *ownerIdP);
@@ -54,7 +54,6 @@ createdb(const char *dbname, const char *dbpath, int encoding)
 	char		buf[2 * MAXPGPATH + 100];
 	char	   *loc;
 	char		locbuf[512];
-	int4		user_id;
 	int			ret;
 	bool		use_super,
 				use_createdb;
@@ -64,7 +63,7 @@ createdb(const char *dbname, const char *dbpath, int encoding)
 	Datum		new_record[Natts_pg_database];
 	char		new_record_nulls[Natts_pg_database] = {' ', ' ', ' ', ' '};
 
-	if (!get_user_info(GetPgUserName(), &user_id, &use_super, &use_createdb))
+	if (!get_user_info(GetUserId(), &use_super, &use_createdb))
 		elog(ERROR, "current user name is invalid");
 
 	if (!use_createdb && !use_super)
@@ -100,7 +99,7 @@ createdb(const char *dbname, const char *dbpath, int encoding)
 	/* Form tuple */
 	new_record[Anum_pg_database_datname - 1] = DirectFunctionCall1(namein,
 													CStringGetDatum(dbname));
-	new_record[Anum_pg_database_datdba - 1] = Int32GetDatum(user_id);
+	new_record[Anum_pg_database_datdba - 1] = Int32GetDatum(GetUserId());
 	new_record[Anum_pg_database_encoding - 1] = Int32GetDatum(encoding);
 	new_record[Anum_pg_database_datpath - 1] = DirectFunctionCall1(textin,
 													CStringGetDatum(locbuf));
@@ -174,8 +173,7 @@ createdb(const char *dbname, const char *dbpath, int encoding)
 void
 dropdb(const char *dbname)
 {
-	int4		user_id,
-				db_owner;
+	int4		db_owner;
 	bool		use_super;
 	Oid			db_id;
 	char	   *path,
@@ -197,13 +195,13 @@ dropdb(const char *dbname)
 	if (IsTransactionBlock())
 		elog(ERROR, "DROP DATABASE: May not be called in a transaction block");
 
-	if (!get_user_info(GetPgUserName(), &user_id, &use_super, NULL))
+	if (!get_user_info(GetUserId(), &use_super, NULL))
 		elog(ERROR, "Current user name is invalid");
 
 	if (!get_db_info(dbname, dbpath, &db_id, &db_owner))
 		elog(ERROR, "DROP DATABASE: Database \"%s\" does not exist", dbname);
 
-	if (user_id != db_owner && !use_super)
+	if (GetUserId() != db_owner && !use_super)
 		elog(ERROR, "DROP DATABASE: Permission denied");
 
 	path = ExpandDatabasePath(dbpath);
@@ -374,20 +372,17 @@ get_db_info(const char *name, char *dbpath, Oid *dbIdP, int4 *ownerIdP)
 
 
 static bool
-get_user_info(const char *name, int4 *use_sysid, bool *use_super, bool *use_createdb)
+get_user_info(Oid use_sysid, bool *use_super, bool *use_createdb)
 {
 	HeapTuple	utup;
 
-	AssertArg(name);
-	utup = SearchSysCacheTuple(SHADOWNAME,
-							   PointerGetDatum(name),
+	utup = SearchSysCacheTuple(SHADOWSYSID,
+							   ObjectIdGetDatum(use_sysid),
 							   0, 0, 0);
 
 	if (!HeapTupleIsValid(utup))
 		return false;
 
-	if (use_sysid)
-		*use_sysid = ((Form_pg_shadow) GETSTRUCT(utup))->usesysid;
 	if (use_super)
 		*use_super = ((Form_pg_shadow) GETSTRUCT(utup))->usesuper;
 	if (use_createdb)
diff --git a/src/backend/commands/indexcmds.c b/src/backend/commands/indexcmds.c
index 0fb1129f731..64cdf840f06 100644
--- a/src/backend/commands/indexcmds.c
+++ b/src/backend/commands/indexcmds.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/commands/indexcmds.c,v 1.37 2000/08/20 00:44:19 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/commands/indexcmds.c,v 1.38 2000/09/06 14:15:16 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -697,15 +697,11 @@ ReindexDatabase(const char *dbname, bool force, bool all)
 {
 	Relation	relation,
 				relationRelation;
-	HeapTuple	usertuple,
-				dbtuple,
+	HeapTuple	dbtuple,
 				tuple;
 	HeapScanDesc scan;
-	int4		user_id,
-				db_owner;
-	bool		superuser;
+	int4		db_owner;
 	Oid			db_id;
-	char	   *username;
 	ScanKeyData scankey;
 	MemoryContext private_context;
 	MemoryContext old;
@@ -717,14 +713,6 @@ ReindexDatabase(const char *dbname, bool force, bool all)
 
 	AssertArg(dbname);
 
-	username = GetPgUserName();
-	usertuple = SearchSysCacheTuple(SHADOWNAME, PointerGetDatum(username),
-									0, 0, 0);
-	if (!HeapTupleIsValid(usertuple))
-		elog(ERROR, "Current user \"%s\" is invalid.", username);
-	user_id = ((Form_pg_shadow) GETSTRUCT(usertuple))->usesysid;
-	superuser = ((Form_pg_shadow) GETSTRUCT(usertuple))->usesuper;
-
 	relation = heap_openr(DatabaseRelationName, AccessShareLock);
 	ScanKeyEntryInitialize(&scankey, 0, Anum_pg_database_datname,
 						   F_NAMEEQ, NameGetDatum(dbname));
@@ -737,7 +725,7 @@ ReindexDatabase(const char *dbname, bool force, bool all)
 	heap_endscan(scan);
 	heap_close(relation, NoLock);
 
-	if (user_id != db_owner && !superuser)
+	if (GetUserId() != db_owner && !superuser())
 		elog(ERROR, "REINDEX DATABASE: Permission denied.");
 
 	if (db_id != MyDatabaseId)
diff --git a/src/backend/commands/remove.c b/src/backend/commands/remove.c
index 75f3356289d..f0958ab393c 100644
--- a/src/backend/commands/remove.c
+++ b/src/backend/commands/remove.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/commands/Attic/remove.c,v 1.50 2000/07/04 06:11:29 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/commands/Attic/remove.c,v 1.51 2000/09/06 14:15:16 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -47,7 +47,6 @@ RemoveOperator(char *operatorName,		/* operator name */
 	Oid			typeId1 = InvalidOid;
 	Oid			typeId2 = InvalidOid;
 	bool		defined;
-	char	   *userName;
 	char		oprtype;
 
 	if (typeName1)
@@ -88,8 +87,7 @@ RemoveOperator(char *operatorName,		/* operator name */
 	if (HeapTupleIsValid(tup))
 	{
 #ifndef NO_SECURITY
-		userName = GetPgUserName();
-		if (!pg_ownercheck(userName,
+		if (!pg_ownercheck(GetUserId(),
 						   (char *) ObjectIdGetDatum(tup->t_data->t_oid),
 						   OPEROID))
 			elog(ERROR, "RemoveOperator: operator '%s': permission denied",
@@ -257,11 +255,9 @@ RemoveType(char *typeName)		/* type name to be removed */
 	HeapTuple	tup;
 	Oid			typeOid;
 	char	   *shadow_type;
-	char	   *userName;
 
 #ifndef NO_SECURITY
-	userName = GetPgUserName();
-	if (!pg_ownercheck(userName, typeName, TYPENAME))
+	if (!pg_ownercheck(GetUserId(), typeName, TYPENAME))
 		elog(ERROR, "RemoveType: type '%s': permission denied",
 			 typeName);
 #endif
@@ -318,7 +314,6 @@ RemoveFunction(char *functionName,		/* function name to be removed */
 	Relation	relation;
 	HeapTuple	tup;
 	Oid			argList[FUNC_MAX_ARGS];
-	char	   *userName;
 	char	   *typename;
 	int			i;
 
@@ -346,8 +341,7 @@ RemoveFunction(char *functionName,		/* function name to be removed */
 	}
 
 #ifndef NO_SECURITY
-	userName = GetPgUserName();
-	if (!pg_func_ownercheck(userName, functionName, nargs, argList))
+	if (!pg_func_ownercheck(GetUserId(), functionName, nargs, argList))
 	{
 		elog(ERROR, "RemoveFunction: function '%s': permission denied",
 			 functionName);
@@ -388,7 +382,6 @@ RemoveAggregate(char *aggName, char *aggType)
 {
 	Relation	relation;
 	HeapTuple	tup;
-	char	   *userName;
 	Oid			basetypeID = InvalidOid;
 	bool		defined;
 
@@ -413,8 +406,7 @@ RemoveAggregate(char *aggName, char *aggType)
 		basetypeID = 0;
 
 #ifndef NO_SECURITY
-	userName = GetPgUserName();
-	if (!pg_aggr_ownercheck(userName, aggName, basetypeID))
+	if (!pg_aggr_ownercheck(GetUserId(), aggName, basetypeID))
 	{
 		if (aggType)
 		{
diff --git a/src/backend/commands/rename.c b/src/backend/commands/rename.c
index 2daebf7c5e1..0519df323da 100644
--- a/src/backend/commands/rename.c
+++ b/src/backend/commands/rename.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/commands/Attic/rename.c,v 1.46 2000/06/20 06:41:13 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/commands/Attic/rename.c,v 1.47 2000/09/06 14:15:16 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -53,7 +53,6 @@ void
 renameatt(char *relname,
 		  char *oldattname,
 		  char *newattname,
-		  char *userName,
 		  int recurse)
 {
 	Relation	targetrelation;
@@ -74,7 +73,7 @@ renameatt(char *relname,
 			 relname);
 #ifndef NO_SECURITY
 	if (!IsBootstrapProcessingMode() &&
-		!pg_ownercheck(userName, relname, RELNAME))
+		!pg_ownercheck(GetUserId(), relname, RELNAME))
 		elog(ERROR, "renameatt: you do not own class \"%s\"",
 			 relname);
 #endif
@@ -129,7 +128,7 @@ renameatt(char *relname,
 					NameStr(((Form_pg_class) GETSTRUCT(reltup))->relname),
 					NAMEDATALEN);
 			/* note we need not recurse again! */
-			renameatt(childname, oldattname, newattname, userName, 0);
+			renameatt(childname, oldattname, newattname, 0);
 		}
 	}
 
diff --git a/src/backend/commands/sequence.c b/src/backend/commands/sequence.c
index f528abed752..d623c0630e0 100644
--- a/src/backend/commands/sequence.c
+++ b/src/backend/commands/sequence.c
@@ -201,7 +201,7 @@ nextval(PG_FUNCTION_ARGS)
 				rescnt = 0;
 
 #ifndef NO_SECURITY
-	if (pg_aclcheck(seqname, GetPgUserName(), ACL_WR) != ACLCHECK_OK)
+	if (pg_aclcheck(seqname, GetUserId(), ACL_WR) != ACLCHECK_OK)
 		elog(ERROR, "%s.nextval: you don't have permissions to set sequence %s",
 			 seqname, seqname);
 #endif
@@ -298,7 +298,7 @@ currval(PG_FUNCTION_ARGS)
 	int32		result;
 
 #ifndef NO_SECURITY
-	if (pg_aclcheck(seqname, GetPgUserName(), ACL_RD) != ACLCHECK_OK)
+	if (pg_aclcheck(seqname, GetUserId(), ACL_RD) != ACLCHECK_OK)
 		elog(ERROR, "%s.currval: you don't have permissions to read sequence %s",
 			 seqname, seqname);
 #endif
@@ -328,7 +328,7 @@ setval(PG_FUNCTION_ARGS)
 	Form_pg_sequence seq;
 
 #ifndef NO_SECURITY
-	if (pg_aclcheck(seqname, GetPgUserName(), ACL_WR) != ACLCHECK_OK)
+	if (pg_aclcheck(seqname, GetUserId(), ACL_WR) != ACLCHECK_OK)
 		elog(ERROR, "%s.setval: you don't have permissions to set sequence %s",
 			 seqname, seqname);
 #endif
diff --git a/src/backend/commands/trigger.c b/src/backend/commands/trigger.c
index 4a63094d6e2..c2db6a93745 100644
--- a/src/backend/commands/trigger.c
+++ b/src/backend/commands/trigger.c
@@ -7,7 +7,7 @@
  * Portions Copyright (c) 1994, Regents of the University of California
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/commands/trigger.c,v 1.76 2000/08/11 23:45:28 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/commands/trigger.c,v 1.77 2000/09/06 14:15:16 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -69,7 +69,7 @@ CreateTrigger(CreateTrigStmt *stmt)
 		elog(ERROR, "CreateTrigger: can't create trigger for system relation %s", stmt->relname);
 
 #ifndef NO_SECURITY
-	if (!pg_ownercheck(GetPgUserName(), stmt->relname, RELNAME))
+	if (!pg_ownercheck(GetUserId(), stmt->relname, RELNAME))
 		elog(ERROR, "%s: %s", stmt->relname, aclcheck_error_strings[ACLCHECK_NOT_OWNER]);
 #endif
 
@@ -309,7 +309,7 @@ DropTrigger(DropTrigStmt *stmt)
 	int			tgfound = 0;
 
 #ifndef NO_SECURITY
-	if (!pg_ownercheck(GetPgUserName(), stmt->relname, RELNAME))
+	if (!pg_ownercheck(GetUserId(), stmt->relname, RELNAME))
 		elog(ERROR, "%s: %s", stmt->relname, aclcheck_error_strings[ACLCHECK_NOT_OWNER]);
 #endif
 
diff --git a/src/backend/commands/vacuum.c b/src/backend/commands/vacuum.c
index ee0ebeb4bb7..398d002ffcd 100644
--- a/src/backend/commands/vacuum.c
+++ b/src/backend/commands/vacuum.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/commands/vacuum.c,v 1.163 2000/07/14 22:17:42 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/commands/vacuum.c,v 1.164 2000/09/06 14:15:16 petere Exp $
  *
 
  *-------------------------------------------------------------------------
@@ -404,7 +404,7 @@ vacuum_rel(Oid relid, bool analyze, bool is_toastrel)
 	toast_relid = onerel->rd_rel->reltoastrelid;
 
 #ifndef NO_SECURITY
-	if (!pg_ownercheck(GetPgUserName(), RelationGetRelationName(onerel),
+	if (!pg_ownercheck(GetUserId(), RelationGetRelationName(onerel),
 					   RELNAME))
 	{
 		elog(NOTICE, "Skipping \"%s\" --- only table owner can VACUUM it",
diff --git a/src/backend/executor/execMain.c b/src/backend/executor/execMain.c
index 2db826144dc..c6571279e1f 100644
--- a/src/backend/executor/execMain.c
+++ b/src/backend/executor/execMain.c
@@ -27,7 +27,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/executor/execMain.c,v 1.124 2000/08/22 04:06:19 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/executor/execMain.c,v 1.125 2000/09/06 14:15:17 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -571,8 +571,8 @@ ExecCheckRTEPerms(RangeTblEntry *rte, CmdType operation,
 				  bool isResultRelation, bool resultIsScanned)
 {
 	char	   *relName;
-	char	   *userName;
 	int32		aclcheck_result;
+	Oid		userid;
 
 	if (rte->skipAcl)
 	{
@@ -588,14 +588,14 @@ ExecCheckRTEPerms(RangeTblEntry *rte, CmdType operation,
 	relName = rte->relname;
 
 	/*
-	 * Note: GetPgUserName is presently fast enough that there's no harm
+	 * Note: GetUserId() is presently fast enough that there's no harm
 	 * in calling it separately for each RTE.  If that stops being true,
-	 * we could call it once in ExecCheckQueryPerms and pass the userName
+	 * we could call it once in ExecCheckQueryPerms and pass the userid
 	 * down from there.  But for now, no need for the extra clutter.
 	 */
-	userName = GetPgUserName();
+	userid = GetUserId();
 
-#define CHECK(MODE)		pg_aclcheck(relName, userName, MODE)
+#define CHECK(MODE)		pg_aclcheck(relName, userid, MODE)
 
 	if (isResultRelation)
 	{
diff --git a/src/backend/main/main.c b/src/backend/main/main.c
index ec36b602f45..a20b39886d5 100644
--- a/src/backend/main/main.c
+++ b/src/backend/main/main.c
@@ -8,10 +8,13 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/main/main.c,v 1.29 2000/01/26 05:56:30 momjian Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/main/main.c,v 1.30 2000/09/06 14:15:19 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
+#include "postgres.h"
+
+#include <pwd.h>
 #include <unistd.h>
 
 #if defined(__alpha__) && !defined(linux)
@@ -22,7 +25,6 @@
 #undef ASSEMBLER
 #endif
 
-#include "postgres.h"
 #ifdef USE_LOCALE
 #include <locale.h>
 #endif
@@ -100,5 +102,15 @@ main(int argc, char *argv[])
 		exit(BootstrapMain(argc - 1, argv + 1));		/* remove the -boot arg
 														 * from the command line */
 	else
-		exit(PostgresMain(argc, argv, argc, argv));
+	{
+		struct passwd *pw;
+
+		pw = getpwuid(geteuid());
+		if (!pw)
+		{
+			fprintf(stderr, "%s: invalid current euid", argv[0]);
+			exit(1);
+		}
+		exit(PostgresMain(argc, argv, argc, argv, pw->pw_name));
+	}
 }
diff --git a/src/backend/postmaster/postmaster.c b/src/backend/postmaster/postmaster.c
index 223b5bbe24c..59a42cd915e 100644
--- a/src/backend/postmaster/postmaster.c
+++ b/src/backend/postmaster/postmaster.c
@@ -11,7 +11,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/postmaster/postmaster.c,v 1.164 2000/08/30 14:54:22 momjian Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/postmaster/postmaster.c,v 1.165 2000/09/06 14:15:19 petere Exp $
  *
  * NOTES
  *
@@ -1635,11 +1635,11 @@ BackendStartup(Port *port)
 				i;
 
 #ifdef CYR_RECODE
-#define NR_ENVIRONMENT_VBL 6
+#define NR_ENVIRONMENT_VBL 5
 	char		ChTable[80];
 
 #else
-#define NR_ENVIRONMENT_VBL 5
+#define NR_ENVIRONMENT_VBL 4
 #endif
 
 	static char envEntry[NR_ENVIRONMENT_VBL][2 * ARGV_SIZE];
@@ -1655,19 +1655,17 @@ BackendStartup(Port *port)
 	putenv(envEntry[0]);
 	sprintf(envEntry[1], "POSTID=%d", NextBackendTag);
 	putenv(envEntry[1]);
-	sprintf(envEntry[2], "PG_USER=%s", port->user);
+	sprintf(envEntry[2], "PGDATA=%s", DataDir);
 	putenv(envEntry[2]);
-	sprintf(envEntry[3], "PGDATA=%s", DataDir);
+	sprintf(envEntry[3], "IPC_KEY=%d", ipc_key);
 	putenv(envEntry[3]);
-	sprintf(envEntry[4], "IPC_KEY=%d", ipc_key);
-	putenv(envEntry[4]);
 
 #ifdef CYR_RECODE
 	GetCharSetByHost(ChTable, port->raddr.in.sin_addr.s_addr, DataDir);
 	if (*ChTable != '\0')
 	{
-		sprintf(envEntry[5], "PG_RECODETABLE=%s", ChTable);
-		putenv(envEntry[5]);
+		sprintf(envEntry[4], "PG_RECODETABLE=%s", ChTable);
+		putenv(envEntry[4]);
 	}
 #endif
 
@@ -1931,7 +1929,7 @@ DoBackend(Port *port)
 		fprintf(stderr, ")\n");
 	}
 
-	return (PostgresMain(ac, av, real_argc, real_argv));
+	return (PostgresMain(ac, av, real_argc, real_argv, port->user));
 }
 
 /*
diff --git a/src/backend/rewrite/locks.c b/src/backend/rewrite/locks.c
index 5054b215438..a14e1b48684 100644
--- a/src/backend/rewrite/locks.c
+++ b/src/backend/rewrite/locks.c
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/rewrite/Attic/locks.c,v 1.30 2000/07/09 04:56:32 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/rewrite/Attic/locks.c,v 1.31 2000/09/06 14:15:20 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -175,7 +175,7 @@ matchLocks(CmdType event,
 
 typedef struct
 {
-	char	   *evowner;
+	Oid	evowner;
 } checkLockPerms_context;
 
 static bool
@@ -289,7 +289,7 @@ checkLockPerms(List *locks, Query *parsetree, int rt_index)
 		elog(ERROR, "cache lookup for userid %d failed",
 			 ev_rel->rd_rel->relowner);
 	userform = (Form_pg_shadow) GETSTRUCT(usertup);
-	context.evowner = pstrdup(NameStr(userform->usename));
+	context.evowner = userform->usesysid;
 	heap_close(ev_rel, AccessShareLock);
 
 	/*
diff --git a/src/backend/rewrite/rewriteHandler.c b/src/backend/rewrite/rewriteHandler.c
index 1f4073f9fcf..4362687f8b8 100644
--- a/src/backend/rewrite/rewriteHandler.c
+++ b/src/backend/rewrite/rewriteHandler.c
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/rewrite/rewriteHandler.c,v 1.78 2000/08/08 15:42:14 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/rewrite/rewriteHandler.c,v 1.79 2000/09/06 14:15:20 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -1137,7 +1137,7 @@ fireRules(Query *parsetree,
 			if (!rte->skipAcl)
 			{
 				acl_rc = pg_aclcheck(rte->relname,
-									 GetPgUserName(), reqperm);
+									 GetUserId(), reqperm);
 				if (acl_rc != ACLCHECK_OK)
 				{
 					elog(ERROR, "%s: %s",
diff --git a/src/backend/tcop/postgres.c b/src/backend/tcop/postgres.c
index 3369e22825e..373d6831df6 100644
--- a/src/backend/tcop/postgres.c
+++ b/src/backend/tcop/postgres.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/tcop/postgres.c,v 1.174 2000/08/30 20:30:06 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/tcop/postgres.c,v 1.175 2000/09/06 14:15:21 petere Exp $
  *
  * NOTES
  *	  this is the "main" module of the postgres backend and
@@ -817,28 +817,27 @@ usage(char *progname)
 }
 
 /* ----------------------------------------------------------------
- *	PostgresMain
- *		postgres main loop
- *		all backends, interactive or otherwise start here
+ * PostgresMain
+ *     postgres main loop -- all backends, interactive or otherwise start here
  *
- *	argc/argv are the command line arguments to be used.  When being forked
- *	by the postmaster, these are not the original argv array of the process.
- *	real_argc/real_argv point to the original argv array, which is needed by
- *	PS_INIT_STATUS on some platforms.
+ * argc/argv are the command line arguments to be used.  When being forked
+ * by the postmaster, these are not the original argv array of the process.
+ * real_argc/real_argv point to the original argv array, which is needed by
+ * `ps' display on some platforms. username is the (possibly authenticated)
+ * PostgreSQL user name to be used for the session.
  * ----------------------------------------------------------------
  */
 int
-PostgresMain(int argc, char *argv[], int real_argc, char *real_argv[])
+PostgresMain(int argc, char *argv[], int real_argc, char *real_argv[], const char * username)
 {
 	int			flag;
 
-	char	   *DBName = NULL;
+	const char	   *DBName = NULL;
 	bool		secure = true;
 	int			errs = 0;
 
 	int			firstchar;
 	StringInfo	parser_input;
-	char	   *userName;
 
 	char	   *remote_host;
 	unsigned short remote_port;
@@ -1244,12 +1243,6 @@ PostgresMain(int argc, char *argv[], int real_argc, char *real_argv[])
 	pqsignal(SIGTTOU, SIG_DFL);
 	pqsignal(SIGCONT, SIG_DFL);
 
-	/*
-	 * Get user name (needed now in case it is the default database name)
-	 * and check command line validity
-	 */
-	SetPgUserName();
-	userName = GetPgUserName();
 
 	if (IsUnderPostmaster)
 	{
@@ -1274,9 +1267,9 @@ PostgresMain(int argc, char *argv[], int real_argc, char *real_argv[])
 		}
 		else if (argc - optind == 1)
 			DBName = argv[optind];
-		else if ((DBName = userName) == NULL)
+		else if ((DBName = username) == NULL)
 		{
-			fprintf(stderr, "%s: USER undefined and no database specified\n",
+			fprintf(stderr, "%s: user name undefined and no database specified\n",
 					argv[0]);
 			proc_exit(0);
 		}
@@ -1361,20 +1354,20 @@ PostgresMain(int argc, char *argv[], int real_argc, char *real_argv[])
 		 * references to optarg or getenv() from above will be invalid
 		 * after this call. Better use strdup or something similar.
 		 */
-		init_ps_display(real_argc, real_argv, userName, DBName, remote_host);
+		init_ps_display(real_argc, real_argv, username, DBName, remote_host);
 		set_ps_display("startup");
 	}
 
 	if (Log_connections)
 		elog(DEBUG, "connection: host=%s user=%s database=%s",
-			 remote_host, userName, DBName);
+			 remote_host, username, DBName);
 
 	/*
 	 * general initialization
 	 */
 	if (DebugLvl > 1)
 		elog(DEBUG, "InitPostgres");
-	InitPostgres(DBName);
+	InitPostgres(DBName, username);
 
 #ifdef MULTIBYTE
 	/* set default client encoding */
@@ -1404,7 +1397,7 @@ PostgresMain(int argc, char *argv[], int real_argc, char *real_argv[])
 	if (!IsUnderPostmaster)
 	{
 		puts("\nPOSTGRES backend interactive interface ");
-		puts("$Revision: 1.174 $ $Date: 2000/08/30 20:30:06 $\n");
+		puts("$Revision: 1.175 $ $Date: 2000/09/06 14:15:21 $\n");
 	}
 
 	/*
diff --git a/src/backend/tcop/utility.c b/src/backend/tcop/utility.c
index 409aca70ada..558f678430f 100644
--- a/src/backend/tcop/utility.c
+++ b/src/backend/tcop/utility.c
@@ -10,7 +10,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/tcop/utility.c,v 1.91 2000/07/05 12:45:26 wieck Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/tcop/utility.c,v 1.92 2000/09/06 14:15:21 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -74,9 +74,6 @@ ProcessUtility(Node *parsetree,
 	char	   *commandTag = NULL;
 	char	   *relname;
 	char	   *relationName;
-	char	   *userName;
-
-	userName = GetPgUserName();
 
 	switch (nodeTag(parsetree))
 	{
@@ -200,7 +197,7 @@ ProcessUtility(Node *parsetree,
 					/* close rel, but keep lock until end of xact */
 					heap_close(rel, NoLock);
 #ifndef NO_SECURITY
-					if (!pg_ownercheck(userName, relname, RELNAME))
+					if (!pg_ownercheck(GetUserId(), relname, RELNAME))
 						elog(ERROR, "you do not own class \"%s\"",
 							 relname);
 #endif
@@ -234,7 +231,7 @@ ProcessUtility(Node *parsetree,
 				heap_close(rel, NoLock);
 
 #ifndef NO_SECURITY
-				if (!pg_ownercheck(userName, relname, RELNAME))
+				if (!pg_ownercheck(GetUserId(), relname, RELNAME))
 					elog(ERROR, "you do not own class \"%s\"", relname);
 #endif
 				TruncateRelation(relname);
@@ -299,7 +296,7 @@ ProcessUtility(Node *parsetree,
 					elog(ERROR, "ALTER TABLE: relation \"%s\" is a system catalog",
 						 relname);
 #ifndef NO_SECURITY
-				if (!pg_ownercheck(userName, relname, RELNAME))
+				if (!pg_ownercheck(GetUserId(), relname, RELNAME))
 					elog(ERROR, "permission denied");
 #endif
 
@@ -333,7 +330,6 @@ ProcessUtility(Node *parsetree,
 					renameatt(relname,	/* relname */
 							  stmt->column,		/* old att name */
 							  stmt->newname,	/* new att name */
-							  userName,
 							  stmt->inh);		/* recursive? */
 				}
 			}
@@ -405,7 +401,7 @@ ProcessUtility(Node *parsetree,
 					/* close rel, but keep lock until end of xact */
 					heap_close(rel, NoLock);
 #ifndef NO_SECURITY
-					if (!pg_ownercheck(userName, relname, RELNAME))
+					if (!pg_ownercheck(GetUserId(), relname, RELNAME))
 						elog(ERROR, "you do not own class \"%s\"",
 							 relname);
 #endif
@@ -484,7 +480,7 @@ ProcessUtility(Node *parsetree,
 
 #ifndef NO_SECURITY
 				relname = stmt->object->relname;
-				aclcheck_result = pg_aclcheck(relname, userName, ACL_RU);
+				aclcheck_result = pg_aclcheck(relname, GetUserId(), ACL_RU);
 				if (aclcheck_result != ACLCHECK_OK)
 					elog(ERROR, "%s: %s", relname, aclcheck_error_strings[aclcheck_result]);
 #endif
@@ -529,7 +525,7 @@ ProcessUtility(Node *parsetree,
 							elog(ERROR, "class \"%s\" is a system catalog index",
 								 relname);
 #ifndef NO_SECURITY
-						if (!pg_ownercheck(userName, relname, RELNAME))
+						if (!pg_ownercheck(GetUserId(), relname, RELNAME))
 							elog(ERROR, "%s: %s", relname, aclcheck_error_strings[ACLCHECK_NOT_OWNER]);
 #endif
 						RemoveIndex(relname);
@@ -542,7 +538,7 @@ ProcessUtility(Node *parsetree,
 #ifndef NO_SECURITY
 
 							relationName = RewriteGetRuleEventRel(rulename);
-							aclcheck_result = pg_aclcheck(relationName, userName, ACL_RU);
+							aclcheck_result = pg_aclcheck(relationName, GetUserId(), ACL_RU);
 							if (aclcheck_result != ACLCHECK_OK)
 								elog(ERROR, "%s: %s", relationName, aclcheck_error_strings[aclcheck_result]);
 #endif
@@ -564,7 +560,7 @@ ProcessUtility(Node *parsetree,
 
 							ruleName = MakeRetrieveViewRuleName(viewName);
 							relationName = RewriteGetRuleEventRel(ruleName);
-							if (!pg_ownercheck(userName, relationName, RELNAME))
+							if (!pg_ownercheck(GetUserId(), relationName, RELNAME))
 								elog(ERROR, "%s: %s", relationName, aclcheck_error_strings[ACLCHECK_NOT_OWNER]);
 							pfree(ruleName);
 #endif
@@ -881,7 +877,7 @@ ProcessUtility(Node *parsetree,
 								 relname);
 						}
 #ifndef NO_SECURITY
-						if (!pg_ownercheck(userName, relname, RELNAME))
+						if (!pg_ownercheck(GetUserId(), relname, RELNAME))
 							elog(ERROR, "%s: %s", relname, aclcheck_error_strings[ACLCHECK_NOT_OWNER]);
 #endif
 						ReindexIndex(relname, stmt->force);
@@ -899,7 +895,7 @@ ProcessUtility(Node *parsetree,
 								 relname);
 						}
 #ifndef NO_SECURITY
-						if (!pg_ownercheck(userName, relname, RELNAME))
+						if (!pg_ownercheck(GetUserId(), relname, RELNAME))
 							elog(ERROR, "%s: %s", relname, aclcheck_error_strings[ACLCHECK_NOT_OWNER]);
 #endif
 						ReindexTable(relname, stmt->force);
diff --git a/src/backend/utils/init/globals.c b/src/backend/utils/init/globals.c
index c886af6309a..70bb40f328f 100644
--- a/src/backend/utils/init/globals.c
+++ b/src/backend/utils/init/globals.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/utils/init/globals.c,v 1.45 2000/05/31 00:28:32 petere Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/utils/init/globals.c,v 1.46 2000/09/06 14:15:22 petere Exp $
  *
  * NOTES
  *	  Globals used all over the place should be declared here and not
@@ -54,7 +54,6 @@ char		OutputFileName[MAXPGPATH] = "";
 BackendId	MyBackendId;
 BackendTag	MyBackendTag;
 
-char	   *UserName = NULL;
 char	   *DatabaseName = NULL;
 char	   *DatabasePath = NULL;
 
diff --git a/src/backend/utils/init/miscinit.c b/src/backend/utils/init/miscinit.c
index 01182c765a9..20babcc616c 100644
--- a/src/backend/utils/init/miscinit.c
+++ b/src/backend/utils/init/miscinit.c
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/utils/init/miscinit.c,v 1.53 2000/08/03 16:34:24 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/utils/init/miscinit.c,v 1.54 2000/09/06 14:15:22 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -273,87 +273,67 @@ convertstr(unsigned char *buff, int len, int dest)
 #endif
 
 /* ----------------
- *		GetPgUserName and SetPgUserName
- *
- *		SetPgUserName must be called before InitPostgres, since the setuid()
- *		is done there.
+ *		GetPgUserName
  * ----------------
  */
 char *
 GetPgUserName(void)
 {
-	return UserName;
-}
+	HeapTuple tuple;
+	Oid userid;
 
-void
-SetPgUserName(void)
-{
-#ifndef NO_SECURITY
-	char	   *p;
-	struct passwd *pw;
+	userid = GetUserId();
 
-	if (IsUnderPostmaster)
-	{
-		/* use the (possibly) authenticated name that's provided */
-		if (!(p = getenv("PG_USER")))
-			elog(FATAL, "SetPgUserName: PG_USER environment variable is unset");
-	}
-	else
-	{
-		/* setuid() has not yet been done, see above comment */
-		if (!(pw = getpwuid(geteuid())))
-			elog(FATAL, "SetPgUserName: no entry in host passwd file");
-		p = pw->pw_name;
-	}
-	if (UserName)
-		free(UserName);
-	UserName = malloc(strlen(p) + 1);
-	strcpy(UserName, p);
-#endif	 /* NO_SECURITY */
+	tuple = SearchSysCacheTuple(SHADOWSYSID, ObjectIdGetDatum(userid), 0, 0, 0);
+	if (!HeapTupleIsValid(tuple))
+		elog(ERROR, "invalid user id %u", (unsigned) userid);
+
+	return pstrdup( NameStr(((Form_pg_shadow) GETSTRUCT(tuple))->usename) );
 }
 
+
 /* ----------------------------------------------------------------
  *		GetUserId and SetUserId
  * ----------------------------------------------------------------
  */
 static Oid	UserId = InvalidOid;
 
-int
+
+Oid
 GetUserId()
 {
 	AssertState(OidIsValid(UserId));
 	return UserId;
 }
 
+
 void
-SetUserId()
+SetUserId(Oid newid)
 {
-	HeapTuple	userTup;
-	char	   *userName;
+	UserId = newid;
+}
 
-	AssertState(!OidIsValid(UserId));	/* only once */
+
+void
+SetUserIdFromUserName(const char *username)
+{
+	HeapTuple	userTup;
 
 	/*
 	 * Don't do scans if we're bootstrapping, none of the system catalogs
 	 * exist yet, and they should be owned by postgres anyway.
 	 */
-	if (IsBootstrapProcessingMode())
-	{
-		UserId = geteuid();
-		return;
-	}
+	AssertState(!IsBootstrapProcessingMode());
 
-	userName = GetPgUserName();
 	userTup = SearchSysCacheTuple(SHADOWNAME,
-								  PointerGetDatum(userName),
+								  PointerGetDatum(username),
 								  0, 0, 0);
 	if (!HeapTupleIsValid(userTup))
-		elog(FATAL, "SetUserId: user '%s' is not in '%s'",
-			 userName,
-			 ShadowRelationName);
-	UserId = (Oid) ((Form_pg_shadow) GETSTRUCT(userTup))->usesysid;
+		elog(FATAL, "user \"%s\" does not exist", username);
+	SetUserId( ((Form_pg_shadow) GETSTRUCT(userTup))->usesysid );
 }
 
+
 /*-------------------------------------------------------------------------
  *
  * posmaster pid file stuffs. $DATADIR/postmaster.pid is created when:
diff --git a/src/backend/utils/init/postinit.c b/src/backend/utils/init/postinit.c
index f63590cdb98..a9e083557e0 100644
--- a/src/backend/utils/init/postinit.c
+++ b/src/backend/utils/init/postinit.c
@@ -8,19 +8,19 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/utils/init/postinit.c,v 1.64 2000/08/06 04:39:10 tgl Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/utils/init/postinit.c,v 1.65 2000/09/06 14:15:22 petere Exp $
  *
  *
  *-------------------------------------------------------------------------
  */
+#include "postgres.h"
+
 #include <fcntl.h>
 #include <sys/file.h>
 #include <sys/types.h>
 #include <math.h>
 #include <unistd.h>
 
-#include "postgres.h"
-
 #include "access/heapam.h"
 #include "catalog/catname.h"
 #include "catalog/pg_database.h"
@@ -223,7 +223,7 @@ int			lockingOff = 0;		/* backend -L switch */
 /*
  */
 void
-InitPostgres(const char *dbname)
+InitPostgres(const char *dbname, const char *username)
 {
 	bool		bootstrap = IsBootstrapProcessingMode();
 
@@ -366,16 +366,19 @@ InitPostgres(const char *dbname)
 	/* replace faked-up relcache entries with the real info */
 	RelationCacheInitializePhase2();
 
+	if (lockingOff)
+		LockDisable(true);
+
 	/*
 	 * Set ourselves to the proper user id and figure out our postgres
-	 * user id.  If we ever add security so that we check for valid
-	 * postgres users, we might do it here.
+	 * user id.
 	 */
-	setuid(geteuid());
-	SetUserId();
+	if (bootstrap)
+		SetUserId(geteuid());
+	else
+		SetUserIdFromUserName(username);
 
-	if (lockingOff)
-		LockDisable(true);
+	setuid(geteuid());
 
 	/*
 	 * Unless we are bootstrapping, double-check that InitMyDatabaseInfo()
diff --git a/src/backend/utils/misc/superuser.c b/src/backend/utils/misc/superuser.c
index 8c36c4f2972..1852b35e465 100644
--- a/src/backend/utils/misc/superuser.c
+++ b/src/backend/utils/misc/superuser.c
@@ -9,7 +9,7 @@
  *
  *
  * IDENTIFICATION
- *	  $Header: /cvsroot/pgsql/src/backend/utils/misc/superuser.c,v 1.14 2000/01/26 05:57:28 momjian Exp $
+ *	  $Header: /cvsroot/pgsql/src/backend/utils/misc/superuser.c,v 1.15 2000/09/06 14:15:22 petere Exp $
  *
  * DESCRIPTION
  *	  See superuser().
@@ -30,8 +30,8 @@ superuser(void)
 --------------------------------------------------------------------------*/
 	HeapTuple	utup;
 
-	utup = SearchSysCacheTuple(SHADOWNAME,
-							   PointerGetDatum(GetPgUserName()),
+	utup = SearchSysCacheTuple(SHADOWSYSID,
+							   ObjectIdGetDatum(GetUserId()),
 							   0, 0, 0);
 	Assert(utup != NULL);
 	return ((Form_pg_shadow) GETSTRUCT(utup))->usesuper;
diff --git a/src/include/commands/rename.h b/src/include/commands/rename.h
index 230a2162d46..e5ee7db66c6 100644
--- a/src/include/commands/rename.h
+++ b/src/include/commands/rename.h
@@ -7,7 +7,7 @@
  * Portions Copyright (c) 1996-2000, PostgreSQL, Inc
  * Portions Copyright (c) 1994, Regents of the University of California
  *
- * $Id: rename.h,v 1.8 2000/01/26 05:58:00 momjian Exp $
+ * $Id: rename.h,v 1.9 2000/09/06 14:15:25 petere Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -17,7 +17,7 @@
 extern void renameatt(char *relname,
 		  char *oldattname,
 		  char *newattname,
-		  char *userName, int recurse);
+		  int recurse);
 
 extern void renamerel(const char *oldrelname,
 		  const char *newrelname);
diff --git a/src/include/miscadmin.h b/src/include/miscadmin.h
index 83ad67602cc..187f6f91b7f 100644
--- a/src/include/miscadmin.h
+++ b/src/include/miscadmin.h
@@ -12,7 +12,7 @@
  * Portions Copyright (c) 1996-2000, PostgreSQL, Inc
  * Portions Copyright (c) 1994, Regents of the University of California
  *
- * $Id: miscadmin.h,v 1.64 2000/08/03 16:34:43 tgl Exp $
+ * $Id: miscadmin.h,v 1.65 2000/09/06 14:15:24 petere Exp $
  *
  * NOTES
  *	  some of the information in this file will be moved to
@@ -51,8 +51,6 @@ extern long MyCancelKey;
 
 extern char OutputFileName[];
 
-extern char *UserName;
-
 /*
  * done in storage/backendid.h for now.
  *
@@ -130,9 +128,9 @@ extern void SetDatabaseName(const char *name);
 extern void SetDatabasePath(const char *path);
 
 extern char *GetPgUserName(void);
-extern void SetPgUserName(void);
-extern int	GetUserId(void);
-extern void SetUserId(void);
+extern Oid	GetUserId(void);
+extern void SetUserId(Oid userid);
+extern void SetUserIdFromUserName(const char *username);
 extern int	FindExec(char *full_path, const char *argv0, const char *binary_name);
 extern int	CheckPathAccess(char *path, char *name, int open_mode);
 
@@ -186,7 +184,7 @@ typedef int16 ExitStatus;
 
 extern int	lockingOff;
 
-extern void InitPostgres(const char *dbname);
+extern void InitPostgres(const char *dbname, const char *username);
 extern void BaseInit(void);
 
 /* one of the ways to get out of here */
diff --git a/src/include/tcop/tcopprot.h b/src/include/tcop/tcopprot.h
index 11e3a2ca5d2..562efca25cc 100644
--- a/src/include/tcop/tcopprot.h
+++ b/src/include/tcop/tcopprot.h
@@ -7,7 +7,7 @@
  * Portions Copyright (c) 1996-2000, PostgreSQL, Inc
  * Portions Copyright (c) 1994, Regents of the University of California
  *
- * $Id: tcopprot.h,v 1.33 2000/08/29 09:36:51 petere Exp $
+ * $Id: tcopprot.h,v 1.34 2000/09/06 14:15:28 petere Exp $
  *
  * OLD COMMENTS
  *	  This file was created so that other c files could get the two
@@ -45,7 +45,7 @@ extern void handle_warn(SIGNAL_ARGS);
 extern void die(SIGNAL_ARGS);
 extern void CancelQuery(void);
 extern int PostgresMain(int argc, char *argv[],
-			 int real_argc, char *real_argv[]);
+			 int real_argc, char *real_argv[], const char *username);
 extern void ResetUsage(void);
 extern void ShowUsage(void);
 extern FILE * StatFp;
diff --git a/src/include/utils/acl.h b/src/include/utils/acl.h
index e8a8f3a111b..5e91f56bf50 100644
--- a/src/include/utils/acl.h
+++ b/src/include/utils/acl.h
@@ -7,7 +7,7 @@
  * Portions Copyright (c) 1996-2000, PostgreSQL, Inc
  * Portions Copyright (c) 1994, Regents of the University of California
  *
- * $Id: acl.h,v 1.26 2000/07/31 22:39:02 tgl Exp $
+ * $Id: acl.h,v 1.27 2000/09/06 14:15:31 petere Exp $
  *
  * NOTES
  *	  For backward-compatibility purposes we have to allow there
@@ -197,11 +197,11 @@ extern void ChangeAcl(char *relname, AclItem *mod_aip, unsigned modechg);
 extern AclId get_grosysid(char *groname);
 extern char *get_groname(AclId grosysid);
 
-extern int32 pg_aclcheck(char *relname, char *usename, AclMode mode);
-extern int32 pg_ownercheck(const char *usename, const char *value, int cacheid);
-extern int32 pg_func_ownercheck(char *usename, char *funcname,
+extern int32 pg_aclcheck(char *relname, Oid userid, AclMode mode);
+extern int32 pg_ownercheck(Oid userid, const char *value, int cacheid);
+extern int32 pg_func_ownercheck(Oid userid, char *funcname,
 				   int nargs, Oid *arglist);
-extern int32 pg_aggr_ownercheck(char *usename, char *aggname,
+extern int32 pg_aggr_ownercheck(Oid userid, char *aggname,
 				   Oid basetypeID);
 
 #endif	 /* ACL_H */
-- 
GitLab