Small rebase of this patch set.
From a5ecfa6cfb3963ff069b591254975525ac91b2e1 Mon Sep 17 00:00:00 2001
From: Peter Eisentraut <[email protected]>
Date: Mon, 16 Aug 2021 14:25:59 +0200
Subject: [PATCH v3 1/2] pg_dump: Remove redundant relkind checks
It is checked in flagInhTables() which relkinds can have parents.
After that, those entries will have numParents==0, so we don't need to
check the relkind again.
---
src/bin/pg_dump/common.c | 8 +-------
src/bin/pg_dump/pg_dump.c | 7 +------
2 files changed, 2 insertions(+), 13 deletions(-)
diff --git a/src/bin/pg_dump/common.c b/src/bin/pg_dump/common.c
index ecab0a9e4e..c01555d8e4 100644
--- a/src/bin/pg_dump/common.c
+++ b/src/bin/pg_dump/common.c
@@ -476,13 +476,7 @@ flagInhAttrs(DumpOptions *dopt, TableInfo *tblinfo, int
numTables)
int numParents;
TableInfo **parents;
- /* Some kinds never have parents */
- if (tbinfo->relkind == RELKIND_SEQUENCE ||
- tbinfo->relkind == RELKIND_VIEW ||
- tbinfo->relkind == RELKIND_MATVIEW)
- continue;
-
- /* Don't bother computing anything for non-target tables,
either */
+ /* Don't bother computing anything for non-target tables */
if (!tbinfo->dobj.dump)
continue;
diff --git a/src/bin/pg_dump/pg_dump.c b/src/bin/pg_dump/pg_dump.c
index b9635a95b6..f3c6c28480 100644
--- a/src/bin/pg_dump/pg_dump.c
+++ b/src/bin/pg_dump/pg_dump.c
@@ -2727,12 +2727,7 @@ guessConstraintInheritance(TableInfo *tblinfo, int
numTables)
TableInfo **parents;
TableInfo *parent;
- /* Sequences and views never have parents */
- if (tbinfo->relkind == RELKIND_SEQUENCE ||
- tbinfo->relkind == RELKIND_VIEW)
- continue;
-
- /* Don't bother computing anything for non-target tables,
either */
+ /* Don't bother computing anything for non-target tables */
if (!(tbinfo->dobj.dump & DUMP_COMPONENT_DEFINITION))
continue;
base-commit: 0f9b9938a0367313fcf6a32fcb7fb5be9e281198
--
2.33.1
From 0cf76b6d91c41a86f2e3cb3a3c4cd1854b819bb5 Mon Sep 17 00:00:00 2001
From: Peter Eisentraut <[email protected]>
Date: Mon, 30 Aug 2021 10:09:50 +0200
Subject: [PATCH v3 2/2] Some RELKIND macro refactoring
Add more macros to group some RELKIND_* macros:
- RELKIND_HAS_PARTITIONS()
- RELKIND_HAS_TABLESPACE()
- RELKIND_HAS_TABLE_AM()
Discussion:
https://www.postgresql.org/message-id/flat/a574c8f1-9c84-93ad-a9e5-65233d6fc00f%40enterprisedb.com
---
contrib/amcheck/verify_heapam.c | 4 +-
contrib/pg_surgery/heap_surgery.c | 4 +-
contrib/pg_visibility/pg_visibility.c | 4 +-
contrib/pgstattuple/pgstattuple.c | 17 ++-
src/backend/catalog/heap.c | 154 +++++++++----------------
src/backend/catalog/index.c | 2 +-
src/backend/commands/indexcmds.c | 9 +-
src/backend/commands/tablecmds.c | 8 +-
src/backend/optimizer/util/plancat.c | 41 +++----
src/backend/storage/buffer/bufmgr.c | 43 +++----
src/backend/utils/adt/partitionfuncs.c | 7 +-
src/backend/utils/cache/relcache.c | 90 +++++----------
src/bin/pg_dump/pg_dump.c | 17 ++-
src/include/catalog/pg_class.h | 25 ++++
14 files changed, 171 insertions(+), 254 deletions(-)
diff --git a/contrib/amcheck/verify_heapam.c b/contrib/amcheck/verify_heapam.c
index e84ecd1c98..59fa794450 100644
--- a/contrib/amcheck/verify_heapam.c
+++ b/contrib/amcheck/verify_heapam.c
@@ -303,9 +303,7 @@ verify_heapam(PG_FUNCTION_ARGS)
/*
* Check that a relation's relkind and access method are both supported.
*/
- if (ctx.rel->rd_rel->relkind != RELKIND_RELATION &&
- ctx.rel->rd_rel->relkind != RELKIND_MATVIEW &&
- ctx.rel->rd_rel->relkind != RELKIND_TOASTVALUE &&
+ if (!RELKIND_HAS_TABLE_AM(ctx.rel->rd_rel->relkind) &&
ctx.rel->rd_rel->relkind != RELKIND_SEQUENCE)
ereport(ERROR,
(errcode(ERRCODE_WRONG_OBJECT_TYPE),
diff --git a/contrib/pg_surgery/heap_surgery.c
b/contrib/pg_surgery/heap_surgery.c
index 7edfe4f326..f06385e8d3 100644
--- a/contrib/pg_surgery/heap_surgery.c
+++ b/contrib/pg_surgery/heap_surgery.c
@@ -103,9 +103,7 @@ heap_force_common(FunctionCallInfo fcinfo,
HeapTupleForceOption heap_force_opt)
/*
* Check target relation.
*/
- if (rel->rd_rel->relkind != RELKIND_RELATION &&
- rel->rd_rel->relkind != RELKIND_MATVIEW &&
- rel->rd_rel->relkind != RELKIND_TOASTVALUE)
+ if (!RELKIND_HAS_TABLE_AM(rel->rd_rel->relkind))
ereport(ERROR,
(errcode(ERRCODE_WRONG_OBJECT_TYPE),
errmsg("cannot operate on relation \"%s\"",
diff --git a/contrib/pg_visibility/pg_visibility.c
b/contrib/pg_visibility/pg_visibility.c
index b5362edcee..a206c0abd8 100644
--- a/contrib/pg_visibility/pg_visibility.c
+++ b/contrib/pg_visibility/pg_visibility.c
@@ -776,9 +776,7 @@ tuple_all_visible(HeapTuple tup, TransactionId OldestXmin,
Buffer buffer)
static void
check_relation_relkind(Relation rel)
{
- if (rel->rd_rel->relkind != RELKIND_RELATION &&
- rel->rd_rel->relkind != RELKIND_MATVIEW &&
- rel->rd_rel->relkind != RELKIND_TOASTVALUE)
+ if (!RELKIND_HAS_TABLE_AM(rel->rd_rel->relkind))
ereport(ERROR,
(errcode(ERRCODE_WRONG_OBJECT_TYPE),
errmsg("relation \"%s\" is of wrong relation
kind",
diff --git a/contrib/pgstattuple/pgstattuple.c
b/contrib/pgstattuple/pgstattuple.c
index f408e6d84d..c9b8f01f9b 100644
--- a/contrib/pgstattuple/pgstattuple.c
+++ b/contrib/pgstattuple/pgstattuple.c
@@ -252,14 +252,13 @@ pgstat_relation(Relation rel, FunctionCallInfo fcinfo)
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
errmsg("cannot access temporary tables of
other sessions")));
- switch (rel->rd_rel->relkind)
+ if (RELKIND_HAS_TABLE_AM(rel->rd_rel->relkind) ||
+ rel->rd_rel->relkind == RELKIND_SEQUENCE)
{
- case RELKIND_RELATION:
- case RELKIND_MATVIEW:
- case RELKIND_TOASTVALUE:
- case RELKIND_SEQUENCE:
return pgstat_heap(rel, fcinfo);
- case RELKIND_INDEX:
+ }
+ else if (rel->rd_rel->relkind == RELKIND_INDEX)
+ {
switch (rel->rd_rel->relam)
{
case BTREE_AM_OID:
@@ -288,9 +287,9 @@ pgstat_relation(Relation rel, FunctionCallInfo fcinfo)
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
errmsg("index \"%s\" (%s) is not
supported",
RelationGetRelationName(rel), err)));
- break;
-
- default:
+ }
+ else
+ {
ereport(ERROR,
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
errmsg("cannot get tuple-level
statistics for relation \"%s\"",
diff --git a/src/backend/catalog/heap.c b/src/backend/catalog/heap.c
index 81cc39fb70..a13861e925 100644
--- a/src/backend/catalog/heap.c
+++ b/src/backend/catalog/heap.c
@@ -336,35 +336,12 @@ heap_create(const char *relname,
*relfrozenxid = InvalidTransactionId;
*relminmxid = InvalidMultiXactId;
- /* Handle reltablespace for specific relkinds. */
- switch (relkind)
- {
- case RELKIND_VIEW:
- case RELKIND_COMPOSITE_TYPE:
- case RELKIND_FOREIGN_TABLE:
-
- /*
- * Force reltablespace to zero if the relation has no
physical
- * storage. This is mainly just for cleanliness' sake.
- *
- * Partitioned tables and indexes don't have physical
storage
- * either, but we want to keep their tablespace
settings so that
- * their children can inherit it.
- */
- reltablespace = InvalidOid;
- break;
-
- case RELKIND_SEQUENCE:
-
- /*
- * Force reltablespace to zero for sequences, since we
don't
- * support moving them around into different
tablespaces.
- */
- reltablespace = InvalidOid;
- break;
- default:
- break;
- }
+ /*
+ * Force reltablespace to zero if the relation kind does not support
+ * tablespaces. This is mainly just for cleanliness' sake.
+ */
+ if (!RELKIND_HAS_TABLESPACE(relkind))
+ reltablespace = InvalidOid;
/*
* Decide whether to create storage. If caller passed a valid
relfilenode,
@@ -409,35 +386,18 @@ heap_create(const char *relname,
/*
* Have the storage manager create the relation's disk file, if needed.
*
- * For relations the callback creates both the main and the init fork,
for
- * indexes only the main fork is created. The other forks will be
created
- * on demand.
+ * For tables, the AM callback creates both the main and the init fork.
+ * For others, only the main fork is created; the other forks will be
+ * created on demand.
*/
if (create_storage)
{
- switch (rel->rd_rel->relkind)
- {
- case RELKIND_VIEW:
- case RELKIND_COMPOSITE_TYPE:
- case RELKIND_FOREIGN_TABLE:
- case RELKIND_PARTITIONED_TABLE:
- case RELKIND_PARTITIONED_INDEX:
- Assert(false);
- break;
-
- case RELKIND_INDEX:
- case RELKIND_SEQUENCE:
- RelationCreateStorage(rel->rd_node,
relpersistence);
- break;
-
- case RELKIND_RELATION:
- case RELKIND_TOASTVALUE:
- case RELKIND_MATVIEW:
- table_relation_set_new_filenode(rel,
&rel->rd_node,
-
relpersistence,
-
relfrozenxid, relminmxid);
- break;
- }
+ if (RELKIND_HAS_TABLE_AM(rel->rd_rel->relkind))
+ table_relation_set_new_filenode(rel, &rel->rd_node,
+
relpersistence,
+
relfrozenxid, relminmxid);
+ else
+ RelationCreateStorage(rel->rd_node, relpersistence);
}
/*
@@ -1014,29 +974,16 @@ AddNewRelationTuple(Relation pg_class_desc,
*/
new_rel_reltup = new_rel_desc->rd_rel;
- switch (relkind)
+ /* The relation is empty */
+ new_rel_reltup->relpages = 0;
+ new_rel_reltup->reltuples = -1;
+ new_rel_reltup->relallvisible = 0;
+
+ /* Sequences always have a known size */
+ if (relkind == RELKIND_SEQUENCE)
{
- case RELKIND_RELATION:
- case RELKIND_MATVIEW:
- case RELKIND_INDEX:
- case RELKIND_TOASTVALUE:
- /* The relation is real, but as yet empty */
- new_rel_reltup->relpages = 0;
- new_rel_reltup->reltuples = -1;
- new_rel_reltup->relallvisible = 0;
- break;
- case RELKIND_SEQUENCE:
- /* Sequences always have a known size */
- new_rel_reltup->relpages = 1;
- new_rel_reltup->reltuples = 1;
- new_rel_reltup->relallvisible = 0;
- break;
- default:
- /* Views, etc, have no disk storage */
- new_rel_reltup->relpages = 0;
- new_rel_reltup->reltuples = -1;
- new_rel_reltup->relallvisible = 0;
- break;
+ new_rel_reltup->relpages = 1;
+ new_rel_reltup->reltuples = 1;
}
new_rel_reltup->relfrozenxid = relfrozenxid;
@@ -1234,29 +1181,37 @@ heap_create_with_catalog(const char *relname,
if (!OidIsValid(relid))
{
/* Use binary-upgrade override for pg_class.oid/relfilenode? */
- if (IsBinaryUpgrade &&
- (relkind == RELKIND_RELATION || relkind ==
RELKIND_SEQUENCE ||
- relkind == RELKIND_VIEW || relkind == RELKIND_MATVIEW
||
- relkind == RELKIND_COMPOSITE_TYPE || relkind ==
RELKIND_FOREIGN_TABLE ||
- relkind == RELKIND_PARTITIONED_TABLE))
+ if (IsBinaryUpgrade)
{
- if (!OidIsValid(binary_upgrade_next_heap_pg_class_oid))
- ereport(ERROR,
-
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
- errmsg("pg_class heap OID
value not set when in binary upgrade mode")));
+ /*
+ * Indexes are not supported here; they use
+ * binary_upgrade_next_index_pg_class_oid.
+ */
+ Assert(relkind != RELKIND_INDEX);
+ Assert(relkind != RELKIND_PARTITIONED_INDEX);
- relid = binary_upgrade_next_heap_pg_class_oid;
- binary_upgrade_next_heap_pg_class_oid = InvalidOid;
- }
- /* There might be no TOAST table, so we have to test for it. */
- else if (IsBinaryUpgrade &&
-
OidIsValid(binary_upgrade_next_toast_pg_class_oid) &&
- relkind == RELKIND_TOASTVALUE)
- {
- relid = binary_upgrade_next_toast_pg_class_oid;
- binary_upgrade_next_toast_pg_class_oid = InvalidOid;
+ if (relkind == RELKIND_TOASTVALUE)
+ {
+ /* There might be no TOAST table, so we have to
test for it. */
+ if
(OidIsValid(binary_upgrade_next_toast_pg_class_oid))
+ {
+ relid =
binary_upgrade_next_toast_pg_class_oid;
+ binary_upgrade_next_toast_pg_class_oid
= InvalidOid;
+ }
+ }
+ else
+ {
+ if
(!OidIsValid(binary_upgrade_next_heap_pg_class_oid))
+ ereport(ERROR,
+
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ errmsg("pg_class heap
OID value not set when in binary upgrade mode")));
+
+ relid = binary_upgrade_next_heap_pg_class_oid;
+ binary_upgrade_next_heap_pg_class_oid =
InvalidOid;
+ }
}
- else
+
+ if (!relid)
relid = GetNewRelFileNode(reltablespace, pg_class_desc,
relpersistence);
}
@@ -1467,13 +1422,12 @@ heap_create_with_catalog(const char *relname,
/*
* Make a dependency link to force the relation to be deleted
if its
- * access method is. Do this only for relation and materialized
views.
+ * access method is.
*
* No need to add an explicit dependency for the toast table,
as the
* main table depends on it.
*/
- if (relkind == RELKIND_RELATION ||
- relkind == RELKIND_MATVIEW)
+ if (RELKIND_HAS_TABLE_AM(relkind) && relkind !=
RELKIND_TOASTVALUE)
{
ObjectAddressSet(referenced, AccessMethodRelationId,
accessmtd);
add_exact_object_address(&referenced, addrs);
diff --git a/src/backend/catalog/index.c b/src/backend/catalog/index.c
index c255806e38..27f0385ae0 100644
--- a/src/backend/catalog/index.c
+++ b/src/backend/catalog/index.c
@@ -2293,7 +2293,7 @@ index_drop(Oid indexId, bool concurrent, bool
concurrent_lock_mode)
/*
* Schedule physical removal of the files (if any)
*/
- if (userIndexRelation->rd_rel->relkind != RELKIND_PARTITIONED_INDEX)
+ if (RELKIND_HAS_STORAGE(userIndexRelation->rd_rel->relkind))
RelationDropStorage(userIndexRelation);
/*
diff --git a/src/backend/commands/indexcmds.c b/src/backend/commands/indexcmds.c
index c14ca27c5e..8d3104821e 100644
--- a/src/backend/commands/indexcmds.c
+++ b/src/backend/commands/indexcmds.c
@@ -2954,8 +2954,7 @@ reindex_error_callback(void *arg)
{
ReindexErrorInfo *errinfo = (ReindexErrorInfo *) arg;
- Assert(errinfo->relkind == RELKIND_PARTITIONED_INDEX ||
- errinfo->relkind == RELKIND_PARTITIONED_TABLE);
+ Assert(RELKIND_HAS_PARTITIONS(errinfo->relkind));
if (errinfo->relkind == RELKIND_PARTITIONED_TABLE)
errcontext("while reindexing partitioned table \"%s.%s\"",
@@ -2984,8 +2983,7 @@ ReindexPartitions(Oid relid, ReindexParams *params, bool
isTopLevel)
ErrorContextCallback errcallback;
ReindexErrorInfo errinfo;
- Assert(relkind == RELKIND_PARTITIONED_INDEX ||
- relkind == RELKIND_PARTITIONED_TABLE);
+ Assert(RELKIND_HAS_PARTITIONS(relkind));
/*
* Check if this runs in a transaction block, with an error callback to
@@ -3118,8 +3116,7 @@ ReindexMultipleInternal(List *relids, ReindexParams
*params)
* Partitioned tables and indexes can never be processed
directly, and
* a list of their leaves should be built first.
*/
- Assert(relkind != RELKIND_PARTITIONED_INDEX &&
- relkind != RELKIND_PARTITIONED_TABLE);
+ Assert(!RELKIND_HAS_PARTITIONS(relkind));
if ((params->options & REINDEXOPT_CONCURRENTLY) != 0 &&
relpersistence != RELPERSISTENCE_TEMP)
diff --git a/src/backend/commands/tablecmds.c b/src/backend/commands/tablecmds.c
index 857cc5ce6e..744ed51a9a 100644
--- a/src/backend/commands/tablecmds.c
+++ b/src/backend/commands/tablecmds.c
@@ -916,9 +916,7 @@ DefineRelation(CreateStmt *stmt, char relkind, Oid ownerId,
errmsg("specifying a table access
method is not supported on a partitioned table")));
}
- else if (relkind == RELKIND_RELATION ||
- relkind == RELKIND_TOASTVALUE ||
- relkind == RELKIND_MATVIEW)
+ else if (RELKIND_HAS_TABLE_AM(relkind))
accessMethod = default_table_access_method;
/* look up the access method, verify it is for a table */
@@ -13981,9 +13979,7 @@ ATExecSetTableSpace(Oid tableOid, Oid newTableSpace,
LOCKMODE lockmode)
}
else
{
- Assert(rel->rd_rel->relkind == RELKIND_RELATION ||
- rel->rd_rel->relkind == RELKIND_MATVIEW ||
- rel->rd_rel->relkind == RELKIND_TOASTVALUE);
+ Assert(RELKIND_HAS_TABLE_AM(rel->rd_rel->relkind));
table_relation_copy_data(rel, &newrnode);
}
diff --git a/src/backend/optimizer/util/plancat.c
b/src/backend/optimizer/util/plancat.c
index c5194fdbbf..564a38a13e 100644
--- a/src/backend/optimizer/util/plancat.c
+++ b/src/backend/optimizer/util/plancat.c
@@ -965,17 +965,13 @@ estimate_rel_size(Relation rel, int32 *attr_widths,
BlockNumber relallvisible;
double density;
- switch (rel->rd_rel->relkind)
+ if (RELKIND_HAS_TABLE_AM(rel->rd_rel->relkind))
{
- case RELKIND_RELATION:
- case RELKIND_MATVIEW:
- case RELKIND_TOASTVALUE:
table_relation_estimate_size(rel, attr_widths, pages,
tuples,
allvisfrac);
- break;
-
- case RELKIND_INDEX:
-
+ }
+ else if (rel->rd_rel->relkind == RELKIND_INDEX)
+ {
/*
* XXX: It'd probably be good to move this into a
callback,
* individual index types e.g. know if they have a
metapage.
@@ -991,7 +987,7 @@ estimate_rel_size(Relation rel, int32 *attr_widths,
{
*tuples = 0;
*allvisfrac = 0;
- break;
+ return;
}
/* coerce values in pg_class to more desirable types */
@@ -1055,27 +1051,18 @@ estimate_rel_size(Relation rel, int32 *attr_widths,
*allvisfrac = 1;
else
*allvisfrac = (double) relallvisible / curpages;
- break;
-
- case RELKIND_SEQUENCE:
- /* Sequences always have a known size */
- *pages = 1;
- *tuples = 1;
- *allvisfrac = 0;
- break;
- case RELKIND_FOREIGN_TABLE:
- /* Just use whatever's in pg_class */
- /* Note that FDW must cope if reltuples is -1! */
+ }
+ else
+ {
+ /*
+ * Just use whatever's in pg_class. This covers
foreign tables,
+ * sequences, and also relkinds without storage
(shouldn't get
+ * here?); see initializations in
AddNewRelationTuple(). Note
+ * that FDW must cope if reltuples is -1!
+ */
*pages = rel->rd_rel->relpages;
*tuples = rel->rd_rel->reltuples;
*allvisfrac = 0;
- break;
- default:
- /* else it has no disk storage; probably shouldn't get
here? */
- *pages = 0;
- *tuples = 0;
- *allvisfrac = 0;
- break;
}
}
diff --git a/src/backend/storage/buffer/bufmgr.c
b/src/backend/storage/buffer/bufmgr.c
index 08ebabfe96..16de918e2e 100644
--- a/src/backend/storage/buffer/bufmgr.c
+++ b/src/backend/storage/buffer/bufmgr.c
@@ -2934,37 +2934,26 @@ FlushBuffer(BufferDesc *buf, SMgrRelation reln)
BlockNumber
RelationGetNumberOfBlocksInFork(Relation relation, ForkNumber forkNum)
{
- switch (relation->rd_rel->relkind)
+ if (RELKIND_HAS_TABLE_AM(relation->rd_rel->relkind))
{
- case RELKIND_SEQUENCE:
- case RELKIND_INDEX:
- return smgrnblocks(RelationGetSmgr(relation), forkNum);
-
- case RELKIND_RELATION:
- case RELKIND_TOASTVALUE:
- case RELKIND_MATVIEW:
- {
- /*
- * Not every table AM uses BLCKSZ wide fixed
size blocks.
- * Therefore tableam returns the size in bytes
- but for the
- * purpose of this routine, we want the number
of blocks.
- * Therefore divide, rounding up.
- */
- uint64 szbytes;
+ /*
+ * Not every table AM uses BLCKSZ wide fixed size blocks.
+ * Therefore tableam returns the size in bytes - but for the
+ * purpose of this routine, we want the number of blocks.
+ * Therefore divide, rounding up.
+ */
+ uint64 szbytes;
- szbytes = table_relation_size(relation,
forkNum);
+ szbytes = table_relation_size(relation, forkNum);
- return (szbytes + (BLCKSZ - 1)) / BLCKSZ;
- }
- case RELKIND_VIEW:
- case RELKIND_COMPOSITE_TYPE:
- case RELKIND_FOREIGN_TABLE:
- case RELKIND_PARTITIONED_INDEX:
- case RELKIND_PARTITIONED_TABLE:
- default:
- Assert(false);
- break;
+ return (szbytes + (BLCKSZ - 1)) / BLCKSZ;
+ }
+ else if (RELKIND_HAS_STORAGE(relation->rd_rel->relkind))
+ {
+ return smgrnblocks(RelationGetSmgr(relation), forkNum);
}
+ else
+ Assert(false);
return 0; /* keep compiler quiet
*/
}
diff --git a/src/backend/utils/adt/partitionfuncs.c
b/src/backend/utils/adt/partitionfuncs.c
index 03660d5db6..61aeab75dd 100644
--- a/src/backend/utils/adt/partitionfuncs.c
+++ b/src/backend/utils/adt/partitionfuncs.c
@@ -45,9 +45,7 @@ check_rel_can_be_partition(Oid relid)
relispartition = get_rel_relispartition(relid);
/* Only allow relation types that can appear in partition trees. */
- if (!relispartition &&
- relkind != RELKIND_PARTITIONED_TABLE &&
- relkind != RELKIND_PARTITIONED_INDEX)
+ if (!relispartition && !RELKIND_HAS_PARTITIONS(relkind))
return false;
return true;
@@ -143,8 +141,7 @@ pg_partition_tree(PG_FUNCTION_ARGS)
nulls[1] = true;
/* isleaf */
- values[2] = BoolGetDatum(relkind != RELKIND_PARTITIONED_TABLE &&
- relkind !=
RELKIND_PARTITIONED_INDEX);
+ values[2] = BoolGetDatum(!RELKIND_HAS_PARTITIONS(relkind));
/* level */
if (relid != rootrelid)
diff --git a/src/backend/utils/cache/relcache.c
b/src/backend/utils/cache/relcache.c
index 9fa9e671a1..e6a3e16dcf 100644
--- a/src/backend/utils/cache/relcache.c
+++ b/src/backend/utils/cache/relcache.c
@@ -1203,30 +1203,14 @@ RelationBuildDesc(Oid targetRelId, bool insertIt)
/*
* initialize access method information
*/
- switch (relation->rd_rel->relkind)
- {
- case RELKIND_INDEX:
- case RELKIND_PARTITIONED_INDEX:
- Assert(relation->rd_rel->relam != InvalidOid);
- RelationInitIndexAccessInfo(relation);
- break;
- case RELKIND_RELATION:
- case RELKIND_TOASTVALUE:
- case RELKIND_MATVIEW:
- Assert(relation->rd_rel->relam != InvalidOid);
- RelationInitTableAccessMethod(relation);
- break;
- case RELKIND_SEQUENCE:
- Assert(relation->rd_rel->relam == InvalidOid);
- RelationInitTableAccessMethod(relation);
- break;
- case RELKIND_VIEW:
- case RELKIND_COMPOSITE_TYPE:
- case RELKIND_FOREIGN_TABLE:
- case RELKIND_PARTITIONED_TABLE:
- Assert(relation->rd_rel->relam == InvalidOid);
- break;
- }
+ if (relation->rd_rel->relkind == RELKIND_INDEX ||
+ relation->rd_rel->relkind == RELKIND_PARTITIONED_INDEX)
+ RelationInitIndexAccessInfo(relation);
+ else if (RELKIND_HAS_TABLE_AM(relation->rd_rel->relkind) ||
+ relation->rd_rel->relkind == RELKIND_SEQUENCE)
+ RelationInitTableAccessMethod(relation);
+ else
+ Assert(relation->rd_rel->relam == InvalidOid);
/* extract reloptions if any */
RelationParseRelOptions(relation, pg_class_tuple);
@@ -1444,6 +1428,7 @@ RelationInitIndexAccessInfo(Relation relation)
/*
* Look up the index's access method, save the OID of its handler
function
*/
+ Assert(relation->rd_rel->relam != InvalidOid);
tuple = SearchSysCache1(AMOID,
ObjectIdGetDatum(relation->rd_rel->relam));
if (!HeapTupleIsValid(tuple))
elog(ERROR, "cache lookup failed for access method %u",
@@ -1803,6 +1788,7 @@ RelationInitTableAccessMethod(Relation relation)
* seem prudent to show that in the catalog. So just overwrite
it
* here.
*/
+ Assert(relation->rd_rel->relam == InvalidOid);
relation->rd_amhandler = F_HEAP_TABLEAM_HANDLER;
}
else if (IsCatalogRelation(relation))
@@ -3638,10 +3624,7 @@ RelationBuildLocalRelation(const char *relname,
*/
MemoryContextSwitchTo(oldcxt);
- if (relkind == RELKIND_RELATION ||
- relkind == RELKIND_SEQUENCE ||
- relkind == RELKIND_TOASTVALUE ||
- relkind == RELKIND_MATVIEW)
+ if (RELKIND_HAS_TABLE_AM(relkind) || relkind == RELKIND_SEQUENCE)
RelationInitTableAccessMethod(rel);
/*
@@ -3730,32 +3713,25 @@ RelationSetNewRelfilenode(Relation relation, char
persistence)
newrnode = relation->rd_node;
newrnode.relNode = newrelfilenode;
- switch (relation->rd_rel->relkind)
+ if (RELKIND_HAS_TABLE_AM(relation->rd_rel->relkind))
{
- case RELKIND_INDEX:
- case RELKIND_SEQUENCE:
- {
- /* handle these directly, at least for now */
- SMgrRelation srel;
-
- srel = RelationCreateStorage(newrnode,
persistence);
- smgrclose(srel);
- }
- break;
-
- case RELKIND_RELATION:
- case RELKIND_TOASTVALUE:
- case RELKIND_MATVIEW:
- table_relation_set_new_filenode(relation, &newrnode,
-
persistence,
-
&freezeXid, &minmulti);
- break;
+ table_relation_set_new_filenode(relation, &newrnode,
+
persistence,
+
&freezeXid, &minmulti);
+ }
+ else if (RELKIND_HAS_STORAGE(relation->rd_rel->relkind))
+ {
+ /* handle these directly, at least for now */
+ SMgrRelation srel;
- default:
- /* we shouldn't be called for anything else */
- elog(ERROR, "relation \"%s\" does not have storage",
- RelationGetRelationName(relation));
- break;
+ srel = RelationCreateStorage(newrnode, persistence);
+ smgrclose(srel);
+ }
+ else
+ {
+ /* we shouldn't be called for anything else */
+ elog(ERROR, "relation \"%s\" does not have storage",
+ RelationGetRelationName(relation));
}
/*
@@ -4207,10 +4183,7 @@ RelationCacheInitializePhase3(void)
/* Reload tableam data if needed */
if (relation->rd_tableam == NULL &&
- (relation->rd_rel->relkind == RELKIND_RELATION ||
- relation->rd_rel->relkind == RELKIND_SEQUENCE ||
- relation->rd_rel->relkind == RELKIND_TOASTVALUE ||
- relation->rd_rel->relkind == RELKIND_MATVIEW))
+ (RELKIND_HAS_TABLE_AM(relation->rd_rel->relkind) ||
relation->rd_rel->relkind == RELKIND_SEQUENCE))
{
RelationInitTableAccessMethod(relation);
Assert(relation->rd_tableam != NULL);
@@ -6120,10 +6093,7 @@ load_relcache_init_file(bool shared)
nailed_rels++;
/* Load table AM data */
- if (rel->rd_rel->relkind == RELKIND_RELATION ||
- rel->rd_rel->relkind == RELKIND_SEQUENCE ||
- rel->rd_rel->relkind == RELKIND_TOASTVALUE ||
- rel->rd_rel->relkind == RELKIND_MATVIEW)
+ if (RELKIND_HAS_TABLE_AM(rel->rd_rel->relkind) ||
rel->rd_rel->relkind == RELKIND_SEQUENCE)
RelationInitTableAccessMethod(rel);
Assert(rel->rd_index == NULL);
diff --git a/src/bin/pg_dump/pg_dump.c b/src/bin/pg_dump/pg_dump.c
index f3c6c28480..a5ee03bb75 100644
--- a/src/bin/pg_dump/pg_dump.c
+++ b/src/bin/pg_dump/pg_dump.c
@@ -16439,17 +16439,26 @@ dumpTableSchema(Archive *fout, const TableInfo
*tbinfo)
if (tbinfo->dobj.dump & DUMP_COMPONENT_DEFINITION)
{
+ char *tablespace = NULL;
char *tableam = NULL;
- if (tbinfo->relkind == RELKIND_RELATION ||
- tbinfo->relkind == RELKIND_MATVIEW)
+ /*
+ * _selectTablespace() relies on tablespace-enabled objects in
the
+ * default tablespace to have a tablespace of "" (empty string)
versus
+ * non-tablespace-enabled objects to have a tablespace of NULL.
+ * getTables() sets tbinfo->reltablespace to "" for the default
+ * tablespace (not NULL).
+ */
+ if (RELKIND_HAS_TABLESPACE(tbinfo->relkind))
+ tablespace = tbinfo->reltablespace;
+
+ if (RELKIND_HAS_TABLE_AM(tbinfo->relkind))
tableam = tbinfo->amname;
ArchiveEntry(fout, tbinfo->dobj.catId, tbinfo->dobj.dumpId,
ARCHIVE_OPTS(.tag = tbinfo->dobj.name,
.namespace =
tbinfo->dobj.namespace->dobj.name,
- .tablespace =
(tbinfo->relkind == RELKIND_VIEW) ?
- NULL :
tbinfo->reltablespace,
+ .tablespace =
tablespace,
.tableam =
tableam,
.owner =
tbinfo->rolname,
.description
= reltypename,
diff --git a/src/include/catalog/pg_class.h b/src/include/catalog/pg_class.h
index fef9945ed8..93338d267c 100644
--- a/src/include/catalog/pg_class.h
+++ b/src/include/catalog/pg_class.h
@@ -198,6 +198,31 @@ DECLARE_INDEX(pg_class_tblspc_relfilenode_index, 3455,
ClassTblspcRelfilenodeInd
(relkind) == RELKIND_TOASTVALUE || \
(relkind) == RELKIND_MATVIEW)
+#define RELKIND_HAS_PARTITIONS(relkind) \
+ ((relkind) == RELKIND_PARTITIONED_TABLE || \
+ (relkind) == RELKIND_PARTITIONED_INDEX)
+
+/*
+ * Relation kinds that support tablespaces: All relation kinds with storage
+ * support tablespaces, except that we don't support moving sequences around
+ * into different tablespaces. Partitioned tables and indexes don't have
+ * physical storage, but they have a tablespace settings so that their
+ * children can inherit it.
+ */
+#define RELKIND_HAS_TABLESPACE(relkind) \
+ ((RELKIND_HAS_STORAGE(relkind) || RELKIND_HAS_PARTITIONS(relkind)) \
+ && (relkind) != RELKIND_SEQUENCE)
+
+/*
+ * Relation kinds with a table access method (rd_tableam). Although sequences
+ * use the heap table AM, they are enough of a special case in most uses that
+ * they are not included here.
+ */
+#define RELKIND_HAS_TABLE_AM(relkind) \
+ ((relkind) == RELKIND_RELATION || \
+ (relkind) == RELKIND_TOASTVALUE || \
+ (relkind) == RELKIND_MATVIEW)
+
extern int errdetail_relkind_not_supported(char relkind);
#endif /*
EXPOSE_TO_CLIENT_CODE */
--
2.33.1