mirror of
https://github.com/sqlite/sqlite.git
synced 2025-08-05 15:55:57 +03:00
After an OP_NullRow is executed on a cursor, cause any subsequent OP_Next or OP_Prev to behave as if there were no more rows to traverse. Ticket #3424. (CVS 5782)
FossilOrigin-Name: af679f6170b346fe61df7dae963b2a2853e62a62
This commit is contained in:
19
manifest
19
manifest
@@ -1,5 +1,5 @@
|
|||||||
C Add\sthe\sexperimental\ssqlite3_stmt_status()\sinterface.\s(CVS\s5781)
|
C After\san\sOP_NullRow\sis\sexecuted\son\sa\scursor,\scause\sany\ssubsequent\sOP_Next\sor\sOP_Prev\sto\sbehave\sas\sif\sthere\swere\sno\smore\srows\sto\straverse.\sTicket\s#3424.\s(CVS\s5782)
|
||||||
D 2008-10-07T23:46:38
|
D 2008-10-08T17:58:49
|
||||||
F Makefile.arm-wince-mingw32ce-gcc fcd5e9cd67fe88836360bb4f9ef4cb7f8e2fb5a0
|
F Makefile.arm-wince-mingw32ce-gcc fcd5e9cd67fe88836360bb4f9ef4cb7f8e2fb5a0
|
||||||
F Makefile.in 7fc26e087207e7a4a7723583dbd7997477af3b13
|
F Makefile.in 7fc26e087207e7a4a7723583dbd7997477af3b13
|
||||||
F Makefile.linux-gcc d53183f4aa6a9192d249731c90dbdffbd2c68654
|
F Makefile.linux-gcc d53183f4aa6a9192d249731c90dbdffbd2c68654
|
||||||
@@ -99,8 +99,8 @@ F src/attach.c db3f4a60538733c1e4dcb9d0217a6e0d6ccd615b
|
|||||||
F src/auth.c c8b2ab5c8bad4bd90ed7c294694f48269162c627
|
F src/auth.c c8b2ab5c8bad4bd90ed7c294694f48269162c627
|
||||||
F src/bitvec.c 95c86bd18d8fedf0533f5af196192546e10a7e7d
|
F src/bitvec.c 95c86bd18d8fedf0533f5af196192546e10a7e7d
|
||||||
F src/btmutex.c 3a90096c3080b9057dc570b8e16e46511e1c788a
|
F src/btmutex.c 3a90096c3080b9057dc570b8e16e46511e1c788a
|
||||||
F src/btree.c 64a38df6f0a9997563418ed194984b81e4ab3694
|
F src/btree.c 3e686f899659df8d79f2587d0f34f51fdf6a6276
|
||||||
F src/btree.h 6371c5e599fab391a150c96afbc10062b276d107
|
F src/btree.h 903682f2a88da37435f103da00cb915d63bc8015
|
||||||
F src/btreeInt.h e38e9b2b285f40f5bc0a6664f630d4a141622f16
|
F src/btreeInt.h e38e9b2b285f40f5bc0a6664f630d4a141622f16
|
||||||
F src/build.c 8714bd809583bbe07bf22d0e1808a3fc31abe330
|
F src/build.c 8714bd809583bbe07bf22d0e1808a3fc31abe330
|
||||||
F src/callback.c 7a40fd44da3eb89e7f6eff30aa6f940c45d73a97
|
F src/callback.c 7a40fd44da3eb89e7f6eff30aa6f940c45d73a97
|
||||||
@@ -190,7 +190,7 @@ F src/update.c 206fffc877379affe3a9b42c78e478ea0874c9fe
|
|||||||
F src/utf.c c63e6f69082f85c19ab88d62dedaf91d71ac1a50
|
F src/utf.c c63e6f69082f85c19ab88d62dedaf91d71ac1a50
|
||||||
F src/util.c afe659ccc05d1f8af9e8631dabfec3ee3a7144af
|
F src/util.c afe659ccc05d1f8af9e8631dabfec3ee3a7144af
|
||||||
F src/vacuum.c fd77433d0c26d3ff1eb96eab017a1787ac5aa642
|
F src/vacuum.c fd77433d0c26d3ff1eb96eab017a1787ac5aa642
|
||||||
F src/vdbe.c 374961d5ac5fe91a1e0acf4ed5519531574b69c6
|
F src/vdbe.c b78adf571b9abac4092c641bec148832e8f26f34
|
||||||
F src/vdbe.h 41c99aaad9167c1b5431993db446de74b2f71fc3
|
F src/vdbe.h 41c99aaad9167c1b5431993db446de74b2f71fc3
|
||||||
F src/vdbeInt.h a20f479ec3bf41c61b0c2bd5176a9bad6b2a07ef
|
F src/vdbeInt.h a20f479ec3bf41c61b0c2bd5176a9bad6b2a07ef
|
||||||
F src/vdbeapi.c fd2c286cee63a146d5110c11c0aa2bf3a9ebe220
|
F src/vdbeapi.c fd2c286cee63a146d5110c11c0aa2bf3a9ebe220
|
||||||
@@ -568,6 +568,7 @@ F test/tkt3334.test ea13a53cb176e90571a76c86605b14a09efe366d
|
|||||||
F test/tkt3346.test 2f9a2be8621a87cbdb6283177dd419c7c46dd2a1
|
F test/tkt3346.test 2f9a2be8621a87cbdb6283177dd419c7c46dd2a1
|
||||||
F test/tkt3357.test b37a51a12ba5e143d6714778276438606f8f9e27
|
F test/tkt3357.test b37a51a12ba5e143d6714778276438606f8f9e27
|
||||||
F test/tkt3419.test 1bbf36d7ea03b638c15804251287c2391f5c1f6b
|
F test/tkt3419.test 1bbf36d7ea03b638c15804251287c2391f5c1f6b
|
||||||
|
F test/tkt3424.test 3171193ce340cff6b7ea81c03b8fa1cbc34ec36e
|
||||||
F test/tokenize.test ce430a7aed48fc98301611429595883fdfcab5d7
|
F test/tokenize.test ce430a7aed48fc98301611429595883fdfcab5d7
|
||||||
F test/trace.test 951cd0f5f571e7f36bf7bfe04be70f90fb16fb00
|
F test/trace.test 951cd0f5f571e7f36bf7bfe04be70f90fb16fb00
|
||||||
F test/trans.test 2fd24cd7aa0b879d49a224cbd647d698f1e7ac5c
|
F test/trans.test 2fd24cd7aa0b879d49a224cbd647d698f1e7ac5c
|
||||||
@@ -641,7 +642,7 @@ F tool/speedtest16.c c8a9c793df96db7e4933f0852abb7a03d48f2e81
|
|||||||
F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff
|
F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff
|
||||||
F tool/speedtest8.c 1dbced29de5f59ba2ebf877edcadf171540374d1
|
F tool/speedtest8.c 1dbced29de5f59ba2ebf877edcadf171540374d1
|
||||||
F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e
|
F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e
|
||||||
P 79df72ee836db91647913055ba6cf55558679b01
|
P de473efb35ffdf9a8222a70a84dfd7d3198c87c1
|
||||||
R d426461dcb923755279eeb7df7038b4a
|
R 2f077384d5708b8cad084e75cfae98e5
|
||||||
U drh
|
U danielk1977
|
||||||
Z 4b26af34158fc50efdf02ed1356ecdbc
|
Z 6ddad9a5e2687baf46af1a15bb5e4ff8
|
||||||
|
@@ -1 +1 @@
|
|||||||
de473efb35ffdf9a8222a70a84dfd7d3198c87c1
|
af679f6170b346fe61df7dae963b2a2853e62a62
|
12
src/btree.c
12
src/btree.c
@@ -9,7 +9,7 @@
|
|||||||
** May you share freely, never taking more than you give.
|
** May you share freely, never taking more than you give.
|
||||||
**
|
**
|
||||||
*************************************************************************
|
*************************************************************************
|
||||||
** $Id: btree.c,v 1.524 2008/09/30 17:18:17 drh Exp $
|
** $Id: btree.c,v 1.525 2008/10/08 17:58:49 danielk1977 Exp $
|
||||||
**
|
**
|
||||||
** This file implements a external (disk-based) database using BTrees.
|
** This file implements a external (disk-based) database using BTrees.
|
||||||
** See the header comment on "btreeInt.h" for additional information.
|
** See the header comment on "btreeInt.h" for additional information.
|
||||||
@@ -368,7 +368,7 @@ static int saveAllCursors(BtShared *pBt, Pgno iRoot, BtCursor *pExcept){
|
|||||||
/*
|
/*
|
||||||
** Clear the current cursor position.
|
** Clear the current cursor position.
|
||||||
*/
|
*/
|
||||||
static void clearCursorPosition(BtCursor *pCur){
|
void sqlite3BtreeClearCursor(BtCursor *pCur){
|
||||||
assert( cursorHoldsMutex(pCur) );
|
assert( cursorHoldsMutex(pCur) );
|
||||||
sqlite3_free(pCur->pKey);
|
sqlite3_free(pCur->pKey);
|
||||||
pCur->pKey = 0;
|
pCur->pKey = 0;
|
||||||
@@ -2594,7 +2594,7 @@ void sqlite3BtreeTripAllCursors(Btree *pBtree, int errCode){
|
|||||||
BtCursor *p;
|
BtCursor *p;
|
||||||
sqlite3BtreeEnter(pBtree);
|
sqlite3BtreeEnter(pBtree);
|
||||||
for(p=pBtree->pBt->pCursor; p; p=p->pNext){
|
for(p=pBtree->pBt->pCursor; p; p=p->pNext){
|
||||||
clearCursorPosition(p);
|
sqlite3BtreeClearCursor(p);
|
||||||
p->eState = CURSOR_FAULT;
|
p->eState = CURSOR_FAULT;
|
||||||
p->skip = errCode;
|
p->skip = errCode;
|
||||||
}
|
}
|
||||||
@@ -2867,7 +2867,7 @@ int sqlite3BtreeCloseCursor(BtCursor *pCur){
|
|||||||
BtShared *pBt = pCur->pBt;
|
BtShared *pBt = pCur->pBt;
|
||||||
sqlite3BtreeEnter(pBtree);
|
sqlite3BtreeEnter(pBtree);
|
||||||
pBt->db = pBtree->db;
|
pBt->db = pBtree->db;
|
||||||
clearCursorPosition(pCur);
|
sqlite3BtreeClearCursor(pCur);
|
||||||
if( pCur->pPrev ){
|
if( pCur->pPrev ){
|
||||||
pCur->pPrev->pNext = pCur->pNext;
|
pCur->pPrev->pNext = pCur->pNext;
|
||||||
}else{
|
}else{
|
||||||
@@ -3526,7 +3526,7 @@ static int moveToRoot(BtCursor *pCur){
|
|||||||
if( pCur->eState==CURSOR_FAULT ){
|
if( pCur->eState==CURSOR_FAULT ){
|
||||||
return pCur->skip;
|
return pCur->skip;
|
||||||
}
|
}
|
||||||
clearCursorPosition(pCur);
|
sqlite3BtreeClearCursor(pCur);
|
||||||
}
|
}
|
||||||
|
|
||||||
if( pCur->iPage>=0 ){
|
if( pCur->iPage>=0 ){
|
||||||
@@ -5771,7 +5771,7 @@ int sqlite3BtreeInsert(
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* Save the positions of any other cursors open on this table */
|
/* Save the positions of any other cursors open on this table */
|
||||||
clearCursorPosition(pCur);
|
sqlite3BtreeClearCursor(pCur);
|
||||||
if(
|
if(
|
||||||
SQLITE_OK!=(rc = saveAllCursors(pBt, pCur->pgnoRoot, pCur)) ||
|
SQLITE_OK!=(rc = saveAllCursors(pBt, pCur->pgnoRoot, pCur)) ||
|
||||||
SQLITE_OK!=(rc = sqlite3BtreeMoveto(pCur, pKey, nKey, appendBias, &loc))
|
SQLITE_OK!=(rc = sqlite3BtreeMoveto(pCur, pKey, nKey, appendBias, &loc))
|
||||||
|
@@ -13,7 +13,7 @@
|
|||||||
** subsystem. See comments in the source code for a detailed description
|
** subsystem. See comments in the source code for a detailed description
|
||||||
** of what each interface routine does.
|
** of what each interface routine does.
|
||||||
**
|
**
|
||||||
** @(#) $Id: btree.h,v 1.103 2008/08/13 19:11:48 drh Exp $
|
** @(#) $Id: btree.h,v 1.104 2008/10/08 17:58:49 danielk1977 Exp $
|
||||||
*/
|
*/
|
||||||
#ifndef _BTREE_H_
|
#ifndef _BTREE_H_
|
||||||
#define _BTREE_H_
|
#define _BTREE_H_
|
||||||
@@ -170,6 +170,7 @@ struct Pager *sqlite3BtreePager(Btree*);
|
|||||||
|
|
||||||
int sqlite3BtreePutData(BtCursor*, u32 offset, u32 amt, void*);
|
int sqlite3BtreePutData(BtCursor*, u32 offset, u32 amt, void*);
|
||||||
void sqlite3BtreeCacheOverflow(BtCursor *);
|
void sqlite3BtreeCacheOverflow(BtCursor *);
|
||||||
|
void sqlite3BtreeClearCursor(BtCursor *);
|
||||||
|
|
||||||
#ifdef SQLITE_TEST
|
#ifdef SQLITE_TEST
|
||||||
int sqlite3BtreeCursorInfo(BtCursor*, int*, int);
|
int sqlite3BtreeCursorInfo(BtCursor*, int*, int);
|
||||||
|
@@ -43,7 +43,7 @@
|
|||||||
** in this file for details. If in doubt, do not deviate from existing
|
** in this file for details. If in doubt, do not deviate from existing
|
||||||
** commenting and indentation practices when changing or adding code.
|
** commenting and indentation practices when changing or adding code.
|
||||||
**
|
**
|
||||||
** $Id: vdbe.c,v 1.781 2008/10/07 23:46:38 drh Exp $
|
** $Id: vdbe.c,v 1.782 2008/10/08 17:58:49 danielk1977 Exp $
|
||||||
*/
|
*/
|
||||||
#include "sqliteInt.h"
|
#include "sqliteInt.h"
|
||||||
#include <ctype.h>
|
#include <ctype.h>
|
||||||
@@ -3692,6 +3692,9 @@ case OP_NullRow: {
|
|||||||
assert( pC!=0 );
|
assert( pC!=0 );
|
||||||
pC->nullRow = 1;
|
pC->nullRow = 1;
|
||||||
pC->rowidIsValid = 0;
|
pC->rowidIsValid = 0;
|
||||||
|
if( pC->pCursor ){
|
||||||
|
sqlite3BtreeClearCursor(pC->pCursor);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
54
test/tkt3424.test
Normal file
54
test/tkt3424.test
Normal file
@@ -0,0 +1,54 @@
|
|||||||
|
# 2008 October 06
|
||||||
|
#
|
||||||
|
# The author disclaims copyright to this source code. In place of
|
||||||
|
# a legal notice, here is a blessing:
|
||||||
|
#
|
||||||
|
# May you do good and not evil.
|
||||||
|
# May you find forgiveness for yourself and forgive others.
|
||||||
|
# May you share freely, never taking more than you give.
|
||||||
|
#
|
||||||
|
#***********************************************************************
|
||||||
|
#
|
||||||
|
#
|
||||||
|
# $Id: tkt3424.test,v 1.1 2008/10/08 17:58:50 danielk1977 Exp $
|
||||||
|
|
||||||
|
set testdir [file dirname $argv0]
|
||||||
|
source $testdir/tester.tcl
|
||||||
|
|
||||||
|
do_test tkt3424-1.1 {
|
||||||
|
execsql {
|
||||||
|
CREATE TABLE names(id INTEGER, data TEXT, code TEXT);
|
||||||
|
INSERT INTO names VALUES(1,'E1','AAA');
|
||||||
|
INSERT INTO names VALUES(2,NULL,'BBB');
|
||||||
|
|
||||||
|
CREATE TABLE orig(code TEXT, data TEXT);
|
||||||
|
INSERT INTO orig VALUES('AAA','E1');
|
||||||
|
INSERT INTO orig VALUES('AAA','E2');
|
||||||
|
INSERT INTO orig VALUES('AAA','E3');
|
||||||
|
INSERT INTO orig VALUES('AAA','E4');
|
||||||
|
INSERT INTO orig VALUES('AAA','E5');
|
||||||
|
}
|
||||||
|
} {}
|
||||||
|
|
||||||
|
do_test tkt3424-1.2 {
|
||||||
|
execsql {
|
||||||
|
SELECT * FROM
|
||||||
|
names LEFT OUTER JOIN orig
|
||||||
|
ON names.data = orig.data AND names.code = orig.code;
|
||||||
|
}
|
||||||
|
} {1 E1 AAA AAA E1 2 {} BBB {} {}}
|
||||||
|
|
||||||
|
do_test tkt3424-1.3 {
|
||||||
|
execsql { CREATE INDEX udx_orig_code_data ON orig(code, data) }
|
||||||
|
} {}
|
||||||
|
|
||||||
|
do_test tkt3424-1.4 {
|
||||||
|
execsql {
|
||||||
|
SELECT * FROM
|
||||||
|
names LEFT OUTER JOIN orig
|
||||||
|
ON names.data = orig.data AND names.code = orig.code;
|
||||||
|
}
|
||||||
|
} {1 E1 AAA AAA E1 2 {} BBB {} {}}
|
||||||
|
|
||||||
|
finish_test
|
||||||
|
|
Reference in New Issue
Block a user