Skip to content

Commit 8dcbdea

Browse files
committed
fix leftlink on right page while page is splitting
1 parent dfbffd8 commit 8dcbdea

File tree

1 file changed

+36
-4
lines changed

1 file changed

+36
-4
lines changed

rumbtree.c

Lines changed: 36 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -414,13 +414,14 @@ rumInsertValue(Relation index, RumBtree btree, RumBtreeStack * stack,
414414
btree->placeToPage(btree, page, stack->off);
415415

416416
if (btree->rumstate->isBuild)
417+
{
417418
MarkBufferDirty(stack->buffer);
419+
END_CRIT_SECTION();
420+
}
418421
else
419422
GenericXLogFinish(state);
420423

421424
LockBuffer(stack->buffer, RUM_UNLOCK);
422-
if (btree->rumstate->isBuild)
423-
END_CRIT_SECTION();
424425
freeRumBtreeStack(stack);
425426

426427
return;
@@ -520,6 +521,9 @@ rumInsertValue(Relation index, RumBtree btree, RumBtreeStack * stack,
520521
}
521522
else
522523
{
524+
BlockNumber rightrightBlkno = InvalidBlockNumber;
525+
Buffer rightrightBuffer;
526+
523527
/* split non-root page */
524528
if (btree->rumstate->isBuild)
525529
{
@@ -534,6 +538,8 @@ rumInsertValue(Relation index, RumBtree btree, RumBtreeStack * stack,
534538
rpage = GenericXLogRegisterBuffer(state, rbuffer, 0);
535539
}
536540

541+
rightrightBlkno = RumPageGetOpaque(lpage)->rightlink;
542+
537543
/*
538544
* newlpage is a pointer to memory page, it doesn't associate
539545
* with buffer, stack->buffer should be untouched
@@ -546,6 +552,29 @@ rumInsertValue(Relation index, RumBtree btree, RumBtreeStack * stack,
546552
RumPageGetOpaque(rpage)->leftlink = BufferGetBlockNumber(stack->buffer);
547553
RumPageGetOpaque(newlpage)->rightlink = BufferGetBlockNumber(rbuffer);
548554

555+
/*
556+
* it's safe because we don't have right-to-left walking
557+
* with locking bth pages except vacuum. But vacuum will
558+
* try to lock all pages with conditional lock
559+
*/
560+
if (rightrightBlkno != InvalidBlockNumber)
561+
{
562+
Page rightrightPage;
563+
564+
rightrightBuffer = ReadBuffer(btree->index,
565+
rightrightBlkno);
566+
567+
LockBuffer(rightrightBuffer, RUM_EXCLUSIVE);
568+
if (btree->rumstate->isBuild)
569+
rightrightPage = BufferGetPage(rightrightBuffer);
570+
else
571+
rightrightPage =
572+
GenericXLogRegisterBuffer(state, rightrightBuffer, 0);
573+
574+
RumPageGetOpaque(rightrightPage)->leftlink =
575+
BufferGetBlockNumber(rbuffer);
576+
}
577+
549578
if (btree->rumstate->isBuild)
550579
START_CRIT_SECTION();
551580
PageRestoreTempPage(newlpage, lpage);
@@ -554,13 +583,16 @@ rumInsertValue(Relation index, RumBtree btree, RumBtreeStack * stack,
554583
{
555584
MarkBufferDirty(rbuffer);
556585
MarkBufferDirty(stack->buffer);
586+
if (rightrightBlkno != InvalidBlockNumber)
587+
MarkBufferDirty(rightrightBuffer);
588+
END_CRIT_SECTION();
557589
}
558590
else
559591
GenericXLogFinish(state);
560592

561593
UnlockReleaseBuffer(rbuffer);
562-
if (btree->rumstate->isBuild)
563-
END_CRIT_SECTION();
594+
if (rightrightBlkno != InvalidBlockNumber)
595+
UnlockReleaseBuffer(rightrightBuffer);
564596
}
565597
}
566598

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy