Skip to content

PG16: re-find the proclock after waiting instead of trusting a stale pointer - #85

Merged
akorotkov merged 1 commit into
patches16from
proclock-refind-after-wait-16
Aug 13, 2026
Merged

PG16: re-find the proclock after waiting instead of trusting a stale pointer#85
akorotkov merged 1 commit into
patches16from
proclock-refind-after-wait-16

Conversation

@akorotkov

Copy link
Copy Markdown
Contributor

PG16 counterpart of 2859252 on patches18 (ORI-247, PANIC: proclock table corrupted). Companion to #84 (PG17).

Why a cherry-pick does not apply. On PG18 LockAcquireExtended() releases
the partition lock before WaitOnLock(), so that fix re-takes it around the
lookup. On PG16 ProcSleep() holds the partition lock at entry and re-acquires
it LW_EXCLUSIVE before returning, so it is held here — acquiring it again
would self-deadlock. The lookup is a plain hash_search_with_hash_value.

Unlike PG17 there is no dontWait case in this block (a conditional
acquisition returns earlier), so the re-find is unconditional — this port is
the simpler of the two.

Also guarded the INCONSISTENT prints, which can now see a proclock that is
gone rather than merely one without our bit, and kept the local lock's cached
pointers in step on the granted path.

Validation

Built PG16 with orioledb and ran the same contended-upsert workload used for
the PG18 and PG17 fixes, with a probe reporting a proclock that was freed while
we slept: 161 hits in 60 seconds — 161 reads of freed shared memory that
this change no longer performs — with no panic and no assertion failure.

For the record, the same measurement across the three branches: PG18 163,
PG17 157, PG16 161 hits per 60 s. The defect is equally live on all three.

PG16 counterpart of 2859252 on patches18 (ORI-247, "PANIC: proclock
table corrupted").  A plain cherry-pick does not apply: on PG18
LockAcquireExtended() releases the partition lock before WaitOnLock() and
so the fix there re-takes it around the lookup, while on PG16 ProcSleep()
holds it at entry and re-acquires it EXCLUSIVE before returning -- taking
it again here would self-deadlock.  The lookup is therefore a plain
hash_search.

Unlike PG17 there is no dontWait case in this block (a conditional
acquisition returns earlier), so the re-find is unconditional.

Also guard the INCONSISTENT prints, which can now see a proclock that is
gone rather than merely one without our bit, and keep the local lock's
cached pointers in step on the granted path.

Verified the same way as the PG18 and PG17 fixes: with a probe reporting
a proclock that was freed while we slept, the contended-upsert workload
against orioledb hits it 161 times in 60 seconds on PG16 -- 161 reads of
freed shared memory that this change no longer performs -- and runs with
no panic and no assertion failure.
@akorotkov
akorotkov merged commit 9de7f2b into patches16 Aug 13, 2026
8 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant