From 699073b75d71a8c0d1873bd7f6612e79ebde1a5f Mon Sep 17 00:00:00 2001
From: Matthias van de Meent <boekewurm+postgres@gmail.com>
Date: Tue, 21 Jul 2026 14:16:50 +0200
Subject: [PATCH v1] Fix Assert() in typcache.c

If an error is thrown in the initialization of the TYPEOID catcache
as part of lookup_type_cache, the error handling of that lookup would
cause Assert() failure: It needs to initialize the TYPEOID catcache
to handle the in_progress_list.
---
 src/backend/utils/cache/typcache.c | 18 ++++++++++++++++--
 1 file changed, 16 insertions(+), 2 deletions(-)

diff --git a/src/backend/utils/cache/typcache.c b/src/backend/utils/cache/typcache.c
index 650b5d9bad9..85808d27369 100644
--- a/src/backend/utils/cache/typcache.c
+++ b/src/backend/utils/cache/typcache.c
@@ -459,13 +459,27 @@ lookup_type_cache(Oid type_id, int flags)
 									allocsize * sizeof(*in_progress_list));
 		in_progress_list_maxlen = allocsize;
 	}
-	in_progress_offset = in_progress_list_len++;
-	in_progress_list[in_progress_offset] = type_id;
 
 	/* Try to look up an existing entry */
 	typentry = (TypeCacheEntry *) hash_search(TypeCacheHash,
 											  &type_id,
 											  HASH_FIND, NULL);
+
+	/*
+	 * Only mark the new entry as "in progress" after the initial lookup: the
+	 * TypeCacheHash uses type_cache_syshash(), which can initialize the
+	 * TYPEOID catcache, which in turn could fail on OOM.  The error handling
+	 * would then try to look up this in-progress typeid, and try to look up
+	 * the type in the caches, try to initialize the cache, which then fails
+	 * because we can't initialize catalog caches in the non-transactional
+	 * state of error wind-down.
+	 *
+	 * So, in short, we can't have an in-progress type cache element while
+	 * the TYPEOID catcache is initializing.
+	 */
+	in_progress_offset = in_progress_list_len++;
+	in_progress_list[in_progress_offset] = type_id;
+
 	if (typentry == NULL)
 	{
 		/*
-- 
2.50.1 (Apple Git-155)

