diff --git a/src/backend/catalog/namespace.c b/src/backend/catalog/namespace.c index 5f68cc1377..2c9cea5826 100644 --- a/src/backend/catalog/namespace.c +++ b/src/backend/catalog/namespace.c @@ -3215,7 +3215,7 @@ isOtherTempNamespace(Oid namespaceId) } /* - * isTempNamespaceInUse - is the given namespace owned and actively used + * checkTempNamespaceStatus - is the given namespace owned and actively used * by a backend? * * Note: this can be used while scanning relations in pg_class to detect @@ -3223,8 +3223,8 @@ isOtherTempNamespace(Oid namespaceId) * given database. The result may be out of date quickly, so the caller * must be careful how to handle this information. */ -bool -isTempNamespaceInUse(Oid namespaceId) +TempNamespaceStatus +checkTempNamespaceStatus(Oid namespaceId) { PGPROC *proc; int backendId; @@ -3233,25 +3233,35 @@ isTempNamespaceInUse(Oid namespaceId) backendId = GetTempNamespaceBackendId(namespaceId); - /* No such temporary namespace? */ + /* No such namespace, or its name shows it's not temp? */ if (backendId == InvalidBackendId) - return false; + return TEMP_NAMESPACE_NOT_TEMP; /* Is the backend alive? */ proc = BackendIdGetProc(backendId); if (proc == NULL) - return false; + return TEMP_NAMESPACE_IDLE; /* Is the backend connected to the same database we are looking at? */ if (proc->databaseId != MyDatabaseId) - return false; + return TEMP_NAMESPACE_IDLE; /* Does the backend own the temporary namespace? */ if (proc->tempNamespaceId != namespaceId) - return false; + return TEMP_NAMESPACE_IDLE; - /* all good to go */ - return true; + /* Yup, so namespace is busy */ + return TEMP_NAMESPACE_IN_USE; +} + +/* + * isTempNamespaceInUse - oversimplified, deprecated version of + * checkTempNamespaceStatus + */ +bool +isTempNamespaceInUse(Oid namespaceId) +{ + return checkTempNamespaceStatus(namespaceId) == TEMP_NAMESPACE_IN_USE; } /* diff --git a/src/backend/postmaster/autovacuum.c b/src/backend/postmaster/autovacuum.c index 2d925d2ee0..ac0242c9d3 100644 --- a/src/backend/postmaster/autovacuum.c +++ b/src/backend/postmaster/autovacuum.c @@ -2089,9 +2089,10 @@ do_autovacuum(void) { /* * We just ignore it if the owning backend is still active and - * using the temporary schema. + * using the temporary schema. Also, for safety, ignore it if the + * namespace doesn't exist or isn't a temp namespace after all. */ - if (!isTempNamespaceInUse(classForm->relnamespace)) + if (checkTempNamespaceStatus(classForm->relnamespace) == TEMP_NAMESPACE_IDLE) { /* * The table seems to be orphaned -- although it might be that @@ -2261,7 +2262,7 @@ do_autovacuum(void) continue; } - if (isTempNamespaceInUse(classForm->relnamespace)) + if (checkTempNamespaceStatus(classForm->relnamespace) != TEMP_NAMESPACE_IDLE) { UnlockRelationOid(relid, AccessExclusiveLock); continue; diff --git a/src/include/catalog/namespace.h b/src/include/catalog/namespace.h index 1781751599..922529e39b 100644 --- a/src/include/catalog/namespace.h +++ b/src/include/catalog/namespace.h @@ -37,6 +37,16 @@ typedef struct _FuncCandidateList Oid args[FLEXIBLE_ARRAY_MEMBER]; /* arg types */ } *FuncCandidateList; +/* + * Result of checkTempNamespaceStatus + */ +typedef enum TempNamespaceStatus +{ + TEMP_NAMESPACE_NOT_TEMP, /* nonexistent, or non-temp namespace */ + TEMP_NAMESPACE_IDLE, /* exists, belongs to no active session */ + TEMP_NAMESPACE_IN_USE /* belongs to some active session */ +} TempNamespaceStatus; + /* * Structure for xxxOverrideSearchPath functions */ @@ -138,6 +148,7 @@ extern bool isTempToastNamespace(Oid namespaceId); extern bool isTempOrTempToastNamespace(Oid namespaceId); extern bool isAnyTempNamespace(Oid namespaceId); extern bool isOtherTempNamespace(Oid namespaceId); +extern TempNamespaceStatus checkTempNamespaceStatus(Oid namespaceId); extern bool isTempNamespaceInUse(Oid namespaceId); extern int GetTempNamespaceBackendId(Oid namespaceId); extern Oid GetTempToastNamespace(void);