1
0
mirror of https://github.com/postgres/postgres.git synced 2025-08-24 09:27:52 +03:00

Release cache tuple when no longer needed

There was a small buglet in commit 52e4f0cd47 whereby a tuple acquired
from cache was not released, giving rise to WARNING messages; fix that.

While at it, restructure the code a bit on stylistic grounds.

Author: Hou zj <houzj.fnst@fujitsu.com>
Reported-by: Peter Smith <smithpb2250@gmail.com>
Reviewed-by: Amit Kapila <amit.kapila16@gmail.com>
Discussion: https://postgr.es/m/CAHut+PvKTyhTBtYCQsP6Ph7=o-oWRSX+v+PXXLXp81-o2bazig@mail.gmail.com
This commit is contained in:
Alvaro Herrera
2022-04-13 18:19:38 +02:00
parent 112fdb3528
commit ed0fbc8e5a
3 changed files with 69 additions and 52 deletions

View File

@@ -925,8 +925,9 @@ AlterPublicationOptions(ParseState *pstate, AlterPublicationStmt *stmt,
/*
* If the publication doesn't publish changes via the root partitioned
* table, the partition's row filter and column list will be used. So disallow
* using WHERE clause and column lists on partitioned table in this case.
* table, the partition's row filter and column list will be used. So
* disallow using WHERE clause and column lists on partitioned table in
* this case.
*/
if (!pubform->puballtables && publish_via_partition_root_given &&
!publish_via_partition_root)
@@ -945,60 +946,60 @@ AlterPublicationOptions(ParseState *pstate, AlterPublicationStmt *stmt,
foreach(lc, root_relids)
{
HeapTuple rftuple;
Oid relid = lfirst_oid(lc);
bool has_column_list;
bool has_row_filter;
HeapTuple rftuple;
char relkind;
char *relname;
bool has_rowfilter;
bool has_collist;
/*
* Beware: we don't have lock on the relations, so cope silently
* with the cache lookups returning NULL.
*/
rftuple = SearchSysCache2(PUBLICATIONRELMAP,
ObjectIdGetDatum(relid),
ObjectIdGetDatum(pubform->oid));
has_row_filter
= !heap_attisnull(rftuple, Anum_pg_publication_rel_prqual, NULL);
has_column_list
= !heap_attisnull(rftuple, Anum_pg_publication_rel_prattrs, NULL);
if (HeapTupleIsValid(rftuple) &&
(has_row_filter || has_column_list))
if (!HeapTupleIsValid(rftuple))
continue;
has_rowfilter = !heap_attisnull(rftuple, Anum_pg_publication_rel_prqual, NULL);
has_collist = !heap_attisnull(rftuple, Anum_pg_publication_rel_prattrs, NULL);
if (!has_rowfilter && !has_collist)
{
HeapTuple tuple;
tuple = SearchSysCache1(RELOID, ObjectIdGetDatum(relid));
if (HeapTupleIsValid(tuple))
{
Form_pg_class relform = (Form_pg_class) GETSTRUCT(tuple);
if ((relform->relkind == RELKIND_PARTITIONED_TABLE) &&
has_row_filter)
ereport(ERROR,
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
errmsg("cannot set %s for publication \"%s\"",
"publish_via_partition_root = false",
stmt->pubname),
errdetail("The publication contains a WHERE clause for a partitioned table \"%s\" "
"which is not allowed when %s is false.",
NameStr(relform->relname),
"publish_via_partition_root")));
if ((relform->relkind == RELKIND_PARTITIONED_TABLE) &&
has_column_list)
ereport(ERROR,
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
errmsg("cannot set %s for publication \"%s\"",
"publish_via_partition_root = false",
stmt->pubname),
errdetail("The publication contains a column list for a partitioned table \"%s\" "
"which is not allowed when %s is false.",
NameStr(relform->relname),
"publish_via_partition_root")));
ReleaseSysCache(tuple);
}
ReleaseSysCache(rftuple);
continue;
}
relkind = get_rel_relkind(relid);
if (relkind != RELKIND_PARTITIONED_TABLE)
{
ReleaseSysCache(rftuple);
continue;
}
relname = get_rel_name(relid);
if (relname == NULL) /* table concurrently dropped */
{
ReleaseSysCache(rftuple);
continue;
}
if (has_rowfilter)
ereport(ERROR,
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
errmsg("cannot set parameter \"%s\" to false for publication \"%s\"",
"publish_via_partition_root",
stmt->pubname),
errdetail("The publication contains a WHERE clause for partitioned table \"%s\", which is not allowed when \"%s\" is false.",
relname, "publish_via_partition_root")));
Assert(has_collist);
ereport(ERROR,
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
errmsg("cannot set parameter \"%s\" to false for publication \"%s\"",
"publish_via_partition_root",
stmt->pubname),
errdetail("The publication contains a column list for partitioned table \"%s\", which is not allowed when \"%s\" is false.",
relname, "publish_via_partition_root")));
}
}