Skip to content

Commit

Permalink
Add temp OID support for type, index, and constraint creation (#335)
Browse files Browse the repository at this point in the history
Normal OIDs were still being consumed in some cases during temp table creation even with temp oid buffer on. To fix this, ensure that the appropriate temp table dependent objects also use temp OID.

- Redirect type creation functions to use temp OID when it's a TSQL temp table.
- Redirect constraint creation to use temp OID in those cases as well.
- Remove workaround for indexes on temp tables. Previously, we needed to force indexes on temp tables to consume normal OIDs. With changes described in lines 1+2 above, we can now remove the workaround added in OID Wraparound #232 and properly allow indexes to use temp oid buffer.

Task: BABEL-4750
Signed-off-by: Tim Chang <[email protected]>
  • Loading branch information
timchang514 authored Sep 24, 2024
1 parent 0cfa922 commit 2e1527b
Show file tree
Hide file tree
Showing 9 changed files with 64 additions and 16 deletions.
4 changes: 2 additions & 2 deletions src/backend/catalog/catalog.c
Original file line number Diff line number Diff line change
Expand Up @@ -540,7 +540,7 @@ GetNewOidWithIndex(Relation relation, Oid indexId, AttrNumber oidcolumn)
* created by bootstrap have preassigned OIDs, so there's no need.
*/
RelFileNumber
GetNewRelFileNumber(Oid reltablespace, Relation pg_class, char relpersistence, bool override_temp)
GetNewRelFileNumber(Oid reltablespace, Relation pg_class, char relpersistence)
{
RelFileLocatorBackend rlocator;
char *rpath;
Expand Down Expand Up @@ -584,7 +584,7 @@ GetNewRelFileNumber(Oid reltablespace, Relation pg_class, char relpersistence, b
rlocator.backend = backend;

use_bbf_oid_buffer = (relpersistence == RELPERSISTENCE_TEMP && sql_dialect == SQL_DIALECT_TSQL
&& GetNewTempOidWithIndex_hook && temp_oid_buffer_size > 0 && !override_temp);
&& GetNewTempOidWithIndex_hook && temp_oid_buffer_size > 0);

do
{
Expand Down
28 changes: 26 additions & 2 deletions src/backend/catalog/heap.c
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,7 @@
#include "storage/predicate.h"
#include "utils/builtins.h"
#include "utils/fmgroids.h"
#include "utils/guc.h"
#include "utils/inval.h"
#include "utils/lsyscache.h"
#include "utils/syscache.h"
Expand Down Expand Up @@ -1310,7 +1311,7 @@ heap_create_with_catalog(const char *relname,

if (!OidIsValid(relid))
relid = GetNewRelFileNumber(reltablespace, pg_class_desc,
relpersistence, false);
relpersistence);
}

/*
Expand Down Expand Up @@ -1409,8 +1410,31 @@ heap_create_with_catalog(const char *relname,
/*
* We'll make an array over the composite type, too. For largely
* historical reasons, the array type's OID is assigned first.
*
* For temp tables, we use temp OID assignment code here as well.
*/
new_array_oid = AssignTypeArrayOid();
if (is_enr && useTempOidBuffer())
{
Relation pg_type;

/* We should not be creating TSQL Temp Tables in pg_upgrade. */
Assert(!IsBinaryUpgrade);

pg_type = table_open(TypeRelationId, AccessShareLock);
new_array_oid = GetNewTempOidWithIndex_hook(pg_type, TypeOidIndexId, Anum_pg_type_oid);

Assert(!OidIsValid(reltypeid));

/*
* We also assign reltypeid here. It would usually be assigned during AddNewRelationType
* if the value provided is InvalidOid. Since we are providing a value, it won't
* try to call GetNewOidWithIndex.
*/
reltypeid = GetNewTempOidWithIndex_hook(pg_type, TypeOidIndexId, Anum_pg_type_oid);
table_close(pg_type, AccessShareLock);
}
else
new_array_oid = AssignTypeArrayOid();

/*
* Make the pg_type entry for the composite type. The OID of the
Expand Down
7 changes: 1 addition & 6 deletions src/backend/catalog/index.c
Original file line number Diff line number Diff line change
Expand Up @@ -962,12 +962,7 @@ index_create(Relation heapRelation,
}
else
{
/*
* Index OIDs must be kept in normal OID range due to deletion issues.
* Since deletion is sorted by OID, adding indexes to temp OID range
* causes deletion order issues.
*/
indexRelationId = GetNewRelFileNumber(tableSpaceId, pg_class, relpersistence, is_enr);
indexRelationId = GetNewRelFileNumber(tableSpaceId, pg_class, relpersistence);
}
}

