mirror of
https://github.com/postgres/postgres.git
synced 2025-07-27 12:41:57 +03:00
Invalidate temp entries for aborted transactions.
This commit is contained in:
@ -7,7 +7,7 @@
|
|||||||
*
|
*
|
||||||
*
|
*
|
||||||
* IDENTIFICATION
|
* IDENTIFICATION
|
||||||
* $Header: /cvsroot/pgsql/src/backend/access/transam/xact.c,v 1.48 1999/09/04 18:42:15 tgl Exp $
|
* $Header: /cvsroot/pgsql/src/backend/access/transam/xact.c,v 1.49 1999/09/04 19:55:48 momjian Exp $
|
||||||
*
|
*
|
||||||
* NOTES
|
* NOTES
|
||||||
* Transaction aborts can now occur two ways:
|
* Transaction aborts can now occur two ways:
|
||||||
@ -151,6 +151,7 @@
|
|||||||
#include "commands/vacuum.h"
|
#include "commands/vacuum.h"
|
||||||
#include "libpq/be-fsstubs.h"
|
#include "libpq/be-fsstubs.h"
|
||||||
#include "storage/proc.h"
|
#include "storage/proc.h"
|
||||||
|
#include "utils/temprel.h"
|
||||||
#include "utils/inval.h"
|
#include "utils/inval.h"
|
||||||
#include "utils/portal.h"
|
#include "utils/portal.h"
|
||||||
#include "utils/relcache.h"
|
#include "utils/relcache.h"
|
||||||
@ -1022,6 +1023,7 @@ AbortTransaction()
|
|||||||
RecordTransactionAbort();
|
RecordTransactionAbort();
|
||||||
RelationPurgeLocalRelation(false);
|
RelationPurgeLocalRelation(false);
|
||||||
DestroyNoNameRels();
|
DestroyNoNameRels();
|
||||||
|
invalidate_temp_relations();
|
||||||
AtEOXact_nbtree();
|
AtEOXact_nbtree();
|
||||||
AtAbort_Cache();
|
AtAbort_Cache();
|
||||||
AtAbort_Locks();
|
AtAbort_Locks();
|
||||||
|
@ -8,7 +8,7 @@
|
|||||||
*
|
*
|
||||||
*
|
*
|
||||||
* IDENTIFICATION
|
* IDENTIFICATION
|
||||||
* $Header: /cvsroot/pgsql/src/backend/catalog/indexing.c,v 1.42 1999/07/20 17:14:06 momjian Exp $
|
* $Header: /cvsroot/pgsql/src/backend/catalog/indexing.c,v 1.43 1999/09/04 19:55:49 momjian Exp $
|
||||||
*
|
*
|
||||||
*-------------------------------------------------------------------------
|
*-------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
@ -449,13 +449,14 @@ ClassNameIndexScan(Relation heapRelation, char *relName)
|
|||||||
Relation idesc;
|
Relation idesc;
|
||||||
ScanKeyData skey[1];
|
ScanKeyData skey[1];
|
||||||
HeapTuple tuple;
|
HeapTuple tuple;
|
||||||
|
char *hold_rel;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* we have to do this before looking in system tables because temp
|
* we have to do this before looking in system tables because temp
|
||||||
* table namespace takes precedence
|
* table namespace takes precedence
|
||||||
*/
|
*/
|
||||||
if ((tuple = get_temp_rel_by_name(relName)) != NULL)
|
if ((hold_rel = get_temp_rel_by_name(relName)) != NULL)
|
||||||
return heap_copytuple(tuple);
|
relName = hold_rel;
|
||||||
|
|
||||||
ScanKeyEntryInitialize(&skey[0],
|
ScanKeyEntryInitialize(&skey[0],
|
||||||
(bits16) 0x0,
|
(bits16) 0x0,
|
||||||
|
78
src/backend/utils/cache/temprel.c
vendored
78
src/backend/utils/cache/temprel.c
vendored
@ -7,7 +7,7 @@
|
|||||||
*
|
*
|
||||||
*
|
*
|
||||||
* IDENTIFICATION
|
* IDENTIFICATION
|
||||||
* $Header: /cvsroot/pgsql/src/backend/utils/cache/Attic/temprel.c,v 1.10 1999/07/17 20:18:02 momjian Exp $
|
* $Header: /cvsroot/pgsql/src/backend/utils/cache/Attic/temprel.c,v 1.11 1999/09/04 19:55:50 momjian Exp $
|
||||||
*
|
*
|
||||||
*-------------------------------------------------------------------------
|
*-------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
@ -18,13 +18,13 @@
|
|||||||
* When a temp table is created, a linked list of temp table tuples is
|
* 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
|
* stored here. When a relname cache lookup is done, references to user-named
|
||||||
* temp tables are converted to the internal temp table names.
|
* temp tables are converted to the internal temp table names.
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
|
|
||||||
#include "postgres.h"
|
#include "postgres.h"
|
||||||
#include "access/heapam.h"
|
#include "access/heapam.h"
|
||||||
|
#include "access/xact.h"
|
||||||
#include "catalog/heap.h"
|
#include "catalog/heap.h"
|
||||||
#include "catalog/index.h"
|
#include "catalog/index.h"
|
||||||
#include "utils/temprel.h"
|
#include "utils/temprel.h"
|
||||||
@ -41,7 +41,10 @@ static List *temp_rels = NIL;
|
|||||||
typedef struct TempTable
|
typedef struct TempTable
|
||||||
{
|
{
|
||||||
char *user_relname;
|
char *user_relname;
|
||||||
HeapTuple pg_class_tuple;
|
char *relname;
|
||||||
|
Oid relid;
|
||||||
|
char relkind;
|
||||||
|
TransactionId xid;
|
||||||
} TempTable;
|
} TempTable;
|
||||||
|
|
||||||
|
|
||||||
@ -55,11 +58,15 @@ create_temp_relation(char *relname, HeapTuple pg_class_tuple)
|
|||||||
|
|
||||||
temp_rel = palloc(sizeof(TempTable));
|
temp_rel = palloc(sizeof(TempTable));
|
||||||
temp_rel->user_relname = palloc(NAMEDATALEN);
|
temp_rel->user_relname = palloc(NAMEDATALEN);
|
||||||
|
temp_rel->relname = palloc(NAMEDATALEN);
|
||||||
|
|
||||||
/* save user-supplied name */
|
/* save user-supplied name */
|
||||||
strcpy(temp_rel->user_relname, relname);
|
strcpy(temp_rel->user_relname, relname);
|
||||||
|
StrNCpy(temp_rel->relname, ((Form_pg_class)
|
||||||
temp_rel->pg_class_tuple = heap_copytuple(pg_class_tuple);
|
GETSTRUCT(pg_class_tuple))->relname.data, NAMEDATALEN);
|
||||||
|
temp_rel->relid = pg_class_tuple->t_data->t_oid;
|
||||||
|
temp_rel->relkind = ((Form_pg_class) GETSTRUCT(pg_class_tuple))->relkind;
|
||||||
|
temp_rel->xid = GetCurrentTransactionId();
|
||||||
|
|
||||||
temp_rels = lcons(temp_rel, temp_rels);
|
temp_rels = lcons(temp_rel, temp_rels);
|
||||||
|
|
||||||
@ -79,13 +86,10 @@ remove_all_temp_relations(void)
|
|||||||
while (l != NIL)
|
while (l != NIL)
|
||||||
{
|
{
|
||||||
TempTable *temp_rel = lfirst(l);
|
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 */
|
next = lnext(l); /* do this first, l is deallocated */
|
||||||
|
|
||||||
if (classtuple->relkind != RELKIND_INDEX)
|
if (temp_rel->relkind != RELKIND_INDEX)
|
||||||
{
|
{
|
||||||
char relname[NAMEDATALEN];
|
char relname[NAMEDATALEN];
|
||||||
|
|
||||||
@ -94,7 +98,7 @@ remove_all_temp_relations(void)
|
|||||||
heap_destroy_with_catalog(relname);
|
heap_destroy_with_catalog(relname);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
index_destroy(temp_rel->pg_class_tuple->t_data->t_oid);
|
index_destroy(temp_rel->relid);
|
||||||
|
|
||||||
l = next;
|
l = next;
|
||||||
}
|
}
|
||||||
@ -118,10 +122,10 @@ remove_temp_relation(Oid relid)
|
|||||||
{
|
{
|
||||||
TempTable *temp_rel = lfirst(l);
|
TempTable *temp_rel = lfirst(l);
|
||||||
|
|
||||||
if (temp_rel->pg_class_tuple->t_data->t_oid == relid)
|
if (temp_rel->relid == relid)
|
||||||
{
|
{
|
||||||
pfree(temp_rel->user_relname);
|
pfree(temp_rel->user_relname);
|
||||||
pfree(temp_rel->pg_class_tuple);
|
pfree(temp_rel->relname);
|
||||||
pfree(temp_rel);
|
pfree(temp_rel);
|
||||||
/* remove from linked list */
|
/* remove from linked list */
|
||||||
if (prev != NIL)
|
if (prev != NIL)
|
||||||
@ -148,7 +152,53 @@ remove_temp_relation(Oid relid)
|
|||||||
MemoryContextSwitchTo(oldcxt);
|
MemoryContextSwitchTo(oldcxt);
|
||||||
}
|
}
|
||||||
|
|
||||||
HeapTuple
|
/* remove entries from aborted transactions */
|
||||||
|
void
|
||||||
|
invalidate_temp_relations(void)
|
||||||
|
{
|
||||||
|
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->xid == GetCurrentTransactionId())
|
||||||
|
{
|
||||||
|
pfree(temp_rel->user_relname);
|
||||||
|
pfree(temp_rel->relname);
|
||||||
|
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);
|
||||||
|
}
|
||||||
|
|
||||||
|
char *
|
||||||
get_temp_rel_by_name(char *user_relname)
|
get_temp_rel_by_name(char *user_relname)
|
||||||
{
|
{
|
||||||
List *l;
|
List *l;
|
||||||
@ -158,7 +208,7 @@ get_temp_rel_by_name(char *user_relname)
|
|||||||
TempTable *temp_rel = lfirst(l);
|
TempTable *temp_rel = lfirst(l);
|
||||||
|
|
||||||
if (strcmp(temp_rel->user_relname, user_relname) == 0)
|
if (strcmp(temp_rel->user_relname, user_relname) == 0)
|
||||||
return temp_rel->pg_class_tuple;
|
return temp_rel->relname;
|
||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
@ -6,7 +6,7 @@
|
|||||||
*
|
*
|
||||||
* Copyright (c) 1994, Regents of the University of California
|
* Copyright (c) 1994, Regents of the University of California
|
||||||
*
|
*
|
||||||
* $Id: temprel.h,v 1.4 1999/07/15 15:21:43 momjian Exp $
|
* $Id: temprel.h,v 1.5 1999/09/04 19:55:50 momjian Exp $
|
||||||
*
|
*
|
||||||
*-------------------------------------------------------------------------
|
*-------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
@ -17,7 +17,8 @@
|
|||||||
|
|
||||||
void create_temp_relation(char *relname, HeapTuple pg_class_tuple);
|
void create_temp_relation(char *relname, HeapTuple pg_class_tuple);
|
||||||
void remove_all_temp_relations(void);
|
void remove_all_temp_relations(void);
|
||||||
|
void invalidate_temp_relations(void);
|
||||||
void remove_temp_relation(Oid relid);
|
void remove_temp_relation(Oid relid);
|
||||||
HeapTuple get_temp_rel_by_name(char *user_relname);
|
char *get_temp_rel_by_name(char *user_relname);
|
||||||
|
|
||||||
#endif /* TEMPREL_H */
|
#endif /* TEMPREL_H */
|
||||||
|
Reference in New Issue
Block a user