Ahh ... you know what, never mind about stack traces, let's just see if the attached patch doesn't fix it.
I still haven't reproduced the behavior here, but I think I see what must be happening: we are getting an sinval reset while attempting to open pg_class_oid_index. The latter condition causes its refcount to be above 1, which will cause RelationClearRelation to directly call RelationReloadIndexInfo, which enables the following sequence of calls: RelationCacheInvalidate -> RelationClearRelation -> RelationReloadIndexInfo. And the problem is that RelationCacheInvalidate intentionally forces pg_class_oid_index to be updated first. That was okay when the code was written, because the relcache entry for pg_class itself never really needed any updates. Now it does, so we have to make sure pg_class gets updated first, *then* pg_class_oid_index (which might result in a seqscan of pg_class), then everything else (for which we'll try to use pg_class_oid_index to locate their pg_class tuples). regards, tom lane
diff --git a/src/backend/utils/cache/relcache.c b/src/backend/utils/cache/relcache.c index 81cea8b..0e4b17c 100644 *** a/src/backend/utils/cache/relcache.c --- b/src/backend/utils/cache/relcache.c *************** RelationCacheInvalidate(void) *** 2185,2204 **** { /* * Add this entry to list of stuff to rebuild in second pass. ! * pg_class_oid_index goes on the front of rebuildFirstList, other ! * nailed indexes on the back, and everything else into ! * rebuildList (in no particular order). */ ! if (relation->rd_isnailed && ! relation->rd_rel->relkind == RELKIND_INDEX) { if (RelationGetRelid(relation) == ClassOidIndexId) - rebuildFirstList = lcons(relation, rebuildFirstList); - else rebuildFirstList = lappend(rebuildFirstList, relation); } else ! rebuildList = lcons(relation, rebuildList); } } --- 2185,2207 ---- { /* * Add this entry to list of stuff to rebuild in second pass. ! * pg_class goes on the front of rebuildFirstList, ! * pg_class_oid_index goes to the back of rebuildFirstList, other ! * nailed indexes go on the front of rebuildList, and everything ! * else goes to the back of rebuildList. */ ! if (RelationGetRelid(relation) == RelationRelationId) ! rebuildFirstList = lcons(relation, rebuildFirstList); ! else if (relation->rd_isnailed && ! relation->rd_rel->relkind == RELKIND_INDEX) { if (RelationGetRelid(relation) == ClassOidIndexId) rebuildFirstList = lappend(rebuildFirstList, relation); + else + rebuildList = lcons(relation, rebuildList); } else ! rebuildList = lappend(rebuildList, relation); } }
-- Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org) To make changes to your subscription: http://www.postgresql.org/mailpref/pgsql-hackers