Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit766dcfb

Browse files
committed
Fix off-by-one error in calculating subtrans/multixact truncation point.
If there were no subtransactions (or multixacts) active, we would calculatethe oldestxid == next xid. That's correct, but if next XID happens to beon the next pg_subtrans (pg_multixact) page, the page does not exist yet,and SimpleLruTruncate will produce an "apparent wraparound" warning. Thewarning is harmless in this case, but looks very alarming to users.Backpatch to all supported versions. Patch and analysis by Thomas Munro.
1 parent46d0a9b commit766dcfb

File tree

2 files changed

+16
-4
lines changed

2 files changed

+16
-4
lines changed

‎src/backend/access/transam/multixact.c

Lines changed: 10 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -173,6 +173,8 @@
173173
#defineMULTIXACT_MEMBER_DANGER_THRESHOLD\
174174
(MaxMultiXactOffset - MaxMultiXactOffset / 4)
175175

176+
#definePreviousMultiXactId(xid) \
177+
((xid) == FirstMultiXactId ? MaxMultiXactId : (xid) - 1)
176178

177179
/*
178180
* Links to shared-memory data structures for MultiXact control
@@ -3057,10 +3059,15 @@ TruncateMultiXact(void)
30573059

30583060
SlruScanDirectory(MultiXactMemberCtl,SlruScanDirCbRemoveMembers,&range);
30593061

3060-
/* Now we can truncate MultiXactOffset */
3062+
/*
3063+
* Now we can truncate MultiXactOffset. We step back one multixact to
3064+
* avoid passing a cutoff page that hasn't been created yet in the rare
3065+
* case that oldestMXact would be the first item on a page and oldestMXact
3066+
* == nextMXact. In that case, if we didn't subtract one, we'd trigger
3067+
* SimpleLruTruncate's wraparound detection.
3068+
*/
30613069
SimpleLruTruncate(MultiXactOffsetCtl,
3062-
MultiXactIdToOffsetPage(oldestMXact));
3063-
3070+
MultiXactIdToOffsetPage(PreviousMultiXactId(oldestMXact)));
30643071

30653072
/*
30663073
* Now, and only now, we can advance the stop point for multixact members.

‎src/backend/access/transam/subtrans.c

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -340,8 +340,13 @@ TruncateSUBTRANS(TransactionId oldestXact)
340340

341341
/*
342342
* The cutoff point is the start of the segment containing oldestXact. We
343-
* pass the *page* containing oldestXact to SimpleLruTruncate.
343+
* pass the *page* containing oldestXact to SimpleLruTruncate. We step
344+
* back one transaction to avoid passing a cutoff page that hasn't been
345+
* created yet in the rare case that oldestXact would be the first item on
346+
* a page and oldestXact == next XID. In that case, if we didn't subtract
347+
* one, we'd trigger SimpleLruTruncate's wraparound detection.
344348
*/
349+
TransactionIdRetreat(oldestXact);
345350
cutoffPage=TransactionIdToPage(oldestXact);
346351

347352
SimpleLruTruncate(SubTransCtl,cutoffPage);

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp