]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
The first test file for BTree added. Simple insert and delete tests pass.
authordrh <drh@noemail.net>
Sun, 24 Jun 2001 20:39:41 +0000 (20:39 +0000)
committerdrh <drh@noemail.net>
Sun, 24 Jun 2001 20:39:41 +0000 (20:39 +0000)
There is still a lot of work to be done, though. (CVS 228)

FossilOrigin-Name: 85f015c9750a5eab274e82f0e2c6e8f09dc7ca70

manifest
manifest.uuid
src/btree.c
src/pager.c
test/btree.test [new file with mode: 0644]
test/pager.test

index 78bbaab6873fe6578352be40c3bdef9878598eb0..6bf9b7ae46f0a3d6b6b0ad48d4d9206b8165fe50 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Fix\sa\sbug\sin\spager.c\sintroduced\sin\sthe\sprevious\sdelta.\s(CVS\s227)
-D 2001-06-23T11:36:20
+C The\sfirst\stest\sfile\sfor\sBTree\sadded.\sSimple\sinsert\sand\sdelete\stests\spass.\nThere\sis\sstill\sa\slot\sof\swork\sto\sbe\sdone,\sthough.\s(CVS\s228)
+D 2001-06-24T20:39:41
 F COPYRIGHT 74a8a6531a42e124df07ab5599aad63870fa0bd4
 F Makefile.in 65862a30703b070209b5f5e565d75cc870962b3c
 F README 51f6a4e7408b34afa5bc1c0485f61b6a4efb6958
@@ -12,7 +12,7 @@ F notes/notes1.txt b7c0812b704a022e88c621146ae50955c923d464
 F notes/notes2.txt 7e3fafd5e25906c1fe1e95f13b089aa398ca403e
 F notes/notes3.txt 985bf688b59f1f52bfe6e4b1f896efdeffac1432
 F src/TODO 38a68a489e56e9fd4a96263e0ff9404a47368ad4
-F src/btree.c 0a2b66ce90f0bee87f0449235060529b96cc96e4
+F src/btree.c e46ab610d0bef3d1a9f698bede21d554c42763e5
 F src/btree.h 40ae2c9b6d2ba8feb03461a589ccab9afc04ec29
 F src/build.c 4f6a2d551c56342cd4a0420654835be3ad179651
 F src/dbbe.c b18259f99d87240cbe751021cf14dd3aa83a48af
@@ -31,7 +31,7 @@ F src/ex/sizes.tcl f54bad4a2ac567624be59131a6ee42d71b41a3d7
 F src/expr.c c4c24c3af1eba094a816522eb0e085bed518ee16
 F src/insert.c aa528e20a787af85432a61daaea6df394bd251d7
 F src/main.c 0a13c7a2beb8ce36aee43daf8c95989b200727a7
-F src/pager.c d5cb53ac679d039d40661e50200a8dde6406ca15
+F src/pager.c 866d4d9a736943c9a904d291bc9b66dc4a7f23de
 F src/pager.h 724ac5a79b5fa704a1e1a87e421e421b3da9c1e4
 F src/parse.y 8fc096948994a7ffbf61ba13129cc589f794a9cb
 F src/printf.c b1e22a47be8cdf707815647239991e08e8cb69f9
@@ -53,6 +53,7 @@ F src/vdbe.c f93be4414ba892df9c5589815d2a57c1fb12c820
 F src/vdbe.h dc1205da434c6a9da03b5d6b089270bbc8e6d437
 F src/where.c 0c542fc44bd85152dfb8507862cfe2e60c629e9f
 F test/all.test 21d55a97e39e7ec5776751dc9dd8b1b51ef4a048
+F test/btree.test 8db61fdd957e906d7d237bf0f578f3e8cc9fb33e
 F test/copy.test b77a1214bd7756f2849d5c4fa6e715c0ff0c34eb
 F test/dbbe.test a022fe2d983848f786e17ef1fc6809cfd37fb02c
 F test/delete.test 50b9b1f06c843d591741dba7869433a105360dbf
@@ -65,7 +66,7 @@ F test/insert2.test 732405e30331635af8d159fccabe835eea5cd0c6
 F test/lock.test bca7d53de73138b1f670a2fbdb1f481ff7eaa45a
 F test/main.test da635f9e078cd21ddf074e727381a715064489ff
 F test/malloc.test 3daa97f6a9577d8f4c6e468b274333af19ce5861
-F test/pager.test 475835b84cbec423a7dd3d0492b2c8701435d375
+F test/pager.test aa902a867ce6b925214d28e17400001946e0e5a4
 F test/printf.test 4c71871e1a75a2dacb673945fc13ddb30168798f
 F test/rowid.test 128453599def7435e988216f7fe89c7450b8a9a3
 F test/select1.test 223507655cdb4f9901d83fa7f5c5328e022c211f
@@ -107,7 +108,7 @@ F www/opcode.tcl cb3a1abf8b7b9be9f3a228d097d6bf8b742c2b6f
 F www/sqlite.tcl cb0d23d8f061a80543928755ec7775da6e4f362f
 F www/tclsqlite.tcl 06f81c401f79a04f2c5ebfb97e7c176225c0aef2
 F www/vdbe.tcl 0c8aaa529dd216ccbf7daaabd80985e413d5f9ad
-P b31c49021c260a67b7848bc077b75a7146e31c71
-R e52ea2ba0d86c859453a43591ceb35fc
+P f4df6664037c68e1ce539c84c852124d95cd5a56
+R 3068b07f88f8e6db3749d5669bb8ecc6
 U drh
-Z 86cec7512c643b5b976845158db125a4
+Z ee5edd13b8c55ec829c3087fe59854aa
index 2104dfe1365a4797db0aef25b21956aff1e06a2e..55e4356685c3befda4fac2fc9e4209895dc9f35b 100644 (file)
@@ -1 +1 @@
-f4df6664037c68e1ce539c84c852124d95cd5a56
\ No newline at end of file
+85f015c9750a5eab274e82f0e2c6e8f09dc7ca70
\ No newline at end of file
index eee60492ba2dd71d2368b29ba88a761a6dcd71f6..b4666da4091931e25ffbed956ad35f4a81ad861b 100644 (file)
@@ -21,7 +21,7 @@
 **   http://www.hwaci.com/drh/
 **
 *************************************************************************
-** $Id: btree.c,v 1.13 2001/06/22 19:15:00 drh Exp $
+** $Id: btree.c,v 1.14 2001/06/24 20:39:41 drh Exp $
 **
 ** This file implements a external (disk-based) database using BTrees.
 ** For a detailed discussion of BTrees, refer to
@@ -81,7 +81,7 @@ typedef unsigned char u8;
 ** This macro casts a pointer to an integer.  Useful for doing
 ** pointer arithmetic.
 */
-#define addr(X)  ((uptr)X)
+#define Addr(X)  ((uptr)X)
 
 /*
 ** Forward declarations of structures used only in this file.
@@ -368,8 +368,8 @@ static void defragmentPage(MemPage *pPage){
 
     /* This routine should never be called on an overfull page.  The
     ** following asserts verify that constraint. */
-    assert( addr(pCell) > addr(pPage) );
-    assert( addr(pCell) < addr(pPage) + SQLITE_PAGE_SIZE );
+    assert( Addr(pCell) > Addr(pPage) );
+    assert( Addr(pCell) < Addr(pPage) + SQLITE_PAGE_SIZE );
 
     n = cellSize(pCell);
     pCell->h.iNext = i<pPage->nCell-1 ? pc + n : 0;
