mirror of
https://github.com/postgres/postgres.git
synced 2025-07-08 11:42:09 +03:00
Add TEMP tables/indexes. Add COPY pfree(). Other cleanups.
This commit is contained in:
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Id: hio.c,v 1.15 1998/12/15 12:45:14 vadim Exp $
|
||||
* $Id: hio.c,v 1.16 1999/02/02 03:43:57 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -110,7 +110,7 @@ RelationPutHeapTupleAtEnd(Relation relation, HeapTuple tuple)
|
||||
ItemId itemId;
|
||||
Item item;
|
||||
|
||||
if (!relation->rd_islocal)
|
||||
if (!relation->rd_myxactonly)
|
||||
LockRelation(relation, ExtendLock);
|
||||
|
||||
/*
|
||||
@ -158,7 +158,7 @@ RelationPutHeapTupleAtEnd(Relation relation, HeapTuple tuple)
|
||||
elog(ERROR, "Tuple is too big: size %d", len);
|
||||
}
|
||||
|
||||
if (!relation->rd_islocal)
|
||||
if (!relation->rd_myxactonly)
|
||||
UnlockRelation(relation, ExtendLock);
|
||||
|
||||
offnum = PageAddItem((Page) pageHeader, (Item) tuple->t_data,
|
||||
|
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/access/transam/xact.c,v 1.29 1999/01/29 09:22:53 vadim Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/access/transam/xact.c,v 1.30 1999/02/02 03:44:00 momjian Exp $
|
||||
*
|
||||
* NOTES
|
||||
* Transaction aborts can now occur two ways:
|
||||
@ -850,7 +850,7 @@ StartTransaction()
|
||||
are created in the course of the transactions
|
||||
they need to be destroyed properly at the end of the transactions
|
||||
*/
|
||||
InitTempRelList();
|
||||
InitNoNameRelList();
|
||||
|
||||
/* ----------------
|
||||
* done with start processing, set current transaction
|
||||
@ -917,7 +917,7 @@ CommitTransaction()
|
||||
AtCommit_Notify();
|
||||
|
||||
CloseSequences();
|
||||
DestroyTempRels();
|
||||
DestroyNoNameRels();
|
||||
AtEOXact_portals();
|
||||
RecordTransactionCommit();
|
||||
RelationPurgeLocalRelation(true);
|
||||
@ -984,7 +984,7 @@ AbortTransaction()
|
||||
AtEOXact_portals();
|
||||
RecordTransactionAbort();
|
||||
RelationPurgeLocalRelation(false);
|
||||
DestroyTempRels();
|
||||
DestroyNoNameRels();
|
||||
AtAbort_Cache();
|
||||
AtAbort_Locks();
|
||||
AtAbort_Memory();
|
||||
|
@ -8,7 +8,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/bootstrap/bootparse.y,v 1.22 1999/01/21 22:48:04 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/bootstrap/bootparse.y,v 1.23 1999/02/02 03:44:03 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -164,7 +164,8 @@ Boot_CreateStmt:
|
||||
if (DebugMode)
|
||||
puts("creating bootstrap relation");
|
||||
tupdesc = CreateTupleDesc(numattr,attrtypes);
|
||||
reldesc = heap_create(LexIDStr($3), tupdesc);
|
||||
reldesc = heap_create(LexIDStr($3), tupdesc,
|
||||
false, false);
|
||||
if (DebugMode)
|
||||
puts("bootstrap relation created ok");
|
||||
}
|
||||
@ -175,7 +176,7 @@ Boot_CreateStmt:
|
||||
|
||||
tupdesc = CreateTupleDesc(numattr,attrtypes);
|
||||
id = heap_create_with_catalog(LexIDStr($3),
|
||||
tupdesc, RELKIND_RELATION);
|
||||
tupdesc, RELKIND_RELATION, false);
|
||||
if (!Quiet)
|
||||
printf("CREATED relation %s with OID %d\n",
|
||||
LexIDStr($3), id);
|
||||
|
@ -7,7 +7,8 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/catalog/heap.c,v 1.70 1998/12/15 12:45:40 vadim Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/catalog/heap.c,v 1.71 1999/02/02 03:44:08 momjian Exp $
|
||||
*
|
||||
*
|
||||
* INTERFACE ROUTINES
|
||||
* heap_create() - Create an uncataloged heap relation
|
||||
@ -26,6 +27,7 @@
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
#include "postgres.h"
|
||||
#include "miscadmin.h"
|
||||
|
||||
#include "access/heapam.h"
|
||||
#include "catalog/catalog.h"
|
||||
@ -41,7 +43,6 @@
|
||||
#include "catalog/pg_type.h"
|
||||
#include "commands/trigger.h"
|
||||
#include "fmgr.h"
|
||||
#include "miscadmin.h"
|
||||
#include "nodes/plannodes.h"
|
||||
#include "optimizer/tlist.h"
|
||||
#include "parser/parse_expr.h"
|
||||
@ -53,11 +54,13 @@
|
||||
#include "storage/lmgr.h"
|
||||
#include "storage/smgr.h"
|
||||
#include "tcop/tcopprot.h"
|
||||
#include "utils/catcache.h"
|
||||
#include "utils/builtins.h"
|
||||
#include "utils/mcxt.h"
|
||||
#include "utils/relcache.h"
|
||||
#include "utils/syscache.h"
|
||||
#include "utils/tqual.h"
|
||||
#include "utils/temprel.h"
|
||||
|
||||
#ifndef HAVE_MEMMOVE
|
||||
#include <regex/utils.h>
|
||||
@ -65,18 +68,17 @@
|
||||
#include <string.h>
|
||||
#endif
|
||||
|
||||
static void AddPgRelationTuple(Relation pg_class_desc,
|
||||
static void AddNewRelationTuple(Relation pg_class_desc,
|
||||
Relation new_rel_desc, Oid new_rel_oid, unsigned natts,
|
||||
char relkind);
|
||||
static void AddToTempRelList(Relation r);
|
||||
static void DeletePgAttributeTuples(Relation rel);
|
||||
static void DeletePgRelationTuple(Relation rel);
|
||||
static void DeletePgTypeTuple(Relation rel);
|
||||
static int RelationAlreadyExists(Relation pg_class_desc, char *relname);
|
||||
char relkind, char *temp_relname);
|
||||
static void AddToNoNameRelList(Relation r);
|
||||
static void DeleteAttributeTuples(Relation rel);
|
||||
static void DeleteRelationTuple(Relation rel);
|
||||
static void DeleteTypeTuple(Relation rel);
|
||||
static void RelationRemoveIndexes(Relation relation);
|
||||
static void RelationRemoveInheritance(Relation relation);
|
||||
static void RemoveFromTempRelList(Relation r);
|
||||
static void addNewRelationType(char *typeName, Oid new_rel_oid);
|
||||
static void RemoveFromNoNameRelList(Relation r);
|
||||
static void AddNewRelationType(char *typeName, Oid new_rel_oid);
|
||||
static void StoreConstraints(Relation rel);
|
||||
static void RemoveConstraints(Relation rel);
|
||||
|
||||
@ -167,35 +169,34 @@ static TempRelList *tempRels = NULL;
|
||||
*
|
||||
*
|
||||
* if heap_create is called with "" as the name, then heap_create will create
|
||||
* a temporary name "temp_$RELOID" for the relation
|
||||
* a temporary name "pg_noname.$PID.$SEQUENCE" for the relation
|
||||
* ----------------------------------------------------------------
|
||||
*/
|
||||
Relation
|
||||
heap_create(char *name,
|
||||
TupleDesc tupDesc)
|
||||
heap_create(char *relname,
|
||||
TupleDesc tupDesc,
|
||||
bool isnoname,
|
||||
bool istemp)
|
||||
{
|
||||
unsigned i;
|
||||
Oid relid;
|
||||
Relation rel;
|
||||
int len;
|
||||
bool nailme = false;
|
||||
char *relname = name;
|
||||
char tempname[NAMEDATALEN];
|
||||
int isTemp = 0;
|
||||
int natts = tupDesc->natts;
|
||||
|
||||
/* Form_pg_attribute *att = tupDesc->attrs; */
|
||||
|
||||
static unsigned int uniqueId = 0;
|
||||
|
||||
extern GlobalMemory CacheCxt;
|
||||
MemoryContext oldcxt;
|
||||
|
||||
|
||||
/* ----------------
|
||||
* sanity checks
|
||||
* ----------------
|
||||
*/
|
||||
AssertArg(natts > 0);
|
||||
|
||||
if (IsSystemRelationName(relname) && IsNormalProcessingMode())
|
||||
if (relname && IsSystemRelationName(relname) && IsNormalProcessingMode())
|
||||
{
|
||||
elog(ERROR,
|
||||
"Illegal class name: %s -- pg_ is reserved for system catalogs",
|
||||
@ -218,22 +219,22 @@ heap_create(char *name,
|
||||
* descriptor follows.
|
||||
* ----------------
|
||||
*/
|
||||
if (!strcmp(RelationRelationName, relname))
|
||||
if (relname && !strcmp(RelationRelationName, relname))
|
||||
{
|
||||
relid = RelOid_pg_class;
|
||||
nailme = true;
|
||||
}
|
||||
else if (!strcmp(AttributeRelationName, relname))
|
||||
else if (relname && !strcmp(AttributeRelationName, relname))
|
||||
{
|
||||
relid = RelOid_pg_attribute;
|
||||
nailme = true;
|
||||
}
|
||||
else if (!strcmp(ProcedureRelationName, relname))
|
||||
else if (relname && !strcmp(ProcedureRelationName, relname))
|
||||
{
|
||||
relid = RelOid_pg_proc;
|
||||
nailme = true;
|
||||
}
|
||||
else if (!strcmp(TypeRelationName, relname))
|
||||
else if (relname && !strcmp(TypeRelationName, relname))
|
||||
{
|
||||
relid = RelOid_pg_type;
|
||||
nailme = true;
|
||||
@ -241,14 +242,21 @@ heap_create(char *name,
|
||||
else
|
||||
{
|
||||
relid = newoid();
|
||||
}
|
||||
|
||||
if (name[0] == '\0')
|
||||
{
|
||||
snprintf(tempname, NAMEDATALEN, "temp_%d", relid);
|
||||
Assert(strlen(tempname) < NAMEDATALEN);
|
||||
relname = tempname;
|
||||
isTemp = 1;
|
||||
}
|
||||
if (isnoname)
|
||||
{
|
||||
Assert(!relname);
|
||||
relname = palloc(NAMEDATALEN);
|
||||
snprintf(relname, NAMEDATALEN, "pg_noname.%d.%u",
|
||||
(int) MyProcPid, uniqueId++);
|
||||
}
|
||||
|
||||
if (istemp)
|
||||
{
|
||||
/* replace relname of caller */
|
||||
snprintf(relname, NAMEDATALEN, "pg_temp.%d.%u",
|
||||
(int) MyProcPid, uniqueId++);
|
||||
}
|
||||
|
||||
/* ----------------
|
||||
@ -262,16 +270,11 @@ heap_create(char *name,
|
||||
rel = (Relation) palloc(len);
|
||||
MemSet((char *) rel, 0, len);
|
||||
|
||||
/* ----------
|
||||
create a new tuple descriptor from the one passed in
|
||||
/*
|
||||
* create a new tuple descriptor from the one passed in
|
||||
*/
|
||||
rel->rd_att = CreateTupleDescCopyConstr(tupDesc);
|
||||
|
||||
/* ----------------
|
||||
* initialize the fields of our new relation descriptor
|
||||
* ----------------
|
||||
*/
|
||||
|
||||
/* ----------------
|
||||
* nail the reldesc if this is a bootstrap create reln and
|
||||
* we may need it in the cache later on in the bootstrap
|
||||
@ -285,8 +288,11 @@ heap_create(char *name,
|
||||
|
||||
rel->rd_rel = (Form_pg_class) palloc(sizeof *rel->rd_rel);
|
||||
|
||||
MemSet((char *) rel->rd_rel, 0,
|
||||
sizeof *rel->rd_rel);
|
||||
/* ----------------
|
||||
* initialize the fields of our new relation descriptor
|
||||
* ----------------
|
||||
*/
|
||||
MemSet((char *) rel->rd_rel, 0, sizeof *rel->rd_rel);
|
||||
namestrcpy(&(rel->rd_rel->relname), relname);
|
||||
rel->rd_rel->relkind = RELKIND_UNCATALOGED;
|
||||
rel->rd_rel->relnatts = natts;
|
||||
@ -305,31 +311,30 @@ heap_create(char *name,
|
||||
}
|
||||
|
||||
/* ----------------
|
||||
* remember if this is a temp relation
|
||||
* remember if this is a noname relation
|
||||
* ----------------
|
||||
*/
|
||||
|
||||
rel->rd_istemp = isTemp;
|
||||
rel->rd_isnoname = isnoname;
|
||||
|
||||
/* ----------------
|
||||
* have the storage manager create the relation.
|
||||
* ----------------
|
||||
*/
|
||||
|
||||
rel->rd_tmpunlinked = TRUE; /* change once table is created */
|
||||
rel->rd_nonameunlinked = TRUE; /* change once table is created */
|
||||
rel->rd_fd = (File) smgrcreate(DEFAULT_SMGR, rel);
|
||||
rel->rd_tmpunlinked = FALSE;
|
||||
rel->rd_nonameunlinked = FALSE;
|
||||
|
||||
RelationRegisterRelation(rel);
|
||||
|
||||
MemoryContextSwitchTo(oldcxt);
|
||||
|
||||
/*
|
||||
* add all temporary relations to the tempRels list so they can be
|
||||
* add all noname relations to the tempRels list so they can be
|
||||
* properly disposed of at the end of transaction
|
||||
*/
|
||||
if (isTemp)
|
||||
AddToTempRelList(rel);
|
||||
if (isnoname)
|
||||
AddToNoNameRelList(rel);
|
||||
|
||||
return rel;
|
||||
}
|
||||
@ -343,7 +348,7 @@ heap_create(char *name,
|
||||
* 1) CheckAttributeNames() is used to make certain the tuple
|
||||
* descriptor contains a valid set of attribute names
|
||||
*
|
||||
* 2) pg_class is opened and RelationAlreadyExists()
|
||||
* 2) pg_class is opened and RelationFindRelid()
|
||||
* preforms a scan to ensure that no relation with the
|
||||
* same name already exists.
|
||||
*
|
||||
@ -356,7 +361,7 @@ heap_create(char *name,
|
||||
* 5) AddNewAttributeTuples() is called to register the
|
||||
* new relation's schema in pg_attribute.
|
||||
*
|
||||
* 6) AddPgRelationTuple() is called to register the
|
||||
* 6) AddNewRelationTuple() is called to register the
|
||||
* relation itself in the catalogs.
|
||||
*
|
||||
* 7) StoreConstraints is called () - vadim 08/22/97
|
||||
@ -456,71 +461,78 @@ CheckAttributeNames(TupleDesc tupdesc)
|
||||
}
|
||||
|
||||
/* --------------------------------
|
||||
* RelationAlreadyExists
|
||||
* RelnameFindRelid
|
||||
*
|
||||
* this preforms a scan of pg_class to ensure that
|
||||
* no relation with the same name already exists. The caller
|
||||
* has to open pg_class and pass an open descriptor.
|
||||
* no relation with the same name already exists.
|
||||
* --------------------------------
|
||||
*/
|
||||
static int
|
||||
RelationAlreadyExists(Relation pg_class_desc, char *relname)
|
||||
Oid
|
||||
RelnameFindRelid(char *relname)
|
||||
{
|
||||
ScanKeyData key;
|
||||
HeapScanDesc pg_class_scan;
|
||||
HeapTuple tup;
|
||||
HeapTuple tuple;
|
||||
Oid relid;
|
||||
|
||||
/*
|
||||
* If this is not bootstrap (initdb) time, use the catalog index on
|
||||
* pg_class.
|
||||
*/
|
||||
|
||||
if (!IsBootstrapProcessingMode())
|
||||
{
|
||||
tup = SearchSysCacheTuple(RELNAME,
|
||||
tuple = SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(relname),
|
||||
0, 0, 0);
|
||||
if (HeapTupleIsValid(tup))
|
||||
return true;
|
||||
if (HeapTupleIsValid(tuple))
|
||||
relid = tuple->t_data->t_oid;
|
||||
else
|
||||
return false;
|
||||
relid = InvalidOid;
|
||||
}
|
||||
else
|
||||
{
|
||||
Relation pg_class_desc;
|
||||
ScanKeyData key;
|
||||
HeapScanDesc pg_class_scan;
|
||||
|
||||
pg_class_desc = heap_openr(RelationRelationName);
|
||||
|
||||
/* ----------------
|
||||
* 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,
|
||||
(Datum) relname);
|
||||
/* ----------------
|
||||
* 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,
|
||||
(Datum) 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;
|
||||
|
||||
/* ----------------
|
||||
* begin the scan
|
||||
* ----------------
|
||||
*/
|
||||
pg_class_scan = heap_beginscan(pg_class_desc,
|
||||
0,
|
||||
SnapshotNow,
|
||||
1,
|
||||
&key);
|
||||
heap_endscan(pg_class_scan);
|
||||
|
||||
/* ----------------
|
||||
* get a tuple. if the tuple is NULL then it means we
|
||||
* didn't find an existing relation.
|
||||
* ----------------
|
||||
*/
|
||||
tup = heap_getnext(pg_class_scan, 0);
|
||||
|
||||
/* ----------------
|
||||
* end the scan and return existance of relation.
|
||||
* ----------------
|
||||
*/
|
||||
heap_endscan(pg_class_scan);
|
||||
|
||||
return HeapTupleIsValid(tup);
|
||||
heap_close(pg_class_desc);
|
||||
}
|
||||
return relid;
|
||||
}
|
||||
|
||||
/* --------------------------------
|
||||
@ -583,6 +595,7 @@ AddNewAttributeTuples(Oid new_rel_oid,
|
||||
(char *) *dpp);
|
||||
|
||||
heap_insert(rel, tup);
|
||||
|
||||
if (hasindex)
|
||||
CatalogIndexInsert(idescs, Num_pg_attr_indices, rel, tup);
|
||||
|
||||
@ -623,18 +636,19 @@ AddNewAttributeTuples(Oid new_rel_oid,
|
||||
}
|
||||
|
||||
/* --------------------------------
|
||||
* AddPgRelationTuple
|
||||
* AddNewRelationTuple
|
||||
*
|
||||
* this registers the new relation in the catalogs by
|
||||
* adding a tuple to pg_class.
|
||||
* --------------------------------
|
||||
*/
|
||||
static void
|
||||
AddPgRelationTuple(Relation pg_class_desc,
|
||||
AddNewRelationTuple(Relation pg_class_desc,
|
||||
Relation new_rel_desc,
|
||||
Oid new_rel_oid,
|
||||
unsigned natts,
|
||||
char relkind)
|
||||
char relkind,
|
||||
char *temp_relname)
|
||||
{
|
||||
Form_pg_class new_rel_reltup;
|
||||
HeapTuple tup;
|
||||
@ -679,9 +693,11 @@ AddPgRelationTuple(Relation pg_class_desc,
|
||||
|
||||
heap_insert(pg_class_desc, tup);
|
||||
|
||||
if (temp_relname)
|
||||
create_temp_relation(temp_relname, tup);
|
||||
|
||||
if (!isBootstrap)
|
||||
{
|
||||
|
||||
/*
|
||||
* First, open the catalog indices and insert index tuples for the
|
||||
* new relation.
|
||||
@ -690,23 +706,22 @@ AddPgRelationTuple(Relation pg_class_desc,
|
||||
CatalogOpenIndices(Num_pg_class_indices, Name_pg_class_indices, idescs);
|
||||
CatalogIndexInsert(idescs, Num_pg_class_indices, pg_class_desc, tup);
|
||||
CatalogCloseIndices(Num_pg_class_indices, idescs);
|
||||
|
||||
/* now restore processing mode */
|
||||
SetProcessingMode(NormalProcessing);
|
||||
}
|
||||
|
||||
|
||||
pfree(tup);
|
||||
}
|
||||
|
||||
|
||||
/* --------------------------------
|
||||
* addNewRelationType -
|
||||
* AddNewRelationType -
|
||||
*
|
||||
* define a complex type corresponding to the new relation
|
||||
* --------------------------------
|
||||
*/
|
||||
static void
|
||||
addNewRelationType(char *typeName, Oid new_rel_oid)
|
||||
AddNewRelationType(char *typeName, Oid new_rel_oid)
|
||||
{
|
||||
Oid new_type_oid;
|
||||
|
||||
@ -745,38 +760,55 @@ addNewRelationType(char *typeName, Oid new_rel_oid)
|
||||
Oid
|
||||
heap_create_with_catalog(char *relname,
|
||||
TupleDesc tupdesc,
|
||||
char relkind)
|
||||
char relkind,
|
||||
bool istemp)
|
||||
{
|
||||
Relation pg_class_desc;
|
||||
Relation new_rel_desc;
|
||||
Oid new_rel_oid;
|
||||
|
||||
int natts = tupdesc->natts;
|
||||
|
||||
char *temp_relname = NULL;
|
||||
|
||||
/* ----------------
|
||||
* sanity checks
|
||||
* ----------------
|
||||
*/
|
||||
AssertState(IsNormalProcessingMode() || IsBootstrapProcessingMode());
|
||||
Assert(IsNormalProcessingMode() || IsBootstrapProcessingMode());
|
||||
if (natts == 0 || natts > MaxHeapAttributeNumber)
|
||||
elog(ERROR, "amcreate: from 1 to %d attributes must be specified",
|
||||
MaxHeapAttributeNumber);
|
||||
MaxHeapAttributeNumber);
|
||||
|
||||
CheckAttributeNames(tupdesc);
|
||||
|
||||
/* ----------------
|
||||
* open pg_class and see that the relation doesn't
|
||||
* already exist.
|
||||
* ----------------
|
||||
*/
|
||||
pg_class_desc = heap_openr(RelationRelationName);
|
||||
|
||||
if (RelationAlreadyExists(pg_class_desc, relname))
|
||||
{
|
||||
heap_close(pg_class_desc);
|
||||
/* temp tables can mask non-temp tables */
|
||||
if ((!istemp && RelnameFindRelid(relname)) ||
|
||||
(istemp && get_temp_rel_by_name(relname) != NULL))
|
||||
elog(ERROR, "%s relation already exists", relname);
|
||||
}
|
||||
|
||||
/* invalidate cache so non-temp table is masked by temp */
|
||||
if (istemp)
|
||||
{
|
||||
Oid relid = RelnameFindRelid(relname);
|
||||
|
||||
if (relid != InvalidOid)
|
||||
{
|
||||
/*
|
||||
* This is heavy-handed, but appears necessary bjm 1999/02/01
|
||||
* SystemCacheRelationFlushed(relid) is not enough either.
|
||||
*/
|
||||
RelationForgetRelation(relid);
|
||||
ResetSystemCache();
|
||||
}
|
||||
}
|
||||
|
||||
/* save user relation name because heap_create changes it */
|
||||
if (istemp)
|
||||
{
|
||||
temp_relname = pstrdup(relname); /* save original value */
|
||||
relname = palloc(NAMEDATALEN);
|
||||
strcpy(relname, temp_relname); /* heap_create will change this */
|
||||
}
|
||||
|
||||
/* ----------------
|
||||
* ok, relation does not already exist so now we
|
||||
* create an uncataloged relation and pull its relation oid
|
||||
@ -784,9 +816,11 @@ heap_create_with_catalog(char *relname,
|
||||
*
|
||||
* Note: The call to heap_create() does all the "real" work
|
||||
* of creating the disk file for the relation.
|
||||
* This changes relname for noname and temp tables.
|
||||
* ----------------
|
||||
*/
|
||||
new_rel_desc = heap_create(relname, tupdesc);
|
||||
new_rel_desc = heap_create(relname, tupdesc, false, istemp);
|
||||
|
||||
new_rel_oid = new_rel_desc->rd_att->attrs[0]->attrelid;
|
||||
|
||||
/* ----------------
|
||||
@ -794,7 +828,7 @@ heap_create_with_catalog(char *relname,
|
||||
* we add a new system type corresponding to the new relation.
|
||||
* ----------------
|
||||
*/
|
||||
addNewRelationType(relname, new_rel_oid);
|
||||
AddNewRelationType(relname, new_rel_oid);
|
||||
|
||||
/* ----------------
|
||||
* now add tuples to pg_attribute for the attributes in
|
||||
@ -807,14 +841,23 @@ heap_create_with_catalog(char *relname,
|
||||
* now update the information in pg_class.
|
||||
* ----------------
|
||||
*/
|
||||
AddPgRelationTuple(pg_class_desc,
|
||||
pg_class_desc = heap_openr(RelationRelationName);
|
||||
|
||||
AddNewRelationTuple(pg_class_desc,
|
||||
new_rel_desc,
|
||||
new_rel_oid,
|
||||
natts,
|
||||
relkind);
|
||||
relkind,
|
||||
temp_relname);
|
||||
|
||||
StoreConstraints(new_rel_desc);
|
||||
|
||||
if (istemp)
|
||||
{
|
||||
pfree(relname);
|
||||
pfree(temp_relname);
|
||||
}
|
||||
|
||||
/* ----------------
|
||||
* ok, the relation has been cataloged, so close our relations
|
||||
* and return the oid of the newly created relation.
|
||||
@ -990,12 +1033,12 @@ RelationRemoveIndexes(Relation relation)
|
||||
}
|
||||
|
||||
/* --------------------------------
|
||||
* DeletePgRelationTuple
|
||||
* DeleteRelationTuple
|
||||
*
|
||||
* --------------------------------
|
||||
*/
|
||||
static void
|
||||
DeletePgRelationTuple(Relation rel)
|
||||
DeleteRelationTuple(Relation rel)
|
||||
{
|
||||
Relation pg_class_desc;
|
||||
HeapTuple tup;
|
||||
@ -1012,7 +1055,7 @@ DeletePgRelationTuple(Relation rel)
|
||||
if (!HeapTupleIsValid(tup))
|
||||
{
|
||||
heap_close(pg_class_desc);
|
||||
elog(ERROR, "DeletePgRelationTuple: %s relation nonexistent",
|
||||
elog(ERROR, "DeleteRelationTuple: %s relation nonexistent",
|
||||
&rel->rd_rel->relname);
|
||||
}
|
||||
|
||||
@ -1027,12 +1070,12 @@ DeletePgRelationTuple(Relation rel)
|
||||
}
|
||||
|
||||
/* --------------------------------
|
||||
* DeletePgAttributeTuples
|
||||
* DeleteAttributeTuples
|
||||
*
|
||||
* --------------------------------
|
||||
*/
|
||||
static void
|
||||
DeletePgAttributeTuples(Relation rel)
|
||||
DeleteAttributeTuples(Relation rel)
|
||||
{
|
||||
Relation pg_attribute_desc;
|
||||
HeapTuple tup;
|
||||
@ -1073,7 +1116,7 @@ DeletePgAttributeTuples(Relation rel)
|
||||
}
|
||||
|
||||
/* --------------------------------
|
||||
* DeletePgTypeTuple
|
||||
* DeleteTypeTuple
|
||||
*
|
||||
* If the user attempts to destroy a relation and there
|
||||
* exists attributes in other relations of type
|
||||
@ -1082,7 +1125,7 @@ DeletePgAttributeTuples(Relation rel)
|
||||
* --------------------------------
|
||||
*/
|
||||
static void
|
||||
DeletePgTypeTuple(Relation rel)
|
||||
DeleteTypeTuple(Relation rel)
|
||||
{
|
||||
Relation pg_type_desc;
|
||||
HeapScanDesc pg_type_scan;
|
||||
@ -1127,7 +1170,7 @@ DeletePgTypeTuple(Relation rel)
|
||||
{
|
||||
heap_endscan(pg_type_scan);
|
||||
heap_close(pg_type_desc);
|
||||
elog(ERROR, "DeletePgTypeTuple: %s type nonexistent",
|
||||
elog(ERROR, "DeleteTypeTuple: %s type nonexistent",
|
||||
&rel->rd_rel->relname);
|
||||
}
|
||||
|
||||
@ -1171,7 +1214,7 @@ DeletePgTypeTuple(Relation rel)
|
||||
heap_endscan(pg_attribute_scan);
|
||||
heap_close(pg_attribute_desc);
|
||||
|
||||
elog(ERROR, "DeletePgTypeTuple: att of type %s exists in relation %d",
|
||||
elog(ERROR, "DeleteTypeTuple: att of type %s exists in relation %d",
|
||||
&rel->rd_rel->relname, relid);
|
||||
}
|
||||
heap_endscan(pg_attribute_scan);
|
||||
@ -1199,6 +1242,7 @@ heap_destroy_with_catalog(char *relname)
|
||||
{
|
||||
Relation rel;
|
||||
Oid rid;
|
||||
bool istemp = (get_temp_rel_by_name(relname) != NULL);
|
||||
|
||||
/* ----------------
|
||||
* first open the relation. if the relation does exist,
|
||||
@ -1216,7 +1260,8 @@ heap_destroy_with_catalog(char *relname)
|
||||
* prevent deletion of system relations
|
||||
* ----------------
|
||||
*/
|
||||
if (IsSystemRelationName(RelationGetRelationName(rel)->data))
|
||||
/* allow temp of pg_class? Guess so. */
|
||||
if (!istemp && IsSystemRelationName(RelationGetRelationName(rel)->data))
|
||||
elog(ERROR, "amdestroy: cannot destroy %s relation",
|
||||
&rel->rd_rel->relname);
|
||||
|
||||
@ -1248,22 +1293,26 @@ heap_destroy_with_catalog(char *relname)
|
||||
* delete attribute tuples
|
||||
* ----------------
|
||||
*/
|
||||
DeletePgAttributeTuples(rel);
|
||||
DeleteAttributeTuples(rel);
|
||||
|
||||
if (istemp)
|
||||
remove_temp_relation(rid);
|
||||
|
||||
/* ----------------
|
||||
* delete type tuple. here we want to see the effects
|
||||
* of the deletions we just did, so we use setheapoverride().
|
||||
* ----------------
|
||||
*/
|
||||
setheapoverride(true);
|
||||
DeletePgTypeTuple(rel);
|
||||
DeleteTypeTuple(rel);
|
||||
setheapoverride(false);
|
||||
|
||||
/* ----------------
|
||||
* delete relation tuple
|
||||
* ----------------
|
||||
*/
|
||||
DeletePgRelationTuple(rel);
|
||||
/* must delete fake tuple in cache */
|
||||
DeleteRelationTuple(rel);
|
||||
|
||||
/*
|
||||
* release dirty buffers of this relation
|
||||
@ -1283,16 +1332,15 @@ heap_destroy_with_catalog(char *relname)
|
||||
* unlink the relation and finish up.
|
||||
* ----------------
|
||||
*/
|
||||
if (!(rel->rd_istemp) || !(rel->rd_tmpunlinked))
|
||||
if (!(rel->rd_isnoname) || !(rel->rd_nonameunlinked))
|
||||
smgrunlink(DEFAULT_SMGR, rel);
|
||||
|
||||
rel->rd_tmpunlinked = TRUE;
|
||||
rel->rd_nonameunlinked = TRUE;
|
||||
|
||||
UnlockRelation(rel, AccessExclusiveLock);
|
||||
|
||||
heap_close(rel);
|
||||
|
||||
/* ok - flush the relation from the relcache */
|
||||
RelationForgetRelation(rid);
|
||||
}
|
||||
|
||||
@ -1306,11 +1354,11 @@ void
|
||||
heap_destroy(Relation rel)
|
||||
{
|
||||
ReleaseRelationBuffers(rel);
|
||||
if (!(rel->rd_istemp) || !(rel->rd_tmpunlinked))
|
||||
if (!(rel->rd_isnoname) || !(rel->rd_nonameunlinked))
|
||||
smgrunlink(DEFAULT_SMGR, rel);
|
||||
rel->rd_tmpunlinked = TRUE;
|
||||
rel->rd_nonameunlinked = TRUE;
|
||||
heap_close(rel);
|
||||
RemoveFromTempRelList(rel);
|
||||
RemoveFromNoNameRelList(rel);
|
||||
}
|
||||
|
||||
|
||||
@ -1336,7 +1384,7 @@ heap_destroy(Relation rel)
|
||||
|
||||
*/
|
||||
void
|
||||
InitTempRelList(void)
|
||||
InitNoNameRelList(void)
|
||||
{
|
||||
if (tempRels)
|
||||
{
|
||||
@ -1356,10 +1404,10 @@ InitTempRelList(void)
|
||||
|
||||
MODIFIES the global variable tempRels
|
||||
we don't really remove it, just mark it as NULL
|
||||
and DestroyTempRels will look for NULLs
|
||||
and DestroyNoNameRels will look for NULLs
|
||||
*/
|
||||
static void
|
||||
RemoveFromTempRelList(Relation r)
|
||||
RemoveFromNoNameRelList(Relation r)
|
||||
{
|
||||
int i;
|
||||
|
||||
@ -1382,7 +1430,7 @@ RemoveFromTempRelList(Relation r)
|
||||
MODIFIES the global variable tempRels
|
||||
*/
|
||||
static void
|
||||
AddToTempRelList(Relation r)
|
||||
AddToNoNameRelList(Relation r)
|
||||
{
|
||||
if (!tempRels)
|
||||
return;
|
||||
@ -1401,7 +1449,7 @@ AddToTempRelList(Relation r)
|
||||
go through the tempRels list and destroy each of the relations
|
||||
*/
|
||||
void
|
||||
DestroyTempRels(void)
|
||||
DestroyNoNameRels(void)
|
||||
{
|
||||
int i;
|
||||
Relation rel;
|
||||
|
@ -7,19 +7,13 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/catalog/index.c,v 1.67 1999/01/21 22:48:05 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/catalog/index.c,v 1.68 1999/02/02 03:44:13 momjian Exp $
|
||||
*
|
||||
*
|
||||
* INTERFACE ROUTINES
|
||||
* index_create() - Create a cataloged index relation
|
||||
* index_destroy() - Removes index relation from catalogs
|
||||
*
|
||||
* NOTES
|
||||
* Much of this code uses hardcoded sequential heap relation scans
|
||||
* to fetch information from the catalogs. These should all be
|
||||
* rewritten to use the system caches lookup routines like
|
||||
* SearchSysCacheTuple, which can do efficient lookup and
|
||||
* caching.
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -46,10 +40,12 @@
|
||||
#include "storage/lmgr.h"
|
||||
#include "storage/smgr.h"
|
||||
#include "utils/builtins.h"
|
||||
#include "utils/catcache.h"
|
||||
#include "utils/mcxt.h"
|
||||
#include "utils/relcache.h"
|
||||
#include "utils/syscache.h"
|
||||
#include "utils/tqual.h"
|
||||
#include "utils/temprel.h"
|
||||
|
||||
#ifndef HAVE_MEMMOVE
|
||||
#include <regex/utils.h>
|
||||
@ -64,16 +60,15 @@
|
||||
#define NTUPLES_PER_PAGE(natts) (BLCKSZ/((natts)*AVG_TUPLE_SIZE))
|
||||
|
||||
/* non-export function prototypes */
|
||||
static Oid
|
||||
RelationNameGetObjectId(char *relationName, Relation pg_class);
|
||||
static Oid GetHeapRelationOid(char *heapRelationName, char *indexRelationName);
|
||||
static Oid GetHeapRelationOid(char *heapRelationName, char *indexRelationName,
|
||||
bool istemp);
|
||||
static TupleDesc BuildFuncTupleDesc(FuncIndexInfo *funcInfo);
|
||||
static TupleDesc ConstructTupleDescriptor(Oid heapoid, Relation heapRelation,
|
||||
List *attributeList,
|
||||
int numatts, AttrNumber *attNums);
|
||||
|
||||
static void ConstructIndexReldesc(Relation indexRelation, Oid amoid);
|
||||
static Oid UpdateRelationRelation(Relation indexRelation);
|
||||
static Oid UpdateRelationRelation(Relation indexRelation, char *temp_relname);
|
||||
static void InitializeAttributeOids(Relation indexRelation,
|
||||
int numatts,
|
||||
Oid indexoid);
|
||||
@ -121,105 +116,30 @@ static FormData_pg_attribute sysatts[] = {
|
||||
{0, {"cmax"}, CIDOID, 0, 4, -6, 0, -1, -1, '\001', '\0', 'i', '\0', '\0'},
|
||||
};
|
||||
|
||||
/* ----------------------------------------------------------------
|
||||
* RelationNameGetObjectId --
|
||||
* Returns the object identifier for a relation given its name.
|
||||
*
|
||||
* ----------------------------------------------------------------
|
||||
*/
|
||||
static Oid
|
||||
RelationNameGetObjectId(char *relationName,
|
||||
Relation pg_class)
|
||||
{
|
||||
HeapScanDesc pg_class_scan;
|
||||
HeapTuple pg_class_tuple;
|
||||
Oid relationObjectId;
|
||||
ScanKeyData key;
|
||||
|
||||
/*
|
||||
* If this isn't bootstrap time, we can use the system catalogs to
|
||||
* speed this up.
|
||||
*/
|
||||
|
||||
if (!IsBootstrapProcessingMode())
|
||||
{
|
||||
HeapTuple tuple;
|
||||
|
||||
tuple = SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(relationName),
|
||||
0, 0, 0);
|
||||
|
||||
if (HeapTupleIsValid(tuple))
|
||||
return tuple->t_data->t_oid;
|
||||
else
|
||||
return InvalidOid;
|
||||
}
|
||||
|
||||
/* ----------------
|
||||
* BOOTSTRAP TIME, do this the hard way.
|
||||
* begin a scan of pg_class for the named relation
|
||||
* ----------------
|
||||
*/
|
||||
ScanKeyEntryInitialize(&key, 0, Anum_pg_class_relname,
|
||||
F_NAMEEQ,
|
||||
PointerGetDatum(relationName));
|
||||
|
||||
pg_class_scan = heap_beginscan(pg_class, 0, SnapshotNow, 1, &key);
|
||||
|
||||
/* ----------------
|
||||
* if we find the named relation, fetch its relation id
|
||||
* (the oid of the tuple we found).
|
||||
* ----------------
|
||||
*/
|
||||
pg_class_tuple = heap_getnext(pg_class_scan, 0);
|
||||
|
||||
if (!HeapTupleIsValid(pg_class_tuple))
|
||||
relationObjectId = InvalidOid;
|
||||
else
|
||||
relationObjectId = pg_class_tuple->t_data->t_oid;
|
||||
|
||||
/* ----------------
|
||||
* cleanup and return results
|
||||
* ----------------
|
||||
*/
|
||||
heap_endscan(pg_class_scan);
|
||||
|
||||
return relationObjectId;
|
||||
}
|
||||
|
||||
|
||||
/* ----------------------------------------------------------------
|
||||
* GetHeapRelationOid
|
||||
* ----------------------------------------------------------------
|
||||
*/
|
||||
static Oid
|
||||
GetHeapRelationOid(char *heapRelationName, char *indexRelationName)
|
||||
GetHeapRelationOid(char *heapRelationName, char *indexRelationName, bool istemp)
|
||||
{
|
||||
Relation pg_class;
|
||||
Oid indoid;
|
||||
Oid heapoid;
|
||||
|
||||
/* ----------------
|
||||
* open pg_class and get the oid of the relation
|
||||
* corresponding to the name of the index relation.
|
||||
* ----------------
|
||||
*/
|
||||
pg_class = heap_openr(RelationRelationName);
|
||||
|
||||
indoid = RelnameFindRelid(indexRelationName);
|
||||
|
||||
indoid = RelationNameGetObjectId(indexRelationName, pg_class);
|
||||
|
||||
if (OidIsValid(indoid))
|
||||
if ((!istemp && OidIsValid(indoid)) ||
|
||||
(istemp && get_temp_rel_by_name(indexRelationName) != NULL))
|
||||
elog(ERROR, "Cannot create index: '%s' already exists",
|
||||
indexRelationName);
|
||||
|
||||
heapoid = RelationNameGetObjectId(heapRelationName, pg_class);
|
||||
heapoid = RelnameFindRelid(heapRelationName);
|
||||
|
||||
if (!OidIsValid(heapoid))
|
||||
elog(ERROR, "Cannot create index on '%s': relation does not exist",
|
||||
heapRelationName);
|
||||
|
||||
heap_close(pg_class);
|
||||
|
||||
|
||||
return heapoid;
|
||||
}
|
||||
|
||||
@ -538,7 +458,7 @@ ConstructIndexReldesc(Relation indexRelation, Oid amoid)
|
||||
* ----------------------------------------------------------------
|
||||
*/
|
||||
static Oid
|
||||
UpdateRelationRelation(Relation indexRelation)
|
||||
UpdateRelationRelation(Relation indexRelation, char *temp_relname)
|
||||
{
|
||||
Relation pg_class;
|
||||
HeapTuple tuple;
|
||||
@ -561,6 +481,9 @@ UpdateRelationRelation(Relation indexRelation)
|
||||
tuple->t_data->t_oid = RelationGetRelid(indexRelation);
|
||||
heap_insert(pg_class, tuple);
|
||||
|
||||
if (temp_relname)
|
||||
create_temp_relation(temp_relname, tuple);
|
||||
|
||||
/*
|
||||
* During normal processing, we need to make sure that the system
|
||||
* catalog indices are correct. Bootstrap (initdb) time doesn't
|
||||
@ -760,6 +683,7 @@ UpdateIndexRelation(Oid indexoid,
|
||||
}
|
||||
else
|
||||
predText = (text *) fmgr(F_TEXTIN, "");
|
||||
|
||||
predLen = VARSIZE(predText);
|
||||
itupLen = predLen + sizeof(FormData_pg_index);
|
||||
indexForm = (Form_pg_index) palloc(itupLen);
|
||||
@ -1025,27 +949,28 @@ index_create(char *heapRelationName,
|
||||
Oid heapoid;
|
||||
Oid indexoid;
|
||||
PredInfo *predInfo;
|
||||
|
||||
bool istemp = (get_temp_rel_by_name(heapRelationName) != NULL);
|
||||
char *temp_relname = NULL;
|
||||
|
||||
/* ----------------
|
||||
* check parameters
|
||||
* ----------------
|
||||
*/
|
||||
if (numatts < 1)
|
||||
elog(ERROR, "must index at least one attribute");
|
||||
|
||||
|
||||
/* ----------------
|
||||
* get heap relation oid and open the heap relation
|
||||
* XXX ADD INDEXING
|
||||
* ----------------
|
||||
*/
|
||||
heapoid = GetHeapRelationOid(heapRelationName, indexRelationName);
|
||||
heapoid = GetHeapRelationOid(heapRelationName, indexRelationName, istemp);
|
||||
|
||||
heapRelation = heap_open(heapoid);
|
||||
|
||||
/*
|
||||
* Only SELECT ... FOR UPDATE are allowed
|
||||
*/
|
||||
|
||||
LockRelation(heapRelation, ShareLock);
|
||||
|
||||
/* ----------------
|
||||
@ -1061,12 +986,36 @@ index_create(char *heapRelationName,
|
||||
numatts,
|
||||
attNums);
|
||||
|
||||
/* invalidate cache so possible non-temp index is masked by temp */
|
||||
if (istemp)
|
||||
{
|
||||
Oid relid = RelnameFindRelid(indexRelationName);
|
||||
|
||||
if (relid != InvalidOid)
|
||||
{
|
||||
/*
|
||||
* This is heavy-handed, but appears necessary bjm 1999/02/01
|
||||
* SystemCacheRelationFlushed(relid) is not enough either.
|
||||
*/
|
||||
RelationForgetRelation(relid);
|
||||
ResetSystemCache();
|
||||
}
|
||||
}
|
||||
|
||||
/* save user relation name because heap_create changes it */
|
||||
if (istemp)
|
||||
{
|
||||
temp_relname = pstrdup(indexRelationName); /* save original value */
|
||||
indexRelationName = palloc(NAMEDATALEN);
|
||||
strcpy(indexRelationName, temp_relname); /* heap_create will change this */
|
||||
}
|
||||
|
||||
/* ----------------
|
||||
* create the index relation
|
||||
* ----------------
|
||||
*/
|
||||
indexRelation = heap_create(indexRelationName,
|
||||
indexTupDesc);
|
||||
indexTupDesc, false, istemp);
|
||||
|
||||
/* ----------------
|
||||
* construct the index relation descriptor
|
||||
@ -1081,7 +1030,7 @@ index_create(char *heapRelationName,
|
||||
* (append RELATION tuple)
|
||||
* ----------------
|
||||
*/
|
||||
indexoid = UpdateRelationRelation(indexRelation);
|
||||
indexoid = UpdateRelationRelation(indexRelation, temp_relname);
|
||||
|
||||
/* ----------------
|
||||
* Now get the index procedure (only relevant for functional indices).
|
||||
@ -1162,9 +1111,9 @@ index_create(char *heapRelationName,
|
||||
}
|
||||
|
||||
/* ----------------------------------------------------------------
|
||||
*
|
||||
* index_destroy
|
||||
*
|
||||
* XXX break into modules like index_create
|
||||
* ----------------------------------------------------------------
|
||||
*/
|
||||
void
|
||||
@ -1175,11 +1124,11 @@ index_destroy(Oid indexId)
|
||||
Relation relationRelation;
|
||||
Relation attributeRelation;
|
||||
HeapTuple tuple;
|
||||
int16 attnum;
|
||||
|
||||
int16 attnum;
|
||||
|
||||
Assert(OidIsValid(indexId));
|
||||
|
||||
/* why open it here? bjm 1998/08/20 */
|
||||
/* Open now to obtain lock by referencing table? bjm */
|
||||
userindexRelation = index_open(indexId);
|
||||
|
||||
/* ----------------
|
||||
@ -1192,7 +1141,7 @@ index_destroy(Oid indexId)
|
||||
ObjectIdGetDatum(indexId),
|
||||
0, 0, 0);
|
||||
|
||||
AssertState(HeapTupleIsValid(tuple));
|
||||
Assert(HeapTupleIsValid(tuple));
|
||||
|
||||
heap_delete(relationRelation, &tuple->t_self, NULL);
|
||||
pfree(tuple);
|
||||
@ -1217,6 +1166,9 @@ index_destroy(Oid indexId)
|
||||
}
|
||||
heap_close(attributeRelation);
|
||||
|
||||
/* does something only if it is a temp index */
|
||||
remove_temp_relation(indexId);
|
||||
|
||||
/* ----------------
|
||||
* fix INDEX relation
|
||||
* ----------------
|
||||
@ -1224,10 +1176,7 @@ index_destroy(Oid indexId)
|
||||
tuple = SearchSysCacheTupleCopy(INDEXRELID,
|
||||
ObjectIdGetDatum(indexId),
|
||||
0, 0, 0);
|
||||
|
||||
if (!HeapTupleIsValid(tuple))
|
||||
elog(NOTICE, "IndexRelationDestroy: %s's INDEX tuple missing",
|
||||
RelationGetRelationName(userindexRelation));
|
||||
Assert(HeapTupleIsValid(tuple));
|
||||
|
||||
indexRelation = heap_openr(IndexRelationName);
|
||||
|
||||
|
@ -8,7 +8,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/catalog/indexing.c,v 1.34 1998/11/27 19:51:50 vadim Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/catalog/indexing.c,v 1.35 1999/02/02 03:44:13 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -30,6 +30,7 @@
|
||||
#include "storage/bufmgr.h"
|
||||
#include "utils/builtins.h"
|
||||
#include "utils/syscache.h"
|
||||
#include "utils/temprel.h"
|
||||
|
||||
/*
|
||||
* Names of indices on the following system catalogs:
|
||||
@ -455,6 +456,13 @@ ClassNameIndexScan(Relation heapRelation, char *relName)
|
||||
ScanKeyData skey[1];
|
||||
HeapTuple tuple;
|
||||
|
||||
/*
|
||||
* we have to do this before looking in system tables because temp
|
||||
* table namespace takes precedence
|
||||
*/
|
||||
if ((tuple = get_temp_rel_by_name(relName)) != NULL)
|
||||
return heap_copytuple(tuple);
|
||||
|
||||
ScanKeyEntryInitialize(&skey[0],
|
||||
(bits16) 0x0,
|
||||
(AttrNumber) 1,
|
||||
|
@ -14,7 +14,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/cluster.c,v 1.35 1999/01/21 22:48:06 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/cluster.c,v 1.36 1999/02/02 03:44:17 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -219,7 +219,8 @@ copy_heap(Oid OIDOldHeap)
|
||||
|
||||
tupdesc = CreateTupleDescCopy(OldHeapDesc);
|
||||
|
||||
OIDNewHeap = heap_create_with_catalog(NewName, tupdesc, RELKIND_RELATION);
|
||||
OIDNewHeap = heap_create_with_catalog(NewName, tupdesc,
|
||||
RELKIND_RELATION, false);
|
||||
|
||||
if (!OidIsValid(OIDNewHeap))
|
||||
elog(ERROR, "clusterheap: cannot create temporary heap relation\n");
|
||||
|
@ -6,7 +6,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/copy.c,v 1.69 1999/02/01 20:25:54 wieck Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/copy.c,v 1.70 1999/02/02 03:44:18 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -646,7 +646,6 @@ CopyFrom(Relation rel, bool binary, bool oids, FILE *fp, char *delim)
|
||||
index_nulls[i] = ' ';
|
||||
byval[i] = (bool) IsTypeByVal(attr[i]->atttypid);
|
||||
}
|
||||
values = (Datum *) palloc(sizeof(Datum) * attr_count);
|
||||
|
||||
lineno = 0;
|
||||
while (!done)
|
||||
@ -873,13 +872,16 @@ CopyFrom(Relation rel, bool binary, bool oids, FILE *fp, char *delim)
|
||||
}
|
||||
pfree(values);
|
||||
pfree(nulls);
|
||||
pfree(index_nulls);
|
||||
pfree(idatum);
|
||||
pfree(byval);
|
||||
|
||||
if (!binary)
|
||||
{
|
||||
pfree(in_functions);
|
||||
pfree(elements);
|
||||
pfree(typmod);
|
||||
}
|
||||
pfree(byval);
|
||||
|
||||
/* comments in execUtils.c */
|
||||
if (has_index)
|
||||
|
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/creatinh.c,v 1.37 1998/12/14 05:18:43 scrappy Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/creatinh.c,v 1.38 1999/02/02 03:44:19 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -138,8 +138,8 @@ DefineRelation(CreateStmt *stmt, char relkind)
|
||||
}
|
||||
}
|
||||
|
||||
relationId = heap_create_with_catalog(relname,
|
||||
descriptor, relkind);
|
||||
relationId = heap_create_with_catalog(relname, descriptor,
|
||||
relkind, stmt->istemp);
|
||||
|
||||
StoreCatalogInheritance(relationId, inheritList);
|
||||
}
|
||||
@ -279,7 +279,7 @@ MergeAttributes(List *schema, List *supers, List **supconstr)
|
||||
SearchSysCacheTuple(TYPOID,
|
||||
ObjectIdGetDatum(attribute->atttypid),
|
||||
0, 0, 0);
|
||||
AssertState(HeapTupleIsValid(tuple));
|
||||
Assert(HeapTupleIsValid(tuple));
|
||||
attributeType =
|
||||
(((Form_pg_type) GETSTRUCT(tuple))->typname).data;
|
||||
|
||||
|
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/defind.c,v 1.30 1999/01/21 22:48:06 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/defind.c,v 1.31 1999/02/02 03:44:19 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -98,15 +98,11 @@ DefineIndex(char *heapRelationName,
|
||||
/*
|
||||
* compute heap relation id
|
||||
*/
|
||||
tuple = SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(heapRelationName),
|
||||
0, 0, 0);
|
||||
if (!HeapTupleIsValid(tuple))
|
||||
if ((relationId = RelnameFindRelid(heapRelationName)) == InvalidOid)
|
||||
{
|
||||
elog(ERROR, "DefineIndex: %s relation not found",
|
||||
heapRelationName);
|
||||
}
|
||||
relationId = tuple->t_data->t_oid;
|
||||
|
||||
if (unique && strcmp(accessMethodName, "btree") != 0)
|
||||
elog(ERROR, "DefineIndex: unique indices are only available with the btree access method");
|
||||
|
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/recipe.c,v 1.26 1998/12/14 05:18:44 scrappy Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/recipe.c,v 1.27 1999/02/02 03:44:20 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -1025,7 +1025,7 @@ tg_parseSubQuery(TgRecipe * r, TgNode * n, TeeInfo * teeInfo)
|
||||
|
||||
relid = heap_create_with_catalog(
|
||||
child->nodeElem->outTypes->val[0],
|
||||
tupdesc, RELKIND_RELATION);
|
||||
tupdesc, RELKIND_RELATION, false);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -1049,7 +1049,7 @@ tg_parseSubQuery(TgRecipe * r, TgNode * n, TeeInfo * teeInfo)
|
||||
{
|
||||
relid = heap_create_with_catalog(
|
||||
child->nodeElem->outTypes->val[0],
|
||||
tupdesc, RELKIND_RELATION);
|
||||
tupdesc, RELKIND_RELATION, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/rename.c,v 1.19 1998/12/15 12:45:58 vadim Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/commands/Attic/rename.c,v 1.20 1999/02/02 03:44:20 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -18,6 +18,7 @@
|
||||
#include <utils/builtins.h>
|
||||
#include <catalog/catname.h>
|
||||
#include <utils/syscache.h>
|
||||
#include <catalog/heap.h>
|
||||
#include <catalog/indexing.h>
|
||||
#include <catalog/catalog.h>
|
||||
#include <commands/copy.h>
|
||||
@ -106,15 +107,9 @@ renameatt(char *relname,
|
||||
List *child,
|
||||
*children;
|
||||
|
||||
reltup = SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(relname),
|
||||
0, 0, 0);
|
||||
|
||||
if (!HeapTupleIsValid(reltup))
|
||||
if ((myrelid = RelnameFindRelid(relname)) == InvalidOid)
|
||||
elog(ERROR, "renameatt: unknown relation: \"%s\"", relname);
|
||||
|
||||
myrelid = reltup->t_data->t_oid;
|
||||
|
||||
/* this routine is actually in the planner */
|
||||
children = find_all_inheritors(lconsi(myrelid, NIL), NIL);
|
||||
|
||||
@ -147,14 +142,10 @@ renameatt(char *relname,
|
||||
}
|
||||
}
|
||||
|
||||
reltup = SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(relname),
|
||||
0, 0, 0);
|
||||
if (!HeapTupleIsValid(reltup))
|
||||
|
||||
if ((relid = RelnameFindRelid(relname)) == InvalidOid)
|
||||
elog(ERROR, "renameatt: relation \"%s\" nonexistent", relname);
|
||||
|
||||
relid = reltup->t_data->t_oid;
|
||||
|
||||
oldatttup = SearchSysCacheTupleCopy(ATTNAME,
|
||||
ObjectIdGetDatum(relid),
|
||||
PointerGetDatum(oldattname),
|
||||
@ -211,8 +202,7 @@ void
|
||||
renamerel(char *oldrelname, char *newrelname)
|
||||
{
|
||||
Relation relrelation; /* for RELATION relation */
|
||||
HeapTuple oldreltup,
|
||||
newreltup;
|
||||
HeapTuple oldreltup;
|
||||
char oldpath[MAXPGPATH],
|
||||
newpath[MAXPGPATH];
|
||||
Relation irelations[Num_pg_class_indices];
|
||||
@ -231,10 +221,7 @@ renamerel(char *oldrelname, char *newrelname)
|
||||
if (!HeapTupleIsValid(oldreltup))
|
||||
elog(ERROR, "renamerel: relation \"%s\" does not exist", oldrelname);
|
||||
|
||||
newreltup = SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(newrelname),
|
||||
0, 0, 0);
|
||||
if (HeapTupleIsValid(newreltup))
|
||||
if (RelnameFindRelid(newrelname) != InvalidOid)
|
||||
elog(ERROR, "renamerel: relation \"%s\" exists", newrelname);
|
||||
|
||||
/* rename the path first, so if this fails the rename's not done */
|
||||
|
@ -5,7 +5,7 @@
|
||||
*
|
||||
* Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
* $Id: view.c,v 1.29 1998/12/14 08:11:01 scrappy Exp $
|
||||
* $Id: view.c,v 1.30 1999/02/02 03:44:20 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -95,6 +95,7 @@ DefineVirtualRelation(char *relname, List *tlist)
|
||||
* nil...
|
||||
*/
|
||||
createStmt.relname = relname;
|
||||
createStmt.istemp = false;
|
||||
createStmt.tableElts = attrList;
|
||||
/* createStmt.tableType = NULL;*/
|
||||
createStmt.inhRelnames = NIL;
|
||||
|
@ -5,7 +5,7 @@
|
||||
*
|
||||
* Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
* $Id: execAmi.c,v 1.29 1999/01/18 00:09:45 momjian Exp $
|
||||
* $Id: execAmi.c,v 1.30 1999/02/02 03:44:23 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -524,7 +524,7 @@ ExecCreatR(TupleDesc tupType,
|
||||
* heap_create creates a name if the argument to heap_create is
|
||||
* '\0 '
|
||||
*/
|
||||
relDesc = heap_create("", tupType);
|
||||
relDesc = heap_create(NULL, tupType, true, false);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -26,7 +26,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/executor/execMain.c,v 1.69 1999/01/29 13:24:36 vadim Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/executor/execMain.c,v 1.70 1999/02/02 03:44:23 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -654,7 +654,7 @@ InitPlan(CmdType operation, Query *parseTree, Plan *plan, EState *estate)
|
||||
tupdesc = CreateTupleDescCopy(tupType);
|
||||
|
||||
intoRelationId = heap_create_with_catalog(intoName,
|
||||
tupdesc, RELKIND_RELATION);
|
||||
tupdesc, RELKIND_RELATION,parseTree->isTemp);
|
||||
|
||||
FreeTupleDesc(tupdesc);
|
||||
|
||||
|
@ -14,7 +14,7 @@
|
||||
* ExecInitTee
|
||||
* ExecEndTee
|
||||
*
|
||||
* $Id: nodeTee.c,v 1.28 1999/02/01 13:33:27 vadim Exp $
|
||||
* $Id: nodeTee.c,v 1.29 1999/02/02 03:44:24 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -167,7 +167,7 @@ ExecInitTee(Tee *node, EState *currentEstate, Plan *parent)
|
||||
else
|
||||
bufferRel = heap_open(
|
||||
heap_create_with_catalog(teeState->tee_bufferRelname,
|
||||
tupType, RELKIND_RELATION));
|
||||
tupType, RELKIND_RELATION, false));
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -176,7 +176,7 @@ ExecInitTee(Tee *node, EState *currentEstate, Plan *parent)
|
||||
newoid());
|
||||
bufferRel = heap_open(
|
||||
heap_create_with_catalog(teeState->tee_bufferRelname,
|
||||
tupType, RELKIND_RELATION));
|
||||
tupType, RELKIND_RELATION, false));
|
||||
}
|
||||
|
||||
teeState->tee_bufferRel = bufferRel;
|
||||
|
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/nodes/copyfuncs.c,v 1.56 1999/01/29 09:22:59 vadim Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/nodes/copyfuncs.c,v 1.57 1999/02/02 03:44:26 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -29,6 +29,7 @@
|
||||
#include "utils/palloc.h"
|
||||
#include "catalog/pg_type.h"
|
||||
#include "storage/lmgr.h"
|
||||
#include "optimizer/planmain.h"
|
||||
|
||||
/*
|
||||
* listCopy--
|
||||
@ -1572,6 +1573,7 @@ _copyQuery(Query *from)
|
||||
newnode->into = pstrdup(from->into);
|
||||
newnode->isPortal = from->isPortal;
|
||||
newnode->isBinary = from->isBinary;
|
||||
newnode->isTemp = from->isTemp;
|
||||
newnode->unionall = from->unionall;
|
||||
if (from->uniqueFlag)
|
||||
newnode->uniqueFlag = pstrdup(from->uniqueFlag);
|
||||
|
@ -5,7 +5,7 @@
|
||||
*
|
||||
* Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
* $Id: outfuncs.c,v 1.61 1999/01/24 00:28:20 momjian Exp $
|
||||
* $Id: outfuncs.c,v 1.62 1999/02/02 03:44:26 momjian Exp $
|
||||
*
|
||||
* NOTES
|
||||
* Every (plan) node in POSTGRES has an associated "out" routine which
|
||||
@ -69,8 +69,13 @@ _outIntList(StringInfo str, List *list)
|
||||
static void
|
||||
_outCreateStmt(StringInfo str, CreateStmt *node)
|
||||
{
|
||||
appendStringInfo(str, " CREATE :relname %s :columns ",
|
||||
appendStringInfo(str, " CREATE :relname %s ",
|
||||
stringStringInfo(node->relname));
|
||||
|
||||
appendStringInfo(str, " :istemp %s ",
|
||||
node->istemp ? "true" : "false");
|
||||
|
||||
appendStringInfo(str, " :columns ");
|
||||
_outNode(str, node->tableElts);
|
||||
|
||||
appendStringInfo(str, " :inhRelnames ");
|
||||
@ -197,11 +202,12 @@ _outQuery(StringInfo str, Query *node)
|
||||
}
|
||||
|
||||
appendStringInfo(str,
|
||||
" :resultRelation %d :into %s :isPortal %s :isBinary %s :unionall %s ",
|
||||
" :resultRelation %d :into %s :isPortal %s :isBinary %s :isTemp %s :unionall %s ",
|
||||
node->resultRelation,
|
||||
stringStringInfo(node->into),
|
||||
node->isPortal ? "true" : "false",
|
||||
node->isBinary ? "true" : "false",
|
||||
node->isTemp ? "true" : "false",
|
||||
node->unionall ? "true" : "false");
|
||||
|
||||
appendStringInfo(str, " :unique %s :sortClause ",
|
||||
|
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/nodes/readfuncs.c,v 1.43 1999/01/24 00:28:20 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/nodes/readfuncs.c,v 1.44 1999/02/02 03:44:27 momjian Exp $
|
||||
*
|
||||
* NOTES
|
||||
* Most of the read functions for plan nodes are tested. (In fact, they
|
||||
@ -120,6 +120,10 @@ _readQuery()
|
||||
token = lsptok(NULL, &length); /* get isBinary */
|
||||
local_node->isBinary = (token[0] == 't') ? true : false;
|
||||
|
||||
token = lsptok(NULL, &length); /* skip :isTemp */
|
||||
token = lsptok(NULL, &length); /* get isTemp */
|
||||
local_node->isTemp = (token[0] == 't') ? true : false;
|
||||
|
||||
token = lsptok(NULL, &length); /* skip :unionall */
|
||||
token = lsptok(NULL, &length); /* get unionall */
|
||||
local_node->unionall = (token[0] == 't') ? true : false;
|
||||
|
@ -5,7 +5,7 @@
|
||||
*
|
||||
* Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
* $Id: analyze.c,v 1.96 1999/01/27 01:18:20 scrappy Exp $
|
||||
* $Id: analyze.c,v 1.97 1999/02/02 03:44:32 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -924,6 +924,7 @@ transformSelectStmt(ParseState *pstate, SelectStmt *stmt)
|
||||
qry->uniqueFlag = stmt->unique;
|
||||
|
||||
qry->into = stmt->into;
|
||||
qry->isTemp = stmt->istemp;
|
||||
qry->isPortal = FALSE;
|
||||
|
||||
qry->targetList = transformTargetList(pstate, stmt->targetList);
|
||||
@ -1032,6 +1033,7 @@ transformCursorStmt(ParseState *pstate, SelectStmt *stmt)
|
||||
qry = transformSelectStmt(pstate, stmt);
|
||||
|
||||
qry->into = stmt->portalname;
|
||||
qry->isTemp = stmt->istemp;
|
||||
qry->isPortal = TRUE;
|
||||
qry->isBinary = stmt->binary; /* internal portal */
|
||||
|
||||
@ -1074,7 +1076,7 @@ create_select_list(Node *ptr, List **select_list, bool *unionall_present)
|
||||
* hands back 'true' */
|
||||
Node *A_Expr_to_Expr(Node *ptr, bool *intersect_present)
|
||||
{
|
||||
Node *result;
|
||||
Node *result = NULL;
|
||||
|
||||
switch(nodeTag(ptr))
|
||||
{
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -10,7 +10,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/gram.y,v 2.49 1999/01/25 12:01:13 vadim Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/gram.y,v 2.50 1999/02/02 03:44:42 momjian Exp $
|
||||
*
|
||||
* HISTORY
|
||||
* AUTHOR DATE MAJOR EVENT
|
||||
@ -154,13 +154,13 @@ Oid param_type(int t); /* used in parse_expr.c */
|
||||
|
||||
%type <str> opt_id, opt_portal_name,
|
||||
all_Op, MathOp, opt_name, opt_unique,
|
||||
result, OptUseOp, opt_class, SpecialRuleRelation
|
||||
OptUseOp, opt_class, SpecialRuleRelation
|
||||
|
||||
%type <str> privileges, operation_commalist, grantee
|
||||
%type <chr> operation, TriggerOneEvent
|
||||
|
||||
%type <list> stmtblock, stmtmulti,
|
||||
relation_name_list, OptTableElementList,
|
||||
result, relation_name_list, OptTableElementList,
|
||||
OptInherit, definition,
|
||||
opt_with, func_args, func_args_list,
|
||||
oper_argtypes, OptStmtList, OptStmtBlock, OptStmtMulti,
|
||||
@ -173,7 +173,7 @@ Oid param_type(int t); /* used in parse_expr.c */
|
||||
%type <node> func_return
|
||||
%type <boolean> set_opt
|
||||
|
||||
%type <boolean> TriggerForOpt, TriggerForType
|
||||
%type <boolean> TriggerForOpt, TriggerForType, OptTemp
|
||||
|
||||
%type <list> for_update_clause
|
||||
%type <list> join_list
|
||||
@ -283,7 +283,7 @@ Oid param_type(int t); /* used in parse_expr.c */
|
||||
PARTIAL, POSITION, PRECISION, PRIMARY, PRIOR, PRIVILEGES, PROCEDURE, PUBLIC,
|
||||
READ, REFERENCES, RELATIVE, REVOKE, RIGHT, ROLLBACK,
|
||||
SCROLL, SECOND_P, SELECT, SET, SUBSTRING,
|
||||
TABLE, THEN, TIME, TIMESTAMP, TIMEZONE_HOUR, TIMEZONE_MINUTE,
|
||||
TABLE, TEMP, THEN, TIME, TIMESTAMP, TIMEZONE_HOUR, TIMEZONE_MINUTE,
|
||||
TO, TRAILING, TRANSACTION, TRIM, TRUE_P,
|
||||
UNION, UNIQUE, UPDATE, USER, USING,
|
||||
VALUES, VARCHAR, VARYING, VIEW,
|
||||
@ -747,18 +747,23 @@ copy_delimiter: USING DELIMITERS Sconst { $$ = $3; }
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
CreateStmt: CREATE TABLE relation_name '(' OptTableElementList ')'
|
||||
CreateStmt: CREATE OptTemp TABLE relation_name '(' OptTableElementList ')'
|
||||
OptInherit
|
||||
{
|
||||
CreateStmt *n = makeNode(CreateStmt);
|
||||
n->relname = $3;
|
||||
n->tableElts = $5;
|
||||
n->inhRelnames = $7;
|
||||
n->istemp = $2;
|
||||
n->relname = $4;
|
||||
n->tableElts = $6;
|
||||
n->inhRelnames = $8;
|
||||
n->constraints = NIL;
|
||||
$$ = (Node *)n;
|
||||
}
|
||||
;
|
||||
|
||||
OptTemp: TEMP { $$ = TRUE; }
|
||||
| /*EMPTY*/ { $$ = FALSE; }
|
||||
;
|
||||
|
||||
OptTableElementList: OptTableElementList ',' OptTableElement
|
||||
{
|
||||
if ($3 != NULL)
|
||||
@ -1236,12 +1241,13 @@ OptInherit: INHERITS '(' relation_name_list ')' { $$ = $3; }
|
||||
| /*EMPTY*/ { $$ = NIL; }
|
||||
;
|
||||
|
||||
CreateAsStmt: CREATE TABLE relation_name OptCreateAs AS SubSelect
|
||||
CreateAsStmt: CREATE OptTemp TABLE relation_name OptCreateAs AS SubSelect
|
||||
{
|
||||
SelectStmt *n = (SelectStmt *)$6;
|
||||
if ($4 != NIL)
|
||||
mapTargetColumns($4, n->targetList);
|
||||
n->into = $3;
|
||||
SelectStmt *n = (SelectStmt *)$7;
|
||||
if ($5 != NIL)
|
||||
mapTargetColumns($5, n->targetList);
|
||||
n->istemp = $2;
|
||||
n->into = $4;
|
||||
$$ = (Node *)n;
|
||||
}
|
||||
;
|
||||
@ -2862,8 +2868,9 @@ SubSelect: SELECT opt_unique res_target_list2
|
||||
* want to create a new rule 'SubSelect1' including the
|
||||
* feature. If it makes troubles we will have to add
|
||||
* a new rule and change this to prevent INTOs in
|
||||
* Subselects again */
|
||||
n->into = $4;
|
||||
* Subselects again */
|
||||
n->istemp = (bool)((A_Const *)lfirst($4))->val.val.ival;
|
||||
n->into = (char *)lnext($4);
|
||||
|
||||
n->fromClause = $5;
|
||||
n->whereClause = $6;
|
||||
@ -2873,8 +2880,9 @@ SubSelect: SELECT opt_unique res_target_list2
|
||||
}
|
||||
;
|
||||
|
||||
result: INTO opt_table relation_name { $$= $3; }
|
||||
| /*EMPTY*/ { $$ = NULL; }
|
||||
/* easy way to return two values. Can someone improve this? bjm */
|
||||
result: INTO OptTemp opt_table relation_name { $$ = lcons(makeInteger($2), (List *)$4); }
|
||||
| /*EMPTY*/ { $$ = lcons(makeInteger(false), NIL); }
|
||||
;
|
||||
|
||||
opt_table: TABLE { $$ = TRUE; }
|
||||
|
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/keywords.c,v 1.51 1999/01/18 00:09:53 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/parser/keywords.c,v 1.52 1999/02/02 03:44:42 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -213,6 +213,7 @@ static ScanKeyword ScanKeywords[] = {
|
||||
{"stdout", STDOUT},
|
||||
{"substring", SUBSTRING},
|
||||
{"table", TABLE},
|
||||
{"temp", TEMP},
|
||||
{"then", THEN},
|
||||
{"time", TIME},
|
||||
{"timestamp", TIMESTAMP},
|
||||
|
@ -145,110 +145,111 @@ typedef union
|
||||
#define SET 371
|
||||
#define SUBSTRING 372
|
||||
#define TABLE 373
|
||||
#define THEN 374
|
||||
#define TIME 375
|
||||
#define TIMESTAMP 376
|
||||
#define TIMEZONE_HOUR 377
|
||||
#define TIMEZONE_MINUTE 378
|
||||
#define TO 379
|
||||
#define TRAILING 380
|
||||
#define TRANSACTION 381
|
||||
#define TRIM 382
|
||||
#define TRUE_P 383
|
||||
#define UNION 384
|
||||
#define UNIQUE 385
|
||||
#define UPDATE 386
|
||||
#define USER 387
|
||||
#define USING 388
|
||||
#define VALUES 389
|
||||
#define VARCHAR 390
|
||||
#define VARYING 391
|
||||
#define VIEW 392
|
||||
#define WHEN 393
|
||||
#define WHERE 394
|
||||
#define WITH 395
|
||||
#define WORK 396
|
||||
#define YEAR_P 397
|
||||
#define ZONE 398
|
||||
#define TRIGGER 399
|
||||
#define TYPE_P 400
|
||||
#define ABORT_TRANS 401
|
||||
#define AFTER 402
|
||||
#define AGGREGATE 403
|
||||
#define ANALYZE 404
|
||||
#define BACKWARD 405
|
||||
#define BEFORE 406
|
||||
#define BINARY 407
|
||||
#define CACHE 408
|
||||
#define CLUSTER 409
|
||||
#define COPY 410
|
||||
#define CREATEDB 411
|
||||
#define CREATEUSER 412
|
||||
#define CYCLE 413
|
||||
#define DATABASE 414
|
||||
#define DELIMITERS 415
|
||||
#define DO 416
|
||||
#define EACH 417
|
||||
#define ENCODING 418
|
||||
#define EXPLAIN 419
|
||||
#define EXTEND 420
|
||||
#define FORWARD 421
|
||||
#define FUNCTION 422
|
||||
#define HANDLER 423
|
||||
#define INCREMENT 424
|
||||
#define INDEX 425
|
||||
#define INHERITS 426
|
||||
#define INSTEAD 427
|
||||
#define ISNULL 428
|
||||
#define LANCOMPILER 429
|
||||
#define LISTEN 430
|
||||
#define LOAD 431
|
||||
#define LOCATION 432
|
||||
#define LOCK_P 433
|
||||
#define MAXVALUE 434
|
||||
#define MINVALUE 435
|
||||
#define MOVE 436
|
||||
#define NEW 437
|
||||
#define NOCREATEDB 438
|
||||
#define NOCREATEUSER 439
|
||||
#define NONE 440
|
||||
#define NOTHING 441
|
||||
#define NOTIFY 442
|
||||
#define NOTNULL 443
|
||||
#define OIDS 444
|
||||
#define OPERATOR 445
|
||||
#define PASSWORD 446
|
||||
#define PROCEDURAL 447
|
||||
#define RECIPE 448
|
||||
#define RENAME 449
|
||||
#define RESET 450
|
||||
#define RETURNS 451
|
||||
#define ROW 452
|
||||
#define RULE 453
|
||||
#define SEQUENCE 454
|
||||
#define SERIAL 455
|
||||
#define SETOF 456
|
||||
#define SHOW 457
|
||||
#define START 458
|
||||
#define STATEMENT 459
|
||||
#define STDIN 460
|
||||
#define STDOUT 461
|
||||
#define TRUSTED 462
|
||||
#define UNLISTEN 463
|
||||
#define UNTIL 464
|
||||
#define VACUUM 465
|
||||
#define VALID 466
|
||||
#define VERBOSE 467
|
||||
#define VERSION 468
|
||||
#define IDENT 469
|
||||
#define SCONST 470
|
||||
#define Op 471
|
||||
#define ICONST 472
|
||||
#define PARAM 473
|
||||
#define FCONST 474
|
||||
#define OP 475
|
||||
#define UMINUS 476
|
||||
#define TYPECAST 477
|
||||
#define TEMP 374
|
||||
#define THEN 375
|
||||
#define TIME 376
|
||||
#define TIMESTAMP 377
|
||||
#define TIMEZONE_HOUR 378
|
||||
#define TIMEZONE_MINUTE 379
|
||||
#define TO 380
|
||||
#define TRAILING 381
|
||||
#define TRANSACTION 382
|
||||
#define TRIM 383
|
||||
#define TRUE_P 384
|
||||
#define UNION 385
|
||||
#define UNIQUE 386
|
||||
#define UPDATE 387
|
||||
#define USER 388
|
||||
#define USING 389
|
||||
#define VALUES 390
|
||||
#define VARCHAR 391
|
||||
#define VARYING 392
|
||||
#define VIEW 393
|
||||
#define WHEN 394
|
||||
#define WHERE 395
|
||||
#define WITH 396
|
||||
#define WORK 397
|
||||
#define YEAR_P 398
|
||||
#define ZONE 399
|
||||
#define TRIGGER 400
|
||||
#define TYPE_P 401
|
||||
#define ABORT_TRANS 402
|
||||
#define AFTER 403
|
||||
#define AGGREGATE 404
|
||||
#define ANALYZE 405
|
||||
#define BACKWARD 406
|
||||
#define BEFORE 407
|
||||
#define BINARY 408
|
||||
#define CACHE 409
|
||||
#define CLUSTER 410
|
||||
#define COPY 411
|
||||
#define CREATEDB 412
|
||||
#define CREATEUSER 413
|
||||
#define CYCLE 414
|
||||
#define DATABASE 415
|
||||
#define DELIMITERS 416
|
||||
#define DO 417
|
||||
#define EACH 418
|
||||
#define ENCODING 419
|
||||
#define EXPLAIN 420
|
||||
#define EXTEND 421
|
||||
#define FORWARD 422
|
||||
#define FUNCTION 423
|
||||
#define HANDLER 424
|
||||
#define INCREMENT 425
|
||||
#define INDEX 426
|
||||
#define INHERITS 427
|
||||
#define INSTEAD 428
|
||||
#define ISNULL 429
|
||||
#define LANCOMPILER 430
|
||||
#define LISTEN 431
|
||||
#define LOAD 432
|
||||
#define LOCATION 433
|
||||
#define LOCK_P 434
|
||||
#define MAXVALUE 435
|
||||
#define MINVALUE 436
|
||||
#define MOVE 437
|
||||
#define NEW 438
|
||||
#define NOCREATEDB 439
|
||||
#define NOCREATEUSER 440
|
||||
#define NONE 441
|
||||
#define NOTHING 442
|
||||
#define NOTIFY 443
|
||||
#define NOTNULL 444
|
||||
#define OIDS 445
|
||||
#define OPERATOR 446
|
||||
#define PASSWORD 447
|
||||
#define PROCEDURAL 448
|
||||
#define RECIPE 449
|
||||
#define RENAME 450
|
||||
#define RESET 451
|
||||
#define RETURNS 452
|
||||
#define ROW 453
|
||||
#define RULE 454
|
||||
#define SEQUENCE 455
|
||||
#define SERIAL 456
|
||||
#define SETOF 457
|
||||
#define SHOW 458
|
||||
#define START 459
|
||||
#define STATEMENT 460
|
||||
#define STDIN 461
|
||||
#define STDOUT 462
|
||||
#define TRUSTED 463
|
||||
#define UNLISTEN 464
|
||||
#define UNTIL 465
|
||||
#define VACUUM 466
|
||||
#define VALID 467
|
||||
#define VERBOSE 468
|
||||
#define VERSION 469
|
||||
#define IDENT 470
|
||||
#define SCONST 471
|
||||
#define Op 472
|
||||
#define ICONST 473
|
||||
#define PARAM 474
|
||||
#define FCONST 475
|
||||
#define OP 476
|
||||
#define UMINUS 477
|
||||
#define TYPECAST 478
|
||||
|
||||
|
||||
extern YYSTYPE yylval;
|
||||
|
@ -6,7 +6,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/rewrite/rewriteHandler.c,v 1.32 1999/01/25 18:02:20 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/rewrite/rewriteHandler.c,v 1.33 1999/02/02 03:44:45 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -1135,6 +1135,7 @@ modifyAggrefMakeSublink(Expr *origexp, Query *parsetree)
|
||||
subquery->into = NULL;
|
||||
subquery->isPortal = FALSE;
|
||||
subquery->isBinary = FALSE;
|
||||
subquery->isTemp = FALSE;
|
||||
subquery->unionall = FALSE;
|
||||
subquery->uniqueFlag = NULL;
|
||||
subquery->sortClause = NULL;
|
||||
@ -2767,7 +2768,7 @@ Except_Intersect_Rewrite (Query *parsetree)
|
||||
List *union_list = NIL, *sortClause;
|
||||
List *left_expr, *right_expr, *resnames = NIL;
|
||||
char *op, *uniqueFlag, *into;
|
||||
bool isBinary, isPortal;
|
||||
bool isBinary, isPortal, isTemp;
|
||||
CmdType commandType = CMD_SELECT;
|
||||
List *rtable_insert = NIL;
|
||||
|
||||
@ -2811,7 +2812,8 @@ Except_Intersect_Rewrite (Query *parsetree)
|
||||
into = parsetree->into;
|
||||
isBinary = parsetree->isBinary;
|
||||
isPortal = parsetree->isPortal;
|
||||
|
||||
isTemp = parsetree->isTemp;
|
||||
|
||||
/* The operator tree attached to parsetree->intersectClause is still 'raw'
|
||||
* ( = the leaf nodes are still SelectStmt nodes instead of Query nodes)
|
||||
* So step through the tree and transform the nodes using parse_analyze().
|
||||
@ -2959,6 +2961,8 @@ Except_Intersect_Rewrite (Query *parsetree)
|
||||
result->into = into;
|
||||
result->isPortal = isPortal;
|
||||
result->isBinary = isBinary;
|
||||
result->isTemp = isTemp;
|
||||
|
||||
/* The relation to insert into is attached to the range table
|
||||
* of the new top node */
|
||||
if (commandType == CMD_INSERT)
|
||||
|
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/storage/buffer/bufmgr.c,v 1.45 1998/12/15 12:46:19 vadim Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/storage/buffer/bufmgr.c,v 1.46 1999/02/02 03:44:46 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -231,7 +231,7 @@ ReadBufferWithBufferLock(Relation reln,
|
||||
bool isLocalBuf;
|
||||
|
||||
extend = (blockNum == P_NEW);
|
||||
isLocalBuf = reln->rd_islocal;
|
||||
isLocalBuf = reln->rd_myxactonly;
|
||||
|
||||
if (isLocalBuf)
|
||||
{
|
||||
@ -1374,7 +1374,7 @@ BlockNumber
|
||||
RelationGetNumberOfBlocks(Relation relation)
|
||||
{
|
||||
return
|
||||
((relation->rd_islocal) ? relation->rd_nblocks :
|
||||
((relation->rd_myxactonly) ? relation->rd_nblocks :
|
||||
smgrnblocks(DEFAULT_SMGR, relation));
|
||||
}
|
||||
|
||||
@ -1395,7 +1395,7 @@ ReleaseRelationBuffers(Relation rel)
|
||||
int holding = 0;
|
||||
BufferDesc *buf;
|
||||
|
||||
if (rel->rd_islocal)
|
||||
if (rel->rd_myxactonly)
|
||||
{
|
||||
for (i = 0; i < NLocBuffer; i++)
|
||||
{
|
||||
@ -1564,7 +1564,7 @@ BlowawayRelationBuffers(Relation rel, BlockNumber block)
|
||||
int i;
|
||||
BufferDesc *buf;
|
||||
|
||||
if (rel->rd_islocal)
|
||||
if (rel->rd_myxactonly)
|
||||
{
|
||||
for (i = 0; i < NLocBuffer; i++)
|
||||
{
|
||||
|
@ -8,7 +8,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/storage/large_object/inv_api.c,v 1.45 1999/01/21 22:48:09 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/storage/large_object/inv_api.c,v 1.46 1999/02/02 03:44:50 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -47,7 +47,6 @@
|
||||
#include "utils/builtins.h" /* for namestrcpy() */
|
||||
#include "utils/rel.h"
|
||||
#include "utils/relcache.h"
|
||||
#include "utils/syscache.h"
|
||||
|
||||
/*
|
||||
* Warning, Will Robinson... In order to pack data into an inversion
|
||||
@ -120,20 +119,16 @@ inv_create(int flags)
|
||||
sprintf(objname, "xinv%d", file_oid);
|
||||
sprintf(indname, "xinx%d", file_oid);
|
||||
|
||||
if (SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(objname),
|
||||
0, 0, 0) != NULL)
|
||||
if (RelnameFindRelid(objname) != InvalidOid)
|
||||
{
|
||||
elog(ERROR,
|
||||
"internal error: %s already exists -- cannot create large obj",
|
||||
objname);
|
||||
}
|
||||
if (SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(indname),
|
||||
0, 0, 0) != NULL)
|
||||
if (RelnameFindRelid(indname) != InvalidOid)
|
||||
{
|
||||
elog(ERROR,
|
||||
"internal error: %s already exists -- cannot create large obj",
|
||||
"internal error: %s already exists -- cannot create large obj",
|
||||
indname);
|
||||
}
|
||||
|
||||
@ -153,7 +148,7 @@ inv_create(int flags)
|
||||
* be located on whatever storage manager the user requested.
|
||||
*/
|
||||
|
||||
heap_create_with_catalog(objname, tupdesc, RELKIND_LOBJECT);
|
||||
heap_create_with_catalog(objname, tupdesc, RELKIND_LOBJECT, false);
|
||||
|
||||
/* make the relation visible in this transaction */
|
||||
CommandCounterIncrement();
|
||||
|
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/tcop/postgres.c,v 1.97 1999/01/18 00:09:56 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/tcop/postgres.c,v 1.98 1999/02/02 03:44:51 momjian Exp $
|
||||
*
|
||||
* NOTES
|
||||
* this is the "main" module of the postgres backend and
|
||||
@ -72,6 +72,7 @@
|
||||
#include "utils/mcxt.h"
|
||||
#include "utils/rel.h"
|
||||
#include "utils/ps_status.h"
|
||||
#include "utils/temprel.h"
|
||||
|
||||
#if FALSE
|
||||
#include "nodes/relation.h"
|
||||
@ -1502,6 +1503,8 @@ PostgresMain(int argc, char *argv[], int real_argc, char *real_argv[])
|
||||
if (!TransactionFlushEnabled())
|
||||
on_shmem_exit(FlushBufferPool, NULL);
|
||||
|
||||
on_shmem_exit(remove_all_temp_relations, NULL);
|
||||
|
||||
/* ----------------
|
||||
* Set up handler for cancel-request signal, and
|
||||
* send this backend's cancellation info to the frontend.
|
||||
@ -1535,7 +1538,7 @@ PostgresMain(int argc, char *argv[], int real_argc, char *real_argv[])
|
||||
if (!IsUnderPostmaster)
|
||||
{
|
||||
puts("\nPOSTGRES backend interactive interface ");
|
||||
puts("$Revision: 1.97 $ $Date: 1999/01/18 00:09:56 $\n");
|
||||
puts("$Revision: 1.98 $ $Date: 1999/02/02 03:44:51 $\n");
|
||||
}
|
||||
|
||||
/* ----------------
|
||||
|
5
src/backend/utils/cache/Makefile
vendored
5
src/backend/utils/cache/Makefile
vendored
@ -4,7 +4,7 @@
|
||||
# Makefile for utils/cache
|
||||
#
|
||||
# IDENTIFICATION
|
||||
# $Header: /cvsroot/pgsql/src/backend/utils/cache/Makefile,v 1.9 1998/08/24 01:13:52 momjian Exp $
|
||||
# $Header: /cvsroot/pgsql/src/backend/utils/cache/Makefile,v 1.10 1999/02/02 03:44:54 momjian Exp $
|
||||
#
|
||||
#-------------------------------------------------------------------------
|
||||
|
||||
@ -13,7 +13,8 @@ include ../../../Makefile.global
|
||||
|
||||
CFLAGS += -I../..
|
||||
|
||||
OBJS = catcache.o inval.o rel.o relcache.o syscache.o lsyscache.o fcache.o
|
||||
OBJS = catcache.o inval.o rel.o relcache.o syscache.o lsyscache.o \
|
||||
fcache.o temprel.o
|
||||
|
||||
all: SUBSYS.o
|
||||
|
||||
|
3
src/backend/utils/cache/catcache.c
vendored
3
src/backend/utils/cache/catcache.c
vendored
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/utils/cache/catcache.c,v 1.36 1998/11/27 19:52:26 vadim Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/utils/cache/catcache.c,v 1.37 1999/02/02 03:44:58 momjian Exp $
|
||||
*
|
||||
* Notes:
|
||||
* XXX This needs to use exception.h to handle recovery when
|
||||
@ -196,7 +196,6 @@ CatalogCacheInitializeCache(struct catcache * cache,
|
||||
|
||||
if (cache->cc_key[i] > 0)
|
||||
{
|
||||
|
||||
/*
|
||||
* Yoiks. The implementation of the hashing code and the
|
||||
* implementation of int28's are at loggerheads. The right
|
||||
|
45
src/backend/utils/cache/inval.c
vendored
45
src/backend/utils/cache/inval.c
vendored
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/utils/cache/inval.c,v 1.18 1998/11/27 19:52:28 vadim Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/utils/cache/inval.c,v 1.19 1999/02/02 03:45:01 momjian Exp $
|
||||
*
|
||||
* Note - this code is real crufty...
|
||||
*
|
||||
@ -20,6 +20,7 @@
|
||||
#include "access/heapam.h" /* XXX to support hacks below */
|
||||
#include "access/htup.h"
|
||||
#include "catalog/catalog.h"
|
||||
#include "catalog/heap.h"
|
||||
#include "storage/bufpage.h"
|
||||
#include "storage/buf.h" /* XXX for InvalidBuffer */
|
||||
#include "storage/ipc.h"
|
||||
@ -244,31 +245,17 @@ RelationIdRegisterLocalInvalid(Oid relationId, Oid objectId)
|
||||
static void
|
||||
getmyrelids()
|
||||
{
|
||||
HeapTuple tuple;
|
||||
MyRelationRelationId = RelnameFindRelid(RelationRelationName);
|
||||
Assert(RelationRelationName != InvalidOid);
|
||||
|
||||
tuple = SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(RelationRelationName),
|
||||
0, 0, 0);
|
||||
Assert(HeapTupleIsValid(tuple));
|
||||
MyRelationRelationId = tuple->t_data->t_oid;
|
||||
MyAttributeRelationId = RelnameFindRelid(AttributeRelationName);
|
||||
Assert(AttributeRelationName != InvalidOid);
|
||||
|
||||
tuple = SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(AttributeRelationName),
|
||||
0, 0, 0);
|
||||
Assert(HeapTupleIsValid(tuple));
|
||||
MyAttributeRelationId = tuple->t_data->t_oid;
|
||||
MyAMRelationId = RelnameFindRelid(AccessMethodRelationName);
|
||||
Assert(MyAMRelationId != InvalidOid);
|
||||
|
||||
tuple = SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(AccessMethodRelationName),
|
||||
0, 0, 0);
|
||||
Assert(HeapTupleIsValid(tuple));
|
||||
MyAMRelationId = tuple->t_data->t_oid;
|
||||
|
||||
tuple = SearchSysCacheTuple(RELNAME,
|
||||
PointerGetDatum(AccessMethodOperatorRelationName),
|
||||
0, 0, 0);
|
||||
Assert(HeapTupleIsValid(tuple));
|
||||
MyAMOPRelationId = tuple->t_data->t_oid;
|
||||
MyAMOPRelationId = RelnameFindRelid(AccessMethodOperatorRelationName);
|
||||
Assert(MyAMOPRelationId != InvalidOid);
|
||||
}
|
||||
|
||||
/* --------------------------------
|
||||
@ -614,10 +601,6 @@ RelationInvalidateHeapTuple(Relation relation, HeapTuple tuple)
|
||||
*/
|
||||
RelationInvalidateHeapTuple_DEBUG1;
|
||||
|
||||
/* ----------------
|
||||
*
|
||||
* ----------------
|
||||
*/
|
||||
RelationInvalidateCatalogCacheTuple(relation,
|
||||
tuple,
|
||||
CacheIdRegisterLocalInvalid);
|
||||
@ -625,12 +608,4 @@ RelationInvalidateHeapTuple(Relation relation, HeapTuple tuple)
|
||||
RelationInvalidateRelationCache(relation,
|
||||
tuple,
|
||||
RelationIdRegisterLocalInvalid);
|
||||
|
||||
#ifdef NOT_USED
|
||||
if (RefreshWhenInvalidate)
|
||||
/* what does this do? bjm 1998/08/20 */
|
||||
RelationInvalidateCatalogCacheTuple(relation,
|
||||
tuple,
|
||||
(void (*) ()) NULL);
|
||||
#endif
|
||||
}
|
||||
|
92
src/backend/utils/cache/relcache.c
vendored
92
src/backend/utils/cache/relcache.c
vendored
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/utils/cache/relcache.c,v 1.55 1999/01/22 18:47:37 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/utils/cache/relcache.c,v 1.56 1999/02/02 03:45:02 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -404,7 +404,7 @@ scan_pg_rel_ind(RelationBuildDescInfo buildinfo)
|
||||
switch (buildinfo.infotype)
|
||||
{
|
||||
case INFO_RELID:
|
||||
return_tuple = ClassOidIndexScan(pg_class_desc, buildinfo.i.info_id);
|
||||
return_tuple = ClassOidIndexScan(pg_class_desc,buildinfo.i.info_id);
|
||||
break;
|
||||
|
||||
case INFO_RELNAME:
|
||||
@ -821,7 +821,6 @@ RelationBuildDesc(RelationBuildDescInfo buildinfo)
|
||||
*/
|
||||
if (!HeapTupleIsValid(pg_class_tuple))
|
||||
{
|
||||
|
||||
MemoryContextSwitchTo(oldcxt);
|
||||
|
||||
return NULL;
|
||||
@ -867,8 +866,7 @@ RelationBuildDesc(RelationBuildDescInfo buildinfo)
|
||||
*/
|
||||
if (OidIsValid(relam))
|
||||
{
|
||||
relation->rd_am = (Form_pg_am)
|
||||
AccessMethodObjectIdGetForm(relam);
|
||||
relation->rd_am = (Form_pg_am) AccessMethodObjectIdGetForm(relam);
|
||||
}
|
||||
|
||||
/* ----------------
|
||||
@ -927,7 +925,6 @@ RelationBuildDesc(RelationBuildDescInfo buildinfo)
|
||||
* restore memory context and return the new reldesc.
|
||||
* ----------------
|
||||
*/
|
||||
|
||||
RelationCacheInsert(relation);
|
||||
|
||||
/* -------------------
|
||||
@ -1197,8 +1194,7 @@ RelationIdGetRelation(Oid relationId)
|
||||
buildinfo.i.info_id = relationId;
|
||||
|
||||
rd = RelationBuildDesc(buildinfo);
|
||||
return
|
||||
rd;
|
||||
return rd;
|
||||
}
|
||||
|
||||
/* --------------------------------
|
||||
@ -1332,8 +1328,9 @@ RelationFlushRelation(Relation *relationPtr,
|
||||
|
||||
/* --------------------------------
|
||||
* RelationForgetRelation -
|
||||
* RelationFlushRelation + if the relation is local then get rid of
|
||||
* the relation descriptor from the newly created relation list.
|
||||
* RelationFlushRelation + if the relation is myxactonly then
|
||||
* get rid of the relation descriptor from the newly created
|
||||
* relation list.
|
||||
* --------------------------------
|
||||
*/
|
||||
void
|
||||
@ -1342,37 +1339,39 @@ RelationForgetRelation(Oid rid)
|
||||
Relation relation;
|
||||
|
||||
RelationIdCacheLookup(rid, relation);
|
||||
Assert(PointerIsValid(relation));
|
||||
|
||||
if (relation->rd_islocal)
|
||||
if (PointerIsValid(relation))
|
||||
{
|
||||
MemoryContext oldcxt;
|
||||
List *curr;
|
||||
List *prev = NIL;
|
||||
|
||||
oldcxt = MemoryContextSwitchTo((MemoryContext) CacheCxt);
|
||||
|
||||
foreach(curr, newlyCreatedRelns)
|
||||
if (relation->rd_myxactonly)
|
||||
{
|
||||
Relation reln = lfirst(curr);
|
||||
|
||||
Assert(reln != NULL && reln->rd_islocal);
|
||||
if (RelationGetRelid(reln) == rid)
|
||||
break;
|
||||
prev = curr;
|
||||
MemoryContext oldcxt;
|
||||
List *curr;
|
||||
List *prev = NIL;
|
||||
|
||||
oldcxt = MemoryContextSwitchTo((MemoryContext) CacheCxt);
|
||||
|
||||
foreach(curr, newlyCreatedRelns)
|
||||
{
|
||||
Relation reln = lfirst(curr);
|
||||
|
||||
Assert(reln != NULL && reln->rd_myxactonly);
|
||||
if (RelationGetRelid(reln) == rid)
|
||||
break;
|
||||
prev = curr;
|
||||
}
|
||||
if (curr == NIL)
|
||||
elog(FATAL, "Local relation %s not found in list",
|
||||
(RelationGetRelationName(relation))->data);
|
||||
if (prev == NIL)
|
||||
newlyCreatedRelns = lnext(newlyCreatedRelns);
|
||||
else
|
||||
lnext(prev) = lnext(curr);
|
||||
pfree(curr);
|
||||
MemoryContextSwitchTo(oldcxt);
|
||||
}
|
||||
if (curr == NIL)
|
||||
elog(FATAL, "Local relation %s not found in list",
|
||||
(RelationGetRelationName(relation))->data);
|
||||
if (prev == NIL)
|
||||
newlyCreatedRelns = lnext(newlyCreatedRelns);
|
||||
else
|
||||
lnext(prev) = lnext(curr);
|
||||
pfree(curr);
|
||||
MemoryContextSwitchTo(oldcxt);
|
||||
|
||||
RelationFlushRelation(&relation, false);
|
||||
}
|
||||
|
||||
RelationFlushRelation(&relation, false);
|
||||
}
|
||||
|
||||
/* --------------------------------
|
||||
@ -1393,9 +1392,8 @@ RelationIdInvalidateRelationCacheByRelationId(Oid relationId)
|
||||
* BufferSync also? But I'll leave it for now since I don't want to
|
||||
* break anything.) - ay 3/95
|
||||
*/
|
||||
if (PointerIsValid(relation) && !relation->rd_islocal)
|
||||
if (PointerIsValid(relation) && !relation->rd_myxactonly)
|
||||
{
|
||||
|
||||
/*
|
||||
* The boolean onlyFlushReferenceCountZero in RelationFlushReln()
|
||||
* should be set to true when we are incrementing the command
|
||||
@ -1502,13 +1500,13 @@ RelationRegisterRelation(Relation relation)
|
||||
|
||||
/*
|
||||
* we've just created the relation. It is invisible to anyone else
|
||||
* before the transaction is committed. Setting rd_islocal allows us
|
||||
* before the transaction is committed. Setting rd_myxactonly allows us
|
||||
* to use the local buffer manager for select/insert/etc before the
|
||||
* end of transaction. (We also need to keep track of relations
|
||||
* created during a transaction and does the necessary clean up at the
|
||||
* end of the transaction.) - ay 3/95
|
||||
*/
|
||||
relation->rd_islocal = TRUE;
|
||||
relation->rd_myxactonly = TRUE;
|
||||
newlyCreatedRelns = lcons(relation, newlyCreatedRelns);
|
||||
|
||||
MemoryContextSwitchTo(oldcxt);
|
||||
@ -1516,7 +1514,7 @@ RelationRegisterRelation(Relation relation)
|
||||
|
||||
/*
|
||||
* RelationPurgeLocalRelation -
|
||||
* find all the Relation descriptors marked rd_islocal and reset them.
|
||||
* find all the Relation descriptors marked rd_myxactonly and reset them.
|
||||
* This should be called at the end of a transaction (commit/abort) when
|
||||
* the "local" relations will become visible to others and the multi-user
|
||||
* buffer pool should be used.
|
||||
@ -1536,7 +1534,7 @@ RelationPurgeLocalRelation(bool xactCommitted)
|
||||
List *l = newlyCreatedRelns;
|
||||
Relation reln = lfirst(l);
|
||||
|
||||
Assert(reln != NULL && reln->rd_islocal);
|
||||
Assert(reln != NULL && reln->rd_myxactonly);
|
||||
|
||||
if (!xactCommitted)
|
||||
{
|
||||
@ -1545,18 +1543,18 @@ RelationPurgeLocalRelation(bool xactCommitted)
|
||||
* remove the file if we abort. This is so that files for
|
||||
* tables created inside a transaction block get removed.
|
||||
*/
|
||||
if (reln->rd_istemp)
|
||||
if (reln->rd_isnoname)
|
||||
{
|
||||
if (!(reln->rd_tmpunlinked))
|
||||
if (!(reln->rd_nonameunlinked))
|
||||
{
|
||||
smgrunlink(DEFAULT_SMGR, reln);
|
||||
reln->rd_tmpunlinked = TRUE;
|
||||
reln->rd_nonameunlinked = TRUE;
|
||||
}
|
||||
}
|
||||
else
|
||||
smgrunlink(DEFAULT_SMGR, reln);
|
||||
}
|
||||
else if (!IsBootstrapProcessingMode() && !(reln->rd_istemp))
|
||||
else if (!IsBootstrapProcessingMode() && !(reln->rd_isnoname))
|
||||
|
||||
/*
|
||||
* RelationFlushRelation () below will flush relation
|
||||
@ -1568,7 +1566,7 @@ RelationPurgeLocalRelation(bool xactCommitted)
|
||||
*/
|
||||
smgrclose(DEFAULT_SMGR, reln);
|
||||
|
||||
reln->rd_islocal = FALSE;
|
||||
reln->rd_myxactonly = FALSE;
|
||||
|
||||
if (!IsBootstrapProcessingMode())
|
||||
RelationFlushRelation(&reln, FALSE);
|
||||
|
165
src/backend/utils/cache/temprel.c
vendored
Normal file
165
src/backend/utils/cache/temprel.c
vendored
Normal file
@ -0,0 +1,165 @@
|
||||
/*-------------------------------------------------------------------------
|
||||
*
|
||||
* temprel.c--
|
||||
* POSTGRES temporary relation handling
|
||||
*
|
||||
* Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/utils/cache/Attic/temprel.c,v 1.1 1999/02/02 03:45:03 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
|
||||
/*
|
||||
* This implements temp tables by modifying the relname cache lookups
|
||||
* of pg_class.
|
||||
* When a temp table is created, a linked list of temp table tuples is
|
||||
* stored here. When a relname cache lookup is done, references to user-named
|
||||
* temp tables are converted to the internal temp table names.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "postgres.h"
|
||||
#include "miscadmin.h"
|
||||
#include "nodes/pg_list.h"
|
||||
#include "utils/mcxt.h"
|
||||
#include "utils/temprel.h"
|
||||
#include "access/htup.h"
|
||||
#include "access/heapam.h"
|
||||
#include "catalog/heap.h"
|
||||
#include "catalog/index.h"
|
||||
#include "catalog/pg_class.h"
|
||||
|
||||
GlobalMemory CacheCxt;
|
||||
|
||||
/* ----------------
|
||||
* global variables
|
||||
* ----------------
|
||||
*/
|
||||
|
||||
static List *temp_rels = NIL;
|
||||
|
||||
typedef struct TempTable
|
||||
{
|
||||
char *user_relname;
|
||||
HeapTuple pg_class_tuple;
|
||||
} TempTable;
|
||||
|
||||
|
||||
void
|
||||
create_temp_relation(char *relname, HeapTuple pg_class_tuple)
|
||||
{
|
||||
MemoryContext oldcxt;
|
||||
TempTable *temp_rel;
|
||||
|
||||
oldcxt = MemoryContextSwitchTo((MemoryContext) CacheCxt);
|
||||
|
||||
temp_rel = palloc(sizeof(TempTable));
|
||||
temp_rel->user_relname = palloc(NAMEDATALEN);
|
||||
|
||||
/* save user-supplied name */
|
||||
strcpy(temp_rel->user_relname, relname);
|
||||
|
||||
temp_rel->pg_class_tuple = heap_copytuple(pg_class_tuple);
|
||||
|
||||
temp_rels = lcons(temp_rel, temp_rels);
|
||||
|
||||
MemoryContextSwitchTo(oldcxt);
|
||||
}
|
||||
|
||||
void
|
||||
remove_all_temp_relations(void)
|
||||
{
|
||||
List *l, *next;
|
||||
|
||||
l = temp_rels;
|
||||
while (l != NIL)
|
||||
{
|
||||
TempTable *temp_rel = lfirst(l);
|
||||
Form_pg_class classtuple;
|
||||
|
||||
classtuple = (Form_pg_class)GETSTRUCT(temp_rel->pg_class_tuple);
|
||||
|
||||
next = lnext(l); /* do this first, l is deallocated */
|
||||
|
||||
if (classtuple->relkind != RELKIND_INDEX)
|
||||
{
|
||||
char relname[NAMEDATALEN];
|
||||
|
||||
/* safe from deallocation */
|
||||
strcpy(relname, temp_rel->user_relname);
|
||||
heap_destroy_with_catalog(relname);
|
||||
}
|
||||
else
|
||||
index_destroy(temp_rel->pg_class_tuple->t_data->t_oid);
|
||||
|
||||
l = next;
|
||||
}
|
||||
}
|
||||
|
||||
/* we don't have the relname for indexes, so we just pass the oid */
|
||||
void
|
||||
remove_temp_relation(Oid relid)
|
||||
{
|
||||
|
||||
MemoryContext oldcxt;
|
||||
List *l, *prev;
|
||||
|
||||
oldcxt = MemoryContextSwitchTo((MemoryContext) CacheCxt);
|
||||
|
||||
prev = NIL;
|
||||
l = temp_rels;
|
||||
while (l != NIL)
|
||||
{
|
||||
TempTable *temp_rel = lfirst(l);
|
||||
|
||||
if (temp_rel->pg_class_tuple->t_data->t_oid == relid)
|
||||
{
|
||||
pfree(temp_rel->user_relname);
|
||||
pfree(temp_rel->pg_class_tuple);
|
||||
pfree(temp_rel);
|
||||
/* remove from linked list */
|
||||
if (prev != NIL)
|
||||
{
|
||||
lnext(prev) = lnext(l);
|
||||
pfree(l);
|
||||
l = lnext(prev);
|
||||
}
|
||||
else
|
||||
{
|
||||
temp_rels = lnext(l);
|
||||
pfree(l);
|
||||
l = temp_rels;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
prev = l;
|
||||
l = lnext(l);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
MemoryContextSwitchTo(oldcxt);
|
||||
}
|
||||
|
||||
HeapTuple
|
||||
get_temp_rel_by_name(char *user_relname)
|
||||
{
|
||||
List *l;
|
||||
|
||||
foreach(l, temp_rels)
|
||||
{
|
||||
TempTable *temp_rel = lfirst(l);
|
||||
|
||||
if (strcmp(temp_rel->user_relname, user_relname) == 0)
|
||||
return temp_rel->pg_class_tuple;
|
||||
}
|
||||
return NULL;
|
||||
}
|
@ -7,7 +7,7 @@
|
||||
*
|
||||
*
|
||||
* IDENTIFICATION
|
||||
* $Header: /cvsroot/pgsql/src/backend/utils/init/Attic/enbl.c,v 1.4 1998/09/01 03:26:49 momjian Exp $
|
||||
* $Header: /cvsroot/pgsql/src/backend/utils/init/Attic/enbl.c,v 1.5 1999/02/02 03:45:04 momjian Exp $
|
||||
*
|
||||
*-------------------------------------------------------------------------
|
||||
*/
|
||||
@ -38,7 +38,7 @@ BypassEnable(int *enableCountInOutP, bool on)
|
||||
return (bool) (*enableCountInOutP >= 2);
|
||||
}
|
||||
|
||||
AssertState(*enableCountInOutP >= 1);
|
||||
Assert(*enableCountInOutP >= 1);
|
||||
|
||||
*enableCountInOutP -= 1;
|
||||
|
||||
|
@ -4,7 +4,7 @@
|
||||
*
|
||||
* Copyright (c) 1994, Regents of the University of California
|
||||
*
|
||||
* $Id: psort.c,v 1.47 1999/01/17 06:19:02 momjian Exp $
|
||||
* $Id: psort.c,v 1.48 1999/02/02 03:45:12 momjian Exp $
|
||||
*
|
||||
* NOTES
|
||||
* Sorts the first relation into the second relation.
|
||||
@ -1019,9 +1019,8 @@ gettape()
|
||||
|
||||
tp = (struct tapelst *) palloc((unsigned) sizeof(struct tapelst));
|
||||
|
||||
snprintf(uniqueName, MAXPGPATH - 1, "%spg_psort.%d.%d",
|
||||
TEMPDIR, (int) MyProcPid, uniqueFileId);
|
||||
uniqueFileId++;
|
||||
snprintf(uniqueName, MAXPGPATH - 1, "%spg_psort.%d.%u",
|
||||
TEMPDIR, (int) MyProcPid, uniqueFileId++);
|
||||
|
||||
tapeinit = 1;
|
||||
|
||||
|
Reference in New Issue
Block a user