mirror of
https://github.com/postgres/postgres.git
synced 2025-04-27 22:56:53 +03:00
The code recorded cache invalidation events by zeroing the "localreloid" field of affected cache entries. However, it's possible for an inval event to occur even while we have the entry open and locked. So an ill-timed inval could result in "cache lookup failed for relation 0" errors, if the worker's code tried to use the cleared field. We can fix that by creating a separate bool field to record whether the entry needs to be revalidated. (In the back branches, cram the bool into what had been padding space, to avoid an ABI break in the somewhat unlikely event that any extension is looking at this struct.) Also, rearrange the logic in logicalrep_rel_open so that it does the right thing in cases where table_open would fail. We should retry the lookup by name in that case, but we didn't. The real-world impact of this is probably small. In the first place, the error conditions are very low probability, and in the second place, the worker would just exit and get restarted. We only noticed because in a CLOBBER_CACHE_ALWAYS build, the failure can occur repeatedly, preventing the worker from making progress. Nonetheless, it's clearly a bug, and it impedes a useful type of testing; so back-patch to v10 where this code was introduced. Discussion: https://postgr.es/m/1032727.1600096803@sss.pgh.pa.us
48 lines
1.6 KiB
C
48 lines
1.6 KiB
C
/*-------------------------------------------------------------------------
|
|
*
|
|
* logicalrelation.h
|
|
* Relation definitions for logical replication relation mapping.
|
|
*
|
|
* Portions Copyright (c) 2016-2020, PostgreSQL Global Development Group
|
|
*
|
|
* src/include/replication/logicalrelation.h
|
|
*
|
|
*-------------------------------------------------------------------------
|
|
*/
|
|
#ifndef LOGICALRELATION_H
|
|
#define LOGICALRELATION_H
|
|
|
|
#include "access/attmap.h"
|
|
#include "replication/logicalproto.h"
|
|
|
|
typedef struct LogicalRepRelMapEntry
|
|
{
|
|
LogicalRepRelation remoterel; /* key is remoterel.remoteid */
|
|
|
|
/* Mapping to local relation. */
|
|
Oid localreloid; /* local relation id */
|
|
Relation localrel; /* relcache entry (NULL when closed) */
|
|
AttrMap *attrmap; /* map of local attributes to remote ones */
|
|
bool updatable; /* Can apply updates/deletes? */
|
|
|
|
/* Sync state. */
|
|
char state;
|
|
/* Validity flag ... inserted here to avoid ABI break in back branches. */
|
|
bool localrelvalid;
|
|
XLogRecPtr statelsn;
|
|
} LogicalRepRelMapEntry;
|
|
|
|
extern void logicalrep_relmap_update(LogicalRepRelation *remoterel);
|
|
|
|
extern LogicalRepRelMapEntry *logicalrep_rel_open(LogicalRepRelId remoteid,
|
|
LOCKMODE lockmode);
|
|
extern LogicalRepRelMapEntry *logicalrep_partition_open(LogicalRepRelMapEntry *root,
|
|
Relation partrel, AttrMap *map);
|
|
extern void logicalrep_rel_close(LogicalRepRelMapEntry *rel,
|
|
LOCKMODE lockmode);
|
|
|
|
extern void logicalrep_typmap_update(LogicalRepTyp *remotetyp);
|
|
extern char *logicalrep_typmap_gettypname(Oid remoteid);
|
|
|
|
#endif /* LOGICALRELATION_H */
|