Expand Down
12 changes: 10 additions & 2 deletions src/backend/catalog/pg_constraint.c
Original file line number Diff line number Diff line change
Expand Up @@ -22,16 +22,20 @@
#include "catalog/catalog.h"
#include "catalog/dependency.h"
#include "catalog/indexing.h"
#include "catalog/namespace.h"
#include "catalog/objectaccess.h"
#include "catalog/pg_constraint.h"
#include "catalog/pg_operator.h"
#include "catalog/pg_type.h"
#include "commands/defrem.h"
#include "commands/tablecmds.h"
#include "parser/parser.h"
#include "utils/array.h"
#include "utils/builtins.h"
#include "utils/fmgroids.h"
#include "utils/guc.h"
#include "utils/lsyscache.h"
#include "utils/queryenvironment.h"
#include "utils/rel.h"
#include "utils/syscache.h"

Expand Down Expand Up @@ -172,8 +176,12 @@ CreateConstraintEntry(const char *constraintName,
values[i] = (Datum) NULL;
}

conOid = GetNewOidWithIndex(conDesc, ConstraintOidIndexId,
Anum_pg_constraint_oid);
if (useTempOidBufferForOid(relId) && isTempNamespace(constraintNamespace))
conOid = GetNewTempOidWithIndex_hook(conDesc, ConstraintOidIndexId,
Anum_pg_constraint_oid);
else
conOid = GetNewOidWithIndex(conDesc, ConstraintOidIndexId,
Anum_pg_constraint_oid);
values[Anum_pg_constraint_oid - 1] = ObjectIdGetDatum(conOid);
values[Anum_pg_constraint_conname - 1] = NameGetDatum(&cname);
values[Anum_pg_constraint_connamespace - 1] = ObjectIdGetDatum(constraintNamespace);
Expand Down
2 changes: 1 addition & 1 deletion src/backend/commands/tablecmds.c
Original file line number Diff line number Diff line change
Expand Up @@ -14707,7 +14707,7 @@ ATExecSetTableSpace(Oid tableOid, Oid newTableSpace, LOCKMODE lockmode)
* need to allocate a new one in the new tablespace.
*/
newrelfilenumber = GetNewRelFileNumber(newTableSpace, NULL,
rel->rd_rel->relpersistence, false);
rel->rd_rel->relpersistence);

/* Open old and new relation */
newrlocator = rel->rd_locator;
Expand Down
2 changes: 1 addition & 1 deletion src/backend/utils/cache/relcache.c
Original file line number Diff line number Diff line change
Expand Up @@ -3722,7 +3722,7 @@ RelationSetNewRelfilenumber(Relation relation, char persistence)
{
/* Allocate a new relfilenumber */
newrelfilenumber = GetNewRelFileNumber(relation->rd_rel->reltablespace,
NULL, persistence, false);
NULL, persistence);
}
else if (relation->rd_rel->relkind == RELKIND_INDEX)
{
Expand Down
19 changes: 19 additions & 0 deletions src/backend/utils/misc/queryenvironment.c
Original file line number Diff line number Diff line change
Expand Up @@ -1442,6 +1442,25 @@ void ENRRollbackSubtransaction(SubTransactionId subid, QueryEnvironment *queryEn
MemoryContextSwitchTo(oldcxt);
}

/*
* Simple check for whether to use temp OID buffer.
*/
bool useTempOidBuffer()
{
return sql_dialect == SQL_DIALECT_TSQL
&& GetNewTempOidWithIndex_hook
&& temp_oid_buffer_size > 0;
}

/* Simple check for whether to use temp OID buffer given an existing OID. */
bool useTempOidBufferForOid(Oid relId)
{
return sql_dialect == SQL_DIALECT_TSQL
&& GetNewTempOidWithIndex_hook
&& temp_oid_buffer_size > 0
&& get_ENR_withoid(currentQueryEnv, relId, ENR_TSQL_TEMP);
}

/*
* Drop all the temp tables registered as ENR in the given query environment.
*/
Expand Down
3 changes: 1 addition & 2 deletions src/include/catalog/catalog.h
Original file line number Diff line number Diff line change
Expand Up @@ -42,8 +42,7 @@ extern Oid GetNewOidWithIndex(Relation relation, Oid indexId,
AttrNumber oidcolumn);
extern RelFileNumber GetNewRelFileNumber(Oid reltablespace,
Relation pg_class,
char relpersistence,
bool override_temp);
char relpersistence);

typedef Oid (*GetNewTempObjectId_hook_type) (void);
extern GetNewTempObjectId_hook_type GetNewTempObjectId_hook;
Expand Down
3 changes: 3 additions & 0 deletions src/include/utils/queryenvironment.h
Original file line number Diff line number Diff line change
Expand Up @@ -150,6 +150,9 @@ extern void ENRCommitChanges(QueryEnvironment *queryEnv);
extern void ENRRollbackChanges(QueryEnvironment *queryEnv);
extern void ENRRollbackSubtransaction(SubTransactionId subid, QueryEnvironment *queryEnv);

extern bool useTempOidBuffer(void);
extern bool useTempOidBufferForOid(Oid relId);

typedef EphemeralNamedRelation (*pltsql_get_tsql_enr_from_oid_hook_type) (Oid oid);
extern PGDLLIMPORT pltsql_get_tsql_enr_from_oid_hook_type pltsql_get_tsql_enr_from_oid_hook;

Expand Down

0 comments on commit 2e1527b

Please sign in to comment.