Skip to content

Commit ef92b82

Browse files
committed
Further cleanup in _bt_first: eliminate duplicate code paths.
1 parent 550d347 commit ef92b82

File tree

1 file changed

+70
-99
lines changed

1 file changed

+70
-99
lines changed

src/backend/access/nbtree/nbtsearch.c

Lines changed: 70 additions & 99 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88
* Portions Copyright (c) 1994, Regents of the University of California
99
*
1010
* IDENTIFICATION
11-
* $PostgreSQL: pgsql/src/backend/access/nbtree/nbtsearch.c,v 1.85 2003/12/21 03:00:04 tgl Exp $
11+
* $PostgreSQL: pgsql/src/backend/access/nbtree/nbtsearch.c,v 1.86 2003/12/21 17:52:34 tgl Exp $
1212
*
1313
*-------------------------------------------------------------------------
1414
*/
@@ -496,6 +496,7 @@ _bt_first(IndexScanDesc scan, ScanDirection dir)
496496
StrategyNumber strat;
497497
bool res;
498498
bool nextkey;
499+
bool goback;
499500
bool continuescan;
500501
ScanKey scankeys;
501502
ScanKey *startKeys = NULL;
@@ -695,18 +696,41 @@ _bt_first(IndexScanDesc scan, ScanDirection dir)
695696
pfree(startKeys);
696697

697698
/*
698-
* We want to locate either the first item >= boundary point, or
699-
* first item > boundary point, depending on the initial-positioning
700-
* strategy we just chose.
699+
* Examine the selected initial-positioning strategy to determine
700+
* exactly where we need to start the scan, and set flag variables
701+
* to control the code below.
702+
*
703+
* If nextkey = false, _bt_search and _bt_binsrch will locate the
704+
* first item >= scan key. If nextkey = true, they will locate the
705+
* first item > scan key.
706+
*
707+
* If goback = true, we will then step back one item, while if
708+
* goback = false, we will start the scan on the located item.
709+
*
710+
* it's yet other place to add some code later for is(not)null ...
701711
*/
702712
switch (strat_total)
703713
{
704714
case BTLessStrategyNumber:
715+
/*
716+
* Find first item >= scankey, then back up one to arrive at last
717+
* item < scankey. (Note: this positioning strategy is only used
718+
* for a backward scan, so that is always the correct starting
719+
* position.)
720+
*/
705721
nextkey = false;
722+
goback = true;
706723
break;
707724

708725
case BTLessEqualStrategyNumber:
726+
/*
727+
* Find first item > scankey, then back up one to arrive at last
728+
* item <= scankey. (Note: this positioning strategy is only used
729+
* for a backward scan, so that is always the correct starting
730+
* position.)
731+
*/
709732
nextkey = true;
733+
goback = true;
710734
break;
711735

712736
case BTEqualStrategyNumber:
@@ -715,17 +739,41 @@ _bt_first(IndexScanDesc scan, ScanDirection dir)
715739
* equal item not first one.
716740
*/
717741
if (ScanDirectionIsBackward(dir))
742+
{
743+
/*
744+
* This is the same as the <= strategy. We will check
745+
* at the end whether the found item is actually =.
746+
*/
718747
nextkey = true;
748+
goback = true;
749+
}
719750
else
751+
{
752+
/*
753+
* This is the same as the >= strategy. We will check
754+
* at the end whether the found item is actually =.
755+
*/
720756
nextkey = false;
757+
goback = false;
758+
}
721759
break;
722760

723761
case BTGreaterEqualStrategyNumber:
762+
/*
763+
* Find first item >= scankey. (This is only used for
764+
* forward scans.)
765+
*/
724766
nextkey = false;
767+
goback = false;
725768
break;
726769

727770
case BTGreaterStrategyNumber:
771+
/*
772+
* Find first item > scankey. (This is only used for
773+
* forward scans.)
774+
*/
728775
nextkey = true;
776+
goback = false;
729777
break;
730778

731779
default:
@@ -756,21 +804,18 @@ _bt_first(IndexScanDesc scan, ScanDirection dir)
756804

757805
/* remember which buffer we have pinned */
758806
so->btso_curbuf = buf;
759-
blkno = BufferGetBlockNumber(buf);
760-
page = BufferGetPage(buf);
761807

762808
/* position to the precise item on the page */
763809
offnum = _bt_binsrch(rel, buf, keysCount, scankeys, nextkey);
764810

811+
page = BufferGetPage(buf);
812+
blkno = BufferGetBlockNumber(buf);
765813
ItemPointerSet(current, blkno, offnum);
766814

767815
/* done with manufactured scankey, now */
768816
pfree(scankeys);
769817

770818
/*
771-
* It's now time to examine the initial-positioning strategy to find the
772-
* exact place to start the scan.
773-
*
774819
* If nextkey = false, we are positioned at the first item >= scan key,
775820
* or possibly at the end of a page on which all the existing items are
776821
* less than the scan key and we know that everything on later pages
@@ -781,103 +826,29 @@ _bt_first(IndexScanDesc scan, ScanDirection dir)
781826
* less than or equal to the scan key and we know that everything on
782827
* later pages is greater than scan key.
783828
*
784-
* The actually desired starting point is either this item or an adjacent
785-
* one, or in the end-of-page case it's the last item on this page or
786-
* the first item on the next. We apply _bt_step if needed to get to
829+
* The actually desired starting point is either this item or the prior
830+
* one, or in the end-of-page case it's the first item on the next page
831+
* or the last item on this page. We apply _bt_step if needed to get to
787832
* the right place.
788833
*
789-
* Note: if _bt_step fails (meaning we fell off the end of the index in
834+
* If _bt_step fails (meaning we fell off the end of the index in
790835
* one direction or the other), then there are no matches so we just
791836
* return false.
792-
*
793-
* it's yet other place to add some code later for is(not)null ...
794837
*/
795-
switch (strat_total)
838+
if (goback)
796839
{
797-
case BTLessStrategyNumber:
798-
799-
/*
800-
* We are on first item >= scankey.
801-
*
802-
* Back up one to arrive at last item < scankey. (Note: this
803-
* positioning strategy is only used for a backward scan, so
804-
* that is always the correct starting position.)
805-
*/
806-
if (!_bt_step(scan, &buf, BackwardScanDirection))
807-
return false;
808-
break;
809-
810-
case BTLessEqualStrategyNumber:
811-
812-
/*
813-
* We are on first item > scankey.
814-
*
815-
* Back up one to arrive at last item <= scankey. (Note: this
816-
* positioning strategy is only used for a backward scan, so
817-
* that is always the correct starting position.)
818-
*/
819-
if (!_bt_step(scan, &buf, BackwardScanDirection))
840+
/* _bt_step will do the right thing if we are at end-of-page */
841+
if (!_bt_step(scan, &buf, BackwardScanDirection))
842+
return false;
843+
}
844+
else
845+
{
846+
/* If we're at end-of-page, must step forward to next page */
847+
if (offnum > PageGetMaxOffsetNumber(page))
848+
{
849+
if (!_bt_step(scan, &buf, ForwardScanDirection))
820850
return false;
821-
break;
822-
823-
case BTEqualStrategyNumber:
824-
/*
825-
* If a backward scan was specified, need to start with last
826-
* equal item not first one.
827-
*/
828-
if (ScanDirectionIsBackward(dir))
829-
{
830-
/*
831-
* We are on first item > scankey.
832-
*
833-
* Back up one to arrive at last item <= scankey.
834-
* We will check below to see if it is equal to scankey.
835-
*/
836-
if (!_bt_step(scan, &buf, BackwardScanDirection))
837-
return false;
838-
}
839-
else
840-
{
841-
/*
842-
* We are on first item >= scankey.
843-
*
844-
* Make sure we are on a real item; might have to
845-
* step forward if currently at end of page.
846-
* We will check below to see if it is equal to scankey.
847-
*/
848-
if (offnum > PageGetMaxOffsetNumber(page))
849-
{
850-
if (!_bt_step(scan, &buf, ForwardScanDirection))
851-
return false;
852-
}
853-
}
854-
break;
855-
856-
case BTGreaterEqualStrategyNumber:
857-
858-
/*
859-
* We want the first item >= scankey, which is where we are...
860-
* unless we're not anywhere at all...
861-
*/
862-
if (offnum > PageGetMaxOffsetNumber(page))
863-
{
864-
if (!_bt_step(scan, &buf, ForwardScanDirection))
865-
return false;
866-
}
867-
break;
868-
869-
case BTGreaterStrategyNumber:
870-
871-
/*
872-
* We want the first item > scankey, which is where we are...
873-
* unless we're not anywhere at all...
874-
*/
875-
if (offnum > PageGetMaxOffsetNumber(page))
876-
{
877-
if (!_bt_step(scan, &buf, ForwardScanDirection))
878-
return false;
879-
}
880-
break;
851+
}
881852
}
882853

883854
/* okay, current item pointer for the scan is right */

0 commit comments

Comments
 (0)