@@ -534,7 +534,7 @@ static int initPage(MemPage *pPage, Pgno pgnoThis, MemPage *pParent){
     if( idx<sizeof(PageHdr) ) goto page_format_error;
     pFBlk = (FreeBlk*)&pPage->u.aDisk[idx];
     pPage->nFree += pFBlk->iSize;
-    if( pFBlk->iNext <= idx ) goto page_format_error;
+    if( pFBlk->iNext>0 && pFBlk->iNext <= idx ) goto page_format_error;
     idx = pFBlk->iNext;
   }
   if( pPage->nCell==0 && pPage->nFree==0 ){
@@ -666,7 +666,7 @@ static int newDatabase(Btree *pBt){
   MemPage *pRoot;
   PageOne *pP1;
   int rc;
-  if( sqlitepager_pagecount(pBt->pPager)>0 ) return SQLITE_OK;
+  if( sqlitepager_pagecount(pBt->pPager)>1 ) return SQLITE_OK;
   pP1 = pBt->page1;
   rc = sqlitepager_write(pBt->page1);
   if( rc ) return rc;
@@ -721,7 +721,7 @@ int sqliteBtreeBeginTrans(Btree *pBt){
 ** remove the read lock.
 */
 static void unlockBtree(Btree *pBt){
-  if( pBt->pCursor==0 && pBt->page1!=0 ){
+  if( pBt->inTrans==0 && pBt->pCursor==0 && pBt->page1!=0 ){
     sqlitepager_unref(pBt->page1);
     pBt->page1 = 0;
     pBt->inTrans = 0;
@@ -734,8 +734,9 @@ static void unlockBtree(Btree *pBt){
 */
 int sqliteBtreeCommit(Btree *pBt){
   int rc;
-  if( pBt->pCursor!=0 ) return SQLITE_ERROR;
+  if( pBt->pCursor!=0 || pBt->inTrans==0 ) return SQLITE_ERROR;
   rc = sqlitepager_commit(pBt->pPager);
+  pBt->inTrans = 0;
   unlockBtree(pBt);
   return rc;
 }
@@ -747,6 +748,8 @@ int sqliteBtreeCommit(Btree *pBt){
 int sqliteBtreeRollback(Btree *pBt){
   int rc;
   if( pBt->pCursor!=0 ) return SQLITE_ERROR;
+  if( pBt->inTrans==0 ) return SQLITE_OK;
+  pBt->inTrans = 0;
   rc = sqlitepager_rollback(pBt->pPager);
   unlockBtree(pBt);
   return rc;
@@ -1144,16 +1147,17 @@ static int moveToLeftmost(BtCursor *pCur){
 ** this value is as follows:
 **
 **     *pRes<0      The cursor is left pointing at an entry that
-**                  is larger than pKey.
+**                  is smaller than pKey.
 **
 **     *pRes==0     The cursor is left pointing at an entry that
 **                  exactly matches pKey.
 **
 **     *pRes>0      The cursor is left pointing at an entry that
-**                  is smaller than pKey.
+**                  is larger than pKey.
 */
 int sqliteBtreeMoveto(BtCursor *pCur, void *pKey, int nKey, int *pRes){
   int rc;
+  pCur->bSkipNext = 0;
   rc = moveToRoot(pCur);
   if( rc ) return rc;
   for(;;){
@@ -1449,8 +1453,8 @@ static void dropCell(MemPage *pPage, int idx, int sz){
   int j;
   assert( idx>=0 && idx<pPage->nCell );
   assert( sz==cellSize(pPage->apCell[idx]) );
-  freeSpace(pPage, idx, sz);
-  for(j=idx; j<pPage->nCell-2; j++){
+  freeSpace(pPage, Addr(pPage->apCell[idx]) - Addr(pPage), sz);
+  for(j=idx; j<pPage->nCell-1; j++){
     pPage->apCell[j] = pPage->apCell[j+1];
   }
   pPage->nCell--;
@@ -1498,7 +1502,7 @@ static void relinkCellList(MemPage *pPage){
   u16 *pIdx;
   pIdx = &pPage->u.hdr.firstCell;
   for(i=0; i<pPage->nCell; i++){
-    int idx = addr(pPage->apCell[i]) - addr(pPage);
+    int idx = Addr(pPage->apCell[i]) - Addr(pPage);
     assert( idx>0 && idx<SQLITE_PAGE_SIZE );
     *pIdx = idx;
     pIdx = &pPage->apCell[i]->h.iNext;
@@ -1521,10 +1525,10 @@ static void copyPage(MemPage *pTo, MemPage *pFrom){
   pTo->nCell = pFrom->nCell;
   pTo->nFree = pFrom->nFree;
   pTo->isOverfull = pFrom->isOverfull;
-  to = addr(pTo);
-  from = addr(pFrom);
+  to = Addr(pTo);
+  from = Addr(pFrom);
   for(i=0; i<pTo->nCell; i++){
-    uptr x = addr(pFrom->apCell[i]);
+    uptr x = Addr(pFrom->apCell[i]);
     if( x>from && x<from+SQLITE_PAGE_SIZE ){
       *((uptr*)&pTo->apCell[i]) = x + to - from;
     }
@@ -1903,13 +1907,13 @@ int sqliteBtreeInsert(
     rc = clearCell(pBt, pPage->apCell[pCur->idx]);
     if( rc ) return rc;
     dropCell(pPage, pCur->idx, cellSize(pPage->apCell[pCur->idx]));
-  }else if( loc>0 ){
+  }else if( loc<0 && pPage->nCell>0 ){
     assert( pPage->u.hdr.rightChild==0 );  /* Must be a leaf page */
     pCur->idx++;
   }else{
     assert( pPage->u.hdr.rightChild==0 );  /* Must be a leaf page */
   }
-  insertCell(pPage, pCur->idx, &newCell, cellSize(&newCell));
+  insertCell(pPage, pCur->idx, &newCell, szNew);
   rc = balance(pCur->pBt, pPage, pCur);
   return rc;
 }
@@ -2123,6 +2127,7 @@ int sqliteBtreePageDump(Btree *pBt, int pgno){
       i, range, (int)pCell->h.leftChild, pCell->h.nKey, pCell->h.nData,
       pCell->aPayload
     );
+    i++;
     idx = pCell->h.iNext;
   }
   if( idx!=0 ){
index a630720a562a6caa1bfe3db8957c7ffd7b56438f..4e759ac802b362359a29e021e8f3415a63b31d8d 100644 (file)
@@ -27,7 +27,7 @@
 ** all writes in order to support rollback.  Locking is used to limit
 ** access to one or more reader or one writer.
 **
-** @(#) $Id: pager.c,v 1.10 2001/06/23 11:36:20 drh Exp $
+** @(#) $Id: pager.c,v 1.11 2001/06/24 20:39:41 drh Exp $
 */
 #include "sqliteInt.h"
 #include "pager.h"
@@ -476,6 +476,7 @@ int sqlitepager_open(
   pPager->errMask = 0;
   pPager->pFirst = 0;
   pPager->pLast = 0;
+  pPager->nExtra = nExtra;
   memset(pPager->aHash, 0, sizeof(pPager->aHash));
   *ppPager = pPager;
   return SQLITE_OK;
diff --git a/test/btree.test b/test/btree.test
new file mode 100644 (file)
index 0000000..bf849f2
--- /dev/null
@@ -0,0 +1,315 @@
+# Copyright (c) 1999, 2000 D. Richard Hipp
+#
+# This program is free software; you can redistribute it and/or
+# modify it under the terms of the GNU General Public
+# License as published by the Free Software Foundation; either
+# version 2 of the License, or (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+# General Public License for more details.
+# 
+# You should have received a copy of the GNU General Public
+# License along with this library; if not, write to the
+# Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+# Boston, MA  02111-1307, USA.
+#
+# Author contact information:
+#   drh@hwaci.com
+#   http://www.hwaci.com/drh/
+#
+#***********************************************************************
+# This file implements regression tests for SQLite library.  The
+# focus of this script is btree database backend
+#
+# $Id: btree.test,v 1.1 2001/06/24 20:39:41 drh Exp $
+
+
+set testdir [file dirname $argv0]
+source $testdir/tester.tcl
+
+if {$dbprefix!="memory:" && [info commands btree_open]!=""} {
+
+# Basic functionality.  Open and close a database.
+#
+do_test btree-1.1 {
+  file delete -force test1.bt
+  file delete -force test1.bt-journal
+  set rc [catch {btree_open test1.bt} ::b1]
+} {0}
+do_test btree-1.2 {
+  set rc [catch {btree_open test1.bt} ::b2]
+} {0}
+do_test btree-1.3 {
+  set rc [catch {btree_close $::b2} msg]
+  lappend rc $msg
+} {0 {}}
+
+# Do an insert and verify that the database file grows in size.
+#
+do_test btree-1.4 {
+  set rc [catch {btree_begin_transaction $::b1} msg]
+  lappend rc $msg
+} {0 {}}
+do_test btree-1.5 {
+  set rc [catch {btree_cursor $::b1 2} ::c1]
+  if {$rc} {lappend rc $::c1}
+  set rc
+} {0}
+do_test btree-1.6 {
+  set rc [catch {btree_insert $::c1 one 1.00} msg]
+  lappend rc $msg
+} {0 {}}
+do_test btree-1.7 {
+  btree_key $::c1
+} {one}
+do_test btree-1.8 {
+  btree_data $::c1
+} {1.00}
+do_test btree-1.9 {
+  set rc [catch {btree_close_cursor $::c1} msg]
+  lappend rc $msg
+} {0 {}}
+do_test btree-1.10 {
+  set rc [catch {btree_commit $::b1} msg]
+  lappend rc $msg
+} {0 {}}
+do_test btree-1.11 {
+  file size test1.bt
+} {2048}
+
+# Reopen the database and attempt to read the record that we wrote.
+#
+do_test btree-2.1 {
+  set rc [catch {btree_cursor $::b1 2} ::c1]
+  if {$rc} {lappend rc $::c1}
+  set rc
+} {0}
+do_test btree-2.2 {
+  btree_move_to $::c1 abc
+} {1}
+do_test btree-2.3 {
+  btree_move_to $::c1 xyz
+} {-1}
+do_test btree-2.4 {
+  btree_move_to $::c1 one
+} {0}
+do_test btree-2.5 {
+  btree_key $::c1
+} {one}
+do_test btree-2.6 {
+  btree_data $::c1
+} {1.00}
+
+# Do some additional inserts
+#
+do_test btree-3.1 {
+  btree_begin_transaction $::b1
+  btree_insert $::c1 two 2.00
+  btree_key $::c1
+} {two}
+do_test btree-3.2 {
+  btree_insert $::c1 three 3.00
+  btree_key $::c1
+} {three}
+do_test btree-3.4 {
+  btree_insert $::c1 four 4.00
+  btree_key $::c1
+} {four}
+do_test btree-3.5 {
+  btree_insert $::c1 five 5.00
+  btree_key $::c1
+} {five}
+do_test btree-3.6 {
+  btree_insert $::c1 six 6.00
+  btree_key $::c1
+} {six}
+#btree_page_dump $::b1 2
+do_test btree-3.7 {
+  set rc [btree_move_to $::c1 {}]
+  expr {$rc>0}
+} {1}
+do_test btree-3.8 {
+  btree_key $::c1
+} {five}
+do_test btree-3.9 {
+  btree_data $::c1
+} {5.00}
+do_test btree-3.10 {
+  btree_next $::c1
+  btree_key $::c1
+} {four}
+do_test btree-3.11 {
+  btree_data $::c1
+} {4.00}
+do_test btree-3.12 {
+  btree_next $::c1
+  btree_key $::c1
+} {one}
+do_test btree-3.13 {
+  btree_data $::c1
+} {1.00}
+do_test btree-3.14 {
+  btree_next $::c1
+  btree_key $::c1
+} {six}
+do_test btree-3.15 {
+  btree_data $::c1
+} {6.00}
+do_test btree-3.16 {
+  btree_next $::c1
+  btree_key $::c1
+} {three}
+do_test btree-3.17 {
+  btree_data $::c1
+} {3.00}
+do_test btree-3.18 {
+  btree_next $::c1
+  btree_key $::c1
+} {two}
+do_test btree-3.19 {
+  btree_data $::c1
+} {2.00}
+do_test btree-3.20 {
+  btree_next $::c1
+  btree_key $::c1
+} {}
+do_test btree-3.21 {
+  btree_data $::c1
+} {}
+
+# Commit the changes, reopen and reread the data
+#
+do_test btree-3.22 {
+  set rc [catch {btree_close_cursor $::c1} msg]
+  lappend rc $msg
+} {0 {}}
+do_test btree-3.23 {
+  set rc [catch {btree_commit $::b1} msg]
+  lappend rc $msg
+} {0 {}}
+do_test btree-3.24 {
+  file size test1.bt
+} {2048}
+do_test btree-3.25 {
+  set rc [catch {btree_cursor $::b1 2} ::c1]
+  if {$rc} {lappend rc $::c1}
+  set rc
+} {0}
+do_test btree-3.26 {
+  set rc [btree_move_to $::c1 {}]
+  expr {$rc>0}
+} {1}
+do_test btree-3.27 {
+  btree_key $::c1
+} {five}
+do_test btree-3.28 {
+  btree_data $::c1
+} {5.00}
+do_test btree-3.29 {
+  btree_next $::c1
+  btree_key $::c1
+} {four}
+do_test btree-3.30 {
+  btree_data $::c1
+} {4.00}
+do_test btree-3.31 {
+  btree_next $::c1
+  btree_key $::c1
+} {one}
+do_test btree-3.32 {
+  btree_data $::c1
+} {1.00}
+do_test btree-3.33 {
+  btree_next $::c1
+  btree_key $::c1
+} {six}
+do_test btree-3.34 {
+  btree_data $::c1
+} {6.00}
+do_test btree-3.35 {
+  btree_next $::c1
+  btree_key $::c1
+} {three}
+do_test btree-3.36 {
+  btree_data $::c1
+} {3.00}
+do_test btree-3.37 {
+  btree_next $::c1
+  btree_key $::c1
+} {two}
+do_test btree-3.38 {
+  btree_data $::c1
+} {2.00}
+do_test btree-3.39 {
+  btree_next $::c1
+  btree_key $::c1
+} {}
+do_test btree-3.40 {
+  btree_data $::c1
+} {}
+
+# Now try a delete
+#
+do_test btree-4.1 {
+  btree_begin_transaction $::b1
+  btree_move_to $::c1 one
+  btree_key $::c1
+} {one}
+do_test btree-4.2 {
+  btree_delete $::c1
+} {}
+do_test btree-4.3 {
+  btree_key $::c1
+} {six}
+do_test btree-4.4 {
+  btree_next $::c1
+  btree_key $::c1
+} {six}
+do_test btree-4.5 {
+  btree_next $::c1
+  btree_key $::c1
+} {three}
+do_test btree-4.4 {
+  btree_move_to $::c1 {}
+  set r {}
+  while 1 {
+    set key [btree_key $::c1]
+    if {$key==""} break
+    lappend r $key
+    lappend r [btree_data $::c1]
+    btree_next $::c1
+  }
+  set r   
+} {five 5.00 four 4.00 six 6.00 three 3.00 two 2.00}
+
+# Commit and make sure the delete is still there.
+#
+do_test btree-4.5 {
+  btree_close_cursor $::c1
+  btree_commit $::b1
+  set ::c1 [btree_cursor $::b1 2]
+  btree_move_to $::c1 {}
+  set r {}
+  while 1 {
+    set key [btree_key $::c1]
+    if {$key==""} break
+    lappend r $key
+    lappend r [btree_data $::c1]
+    btree_next $::c1
+  }
+  set r   
+} {five 5.00 four 4.00 six 6.00 three 3.00 two 2.00}
+
+
+
+
+do_test btree-99.1 {
+  btree_close $::b1
+} {}
+
+
+} ;# end if( not mem: and has pager_open command );
+
+finish_test
index 102c8280b33a56efccdc93907858c74926a8bc1c..40777e8c25b00378eabb131359904f6321f19533 100644 (file)
 # This file implements regression tests for SQLite library.  The
 # focus of this script is page cache subsystem.
 #
-# $Id: pager.test,v 1.5 2001/05/24 21:06:36 drh Exp $
+# $Id: pager.test,v 1.6 2001/06/24 20:39:41 drh Exp $
 
 
 set testdir [file dirname $argv0]
 source $testdir/tester.tcl
 
-if {$dbprefix!="mem:" && [info commands pager_open]!=""} {
+if {$dbprefix!="memory:" && [info commands pager_open]!=""} {
 
 # Basic sanity check.  Open and close a pager.
 #