Commit c3b51e0d authored by Vadim B. Mikheev's avatar Vadim B. Mikheev

Bug: backend crashes in btbeginscan()->btrescan()->_bt_orderkeys()

when btree used in innerscan with run-time key which value
passed by pointer.

Fix: keys ordering stuff moved to _bt_first().

Pointed by Thomas Lockhart.
parent 917abdd1
...@@ -8,7 +8,7 @@ ...@@ -8,7 +8,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/access/nbtree/nbtree.c,v 1.18 1997/04/18 03:37:53 vadim Exp $ * $Header: /cvsroot/pgsql/src/backend/access/nbtree/nbtree.c,v 1.19 1997/05/05 03:41:17 vadim Exp $
* *
* NOTES * NOTES
* This file contains only the public interface routines. * This file contains only the public interface routines.
...@@ -410,7 +410,6 @@ btrescan(IndexScanDesc scan, bool fromEnd, ScanKey scankey) ...@@ -410,7 +410,6 @@ btrescan(IndexScanDesc scan, bool fromEnd, ScanKey scankey)
{ {
ItemPointer iptr; ItemPointer iptr;
BTScanOpaque so; BTScanOpaque so;
StrategyNumber strat;
so = (BTScanOpaque) scan->opaque; so = (BTScanOpaque) scan->opaque;
...@@ -439,10 +438,11 @@ btrescan(IndexScanDesc scan, bool fromEnd, ScanKey scankey) ...@@ -439,10 +438,11 @@ btrescan(IndexScanDesc scan, bool fromEnd, ScanKey scankey)
scan->flags = 0x0; scan->flags = 0x0;
} }
/* reset the scan key */ /*
* Reset the scan keys. Note that keys ordering stuff
* moved to _bt_first. - vadim 05/05/97
*/
so->numberOfKeys = scan->numberOfKeys; so->numberOfKeys = scan->numberOfKeys;
so->numberOfFirstKeys = 0; /* may be changed by _bt_orderkeys */
so->qual_ok = 1; /* may be changed by _bt_orderkeys */
if (scan->numberOfKeys > 0) { if (scan->numberOfKeys > 0) {
memmove(scan->keyData, memmove(scan->keyData,
scankey, scankey,
...@@ -450,21 +450,6 @@ btrescan(IndexScanDesc scan, bool fromEnd, ScanKey scankey) ...@@ -450,21 +450,6 @@ btrescan(IndexScanDesc scan, bool fromEnd, ScanKey scankey)
memmove(so->keyData, memmove(so->keyData,
scankey, scankey,
so->numberOfKeys * sizeof(ScanKeyData)); so->numberOfKeys * sizeof(ScanKeyData));
/* order the keys in the qualification */
_bt_orderkeys(scan->relation, so);
}
/* finally, be sure that the scan exploits the tree order */
scan->scanFromEnd = false;
if ( so->numberOfKeys > 0 ) {
strat = _bt_getstrat(scan->relation, 1 /* XXX */,
so->keyData[0].sk_procedure);
if (strat == BTLessStrategyNumber
|| strat == BTLessEqualStrategyNumber)
scan->scanFromEnd = true;
} else {
scan->scanFromEnd = true;
} }
} }
......
...@@ -7,7 +7,7 @@ ...@@ -7,7 +7,7 @@
* *
* *
* IDENTIFICATION * IDENTIFICATION
* $Header: /cvsroot/pgsql/src/backend/access/nbtree/nbtsearch.c,v 1.18 1997/04/24 15:46:44 vadim Exp $ * $Header: /cvsroot/pgsql/src/backend/access/nbtree/nbtsearch.c,v 1.19 1997/05/05 03:41:19 vadim Exp $
* *
*------------------------------------------------------------------------- *-------------------------------------------------------------------------
*/ */
...@@ -751,16 +751,38 @@ _bt_first(IndexScanDesc scan, ScanDirection dir) ...@@ -751,16 +751,38 @@ _bt_first(IndexScanDesc scan, ScanDirection dir)
ScanKeyData skdata; ScanKeyData skdata;
Size keysok; Size keysok;
rel = scan->relation;
so = (BTScanOpaque) scan->opaque; so = (BTScanOpaque) scan->opaque;
if ( so->qual_ok == 0 ) /* may be set by _bt_orderkeys */
/*
* Order the keys in the qualification and be sure
* that the scan exploits the tree order.
*/
so->numberOfFirstKeys = 0; /* may be changed by _bt_orderkeys */
so->qual_ok = 1; /* may be changed by _bt_orderkeys */
scan->scanFromEnd = false;
if ( so->numberOfKeys > 0 )
{
_bt_orderkeys(rel, so);
strat = _bt_getstrat(rel, 1, so->keyData[0].sk_procedure);
/* NOTE: it assumes ForwardScanDirection */
if ( strat == BTLessStrategyNumber ||
strat == BTLessEqualStrategyNumber )
scan->scanFromEnd = true;
}
else
scan->scanFromEnd = true;
if ( so->qual_ok == 0 )
return ((RetrieveIndexResult) NULL); return ((RetrieveIndexResult) NULL);
/* if we just need to walk down one edge of the tree, do that */ /* if we just need to walk down one edge of the tree, do that */
if (scan->scanFromEnd) if (scan->scanFromEnd)
return (_bt_endpoint(scan, dir)); return (_bt_endpoint(scan, dir));
rel = scan->relation; itupdesc = RelationGetTupleDescriptor(rel);
itupdesc = RelationGetTupleDescriptor(scan->relation);
current = &(scan->currentItemData); current = &(scan->currentItemData);
/* /*
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment