Commit 1dbf8aa7 authored by Tom Lane's avatar Tom Lane

pg_class has a relnamespace column. You can create and access tables

in schemas other than the system namespace; however, there's no search
path yet, and not all operations work yet on tables outside the system
namespace.
parent da631e93
<!-- <!--
Documentation of the system catalogs, directed toward PostgreSQL developers Documentation of the system catalogs, directed toward PostgreSQL developers
$Header: /cvsroot/pgsql/doc/src/sgml/catalogs.sgml,v 2.37 2002/03/22 21:34:43 tgl Exp $ $Header: /cvsroot/pgsql/doc/src/sgml/catalogs.sgml,v 2.38 2002/03/26 19:15:10 tgl Exp $
--> -->
<chapter id="catalogs"> <chapter id="catalogs">
...@@ -568,6 +568,15 @@ ...@@ -568,6 +568,15 @@
<entry>Name of the table, index, view, etc.</entry> <entry>Name of the table, index, view, etc.</entry>
</row> </row>
<row>
<entry>relnamespace</entry>
<entry><type>oid</type></entry>
<entry>pg_namespace.oid</entry>
<entry>
The OID of the namespace that contains this relation
</entry>
</row>
<row> <row>
<entry>reltype</entry> <entry>reltype</entry>
<entry><type>oid</type></entry> <entry><type>oid</type></entry>
......
...@@ -8,15 +8,17 @@ ...@@ -8,15 +8,17 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/access/heap/heapam.c,v 1.131 2002/03/03 17:47:53 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/access/heap/heapam.c,v 1.132 2002/03/26 19:15:11 tgl Exp $
* *
* *
* INTERFACE ROUTINES * INTERFACE ROUTINES
* relation_open - open any relation by relation OID * relation_open - open any relation by relation OID
* relation_openr - open any relation by name * relation_openrv - open any relation specified by a RangeVar
* relation_openr - open a system relation by name
* relation_close - close any relation * relation_close - close any relation
* heap_open - open a heap relation by relation OID * heap_open - open a heap relation by relation OID
* heap_openr - open a heap relation by name * heap_openrv - open a heap relation specified by a RangeVar
* heap_openr - open a system heap relation by name
* heap_close - (now just a macro for relation_close) * heap_close - (now just a macro for relation_close)
* heap_beginscan - begin relation scan * heap_beginscan - begin relation scan
* heap_rescan - restart a relation scan * heap_rescan - restart a relation scan
...@@ -44,6 +46,7 @@ ...@@ -44,6 +46,7 @@
#include "access/valid.h" #include "access/valid.h"
#include "access/xlogutils.h" #include "access/xlogutils.h"
#include "catalog/catalog.h" #include "catalog/catalog.h"
#include "catalog/namespace.h"
#include "miscadmin.h" #include "miscadmin.h"
#include "utils/inval.h" #include "utils/inval.h"
#include "utils/relcache.h" #include "utils/relcache.h"
...@@ -481,29 +484,30 @@ relation_open(Oid relationId, LOCKMODE lockmode) ...@@ -481,29 +484,30 @@ relation_open(Oid relationId, LOCKMODE lockmode)
} }
/* ---------------- /* ----------------
* relation_openr - open any relation by name * relation_openrv - open any relation specified by a RangeVar
* *
* As above, but lookup by name instead of OID. * As above, but the relation is specified by a RangeVar.
* ---------------- * ----------------
*/ */
Relation Relation
relation_openr(const char *relationName, LOCKMODE lockmode) relation_openrv(const RangeVar *relation, LOCKMODE lockmode)
{ {
Relation r; Oid relOid;
Assert(lockmode >= NoLock && lockmode < MAX_LOCKMODES);
/* /*
* increment access statistics * In bootstrap mode, don't do any namespace processing.
*/ */
IncrHeapAccessStat(local_openr); if (IsBootstrapProcessingMode())
IncrHeapAccessStat(global_openr); {
Assert(relation->schemaname == NULL);
return relation_openr(relation->relname, lockmode);
}
/* /*
* Check for shared-cache-inval messages before trying to open the * Check for shared-cache-inval messages before trying to open the
* relation. This is needed to cover the case where the name * relation. This is needed to cover the case where the name
* identifies a rel that has been dropped and recreated since the * identifies a rel that has been dropped and recreated since the
* start of our transaction: if we don't flush the old relcache entry * start of our transaction: if we don't flush the old syscache entry
* then we'll latch onto that entry and suffer an error when we do * then we'll latch onto that entry and suffer an error when we do
* LockRelation. Note that relation_open does not need to do this, * LockRelation. Note that relation_open does not need to do this,
* since a relation's OID never changes. * since a relation's OID never changes.
...@@ -514,11 +518,43 @@ relation_openr(const char *relationName, LOCKMODE lockmode) ...@@ -514,11 +518,43 @@ relation_openr(const char *relationName, LOCKMODE lockmode)
if (lockmode != NoLock) if (lockmode != NoLock)
AcceptInvalidationMessages(); AcceptInvalidationMessages();
/* Look up the appropriate relation using namespace search */
relOid = RangeVarGetRelid(relation, false);
/* Let relation_open do the rest */
return relation_open(relOid, lockmode);
}
/* ----------------
* relation_openr - open a system relation specified by name.
*
* As above, but the relation is specified by an unqualified name;
* it is assumed to live in the system catalog namespace.
* ----------------
*/
Relation
relation_openr(const char *sysRelationName, LOCKMODE lockmode)
{
Relation r;
Assert(lockmode >= NoLock && lockmode < MAX_LOCKMODES);
/*
* increment access statistics
*/
IncrHeapAccessStat(local_openr);
IncrHeapAccessStat(global_openr);
/*
* We assume we should not need to worry about the rel's OID changing,
* hence no need for AcceptInvalidationMessages here.
*/
/* The relcache does all the real work... */ /* The relcache does all the real work... */
r = RelationNameGetRelation(relationName); r = RelationSysNameGetRelation(sysRelationName);
if (!RelationIsValid(r)) if (!RelationIsValid(r))
elog(ERROR, "Relation \"%s\" does not exist", relationName); elog(ERROR, "Relation \"%s\" does not exist", sysRelationName);
if (lockmode != NoLock) if (lockmode != NoLock)
LockRelation(r, lockmode); LockRelation(r, lockmode);
...@@ -582,17 +618,44 @@ heap_open(Oid relationId, LOCKMODE lockmode) ...@@ -582,17 +618,44 @@ heap_open(Oid relationId, LOCKMODE lockmode)
} }
/* ---------------- /* ----------------
* heap_openr - open a heap relation by name * heap_openrv - open a heap relation specified
* by a RangeVar node
*
* As above, but relation is specified by a RangeVar.
* ----------------
*/
Relation
heap_openrv(const RangeVar *relation, LOCKMODE lockmode)
{
Relation r;
r = relation_openrv(relation, lockmode);
if (r->rd_rel->relkind == RELKIND_INDEX)
elog(ERROR, "%s is an index relation",
RelationGetRelationName(r));
else if (r->rd_rel->relkind == RELKIND_SPECIAL)
elog(ERROR, "%s is a special relation",
RelationGetRelationName(r));
pgstat_initstats(&r->pgstat_info, r);
return r;
}
/* ----------------
* heap_openr - open a system heap relation specified by name.
* *
* As above, but lookup by name instead of OID. * As above, but the relation is specified by an unqualified name;
* it is assumed to live in the system catalog namespace.
* ---------------- * ----------------
*/ */
Relation Relation
heap_openr(const char *relationName, LOCKMODE lockmode) heap_openr(const char *sysRelationName, LOCKMODE lockmode)
{ {
Relation r; Relation r;
r = relation_openr(relationName, lockmode); r = relation_openr(sysRelationName, lockmode);
if (r->rd_rel->relkind == RELKIND_INDEX) if (r->rd_rel->relkind == RELKIND_INDEX)
elog(ERROR, "%s is an index relation", elog(ERROR, "%s is an index relation",
......
...@@ -8,11 +8,12 @@ ...@@ -8,11 +8,12 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/access/index/indexam.c,v 1.55 2001/11/02 16:30:29 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/access/index/indexam.c,v 1.56 2002/03/26 19:15:14 tgl Exp $
* *
* INTERFACE ROUTINES * INTERFACE ROUTINES
* index_open - open an index relation by relation OID * index_open - open an index relation by relation OID
* index_openr - open an index relation by name * index_openrv - open an index relation specified by a RangeVar
* index_openr - open a system index relation by name
* index_close - close an index relation * index_close - close an index relation
* index_beginscan - start a scan of an index * index_beginscan - start a scan of an index
* index_rescan - restart a scan of an index * index_rescan - restart a scan of an index
...@@ -136,17 +137,41 @@ index_open(Oid relationId) ...@@ -136,17 +137,41 @@ index_open(Oid relationId)
} }
/* ---------------- /* ----------------
* index_openr - open an index relation by name * index_openrv - open an index relation specified
* by a RangeVar node
* *
* As above, but lookup by name instead of OID. * As above, but relation is specified by a RangeVar.
* ---------------- * ----------------
*/ */
Relation Relation
index_openr(const char *relationName) index_openrv(const RangeVar *relation)
{ {
Relation r; Relation r;
r = relation_openr(relationName, NoLock); r = relation_openrv(relation, NoLock);
if (r->rd_rel->relkind != RELKIND_INDEX)
elog(ERROR, "%s is not an index relation",
RelationGetRelationName(r));
pgstat_initstats(&r->pgstat_info, r);
return r;
}
/* ----------------
* index_openr - open a system index relation specified by name.
*
* As above, but the relation is specified by an unqualified name;
* it is assumed to live in the system catalog namespace.
* ----------------
*/
Relation
index_openr(const char *sysRelationName)
{
Relation r;
r = relation_openr(sysRelationName, NoLock);
if (r->rd_rel->relkind != RELKIND_INDEX) if (r->rd_rel->relkind != RELKIND_INDEX)
elog(ERROR, "%s is not an index relation", elog(ERROR, "%s is not an index relation",
......
...@@ -9,7 +9,7 @@ ...@@ -9,7 +9,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/bootstrap/bootparse.y,v 1.40 2002/03/02 21:39:20 momjian Exp $ * $Header: /cvsroot/pgsql/src/backend/bootstrap/bootparse.y,v 1.41 2002/03/26 19:15:16 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -32,8 +32,10 @@ ...@@ -32,8 +32,10 @@
#include "catalog/pg_am.h" #include "catalog/pg_am.h"
#include "catalog/pg_attribute.h" #include "catalog/pg_attribute.h"
#include "catalog/pg_class.h" #include "catalog/pg_class.h"
#include "catalog/pg_namespace.h"
#include "commands/defrem.h" #include "commands/defrem.h"
#include "miscadmin.h" #include "miscadmin.h"
#include "nodes/makefuncs.h"
#include "nodes/nodes.h" #include "nodes/nodes.h"
#include "nodes/parsenodes.h" #include "nodes/parsenodes.h"
#include "nodes/pg_list.h" #include "nodes/pg_list.h"
...@@ -179,7 +181,9 @@ Boot_CreateStmt: ...@@ -179,7 +181,9 @@ Boot_CreateStmt:
} }
tupdesc = CreateTupleDesc(numattr, attrtypes); tupdesc = CreateTupleDesc(numattr, attrtypes);
reldesc = heap_create(LexIDStr($4), tupdesc, reldesc = heap_create(LexIDStr($4),
PG_CATALOG_NAMESPACE,
tupdesc,
false, true, true); false, true, true);
reldesc->rd_rel->relhasoids = ! ($3); reldesc->rd_rel->relhasoids = ! ($3);
elog(DEBUG3, "bootstrap relation created"); elog(DEBUG3, "bootstrap relation created");
...@@ -191,6 +195,7 @@ Boot_CreateStmt: ...@@ -191,6 +195,7 @@ Boot_CreateStmt:
tupdesc = CreateTupleDesc(numattr,attrtypes); tupdesc = CreateTupleDesc(numattr,attrtypes);
id = heap_create_with_catalog(LexIDStr($4), id = heap_create_with_catalog(LexIDStr($4),
PG_CATALOG_NAMESPACE,
tupdesc, tupdesc,
RELKIND_RELATION, RELKIND_RELATION,
! ($3), ! ($3),
...@@ -232,7 +237,7 @@ Boot_DeclareIndexStmt: ...@@ -232,7 +237,7 @@ Boot_DeclareIndexStmt:
{ {
do_start(); do_start();
DefineIndex(LexIDStr($5), DefineIndex(makeRangeVar(NULL, LexIDStr($5)),
LexIDStr($3), LexIDStr($3),
LexIDStr($7), LexIDStr($7),
$9, false, false, NULL, NIL); $9, false, false, NULL, NIL);
...@@ -245,7 +250,7 @@ Boot_DeclareUniqueIndexStmt: ...@@ -245,7 +250,7 @@ Boot_DeclareUniqueIndexStmt:
{ {
do_start(); do_start();
DefineIndex(LexIDStr($6), DefineIndex(makeRangeVar(NULL, LexIDStr($6)),
LexIDStr($4), LexIDStr($4),
LexIDStr($8), LexIDStr($8),
$10, true, false, NULL, NIL); $10, true, false, NULL, NIL);
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/bootstrap/bootstrap.c,v 1.124 2002/03/15 19:20:34 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/bootstrap/bootstrap.c,v 1.125 2002/03/26 19:15:16 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -153,8 +153,8 @@ extern char *optarg; ...@@ -153,8 +153,8 @@ extern char *optarg;
typedef struct _IndexList typedef struct _IndexList
{ {
char *il_heap; Oid il_heap;
char *il_ind; Oid il_ind;
IndexInfo *il_info; IndexInfo *il_info;
struct _IndexList *il_next; struct _IndexList *il_next;
} IndexList; } IndexList;
...@@ -1080,8 +1080,8 @@ AddStr(char *str, int strlength, int mderef) ...@@ -1080,8 +1080,8 @@ AddStr(char *str, int strlength, int mderef)
* are present in the index. * are present in the index.
*/ */
void void
index_register(char *heap, index_register(Oid heap,
char *ind, Oid ind,
IndexInfo *indexInfo) IndexInfo *indexInfo)
{ {
IndexList *newind; IndexList *newind;
...@@ -1103,8 +1103,8 @@ index_register(char *heap, ...@@ -1103,8 +1103,8 @@ index_register(char *heap,
oldcxt = MemoryContextSwitchTo(nogc); oldcxt = MemoryContextSwitchTo(nogc);
newind = (IndexList *) palloc(sizeof(IndexList)); newind = (IndexList *) palloc(sizeof(IndexList));
newind->il_heap = pstrdup(heap); newind->il_heap = heap;
newind->il_ind = pstrdup(ind); newind->il_ind = ind;
newind->il_info = (IndexInfo *) palloc(sizeof(IndexInfo)); newind->il_info = (IndexInfo *) palloc(sizeof(IndexInfo));
memcpy(newind->il_info, indexInfo, sizeof(IndexInfo)); memcpy(newind->il_info, indexInfo, sizeof(IndexInfo));
...@@ -1126,8 +1126,8 @@ build_indices() ...@@ -1126,8 +1126,8 @@ build_indices()
Relation heap; Relation heap;
Relation ind; Relation ind;
heap = heap_openr(ILHead->il_heap, NoLock); heap = heap_open(ILHead->il_heap, NoLock);
ind = index_openr(ILHead->il_ind); ind = index_open(ILHead->il_ind);
index_build(heap, ind, ILHead->il_info); index_build(heap, ind, ILHead->il_info);
/* /*
......
...@@ -2,7 +2,7 @@ ...@@ -2,7 +2,7 @@
# #
# Makefile for backend/catalog # Makefile for backend/catalog
# #
# $Header: /cvsroot/pgsql/src/backend/catalog/Makefile,v 1.38 2002/03/22 21:34:43 tgl Exp $ # $Header: /cvsroot/pgsql/src/backend/catalog/Makefile,v 1.39 2002/03/26 19:15:22 tgl Exp $
# #
#------------------------------------------------------------------------- #-------------------------------------------------------------------------
...@@ -10,7 +10,7 @@ subdir = src/backend/catalog ...@@ -10,7 +10,7 @@ subdir = src/backend/catalog
top_builddir = ../../.. top_builddir = ../../..
include $(top_builddir)/src/Makefile.global include $(top_builddir)/src/Makefile.global
OBJS = catalog.o heap.o index.o indexing.o aclchk.o \ OBJS = catalog.o heap.o index.o indexing.o namespace.o aclchk.o \
pg_aggregate.o pg_largeobject.o pg_namespace.o \ pg_aggregate.o pg_largeobject.o pg_namespace.o \
pg_operator.o pg_proc.o pg_type.o pg_operator.o pg_proc.o pg_type.o
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/catalog/aclchk.c,v 1.58 2002/03/21 23:27:19 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/catalog/aclchk.c,v 1.59 2002/03/26 19:15:22 tgl Exp $
* *
* NOTES * NOTES
* See acl.h. * See acl.h.
...@@ -22,6 +22,7 @@ ...@@ -22,6 +22,7 @@
#include "catalog/catalog.h" #include "catalog/catalog.h"
#include "catalog/catname.h" #include "catalog/catname.h"
#include "catalog/indexing.h" #include "catalog/indexing.h"
#include "catalog/namespace.h"
#include "catalog/pg_aggregate.h" #include "catalog/pg_aggregate.h"
#include "catalog/pg_group.h" #include "catalog/pg_group.h"
#include "catalog/pg_language.h" #include "catalog/pg_language.h"
...@@ -200,7 +201,8 @@ ExecuteGrantStmt_Table(GrantStmt *stmt) ...@@ -200,7 +201,8 @@ ExecuteGrantStmt_Table(GrantStmt *stmt)
foreach(i, stmt->objects) foreach(i, stmt->objects)
{ {
char *relname = ((RangeVar *) lfirst(i))->relname; RangeVar *relvar = (RangeVar *) lfirst(i);
Oid relOid;
Relation relation; Relation relation;
HeapTuple tuple; HeapTuple tuple;
Form_pg_class pg_class_tuple; Form_pg_class pg_class_tuple;
...@@ -216,27 +218,27 @@ ExecuteGrantStmt_Table(GrantStmt *stmt) ...@@ -216,27 +218,27 @@ ExecuteGrantStmt_Table(GrantStmt *stmt)
/* open pg_class */ /* open pg_class */
relation = heap_openr(RelationRelationName, RowExclusiveLock); relation = heap_openr(RelationRelationName, RowExclusiveLock);
tuple = SearchSysCache(RELNAME, relOid = RangeVarGetRelid(relvar, false);
PointerGetDatum(relname), tuple = SearchSysCache(RELOID,
ObjectIdGetDatum(relOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tuple)) if (!HeapTupleIsValid(tuple))
elog(ERROR, "relation \"%s\" not found", elog(ERROR, "relation %u not found", relOid);
relname);
pg_class_tuple = (Form_pg_class) GETSTRUCT(tuple); pg_class_tuple = (Form_pg_class) GETSTRUCT(tuple);
if (!pg_class_ownercheck(tuple->t_data->t_oid, GetUserId())) if (!pg_class_ownercheck(relOid, GetUserId()))
elog(ERROR, "%s: permission denied", elog(ERROR, "%s: permission denied",
relname); relvar->relname);
if (pg_class_tuple->relkind == RELKIND_INDEX) if (pg_class_tuple->relkind == RELKIND_INDEX)
elog(ERROR, "\"%s\" is an index", elog(ERROR, "\"%s\" is an index",
relname); relvar->relname);
/* /*
* If there's no ACL, create a default using the pg_class.relowner * If there's no ACL, create a default using the pg_class.relowner
* field. * field.
*/ */
aclDatum = SysCacheGetAttr(RELNAME, tuple, Anum_pg_class_relacl, aclDatum = SysCacheGetAttr(RELOID, tuple, Anum_pg_class_relacl,
&isNull); &isNull);
if (isNull) if (isNull)
old_acl = acldefault(pg_class_tuple->relowner); old_acl = acldefault(pg_class_tuple->relowner);
......
...@@ -10,7 +10,7 @@ ...@@ -10,7 +10,7 @@
# #
# #
# IDENTIFICATION # IDENTIFICATION
# $Header: /cvsroot/pgsql/src/backend/catalog/Attic/genbki.sh,v 1.25 2001/11/30 20:21:06 tgl Exp $ # $Header: /cvsroot/pgsql/src/backend/catalog/Attic/genbki.sh,v 1.26 2002/03/26 19:15:24 tgl Exp $
# #
# NOTES # NOTES
# non-essential whitespace is removed from the generated file. # non-essential whitespace is removed from the generated file.
...@@ -136,6 +136,14 @@ for dir in $INCLUDE_DIRS; do ...@@ -136,6 +136,14 @@ for dir in $INCLUDE_DIRS; do
fi fi
done done
# Get PG_CATALOG_NAMESPACE from catalog/pg_namespace.h
for dir in $INCLUDE_DIRS; do
if [ -f "$dir/catalog/pg_namespace.h" ]; then
PG_CATALOG_NAMESPACE=`grep '^#define[ ]*PG_CATALOG_NAMESPACE' $dir/catalog/pg_namespace.h | $AWK '{ print $3 }'`
break
fi
done
# Get FirstGenBKIObjectId from access/transam.h # Get FirstGenBKIObjectId from access/transam.h
for dir in $INCLUDE_DIRS; do for dir in $INCLUDE_DIRS; do
if [ -f "$dir/access/transam.h" ]; then if [ -f "$dir/access/transam.h" ]; then
...@@ -185,6 +193,7 @@ sed -e "s/;[ ]*$//g" \ ...@@ -185,6 +193,7 @@ sed -e "s/;[ ]*$//g" \
-e "s/(TransactionId/(xid/g" \ -e "s/(TransactionId/(xid/g" \
-e "s/PGUID/1/g" \ -e "s/PGUID/1/g" \
-e "s/NAMEDATALEN/$NAMEDATALEN/g" \ -e "s/NAMEDATALEN/$NAMEDATALEN/g" \
-e "s/PGNSP/$PG_CATALOG_NAMESPACE/g" \
-e "s/DEFAULT_ATTSTATTARGET/$DEFAULTATTSTATTARGET/g" \ -e "s/DEFAULT_ATTSTATTARGET/$DEFAULTATTSTATTARGET/g" \
-e "s/INDEX_MAX_KEYS\*2/$INDEXMAXKEYS2/g" \ -e "s/INDEX_MAX_KEYS\*2/$INDEXMAXKEYS2/g" \
-e "s/INDEX_MAX_KEYS\*4/$INDEXMAXKEYS4/g" \ -e "s/INDEX_MAX_KEYS\*4/$INDEXMAXKEYS4/g" \
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/catalog/heap.c,v 1.191 2002/03/22 02:56:30 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/catalog/heap.c,v 1.192 2002/03/26 19:15:25 tgl Exp $
* *
* *
* INTERFACE ROUTINES * INTERFACE ROUTINES
...@@ -38,7 +38,7 @@ ...@@ -38,7 +38,7 @@
#include "catalog/indexing.h" #include "catalog/indexing.h"
#include "catalog/pg_attrdef.h" #include "catalog/pg_attrdef.h"
#include "catalog/pg_inherits.h" #include "catalog/pg_inherits.h"
#include "catalog/pg_index.h" #include "catalog/pg_namespace.h"
#include "catalog/pg_relcheck.h" #include "catalog/pg_relcheck.h"
#include "catalog/pg_statistic.h" #include "catalog/pg_statistic.h"
#include "catalog/pg_type.h" #include "catalog/pg_type.h"
...@@ -50,11 +50,9 @@ ...@@ -50,11 +50,9 @@
#include "optimizer/planmain.h" #include "optimizer/planmain.h"
#include "optimizer/prep.h" #include "optimizer/prep.h"
#include "optimizer/var.h" #include "optimizer/var.h"
#include "parser/parse_coerce.h"
#include "parser/parse_expr.h" #include "parser/parse_expr.h"
#include "parser/parse_relation.h" #include "parser/parse_relation.h"
#include "parser/parse_target.h" #include "parser/parse_target.h"
#include "parser/parse_type.h"
#include "rewrite/rewriteRemove.h" #include "rewrite/rewriteRemove.h"
#include "storage/smgr.h" #include "storage/smgr.h"
#include "utils/builtins.h" #include "utils/builtins.h"
...@@ -214,6 +212,7 @@ SystemAttributeByName(const char *attname, bool relhasoids) ...@@ -214,6 +212,7 @@ SystemAttributeByName(const char *attname, bool relhasoids)
*/ */
Relation Relation
heap_create(char *relname, heap_create(char *relname,
Oid relnamespace,
TupleDesc tupDesc, TupleDesc tupDesc,
bool istemp, bool istemp,
bool storage_create, bool storage_create,
...@@ -222,7 +221,8 @@ heap_create(char *relname, ...@@ -222,7 +221,8 @@ heap_create(char *relname,
static unsigned int uniqueId = 0; static unsigned int uniqueId = 0;
Oid relid; Oid relid;
Oid tblNode = MyDatabaseId; Oid dbid = MyDatabaseId;
RelFileNode rnode;
bool nailme = false; bool nailme = false;
Relation rel; Relation rel;
...@@ -238,9 +238,11 @@ heap_create(char *relname, ...@@ -238,9 +238,11 @@ heap_create(char *relname,
/* /*
* Real ugly stuff to assign the proper relid in the relation * Real ugly stuff to assign the proper relid in the relation
* descriptor follows. Note that only "bootstrapped" relations whose * descriptor follows. Note that only "bootstrapped" relations whose
* OIDs are hard-coded in pg_class.h need be listed here. * OIDs are hard-coded in pg_class.h need be listed here. We also
* have to take special care for those rels that should be nailed
* in cache and/or are shared across databases.
*/ */
if (relname && IsSystemRelationName(relname)) if (relname && relnamespace == PG_CATALOG_NAMESPACE)
{ {
if (strcmp(TypeRelationName, relname) == 0) if (strcmp(TypeRelationName, relname) == 0)
{ {
...@@ -264,24 +266,24 @@ heap_create(char *relname, ...@@ -264,24 +266,24 @@ heap_create(char *relname,
} }
else if (strcmp(ShadowRelationName, relname) == 0) else if (strcmp(ShadowRelationName, relname) == 0)
{ {
tblNode = InvalidOid; dbid = InvalidOid;
relid = RelOid_pg_shadow; relid = RelOid_pg_shadow;
} }
else if (strcmp(GroupRelationName, relname) == 0) else if (strcmp(GroupRelationName, relname) == 0)
{ {
tblNode = InvalidOid; dbid = InvalidOid;
relid = RelOid_pg_group; relid = RelOid_pg_group;
} }
else if (strcmp(DatabaseRelationName, relname) == 0) else if (strcmp(DatabaseRelationName, relname) == 0)
{ {
tblNode = InvalidOid; dbid = InvalidOid;
relid = RelOid_pg_database; relid = RelOid_pg_database;
} }
else else
{ {
relid = newoid(); relid = newoid();
if (IsSharedSystemRelationName(relname)) if (IsSharedSystemRelationName(relname))
tblNode = InvalidOid; dbid = InvalidOid;
} }
} }
else else
...@@ -297,11 +299,21 @@ heap_create(char *relname, ...@@ -297,11 +299,21 @@ heap_create(char *relname,
PG_TEMP_REL_PREFIX, (int) MyProcPid, uniqueId++); PG_TEMP_REL_PREFIX, (int) MyProcPid, uniqueId++);
} }
/*
* For now, the physical identifier of the relation is the same as the
* logical identifier.
*/
rnode.tblNode = dbid;
rnode.relNode = relid;
/* /*
* build the relcache entry. * build the relcache entry.
*/ */
rel = RelationBuildLocalRelation(relname, tupDesc, rel = RelationBuildLocalRelation(relname,
relid, tblNode, relnamespace,
tupDesc,
relid, dbid,
rnode,
nailme); nailme);
/* /*
...@@ -329,7 +341,7 @@ heap_storage_create(Relation rel) ...@@ -329,7 +341,7 @@ heap_storage_create(Relation rel)
* 1) CheckAttributeNames() is used to make certain the tuple * 1) CheckAttributeNames() is used to make certain the tuple
* descriptor contains a valid set of attribute names * descriptor contains a valid set of attribute names
* *
* 2) pg_class is opened and RelationFindRelid() * 2) pg_class is opened and get_relname_relid()
* performs a scan to ensure that no relation with the * performs a scan to ensure that no relation with the
* same name already exists. * same name already exists.
* *
...@@ -400,73 +412,6 @@ CheckAttributeNames(TupleDesc tupdesc, bool relhasoids) ...@@ -400,73 +412,6 @@ CheckAttributeNames(TupleDesc tupdesc, bool relhasoids)
} }
} }
/* --------------------------------
* RelnameFindRelid
*
* Find any existing relation of the given name.
* --------------------------------
*/
Oid
RelnameFindRelid(const char *relname)
{
Oid relid;
/*
* If this is not bootstrap (initdb) time, use the catalog index on
* pg_class.
*/
if (!IsBootstrapProcessingMode())
{
relid = GetSysCacheOid(RELNAME,
PointerGetDatum(relname),
0, 0, 0);
}
else
{
Relation pg_class_desc;
ScanKeyData key;
HeapScanDesc pg_class_scan;
HeapTuple tuple;
pg_class_desc = heap_openr(RelationRelationName, AccessShareLock);
/*
* At bootstrap time, we have to do this the hard way. Form the
* scan key.
*/
ScanKeyEntryInitialize(&key,
0,
(AttrNumber) Anum_pg_class_relname,
(RegProcedure) F_NAMEEQ,
PointerGetDatum(relname));
/*
* begin the scan
*/
pg_class_scan = heap_beginscan(pg_class_desc,
0,
SnapshotNow,
1,
&key);
/*
* get a tuple. if the tuple is NULL then it means we didn't find
* an existing relation.
*/
tuple = heap_getnext(pg_class_scan, 0);
if (HeapTupleIsValid(tuple))
relid = tuple->t_data->t_oid;
else
relid = InvalidOid;
heap_endscan(pg_class_scan);
heap_close(pg_class_desc, AccessShareLock);
}
return relid;
}
/* -------------------------------- /* --------------------------------
* AddNewAttributeTuples * AddNewAttributeTuples
* *
...@@ -719,6 +664,7 @@ AddNewRelationType(char *typeName, Oid new_rel_oid, Oid new_type_oid) ...@@ -719,6 +664,7 @@ AddNewRelationType(char *typeName, Oid new_rel_oid, Oid new_type_oid)
*/ */
Oid Oid
heap_create_with_catalog(char *relname, heap_create_with_catalog(char *relname,
Oid relnamespace,
TupleDesc tupdesc, TupleDesc tupdesc,
char relkind, char relkind,
bool relhasoids, bool relhasoids,
...@@ -742,7 +688,7 @@ heap_create_with_catalog(char *relname, ...@@ -742,7 +688,7 @@ heap_create_with_catalog(char *relname,
CheckAttributeNames(tupdesc, relhasoids); CheckAttributeNames(tupdesc, relhasoids);
/* temp tables can mask non-temp tables */ /* temp tables can mask non-temp tables */
if ((!istemp && RelnameFindRelid(relname)) || if ((!istemp && get_relname_relid(relname, relnamespace)) ||
(istemp && is_temp_rel_name(relname))) (istemp && is_temp_rel_name(relname)))
elog(ERROR, "Relation '%s' already exists", relname); elog(ERROR, "Relation '%s' already exists", relname);
...@@ -765,8 +711,8 @@ heap_create_with_catalog(char *relname, ...@@ -765,8 +711,8 @@ heap_create_with_catalog(char *relname,
* heap_storage_create() does all the "real" work of creating the disk * heap_storage_create() does all the "real" work of creating the disk
* file for the relation. * file for the relation.
*/ */
new_rel_desc = heap_create(relname, tupdesc, istemp, false, new_rel_desc = heap_create(relname, relnamespace, tupdesc,
allow_system_table_mods); istemp, false, allow_system_table_mods);
/* Fetch the relation OID assigned by heap_create */ /* Fetch the relation OID assigned by heap_create */
new_rel_oid = new_rel_desc->rd_att->attrs[0]->attrelid; new_rel_oid = new_rel_desc->rd_att->attrs[0]->attrelid;
...@@ -916,10 +862,8 @@ RelationRemoveInheritance(Relation relation) ...@@ -916,10 +862,8 @@ RelationRemoveInheritance(Relation relation)
heap_close(catalogRelation, RowExclusiveLock); heap_close(catalogRelation, RowExclusiveLock);
} }
/* -------------------------------- /*
* RelationRemoveIndexes * RelationRemoveIndexes
*
* --------------------------------
*/ */
static void static void
RelationRemoveIndexes(Relation relation) RelationRemoveIndexes(Relation relation)
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/catalog/index.c,v 1.173 2002/03/03 17:47:54 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/catalog/index.c,v 1.174 2002/03/26 19:15:28 tgl Exp $
* *
* *
* INTERFACE ROUTINES * INTERFACE ROUTINES
...@@ -48,10 +48,12 @@ ...@@ -48,10 +48,12 @@
#include "utils/catcache.h" #include "utils/catcache.h"
#include "utils/fmgroids.h" #include "utils/fmgroids.h"
#include "utils/inval.h" #include "utils/inval.h"
#include "utils/lsyscache.h"
#include "utils/relcache.h" #include "utils/relcache.h"
#include "utils/syscache.h" #include "utils/syscache.h"
#include "utils/temprel.h" #include "utils/temprel.h"
/* /*
* macros used in guessing how many tuples are on a page. * macros used in guessing how many tuples are on a page.
*/ */
...@@ -61,15 +63,13 @@ ...@@ -61,15 +63,13 @@
((natts) * AVG_ATTR_SIZE + MAXALIGN(sizeof(HeapTupleHeaderData)))) ((natts) * AVG_ATTR_SIZE + MAXALIGN(sizeof(HeapTupleHeaderData))))
/* non-export function prototypes */ /* non-export function prototypes */
static Oid GetHeapRelationOid(char *heapRelationName, char *indexRelationName,
bool istemp);
static TupleDesc BuildFuncTupleDesc(Oid funcOid, static TupleDesc BuildFuncTupleDesc(Oid funcOid,
Oid *classObjectId); Oid *classObjectId);
static TupleDesc ConstructTupleDescriptor(Relation heapRelation, static TupleDesc ConstructTupleDescriptor(Relation heapRelation,
int numatts, AttrNumber *attNums, int numatts, AttrNumber *attNums,
Oid *classObjectId); Oid *classObjectId);
static void ConstructIndexReldesc(Relation indexRelation, Oid amoid); static void ConstructIndexReldesc(Relation indexRelation, Oid amoid);
static Oid UpdateRelationRelation(Relation indexRelation, char *temp_relname); static void UpdateRelationRelation(Relation indexRelation, char *temp_relname);
static void InitializeAttributeOids(Relation indexRelation, static void InitializeAttributeOids(Relation indexRelation,
int numatts, Oid indexoid); int numatts, Oid indexoid);
static void AppendAttributeTuples(Relation indexRelation, int numatts); static void AppendAttributeTuples(Relation indexRelation, int numatts);
...@@ -99,33 +99,6 @@ IsReindexProcessing(void) ...@@ -99,33 +99,6 @@ IsReindexProcessing(void)
return reindexing; return reindexing;
} }
/* ----------------------------------------------------------------
* GetHeapRelationOid
* ----------------------------------------------------------------
*/
static Oid
GetHeapRelationOid(char *heapRelationName, char *indexRelationName, bool istemp)
{
Oid indoid;
Oid heapoid;
indoid = RelnameFindRelid(indexRelationName);
if ((!istemp && OidIsValid(indoid)) ||
(istemp && is_temp_rel_name(indexRelationName)))
elog(ERROR, "index named \"%s\" already exists",
indexRelationName);
heapoid = RelnameFindRelid(heapRelationName);
if (!OidIsValid(heapoid))
elog(ERROR, "cannot create index on non-existent relation \"%s\"",
heapRelationName);
return heapoid;
}
static TupleDesc static TupleDesc
BuildFuncTupleDesc(Oid funcOid, BuildFuncTupleDesc(Oid funcOid,
Oid *classObjectId) Oid *classObjectId)
...@@ -356,12 +329,11 @@ ConstructIndexReldesc(Relation indexRelation, Oid amoid) ...@@ -356,12 +329,11 @@ ConstructIndexReldesc(Relation indexRelation, Oid amoid)
* UpdateRelationRelation * UpdateRelationRelation
* ---------------------------------------------------------------- * ----------------------------------------------------------------
*/ */
static Oid static void
UpdateRelationRelation(Relation indexRelation, char *temp_relname) UpdateRelationRelation(Relation indexRelation, char *temp_relname)
{ {
Relation pg_class; Relation pg_class;
HeapTuple tuple; HeapTuple tuple;
Oid tupleOid;
Relation idescs[Num_pg_class_indices]; Relation idescs[Num_pg_class_indices];
pg_class = heap_openr(RelationRelationName, RowExclusiveLock); pg_class = heap_openr(RelationRelationName, RowExclusiveLock);
...@@ -372,9 +344,8 @@ UpdateRelationRelation(Relation indexRelation, char *temp_relname) ...@@ -372,9 +344,8 @@ UpdateRelationRelation(Relation indexRelation, char *temp_relname)
(void *) indexRelation->rd_rel); (void *) indexRelation->rd_rel);
/* /*
* the new tuple must have the same oid as the relcache entry for the * the new tuple must have the oid already chosen for the index.
* index. sure would be embarrassing to do this sort of thing in * sure would be embarrassing to do this sort of thing in polite company.
* polite company.
*/ */
tuple->t_data->t_oid = RelationGetRelid(indexRelation); tuple->t_data->t_oid = RelationGetRelid(indexRelation);
heap_insert(pg_class, tuple); heap_insert(pg_class, tuple);
...@@ -396,11 +367,8 @@ UpdateRelationRelation(Relation indexRelation, char *temp_relname) ...@@ -396,11 +367,8 @@ UpdateRelationRelation(Relation indexRelation, char *temp_relname)
CatalogCloseIndices(Num_pg_class_indices, idescs); CatalogCloseIndices(Num_pg_class_indices, idescs);
} }
tupleOid = tuple->t_data->t_oid;
heap_freetuple(tuple); heap_freetuple(tuple);
heap_close(pg_class, RowExclusiveLock); heap_close(pg_class, RowExclusiveLock);
return tupleOid;
} }
/* ---------------------------------------------------------------- /* ----------------------------------------------------------------
...@@ -586,24 +554,31 @@ UpdateIndexRelation(Oid indexoid, ...@@ -586,24 +554,31 @@ UpdateIndexRelation(Oid indexoid,
* ---------------------------------------------------------------- * ----------------------------------------------------------------
*/ */
Oid Oid
index_create(char *heapRelationName, index_create(Oid heapRelationId,
char *indexRelationName, char *indexRelationName,
IndexInfo *indexInfo, IndexInfo *indexInfo,
Oid accessMethodObjectId, Oid accessMethodObjectId,
Oid *classObjectId, Oid *classObjectId,
bool istemp,
bool primary, bool primary,
bool allow_system_table_mods) bool allow_system_table_mods)
{ {
Relation heapRelation; Relation heapRelation;
Relation indexRelation; Relation indexRelation;
TupleDesc indexTupDesc; TupleDesc indexTupDesc;
Oid heapoid; Oid namespaceId;
Oid indexoid; Oid indexoid;
bool istemp = is_temp_rel_name(heapRelationName);
char *temp_relname = NULL; char *temp_relname = NULL;
SetReindexProcessing(false); SetReindexProcessing(false);
/*
* Only SELECT ... FOR UPDATE are allowed while doing this
*/
heapRelation = heap_open(heapRelationId, ShareLock);
namespaceId = RelationGetNamespace(heapRelation);
/* /*
* check parameters * check parameters
*/ */
...@@ -611,19 +586,15 @@ index_create(char *heapRelationName, ...@@ -611,19 +586,15 @@ index_create(char *heapRelationName,
indexInfo->ii_NumKeyAttrs < 1) indexInfo->ii_NumKeyAttrs < 1)
elog(ERROR, "must index at least one column"); elog(ERROR, "must index at least one column");
if (heapRelationName && !allow_system_table_mods && if (!allow_system_table_mods &&
IsSystemRelationName(heapRelationName) && IsNormalProcessingMode()) IsSystemRelationName(RelationGetRelationName(heapRelation)) &&
IsNormalProcessingMode())
elog(ERROR, "User-defined indexes on system catalogs are not supported"); elog(ERROR, "User-defined indexes on system catalogs are not supported");
/* if ((!istemp && get_relname_relid(indexRelationName, namespaceId)) ||
* get heap relation oid and open the heap relation (istemp && is_temp_rel_name(indexRelationName)))
*/ elog(ERROR, "index named \"%s\" already exists",
heapoid = GetHeapRelationOid(heapRelationName, indexRelationName, istemp); indexRelationName);
/*
* Only SELECT ... FOR UPDATE are allowed while doing this
*/
heapRelation = heap_open(heapoid, ShareLock);
/* /*
* construct tuple descriptor for index tuples * construct tuple descriptor for index tuples
...@@ -649,8 +620,11 @@ index_create(char *heapRelationName, ...@@ -649,8 +620,11 @@ index_create(char *heapRelationName,
/* /*
* create the index relation * create the index relation
*/ */
indexRelation = heap_create(indexRelationName, indexTupDesc, indexRelation = heap_create(indexRelationName,
namespaceId,
indexTupDesc,
istemp, false, allow_system_table_mods); istemp, false, allow_system_table_mods);
indexoid = RelationGetRelid(indexRelation);
/* /*
* Obtain exclusive lock on it. Although no other backends can see it * Obtain exclusive lock on it. Although no other backends can see it
...@@ -671,7 +645,7 @@ index_create(char *heapRelationName, ...@@ -671,7 +645,7 @@ index_create(char *heapRelationName,
* (append RELATION tuple) * (append RELATION tuple)
* ---------------- * ----------------
*/ */
indexoid = UpdateRelationRelation(indexRelation, temp_relname); UpdateRelationRelation(indexRelation, temp_relname);
/* /*
* We create the disk file for this relation here * We create the disk file for this relation here
...@@ -699,7 +673,7 @@ index_create(char *heapRelationName, ...@@ -699,7 +673,7 @@ index_create(char *heapRelationName,
* (Or, could define a rule to maintain the predicate) --Nels, Feb '92 * (Or, could define a rule to maintain the predicate) --Nels, Feb '92
* ---------------- * ----------------
*/ */
UpdateIndexRelation(indexoid, heapoid, indexInfo, UpdateIndexRelation(indexoid, heapRelationId, indexInfo,
classObjectId, primary); classObjectId, primary);
/* /*
...@@ -725,7 +699,7 @@ index_create(char *heapRelationName, ...@@ -725,7 +699,7 @@ index_create(char *heapRelationName,
*/ */
if (IsBootstrapProcessingMode()) if (IsBootstrapProcessingMode())
{ {
index_register(heapRelationName, indexRelationName, indexInfo); index_register(heapRelationId, indexoid, indexInfo);
/* XXX shouldn't we close the heap and index rels here? */ /* XXX shouldn't we close the heap and index rels here? */
} }
else else
......
...@@ -9,7 +9,7 @@ ...@@ -9,7 +9,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/catalog/indexing.c,v 1.84 2002/03/22 21:34:44 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/catalog/indexing.c,v 1.85 2002/03/26 19:15:30 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -44,7 +44,7 @@ char *Name_pg_attr_indices[Num_pg_attr_indices] = ...@@ -44,7 +44,7 @@ char *Name_pg_attr_indices[Num_pg_attr_indices] =
char *Name_pg_attrdef_indices[Num_pg_attrdef_indices] = char *Name_pg_attrdef_indices[Num_pg_attrdef_indices] =
{AttrDefaultIndex}; {AttrDefaultIndex};
char *Name_pg_class_indices[Num_pg_class_indices] = char *Name_pg_class_indices[Num_pg_class_indices] =
{ClassNameIndex, ClassOidIndex}; {ClassNameNspIndex, ClassOidIndex};
char *Name_pg_database_indices[Num_pg_database_indices] = char *Name_pg_database_indices[Num_pg_database_indices] =
{DatabaseNameIndex, DatabaseOidIndex}; {DatabaseNameIndex, DatabaseOidIndex};
char *Name_pg_group_indices[Num_pg_group_indices] = char *Name_pg_group_indices[Num_pg_group_indices] =
......
/*-------------------------------------------------------------------------
*
* namespace.c
* code to support accessing and searching namespaces
*
* This is separate from pg_namespace.c, which contains the routines that
* directly manipulate the pg_namespace system catalog. This module
* provides routines associated with defining a "namespace search path"
* and implementing search-path-controlled searches.
*
*
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/catalog/namespace.c,v 1.1 2002/03/26 19:15:32 tgl Exp $
*
*-------------------------------------------------------------------------
*/
#include "postgres.h"
#include "catalog/namespace.h"
#include "catalog/pg_namespace.h"
#include "miscadmin.h"
#include "utils/lsyscache.h"
#include "utils/syscache.h"
/*
* RangeVarGetRelid
* Given a RangeVar describing an existing relation,
* select the proper namespace and look up the relation OID.
*
* If the relation is not found, return InvalidOid if failOK = true,
* otherwise raise an error.
*/
Oid
RangeVarGetRelid(const RangeVar *relation, bool failOK)
{
Oid namespaceId;
Oid relId;
/*
* We check the catalog name and then ignore it.
*/
if (relation->catalogname)
{
if (strcmp(relation->catalogname, DatabaseName) != 0)
elog(ERROR, "Cross-database references are not implemented");
}
if (relation->schemaname)
{
namespaceId = GetSysCacheOid(NAMESPACENAME,
CStringGetDatum(relation->schemaname),
0, 0, 0);
if (!OidIsValid(namespaceId))
elog(ERROR, "Namespace \"%s\" does not exist",
relation->schemaname);
relId = get_relname_relid(relation->relname, namespaceId);
}
else
{
relId = RelnameGetRelid(relation->relname);
}
if (!OidIsValid(relId) && !failOK)
{
if (relation->schemaname)
elog(ERROR, "Relation \"%s\".\"%s\" does not exist",
relation->schemaname, relation->relname);
else
elog(ERROR, "Relation \"%s\" does not exist",
relation->relname);
}
return relId;
}
/*
* RangeVarGetCreationNamespace
* Given a RangeVar describing a to-be-created relation,
* choose which namespace to create it in.
*/
Oid
RangeVarGetCreationNamespace(const RangeVar *newRelation)
{
Oid namespaceId;
/*
* We check the catalog name and then ignore it.
*/
if (newRelation->catalogname)
{
if (strcmp(newRelation->catalogname, DatabaseName) != 0)
elog(ERROR, "Cross-database references are not implemented");
}
if (newRelation->schemaname)
{
namespaceId = GetSysCacheOid(NAMESPACENAME,
CStringGetDatum(newRelation->schemaname),
0, 0, 0);
if (!OidIsValid(namespaceId))
elog(ERROR, "Namespace \"%s\" does not exist",
newRelation->schemaname);
}
else
{
/* XXX Wrong! Need to get a default schema from somewhere */
namespaceId = PG_CATALOG_NAMESPACE;
}
return namespaceId;
}
/*
* RelnameGetRelid
* Try to resolve an unqualified relation name.
* Returns OID if relation found in search path, else InvalidOid.
*/
Oid
RelnameGetRelid(const char *relname)
{
/* XXX Wrong! must search search path */
return get_relname_relid(relname, PG_CATALOG_NAMESPACE);
}
...@@ -15,7 +15,7 @@ ...@@ -15,7 +15,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/commands/cluster.c,v 1.72 2002/02/19 20:11:12 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/commands/cluster.c,v 1.73 2002/03/26 19:15:35 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -38,7 +38,8 @@ ...@@ -38,7 +38,8 @@
static Oid copy_heap(Oid OIDOldHeap, char *NewName, bool istemp); static Oid copy_heap(Oid OIDOldHeap, char *NewName, bool istemp);
static void copy_index(Oid OIDOldIndex, Oid OIDNewHeap, char *NewIndexName); static void copy_index(Oid OIDOldIndex, Oid OIDNewHeap, char *NewIndexName,
bool istemp);
static void rebuildheap(Oid OIDNewHeap, Oid OIDOldHeap, Oid OIDOldIndex); static void rebuildheap(Oid OIDNewHeap, Oid OIDOldHeap, Oid OIDOldIndex);
/* /*
...@@ -54,7 +55,7 @@ static void rebuildheap(Oid OIDNewHeap, Oid OIDOldHeap, Oid OIDOldIndex); ...@@ -54,7 +55,7 @@ static void rebuildheap(Oid OIDNewHeap, Oid OIDOldHeap, Oid OIDOldIndex);
* hand, re-creating n indexes may blow out the space. * hand, re-creating n indexes may blow out the space.
*/ */
void void
cluster(char *oldrelname, char *oldindexname) cluster(RangeVar *oldrelation, char *oldindexname)
{ {
Oid OIDOldHeap, Oid OIDOldHeap,
OIDOldIndex, OIDOldIndex,
...@@ -64,34 +65,40 @@ cluster(char *oldrelname, char *oldindexname) ...@@ -64,34 +65,40 @@ cluster(char *oldrelname, char *oldindexname)
bool istemp; bool istemp;
char NewHeapName[NAMEDATALEN]; char NewHeapName[NAMEDATALEN];
char NewIndexName[NAMEDATALEN]; char NewIndexName[NAMEDATALEN];
char saveoldrelname[NAMEDATALEN]; RangeVar *saveoldrelation;
char saveoldindexname[NAMEDATALEN]; RangeVar *saveoldindex;
RangeVar *NewHeap;
RangeVar *NewIndex;
/* /*
* Copy the arguments into local storage, just to be safe. * FIXME SCHEMAS: The old code had the comment:
* "Copy the arguments into local storage, just to be safe."
* By using copyObject we are not using local storage.
* Was that really necessary?
*/ */
StrNCpy(saveoldrelname, oldrelname, NAMEDATALEN); saveoldrelation = copyObject(oldrelation);
StrNCpy(saveoldindexname, oldindexname, NAMEDATALEN); saveoldindex = copyObject(oldrelation);
saveoldindex->relname = pstrdup(oldindexname);
/* /*
* We grab exclusive access to the target rel and index for the * We grab exclusive access to the target rel and index for the
* duration of the transaction. * duration of the transaction.
*/ */
OldHeap = heap_openr(saveoldrelname, AccessExclusiveLock); OldHeap = heap_openrv(saveoldrelation, AccessExclusiveLock);
OIDOldHeap = RelationGetRelid(OldHeap); OIDOldHeap = RelationGetRelid(OldHeap);
OldIndex = index_openr(saveoldindexname); OldIndex = index_openrv(saveoldindex);
LockRelation(OldIndex, AccessExclusiveLock); LockRelation(OldIndex, AccessExclusiveLock);
OIDOldIndex = RelationGetRelid(OldIndex); OIDOldIndex = RelationGetRelid(OldIndex);
istemp = is_temp_rel_name(saveoldrelname); istemp = is_temp_rel_name(saveoldrelation->relname);
/* /*
* Check that index is in fact an index on the given relation * Check that index is in fact an index on the given relation
*/ */
if (OldIndex->rd_index->indrelid != OIDOldHeap) if (OldIndex->rd_index->indrelid != OIDOldHeap)
elog(ERROR, "CLUSTER: \"%s\" is not an index for table \"%s\"", elog(ERROR, "CLUSTER: \"%s\" is not an index for table \"%s\"",
saveoldindexname, saveoldrelname); saveoldindex->relname, saveoldrelation->relname);
/* Drop relcache refcnts, but do NOT give up the locks */ /* Drop relcache refcnts, but do NOT give up the locks */
heap_close(OldHeap, NoLock); heap_close(OldHeap, NoLock);
...@@ -117,21 +124,26 @@ cluster(char *oldrelname, char *oldindexname) ...@@ -117,21 +124,26 @@ cluster(char *oldrelname, char *oldindexname)
/* Create new index over the tuples of the new heap. */ /* Create new index over the tuples of the new heap. */
snprintf(NewIndexName, NAMEDATALEN, "temp_%u", OIDOldIndex); snprintf(NewIndexName, NAMEDATALEN, "temp_%u", OIDOldIndex);
copy_index(OIDOldIndex, OIDNewHeap, NewIndexName); copy_index(OIDOldIndex, OIDNewHeap, NewIndexName, istemp);
CommandCounterIncrement(); CommandCounterIncrement();
/* Destroy old heap (along with its index) and rename new. */ /* Destroy old heap (along with its index) and rename new. */
heap_drop_with_catalog(saveoldrelname, allowSystemTableMods); heap_drop_with_catalog(saveoldrelation->relname, allowSystemTableMods);
CommandCounterIncrement(); CommandCounterIncrement();
renamerel(NewHeapName, saveoldrelname); NewHeap = copyObject(saveoldrelation);
NewHeap->relname = NewHeapName;
NewIndex = copyObject(saveoldindex);
NewIndex->relname = NewIndexName;
renamerel(NewHeap, saveoldrelation->relname);
/* This one might be unnecessary, but let's be safe. */ /* This one might be unnecessary, but let's be safe. */
CommandCounterIncrement(); CommandCounterIncrement();
renamerel(NewIndexName, saveoldindexname); renamerel(NewIndex, saveoldindex->relname);
} }
static Oid static Oid
...@@ -151,7 +163,9 @@ copy_heap(Oid OIDOldHeap, char *NewName, bool istemp) ...@@ -151,7 +163,9 @@ copy_heap(Oid OIDOldHeap, char *NewName, bool istemp)
*/ */
tupdesc = CreateTupleDescCopyConstr(OldHeapDesc); tupdesc = CreateTupleDescCopyConstr(OldHeapDesc);
OIDNewHeap = heap_create_with_catalog(NewName, tupdesc, OIDNewHeap = heap_create_with_catalog(NewName,
RelationGetNamespace(OldHeap),
tupdesc,
OldHeap->rd_rel->relkind, OldHeap->rd_rel->relkind,
OldHeap->rd_rel->relhasoids, OldHeap->rd_rel->relhasoids,
istemp, istemp,
...@@ -168,7 +182,7 @@ copy_heap(Oid OIDOldHeap, char *NewName, bool istemp) ...@@ -168,7 +182,7 @@ copy_heap(Oid OIDOldHeap, char *NewName, bool istemp)
* AlterTableCreateToastTable ends with CommandCounterIncrement(), so * AlterTableCreateToastTable ends with CommandCounterIncrement(), so
* that the TOAST table will be visible for insertion. * that the TOAST table will be visible for insertion.
*/ */
AlterTableCreateToastTable(NewName, true); AlterTableCreateToastTable(OIDNewHeap, true);
heap_close(OldHeap, NoLock); heap_close(OldHeap, NoLock);
...@@ -176,7 +190,7 @@ copy_heap(Oid OIDOldHeap, char *NewName, bool istemp) ...@@ -176,7 +190,7 @@ copy_heap(Oid OIDOldHeap, char *NewName, bool istemp)
} }
static void static void
copy_index(Oid OIDOldIndex, Oid OIDNewHeap, char *NewIndexName) copy_index(Oid OIDOldIndex, Oid OIDNewHeap, char *NewIndexName, bool istemp)
{ {
Relation OldIndex, Relation OldIndex,
NewHeap; NewHeap;
...@@ -189,18 +203,15 @@ copy_index(Oid OIDOldIndex, Oid OIDNewHeap, char *NewIndexName) ...@@ -189,18 +203,15 @@ copy_index(Oid OIDOldIndex, Oid OIDNewHeap, char *NewIndexName)
* Create a new index like the old one. To do this I get the info * Create a new index like the old one. To do this I get the info
* from pg_index, and add a new index with a temporary name (that will * from pg_index, and add a new index with a temporary name (that will
* be changed later). * be changed later).
*
* NOTE: index_create will cause the new index to be a temp relation if
* its parent table is, so we don't need to do anything special for
* the temp-table case here.
*/ */
indexInfo = BuildIndexInfo(OldIndex->rd_index); indexInfo = BuildIndexInfo(OldIndex->rd_index);
index_create(RelationGetRelationName(NewHeap), index_create(OIDNewHeap,
NewIndexName, NewIndexName,
indexInfo, indexInfo,
OldIndex->rd_rel->relam, OldIndex->rd_rel->relam,
OldIndex->rd_index->indclass, OldIndex->rd_index->indclass,
istemp,
OldIndex->rd_index->indisprimary, OldIndex->rd_index->indisprimary,
allowSystemTableMods); allowSystemTableMods);
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/command.c,v 1.165 2002/03/22 21:34:44 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/commands/Attic/command.c,v 1.166 2002/03/26 19:15:36 tgl Exp $
* *
* NOTES * NOTES
* The PerformAddAttribute() code, like most of the relation * The PerformAddAttribute() code, like most of the relation
...@@ -26,6 +26,7 @@ ...@@ -26,6 +26,7 @@
#include "catalog/heap.h" #include "catalog/heap.h"
#include "catalog/index.h" #include "catalog/index.h"
#include "catalog/indexing.h" #include "catalog/indexing.h"
#include "catalog/namespace.h"
#include "catalog/pg_attrdef.h" #include "catalog/pg_attrdef.h"
#include "catalog/pg_index.h" #include "catalog/pg_index.h"
#include "catalog/pg_namespace.h" #include "catalog/pg_namespace.h"
...@@ -34,7 +35,6 @@ ...@@ -34,7 +35,6 @@
#include "catalog/pg_type.h" #include "catalog/pg_type.h"
#include "commands/command.h" #include "commands/command.h"
#include "commands/trigger.h" #include "commands/trigger.h"
#include "commands/defrem.h"
#include "executor/execdefs.h" #include "executor/execdefs.h"
#include "executor/executor.h" #include "executor/executor.h"
#include "miscadmin.h" #include "miscadmin.h"
...@@ -415,8 +415,8 @@ AlterTableAddColumn(const char *relationName, ...@@ -415,8 +415,8 @@ AlterTableAddColumn(const char *relationName,
rel = heap_openr(RelationRelationName, RowExclusiveLock); rel = heap_openr(RelationRelationName, RowExclusiveLock);
reltup = SearchSysCache(RELNAME, reltup = SearchSysCache(RELOID,
PointerGetDatum(relationName), ObjectIdGetDatum(myrelid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(reltup)) if (!HeapTupleIsValid(reltup))
...@@ -424,7 +424,7 @@ AlterTableAddColumn(const char *relationName, ...@@ -424,7 +424,7 @@ AlterTableAddColumn(const char *relationName,
relationName); relationName);
if (SearchSysCacheExists(ATTNAME, if (SearchSysCacheExists(ATTNAME,
ObjectIdGetDatum(reltup->t_data->t_oid), ObjectIdGetDatum(myrelid),
PointerGetDatum(colDef->colname), PointerGetDatum(colDef->colname),
0, 0)) 0, 0))
elog(ERROR, "ALTER TABLE: column name \"%s\" already exists in table \"%s\"", elog(ERROR, "ALTER TABLE: column name \"%s\" already exists in table \"%s\"",
...@@ -463,7 +463,7 @@ AlterTableAddColumn(const char *relationName, ...@@ -463,7 +463,7 @@ AlterTableAddColumn(const char *relationName,
attribute = (Form_pg_attribute) GETSTRUCT(attributeTuple); attribute = (Form_pg_attribute) GETSTRUCT(attributeTuple);
attribute->attrelid = reltup->t_data->t_oid; attribute->attrelid = myrelid;
namestrcpy(&(attribute->attname), colDef->colname); namestrcpy(&(attribute->attname), colDef->colname);
attribute->atttypid = typeTuple->t_data->t_oid; attribute->atttypid = typeTuple->t_data->t_oid;
attribute->attstattarget = DEFAULT_ATTSTATTARGET; attribute->attstattarget = DEFAULT_ATTSTATTARGET;
...@@ -532,7 +532,7 @@ AlterTableAddColumn(const char *relationName, ...@@ -532,7 +532,7 @@ AlterTableAddColumn(const char *relationName,
*/ */
if (colDef->constraints != NIL) if (colDef->constraints != NIL)
{ {
rel = heap_openr(relationName, AccessExclusiveLock); rel = heap_open(myrelid, AccessExclusiveLock);
AddRelationRawConstraints(rel, NIL, colDef->constraints); AddRelationRawConstraints(rel, NIL, colDef->constraints);
heap_close(rel, NoLock); heap_close(rel, NoLock);
} }
...@@ -541,7 +541,7 @@ AlterTableAddColumn(const char *relationName, ...@@ -541,7 +541,7 @@ AlterTableAddColumn(const char *relationName,
* Automatically create the secondary relation for TOAST if it * Automatically create the secondary relation for TOAST if it
* formerly had no such but now has toastable attributes. * formerly had no such but now has toastable attributes.
*/ */
AlterTableCreateToastTable(relationName, true); AlterTableCreateToastTable(myrelid, true);
} }
...@@ -989,11 +989,7 @@ RemoveColumnReferences(Oid reloid, int attnum, bool checkonly, HeapTuple reltup) ...@@ -989,11 +989,7 @@ RemoveColumnReferences(Oid reloid, int attnum, bool checkonly, HeapTuple reltup)
} }
else else
{ {
htup = SearchSysCache(RELOID, index_drop(index->indexrelid);
ObjectIdGetDatum(index->indexrelid),
0, 0, 0);
RemoveIndex(NameStr(((Form_pg_class) GETSTRUCT(htup))->relname));
ReleaseSysCache(htup);
} }
break; break;
} }
...@@ -1066,8 +1062,8 @@ AlterTableDropColumn(const char *relationName, ...@@ -1066,8 +1062,8 @@ AlterTableDropColumn(const char *relationName,
* lock the pg_class tuple for update * lock the pg_class tuple for update
*/ */
rel = heap_openr(RelationRelationName, RowExclusiveLock); rel = heap_openr(RelationRelationName, RowExclusiveLock);
reltup = SearchSysCache(RELNAME, reltup = SearchSysCache(RELOID,
PointerGetDatum(relationName), ObjectIdGetDatum(myrelid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(reltup)) if (!HeapTupleIsValid(reltup))
elog(ERROR, "ALTER TABLE: relation \"%s\" not found", elog(ERROR, "ALTER TABLE: relation \"%s\" not found",
...@@ -1092,7 +1088,7 @@ AlterTableDropColumn(const char *relationName, ...@@ -1092,7 +1088,7 @@ AlterTableDropColumn(const char *relationName,
* Get the target pg_attribute tuple and make a modifiable copy * Get the target pg_attribute tuple and make a modifiable copy
*/ */
tup = SearchSysCacheCopy(ATTNAME, tup = SearchSysCacheCopy(ATTNAME,
ObjectIdGetDatum(reltup->t_data->t_oid), ObjectIdGetDatum(myrelid),
PointerGetDatum(colName), PointerGetDatum(colName),
0, 0); 0, 0);
if (!HeapTupleIsValid(tup)) if (!HeapTupleIsValid(tup))
...@@ -1370,7 +1366,8 @@ AlterTableAddConstraint(char *relationName, ...@@ -1370,7 +1366,8 @@ AlterTableAddConstraint(char *relationName,
* someone doesn't delete rows out from under us. * someone doesn't delete rows out from under us.
*/ */
pkrel = heap_openr(fkconstraint->pktable->relname, AccessExclusiveLock); pkrel = heap_openrv(fkconstraint->pktable,
AccessExclusiveLock);
if (pkrel->rd_rel->relkind != RELKIND_RELATION) if (pkrel->rd_rel->relkind != RELKIND_RELATION)
elog(ERROR, "referenced table \"%s\" not a relation", elog(ERROR, "referenced table \"%s\" not a relation",
fkconstraint->pktable->relname); fkconstraint->pktable->relname);
...@@ -1557,43 +1554,48 @@ AlterTableDropConstraint(const char *relationName, ...@@ -1557,43 +1554,48 @@ AlterTableDropConstraint(const char *relationName,
* ALTER TABLE OWNER * ALTER TABLE OWNER
*/ */
void void
AlterTableOwner(const char *relationName, const char *newOwnerName) AlterTableOwner(const RangeVar *tgtrel, const char *newOwnerName)
{ {
Oid relationOid; Relation rel;
Relation relation; Oid myrelid;
int32 newOwnerSysId; int32 newOwnerSysId;
/* check that we are the superuser */ /* check that we are the superuser */
if (!superuser()) if (!superuser())
elog(ERROR, "ALTER TABLE: permission denied"); elog(ERROR, "ALTER TABLE: permission denied");
/* lookup the OID of the target relation */ /* lookup the OID of the target relation */
relation = RelationNameGetRelation(relationName); rel = relation_openrv(tgtrel, AccessExclusiveLock);
relationOid = relation->rd_id; myrelid = RelationGetRelid(rel);
RelationClose(relation); heap_close(rel, NoLock); /* close rel but keep lock! */
/* lookup the sysid of the new owner */ /* lookup the sysid of the new owner */
newOwnerSysId = get_usesysid(newOwnerName); newOwnerSysId = get_usesysid(newOwnerName);
/* do all the actual work */ /* do all the actual work */
AlterTableOwnerId(relationOid, newOwnerSysId); AlterTableOwnerId(myrelid, newOwnerSysId);
} }
static void static void
AlterTableOwnerId(Oid relationOid, int32 newOwnerSysId) AlterTableOwnerId(Oid relationOid, int32 newOwnerSysId)
{ {
Relation target_rel;
Relation class_rel; Relation class_rel;
HeapTuple tuple; HeapTuple tuple;
Relation idescs[Num_pg_class_indices]; Relation idescs[Num_pg_class_indices];
Form_pg_class tuple_class; Form_pg_class tuple_class;
/* Get exclusive lock till end of transaction on the target table */
target_rel = heap_open(relationOid, AccessExclusiveLock);
/* Get its pg_class tuple, too */
class_rel = heap_openr(RelationRelationName, RowExclusiveLock);
tuple = SearchSysCacheCopy(RELOID, tuple = SearchSysCacheCopy(RELOID,
ObjectIdGetDatum(relationOid), ObjectIdGetDatum(relationOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tuple)) if (!HeapTupleIsValid(tuple))
elog(ERROR, "ALTER TABLE: object ID %hd not found", elog(ERROR, "ALTER TABLE: relation %u not found", relationOid);
relationOid);
tuple_class = (Form_pg_class) GETSTRUCT(tuple); tuple_class = (Form_pg_class) GETSTRUCT(tuple);
/* Can we change the ownership of this tuple? */ /* Can we change the ownership of this tuple? */
...@@ -1603,7 +1605,6 @@ AlterTableOwnerId(Oid relationOid, int32 newOwnerSysId) ...@@ -1603,7 +1605,6 @@ AlterTableOwnerId(Oid relationOid, int32 newOwnerSysId)
* Okay, this is a valid tuple: change its ownership and * Okay, this is a valid tuple: change its ownership and
* write to the heap. * write to the heap.
*/ */
class_rel = heap_openr(RelationRelationName, RowExclusiveLock);
tuple_class->relowner = newOwnerSysId; tuple_class->relowner = newOwnerSysId;
simple_heap_update(class_rel, &tuple->t_self, tuple); simple_heap_update(class_rel, &tuple->t_self, tuple);
...@@ -1617,25 +1618,25 @@ AlterTableOwnerId(Oid relationOid, int32 newOwnerSysId) ...@@ -1617,25 +1618,25 @@ AlterTableOwnerId(Oid relationOid, int32 newOwnerSysId)
* indexes that belong to the table, as well as the table's toast * indexes that belong to the table, as well as the table's toast
* table (if it has one) * table (if it has one)
*/ */
if (tuple_class->relkind == RELKIND_RELATION) if (tuple_class->relkind == RELKIND_RELATION ||
tuple_class->relkind == RELKIND_TOASTVALUE)
{ {
/* Search for indexes belonging to this table */
Relation target_rel;
List *index_oid_list, *i; List *index_oid_list, *i;
/* Find all the indexes belonging to this relation */ /* Find all the indexes belonging to this relation */
target_rel = heap_open(relationOid, RowExclusiveLock);
index_oid_list = RelationGetIndexList(target_rel); index_oid_list = RelationGetIndexList(target_rel);
heap_close(target_rel, RowExclusiveLock);
/* For each index, recursively change its ownership */ /* For each index, recursively change its ownership */
foreach (i, index_oid_list) foreach(i, index_oid_list)
{ {
AlterTableOwnerId(lfirsti(i), newOwnerSysId); AlterTableOwnerId(lfirsti(i), newOwnerSysId);
} }
freeList(index_oid_list); freeList(index_oid_list);
}
if (tuple_class->relkind == RELKIND_RELATION)
{
/* If it has a toast table, recurse to change its ownership */ /* If it has a toast table, recurse to change its ownership */
if (tuple_class->reltoastrelid != InvalidOid) if (tuple_class->reltoastrelid != InvalidOid)
{ {
...@@ -1644,7 +1645,8 @@ AlterTableOwnerId(Oid relationOid, int32 newOwnerSysId) ...@@ -1644,7 +1645,8 @@ AlterTableOwnerId(Oid relationOid, int32 newOwnerSysId)
} }
heap_freetuple(tuple); heap_freetuple(tuple);
heap_close(class_rel, NoLock); heap_close(class_rel, RowExclusiveLock);
heap_close(target_rel, NoLock);
} }
static void static void
...@@ -1669,10 +1671,9 @@ CheckTupleType(Form_pg_class tuple_class) ...@@ -1669,10 +1671,9 @@ CheckTupleType(Form_pg_class tuple_class)
* ALTER TABLE CREATE TOAST TABLE * ALTER TABLE CREATE TOAST TABLE
*/ */
void void
AlterTableCreateToastTable(const char *relationName, bool silent) AlterTableCreateToastTable(Oid relOid, bool silent)
{ {
Relation rel; Relation rel;
Oid myrelid;
HeapTuple reltup; HeapTuple reltup;
HeapTupleData classtuple; HeapTupleData classtuple;
TupleDesc tupdesc; TupleDesc tupdesc;
...@@ -1690,14 +1691,13 @@ AlterTableCreateToastTable(const char *relationName, bool silent) ...@@ -1690,14 +1691,13 @@ AlterTableCreateToastTable(const char *relationName, bool silent)
* Grab an exclusive lock on the target table, which we will NOT * Grab an exclusive lock on the target table, which we will NOT
* release until end of transaction. * release until end of transaction.
*/ */
rel = heap_openr(relationName, AccessExclusiveLock); rel = heap_open(relOid, AccessExclusiveLock);
myrelid = RelationGetRelid(rel);
if (rel->rd_rel->relkind != RELKIND_RELATION) if (rel->rd_rel->relkind != RELKIND_RELATION)
elog(ERROR, "ALTER TABLE: relation \"%s\" is not a table", elog(ERROR, "ALTER TABLE: relation \"%s\" is not a table",
relationName); RelationGetRelationName(rel));
if (!pg_class_ownercheck(myrelid, GetUserId())) if (!pg_class_ownercheck(relOid, GetUserId()))
elog(ERROR, "ALTER TABLE: permission denied"); elog(ERROR, "ALTER TABLE: permission denied");
/* /*
...@@ -1705,12 +1705,12 @@ AlterTableCreateToastTable(const char *relationName, bool silent) ...@@ -1705,12 +1705,12 @@ AlterTableCreateToastTable(const char *relationName, bool silent)
*/ */
class_rel = heap_openr(RelationRelationName, RowExclusiveLock); class_rel = heap_openr(RelationRelationName, RowExclusiveLock);
reltup = SearchSysCache(RELNAME, reltup = SearchSysCache(RELOID,
PointerGetDatum(relationName), ObjectIdGetDatum(relOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(reltup)) if (!HeapTupleIsValid(reltup))
elog(ERROR, "ALTER TABLE: relation \"%s\" not found", elog(ERROR, "ALTER TABLE: relation \"%s\" not found",
relationName); RelationGetRelationName(rel));
classtuple.t_self = reltup->t_self; classtuple.t_self = reltup->t_self;
ReleaseSysCache(reltup); ReleaseSysCache(reltup);
...@@ -1739,7 +1739,7 @@ AlterTableCreateToastTable(const char *relationName, bool silent) ...@@ -1739,7 +1739,7 @@ AlterTableCreateToastTable(const char *relationName, bool silent)
} }
elog(ERROR, "ALTER TABLE: relation \"%s\" already has a toast table", elog(ERROR, "ALTER TABLE: relation \"%s\" already has a toast table",
relationName); RelationGetRelationName(rel));
} }
/* /*
...@@ -1756,14 +1756,14 @@ AlterTableCreateToastTable(const char *relationName, bool silent) ...@@ -1756,14 +1756,14 @@ AlterTableCreateToastTable(const char *relationName, bool silent)
} }
elog(ERROR, "ALTER TABLE: relation \"%s\" does not need a toast table", elog(ERROR, "ALTER TABLE: relation \"%s\" does not need a toast table",
relationName); RelationGetRelationName(rel));
} }
/* /*
* Create the toast table and its index * Create the toast table and its index
*/ */
sprintf(toast_relname, "pg_toast_%u", myrelid); sprintf(toast_relname, "pg_toast_%u", relOid);
sprintf(toast_idxname, "pg_toast_%u_idx", myrelid); sprintf(toast_idxname, "pg_toast_%u_idx", relOid);
/* this is pretty painful... need a tuple descriptor */ /* this is pretty painful... need a tuple descriptor */
tupdesc = CreateTemplateTupleDesc(3); tupdesc = CreateTemplateTupleDesc(3);
...@@ -1795,7 +1795,9 @@ AlterTableCreateToastTable(const char *relationName, bool silent) ...@@ -1795,7 +1795,9 @@ AlterTableCreateToastTable(const char *relationName, bool silent)
* collision, and the toast rel will be destroyed when its master is, * collision, and the toast rel will be destroyed when its master is,
* so there's no need to handle the toast rel as temp. * so there's no need to handle the toast rel as temp.
*/ */
toast_relid = heap_create_with_catalog(toast_relname, tupdesc, toast_relid = heap_create_with_catalog(toast_relname,
RelationGetNamespace(rel),
tupdesc,
RELKIND_TOASTVALUE, false, RELKIND_TOASTVALUE, false,
false, true); false, true);
...@@ -1825,9 +1827,9 @@ AlterTableCreateToastTable(const char *relationName, bool silent) ...@@ -1825,9 +1827,9 @@ AlterTableCreateToastTable(const char *relationName, bool silent)
classObjectId[0] = OID_BTREE_OPS_OID; classObjectId[0] = OID_BTREE_OPS_OID;
classObjectId[1] = INT4_BTREE_OPS_OID; classObjectId[1] = INT4_BTREE_OPS_OID;
toast_idxid = index_create(toast_relname, toast_idxname, indexInfo, toast_idxid = index_create(toast_relid, toast_idxname, indexInfo,
BTREE_AM_OID, classObjectId, BTREE_AM_OID, classObjectId,
true, true); false, true, true);
/* /*
* Update toast rel's pg_class entry to show that it has an index. The * Update toast rel's pg_class entry to show that it has an index. The
...@@ -1927,21 +1929,15 @@ LockTableCommand(LockStmt *lockstmt) ...@@ -1927,21 +1929,15 @@ LockTableCommand(LockStmt *lockstmt)
foreach(p, lockstmt->relations) foreach(p, lockstmt->relations)
{ {
RangeVar *relation = lfirst(p); RangeVar *relation = lfirst(p);
char *relname = relation->relname;
Oid reloid; Oid reloid;
int aclresult; int32 aclresult;
Relation rel; Relation rel;
/* /*
* We don't want to open the relation until we've checked privilege. * We don't want to open the relation until we've checked privilege.
* So, manually get the relation OID. * So, manually get the relation OID.
*/ */
reloid = GetSysCacheOid(RELNAME, reloid = RangeVarGetRelid(relation, false);
PointerGetDatum(relname),
0, 0, 0);
if (!OidIsValid(reloid))
elog(ERROR, "LOCK TABLE: relation \"%s\" does not exist",
relname);
if (lockstmt->mode == AccessShareLock) if (lockstmt->mode == AccessShareLock)
aclresult = pg_class_aclcheck(reloid, GetUserId(), aclresult = pg_class_aclcheck(reloid, GetUserId(),
...@@ -1958,7 +1954,7 @@ LockTableCommand(LockStmt *lockstmt) ...@@ -1958,7 +1954,7 @@ LockTableCommand(LockStmt *lockstmt)
/* Currently, we only allow plain tables to be locked */ /* Currently, we only allow plain tables to be locked */
if (rel->rd_rel->relkind != RELKIND_RELATION) if (rel->rd_rel->relkind != RELKIND_RELATION)
elog(ERROR, "LOCK TABLE: %s is not a table", elog(ERROR, "LOCK TABLE: %s is not a table",
relname); relation->relname);
relation_close(rel, NoLock); /* close rel, keep lock */ relation_close(rel, NoLock); /* close rel, keep lock */
} }
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Copyright (c) 1999-2001, PostgreSQL Global Development Group * Copyright (c) 1999-2001, PostgreSQL Global Development Group
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/commands/comment.c,v 1.36 2002/03/21 23:27:20 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/commands/comment.c,v 1.37 2002/03/26 19:15:38 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -20,6 +20,7 @@ ...@@ -20,6 +20,7 @@
#include "catalog/indexing.h" #include "catalog/indexing.h"
#include "catalog/pg_database.h" #include "catalog/pg_database.h"
#include "catalog/pg_description.h" #include "catalog/pg_description.h"
#include "catalog/pg_namespace.h"
#include "catalog/pg_operator.h" #include "catalog/pg_operator.h"
#include "catalog/pg_rewrite.h" #include "catalog/pg_rewrite.h"
#include "catalog/pg_trigger.h" #include "catalog/pg_trigger.h"
...@@ -48,7 +49,8 @@ ...@@ -48,7 +49,8 @@
*------------------------------------------------------------------ *------------------------------------------------------------------
*/ */
static void CommentRelation(int objtype, char *relation, char *comment); static void CommentRelation(int objtype, char * schemaname, char *relation,
char *comment);
static void CommentAttribute(char *relation, char *attrib, char *comment); static void CommentAttribute(char *relation, char *attrib, char *comment);
static void CommentDatabase(char *database, char *comment); static void CommentDatabase(char *database, char *comment);
static void CommentRewrite(char *rule, char *comment); static void CommentRewrite(char *rule, char *comment);
...@@ -74,7 +76,7 @@ static void CommentTrigger(char *trigger, char *relation, char *comments); ...@@ -74,7 +76,7 @@ static void CommentTrigger(char *trigger, char *relation, char *comments);
*/ */
void void
CommentObject(int objtype, char *objname, char *objproperty, CommentObject(int objtype, char *schemaname, char *objname, char *objproperty,
List *objlist, char *comment) List *objlist, char *comment)
{ {
switch (objtype) switch (objtype)
...@@ -83,7 +85,7 @@ CommentObject(int objtype, char *objname, char *objproperty, ...@@ -83,7 +85,7 @@ CommentObject(int objtype, char *objname, char *objproperty,
case SEQUENCE: case SEQUENCE:
case TABLE: case TABLE:
case VIEW: case VIEW:
CommentRelation(objtype, objname, comment); CommentRelation(objtype, schemaname, objname, comment);
break; break;
case COLUMN: case COLUMN:
CommentAttribute(objname, objproperty, comment); CommentAttribute(objname, objproperty, comment);
...@@ -323,9 +325,16 @@ DeleteComments(Oid oid, Oid classoid) ...@@ -323,9 +325,16 @@ DeleteComments(Oid oid, Oid classoid)
*/ */
static void static void
CommentRelation(int reltype, char *relname, char *comment) CommentRelation(int reltype, char *schemaname, char *relname, char *comment)
{ {
Relation relation; Relation relation;
RangeVar *tgtrel = makeNode(RangeVar);
tgtrel->relname = relname;
tgtrel->schemaname = schemaname;
/* FIXME SCHEMA: Can we add comments to temp relations? */
tgtrel->istemp = false;
/* /*
* Open the relation. We do this mainly to acquire a lock that * Open the relation. We do this mainly to acquire a lock that
...@@ -333,7 +342,7 @@ CommentRelation(int reltype, char *relname, char *comment) ...@@ -333,7 +342,7 @@ CommentRelation(int reltype, char *relname, char *comment)
* did, they'd fail to remove the entry we are about to make in * did, they'd fail to remove the entry we are about to make in
* pg_description.) * pg_description.)
*/ */
relation = relation_openr(relname, AccessShareLock); relation = relation_openrv(tgtrel, AccessShareLock);
/* Check object security */ /* Check object security */
if (!pg_class_ownercheck(RelationGetRelid(relation), GetUserId())) if (!pg_class_ownercheck(RelationGetRelid(relation), GetUserId()))
...@@ -504,9 +513,7 @@ CommentRewrite(char *rule, char *comment) ...@@ -504,9 +513,7 @@ CommentRewrite(char *rule, char *comment)
/* pg_rewrite doesn't have a hard-coded OID, so must look it up */ /* pg_rewrite doesn't have a hard-coded OID, so must look it up */
classoid = GetSysCacheOid(RELNAME, classoid = get_relname_relid(RewriteRelationName, PG_CATALOG_NAMESPACE);
PointerGetDatum(RewriteRelationName),
0, 0, 0);
Assert(OidIsValid(classoid)); Assert(OidIsValid(classoid));
/* Call CreateComments() to create/drop the comments */ /* Call CreateComments() to create/drop the comments */
...@@ -604,9 +611,7 @@ CommentAggregate(char *aggregate, List *arguments, char *comment) ...@@ -604,9 +611,7 @@ CommentAggregate(char *aggregate, List *arguments, char *comment)
/* pg_aggregate doesn't have a hard-coded OID, so must look it up */ /* pg_aggregate doesn't have a hard-coded OID, so must look it up */
classoid = GetSysCacheOid(RELNAME, classoid = get_relname_relid(AggregateRelationName, PG_CATALOG_NAMESPACE);
PointerGetDatum(AggregateRelationName),
0, 0, 0);
Assert(OidIsValid(classoid)); Assert(OidIsValid(classoid));
/* Call CreateComments() to create/drop the comments */ /* Call CreateComments() to create/drop the comments */
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/creatinh.c,v 1.91 2002/03/22 02:56:31 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/commands/Attic/creatinh.c,v 1.92 2002/03/26 19:15:40 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -18,9 +18,11 @@ ...@@ -18,9 +18,11 @@
#include "access/heapam.h" #include "access/heapam.h"
#include "catalog/catalog.h" #include "catalog/catalog.h"
#include "catalog/catname.h" #include "catalog/catname.h"
#include "catalog/indexing.h"
#include "catalog/heap.h" #include "catalog/heap.h"
#include "catalog/indexing.h"
#include "catalog/namespace.h"
#include "catalog/pg_inherits.h" #include "catalog/pg_inherits.h"
#include "catalog/pg_namespace.h"
#include "catalog/pg_type.h" #include "catalog/pg_type.h"
#include "commands/creatinh.h" #include "commands/creatinh.h"
#include "miscadmin.h" #include "miscadmin.h"
...@@ -54,6 +56,7 @@ Oid ...@@ -54,6 +56,7 @@ Oid
DefineRelation(CreateStmt *stmt, char relkind) DefineRelation(CreateStmt *stmt, char relkind)
{ {
char *relname = palloc(NAMEDATALEN); char *relname = palloc(NAMEDATALEN);
Oid namespaceId;
List *schema = stmt->tableElts; List *schema = stmt->tableElts;
int numberOfAttributes; int numberOfAttributes;
Oid relationId; Oid relationId;
...@@ -73,6 +76,12 @@ DefineRelation(CreateStmt *stmt, char relkind) ...@@ -73,6 +76,12 @@ DefineRelation(CreateStmt *stmt, char relkind)
*/ */
StrNCpy(relname, (stmt->relation)->relname, NAMEDATALEN); StrNCpy(relname, (stmt->relation)->relname, NAMEDATALEN);
/*
* Look up the namespace in which we are supposed to create the
* relation.
*/
namespaceId = RangeVarGetCreationNamespace(stmt->relation);
/* /*
* Merge domain attributes into the known columns before processing table * Merge domain attributes into the known columns before processing table
* inheritance. Otherwise we risk adding double constraints to a * inheritance. Otherwise we risk adding double constraints to a
...@@ -147,7 +156,8 @@ DefineRelation(CreateStmt *stmt, char relkind) ...@@ -147,7 +156,8 @@ DefineRelation(CreateStmt *stmt, char relkind)
} }
} }
relationId = heap_create_with_catalog(relname, descriptor, relationId = heap_create_with_catalog(relname, namespaceId,
descriptor,
relkind, relkind,
stmt->hasoids || parentHasOids, stmt->hasoids || parentHasOids,
stmt->relation->istemp, stmt->relation->istemp,
...@@ -330,7 +340,7 @@ MergeDomainAttributes(List *schema) ...@@ -330,7 +340,7 @@ MergeDomainAttributes(List *schema)
* Input arguments: * Input arguments:
* 'schema' is the column/attribute definition for the table. (It's a list * 'schema' is the column/attribute definition for the table. (It's a list
* of ColumnDef's.) It is destructively changed. * of ColumnDef's.) It is destructively changed.
* 'supers' is a list of names (as Value objects) of parent relations. * 'supers' is a list of names (as RangeVar nodes) of parent relations.
* 'istemp' is TRUE if we are creating a temp relation. * 'istemp' is TRUE if we are creating a temp relation.
* *
* Output arguments: * Output arguments:
...@@ -417,24 +427,6 @@ MergeAttributes(List *schema, List *supers, bool istemp, ...@@ -417,24 +427,6 @@ MergeAttributes(List *schema, List *supers, bool istemp,
} }
} }
/*
* Reject duplicate names in the list of parents, too.
*
* XXX needs to be smarter about schema-qualified table names.
*/
foreach(entry, supers)
{
List *rest;
foreach(rest, lnext(entry))
{
if (strcmp(((RangeVar *) lfirst(entry))->relname,
((RangeVar *) lfirst(rest))->relname) == 0)
elog(ERROR, "CREATE TABLE: inherited relation \"%s\" duplicated",
((RangeVar *) lfirst(entry))->relname);
}
}
/* /*
* Scan the parents left-to-right, and merge their attributes to form * Scan the parents left-to-right, and merge their attributes to form
* a list of inherited attributes (inhSchema). Also check to see if * a list of inherited attributes (inhSchema). Also check to see if
...@@ -443,30 +435,40 @@ MergeAttributes(List *schema, List *supers, bool istemp, ...@@ -443,30 +435,40 @@ MergeAttributes(List *schema, List *supers, bool istemp,
child_attno = 0; child_attno = 0;
foreach(entry, supers) foreach(entry, supers)
{ {
char *name = ((RangeVar *) lfirst(entry))->relname; RangeVar *parent = (RangeVar *) lfirst(entry);
Relation relation; Relation relation;
TupleDesc tupleDesc; TupleDesc tupleDesc;
TupleConstr *constr; TupleConstr *constr;
AttrNumber *newattno; AttrNumber *newattno;
AttrNumber parent_attno; AttrNumber parent_attno;
relation = heap_openr(name, AccessShareLock); relation = heap_openrv(parent, AccessShareLock);
if (relation->rd_rel->relkind != RELKIND_RELATION) if (relation->rd_rel->relkind != RELKIND_RELATION)
elog(ERROR, "CREATE TABLE: inherited relation \"%s\" is not a table", name); elog(ERROR, "CREATE TABLE: inherited relation \"%s\" is not a table",
parent->relname);
/* Permanent rels cannot inherit from temporary ones */ /* Permanent rels cannot inherit from temporary ones */
if (!istemp && is_temp_rel_name(name)) if (!istemp && is_temp_rel_name(parent->relname))
elog(ERROR, "CREATE TABLE: cannot inherit from temp relation \"%s\"", name); elog(ERROR, "CREATE TABLE: cannot inherit from temp relation \"%s\"",
parent->relname);
/* /*
* We should have an UNDER permission flag for this, but for now, * We should have an UNDER permission flag for this, but for now,
* demand that creator of a child table own the parent. * demand that creator of a child table own the parent.
*/ */
if (!pg_class_ownercheck(RelationGetRelid(relation), GetUserId())) if (!pg_class_ownercheck(RelationGetRelid(relation), GetUserId()))
elog(ERROR, "you do not own table \"%s\"", name); elog(ERROR, "you do not own table \"%s\"",
parent->relname);
/*
* Reject duplications in the list of parents.
*/
if (intMember(RelationGetRelid(relation), parentOids))
elog(ERROR, "CREATE TABLE: inherited relation \"%s\" duplicated",
parent->relname);
parentOids = lappendi(parentOids, relation->rd_id); parentOids = lappendi(parentOids, RelationGetRelid(relation));
setRelhassubclassInRelation(relation->rd_id, true); setRelhassubclassInRelation(RelationGetRelid(relation), true);
parentHasOids |= relation->rd_rel->relhasoids; parentHasOids |= relation->rd_rel->relhasoids;
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/commands/indexcmds.c,v 1.64 2002/03/20 19:43:47 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/commands/indexcmds.c,v 1.65 2002/03/26 19:15:41 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -18,8 +18,8 @@ ...@@ -18,8 +18,8 @@
#include "access/heapam.h" #include "access/heapam.h"
#include "catalog/catalog.h" #include "catalog/catalog.h"
#include "catalog/catname.h" #include "catalog/catname.h"
#include "catalog/heap.h"
#include "catalog/index.h" #include "catalog/index.h"
#include "catalog/namespace.h"
#include "catalog/pg_opclass.h" #include "catalog/pg_opclass.h"
#include "commands/defrem.h" #include "commands/defrem.h"
#include "miscadmin.h" #include "miscadmin.h"
...@@ -33,6 +33,7 @@ ...@@ -33,6 +33,7 @@
#include "utils/fmgroids.h" #include "utils/fmgroids.h"
#include "utils/lsyscache.h" #include "utils/lsyscache.h"
#include "utils/syscache.h" #include "utils/syscache.h"
#include "utils/temprel.h"
#define IsFuncIndex(ATTR_LIST) (((IndexElem*)lfirst(ATTR_LIST))->args != NIL) #define IsFuncIndex(ATTR_LIST) (((IndexElem*)lfirst(ATTR_LIST))->args != NIL)
...@@ -61,7 +62,7 @@ static Oid GetDefaultOpClass(Oid attrType, Oid accessMethodId); ...@@ -61,7 +62,7 @@ static Oid GetDefaultOpClass(Oid attrType, Oid accessMethodId);
* 'rangetable' is needed to interpret the predicate. * 'rangetable' is needed to interpret the predicate.
*/ */
void void
DefineIndex(char *heapRelationName, DefineIndex(RangeVar *heapRelation,
char *indexRelationName, char *indexRelationName,
char *accessMethodName, char *accessMethodName,
List *attributeList, List *attributeList,
...@@ -73,6 +74,7 @@ DefineIndex(char *heapRelationName, ...@@ -73,6 +74,7 @@ DefineIndex(char *heapRelationName,
Oid *classObjectId; Oid *classObjectId;
Oid accessMethodId; Oid accessMethodId;
Oid relationId; Oid relationId;
bool istemp = is_temp_rel_name(heapRelation->relname);
Relation rel; Relation rel;
HeapTuple tuple; HeapTuple tuple;
Form_pg_am accessMethodForm; Form_pg_am accessMethodForm;
...@@ -93,20 +95,20 @@ DefineIndex(char *heapRelationName, ...@@ -93,20 +95,20 @@ DefineIndex(char *heapRelationName,
/* /*
* Open heap relation, acquire a suitable lock on it, remember its OID * Open heap relation, acquire a suitable lock on it, remember its OID
*/ */
rel = heap_openr(heapRelationName, ShareLock); rel = heap_openrv(heapRelation, ShareLock);
/* Note: during bootstrap may see uncataloged relation */ /* Note: during bootstrap may see uncataloged relation */
if (rel->rd_rel->relkind != RELKIND_RELATION && if (rel->rd_rel->relkind != RELKIND_RELATION &&
rel->rd_rel->relkind != RELKIND_UNCATALOGED) rel->rd_rel->relkind != RELKIND_UNCATALOGED)
elog(ERROR, "DefineIndex: relation \"%s\" is not a table", elog(ERROR, "DefineIndex: relation \"%s\" is not a table",
heapRelationName); heapRelation->relname);
relationId = RelationGetRelid(rel); relationId = RelationGetRelid(rel);
heap_close(rel, NoLock); heap_close(rel, NoLock);
if (!IsBootstrapProcessingMode() && if (!IsBootstrapProcessingMode() &&
IsSystemRelationName(heapRelationName) && IsSystemRelationName(heapRelation->relname) &&
!IndexesAreActive(relationId, false)) !IndexesAreActive(relationId, false))
elog(ERROR, "Existing indexes are inactive. REINDEX first"); elog(ERROR, "Existing indexes are inactive. REINDEX first");
...@@ -187,9 +189,9 @@ DefineIndex(char *heapRelationName, ...@@ -187,9 +189,9 @@ DefineIndex(char *heapRelationName,
relationId, accessMethodName, accessMethodId); relationId, accessMethodName, accessMethodId);
} }
index_create(heapRelationName, indexRelationName, index_create(relationId, indexRelationName,
indexInfo, accessMethodId, classObjectId, indexInfo, accessMethodId, classObjectId,
primary, allowSystemTableMods); istemp, primary, allowSystemTableMods);
/* /*
* We update the relation's pg_class tuple even if it already has * We update the relation's pg_class tuple even if it already has
...@@ -500,23 +502,25 @@ GetDefaultOpClass(Oid attrType, Oid accessMethodId) ...@@ -500,23 +502,25 @@ GetDefaultOpClass(Oid attrType, Oid accessMethodId)
* ... * ...
*/ */
void void
RemoveIndex(char *name) RemoveIndex(RangeVar *relation)
{ {
Oid indOid;
HeapTuple tuple; HeapTuple tuple;
tuple = SearchSysCache(RELNAME, indOid = RangeVarGetRelid(relation, false);
PointerGetDatum(name), tuple = SearchSysCache(RELOID,
ObjectIdGetDatum(indOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tuple)) if (!HeapTupleIsValid(tuple))
elog(ERROR, "index \"%s\" does not exist", name); elog(ERROR, "index \"%s\" does not exist", relation->relname);
if (((Form_pg_class) GETSTRUCT(tuple))->relkind != RELKIND_INDEX) if (((Form_pg_class) GETSTRUCT(tuple))->relkind != RELKIND_INDEX)
elog(ERROR, "relation \"%s\" is of type \"%c\"", elog(ERROR, "relation \"%s\" is of type \"%c\"",
name, ((Form_pg_class) GETSTRUCT(tuple))->relkind); relation->relname, ((Form_pg_class) GETSTRUCT(tuple))->relkind);
index_drop(tuple->t_data->t_oid);
ReleaseSysCache(tuple); ReleaseSysCache(tuple);
index_drop(indOid);
} }
/* /*
...@@ -528,8 +532,9 @@ RemoveIndex(char *name) ...@@ -528,8 +532,9 @@ RemoveIndex(char *name)
* ... * ...
*/ */
void void
ReindexIndex(const char *name, bool force /* currently unused */ ) ReindexIndex(RangeVar *indexRelation, bool force /* currently unused */ )
{ {
Oid indOid;
HeapTuple tuple; HeapTuple tuple;
bool overwrite = false; bool overwrite = false;
...@@ -541,22 +546,24 @@ ReindexIndex(const char *name, bool force /* currently unused */ ) ...@@ -541,22 +546,24 @@ ReindexIndex(const char *name, bool force /* currently unused */ )
if (IsTransactionBlock()) if (IsTransactionBlock())
elog(ERROR, "REINDEX cannot run inside a BEGIN/END block"); elog(ERROR, "REINDEX cannot run inside a BEGIN/END block");
tuple = SearchSysCache(RELNAME, indOid = RangeVarGetRelid(indexRelation, false);
PointerGetDatum(name), tuple = SearchSysCache(RELOID,
ObjectIdGetDatum(indOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tuple)) if (!HeapTupleIsValid(tuple))
elog(ERROR, "index \"%s\" does not exist", name); elog(ERROR, "index \"%s\" does not exist", indexRelation->relname);
if (((Form_pg_class) GETSTRUCT(tuple))->relkind != RELKIND_INDEX) if (((Form_pg_class) GETSTRUCT(tuple))->relkind != RELKIND_INDEX)
elog(ERROR, "relation \"%s\" is of type \"%c\"", elog(ERROR, "relation \"%s\" is of type \"%c\"",
name, ((Form_pg_class) GETSTRUCT(tuple))->relkind); indexRelation->relname,
((Form_pg_class) GETSTRUCT(tuple))->relkind);
ReleaseSysCache(tuple);
if (IsIgnoringSystemIndexes()) if (IsIgnoringSystemIndexes())
overwrite = true; overwrite = true;
if (!reindex_index(tuple->t_data->t_oid, force, overwrite)) if (!reindex_index(indOid, force, overwrite))
elog(WARNING, "index \"%s\" wasn't reindexed", name); elog(WARNING, "index \"%s\" wasn't reindexed", indexRelation->relname);
ReleaseSysCache(tuple);
} }
/* /*
...@@ -568,8 +575,9 @@ ReindexIndex(const char *name, bool force /* currently unused */ ) ...@@ -568,8 +575,9 @@ ReindexIndex(const char *name, bool force /* currently unused */ )
* ... * ...
*/ */
void void
ReindexTable(const char *name, bool force) ReindexTable(RangeVar *relation, bool force)
{ {
Oid heapOid;
HeapTuple tuple; HeapTuple tuple;
/* /*
...@@ -580,20 +588,22 @@ ReindexTable(const char *name, bool force) ...@@ -580,20 +588,22 @@ ReindexTable(const char *name, bool force)
if (IsTransactionBlock()) if (IsTransactionBlock())
elog(ERROR, "REINDEX cannot run inside a BEGIN/END block"); elog(ERROR, "REINDEX cannot run inside a BEGIN/END block");
tuple = SearchSysCache(RELNAME, heapOid = RangeVarGetRelid(relation, false);
PointerGetDatum(name), tuple = SearchSysCache(RELOID,
ObjectIdGetDatum(heapOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tuple)) if (!HeapTupleIsValid(tuple))
elog(ERROR, "table \"%s\" does not exist", name); elog(ERROR, "table \"%s\" does not exist", relation->relname);
if (((Form_pg_class) GETSTRUCT(tuple))->relkind != RELKIND_RELATION) if (((Form_pg_class) GETSTRUCT(tuple))->relkind != RELKIND_RELATION)
elog(ERROR, "relation \"%s\" is of type \"%c\"", elog(ERROR, "relation \"%s\" is of type \"%c\"",
name, ((Form_pg_class) GETSTRUCT(tuple))->relkind); relation->relname,
((Form_pg_class) GETSTRUCT(tuple))->relkind);
if (!reindex_relation(tuple->t_data->t_oid, force))
elog(WARNING, "table \"%s\" wasn't reindexed", name);
ReleaseSysCache(tuple); ReleaseSysCache(tuple);
if (!reindex_relation(heapOid, force))
elog(WARNING, "table \"%s\" wasn't reindexed", relation->relname);
} }
/* /*
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/rename.c,v 1.64 2002/03/21 23:27:21 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/commands/Attic/rename.c,v 1.65 2002/03/26 19:15:43 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -36,6 +36,7 @@ ...@@ -36,6 +36,7 @@
#include "utils/acl.h" #include "utils/acl.h"
#include "utils/builtins.h" #include "utils/builtins.h"
#include "utils/fmgroids.h" #include "utils/fmgroids.h"
#include "utils/lsyscache.h"
#include "utils/relcache.h" #include "utils/relcache.h"
#include "utils/syscache.h" #include "utils/syscache.h"
#include "utils/temprel.h" #include "utils/temprel.h"
...@@ -266,19 +267,20 @@ renameatt(char *relname, ...@@ -266,19 +267,20 @@ renameatt(char *relname,
* renamerel - change the name of a relation * renamerel - change the name of a relation
*/ */
void void
renamerel(const char *oldrelname, const char *newrelname) renamerel(const RangeVar *relation, const char *newrelname)
{ {
Relation targetrelation; Relation targetrelation;
Relation relrelation; /* for RELATION relation */ Relation relrelation; /* for RELATION relation */
HeapTuple reltup; HeapTuple reltup;
Oid namespaceId;
Oid reloid; Oid reloid;
char relkind; char relkind;
bool relhastriggers; bool relhastriggers;
Relation irelations[Num_pg_class_indices]; Relation irelations[Num_pg_class_indices];
if (!allowSystemTableMods && IsSystemRelationName(oldrelname)) if (!allowSystemTableMods && IsSystemRelationName(relation->relname))
elog(ERROR, "renamerel: system relation \"%s\" may not be renamed", elog(ERROR, "renamerel: system relation \"%s\" may not be renamed",
oldrelname); relation->relname);
if (!allowSystemTableMods && IsSystemRelationName(newrelname)) if (!allowSystemTableMods && IsSystemRelationName(newrelname))
elog(ERROR, "renamerel: Illegal class name: \"%s\" -- pg_ is reserved for system catalogs", elog(ERROR, "renamerel: Illegal class name: \"%s\" -- pg_ is reserved for system catalogs",
...@@ -288,15 +290,16 @@ renamerel(const char *oldrelname, const char *newrelname) ...@@ -288,15 +290,16 @@ renamerel(const char *oldrelname, const char *newrelname)
* Check for renaming a temp table, which only requires altering the * Check for renaming a temp table, which only requires altering the
* temp-table mapping, not the underlying table. * temp-table mapping, not the underlying table.
*/ */
if (rename_temp_relation(oldrelname, newrelname)) if (rename_temp_relation(relation->relname, newrelname))
return; /* all done... */ return; /* all done... */
/* /*
* Grab an exclusive lock on the target table or index, which we will * Grab an exclusive lock on the target table or index, which we will
* NOT release until end of transaction. * NOT release until end of transaction.
*/ */
targetrelation = relation_openr(oldrelname, AccessExclusiveLock); targetrelation = relation_openrv(relation, AccessExclusiveLock);
namespaceId = RelationGetNamespace(targetrelation);
reloid = RelationGetRelid(targetrelation); reloid = RelationGetRelid(targetrelation);
relkind = targetrelation->rd_rel->relkind; relkind = targetrelation->rd_rel->relkind;
relhastriggers = (targetrelation->rd_rel->reltriggers > 0); relhastriggers = (targetrelation->rd_rel->reltriggers > 0);
...@@ -323,13 +326,14 @@ renamerel(const char *oldrelname, const char *newrelname) ...@@ -323,13 +326,14 @@ renamerel(const char *oldrelname, const char *newrelname)
*/ */
relrelation = heap_openr(RelationRelationName, RowExclusiveLock); relrelation = heap_openr(RelationRelationName, RowExclusiveLock);
reltup = SearchSysCacheCopy(RELNAME, reltup = SearchSysCacheCopy(RELOID,
PointerGetDatum(oldrelname), PointerGetDatum(reloid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(reltup)) if (!HeapTupleIsValid(reltup))
elog(ERROR, "renamerel: relation \"%s\" does not exist", oldrelname); elog(ERROR, "renamerel: relation \"%s\" does not exist",
relation->relname);
if (RelnameFindRelid(newrelname) != InvalidOid) if (get_relname_relid(newrelname, namespaceId) != InvalidOid)
elog(ERROR, "renamerel: relation \"%s\" exists", newrelname); elog(ERROR, "renamerel: relation \"%s\" exists", newrelname);
/* /*
...@@ -352,7 +356,7 @@ renamerel(const char *oldrelname, const char *newrelname) ...@@ -352,7 +356,7 @@ renamerel(const char *oldrelname, const char *newrelname)
* Also rename the associated type, if any. * Also rename the associated type, if any.
*/ */
if (relkind != RELKIND_INDEX) if (relkind != RELKIND_INDEX)
TypeRename(oldrelname, newrelname); TypeRename(relation->relname, newrelname);
/* /*
* If it's a view, must also rename the associated ON SELECT rule. * If it's a view, must also rename the associated ON SELECT rule.
...@@ -362,7 +366,7 @@ renamerel(const char *oldrelname, const char *newrelname) ...@@ -362,7 +366,7 @@ renamerel(const char *oldrelname, const char *newrelname)
char *oldrulename, char *oldrulename,
*newrulename; *newrulename;
oldrulename = MakeRetrieveViewRuleName(oldrelname); oldrulename = MakeRetrieveViewRuleName(relation->relname);
newrulename = MakeRetrieveViewRuleName(newrelname); newrulename = MakeRetrieveViewRuleName(newrelname);
RenameRewriteRule(oldrulename, newrulename); RenameRewriteRule(oldrulename, newrulename);
} }
...@@ -374,11 +378,11 @@ renamerel(const char *oldrelname, const char *newrelname) ...@@ -374,11 +378,11 @@ renamerel(const char *oldrelname, const char *newrelname)
{ {
/* update tgargs where relname is primary key */ /* update tgargs where relname is primary key */
update_ri_trigger_args(reloid, update_ri_trigger_args(reloid,
oldrelname, newrelname, relation->relname, newrelname,
false, true); false, true);
/* update tgargs where relname is foreign key */ /* update tgargs where relname is foreign key */
update_ri_trigger_args(reloid, update_ri_trigger_args(reloid,
oldrelname, newrelname, relation->relname, newrelname,
true, true); true, true);
} }
} }
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/commands/trigger.c,v 1.107 2002/03/21 23:27:22 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/commands/trigger.c,v 1.108 2002/03/26 19:15:45 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -71,7 +71,7 @@ CreateTrigger(CreateTrigStmt *stmt) ...@@ -71,7 +71,7 @@ CreateTrigger(CreateTrigStmt *stmt)
char *constrname = ""; char *constrname = "";
Oid constrrelid = InvalidOid; Oid constrrelid = InvalidOid;
rel = heap_openr(stmt->relation->relname, AccessExclusiveLock); rel = heap_openrv(stmt->relation, AccessExclusiveLock);
if (rel->rd_rel->relkind != RELKIND_RELATION) if (rel->rd_rel->relkind != RELKIND_RELATION)
elog(ERROR, "CreateTrigger: relation \"%s\" is not a table", elog(ERROR, "CreateTrigger: relation \"%s\" is not a table",
...@@ -106,7 +106,7 @@ CreateTrigger(CreateTrigStmt *stmt) ...@@ -106,7 +106,7 @@ CreateTrigger(CreateTrigStmt *stmt)
*/ */
Relation conrel; Relation conrel;
conrel = heap_openr(stmt->constrrel->relname, NoLock); conrel = heap_openrv(stmt->constrrel, NoLock);
constrrelid = conrel->rd_id; constrrelid = conrel->rd_id;
heap_close(conrel, NoLock); heap_close(conrel, NoLock);
} }
...@@ -285,8 +285,8 @@ CreateTrigger(CreateTrigStmt *stmt) ...@@ -285,8 +285,8 @@ CreateTrigger(CreateTrigStmt *stmt)
* rebuild relcache entries. * rebuild relcache entries.
*/ */
pgrel = heap_openr(RelationRelationName, RowExclusiveLock); pgrel = heap_openr(RelationRelationName, RowExclusiveLock);
tuple = SearchSysCacheCopy(RELNAME, tuple = SearchSysCacheCopy(RELOID,
PointerGetDatum(stmt->relation->relname), ObjectIdGetDatum(RelationGetRelid(rel)),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tuple)) if (!HeapTupleIsValid(tuple))
elog(ERROR, "CreateTrigger: relation %s not found in pg_class", elog(ERROR, "CreateTrigger: relation %s not found in pg_class",
...@@ -323,7 +323,7 @@ DropTrigger(DropTrigStmt *stmt) ...@@ -323,7 +323,7 @@ DropTrigger(DropTrigStmt *stmt)
int found = 0; int found = 0;
int tgfound = 0; int tgfound = 0;
rel = heap_openr(stmt->relation->relname, AccessExclusiveLock); rel = heap_openrv(stmt->relation, AccessExclusiveLock);
if (rel->rd_rel->relkind != RELKIND_RELATION) if (rel->rd_rel->relkind != RELKIND_RELATION)
elog(ERROR, "DropTrigger: relation \"%s\" is not a table", elog(ERROR, "DropTrigger: relation \"%s\" is not a table",
...@@ -380,8 +380,8 @@ DropTrigger(DropTrigStmt *stmt) ...@@ -380,8 +380,8 @@ DropTrigger(DropTrigStmt *stmt)
* rebuild relcache entries. * rebuild relcache entries.
*/ */
pgrel = heap_openr(RelationRelationName, RowExclusiveLock); pgrel = heap_openr(RelationRelationName, RowExclusiveLock);
tuple = SearchSysCacheCopy(RELNAME, tuple = SearchSysCacheCopy(RELOID,
PointerGetDatum(stmt->relation->relname), ObjectIdGetDatum(RelationGetRelid(rel)),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tuple)) if (!HeapTupleIsValid(tuple))
elog(ERROR, "DropTrigger: relation %s not found in pg_class", elog(ERROR, "DropTrigger: relation %s not found in pg_class",
...@@ -452,7 +452,7 @@ RelationRemoveTriggers(Relation rel) ...@@ -452,7 +452,7 @@ RelationRemoveTriggers(Relation rel)
pgrel = heap_openr(RelationRelationName, RowExclusiveLock); pgrel = heap_openr(RelationRelationName, RowExclusiveLock);
tup = SearchSysCacheCopy(RELOID, tup = SearchSysCacheCopy(RELOID,
RelationGetRelid(rel), ObjectIdGetDatum(RelationGetRelid(rel)),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tup)) if (!HeapTupleIsValid(tup))
elog(ERROR, "RelationRemoveTriggers: relation %u not found in pg_class", elog(ERROR, "RelationRemoveTriggers: relation %u not found in pg_class",
......
...@@ -6,7 +6,7 @@ ...@@ -6,7 +6,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Header: /cvsroot/pgsql/src/backend/commands/user.c,v 1.93 2002/03/06 06:09:37 momjian Exp $ * $Header: /cvsroot/pgsql/src/backend/commands/user.c,v 1.94 2002/03/26 19:15:48 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -919,12 +919,12 @@ DropUser(DropUserStmt *stmt) ...@@ -919,12 +919,12 @@ DropUser(DropUserStmt *stmt)
* check to see if there is an ACL on pg_shadow * check to see if there is an ACL on pg_shadow
*/ */
static void static void
CheckPgUserAclNotNull() CheckPgUserAclNotNull(void)
{ {
HeapTuple htup; HeapTuple htup;
htup = SearchSysCache(RELNAME, htup = SearchSysCache(RELOID,
PointerGetDatum(ShadowRelationName), ObjectIdGetDatum(RelOid_pg_shadow),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(htup)) if (!HeapTupleIsValid(htup))
elog(ERROR, "CheckPgUserAclNotNull: \"%s\" not found", elog(ERROR, "CheckPgUserAclNotNull: \"%s\" not found",
......
...@@ -27,7 +27,7 @@ ...@@ -27,7 +27,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/executor/execMain.c,v 1.154 2002/03/21 23:27:23 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/executor/execMain.c,v 1.155 2002/03/26 19:15:54 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -35,6 +35,7 @@ ...@@ -35,6 +35,7 @@
#include "access/heapam.h" #include "access/heapam.h"
#include "catalog/heap.h" #include "catalog/heap.h"
#include "catalog/namespace.h"
#include "commands/command.h" #include "commands/command.h"
#include "commands/trigger.h" #include "commands/trigger.h"
#include "executor/execdebug.h" #include "executor/execdebug.h"
...@@ -696,10 +697,6 @@ InitPlan(CmdType operation, Query *parseTree, Plan *plan, EState *estate) ...@@ -696,10 +697,6 @@ InitPlan(CmdType operation, Query *parseTree, Plan *plan, EState *estate)
if (operation == CMD_SELECT) if (operation == CMD_SELECT)
{ {
char *intoName;
Oid intoRelationId;
TupleDesc tupdesc;
if (!parseTree->isPortal) if (!parseTree->isPortal)
{ {
/* /*
...@@ -707,10 +704,16 @@ InitPlan(CmdType operation, Query *parseTree, Plan *plan, EState *estate) ...@@ -707,10 +704,16 @@ InitPlan(CmdType operation, Query *parseTree, Plan *plan, EState *estate)
*/ */
if (parseTree->into != NULL) if (parseTree->into != NULL)
{ {
char *intoName;
Oid namespaceId;
Oid intoRelationId;
TupleDesc tupdesc;
/* /*
* create the "into" relation * create the "into" relation
*/ */
intoName = parseTree->into->relname; intoName = parseTree->into->relname;
namespaceId = RangeVarGetCreationNamespace(parseTree->into);
/* /*
* have to copy tupType to get rid of constraints * have to copy tupType to get rid of constraints
...@@ -719,6 +722,7 @@ InitPlan(CmdType operation, Query *parseTree, Plan *plan, EState *estate) ...@@ -719,6 +722,7 @@ InitPlan(CmdType operation, Query *parseTree, Plan *plan, EState *estate)
intoRelationId = intoRelationId =
heap_create_with_catalog(intoName, heap_create_with_catalog(intoName,
namespaceId,
tupdesc, tupdesc,
RELKIND_RELATION, true, RELKIND_RELATION, true,
parseTree->into->istemp, parseTree->into->istemp,
...@@ -738,7 +742,7 @@ InitPlan(CmdType operation, Query *parseTree, Plan *plan, EState *estate) ...@@ -738,7 +742,7 @@ InitPlan(CmdType operation, Query *parseTree, Plan *plan, EState *estate)
* with CommandCounterIncrement(), so that the TOAST table * with CommandCounterIncrement(), so that the TOAST table
* will be visible for insertion. * will be visible for insertion.
*/ */
AlterTableCreateToastTable(intoName, true); AlterTableCreateToastTable(intoRelationId, true);
intoRelationDesc = heap_open(intoRelationId, intoRelationDesc = heap_open(intoRelationId,
AccessExclusiveLock); AccessExclusiveLock);
......
...@@ -6,7 +6,7 @@ ...@@ -6,7 +6,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Header: /cvsroot/pgsql/src/backend/parser/analyze.c,v 1.222 2002/03/22 02:56:33 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/parser/analyze.c,v 1.223 2002/03/26 19:15:56 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -17,6 +17,7 @@ ...@@ -17,6 +17,7 @@
#include "catalog/catname.h" #include "catalog/catname.h"
#include "catalog/heap.h" #include "catalog/heap.h"
#include "catalog/index.h" #include "catalog/index.h"
#include "catalog/namespace.h"
#include "catalog/pg_index.h" #include "catalog/pg_index.h"
#include "catalog/pg_type.h" #include "catalog/pg_type.h"
#include "nodes/makefuncs.h" #include "nodes/makefuncs.h"
...@@ -118,7 +119,7 @@ static void transformConstraintAttrs(List *constraintList); ...@@ -118,7 +119,7 @@ static void transformConstraintAttrs(List *constraintList);
static void transformColumnType(ParseState *pstate, ColumnDef *column); static void transformColumnType(ParseState *pstate, ColumnDef *column);
static void transformFkeyCheckAttrs(FkConstraint *fkconstraint, Oid *pktypoid); static void transformFkeyCheckAttrs(FkConstraint *fkconstraint, Oid *pktypoid);
static void transformFkeyGetPrimaryKey(FkConstraint *fkconstraint, Oid *pktypoid); static void transformFkeyGetPrimaryKey(FkConstraint *fkconstraint, Oid *pktypoid);
static bool relationHasPrimaryKey(char *relname); static bool relationHasPrimaryKey(Oid relationOid);
static Oid transformFkeyGetColType(CreateStmtContext *cxt, char *colname); static Oid transformFkeyGetColType(CreateStmtContext *cxt, char *colname);
static void release_pstate_resources(ParseState *pstate); static void release_pstate_resources(ParseState *pstate);
static FromExpr *makeFromExpr(List *fromlist, Node *quals); static FromExpr *makeFromExpr(List *fromlist, Node *quals);
...@@ -1048,7 +1049,7 @@ transformIndexConstraints(ParseState *pstate, CreateStmtContext *cxt) ...@@ -1048,7 +1049,7 @@ transformIndexConstraints(ParseState *pstate, CreateStmtContext *cxt)
/* In ALTER TABLE case, a primary index might already exist */ /* In ALTER TABLE case, a primary index might already exist */
if (cxt->pkey != NULL || if (cxt->pkey != NULL ||
(OidIsValid(cxt->relOid) && (OidIsValid(cxt->relOid) &&
relationHasPrimaryKey((cxt->relation)->relname))) relationHasPrimaryKey(cxt->relOid)))
elog(ERROR, "%s / PRIMARY KEY multiple primary keys" elog(ERROR, "%s / PRIMARY KEY multiple primary keys"
" for table '%s' are not allowed", " for table '%s' are not allowed",
cxt->stmtType, (cxt->relation)->relname); cxt->stmtType, (cxt->relation)->relname);
...@@ -1115,10 +1116,10 @@ transformIndexConstraints(ParseState *pstate, CreateStmtContext *cxt) ...@@ -1115,10 +1116,10 @@ transformIndexConstraints(ParseState *pstate, CreateStmtContext *cxt)
int count; int count;
Assert(IsA(inh, RangeVar)); Assert(IsA(inh, RangeVar));
rel = heap_openr(inh->relname, AccessShareLock); rel = heap_openrv(inh, AccessShareLock);
if (rel->rd_rel->relkind != RELKIND_RELATION) if (rel->rd_rel->relkind != RELKIND_RELATION)
elog(ERROR, "inherited table \"%s\" is not a relation", elog(ERROR, "inherited table \"%s\" is not a relation",
strVal(inh)); inh->relname);
for (count = 0; count < rel->rd_att->natts; count++) for (count = 0; count < rel->rd_att->natts; count++)
{ {
Form_pg_attribute inhattr = rel->rd_att->attrs[count]; Form_pg_attribute inhattr = rel->rd_att->attrs[count];
...@@ -1724,7 +1725,7 @@ transformRuleStmt(ParseState *pstate, RuleStmt *stmt, ...@@ -1724,7 +1725,7 @@ transformRuleStmt(ParseState *pstate, RuleStmt *stmt,
* beforehand. We don't need to hold a refcount on the relcache * beforehand. We don't need to hold a refcount on the relcache
* entry, however. * entry, however.
*/ */
heap_close(heap_openr(stmt->relation->relname, AccessExclusiveLock), heap_close(heap_openrv(stmt->relation, AccessExclusiveLock),
NoLock); NoLock);
/* /*
...@@ -2562,9 +2563,7 @@ transformAlterTableStmt(ParseState *pstate, AlterTableStmt *stmt, ...@@ -2562,9 +2563,7 @@ transformAlterTableStmt(ParseState *pstate, AlterTableStmt *stmt,
cxt.relation = stmt->relation; cxt.relation = stmt->relation;
cxt.inhRelations = NIL; cxt.inhRelations = NIL;
cxt.relation->istemp = is_temp_rel_name(stmt->relation->relname); cxt.relation->istemp = is_temp_rel_name(stmt->relation->relname);
cxt.relOid = GetSysCacheOid(RELNAME, cxt.relOid = RangeVarGetRelid(stmt->relation, false);
PointerGetDatum((stmt->relation)->relname),
0, 0, 0);
cxt.hasoids = SearchSysCacheExists(ATTNUM, cxt.hasoids = SearchSysCacheExists(ATTNUM,
ObjectIdGetDatum(cxt.relOid), ObjectIdGetDatum(cxt.relOid),
Int16GetDatum(ObjectIdAttributeNumber), Int16GetDatum(ObjectIdAttributeNumber),
...@@ -2594,9 +2593,7 @@ transformAlterTableStmt(ParseState *pstate, AlterTableStmt *stmt, ...@@ -2594,9 +2593,7 @@ transformAlterTableStmt(ParseState *pstate, AlterTableStmt *stmt,
cxt.relation = stmt->relation; cxt.relation = stmt->relation;
cxt.inhRelations = NIL; cxt.inhRelations = NIL;
cxt.relation->istemp = is_temp_rel_name(stmt->relation->relname); cxt.relation->istemp = is_temp_rel_name(stmt->relation->relname);
cxt.relOid = GetSysCacheOid(RELNAME, cxt.relOid = RangeVarGetRelid(stmt->relation, false);
PointerGetDatum((stmt->relation)->relname),
0, 0, 0);
cxt.hasoids = SearchSysCacheExists(ATTNUM, cxt.hasoids = SearchSysCacheExists(ATTNUM,
ObjectIdGetDatum(cxt.relOid), ObjectIdGetDatum(cxt.relOid),
Int16GetDatum(ObjectIdAttributeNumber), Int16GetDatum(ObjectIdAttributeNumber),
...@@ -2844,7 +2841,7 @@ transformFkeyCheckAttrs(FkConstraint *fkconstraint, Oid *pktypoid) ...@@ -2844,7 +2841,7 @@ transformFkeyCheckAttrs(FkConstraint *fkconstraint, Oid *pktypoid)
/* /*
* Open the referenced table * Open the referenced table
*/ */
pkrel = heap_openr(fkconstraint->pktable->relname, AccessShareLock); pkrel = heap_openrv(fkconstraint->pktable, AccessShareLock);
if (pkrel->rd_rel->relkind != RELKIND_RELATION) if (pkrel->rd_rel->relkind != RELKIND_RELATION)
elog(ERROR, "Referenced relation \"%s\" is not a table", elog(ERROR, "Referenced relation \"%s\" is not a table",
...@@ -2937,7 +2934,7 @@ transformFkeyGetPrimaryKey(FkConstraint *fkconstraint, Oid *pktypoid) ...@@ -2937,7 +2934,7 @@ transformFkeyGetPrimaryKey(FkConstraint *fkconstraint, Oid *pktypoid)
/* /*
* Open the referenced table * Open the referenced table
*/ */
pkrel = heap_openr(fkconstraint->pktable->relname, AccessShareLock); pkrel = heap_openrv(fkconstraint->pktable, AccessShareLock);
if (pkrel->rd_rel->relkind != RELKIND_RELATION) if (pkrel->rd_rel->relkind != RELKIND_RELATION)
elog(ERROR, "Referenced relation \"%s\" is not a table", elog(ERROR, "Referenced relation \"%s\" is not a table",
...@@ -3002,14 +2999,14 @@ transformFkeyGetPrimaryKey(FkConstraint *fkconstraint, Oid *pktypoid) ...@@ -3002,14 +2999,14 @@ transformFkeyGetPrimaryKey(FkConstraint *fkconstraint, Oid *pktypoid)
* See whether an existing relation has a primary key. * See whether an existing relation has a primary key.
*/ */
static bool static bool
relationHasPrimaryKey(char *relname) relationHasPrimaryKey(Oid relationOid)
{ {
bool result = false; bool result = false;
Relation rel; Relation rel;
List *indexoidlist, List *indexoidlist,
*indexoidscan; *indexoidscan;
rel = heap_openr(relname, AccessShareLock); rel = heap_open(relationOid, AccessShareLock);
/* /*
* Get the list of index OIDs for the table from the relcache, and * Get the list of index OIDs for the table from the relcache, and
...@@ -3084,10 +3081,10 @@ transformFkeyGetColType(CreateStmtContext *cxt, char *colname) ...@@ -3084,10 +3081,10 @@ transformFkeyGetColType(CreateStmtContext *cxt, char *colname)
int count; int count;
Assert(IsA(inh, RangeVar)); Assert(IsA(inh, RangeVar));
rel = heap_openr(inh->relname, AccessShareLock); rel = heap_openrv(inh, AccessShareLock);
if (rel->rd_rel->relkind != RELKIND_RELATION) if (rel->rd_rel->relkind != RELKIND_RELATION)
elog(ERROR, "inherited table \"%s\" is not a relation", elog(ERROR, "inherited table \"%s\" is not a relation",
strVal(inh)); inh->relname);
for (count = 0; count < rel->rd_att->natts; count++) for (count = 0; count < rel->rd_att->natts; count++)
{ {
char *name = NameStr(rel->rd_att->attrs[count]->attname); char *name = NameStr(rel->rd_att->attrs[count]->attname);
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/parser/parse_clause.c,v 1.86 2002/03/22 02:56:33 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/parser/parse_clause.c,v 1.87 2002/03/26 19:15:57 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -133,7 +133,7 @@ setTargetTable(ParseState *pstate, RangeVar *relation, ...@@ -133,7 +133,7 @@ setTargetTable(ParseState *pstate, RangeVar *relation,
* analyze.c will eventually do the corresponding heap_close(), but *not* * analyze.c will eventually do the corresponding heap_close(), but *not*
* release the lock. * release the lock.
*/ */
pstate->p_target_relation = heap_openr(relation->relname, RowExclusiveLock); pstate->p_target_relation = heap_openrv(relation, RowExclusiveLock);
/* /*
* Now build an RTE. * Now build an RTE.
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/parser/parse_relation.c,v 1.65 2002/03/22 02:56:34 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/parser/parse_relation.c,v 1.66 2002/03/26 19:15:59 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -443,7 +443,7 @@ addRangeTableEntry(ParseState *pstate, ...@@ -443,7 +443,7 @@ addRangeTableEntry(ParseState *pstate,
* access level depending on whether we're doing SELECT FOR UPDATE. * access level depending on whether we're doing SELECT FOR UPDATE.
*/ */
lockmode = isForUpdate(pstate, refname) ? RowShareLock : AccessShareLock; lockmode = isForUpdate(pstate, refname) ? RowShareLock : AccessShareLock;
rel = heap_openr(relation->relname, lockmode); rel = heap_openrv(relation, lockmode);
rte->relid = RelationGetRelid(rel); rte->relid = RelationGetRelid(rel);
eref = alias ? (Alias *) copyObject(alias) : makeAlias(refname, NIL); eref = alias ? (Alias *) copyObject(alias) : makeAlias(refname, NIL);
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/rewrite/rewriteDefine.c,v 1.65 2002/03/21 23:27:23 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/rewrite/rewriteDefine.c,v 1.66 2002/03/26 19:16:02 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -138,7 +138,7 @@ DefineQueryRewrite(RuleStmt *stmt) ...@@ -138,7 +138,7 @@ DefineQueryRewrite(RuleStmt *stmt)
* actions. But for now, let's just grab AccessExclusiveLock all the * actions. But for now, let's just grab AccessExclusiveLock all the
* time. * time.
*/ */
event_relation = heap_openr(event_obj->relname, AccessExclusiveLock); event_relation = heap_openrv(event_obj, AccessExclusiveLock);
ev_relid = RelationGetRelid(event_relation); ev_relid = RelationGetRelid(event_relation);
/* /*
......
...@@ -10,7 +10,7 @@ ...@@ -10,7 +10,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/tcop/utility.c,v 1.139 2002/03/24 04:31:08 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/tcop/utility.c,v 1.140 2002/03/26 19:16:03 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -18,6 +18,7 @@ ...@@ -18,6 +18,7 @@
#include "access/heapam.h" #include "access/heapam.h"
#include "catalog/catalog.h" #include "catalog/catalog.h"
#include "catalog/namespace.h"
#include "catalog/pg_shadow.h" #include "catalog/pg_shadow.h"
#include "commands/async.h" #include "commands/async.h"
#include "commands/cluster.h" #include "commands/cluster.h"
...@@ -94,9 +95,10 @@ DropErrorMsg(char *relname, char wrongkind, char rightkind) ...@@ -94,9 +95,10 @@ DropErrorMsg(char *relname, char wrongkind, char rightkind)
} }
static void static void
CheckDropPermissions(char *name, char rightkind) CheckDropPermissions(RangeVar *rel, char rightkind)
{ {
struct kindstrings *rentry; struct kindstrings *rentry;
Oid relOid;
HeapTuple tuple; HeapTuple tuple;
Form_pg_class classform; Form_pg_class classform;
...@@ -105,49 +107,54 @@ CheckDropPermissions(char *name, char rightkind) ...@@ -105,49 +107,54 @@ CheckDropPermissions(char *name, char rightkind)
break; break;
Assert(rentry->kind != '\0'); Assert(rentry->kind != '\0');
tuple = SearchSysCache(RELNAME, relOid = RangeVarGetRelid(rel, true);
PointerGetDatum(name), if (!OidIsValid(relOid))
elog(ERROR, "%s \"%s\" does not exist", rentry->name, rel->relname);
tuple = SearchSysCache(RELOID,
ObjectIdGetDatum(relOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tuple)) if (!HeapTupleIsValid(tuple))
elog(ERROR, "%s \"%s\" does not exist", rentry->name, name); elog(ERROR, "%s \"%s\" does not exist", rentry->name, rel->relname);
classform = (Form_pg_class) GETSTRUCT(tuple); classform = (Form_pg_class) GETSTRUCT(tuple);
if (classform->relkind != rightkind) if (classform->relkind != rightkind)
DropErrorMsg(name, classform->relkind, rightkind); DropErrorMsg(rel->relname, classform->relkind, rightkind);
if (!pg_class_ownercheck(tuple->t_data->t_oid, GetUserId())) if (!pg_class_ownercheck(relOid, GetUserId()))
elog(ERROR, "you do not own %s \"%s\"", elog(ERROR, "you do not own %s \"%s\"",
rentry->name, name); rentry->name, rel->relname);
if (!allowSystemTableMods && IsSystemRelationName(name) && if (!allowSystemTableMods && IsSystemRelationName(rel->relname) &&
!is_temp_relname(name)) !is_temp_relname(rel->relname))
elog(ERROR, "%s \"%s\" is a system %s", elog(ERROR, "%s \"%s\" is a system %s",
rentry->name, name, rentry->name); rentry->name, rel->relname, rentry->name);
ReleaseSysCache(tuple); ReleaseSysCache(tuple);
} }
static void static void
CheckOwnership(char *relname, bool noCatalogs) CheckOwnership(RangeVar *rel, bool noCatalogs)
{ {
Oid relOid;
HeapTuple tuple; HeapTuple tuple;
tuple = SearchSysCache(RELNAME, relOid = RangeVarGetRelid(rel, false);
PointerGetDatum(relname), tuple = SearchSysCache(RELOID,
ObjectIdGetDatum(relOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(tuple)) if (!HeapTupleIsValid(tuple))
elog(ERROR, "Relation \"%s\" does not exist", relname); elog(ERROR, "Relation \"%s\" does not exist", rel->relname);
if (!pg_class_ownercheck(tuple->t_data->t_oid, GetUserId())) if (!pg_class_ownercheck(relOid, GetUserId()))
elog(ERROR, "%s: %s", relname, elog(ERROR, "%s: %s", rel->relname,
aclcheck_error_strings[ACLCHECK_NOT_OWNER]); aclcheck_error_strings[ACLCHECK_NOT_OWNER]);
if (noCatalogs) if (noCatalogs)
{ {
if (!allowSystemTableMods && IsSystemRelationName(relname)) if (!allowSystemTableMods && IsSystemRelationName(rel->relname))
elog(ERROR, "relation \"%s\" is a system catalog", elog(ERROR, "relation \"%s\" is a system catalog",
relname); rel->relname);
} }
ReleaseSysCache(tuple); ReleaseSysCache(tuple);
...@@ -251,47 +258,52 @@ ProcessUtility(Node *parsetree, ...@@ -251,47 +258,52 @@ ProcessUtility(Node *parsetree,
break; break;
case T_CreateStmt: case T_CreateStmt:
DefineRelation((CreateStmt *) parsetree, RELKIND_RELATION); {
Oid relOid;
/* relOid = DefineRelation((CreateStmt *) parsetree,
* Let AlterTableCreateToastTable decide if this one needs a RELKIND_RELATION);
* secondary relation too.
*/ /*
CommandCounterIncrement(); * Let AlterTableCreateToastTable decide if this one needs a
AlterTableCreateToastTable(((CreateStmt *) parsetree)->relation->relname, * secondary relation too.
true); */
CommandCounterIncrement();
AlterTableCreateToastTable(relOid, true);
}
break; break;
case T_DropStmt: case T_DropStmt:
{ {
DropStmt *stmt = (DropStmt *) parsetree; DropStmt *stmt = (DropStmt *) parsetree;
List *args = stmt->objects;
List *arg; List *arg;
foreach(arg, args) foreach(arg, stmt->objects)
{ {
relname = ((RangeVar *) lfirst(arg))->relname; RangeVar *rel = (RangeVar *) lfirst(arg);
relname = rel->relname;
switch (stmt->removeType) switch (stmt->removeType)
{ {
case DROP_TABLE: case DROP_TABLE:
CheckDropPermissions(relname, RELKIND_RELATION); CheckDropPermissions(rel, RELKIND_RELATION);
RemoveRelation(relname); RemoveRelation(relname);
break; break;
case DROP_SEQUENCE: case DROP_SEQUENCE:
CheckDropPermissions(relname, RELKIND_SEQUENCE); CheckDropPermissions(rel, RELKIND_SEQUENCE);
RemoveRelation(relname); RemoveRelation(relname);
break; break;
case DROP_VIEW: case DROP_VIEW:
CheckDropPermissions(relname, RELKIND_VIEW); CheckDropPermissions(rel, RELKIND_VIEW);
RemoveView(relname); RemoveView(relname);
break; break;
case DROP_INDEX: case DROP_INDEX:
CheckDropPermissions(relname, RELKIND_INDEX); CheckDropPermissions(rel, RELKIND_INDEX);
RemoveIndex(relname); RemoveIndex(rel);
break; break;
case DROP_RULE: case DROP_RULE:
...@@ -329,13 +341,12 @@ ProcessUtility(Node *parsetree, ...@@ -329,13 +341,12 @@ ProcessUtility(Node *parsetree,
case T_CommentStmt: case T_CommentStmt:
{ {
CommentStmt *statement; CommentStmt *stmt;
statement = ((CommentStmt *) parsetree); stmt = ((CommentStmt *) parsetree);
CommentObject(statement->objtype, statement->objname, CommentObject(stmt->objtype, stmt->objschema, stmt->objname,
statement->objproperty, statement->objlist, stmt->objproperty, stmt->objlist, stmt->comment);
statement->comment);
} }
break; break;
...@@ -370,7 +381,7 @@ ProcessUtility(Node *parsetree, ...@@ -370,7 +381,7 @@ ProcessUtility(Node *parsetree,
RenameStmt *stmt = (RenameStmt *) parsetree; RenameStmt *stmt = (RenameStmt *) parsetree;
relname = stmt->relation->relname; relname = stmt->relation->relname;
CheckOwnership(relname, true); CheckOwnership(stmt->relation, true);
/* ---------------- /* ----------------
* XXX using len == 3 to tell the difference * XXX using len == 3 to tell the difference
...@@ -389,7 +400,7 @@ ProcessUtility(Node *parsetree, ...@@ -389,7 +400,7 @@ ProcessUtility(Node *parsetree,
* Note: we also rename the "type" tuple corresponding to * Note: we also rename the "type" tuple corresponding to
* the relation. * the relation.
*/ */
renamerel(relname, /* old name */ renamerel(stmt->relation, /* old relation */
stmt->newname); /* new name */ stmt->newname); /* new name */
} }
else else
...@@ -454,11 +465,11 @@ ProcessUtility(Node *parsetree, ...@@ -454,11 +465,11 @@ ProcessUtility(Node *parsetree,
stmt->behavior); stmt->behavior);
break; break;
case 'E': /* CREATE TOAST TABLE */ case 'E': /* CREATE TOAST TABLE */
AlterTableCreateToastTable(stmt->relation->relname, AlterTableCreateToastTable(RangeVarGetRelid(stmt->relation, false),
false); false);
break; break;
case 'U': /* ALTER OWNER */ case 'U': /* ALTER OWNER */
AlterTableOwner(stmt->relation->relname, AlterTableOwner(stmt->relation,
stmt->name); stmt->name);
break; break;
default: /* oops */ default: /* oops */
...@@ -519,10 +530,9 @@ ProcessUtility(Node *parsetree, ...@@ -519,10 +530,9 @@ ProcessUtility(Node *parsetree,
{ {
IndexStmt *stmt = (IndexStmt *) parsetree; IndexStmt *stmt = (IndexStmt *) parsetree;
relname = stmt->relation->relname; CheckOwnership(stmt->relation, true);
CheckOwnership(relname, true);
DefineIndex(stmt->relation->relname, /* relation */ DefineIndex(stmt->relation, /* relation */
stmt->idxname, /* index name */ stmt->idxname, /* index name */
stmt->accessMethod, /* am name */ stmt->accessMethod, /* am name */
stmt->indexParams, /* parameters */ stmt->indexParams, /* parameters */
...@@ -638,10 +648,9 @@ ProcessUtility(Node *parsetree, ...@@ -638,10 +648,9 @@ ProcessUtility(Node *parsetree,
{ {
ClusterStmt *stmt = (ClusterStmt *) parsetree; ClusterStmt *stmt = (ClusterStmt *) parsetree;
relname = stmt->relation->relname; CheckOwnership(stmt->relation, true);
CheckOwnership(relname, true);
cluster(relname, stmt->indexname); cluster(stmt->relation, stmt->indexname);
} }
break; break;
...@@ -775,13 +784,12 @@ ProcessUtility(Node *parsetree, ...@@ -775,13 +784,12 @@ ProcessUtility(Node *parsetree,
elog(ERROR, "\"%s\" is a system index. call REINDEX under standalone postgres with -P -O options", elog(ERROR, "\"%s\" is a system index. call REINDEX under standalone postgres with -P -O options",
relname); relname);
} }
CheckOwnership(relname, false); CheckOwnership(stmt->relation, false);
ReindexIndex(relname, stmt->force); ReindexIndex(stmt->relation, stmt->force);
break; break;
case TABLE: case TABLE:
relname = (char *) stmt->relation->relname; CheckOwnership(stmt->relation, false);
CheckOwnership(relname, false); ReindexTable(stmt->relation, stmt->force);
ReindexTable(relname, stmt->force);
break; break;
case DATABASE: case DATABASE:
relname = (char *) stmt->name; relname = (char *) stmt->name;
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/utils/adt/acl.c,v 1.69 2002/03/21 23:27:24 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/utils/adt/acl.c,v 1.70 2002/03/26 19:16:05 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -18,6 +18,7 @@ ...@@ -18,6 +18,7 @@
#include "access/heapam.h" #include "access/heapam.h"
#include "catalog/catalog.h" #include "catalog/catalog.h"
#include "catalog/namespace.h"
#include "catalog/pg_shadow.h" #include "catalog/pg_shadow.h"
#include "catalog/pg_type.h" #include "catalog/pg_type.h"
#include "lib/stringinfo.h" #include "lib/stringinfo.h"
...@@ -723,7 +724,7 @@ makeAclString(const char *privileges, const char *grantee, char grant_or_revoke) ...@@ -723,7 +724,7 @@ makeAclString(const char *privileges, const char *grantee, char grant_or_revoke)
/* /*
* has_table_privilege_name_name * has_table_privilege_name_name
* Check user privileges on a relation given * Check user privileges on a relation given
* name usename, name relname, and text priv name. * name username, name relname, and text priv name.
* *
* RETURNS * RETURNS
* a boolean value * a boolean value
...@@ -995,7 +996,8 @@ has_table_privilege_cname_id(char *username, Oid reloid, ...@@ -995,7 +996,8 @@ has_table_privilege_cname_id(char *username, Oid reloid,
text *priv_type_text) text *priv_type_text)
{ {
int32 usesysid; int32 usesysid;
char *relname; AclMode mode;
int32 result;
/* /*
* Lookup userid based on username * Lookup userid based on username
...@@ -1003,18 +1005,19 @@ has_table_privilege_cname_id(char *username, Oid reloid, ...@@ -1003,18 +1005,19 @@ has_table_privilege_cname_id(char *username, Oid reloid,
usesysid = get_usesysid(username); usesysid = get_usesysid(username);
/* /*
* Lookup relname based on rel oid * Convert priv_type_text to an AclMode
*/ */
relname = get_rel_name(reloid); mode = convert_priv_string(priv_type_text);
if (relname == NULL)
elog(ERROR, "has_table_privilege: invalid relation oid %u",
reloid);
/* /*
* Make use of has_table_privilege_id_cname. It accepts the arguments * Finally, check for the privilege
* we now have.
*/ */
return has_table_privilege_id_cname(usesysid, relname, priv_type_text); result = pg_class_aclcheck(reloid, usesysid, mode);
if (result == ACLCHECK_OK)
return true;
else
return false;
} }
...@@ -1039,9 +1042,7 @@ has_table_privilege_id_cname(int32 usesysid, char *relname, ...@@ -1039,9 +1042,7 @@ has_table_privilege_id_cname(int32 usesysid, char *relname,
/* /*
* Convert relname to rel OID. * Convert relname to rel OID.
*/ */
reloid = GetSysCacheOid(RELNAME, reloid = RelnameGetRelid(relname);
PointerGetDatum(relname),
0, 0, 0);
if (!OidIsValid(reloid)) if (!OidIsValid(reloid))
elog(ERROR, "has_table_privilege: relation \"%s\" does not exist", elog(ERROR, "has_table_privilege: relation \"%s\" does not exist",
relname); relname);
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/utils/cache/catcache.c,v 1.92 2002/03/06 20:49:45 momjian Exp $ * $Header: /cvsroot/pgsql/src/backend/utils/cache/catcache.c,v 1.93 2002/03/26 19:16:08 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -656,11 +656,11 @@ do { \ ...@@ -656,11 +656,11 @@ do { \
CatCache * CatCache *
InitCatCache(int id, InitCatCache(int id,
char *relname, const char *relname,
char *indname, const char *indname,
int reloidattr, int reloidattr,
int nkeys, int nkeys,
int *key) const int *key)
{ {
CatCache *cp; CatCache *cp;
MemoryContext oldcxt; MemoryContext oldcxt;
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/utils/cache/lsyscache.c,v 1.65 2002/03/22 02:56:35 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/utils/cache/lsyscache.c,v 1.66 2002/03/26 19:16:09 tgl Exp $
* *
* NOTES * NOTES
* Eventually, the index information should go through here, too. * Eventually, the index information should go through here, too.
...@@ -634,6 +634,21 @@ func_iscachable(Oid funcid) ...@@ -634,6 +634,21 @@ func_iscachable(Oid funcid)
/* ---------- RELATION CACHE ---------- */ /* ---------- RELATION CACHE ---------- */
/*
* get_relname_relid
* Given name and namespace of a relation, look up the OID.
*
* Returns InvalidOid if there is no such relation.
*/
Oid
get_relname_relid(const char *relname, Oid relnamespace)
{
return GetSysCacheOid(RELNAMENSP,
PointerGetDatum(relname),
ObjectIdGetDatum(relnamespace),
0, 0);
}
#ifdef NOT_USED #ifdef NOT_USED
/* /*
* get_relnatts * get_relnatts
...@@ -664,10 +679,12 @@ get_relnatts(Oid relid) ...@@ -664,10 +679,12 @@ get_relnatts(Oid relid)
/* /*
* get_rel_name * get_rel_name
*
* Returns the name of a given relation. * Returns the name of a given relation.
* *
* Note: returns a palloc'd copy of the string, or NULL if no such relation. * Returns a palloc'd copy of the string, or NULL if no such relation.
*
* NOTE: since relation name is not unique, be wary of code that uses this
* for anything except preparing error messages.
*/ */
char * char *
get_rel_name(Oid relid) get_rel_name(Oid relid)
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/utils/cache/relcache.c,v 1.157 2002/03/19 02:18:22 momjian Exp $ * $Header: /cvsroot/pgsql/src/backend/utils/cache/relcache.c,v 1.158 2002/03/26 19:16:10 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -16,10 +16,9 @@ ...@@ -16,10 +16,9 @@
* INTERFACE ROUTINES * INTERFACE ROUTINES
* RelationCacheInitialize - initialize relcache * RelationCacheInitialize - initialize relcache
* RelationCacheInitializePhase2 - finish initializing relcache * RelationCacheInitializePhase2 - finish initializing relcache
* RelationIdCacheGetRelation - get a reldesc from the cache (id)
* RelationNameCacheGetRelation - get a reldesc from the cache (name)
* RelationIdGetRelation - get a reldesc by relation id * RelationIdGetRelation - get a reldesc by relation id
* RelationNameGetRelation - get a reldesc by relation name * RelationSysNameGetRelation - get a reldesc by system rel name
* RelationIdCacheGetRelation - get a cached reldesc by relid
* RelationClose - close an open relation * RelationClose - close an open relation
* *
* NOTES * NOTES
...@@ -39,13 +38,13 @@ ...@@ -39,13 +38,13 @@
#include "access/istrat.h" #include "access/istrat.h"
#include "catalog/catalog.h" #include "catalog/catalog.h"
#include "catalog/catname.h" #include "catalog/catname.h"
#include "catalog/index.h"
#include "catalog/indexing.h" #include "catalog/indexing.h"
#include "catalog/pg_amop.h" #include "catalog/pg_amop.h"
#include "catalog/pg_amproc.h" #include "catalog/pg_amproc.h"
#include "catalog/pg_attrdef.h" #include "catalog/pg_attrdef.h"
#include "catalog/pg_attribute.h" #include "catalog/pg_attribute.h"
#include "catalog/pg_index.h" #include "catalog/pg_index.h"
#include "catalog/pg_namespace.h"
#include "catalog/pg_opclass.h" #include "catalog/pg_opclass.h"
#include "catalog/pg_proc.h" #include "catalog/pg_proc.h"
#include "catalog/pg_relcheck.h" #include "catalog/pg_relcheck.h"
...@@ -70,7 +69,7 @@ ...@@ -70,7 +69,7 @@
#define RELCACHE_INIT_FILENAME "pg_internal.init" #define RELCACHE_INIT_FILENAME "pg_internal.init"
/* /*
* hardcoded tuple descriptors. see lib/backend/catalog/pg_attribute.h * hardcoded tuple descriptors. see include/catalog/pg_attribute.h
*/ */
static FormData_pg_attribute Desc_pg_class[Natts_pg_class] = {Schema_pg_class}; static FormData_pg_attribute Desc_pg_class[Natts_pg_class] = {Schema_pg_class};
static FormData_pg_attribute Desc_pg_attribute[Natts_pg_attribute] = {Schema_pg_attribute}; static FormData_pg_attribute Desc_pg_attribute[Natts_pg_attribute] = {Schema_pg_attribute};
...@@ -80,11 +79,14 @@ static FormData_pg_attribute Desc_pg_type[Natts_pg_type] = {Schema_pg_type}; ...@@ -80,11 +79,14 @@ static FormData_pg_attribute Desc_pg_type[Natts_pg_type] = {Schema_pg_type};
/* /*
* Hash tables that index the relation cache * Hash tables that index the relation cache
* *
* Relations are looked up two ways, by name and by id, * Relations are looked up two ways, by OID and by name,
* thus there are two hash tables for referencing them. * thus there are two hash tables for referencing them.
*
* The OID index covers all relcache entries. The name index
* covers *only* system relations (only those in PG_CATALOG_NAMESPACE).
*/ */
static HTAB *RelationNameCache;
static HTAB *RelationIdCache; static HTAB *RelationIdCache;
static HTAB *RelationSysNameCache;
/* /*
* Bufmgr uses RelFileNode for lookup. Actually, I would like to do * Bufmgr uses RelFileNode for lookup. Actually, I would like to do
...@@ -128,7 +130,7 @@ static List *initFileRelationIds = NIL; ...@@ -128,7 +130,7 @@ static List *initFileRelationIds = NIL;
/* /*
* RelationBuildDescInfo exists so code can be shared * RelationBuildDescInfo exists so code can be shared
* between RelationIdGetRelation() and RelationNameGetRelation() * between RelationIdGetRelation() and RelationSysNameGetRelation()
*/ */
typedef struct RelationBuildDescInfo typedef struct RelationBuildDescInfo
{ {
...@@ -138,22 +140,22 @@ typedef struct RelationBuildDescInfo ...@@ -138,22 +140,22 @@ typedef struct RelationBuildDescInfo
union union
{ {
Oid info_id; /* relation object id */ Oid info_id; /* relation object id */
char *info_name; /* relation name */ char *info_name; /* system relation name */
} i; } i;
} RelationBuildDescInfo; } RelationBuildDescInfo;
typedef struct relnamecacheent
{
NameData relname;
Relation reldesc;
} RelNameCacheEnt;
typedef struct relidcacheent typedef struct relidcacheent
{ {
Oid reloid; Oid reloid;
Relation reldesc; Relation reldesc;
} RelIdCacheEnt; } RelIdCacheEnt;
typedef struct relnamecacheent
{
NameData relname;
Relation reldesc;
} RelNameCacheEnt;
typedef struct relnodecacheent typedef struct relnodecacheent
{ {
RelFileNode relnode; RelFileNode relnode;
...@@ -165,24 +167,14 @@ typedef struct relnodecacheent ...@@ -165,24 +167,14 @@ typedef struct relnodecacheent
*/ */
#define RelationCacheInsert(RELATION) \ #define RelationCacheInsert(RELATION) \
do { \ do { \
RelIdCacheEnt *idhentry; RelNameCacheEnt *namehentry; \ RelIdCacheEnt *idhentry; RelNodeCacheEnt *nodentry; bool found; \
char *relname; RelNodeCacheEnt *nodentry; bool found; \
relname = RelationGetPhysicalRelationName(RELATION); \
namehentry = (RelNameCacheEnt*)hash_search(RelationNameCache, \
relname, \
HASH_ENTER, \
&found); \
if (namehentry == NULL) \
elog(ERROR, "out of memory for relation descriptor cache"); \
/* used to give notice if found -- now just keep quiet */ ; \
namehentry->reldesc = RELATION; \
idhentry = (RelIdCacheEnt*)hash_search(RelationIdCache, \ idhentry = (RelIdCacheEnt*)hash_search(RelationIdCache, \
(void *) &(RELATION->rd_id), \ (void *) &(RELATION->rd_id), \
HASH_ENTER, \ HASH_ENTER, \
&found); \ &found); \
if (idhentry == NULL) \ if (idhentry == NULL) \
elog(ERROR, "out of memory for relation descriptor cache"); \ elog(ERROR, "out of memory for relation descriptor cache"); \
/* used to give notice if found -- now just keep quiet */ ; \ /* used to give notice if found -- now just keep quiet */ \
idhentry->reldesc = RELATION; \ idhentry->reldesc = RELATION; \
nodentry = (RelNodeCacheEnt*)hash_search(RelationNodeCache, \ nodentry = (RelNodeCacheEnt*)hash_search(RelationNodeCache, \
(void *) &(RELATION->rd_node), \ (void *) &(RELATION->rd_node), \
...@@ -190,26 +182,39 @@ do { \ ...@@ -190,26 +182,39 @@ do { \
&found); \ &found); \
if (nodentry == NULL) \ if (nodentry == NULL) \
elog(ERROR, "out of memory for relation descriptor cache"); \ elog(ERROR, "out of memory for relation descriptor cache"); \
/* used to give notice if found -- now just keep quiet */ ; \ /* used to give notice if found -- now just keep quiet */ \
nodentry->reldesc = RELATION; \ nodentry->reldesc = RELATION; \
if (RelationGetNamespace(RELATION) == PG_CATALOG_NAMESPACE) \
{ \
char *relname = RelationGetPhysicalRelationName(RELATION); \
RelNameCacheEnt *namehentry; \
namehentry = (RelNameCacheEnt*)hash_search(RelationSysNameCache, \
relname, \
HASH_ENTER, \
&found); \
if (namehentry == NULL) \
elog(ERROR, "out of memory for relation descriptor cache"); \
/* used to give notice if found -- now just keep quiet */ \
namehentry->reldesc = RELATION; \
} \
} while(0) } while(0)
#define RelationNameCacheLookup(NAME, RELATION) \ #define RelationIdCacheLookup(ID, RELATION) \
do { \ do { \
RelNameCacheEnt *hentry; \ RelIdCacheEnt *hentry; \
hentry = (RelNameCacheEnt*)hash_search(RelationNameCache, \ hentry = (RelIdCacheEnt*)hash_search(RelationIdCache, \
(void *) (NAME), HASH_FIND,NULL); \ (void *)&(ID), HASH_FIND,NULL); \
if (hentry) \ if (hentry) \
RELATION = hentry->reldesc; \ RELATION = hentry->reldesc; \
else \ else \
RELATION = NULL; \ RELATION = NULL; \
} while(0) } while(0)
#define RelationIdCacheLookup(ID, RELATION) \ #define RelationSysNameCacheLookup(NAME, RELATION) \
do { \ do { \
RelIdCacheEnt *hentry; \ RelNameCacheEnt *hentry; \
hentry = (RelIdCacheEnt*)hash_search(RelationIdCache, \ hentry = (RelNameCacheEnt*)hash_search(RelationSysNameCache, \
(void *)&(ID), HASH_FIND,NULL); \ (void *) (NAME), HASH_FIND,NULL); \
if (hentry) \ if (hentry) \
RELATION = hentry->reldesc; \ RELATION = hentry->reldesc; \
else \ else \
...@@ -229,14 +234,7 @@ do { \ ...@@ -229,14 +234,7 @@ do { \
#define RelationCacheDelete(RELATION) \ #define RelationCacheDelete(RELATION) \
do { \ do { \
RelNameCacheEnt *namehentry; RelIdCacheEnt *idhentry; \ RelIdCacheEnt *idhentry; RelNodeCacheEnt *nodentry; \
char *relname; RelNodeCacheEnt *nodentry; \
relname = RelationGetPhysicalRelationName(RELATION); \
namehentry = (RelNameCacheEnt*)hash_search(RelationNameCache, \
relname, \
HASH_REMOVE, NULL); \
if (namehentry == NULL) \
elog(WARNING, "trying to delete a reldesc that does not exist."); \
idhentry = (RelIdCacheEnt*)hash_search(RelationIdCache, \ idhentry = (RelIdCacheEnt*)hash_search(RelationIdCache, \
(void *)&(RELATION->rd_id), \ (void *)&(RELATION->rd_id), \
HASH_REMOVE, NULL); \ HASH_REMOVE, NULL); \
...@@ -247,6 +245,16 @@ do { \ ...@@ -247,6 +245,16 @@ do { \
HASH_REMOVE, NULL); \ HASH_REMOVE, NULL); \
if (nodentry == NULL) \ if (nodentry == NULL) \
elog(WARNING, "trying to delete a reldesc that does not exist."); \ elog(WARNING, "trying to delete a reldesc that does not exist."); \
if (RelationGetNamespace(RELATION) == PG_CATALOG_NAMESPACE) \
{ \
char *relname = RelationGetPhysicalRelationName(RELATION); \
RelNameCacheEnt *namehentry; \
namehentry = (RelNameCacheEnt*)hash_search(RelationSysNameCache, \
relname, \
HASH_REMOVE, NULL); \
if (namehentry == NULL) \
elog(WARNING, "trying to delete a reldesc that does not exist."); \
} \
} while(0) } while(0)
...@@ -275,11 +283,11 @@ static void RelationClearRelation(Relation relation, bool rebuildIt); ...@@ -275,11 +283,11 @@ static void RelationClearRelation(Relation relation, bool rebuildIt);
static void RelationReloadClassinfo(Relation relation); static void RelationReloadClassinfo(Relation relation);
#endif /* ENABLE_REINDEX_NAILED_RELATIONS */ #endif /* ENABLE_REINDEX_NAILED_RELATIONS */
static void RelationFlushRelation(Relation relation); static void RelationFlushRelation(Relation relation);
static Relation RelationNameCacheGetRelation(const char *relationName); static Relation RelationSysNameCacheGetRelation(const char *relationName);
static bool load_relcache_init_file(void); static bool load_relcache_init_file(void);
static void write_relcache_init_file(void); static void write_relcache_init_file(void);
static void formrdesc(char *relationName, int natts, static void formrdesc(const char *relationName, int natts,
FormData_pg_attribute *att); FormData_pg_attribute *att);
static HeapTuple ScanPgRelation(RelationBuildDescInfo buildinfo); static HeapTuple ScanPgRelation(RelationBuildDescInfo buildinfo);
...@@ -303,12 +311,6 @@ static OpClassCacheEnt *LookupOpclassInfo(Oid operatorClassOid, ...@@ -303,12 +311,6 @@ static OpClassCacheEnt *LookupOpclassInfo(Oid operatorClassOid,
StrategyNumber numSupport); StrategyNumber numSupport);
/*
* RelationIdGetRelation() and RelationNameGetRelation()
* support functions
*/
/* /*
* ScanPgRelation * ScanPgRelation
* *
...@@ -326,7 +328,8 @@ ScanPgRelation(RelationBuildDescInfo buildinfo) ...@@ -326,7 +328,8 @@ ScanPgRelation(RelationBuildDescInfo buildinfo)
Relation pg_class_desc; Relation pg_class_desc;
const char *indexRelname; const char *indexRelname;
SysScanDesc pg_class_scan; SysScanDesc pg_class_scan;
ScanKeyData key; ScanKeyData key[2];
int nkeys;
/* /*
* form a scan key * form a scan key
...@@ -334,19 +337,25 @@ ScanPgRelation(RelationBuildDescInfo buildinfo) ...@@ -334,19 +337,25 @@ ScanPgRelation(RelationBuildDescInfo buildinfo)
switch (buildinfo.infotype) switch (buildinfo.infotype)
{ {
case INFO_RELID: case INFO_RELID:
ScanKeyEntryInitialize(&key, 0, ScanKeyEntryInitialize(&key[0], 0,
ObjectIdAttributeNumber, ObjectIdAttributeNumber,
F_OIDEQ, F_OIDEQ,
ObjectIdGetDatum(buildinfo.i.info_id)); ObjectIdGetDatum(buildinfo.i.info_id));
nkeys = 1;
indexRelname = ClassOidIndex; indexRelname = ClassOidIndex;
break; break;
case INFO_RELNAME: case INFO_RELNAME:
ScanKeyEntryInitialize(&key, 0, ScanKeyEntryInitialize(&key[0], 0,
Anum_pg_class_relname, Anum_pg_class_relname,
F_NAMEEQ, F_NAMEEQ,
NameGetDatum(buildinfo.i.info_name)); NameGetDatum(buildinfo.i.info_name));
indexRelname = ClassNameIndex; ScanKeyEntryInitialize(&key[1], 0,
Anum_pg_class_relnamespace,
F_OIDEQ,
ObjectIdGetDatum(PG_CATALOG_NAMESPACE));
nkeys = 2;
indexRelname = ClassNameNspIndex;
break; break;
default: default:
...@@ -363,7 +372,7 @@ ScanPgRelation(RelationBuildDescInfo buildinfo) ...@@ -363,7 +372,7 @@ ScanPgRelation(RelationBuildDescInfo buildinfo)
pg_class_scan = systable_beginscan(pg_class_desc, indexRelname, pg_class_scan = systable_beginscan(pg_class_desc, indexRelname,
criticalRelcachesBuilt, criticalRelcachesBuilt,
SnapshotNow, SnapshotNow,
1, &key); nkeys, key);
pg_class_tuple = systable_getnext(pg_class_scan); pg_class_tuple = systable_getnext(pg_class_scan);
...@@ -512,12 +521,8 @@ RelationBuildTupleDesc(RelationBuildDescInfo buildinfo, ...@@ -512,12 +521,8 @@ RelationBuildTupleDesc(RelationBuildDescInfo buildinfo,
(char *) attp, (char *) attp,
ATTRIBUTE_TUPLE_SIZE); ATTRIBUTE_TUPLE_SIZE);
/* Update constraint/default info */
if (attp->attnotnull)
/*
* Update constraint/default info
*/
if (attp->attnotnull)
constr->has_not_null = true; constr->has_not_null = true;
if (attp->atthasdef) if (attp->atthasdef)
...@@ -1333,7 +1338,7 @@ LookupOpclassInfo(Oid operatorClassOid, ...@@ -1333,7 +1338,7 @@ LookupOpclassInfo(Oid operatorClassOid,
* NOTE: we assume we are already switched into CacheMemoryContext. * NOTE: we assume we are already switched into CacheMemoryContext.
*/ */
static void static void
formrdesc(char *relationName, formrdesc(const char *relationName,
int natts, int natts,
FormData_pg_attribute *att) FormData_pg_attribute *att)
{ {
...@@ -1374,7 +1379,8 @@ formrdesc(char *relationName, ...@@ -1374,7 +1379,8 @@ formrdesc(char *relationName,
relation->rd_rel = (Form_pg_class) palloc(CLASS_TUPLE_SIZE); relation->rd_rel = (Form_pg_class) palloc(CLASS_TUPLE_SIZE);
MemSet(relation->rd_rel, 0, CLASS_TUPLE_SIZE); MemSet(relation->rd_rel, 0, CLASS_TUPLE_SIZE);
strcpy(RelationGetPhysicalRelationName(relation), relationName); namestrcpy(&relation->rd_rel->relname, relationName);
relation->rd_rel->relnamespace = PG_CATALOG_NAMESPACE;
/* /*
* It's important to distinguish between shared and non-shared * It's important to distinguish between shared and non-shared
...@@ -1488,12 +1494,12 @@ RelationIdCacheGetRelation(Oid relationId) ...@@ -1488,12 +1494,12 @@ RelationIdCacheGetRelation(Oid relationId)
} }
/* /*
* RelationNameCacheGetRelation * RelationSysNameCacheGetRelation
* *
* As above, but lookup by name. * As above, but lookup by name; only works for system catalogs.
*/ */
static Relation static Relation
RelationNameCacheGetRelation(const char *relationName) RelationSysNameCacheGetRelation(const char *relationName)
{ {
Relation rd; Relation rd;
NameData name; NameData name;
...@@ -1503,7 +1509,7 @@ RelationNameCacheGetRelation(const char *relationName) ...@@ -1503,7 +1509,7 @@ RelationNameCacheGetRelation(const char *relationName)
* null-padded * null-padded
*/ */
namestrcpy(&name, relationName); namestrcpy(&name, relationName);
RelationNameCacheLookup(NameStr(name), rd); RelationSysNameCacheLookup(NameStr(name), rd);
if (RelationIsValid(rd)) if (RelationIsValid(rd))
RelationIncrementReferenceCount(rd); RelationIncrementReferenceCount(rd);
...@@ -1539,12 +1545,6 @@ RelationIdGetRelation(Oid relationId) ...@@ -1539,12 +1545,6 @@ RelationIdGetRelation(Oid relationId)
Relation rd; Relation rd;
RelationBuildDescInfo buildinfo; RelationBuildDescInfo buildinfo;
/*
* increment access statistics
*/
IncrHeapAccessStat(local_RelationIdGetRelation);
IncrHeapAccessStat(global_RelationIdGetRelation);
/* /*
* first try and get a reldesc from the cache * first try and get a reldesc from the cache
*/ */
...@@ -1564,23 +1564,17 @@ RelationIdGetRelation(Oid relationId) ...@@ -1564,23 +1564,17 @@ RelationIdGetRelation(Oid relationId)
} }
/* /*
* RelationNameGetRelation * RelationSysNameGetRelation
* *
* As above, but lookup by name. * As above, but lookup by name; only works for system catalogs.
*/ */
Relation Relation
RelationNameGetRelation(const char *relationName) RelationSysNameGetRelation(const char *relationName)
{ {
char *temprelname; char *temprelname;
Relation rd; Relation rd;
RelationBuildDescInfo buildinfo; RelationBuildDescInfo buildinfo;
/*
* increment access statistics
*/
IncrHeapAccessStat(local_RelationNameGetRelation);
IncrHeapAccessStat(global_RelationNameGetRelation);
/* /*
* if caller is looking for a temp relation, substitute its real name; * if caller is looking for a temp relation, substitute its real name;
* we only index temp rels by their real names. * we only index temp rels by their real names.
...@@ -1592,7 +1586,7 @@ RelationNameGetRelation(const char *relationName) ...@@ -1592,7 +1586,7 @@ RelationNameGetRelation(const char *relationName)
/* /*
* first try and get a reldesc from the cache * first try and get a reldesc from the cache
*/ */
rd = RelationNameCacheGetRelation(relationName); rd = RelationSysNameCacheGetRelation(relationName);
if (RelationIsValid(rd)) if (RelationIsValid(rd))
return rd; return rd;
...@@ -1951,17 +1945,17 @@ void ...@@ -1951,17 +1945,17 @@ void
RelationCacheInvalidate(void) RelationCacheInvalidate(void)
{ {
HASH_SEQ_STATUS status; HASH_SEQ_STATUS status;
RelNameCacheEnt *namehentry; RelIdCacheEnt *idhentry;
Relation relation; Relation relation;
List *rebuildList = NIL; List *rebuildList = NIL;
List *l; List *l;
/* Phase 1 */ /* Phase 1 */
hash_seq_init(&status, RelationNameCache); hash_seq_init(&status, RelationIdCache);
while ((namehentry = (RelNameCacheEnt *) hash_seq_search(&status)) != NULL) while ((idhentry = (RelIdCacheEnt *) hash_seq_search(&status)) != NULL)
{ {
relation = namehentry->reldesc; relation = idhentry->reldesc;
/* Ignore xact-local relations, since they are never SI targets */ /* Ignore xact-local relations, since they are never SI targets */
if (relation->rd_myxactonly) if (relation->rd_myxactonly)
...@@ -2007,13 +2001,13 @@ void ...@@ -2007,13 +2001,13 @@ void
RelationCacheAbort(void) RelationCacheAbort(void)
{ {
HASH_SEQ_STATUS status; HASH_SEQ_STATUS status;
RelNameCacheEnt *namehentry; RelIdCacheEnt *idhentry;
hash_seq_init(&status, RelationNameCache); hash_seq_init(&status, RelationIdCache);
while ((namehentry = (RelNameCacheEnt *) hash_seq_search(&status)) != NULL) while ((idhentry = (RelIdCacheEnt *) hash_seq_search(&status)) != NULL)
{ {
Relation relation = namehentry->reldesc; Relation relation = idhentry->reldesc;
if (relation->rd_isnailed) if (relation->rd_isnailed)
RelationSetReferenceCount(relation, 1); RelationSetReferenceCount(relation, 1);
...@@ -2029,8 +2023,10 @@ RelationCacheAbort(void) ...@@ -2029,8 +2023,10 @@ RelationCacheAbort(void)
*/ */
Relation Relation
RelationBuildLocalRelation(const char *relname, RelationBuildLocalRelation(const char *relname,
Oid relnamespace,
TupleDesc tupDesc, TupleDesc tupDesc,
Oid relid, Oid dbid, Oid relid, Oid dbid,
RelFileNode rnode,
bool nailit) bool nailit)
{ {
Relation rel; Relation rel;
...@@ -2086,7 +2082,8 @@ RelationBuildLocalRelation(const char *relname, ...@@ -2086,7 +2082,8 @@ RelationBuildLocalRelation(const char *relname,
rel->rd_rel = (Form_pg_class) palloc(CLASS_TUPLE_SIZE); rel->rd_rel = (Form_pg_class) palloc(CLASS_TUPLE_SIZE);
MemSet((char *) rel->rd_rel, 0, CLASS_TUPLE_SIZE); MemSet((char *) rel->rd_rel, 0, CLASS_TUPLE_SIZE);
strcpy(RelationGetPhysicalRelationName(rel), relname); namestrcpy(&rel->rd_rel->relname, relname);
rel->rd_rel->relnamespace = relnamespace;
rel->rd_rel->relkind = RELKIND_UNCATALOGED; rel->rd_rel->relkind = RELKIND_UNCATALOGED;
rel->rd_rel->relhasoids = true; rel->rd_rel->relhasoids = true;
...@@ -2094,10 +2091,8 @@ RelationBuildLocalRelation(const char *relname, ...@@ -2094,10 +2091,8 @@ RelationBuildLocalRelation(const char *relname,
rel->rd_rel->reltype = InvalidOid; rel->rd_rel->reltype = InvalidOid;
/* /*
* Insert relation OID and database/tablespace ID into the right * Insert relation physical and logical identifiers (OIDs) into the
* places. XXX currently we assume physical tblspace/relnode are same * right places.
* as logical dbid/reloid. Probably should pass an extra pair of
* parameters.
*/ */
rel->rd_rel->relisshared = (dbid == InvalidOid); rel->rd_rel->relisshared = (dbid == InvalidOid);
...@@ -2106,11 +2101,10 @@ RelationBuildLocalRelation(const char *relname, ...@@ -2106,11 +2101,10 @@ RelationBuildLocalRelation(const char *relname,
for (i = 0; i < natts; i++) for (i = 0; i < natts; i++)
rel->rd_att->attrs[i]->attrelid = relid; rel->rd_att->attrs[i]->attrelid = relid;
RelationInitLockInfo(rel); /* see lmgr.c */ rel->rd_node = rnode;
rel->rd_rel->relfilenode = rnode.relNode;
rel->rd_node.tblNode = dbid; RelationInitLockInfo(rel); /* see lmgr.c */
rel->rd_node.relNode = relid;
rel->rd_rel->relfilenode = relid;
/* /*
* Okay to insert into the relcache hash tables. * Okay to insert into the relcache hash tables.
...@@ -2201,8 +2195,8 @@ RelationCacheInitialize(void) ...@@ -2201,8 +2195,8 @@ RelationCacheInitialize(void)
MemSet(&ctl, 0, sizeof(ctl)); MemSet(&ctl, 0, sizeof(ctl));
ctl.keysize = sizeof(NameData); ctl.keysize = sizeof(NameData);
ctl.entrysize = sizeof(RelNameCacheEnt); ctl.entrysize = sizeof(RelNameCacheEnt);
RelationNameCache = hash_create("Relcache by name", INITRELCACHESIZE, RelationSysNameCache = hash_create("Relcache by name", INITRELCACHESIZE,
&ctl, HASH_ELEM); &ctl, HASH_ELEM);
ctl.keysize = sizeof(Oid); ctl.keysize = sizeof(Oid);
ctl.entrysize = sizeof(RelIdCacheEnt); ctl.entrysize = sizeof(RelIdCacheEnt);
...@@ -2252,7 +2246,7 @@ void ...@@ -2252,7 +2246,7 @@ void
RelationCacheInitializePhase2(void) RelationCacheInitializePhase2(void)
{ {
HASH_SEQ_STATUS status; HASH_SEQ_STATUS status;
RelNameCacheEnt *namehentry; RelIdCacheEnt *idhentry;
if (IsBootstrapProcessingMode()) if (IsBootstrapProcessingMode())
return; return;
...@@ -2290,7 +2284,7 @@ RelationCacheInitializePhase2(void) ...@@ -2290,7 +2284,7 @@ RelationCacheInitializePhase2(void)
RelationSetReferenceCount(ird, 1); \ RelationSetReferenceCount(ird, 1); \
} while (0) } while (0)
LOAD_CRIT_INDEX(ClassNameIndex); LOAD_CRIT_INDEX(ClassNameNspIndex);
LOAD_CRIT_INDEX(ClassOidIndex); LOAD_CRIT_INDEX(ClassOidIndex);
LOAD_CRIT_INDEX(AttributeRelidNumIndex); LOAD_CRIT_INDEX(AttributeRelidNumIndex);
LOAD_CRIT_INDEX(IndexRelidIndex); LOAD_CRIT_INDEX(IndexRelidIndex);
...@@ -2311,11 +2305,11 @@ RelationCacheInitializePhase2(void) ...@@ -2311,11 +2305,11 @@ RelationCacheInitializePhase2(void)
* Also, if any of the relcache entries have rules or triggers, * Also, if any of the relcache entries have rules or triggers,
* load that info the hard way since it isn't recorded in the cache file. * load that info the hard way since it isn't recorded in the cache file.
*/ */
hash_seq_init(&status, RelationNameCache); hash_seq_init(&status, RelationIdCache);
while ((namehentry = (RelNameCacheEnt *) hash_seq_search(&status)) != NULL) while ((idhentry = (RelIdCacheEnt *) hash_seq_search(&status)) != NULL)
{ {
Relation relation = namehentry->reldesc; Relation relation = idhentry->reldesc;
/* /*
* If it's a faked-up entry, read the real pg_class tuple. * If it's a faked-up entry, read the real pg_class tuple.
...@@ -2399,8 +2393,8 @@ CreateDummyCaches(void) ...@@ -2399,8 +2393,8 @@ CreateDummyCaches(void)
MemSet(&ctl, 0, sizeof(ctl)); MemSet(&ctl, 0, sizeof(ctl));
ctl.keysize = sizeof(NameData); ctl.keysize = sizeof(NameData);
ctl.entrysize = sizeof(RelNameCacheEnt); ctl.entrysize = sizeof(RelNameCacheEnt);
RelationNameCache = hash_create("Relcache by name", INITRELCACHESIZE, RelationSysNameCache = hash_create("Relcache by name", INITRELCACHESIZE,
&ctl, HASH_ELEM); &ctl, HASH_ELEM);
ctl.keysize = sizeof(Oid); ctl.keysize = sizeof(Oid);
ctl.entrysize = sizeof(RelIdCacheEnt); ctl.entrysize = sizeof(RelIdCacheEnt);
...@@ -2427,14 +2421,14 @@ DestroyDummyCaches(void) ...@@ -2427,14 +2421,14 @@ DestroyDummyCaches(void)
oldcxt = MemoryContextSwitchTo(CacheMemoryContext); oldcxt = MemoryContextSwitchTo(CacheMemoryContext);
if (RelationNameCache)
hash_destroy(RelationNameCache);
if (RelationIdCache) if (RelationIdCache)
hash_destroy(RelationIdCache); hash_destroy(RelationIdCache);
if (RelationSysNameCache)
hash_destroy(RelationSysNameCache);
if (RelationNodeCache) if (RelationNodeCache)
hash_destroy(RelationNodeCache); hash_destroy(RelationNodeCache);
RelationNameCache = RelationIdCache = RelationNodeCache = NULL; RelationIdCache = RelationSysNameCache = RelationNodeCache = NULL;
MemoryContextSwitchTo(oldcxt); MemoryContextSwitchTo(oldcxt);
} }
...@@ -3001,7 +2995,7 @@ write_relcache_init_file(void) ...@@ -3001,7 +2995,7 @@ write_relcache_init_file(void)
char tempfilename[MAXPGPATH]; char tempfilename[MAXPGPATH];
char finalfilename[MAXPGPATH]; char finalfilename[MAXPGPATH];
HASH_SEQ_STATUS status; HASH_SEQ_STATUS status;
RelNameCacheEnt *namehentry; RelIdCacheEnt *idhentry;
MemoryContext oldcxt; MemoryContext oldcxt;
int i; int i;
...@@ -3031,13 +3025,13 @@ write_relcache_init_file(void) ...@@ -3031,13 +3025,13 @@ write_relcache_init_file(void)
/* /*
* Write all the reldescs (in no particular order). * Write all the reldescs (in no particular order).
*/ */
hash_seq_init(&status, RelationNameCache); hash_seq_init(&status, RelationIdCache);
initFileRelationIds = NIL; initFileRelationIds = NIL;
while ((namehentry = (RelNameCacheEnt *) hash_seq_search(&status)) != NULL) while ((idhentry = (RelIdCacheEnt *) hash_seq_search(&status)) != NULL)
{ {
Relation rel = namehentry->reldesc; Relation rel = idhentry->reldesc;
Form_pg_class relform = rel->rd_rel; Form_pg_class relform = rel->rd_rel;
Size len; Size len;
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/utils/cache/syscache.c,v 1.69 2002/03/22 21:34:44 tgl Exp $ * $Header: /cvsroot/pgsql/src/backend/utils/cache/syscache.c,v 1.70 2002/03/26 19:16:14 tgl Exp $
* *
* NOTES * NOTES
* These routines allow the parser/planner/executor to perform * These routines allow the parser/planner/executor to perform
...@@ -86,14 +86,14 @@ ...@@ -86,14 +86,14 @@
*/ */
struct cachedesc struct cachedesc
{ {
char *name; /* name of the relation being cached */ const char *name; /* name of the relation being cached */
char *indname; /* name of index relation for this cache */ const char *indname; /* name of index relation for this cache */
int reloidattr; /* attr number of rel OID reference, or 0 */ int reloidattr; /* attr number of rel OID reference, or 0 */
int nkeys; /* # of keys needed for cache lookup */ int nkeys; /* # of keys needed for cache lookup */
int key[4]; /* attribute numbers of key attrs */ int key[4]; /* attribute numbers of key attrs */
}; };
static struct cachedesc cacheinfo[] = { static const struct cachedesc cacheinfo[] = {
{AggregateRelationName, /* AGGNAME */ {AggregateRelationName, /* AGGNAME */
AggregateNameTypeIndex, AggregateNameTypeIndex,
0, 0,
...@@ -324,13 +324,13 @@ static struct cachedesc cacheinfo[] = { ...@@ -324,13 +324,13 @@ static struct cachedesc cacheinfo[] = {
0, 0,
0 0
}}, }},
{RelationRelationName, /* RELNAME */ {RelationRelationName, /* RELNAMENSP */
ClassNameIndex, ClassNameNspIndex,
ObjectIdAttributeNumber, ObjectIdAttributeNumber,
1, 2,
{ {
Anum_pg_class_relname, Anum_pg_class_relname,
0, Anum_pg_class_relnamespace,
0, 0,
0 0
}}, }},
...@@ -515,7 +515,7 @@ SearchSysCache(int cacheId, ...@@ -515,7 +515,7 @@ SearchSysCache(int cacheId,
* when sought. This is a kluge ... temp table substitution should be * when sought. This is a kluge ... temp table substitution should be
* happening at a higher level ... * happening at a higher level ...
*/ */
if (cacheId == RELNAME || cacheId == TYPENAME) if (cacheId == RELNAMENSP || cacheId == TYPENAME)
{ {
char *nontemp_relname; char *nontemp_relname;
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: genam.h,v 1.32 2002/02/19 20:11:19 tgl Exp $ * $Id: genam.h,v 1.33 2002/03/26 19:16:17 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -17,6 +17,7 @@ ...@@ -17,6 +17,7 @@
#include "access/itup.h" #include "access/itup.h"
#include "access/relscan.h" #include "access/relscan.h"
#include "access/sdir.h" #include "access/sdir.h"
#include "nodes/primnodes.h"
/* Struct for statistics returned by bulk-delete operation */ /* Struct for statistics returned by bulk-delete operation */
...@@ -50,7 +51,8 @@ typedef SysScanDescData *SysScanDesc; ...@@ -50,7 +51,8 @@ typedef SysScanDescData *SysScanDesc;
* generalized index_ interface routines (in indexam.c) * generalized index_ interface routines (in indexam.c)
*/ */
extern Relation index_open(Oid relationId); extern Relation index_open(Oid relationId);
extern Relation index_openr(const char *relationName); extern Relation index_openrv(const RangeVar *relation);
extern Relation index_openr(const char *sysRelationName);
extern void index_close(Relation relation); extern void index_close(Relation relation);
extern InsertIndexResult index_insert(Relation relation, extern InsertIndexResult index_insert(Relation relation,
Datum *datum, char *nulls, Datum *datum, char *nulls,
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: heapam.h,v 1.72 2001/11/05 17:46:31 momjian Exp $ * $Id: heapam.h,v 1.73 2002/03/26 19:16:17 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -18,6 +18,7 @@ ...@@ -18,6 +18,7 @@
#include "access/relscan.h" #include "access/relscan.h"
#include "access/tupmacs.h" #include "access/tupmacs.h"
#include "access/xlogutils.h" #include "access/xlogutils.h"
#include "nodes/primnodes.h"
#include "storage/block.h" #include "storage/block.h"
#include "storage/lmgr.h" #include "storage/lmgr.h"
#include "utils/rel.h" #include "utils/rel.h"
...@@ -134,11 +135,13 @@ extern Datum heap_getsysattr(HeapTuple tup, int attnum, bool *isnull); ...@@ -134,11 +135,13 @@ extern Datum heap_getsysattr(HeapTuple tup, int attnum, bool *isnull);
/* heapam.c */ /* heapam.c */
extern Relation relation_open(Oid relationId, LOCKMODE lockmode); extern Relation relation_open(Oid relationId, LOCKMODE lockmode);
extern Relation relation_openr(const char *relationName, LOCKMODE lockmode); extern Relation relation_openrv(const RangeVar *relation, LOCKMODE lockmode);
extern Relation relation_openr(const char *sysRelationName, LOCKMODE lockmode);
extern void relation_close(Relation relation, LOCKMODE lockmode); extern void relation_close(Relation relation, LOCKMODE lockmode);
extern Relation heap_open(Oid relationId, LOCKMODE lockmode); extern Relation heap_open(Oid relationId, LOCKMODE lockmode);
extern Relation heap_openr(const char *relationName, LOCKMODE lockmode); extern Relation heap_openrv(const RangeVar *relation, LOCKMODE lockmode);
extern Relation heap_openr(const char *sysRelationName, LOCKMODE lockmode);
#define heap_close(r,l) relation_close(r,l) #define heap_close(r,l) relation_close(r,l)
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: bootstrap.h,v 1.27 2002/03/02 21:39:34 momjian Exp $ * $Id: bootstrap.h,v 1.28 2002/03/26 19:16:20 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -36,7 +36,7 @@ extern Form_pg_attribute attrtypes[MAXATTR]; ...@@ -36,7 +36,7 @@ extern Form_pg_attribute attrtypes[MAXATTR];
extern int numattr; extern int numattr;
extern int BootstrapMain(int ac, char *av[]); extern int BootstrapMain(int ac, char *av[]);
extern void index_register(char *heap, char *ind, IndexInfo *indexInfo); extern void index_register(Oid heap, Oid ind, IndexInfo *indexInfo);
extern void err_out(void); extern void err_out(void);
extern void InsertOneTuple(Oid objectid); extern void InsertOneTuple(Oid objectid);
......
...@@ -37,7 +37,7 @@ ...@@ -37,7 +37,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: catversion.h,v 1.110 2002/03/22 21:34:44 tgl Exp $ * $Id: catversion.h,v 1.111 2002/03/26 19:16:22 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -53,6 +53,6 @@ ...@@ -53,6 +53,6 @@
*/ */
/* yyyymmddN */ /* yyyymmddN */
#define CATALOG_VERSION_NO 200203221 #define CATALOG_VERSION_NO 200203251
#endif #endif
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: heap.h,v 1.46 2002/03/20 19:44:52 tgl Exp $ * $Id: heap.h,v 1.47 2002/03/26 19:16:23 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -19,6 +19,7 @@ ...@@ -19,6 +19,7 @@
#include "parser/parse_node.h" #include "parser/parse_node.h"
#include "utils/rel.h" #include "utils/rel.h"
typedef struct RawColumnDefault typedef struct RawColumnDefault
{ {
AttrNumber attnum; /* attribute to attach default to */ AttrNumber attnum; /* attribute to attach default to */
...@@ -26,15 +27,15 @@ typedef struct RawColumnDefault ...@@ -26,15 +27,15 @@ typedef struct RawColumnDefault
* tree) */ * tree) */
} RawColumnDefault; } RawColumnDefault;
extern Oid RelnameFindRelid(const char *relname); extern Relation heap_create(char *relname, Oid relnamespace,
TupleDesc tupDesc,
extern Relation heap_create(char *relname, TupleDesc tupDesc,
bool istemp, bool storage_create, bool istemp, bool storage_create,
bool allow_system_table_mods); bool allow_system_table_mods);
extern void heap_storage_create(Relation rel); extern void heap_storage_create(Relation rel);
extern Oid heap_create_with_catalog(char *relname, TupleDesc tupdesc, extern Oid heap_create_with_catalog(char *relname, Oid relnamespace,
TupleDesc tupdesc,
char relkind, bool relhasoids, bool istemp, char relkind, bool relhasoids, bool istemp,
bool allow_system_table_mods); bool allow_system_table_mods);
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: index.h,v 1.45 2002/03/10 06:02:24 momjian Exp $ * $Id: index.h,v 1.46 2002/03/26 19:16:25 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -29,11 +29,12 @@ typedef void (*IndexBuildCallback) (Relation index, ...@@ -29,11 +29,12 @@ typedef void (*IndexBuildCallback) (Relation index,
void *state); void *state);
extern Oid index_create(char *heapRelationName, extern Oid index_create(Oid heapRelationId,
char *indexRelationName, char *indexRelationName,
IndexInfo *indexInfo, IndexInfo *indexInfo,
Oid accessMethodObjectId, Oid accessMethodObjectId,
Oid *classObjectId, Oid *classObjectId,
bool istemp,
bool primary, bool primary,
bool allow_system_table_mods); bool allow_system_table_mods);
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: indexing.h,v 1.58 2002/03/22 21:34:44 tgl Exp $ * $Id: indexing.h,v 1.59 2002/03/26 19:16:26 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -58,7 +58,7 @@ ...@@ -58,7 +58,7 @@
#define AttrDefaultIndex "pg_attrdef_adrelid_adnum_index" #define AttrDefaultIndex "pg_attrdef_adrelid_adnum_index"
#define AttributeRelidNameIndex "pg_attribute_relid_attnam_index" #define AttributeRelidNameIndex "pg_attribute_relid_attnam_index"
#define AttributeRelidNumIndex "pg_attribute_relid_attnum_index" #define AttributeRelidNumIndex "pg_attribute_relid_attnum_index"
#define ClassNameIndex "pg_class_relname_index" #define ClassNameNspIndex "pg_class_relname_nsp_index"
#define ClassOidIndex "pg_class_oid_index" #define ClassOidIndex "pg_class_oid_index"
#define DatabaseNameIndex "pg_database_datname_index" #define DatabaseNameIndex "pg_database_datname_index"
#define DatabaseOidIndex "pg_database_oid_index" #define DatabaseOidIndex "pg_database_oid_index"
...@@ -156,7 +156,7 @@ DECLARE_UNIQUE_INDEX(pg_attrdef_adrelid_adnum_index on pg_attrdef using btree(ad ...@@ -156,7 +156,7 @@ DECLARE_UNIQUE_INDEX(pg_attrdef_adrelid_adnum_index on pg_attrdef using btree(ad
DECLARE_UNIQUE_INDEX(pg_attribute_relid_attnam_index on pg_attribute using btree(attrelid oid_ops, attname name_ops)); DECLARE_UNIQUE_INDEX(pg_attribute_relid_attnam_index on pg_attribute using btree(attrelid oid_ops, attname name_ops));
DECLARE_UNIQUE_INDEX(pg_attribute_relid_attnum_index on pg_attribute using btree(attrelid oid_ops, attnum int2_ops)); DECLARE_UNIQUE_INDEX(pg_attribute_relid_attnum_index on pg_attribute using btree(attrelid oid_ops, attnum int2_ops));
DECLARE_UNIQUE_INDEX(pg_class_oid_index on pg_class using btree(oid oid_ops)); DECLARE_UNIQUE_INDEX(pg_class_oid_index on pg_class using btree(oid oid_ops));
DECLARE_UNIQUE_INDEX(pg_class_relname_index on pg_class using btree(relname name_ops)); DECLARE_UNIQUE_INDEX(pg_class_relname_nsp_index on pg_class using btree(relname name_ops, relnamespace oid_ops));
DECLARE_UNIQUE_INDEX(pg_database_datname_index on pg_database using btree(datname name_ops)); DECLARE_UNIQUE_INDEX(pg_database_datname_index on pg_database using btree(datname name_ops));
DECLARE_UNIQUE_INDEX(pg_database_oid_index on pg_database using btree(oid oid_ops)); DECLARE_UNIQUE_INDEX(pg_database_oid_index on pg_database using btree(oid oid_ops));
DECLARE_UNIQUE_INDEX(pg_description_o_c_o_index on pg_description using btree(objoid oid_ops, classoid oid_ops, objsubid int4_ops)); DECLARE_UNIQUE_INDEX(pg_description_o_c_o_index on pg_description using btree(objoid oid_ops, classoid oid_ops, objsubid int4_ops));
......
/*-------------------------------------------------------------------------
*
* namespace.h
* prototypes for functions in backend/catalog/namespace.c
*
*
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California
*
* $Id: namespace.h,v 1.1 2002/03/26 19:16:28 tgl Exp $
*
*-------------------------------------------------------------------------
*/
#ifndef NAMESPACE_H
#define NAMESPACE_H
#include "nodes/primnodes.h"
extern Oid RangeVarGetRelid(const RangeVar *relation, bool failOK);
extern Oid RangeVarGetCreationNamespace(const RangeVar *newRelation);
extern Oid RelnameGetRelid(const char *relname);
#endif /* NAMESPACE_H */
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: pg_attribute.h,v 1.85 2002/03/20 19:44:55 tgl Exp $ * $Id: pg_attribute.h,v 1.86 2002/03/26 19:16:29 tgl Exp $
* *
* NOTES * NOTES
* the genbki.sh script reads this file and generates .bki * the genbki.sh script reads this file and generates .bki
...@@ -437,52 +437,54 @@ DATA(insert ( 1249 tableoid 26 0 4 -7 0 -1 -1 t p f i f f)); ...@@ -437,52 +437,54 @@ DATA(insert ( 1249 tableoid 26 0 4 -7 0 -1 -1 t p f i f f));
*/ */
#define Schema_pg_class \ #define Schema_pg_class \
{ 1259, {"relname"}, 19, DEFAULT_ATTSTATTARGET, NAMEDATALEN, 1, 0, -1, -1, false, 'p', false, 'i', false, false }, \ { 1259, {"relname"}, 19, DEFAULT_ATTSTATTARGET, NAMEDATALEN, 1, 0, -1, -1, false, 'p', false, 'i', false, false }, \
{ 1259, {"reltype"}, 26, 0, 4, 2, 0, -1, -1, true, 'p', false, 'i', false, false }, \ { 1259, {"relnamespace"}, 26, 0, 4, 2, 0, -1, -1, true, 'p', false, 'i', false, false }, \
{ 1259, {"relowner"}, 23, 0, 4, 3, 0, -1, -1, true, 'p', false, 'i', false, false }, \ { 1259, {"reltype"}, 26, 0, 4, 3, 0, -1, -1, true, 'p', false, 'i', false, false }, \
{ 1259, {"relam"}, 26, 0, 4, 4, 0, -1, -1, true, 'p', false, 'i', false, false }, \ { 1259, {"relowner"}, 23, 0, 4, 4, 0, -1, -1, true, 'p', false, 'i', false, false }, \
{ 1259, {"relfilenode"}, 26, 0, 4, 5, 0, -1, -1, true, 'p', false, 'i', false, false }, \ { 1259, {"relam"}, 26, 0, 4, 5, 0, -1, -1, true, 'p', false, 'i', false, false }, \
{ 1259, {"relpages"}, 23, 0, 4, 6, 0, -1, -1, true, 'p', false, 'i', false, false }, \ { 1259, {"relfilenode"}, 26, 0, 4, 6, 0, -1, -1, true, 'p', false, 'i', false, false }, \
{ 1259, {"reltuples"}, 700, 0, 4, 7, 0, -1, -1, false, 'p', false, 'i', false, false }, \ { 1259, {"relpages"}, 23, 0, 4, 7, 0, -1, -1, true, 'p', false, 'i', false, false }, \
{ 1259, {"reltoastrelid"}, 26, 0, 4, 8, 0, -1, -1, true, 'p', false, 'i', false, false }, \ { 1259, {"reltuples"}, 700, 0, 4, 8, 0, -1, -1, false, 'p', false, 'i', false, false }, \
{ 1259, {"reltoastidxid"}, 26, 0, 4, 9, 0, -1, -1, true, 'p', false, 'i', false, false }, \ { 1259, {"reltoastrelid"}, 26, 0, 4, 9, 0, -1, -1, true, 'p', false, 'i', false, false }, \
{ 1259, {"relhasindex"}, 16, 0, 1, 10, 0, -1, -1, true, 'p', false, 'c', false, false }, \ { 1259, {"reltoastidxid"}, 26, 0, 4, 10, 0, -1, -1, true, 'p', false, 'i', false, false }, \
{ 1259, {"relisshared"}, 16, 0, 1, 11, 0, -1, -1, true, 'p', false, 'c', false, false }, \ { 1259, {"relhasindex"}, 16, 0, 1, 11, 0, -1, -1, true, 'p', false, 'c', false, false }, \
{ 1259, {"relkind"}, 18, 0, 1, 12, 0, -1, -1, true, 'p', false, 'c', false, false }, \ { 1259, {"relisshared"}, 16, 0, 1, 12, 0, -1, -1, true, 'p', false, 'c', false, false }, \
{ 1259, {"relnatts"}, 21, 0, 2, 13, 0, -1, -1, true, 'p', false, 's', false, false }, \ { 1259, {"relkind"}, 18, 0, 1, 13, 0, -1, -1, true, 'p', false, 'c', false, false }, \
{ 1259, {"relchecks"}, 21, 0, 2, 14, 0, -1, -1, true, 'p', false, 's', false, false }, \ { 1259, {"relnatts"}, 21, 0, 2, 14, 0, -1, -1, true, 'p', false, 's', false, false }, \
{ 1259, {"reltriggers"}, 21, 0, 2, 15, 0, -1, -1, true, 'p', false, 's', false, false }, \ { 1259, {"relchecks"}, 21, 0, 2, 15, 0, -1, -1, true, 'p', false, 's', false, false }, \
{ 1259, {"relukeys"}, 21, 0, 2, 16, 0, -1, -1, true, 'p', false, 's', false, false }, \ { 1259, {"reltriggers"}, 21, 0, 2, 16, 0, -1, -1, true, 'p', false, 's', false, false }, \
{ 1259, {"relfkeys"}, 21, 0, 2, 17, 0, -1, -1, true, 'p', false, 's', false, false }, \ { 1259, {"relukeys"}, 21, 0, 2, 17, 0, -1, -1, true, 'p', false, 's', false, false }, \
{ 1259, {"relrefs"}, 21, 0, 2, 18, 0, -1, -1, true, 'p', false, 's', false, false }, \ { 1259, {"relfkeys"}, 21, 0, 2, 18, 0, -1, -1, true, 'p', false, 's', false, false }, \
{ 1259, {"relhasoids"}, 16, 0, 1, 19, 0, -1, -1, true, 'p', false, 'c', false, false }, \ { 1259, {"relrefs"}, 21, 0, 2, 19, 0, -1, -1, true, 'p', false, 's', false, false }, \
{ 1259, {"relhaspkey"}, 16, 0, 1, 20, 0, -1, -1, true, 'p', false, 'c', false, false }, \ { 1259, {"relhasoids"}, 16, 0, 1, 20, 0, -1, -1, true, 'p', false, 'c', false, false }, \
{ 1259, {"relhasrules"}, 16, 0, 1, 21, 0, -1, -1, true, 'p', false, 'c', false, false }, \ { 1259, {"relhaspkey"}, 16, 0, 1, 21, 0, -1, -1, true, 'p', false, 'c', false, false }, \
{ 1259, {"relhassubclass"},16, 0, 1, 22, 0, -1, -1, true, 'p', false, 'c', false, false }, \ { 1259, {"relhasrules"}, 16, 0, 1, 22, 0, -1, -1, true, 'p', false, 'c', false, false }, \
{ 1259, {"relacl"}, 1034, 0, -1, 23, 0, -1, -1, false, 'x', false, 'i', false, false } { 1259, {"relhassubclass"},16, 0, 1, 23, 0, -1, -1, true, 'p', false, 'c', false, false }, \
{ 1259, {"relacl"}, 1034, 0, -1, 24, 0, -1, -1, false, 'x', false, 'i', false, false }
DATA(insert ( 1259 relname 19 DEFAULT_ATTSTATTARGET NAMEDATALEN 1 0 -1 -1 f p f i f f)); DATA(insert ( 1259 relname 19 DEFAULT_ATTSTATTARGET NAMEDATALEN 1 0 -1 -1 f p f i f f));
DATA(insert ( 1259 reltype 26 0 4 2 0 -1 -1 t p f i f f)); DATA(insert ( 1259 relnamespace 26 0 4 2 0 -1 -1 t p f i f f));
DATA(insert ( 1259 relowner 23 0 4 3 0 -1 -1 t p f i f f)); DATA(insert ( 1259 reltype 26 0 4 3 0 -1 -1 t p f i f f));
DATA(insert ( 1259 relam 26 0 4 4 0 -1 -1 t p f i f f)); DATA(insert ( 1259 relowner 23 0 4 4 0 -1 -1 t p f i f f));
DATA(insert ( 1259 relfilenode 26 0 4 5 0 -1 -1 t p f i f f)); DATA(insert ( 1259 relam 26 0 4 5 0 -1 -1 t p f i f f));
DATA(insert ( 1259 relpages 23 0 4 6 0 -1 -1 t p f i f f)); DATA(insert ( 1259 relfilenode 26 0 4 6 0 -1 -1 t p f i f f));
DATA(insert ( 1259 reltuples 700 0 4 7 0 -1 -1 f p f i f f)); DATA(insert ( 1259 relpages 23 0 4 7 0 -1 -1 t p f i f f));
DATA(insert ( 1259 reltoastrelid 26 0 4 8 0 -1 -1 t p f i f f)); DATA(insert ( 1259 reltuples 700 0 4 8 0 -1 -1 f p f i f f));
DATA(insert ( 1259 reltoastidxid 26 0 4 9 0 -1 -1 t p f i f f)); DATA(insert ( 1259 reltoastrelid 26 0 4 9 0 -1 -1 t p f i f f));
DATA(insert ( 1259 relhasindex 16 0 1 10 0 -1 -1 t p f c f f)); DATA(insert ( 1259 reltoastidxid 26 0 4 10 0 -1 -1 t p f i f f));
DATA(insert ( 1259 relisshared 16 0 1 11 0 -1 -1 t p f c f f)); DATA(insert ( 1259 relhasindex 16 0 1 11 0 -1 -1 t p f c f f));
DATA(insert ( 1259 relkind 18 0 1 12 0 -1 -1 t p f c f f)); DATA(insert ( 1259 relisshared 16 0 1 12 0 -1 -1 t p f c f f));
DATA(insert ( 1259 relnatts 21 0 2 13 0 -1 -1 t p f s f f)); DATA(insert ( 1259 relkind 18 0 1 13 0 -1 -1 t p f c f f));
DATA(insert ( 1259 relchecks 21 0 2 14 0 -1 -1 t p f s f f)); DATA(insert ( 1259 relnatts 21 0 2 14 0 -1 -1 t p f s f f));
DATA(insert ( 1259 reltriggers 21 0 2 15 0 -1 -1 t p f s f f)); DATA(insert ( 1259 relchecks 21 0 2 15 0 -1 -1 t p f s f f));
DATA(insert ( 1259 relukeys 21 0 2 16 0 -1 -1 t p f s f f)); DATA(insert ( 1259 reltriggers 21 0 2 16 0 -1 -1 t p f s f f));
DATA(insert ( 1259 relfkeys 21 0 2 17 0 -1 -1 t p f s f f)); DATA(insert ( 1259 relukeys 21 0 2 17 0 -1 -1 t p f s f f));
DATA(insert ( 1259 relrefs 21 0 2 18 0 -1 -1 t p f s f f)); DATA(insert ( 1259 relfkeys 21 0 2 18 0 -1 -1 t p f s f f));
DATA(insert ( 1259 relhasoids 16 0 1 19 0 -1 -1 t p f c f f)); DATA(insert ( 1259 relrefs 21 0 2 19 0 -1 -1 t p f s f f));
DATA(insert ( 1259 relhaspkey 16 0 1 20 0 -1 -1 t p f c f f)); DATA(insert ( 1259 relhasoids 16 0 1 20 0 -1 -1 t p f c f f));
DATA(insert ( 1259 relhasrules 16 0 1 21 0 -1 -1 t p f c f f)); DATA(insert ( 1259 relhaspkey 16 0 1 21 0 -1 -1 t p f c f f));
DATA(insert ( 1259 relhassubclass 16 0 1 22 0 -1 -1 t p f c f f)); DATA(insert ( 1259 relhasrules 16 0 1 22 0 -1 -1 t p f c f f));
DATA(insert ( 1259 relacl 1034 0 -1 23 0 -1 -1 f x f i f f)); DATA(insert ( 1259 relhassubclass 16 0 1 23 0 -1 -1 t p f c f f));
DATA(insert ( 1259 relacl 1034 0 -1 24 0 -1 -1 f x f i f f));
DATA(insert ( 1259 ctid 27 0 6 -1 0 -1 -1 f p f i f f)); DATA(insert ( 1259 ctid 27 0 6 -1 0 -1 -1 f p f i f f));
DATA(insert ( 1259 oid 26 0 4 -2 0 -1 -1 t p f i f f)); DATA(insert ( 1259 oid 26 0 4 -2 0 -1 -1 t p f i f f));
DATA(insert ( 1259 xmin 28 0 4 -3 0 -1 -1 t p f i f f)); DATA(insert ( 1259 xmin 28 0 4 -3 0 -1 -1 t p f i f f));
......
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: pg_class.h,v 1.62 2002/03/19 02:18:22 momjian Exp $ * $Id: pg_class.h,v 1.63 2002/03/26 19:16:35 tgl Exp $
* *
* NOTES * NOTES
* the genbki.sh script reads this file and generates .bki * the genbki.sh script reads this file and generates .bki
...@@ -43,6 +43,7 @@ ...@@ -43,6 +43,7 @@
CATALOG(pg_class) BOOTSTRAP CATALOG(pg_class) BOOTSTRAP
{ {
NameData relname; /* class name */ NameData relname; /* class name */
Oid relnamespace; /* OID of namespace containing this class */
Oid reltype; /* OID of associated entry in pg_type */ Oid reltype; /* OID of associated entry in pg_type */
int4 relowner; /* class owner */ int4 relowner; /* class owner */
Oid relam; /* index access method; 0 if not an index */ Oid relam; /* index access method; 0 if not an index */
...@@ -99,31 +100,32 @@ typedef FormData_pg_class *Form_pg_class; ...@@ -99,31 +100,32 @@ typedef FormData_pg_class *Form_pg_class;
* relacl field. This is a kluge. * relacl field. This is a kluge.
* ---------------- * ----------------
*/ */
#define Natts_pg_class_fixed 22 #define Natts_pg_class_fixed 23
#define Natts_pg_class 23 #define Natts_pg_class 24
#define Anum_pg_class_relname 1 #define Anum_pg_class_relname 1
#define Anum_pg_class_reltype 2 #define Anum_pg_class_relnamespace 2
#define Anum_pg_class_relowner 3 #define Anum_pg_class_reltype 3
#define Anum_pg_class_relam 4 #define Anum_pg_class_relowner 4
#define Anum_pg_class_relfilenode 5 #define Anum_pg_class_relam 5
#define Anum_pg_class_relpages 6 #define Anum_pg_class_relfilenode 6
#define Anum_pg_class_reltuples 7 #define Anum_pg_class_relpages 7
#define Anum_pg_class_reltoastrelid 8 #define Anum_pg_class_reltuples 8
#define Anum_pg_class_reltoastidxid 9 #define Anum_pg_class_reltoastrelid 9
#define Anum_pg_class_relhasindex 10 #define Anum_pg_class_reltoastidxid 10
#define Anum_pg_class_relisshared 11 #define Anum_pg_class_relhasindex 11
#define Anum_pg_class_relkind 12 #define Anum_pg_class_relisshared 12
#define Anum_pg_class_relnatts 13 #define Anum_pg_class_relkind 13
#define Anum_pg_class_relchecks 14 #define Anum_pg_class_relnatts 14
#define Anum_pg_class_reltriggers 15 #define Anum_pg_class_relchecks 15
#define Anum_pg_class_relukeys 16 #define Anum_pg_class_reltriggers 16
#define Anum_pg_class_relfkeys 17 #define Anum_pg_class_relukeys 17
#define Anum_pg_class_relrefs 18 #define Anum_pg_class_relfkeys 18
#define Anum_pg_class_relhasoids 19 #define Anum_pg_class_relrefs 19
#define Anum_pg_class_relhaspkey 20 #define Anum_pg_class_relhasoids 20
#define Anum_pg_class_relhasrules 21 #define Anum_pg_class_relhaspkey 21
#define Anum_pg_class_relhassubclass 22 #define Anum_pg_class_relhasrules 22
#define Anum_pg_class_relacl 23 #define Anum_pg_class_relhassubclass 23
#define Anum_pg_class_relacl 24
/* ---------------- /* ----------------
* initial contents of pg_class * initial contents of pg_class
...@@ -132,21 +134,21 @@ typedef FormData_pg_class *Form_pg_class; ...@@ -132,21 +134,21 @@ typedef FormData_pg_class *Form_pg_class;
* ---------------- * ----------------
*/ */
DATA(insert OID = 1247 ( pg_type 71 PGUID 0 1247 0 0 0 0 f f r 22 0 0 0 0 0 t f f f _null_ )); DATA(insert OID = 1247 ( pg_type PGNSP 71 PGUID 0 1247 0 0 0 0 f f r 22 0 0 0 0 0 t f f f _null_ ));
DESCR(""); DESCR("");
DATA(insert OID = 1249 ( pg_attribute 75 PGUID 0 1249 0 0 0 0 f f r 15 0 0 0 0 0 f f f f _null_ )); DATA(insert OID = 1249 ( pg_attribute PGNSP 75 PGUID 0 1249 0 0 0 0 f f r 15 0 0 0 0 0 f f f f _null_ ));
DESCR(""); DESCR("");
DATA(insert OID = 1255 ( pg_proc 81 PGUID 0 1255 0 0 0 0 f f r 18 0 0 0 0 0 t f f f _null_ )); DATA(insert OID = 1255 ( pg_proc PGNSP 81 PGUID 0 1255 0 0 0 0 f f r 18 0 0 0 0 0 t f f f _null_ ));
DESCR(""); DESCR("");
DATA(insert OID = 1259 ( pg_class 83 PGUID 0 1259 0 0 0 0 f f r 23 0 0 0 0 0 t f f f _null_ )); DATA(insert OID = 1259 ( pg_class PGNSP 83 PGUID 0 1259 0 0 0 0 f f r 24 0 0 0 0 0 t f f f _null_ ));
DESCR(""); DESCR("");
DATA(insert OID = 1260 ( pg_shadow 86 PGUID 0 1260 0 0 0 0 f t r 9 0 0 0 0 0 f f f f _null_ )); DATA(insert OID = 1260 ( pg_shadow PGNSP 86 PGUID 0 1260 0 0 0 0 f t r 9 0 0 0 0 0 f f f f _null_ ));
DESCR(""); DESCR("");
DATA(insert OID = 1261 ( pg_group 87 PGUID 0 1261 0 0 0 0 f t r 3 0 0 0 0 0 f f f f _null_ )); DATA(insert OID = 1261 ( pg_group PGNSP 87 PGUID 0 1261 0 0 0 0 f t r 3 0 0 0 0 0 f f f f _null_ ));
DESCR(""); DESCR("");
DATA(insert OID = 1262 ( pg_database 88 PGUID 0 1262 0 0 0 0 f t r 10 0 0 0 0 0 t f f f _null_ )); DATA(insert OID = 1262 ( pg_database PGNSP 88 PGUID 0 1262 0 0 0 0 f t r 10 0 0 0 0 0 t f f f _null_ ));
DESCR(""); DESCR("");
DATA(insert OID = 376 ( pg_xactlock 0 PGUID 0 0 0 0 0 0 f t s 1 0 0 0 0 0 f f f f _null_ )); DATA(insert OID = 376 ( pg_xactlock PGNSP 0 PGUID 0 0 0 0 0 0 f t s 1 0 0 0 0 0 f f f f _null_ ));
DESCR(""); DESCR("");
#define RelOid_pg_type 1247 #define RelOid_pg_type 1247
......
...@@ -6,7 +6,7 @@ ...@@ -6,7 +6,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994-5, Regents of the University of California * Portions Copyright (c) 1994-5, Regents of the University of California
* *
* $Id: cluster.h,v 1.12 2001/11/05 17:46:33 momjian Exp $ * $Id: cluster.h,v 1.13 2002/03/26 19:16:40 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -23,6 +23,6 @@ ...@@ -23,6 +23,6 @@
/* /*
* functions * functions
*/ */
extern void cluster(char *oldrelname, char *oldindexname); extern void cluster(RangeVar *oldrelation, char *oldindexname);
#endif /* CLUSTER_H */ #endif /* CLUSTER_H */
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: command.h,v 1.34 2002/03/21 16:01:41 tgl Exp $ * $Id: command.h,v 1.35 2002/03/26 19:16:40 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -62,10 +62,9 @@ extern void AlterTableDropConstraint(const char *relationName, ...@@ -62,10 +62,9 @@ extern void AlterTableDropConstraint(const char *relationName,
bool inh, const char *constrName, bool inh, const char *constrName,
int behavior); int behavior);
extern void AlterTableCreateToastTable(const char *relationName, extern void AlterTableCreateToastTable(Oid relOid, bool silent);
bool silent);
extern void AlterTableOwner(const char *relationName, const char *newOwnerName); extern void AlterTableOwner(const RangeVar *tgtrel, const char *newOwnerName);
/* /*
* LOCK * LOCK
......
...@@ -25,8 +25,8 @@ ...@@ -25,8 +25,8 @@
*------------------------------------------------------------------ *------------------------------------------------------------------
*/ */
extern void CommentObject(int objtype, char *objname, char *objproperty, extern void CommentObject(int objtype, char * schemaname, char *objname,
List *objlist, char *comment); char *objproperty, List *objlist, char *comment);
extern void DeleteComments(Oid oid, Oid classoid); extern void DeleteComments(Oid oid, Oid classoid);
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: defrem.h,v 1.31 2002/03/19 02:18:23 momjian Exp $ * $Id: defrem.h,v 1.32 2002/03/26 19:16:47 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -19,7 +19,7 @@ ...@@ -19,7 +19,7 @@
/* /*
* prototypes in indexcmds.c * prototypes in indexcmds.c
*/ */
extern void DefineIndex(char *heapRelationName, extern void DefineIndex(RangeVar *heapRelation,
char *indexRelationName, char *indexRelationName,
char *accessMethodName, char *accessMethodName,
List *attributeList, List *attributeList,
...@@ -27,9 +27,9 @@ extern void DefineIndex(char *heapRelationName, ...@@ -27,9 +27,9 @@ extern void DefineIndex(char *heapRelationName,
bool primary, bool primary,
Expr *predicate, Expr *predicate,
List *rangetable); List *rangetable);
extern void RemoveIndex(char *name); extern void RemoveIndex(RangeVar *relation);
extern void ReindexIndex(const char *indexRelationName, bool force); extern void ReindexIndex(RangeVar *indexRelation, bool force);
extern void ReindexTable(const char *relationName, bool force); extern void ReindexTable(RangeVar *relation, bool force);
extern void ReindexDatabase(const char *databaseName, bool force, bool all); extern void ReindexDatabase(const char *databaseName, bool force, bool all);
/* /*
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: rename.h,v 1.13 2001/11/05 17:46:33 momjian Exp $ * $Id: rename.h,v 1.14 2002/03/26 19:16:49 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -19,7 +19,7 @@ extern void renameatt(char *relname, ...@@ -19,7 +19,7 @@ extern void renameatt(char *relname,
char *newattname, char *newattname,
int recurse); int recurse);
extern void renamerel(const char *oldrelname, extern void renamerel(const RangeVar *relation,
const char *newrelname); const char *newrelname);
#endif /* RENAME_H */ #endif /* RENAME_H */
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: parsenodes.h,v 1.164 2002/03/22 02:56:36 tgl Exp $ * $Id: parsenodes.h,v 1.165 2002/03/26 19:16:53 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -17,14 +17,6 @@ ...@@ -17,14 +17,6 @@
#include "nodes/primnodes.h" #include "nodes/primnodes.h"
typedef enum InhOption
{
INH_NO, /* Do NOT scan child tables */
INH_YES, /* DO scan child tables */
INH_DEFAULT /* Use current SQL_inheritance option */
} InhOption;
/***************************************************************************** /*****************************************************************************
* Query Tree * Query Tree
*****************************************************************************/ *****************************************************************************/
...@@ -49,7 +41,7 @@ typedef struct Query ...@@ -49,7 +41,7 @@ typedef struct Query
* statement */ * statement */
int resultRelation; /* target relation (index into rtable) */ int resultRelation; /* target relation (index into rtable) */
struct RangeVar *into; /* target relation or portal (cursor) RangeVar *into; /* target relation or portal (cursor)
* for portal just name is meaningful */ * for portal just name is meaningful */
bool isPortal; /* is this a retrieve into portal? */ bool isPortal; /* is this a retrieve into portal? */
bool isBinary; /* binary portal? */ bool isBinary; /* binary portal? */
...@@ -368,39 +360,6 @@ typedef struct SortGroupBy ...@@ -368,39 +360,6 @@ typedef struct SortGroupBy
Node *node; /* Expression */ Node *node; /* Expression */
} SortGroupBy; } SortGroupBy;
/*
* Alias -
* specifies an alias for a range variable; the alias might also
* specify renaming of columns within the table.
*/
typedef struct Alias
{
NodeTag type;
char *aliasname; /* aliased rel name (never qualified) */
List *colnames; /* optional list of column aliases */
/* Note: colnames is a list of Value nodes (always strings) */
} Alias;
/*
* RangeVar - range variable, used in FROM clauses
*
* Also used to represent table names in utility statements; there, the alias
* field is not used, and inhOpt shows whether to apply the operation
* recursively to child tables. In some contexts it is also useful to carry
* a TEMP table indication here.
*/
typedef struct RangeVar
{
NodeTag type;
char *catalogname; /* the catalog (database) name, or NULL */
char *schemaname; /* the schema name, or NULL */
char *relname; /* the relation/sequence name */
InhOption inhOpt; /* expand rel by inheritance?
* recursively act on children? */
bool istemp; /* is this a temp relation/sequence? */
Alias *alias; /* table alias & optional column aliases */
} RangeVar;
/* /*
* RangeSubselect - subquery appearing in a FROM clause * RangeSubselect - subquery appearing in a FROM clause
*/ */
......
...@@ -10,7 +10,7 @@ ...@@ -10,7 +10,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: primnodes.h,v 1.59 2002/03/21 16:01:48 tgl Exp $ * $Id: primnodes.h,v 1.60 2002/03/26 19:16:53 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -93,6 +93,47 @@ typedef struct Fjoin ...@@ -93,6 +93,47 @@ typedef struct Fjoin
} Fjoin; } Fjoin;
/*
* Alias -
* specifies an alias for a range variable; the alias might also
* specify renaming of columns within the table.
*/
typedef struct Alias
{
NodeTag type;
char *aliasname; /* aliased rel name (never qualified) */
List *colnames; /* optional list of column aliases */
/* Note: colnames is a list of Value nodes (always strings) */
} Alias;
typedef enum InhOption
{
INH_NO, /* Do NOT scan child tables */
INH_YES, /* DO scan child tables */
INH_DEFAULT /* Use current SQL_inheritance option */
} InhOption;
/*
* RangeVar - range variable, used in FROM clauses
*
* Also used to represent table names in utility statements; there, the alias
* field is not used, and inhOpt shows whether to apply the operation
* recursively to child tables. In some contexts it is also useful to carry
* a TEMP table indication here.
*/
typedef struct RangeVar
{
NodeTag type;
char *catalogname; /* the catalog (database) name, or NULL */
char *schemaname; /* the schema name, or NULL */
char *relname; /* the relation/sequence name */
InhOption inhOpt; /* expand rel by inheritance?
* recursively act on children? */
bool istemp; /* is this a temp relation/sequence? */
Alias *alias; /* table alias & optional column aliases */
} RangeVar;
/* ---------------------------------------------------------------- /* ----------------------------------------------------------------
* node types for executable expressions * node types for executable expressions
* ---------------------------------------------------------------- * ----------------------------------------------------------------
...@@ -527,7 +568,7 @@ typedef struct JoinExpr ...@@ -527,7 +568,7 @@ typedef struct JoinExpr
Node *rarg; /* right subtree */ Node *rarg; /* right subtree */
List *using; /* USING clause, if any (list of String) */ List *using; /* USING clause, if any (list of String) */
Node *quals; /* qualifiers on join, if any */ Node *quals; /* qualifiers on join, if any */
struct Alias *alias; /* user-written alias clause, if any */ Alias *alias; /* user-written alias clause, if any */
int rtindex; /* RT index assigned for join */ int rtindex; /* RT index assigned for join */
} JoinExpr; } JoinExpr;
......
...@@ -13,7 +13,7 @@ ...@@ -13,7 +13,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: catcache.h,v 1.40 2002/03/06 20:49:46 momjian Exp $ * $Id: catcache.h,v 1.41 2002/03/26 19:16:56 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -33,8 +33,8 @@ typedef struct catcache ...@@ -33,8 +33,8 @@ typedef struct catcache
{ {
int id; /* cache identifier --- see syscache.h */ int id; /* cache identifier --- see syscache.h */
struct catcache *cc_next; /* link to next catcache */ struct catcache *cc_next; /* link to next catcache */
char *cc_relname; /* name of relation the tuples come from */ const char *cc_relname; /* name of relation the tuples come from */
char *cc_indname; /* name of index matching cache keys */ const char *cc_indname; /* name of index matching cache keys */
Oid cc_reloid; /* OID of relation the tuples come from */ Oid cc_reloid; /* OID of relation the tuples come from */
bool cc_relisshared; /* is relation shared? */ bool cc_relisshared; /* is relation shared? */
TupleDesc cc_tupdesc; /* tuple descriptor (copied from reldesc) */ TupleDesc cc_tupdesc; /* tuple descriptor (copied from reldesc) */
...@@ -107,9 +107,9 @@ extern MemoryContext CacheMemoryContext; ...@@ -107,9 +107,9 @@ extern MemoryContext CacheMemoryContext;
extern void CreateCacheMemoryContext(void); extern void CreateCacheMemoryContext(void);
extern void AtEOXact_CatCache(bool isCommit); extern void AtEOXact_CatCache(bool isCommit);
extern CatCache *InitCatCache(int id, char *relname, char *indname, extern CatCache *InitCatCache(int id, const char *relname, const char *indname,
int reloidattr, int reloidattr,
int nkeys, int *key); int nkeys, const int *key);
extern void InitCatCachePhase2(CatCache *cache); extern void InitCatCachePhase2(CatCache *cache);
extern HeapTuple SearchCatCache(CatCache *cache, extern HeapTuple SearchCatCache(CatCache *cache,
......
...@@ -6,7 +6,7 @@ ...@@ -6,7 +6,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: lsyscache.h,v 1.45 2002/03/22 02:56:37 tgl Exp $ * $Id: lsyscache.h,v 1.46 2002/03/26 19:16:57 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -39,6 +39,7 @@ extern RegProcedure get_oprrest(Oid opno); ...@@ -39,6 +39,7 @@ extern RegProcedure get_oprrest(Oid opno);
extern RegProcedure get_oprjoin(Oid opno); extern RegProcedure get_oprjoin(Oid opno);
extern Oid get_func_rettype(Oid funcid); extern Oid get_func_rettype(Oid funcid);
extern bool func_iscachable(Oid funcid); extern bool func_iscachable(Oid funcid);
extern Oid get_relname_relid(const char *relname, Oid relnamespace);
extern char *get_rel_name(Oid relid); extern char *get_rel_name(Oid relid);
extern Oid get_rel_type_id(Oid relid); extern Oid get_rel_type_id(Oid relid);
extern int16 get_typlen(Oid typid); extern int16 get_typlen(Oid typid);
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: rel.h,v 1.56 2002/02/19 20:11:19 tgl Exp $ * $Id: rel.h,v 1.57 2002/03/26 19:16:58 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -282,6 +282,14 @@ typedef Relation *RelationPtr; ...@@ -282,6 +282,14 @@ typedef Relation *RelationPtr;
RelationGetPhysicalRelationName(relation) \ RelationGetPhysicalRelationName(relation) \
) )
/*
* RelationGetNamespace
*
* Returns the rel's namespace OID.
*/
#define RelationGetNamespace(relation) \
((relation)->rd_rel->relnamespace)
/* added to prevent circular dependency. bjm 1999/11/15 */ /* added to prevent circular dependency. bjm 1999/11/15 */
extern char *get_temp_rel_by_physicalname(const char *relname); extern char *get_temp_rel_by_physicalname(const char *relname);
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: relcache.h,v 1.30 2002/02/19 20:11:20 tgl Exp $ * $Id: relcache.h,v 1.31 2002/03/26 19:16:59 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -20,11 +20,11 @@ ...@@ -20,11 +20,11 @@
* relation lookup routines * relation lookup routines
*/ */
extern Relation RelationIdGetRelation(Oid relationId); extern Relation RelationIdGetRelation(Oid relationId);
extern Relation RelationNameGetRelation(const char *relationName); extern Relation RelationSysNameGetRelation(const char *relationName);
extern Relation RelationNodeCacheGetRelation(RelFileNode rnode);
/* finds an existing cache entry, but won't make a new one */ /* finds an existing cache entry, but won't make a new one */
extern Relation RelationIdCacheGetRelation(Oid relationId); extern Relation RelationIdCacheGetRelation(Oid relationId);
extern Relation RelationNodeCacheGetRelation(RelFileNode rnode);
extern void RelationClose(Relation relation); extern void RelationClose(Relation relation);
...@@ -46,8 +46,10 @@ extern void RelationCacheInitializePhase3(void); ...@@ -46,8 +46,10 @@ extern void RelationCacheInitializePhase3(void);
* Routine to create a relcache entry for an about-to-be-created relation * Routine to create a relcache entry for an about-to-be-created relation
*/ */
extern Relation RelationBuildLocalRelation(const char *relname, extern Relation RelationBuildLocalRelation(const char *relname,
Oid relnamespace,
TupleDesc tupDesc, TupleDesc tupDesc,
Oid relid, Oid dbid, Oid relid, Oid dbid,
RelFileNode rnode,
bool nailit); bool nailit);
/* /*
......
...@@ -9,7 +9,7 @@ ...@@ -9,7 +9,7 @@
* Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group
* Portions Copyright (c) 1994, Regents of the University of California * Portions Copyright (c) 1994, Regents of the University of California
* *
* $Id: syscache.h,v 1.39 2002/03/22 21:34:44 tgl Exp $ * $Id: syscache.h,v 1.40 2002/03/26 19:16:59 tgl Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -51,7 +51,7 @@ ...@@ -51,7 +51,7 @@
#define OPEROID 20 #define OPEROID 20
#define PROCNAME 21 #define PROCNAME 21
#define PROCOID 22 #define PROCOID 22
#define RELNAME 23 #define RELNAMENSP 23
#define RELOID 24 #define RELOID 24
#define RULENAME 25 #define RULENAME 25
#define SHADOWNAME 26 #define SHADOWNAME 26
......
...@@ -3,7 +3,7 @@ ...@@ -3,7 +3,7 @@
* procedural language * procedural language
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/pl/plpgsql/src/pl_comp.c,v 1.38 2002/03/06 06:10:45 momjian Exp $ * $Header: /cvsroot/pgsql/src/pl/plpgsql/src/pl_comp.c,v 1.39 2002/03/26 19:17:02 tgl Exp $
* *
* This software is copyrighted by Jan Wieck - Hamburg. * This software is copyrighted by Jan Wieck - Hamburg.
* *
...@@ -46,6 +46,7 @@ ...@@ -46,6 +46,7 @@
#include "access/heapam.h" #include "access/heapam.h"
#include "catalog/catname.h" #include "catalog/catname.h"
#include "catalog/namespace.h"
#include "catalog/pg_proc.h" #include "catalog/pg_proc.h"
#include "catalog/pg_type.h" #include "catalog/pg_type.h"
#include "catalog/pg_class.h" #include "catalog/pg_class.h"
...@@ -941,6 +942,7 @@ plpgsql_parse_dblwordtype(char *string) ...@@ -941,6 +942,7 @@ plpgsql_parse_dblwordtype(char *string)
char *word2; char *word2;
PLpgSQL_nsitem *nse; PLpgSQL_nsitem *nse;
bool old_nsstate; bool old_nsstate;
Oid classOid;
HeapTuple classtup; HeapTuple classtup;
Form_pg_class classStruct; Form_pg_class classStruct;
HeapTuple attrtup; HeapTuple attrtup;
...@@ -998,8 +1000,14 @@ plpgsql_parse_dblwordtype(char *string) ...@@ -998,8 +1000,14 @@ plpgsql_parse_dblwordtype(char *string)
/* /*
* First word could also be a table name * First word could also be a table name
*/ */
classtup = SearchSysCache(RELNAME, classOid = RelnameGetRelid(word1);
PointerGetDatum(word1), if (!OidIsValid(classOid))
{
pfree(word1);
return T_ERROR;
}
classtup = SearchSysCache(RELOID,
ObjectIdGetDatum(classOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(classtup)) if (!HeapTupleIsValid(classtup))
{ {
...@@ -1024,7 +1032,7 @@ plpgsql_parse_dblwordtype(char *string) ...@@ -1024,7 +1032,7 @@ plpgsql_parse_dblwordtype(char *string)
* Fetch the named table field and it's type * Fetch the named table field and it's type
*/ */
attrtup = SearchSysCache(ATTNAME, attrtup = SearchSysCache(ATTNAME,
ObjectIdGetDatum(classtup->t_data->t_oid), ObjectIdGetDatum(classOid),
PointerGetDatum(word2), PointerGetDatum(word2),
0, 0); 0, 0);
if (!HeapTupleIsValid(attrtup)) if (!HeapTupleIsValid(attrtup))
...@@ -1049,7 +1057,7 @@ plpgsql_parse_dblwordtype(char *string) ...@@ -1049,7 +1057,7 @@ plpgsql_parse_dblwordtype(char *string)
typ = (PLpgSQL_type *) malloc(sizeof(PLpgSQL_type)); typ = (PLpgSQL_type *) malloc(sizeof(PLpgSQL_type));
typ->typname = strdup(NameStr(typeStruct->typname)); typ->typname = strdup(NameStr(typeStruct->typname));
typ->typoid = typetup->t_data->t_oid; typ->typoid = attrStruct->atttypid;
perm_fmgr_info(typeStruct->typinput, &(typ->typinput)); perm_fmgr_info(typeStruct->typinput, &(typ->typinput));
typ->typelem = typeStruct->typelem; typ->typelem = typeStruct->typelem;
typ->typbyval = typeStruct->typbyval; typ->typbyval = typeStruct->typbyval;
...@@ -1074,6 +1082,7 @@ plpgsql_parse_dblwordtype(char *string) ...@@ -1074,6 +1082,7 @@ plpgsql_parse_dblwordtype(char *string)
int int
plpgsql_parse_wordrowtype(char *string) plpgsql_parse_wordrowtype(char *string)
{ {
Oid classOid;
HeapTuple classtup; HeapTuple classtup;
Form_pg_class classStruct; Form_pg_class classStruct;
HeapTuple typetup; HeapTuple typetup;
...@@ -1093,8 +1102,11 @@ plpgsql_parse_wordrowtype(char *string) ...@@ -1093,8 +1102,11 @@ plpgsql_parse_wordrowtype(char *string)
cp = strchr(word1, '%'); cp = strchr(word1, '%');
*cp = '\0'; *cp = '\0';
classtup = SearchSysCache(RELNAME, classOid = RelnameGetRelid(word1);
PointerGetDatum(word1), if (!OidIsValid(classOid))
elog(ERROR, "%s: no such class", word1);
classtup = SearchSysCache(RELOID,
ObjectIdGetDatum(classOid),
0, 0, 0); 0, 0, 0);
if (!HeapTupleIsValid(classtup)) if (!HeapTupleIsValid(classtup))
elog(ERROR, "%s: no such class", word1); elog(ERROR, "%s: no such class", word1);
...@@ -1105,15 +1117,6 @@ plpgsql_parse_wordrowtype(char *string) ...@@ -1105,15 +1117,6 @@ plpgsql_parse_wordrowtype(char *string)
classStruct->relkind != RELKIND_VIEW) classStruct->relkind != RELKIND_VIEW)
elog(ERROR, "%s isn't a table", word1); elog(ERROR, "%s isn't a table", word1);
/*
* Fetch the table's pg_type tuple too
*/
typetup = SearchSysCache(TYPENAME,
PointerGetDatum(word1),
0, 0, 0);
if (!HeapTupleIsValid(typetup))
elog(ERROR, "cache lookup for %s in pg_type failed", word1);
/* /*
* Create a row datum entry and all the required variables that it * Create a row datum entry and all the required variables that it
* will point to. * will point to.
...@@ -1123,19 +1126,17 @@ plpgsql_parse_wordrowtype(char *string) ...@@ -1123,19 +1126,17 @@ plpgsql_parse_wordrowtype(char *string)
row->dtype = PLPGSQL_DTYPE_ROW; row->dtype = PLPGSQL_DTYPE_ROW;
row->nfields = classStruct->relnatts; row->nfields = classStruct->relnatts;
row->rowtypeclass = typetup->t_data->t_oid; row->rowtypeclass = classStruct->reltype;
row->fieldnames = malloc(sizeof(char *) * row->nfields); row->fieldnames = malloc(sizeof(char *) * row->nfields);
row->varnos = malloc(sizeof(int) * row->nfields); row->varnos = malloc(sizeof(int) * row->nfields);
ReleaseSysCache(typetup);
for (i = 0; i < row->nfields; i++) for (i = 0; i < row->nfields; i++)
{ {
/* /*
* Get the attribute and it's type * Get the attribute and it's type
*/ */
attrtup = SearchSysCache(ATTNUM, attrtup = SearchSysCache(ATTNUM,
ObjectIdGetDatum(classtup->t_data->t_oid), ObjectIdGetDatum(classOid),
Int16GetDatum(i + 1), Int16GetDatum(i + 1),
0, 0); 0, 0);
if (!HeapTupleIsValid(attrtup)) if (!HeapTupleIsValid(attrtup))
...@@ -1172,7 +1173,7 @@ plpgsql_parse_wordrowtype(char *string) ...@@ -1172,7 +1173,7 @@ plpgsql_parse_wordrowtype(char *string)
strcat(var->refname, cp); strcat(var->refname, cp);
var->datatype = malloc(sizeof(PLpgSQL_type)); var->datatype = malloc(sizeof(PLpgSQL_type));
var->datatype->typname = strdup(NameStr(typeStruct->typname)); var->datatype->typname = strdup(NameStr(typeStruct->typname));
var->datatype->typoid = typetup->t_data->t_oid; var->datatype->typoid = attrStruct->atttypid;
perm_fmgr_info(typeStruct->typinput, &(var->datatype->typinput)); perm_fmgr_info(typeStruct->typinput, &(var->datatype->typinput));
var->datatype->typelem = typeStruct->typelem; var->datatype->typelem = typeStruct->typelem;
var->datatype->typbyval = typeStruct->typbyval; var->datatype->typbyval = typeStruct->typbyval;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment