From 63d4a62043bd1d2af381c632553f85c89de4f36f Mon Sep 17 00:00:00 2001 From: Justin Pryzby Date: Sat, 1 Jan 2022 16:47:14 -0600 Subject: [PATCH 04/11] f!0003-gtt-v64-implementation.patch --- src/backend/catalog/heap.c | 8 ++++---- src/backend/catalog/index.c | 24 +++++++++++----------- src/backend/catalog/storage_gtt.c | 32 ++++++++++++++--------------- src/backend/commands/analyze.c | 4 ++-- src/backend/commands/cluster.c | 6 +++--- src/backend/commands/sequence.c | 6 +++--- src/backend/commands/tablecmds.c | 10 ++++----- src/backend/commands/vacuum.c | 2 +- src/backend/commands/view.c | 2 +- src/backend/parser/analyze.c | 2 +- src/backend/parser/parse_utilcmd.c | 2 +- src/backend/postmaster/autovacuum.c | 4 ++-- src/backend/storage/ipc/procarray.c | 5 ++++- src/backend/utils/adt/dbsize.c | 2 +- src/bin/pg_dump/pg_dump.c | 2 +- src/include/catalog/pg_class.h | 2 +- 16 files changed, 58 insertions(+), 55 deletions(-) diff --git a/src/backend/catalog/heap.c b/src/backend/catalog/heap.c index 8e5b56f602..d24afa45c1 100644 --- a/src/backend/catalog/heap.c +++ b/src/backend/catalog/heap.c @@ -2023,15 +2023,15 @@ heap_drop_with_catalog(Oid relid) update_default_partition_oid(parentOid, InvalidOid); /* - * Only when other sessions are not using this Global temporary table, - * is it allowed to DROP it. + * It is not allowed to DROP a Global temporary table when other + * sessions are using it */ if (RELATION_IS_GLOBAL_TEMP(rel)) { if (is_other_backend_use_gtt(RelationGetRelid(rel))) ereport(ERROR, (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), - errmsg("cannot drop global temporary table %s when other backend attached it.", + errmsg("cannot drop global temporary table %s being accessed by another backend", RelationGetRelationName(rel)))); } @@ -3466,7 +3466,7 @@ heap_truncate_one_rel(Relation rel) /* * After the data is cleaned up on the GTT, the transaction information - * for the data(stored in local hash table) is also need reset. + * for the data(stored in local hash table) also needs to be reset. */ if (RELATION_IS_GLOBAL_TEMP(rel)) up_gtt_relstats(RelationGetRelid(rel), 0, 0, 0, RecentXmin, GetOldestMultiXactId()); diff --git a/src/backend/catalog/index.c b/src/backend/catalog/index.c index be08ba376a..e2483426d2 100644 --- a/src/backend/catalog/index.c +++ b/src/backend/catalog/index.c @@ -741,11 +741,11 @@ index_create(Relation heapRelation, /* For global temporary table only */ if (RELATION_IS_GLOBAL_TEMP(heapRelation)) { - /* No support create index on global temporary table with concurrent mode */ + /* No support for creating index on global temporary table with concurrent mode */ Assert(!concurrent); /* - * For the case that some backend is applied relcache message to create + * For the case that some backend is applied relcache message to create XXX * an index on a global temporary table, if this table in the current * backend are not initialized, the creation of index storage on the * table are also skipped. @@ -2201,18 +2201,18 @@ index_drop(Oid indexId, bool concurrent, bool concurrent_lock_mode) CheckTableNotInUse(userIndexRelation, "DROP INDEX"); /* - * Allow to drop index on global temporary table when only current - * backend use it. + * Disallow dropping index on global temporary table if another + * backend is using it. */ if (RELATION_IS_GLOBAL_TEMP(userHeapRelation) && is_other_backend_use_gtt(RelationGetRelid(userHeapRelation))) { - ereport(ERROR, + ereport(ERROR, // XXX (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), errmsg("cannot drop index %s on global temporary table %s", RelationGetRelationName(userIndexRelation), RelationGetRelationName(userHeapRelation)), - errdetail("Because the index is created on the global temporary table and other backend attached it."), - errhint("Please try detach all sessions using this temporary table and try again."))); + errdetail("The index is created on the global temporary table and other backend attached it."), + errhint("Detach other sessions using this temporary table and try again."))); } /* @@ -2926,12 +2926,12 @@ index_update_stats(Relation rel, /* For global temporary table */ if (is_gtt) { - /* Update GTT'statistics into local relcache */ + /* Update GTT's statistics into local relcache */ rel->rd_rel->relpages = (int32) relpages; rel->rd_rel->reltuples = (float4) reltuples; rel->rd_rel->relallvisible = (int32) relallvisible; - /* Update GTT'statistics into local hashtable */ + /* Update GTT's statistics into local hashtable */ up_gtt_relstats(RelationGetRelid(rel), relpages, reltuples, relallvisible, InvalidTransactionId, InvalidMultiXactId); } @@ -3066,7 +3066,7 @@ index_build(Relation heapRelation, pgstat_progress_update_multi_param(6, progress_index, progress_vals); } - /* For build index on global temporary table */ + /* If building index on global temporary table */ if (RELATION_IS_GLOBAL_TEMP(indexRelation)) { /* @@ -3075,7 +3075,7 @@ index_build(Relation heapRelation, */ if (!gtt_storage_attached(RelationGetRelid(indexRelation))) { - /* Before create init storage, fix the local Relcache first */ + /* Before creating init storage, fix the local Relcache first */ force_enable_gtt_index(indexRelation); Assert(gtt_storage_attached(RelationGetRelid(heapRelation))); @@ -3651,7 +3651,7 @@ reindex_index(Oid indexId, bool skip_constraint_checks, char persistence, if (OidIsValid(params->tablespaceOid)) ereport(ERROR, (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), - errmsg("The tablespace of global temporary table can not be changed"))); + errmsg("The tablespace of global temporary table cannot be changed"))); if (!gtt_storage_attached(indexId)) { diff --git a/src/backend/catalog/storage_gtt.c b/src/backend/catalog/storage_gtt.c index d50e1fa9af..1660163e99 100644 --- a/src/backend/catalog/storage_gtt.c +++ b/src/backend/catalog/storage_gtt.c @@ -1,12 +1,12 @@ /*------------------------------------------------------------------------- * * storage_gtt.c - * The body implementation of Global Temparary table. + * The body implementation of Global Temporary table. * * IDENTIFICATION * src/backend/catalog/storage_gtt.c * - * See src/backend/catalog/GTT_README for Global temparary table's + * See src/backend/catalog/GTT_README for Global temporary table's * requirements and design. * *------------------------------------------------------------------------- @@ -197,7 +197,7 @@ active_gtt_shared_hash_size(void) } /* - * Initialization shared hash table for GTT. + * Initialization of shared hash table for GTT. */ void active_gtt_shared_hash_init(void) @@ -277,7 +277,7 @@ gtt_storage_checkin(Oid relid) /* * Remove the GTT relid record from the shared hash table which means that current backend is - * not use this GTT. + * not using this GTT. */ static void gtt_storage_checkout(Oid relid, bool isCommit) @@ -298,7 +298,7 @@ gtt_storage_checkout(Oid relid, bool isCommit) { LWLockRelease(>t_shared_ctl->lock); if (isCommit) - elog(WARNING, "relid %u not exist in gtt shared hash when drop local storage", relid); + elog(WARNING, "relid %u doesn't exist in gtt shared hash when dropping local storage", relid); return; } @@ -319,9 +319,9 @@ gtt_storage_checkout(Oid relid, bool isCommit) /* * Gets usage information for a GTT from shared hash table. - * The information is in the form of bitmap. - * Quickly copy the entire bitmap from shared memory and return it. - * that to avoid holding locks for a long time. + * The information is in the form of a bitmap. + * Quickly copy the entire bitmap from shared memory and return it, + * to avoid holding locks for a long time. */ static Bitmapset * copy_active_gtt_bitmap(Oid relid) @@ -417,18 +417,18 @@ remember_gtt_storage_info(RelFileNode rnode, Relation rel) if (max_active_gtt <= 0) ereport(ERROR, (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), - errmsg("Global temporary table feature is disable"), + errmsg("Global temporary table feature is disabled"), errhint("You might need to increase max_active_global_temporary_table to enable this feature."))); if (RecoveryInProgress()) - elog(ERROR, "readonly mode not support access global temporary table"); + elog(ERROR, "recovery mode does not support accessing global temporary table"); if (rel->rd_rel->relkind == RELKIND_INDEX && rel->rd_index && (!rel->rd_index->indisvalid || !rel->rd_index->indisready || !rel->rd_index->indislive)) - elog(ERROR, "invalid gtt index %s not allow to create storage", RelationGetRelationName(rel)); + elog(ERROR, "invalid gtt index %s not allowed to create storage", RelationGetRelationName(rel)); /* First time through: initialize the hash table */ if (gtt_storage_local_hash == NULL) @@ -757,7 +757,7 @@ up_gtt_relstats(Oid relid, /* * Search GTT relstats(relpage/reltuple/relallvisible) - * from local has. + * from local hash. */ bool get_gtt_relstats(Oid relid, BlockNumber *relpages, double *reltuples, @@ -852,7 +852,7 @@ up_gtt_att_statistic(Oid reloid, int attnum, bool inh, int natts, } MemoryContextSwitchTo(oldcontext); - if (!found) + if (!found) // XXX: should be an ereport with a hint ? elog(WARNING, "analyze can not update relid %u column %d statistics after add or drop column, try truncate table first", reloid, attnum); return; @@ -960,7 +960,7 @@ remove_gtt_relfrozenxid_from_ordered_list(Oid relfrozenxid) /* * Update of backend Level oldest relfrozenxid to MyProc. - * This makes each backend's oldest RelFrozenxID globally visible. + * This makes each backend's oldest RelFrozenXID globally visible. */ static void set_gtt_session_relfrozenxid(void) @@ -1282,7 +1282,7 @@ pg_list_gtt_relfrozenxids(PG_FUNCTION_ARGS) } /* - * In order to build the GTT index, force enable GTT'index. + * In order to build the GTT index, force enable GTT index. */ void force_enable_gtt_index(Relation index) @@ -1331,7 +1331,7 @@ gtt_fix_index_backend_state(Relation index) /* * During the SQL initialization of the executor (InitPlan) - * Initialize storage of GTT GTT'indexes and build empty index. + * Initialize storage of GTT's indexes and build empty index. */ void init_gtt_storage(CmdType operation, Relation relation) diff --git a/src/backend/commands/analyze.c b/src/backend/commands/analyze.c index 72218b2c66..6dee51784f 100644 --- a/src/backend/commands/analyze.c +++ b/src/backend/commands/analyze.c @@ -188,8 +188,8 @@ analyze_rel(Oid relid, RangeVar *relation, } /* - * Skip the global temporary table that did not initialize the storage - * in this backend. + * Skip global temporary tables for which storage was not initialized by + * this backend. */ if (RELATION_IS_GLOBAL_TEMP(onerel) && !gtt_storage_attached(RelationGetRelid(onerel))) diff --git a/src/backend/commands/cluster.c b/src/backend/commands/cluster.c index 535f537aae..ff6ae583f5 100644 --- a/src/backend/commands/cluster.c +++ b/src/backend/commands/cluster.c @@ -392,15 +392,15 @@ cluster_rel(Oid tableOid, Oid indexOid, ClusterParams *params) } /* - * Skip the global temporary table that did not initialize the storage - * in this backend. + * Skip global temporary tables for which storage was not initialized by + * this backend. */ if (RELATION_IS_GLOBAL_TEMP(OldHeap)) { if (gtt_storage_attached(RelationGetRelid(OldHeap))) ereport(ERROR, (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), - errmsg("not support cluster global temporary table"))); + errmsg("clustering is not supported on a global temporary table"))); relation_close(OldHeap, AccessExclusiveLock); pgstat_progress_end_command(); diff --git a/src/backend/commands/sequence.c b/src/backend/commands/sequence.c index af12dd2cdc..4d5aedf2c3 100644 --- a/src/backend/commands/sequence.c +++ b/src/backend/commands/sequence.c @@ -461,7 +461,7 @@ AlterSequence(ParseState *pstate, AlterSeqStmt *stmt) if (is_other_backend_use_gtt(RelationGetRelid(seqrel))) ereport(ERROR, (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), - errmsg("cannot alter global temporary sequence %s when other backend attached it.", + errmsg("cannot alter global temporary sequence %s being accessed by another backend", RelationGetRelationName(seqrel)))); } @@ -1194,7 +1194,7 @@ init_sequence(Oid relid, SeqTable *p_elm, Relation *p_rel) *p_elm = elm; *p_rel = seqrel; - /* Initializes the storage for sequence which the global temporary table belongs. */ + /* Initializes the storage for sequence which belongs to a global temporary table. */ if (RELATION_IS_GLOBAL_TEMP(seqrel) && !gtt_storage_attached(RelationGetRelid(seqrel))) { @@ -1999,7 +1999,7 @@ get_seqence_start_value(Oid seqid) } /* - * Initialize sequence which global temporary table belongs. + * Initialize sequence which belongs to a global temporary table. */ void gtt_init_seq(Relation rel) diff --git a/src/backend/commands/tablecmds.c b/src/backend/commands/tablecmds.c index 7aa3beba2c..e4b67f8731 100644 --- a/src/backend/commands/tablecmds.c +++ b/src/backend/commands/tablecmds.c @@ -2018,8 +2018,8 @@ ExecuteTruncateGuts(List *explicit_rels, } /* - * Skip the global temporary table that is not initialized for storage - * in current backend. + * Skip global temporary tables for which the current backend has not + * initialized storage. */ if (RELATION_IS_GLOBAL_TEMP(rel)) { @@ -3365,7 +3365,7 @@ CheckRelationTableSpaceMove(Relation rel, Oid newTableSpaceId) if (RELATION_IS_GLOBAL_TEMP(rel)) ereport(ERROR, (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), - errmsg("The tablespace of global temporary table can not be changed"))); + errmsg("The tablespace of global temporary table cannot be changed"))); return true; } @@ -4136,13 +4136,13 @@ AlterTable(AlterTableStmt *stmt, LOCKMODE lockmode, /* Caller is required to provide an adequate lock. */ rel = relation_open(context->relid, NoLock); - /* We allow to alter global temporary table only current backend use it */ + /* We disallow altering a global temporary table if another backend is using it */ if (RELATION_IS_GLOBAL_TEMP(rel)) { if (is_other_backend_use_gtt(RelationGetRelid(rel))) ereport(ERROR, (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), - errmsg("cannot alter global temporary table %s when other backend attached it.", + errmsg("cannot alter global temporary table %s being accessed by another backend", RelationGetRelationName(rel)))); } diff --git a/src/backend/commands/vacuum.c b/src/backend/commands/vacuum.c index 47c734aa1c..3a48892feb 100644 --- a/src/backend/commands/vacuum.c +++ b/src/backend/commands/vacuum.c @@ -2140,7 +2140,7 @@ vacuum_rel(Oid relid, RangeVar *relation, VacuumParams *params) } /* - * Skip those global temporary table that are not initialized in + * Skip global temporary tables that are not initialized in the * current backend. */ if (RELATION_IS_GLOBAL_TEMP(rel) && diff --git a/src/backend/commands/view.c b/src/backend/commands/view.c index cd2bd57e38..79e4b0c9c7 100644 --- a/src/backend/commands/view.c +++ b/src/backend/commands/view.c @@ -543,7 +543,7 @@ DefineView(ViewStmt *stmt, const char *queryString, (errcode(ERRCODE_SYNTAX_ERROR), errmsg("views cannot be unlogged because they do not have storage"))); - /* Global temporary table are not sensible. */ + /* Global temporary views are not sensible. */ if (stmt->view->relpersistence == RELPERSISTENCE_GLOBAL_TEMP) ereport(ERROR, (errcode(ERRCODE_SYNTAX_ERROR), diff --git a/src/backend/parser/analyze.c b/src/backend/parser/analyze.c index 75a0940b25..4b96429f30 100644 --- a/src/backend/parser/analyze.c +++ b/src/backend/parser/analyze.c @@ -2912,7 +2912,7 @@ transformCreateTableAsStmt(ParseState *pstate, CreateTableAsStmt *stmt) if (is_query_using_gtt(query)) ereport(ERROR, (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), - errmsg("materialized views must not use global temporary tables or views"))); + errmsg("materialized views must not use global temporary tables"))); /* * A materialized view would either need to save parameters for use in diff --git a/src/backend/parser/parse_utilcmd.c b/src/backend/parser/parse_utilcmd.c index 45241b8b0f..c9bef46339 100644 --- a/src/backend/parser/parse_utilcmd.c +++ b/src/backend/parser/parse_utilcmd.c @@ -449,7 +449,7 @@ generateSerialExtraStmts(CreateStmtContext *cxt, ColumnDef *column, /* * If a sequence is bound to a global temporary table, then the sequence - * must been "global temporary" + * must be "global temporary" */ if (cxt->relation->relpersistence == RELPERSISTENCE_GLOBAL_TEMP) seqstmt->sequence->relpersistence = cxt->relation->relpersistence; diff --git a/src/backend/postmaster/autovacuum.c b/src/backend/postmaster/autovacuum.c index 5601f15d18..fa8c391d40 100644 --- a/src/backend/postmaster/autovacuum.c +++ b/src/backend/postmaster/autovacuum.c @@ -2119,8 +2119,8 @@ do_autovacuum(void) else if (classForm->relpersistence == RELPERSISTENCE_GLOBAL_TEMP) { /* - * Aotuvacuum cannot vacuum the private data stored in each backend - * that belongs to global temporary table, so skip them. + * Autovacuum cannot vacuum the private data stored in each backend + * that belongs to global temporary tables, so skip them. */ continue; } diff --git a/src/backend/storage/ipc/procarray.c b/src/backend/storage/ipc/procarray.c index e9cea9b423..0b207dca16 100644 --- a/src/backend/storage/ipc/procarray.c +++ b/src/backend/storage/ipc/procarray.c @@ -5180,6 +5180,9 @@ KnownAssignedXidsReset(void) /* * search all active backend to get oldest frozenxid * for global temporary table. + * Return the oldest frozenxid, or InvalidTransactionId if none. + * If pids!=NULL, it's populated with qualifying backend pids. + * If xids!=NULL, it's populated with qualifying backend frozenxids. */ int list_all_backend_gtt_frozenxids(int max_size, int *pids, uint32 *xids, int *n) @@ -5216,7 +5219,7 @@ list_all_backend_gtt_frozenxids(int max_size, int *pids, uint32 *xids, int *n) if (max_size > 0 && max_size < arrayP->numProcs) { LWLockRelease(ProcArrayLock); - elog(ERROR, "list_all_gtt_frozenxids require more array"); + elog(ERROR, "list_all_gtt_frozenxids requires a longer array"); } for (index = 0; index < arrayP->numProcs; index++) diff --git a/src/backend/utils/adt/dbsize.c b/src/backend/utils/adt/dbsize.c index 9a6e7cee24..b86bc4fc69 100644 --- a/src/backend/utils/adt/dbsize.c +++ b/src/backend/utils/adt/dbsize.c @@ -984,7 +984,7 @@ pg_relation_filepath(PG_FUNCTION_ARGS) break; case RELPERSISTENCE_GLOBAL_TEMP: /* - * For global temporary table ,each backend has its own storage, + * For global temporary table, each backend has its own storage, * also only sees its own storage. Use Backendid to identify them. */ backend = BackendIdForTempRelations(); diff --git a/src/bin/pg_dump/pg_dump.c b/src/bin/pg_dump/pg_dump.c index 3100ddc704..caab5dc36a 100644 --- a/src/bin/pg_dump/pg_dump.c +++ b/src/bin/pg_dump/pg_dump.c @@ -15431,7 +15431,7 @@ dumpTableSchema(Archive *fout, const TableInfo *tbinfo) /* * Transaction information for the global temporary table is not stored - * in the pg_class. + * in pg_class. */ if (tbinfo->relpersistence == RELPERSISTENCE_GLOBAL_TEMP) { diff --git a/src/include/catalog/pg_class.h b/src/include/catalog/pg_class.h index e23cb49c01..658e9be8de 100644 --- a/src/include/catalog/pg_class.h +++ b/src/include/catalog/pg_class.h @@ -169,10 +169,10 @@ DECLARE_INDEX(pg_class_tblspc_relfilenode_index, 3455, ClassTblspcRelfilenodeInd #define RELKIND_PARTITIONED_TABLE 'p' /* partitioned table */ #define RELKIND_PARTITIONED_INDEX 'I' /* partitioned index */ +#define RELPERSISTENCE_GLOBAL_TEMP 'g' /* global temporary table */ #define RELPERSISTENCE_PERMANENT 'p' /* regular table */ #define RELPERSISTENCE_UNLOGGED 'u' /* unlogged permanent table */ #define RELPERSISTENCE_TEMP 't' /* temporary table */ -#define RELPERSISTENCE_GLOBAL_TEMP 'g' /* global temporary table */ /* default selection for replica identity (primary key or nothing) */ #define REPLICA_IDENTITY_DEFAULT 'd' -- 2.17.1