diff options
author | drh <drh@noemail.net> | 2001-01-21 00:58:07 +0000 |
---|---|---|
committer | drh <drh@noemail.net> | 2001-01-21 00:58:07 +0000 |
commit | 2702114089149ffef188d34db60a50d997a5d277 (patch) | |
tree | cc282dd2895728377f29c71080f265dc5d208928 | |
parent | 41a2b48bd0190da9e00dacc02982cd831e673d38 (diff) | |
download | sqlite-2702114089149ffef188d34db60a50d997a5d277.tar.gz sqlite-2702114089149ffef188d34db60a50d997a5d277.zip |
:-) (CVS 179)
FossilOrigin-Name: d5f2a668978c0d108045237f19b0a7efa07678f2
-rw-r--r-- | manifest | 17 | ||||
-rw-r--r-- | manifest.uuid | 2 | ||||
-rw-r--r-- | src/TODO | 32 | ||||
-rw-r--r-- | src/db.c | 138 | ||||
-rw-r--r-- | src/pg.c | 6 | ||||
-rw-r--r-- | src/pg.h | 4 |
6 files changed, 129 insertions, 70 deletions
@@ -1,5 +1,5 @@ -C :-)\s(CVS\s178) -D 2001-01-20T19:52:49 +C :-)\s(CVS\s179) +D 2001-01-21T00:58:08 F COPYRIGHT 74a8a6531a42e124df07ab5599aad63870fa0bd4 F Makefile.in 7efa81e2985b45ba73db27d55b70cc927f5abfd7 F README 51f6a4e7408b34afa5bc1c0485f61b6a4efb6958 @@ -7,8 +7,9 @@ F VERSION 05e17b646a817240c206186f94f8f4c70974d5dc F configure 3dc1edb9dcf60215e31ff72b447935ab62211442 x F configure.in d892ca33db7e88a055519ce2f36dcb11020e8fff F doc/lemon.html e233a3e97a779c7a87e1bc4528c664a58e49dd47 +F src/TODO 435a4ea4f760375f6821f390ea4ee0767f455b40 F src/build.c 7aa5879bf58ea6bbff22c26c59d1130021fa6ca4 -F src/db.c ba41f4dfd27b9572bf0e1c0690a2316a445b20a3 +F src/db.c af04a75b521be61f5d7f3fab12ba6d477937854e F src/db.h 488f01d3c0182568b0ec1186149603e271e79c43 F src/dbbe.c 162d29b09ac379f160892c5795efc14099dcc8eb F src/dbbe.h 0435a36906a839cce062608f51bd9d3e79878fec @@ -19,8 +20,8 @@ F src/expr.c 49bc261fdc4f4fb91c74cd668a9a952c00e85931 F src/insert.c 4bc1cab84f7805d560a1417734a532843e30b762 F src/main.c 92fcd6d967ceee1f96a5b9543779eef6e9b56913 F src/parse.y 25ee4d8efccc4b247c32fe4ab194e3dd8fd5a4ee -F src/pg.c 11fa728362e9e79abccd3aafe3df567d091d2f07 -F src/pg.h fd0abb277f6aaf47a257b80c33ee8f9ac2878f28 +F src/pg.c 8bf498216976bea261e7a02724c4fdcc96f6ee2f +F src/pg.h a95c4803a1aae99449aa2c0a1af0c8d863a3f340 F src/printf.c 1efb6b3e7f28a93be57132de3f8f400d2ac1460e F src/random.c 3dc42fb35d834901577aa547308ff3c8941fea25 F src/select.c 0cadab95c8011ddbffe804de94f12f3c0e317863 @@ -81,7 +82,7 @@ F www/opcode.tcl cb3a1abf8b7b9be9f3a228d097d6bf8b742c2b6f F www/sqlite.tcl cb0d23d8f061a80543928755ec7775da6e4f362f F www/tclsqlite.tcl 06f81c401f79a04f2c5ebfb97e7c176225c0aef2 F www/vdbe.tcl 0c8aaa529dd216ccbf7daaabd80985e413d5f9ad -P a60af40a3e2e2903d0caa8b81b7e5a4cdc67cd52 -R b2f8b941964b1053933a62dc3ab1e85c +P 1662063dfb0925bd439e3e2e49bff82705e20fd0 +R fd78a6c47a1cf484ff41084553feb3d7 U drh -Z ba0dde0120f3f143a2193838c9b91af7 +Z d0449f87f2ca7d65ae84190b1471dad1 diff --git a/manifest.uuid b/manifest.uuid index 90ea0dfc3..7c49721d7 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -1662063dfb0925bd439e3e2e49bff82705e20fd0
\ No newline at end of file +d5f2a668978c0d108045237f19b0a7efa07678f2
\ No newline at end of file diff --git a/src/TODO b/src/TODO new file mode 100644 index 000000000..50e1b9fba --- /dev/null +++ b/src/TODO @@ -0,0 +1,32 @@ + * Finish fleshing out the db.c file. + - sqliteDbReadOvfl + - sqliteDbSpreadLoad + - sqliteDbSplit + - sqliteDbNextIndexLevel + - fix sqliteDbCursorNext to work right after sqliteDbCursorDelete + * Compile db.c with -Wall and get no errors. + * Make a pass over pg.c and db.c looking for errors. + - correct handling of I/O errors, malloc failures, etc. + - page leaks (not calling sqlitePgUnref) + * Write a test interface for db.c. + * Compile and link against the db test interface. + * Generate tests for the db interface. + * Add read/write locks to pg.c + * Add an sqliteDbReorganize() function. + * Integrate db into vdbe. + * Modify code generation to take advantage of the new db interface. + - Able to delete without disturbing scan order + - Now keeps a count of number of table entries + + Special processing for count(*) + + Better selection of indices on a select + - Transactions + * Modify sqlite_master to store the table number. + * Add a cache in DbCursor to speed up the sqliteDbReadOvfl() routine. + +Longer term: + * Document all the changes and release Sqlite 2.0. + * Techniques for optimizing querys by grouping data with similar + indices. + * "OPTIMIZE select" statement to automatically create and/or tune + indices. + * Parse and use constraints. @@ -21,7 +21,7 @@ ** http://www.hwaci.com/drh/ ** ************************************************************************* -** $Id: db.c,v 1.1 2001/01/20 19:52:49 drh Exp $ +** $Id: db.c,v 1.2 2001/01/21 00:58:08 drh Exp $ */ #include "sqliteInt.h" #include "pg.h" @@ -178,7 +178,7 @@ int sqliteDbAllocPage(Db *pDb, u32 *pPgno, u32 **ppPage){ return SQLITE_OK; } } - if( (rc = sqlitePgAlloc(pDb->pPgr, &pgno))==SQLITE_OK && + if( (rc = sqlitePgCount(pDb->pPgr, &pgno))==SQLITE_OK && (rc = sqlitePgGet(pDb->pPgr, pgno, (void**)ppPage))==SQLITE_OK ){ *pPgno = pgno; return SQLITE_OK; @@ -200,6 +200,36 @@ static void sqliteDbFreePage(DB *pDb, u32 pgno, u32 *aPage){ } /* +** Write data into overflow pages. The first overflow page is +** provided in the second argument. If additional pages are +** needed, they must be allocated. +*/ +static int sqliteDbWriteOvfl(Db *pDb, u32 *aPage, int nData, const void *pData){ + while( nData>0 ){ + int toWrite, rc; + u32 *nxPage, nxPgno; + if( nData > SQLITE_PAGE_SIZE - 2*sizeof(u32) ){ + toWrite = SQLITE_PAGE_SIZE - 2*sizeof(u32); + }else{ + toWrite = nData; + } + memcpy(&aPage[2], pData, toWrite); + nData -= toWrite; + pData = &((char*)pData)[toWrite]; + if( nData<=0 ) break; + rc = sqliteDbAllocPage(pDb, &nxPgno, &nxPage); + if( rc!=SQLITE_OK ) return rc; /* Be smarter here */ + aPage[1] = SWB(nxPgno); + nxPage[0] = SWB(BLOCK_MAGIC|BLOCK_OVERFLOW); + nxPage[1] = 0; + sqlitePgTouch(aPage); + sqlitePgUnref(aPage); + aPage = nxPage; + } + return SQLITE_OK; +} + +/* ** Open a database. */ int sqliteDbOpen(const char *filename, Db **ppDb){ @@ -207,6 +237,7 @@ int sqliteDbOpen(const char *filename, Db **ppDb){ Pgr *pPgr = 0; u32 *aPage1; int rc; + u32 nPage; rc = sqlitePgOpen(filename, &pPgr); if( rc!=SQLITE_OK ) goto open_err; @@ -218,8 +249,15 @@ int sqliteDbOpen(const char *filename, Db **ppDb){ pDb->pPgr = pPgr; pDb->pCursor = 0; pDb->inTransaction = 0; + sqlitePgCount(pDb->pPgr, &nPage); rc = sqlitePgGet(pDb->pPgr, 1, &aPage1); if( rc!=0 ) goto open_err; + if( nPage==0 ){ + sqlitePgBeginTransaction(pDb->pPgr); + aPage1[0] = SWB(BLOCK_MAGIC|BLOCK_CONTENT); + sqlitePgTouch(aPage1); + sqlitePgCommit(pDb->pPgr); + } pDb->nContent = SWB(aPage1[3]) + 2; pDb->nAlloc = 0; rc = sqliteDbExpandContent(pDb, pDb->nContent); @@ -275,10 +313,14 @@ int sqliteDbBeginTransaction(Db *pDb){ ** Commit changes to the database */ int sqliteDbCommit(Db *pDb){ + u32 *aPage; + int rc; if( !pDb->inTransaction ){ return SQLITE_OK; } - sqliteDbWriteOvfl(pDb, 1, 0, pDb->nContent*sizeof(u32), pDb->aContent); + rc = sqlitePgGet(pDb->pPgr, 1, &aPage); + if( rc!=SQLITE_OK ) return rc; + sqliteDbWriteOvfl(pDb, aPage, pDb->nContent*sizeof(u32), pDb->aContent); rc = sqlitePgCommit(pDb->pPgr); if( rc!=SQLITE_OK ) return rc; pDb->inTransaction = 0; @@ -732,7 +774,7 @@ int sqliteDbCursorReadKey(DbCursor *pCur, int amt, int offset, void *buf){ assert( aPage ); assert( idx>=2 && idx+4<(SQLITE_PAGE_SIZE/sizeof(u32)) nKey = SWB(aPage[idx+2]); - if( nKey & 0x80000000 ){ ############### -v + if( nKey & 0x80000000 ){ return sqliteDbReadOvfl(pCur->pDb, SWB(aPage[idx+4]), 0, amt, offset, buf); } if( nKey==4 ){ @@ -979,7 +1021,8 @@ int sqliteDbCursorInsert( rc = sqliteDbAllocPage(pCur->pDb, &newPgno, &newPage); if( rc!=SQLITE_OK ) goto write_err; aPage[i+4] = SWB(newPgno); - rc = sqliteDbWriteOvfl(pCur->pDb, newPgno, newPage, nKey, pKey); ######## + newPage[0] = SWB(BLOCK_MAGIC | BLOCK_OVERFLOW); + rc = sqliteDbWriteOvfl(pCur->pDb, newPage, nKey, pKey); if( rc!=SQLITE_OK ) goto write_err; j = i + 5; available -= 1; @@ -995,7 +1038,8 @@ int sqliteDbCursorInsert( rc = sqliteDbAllocPage(pCur->pDb, &newPgno, &newPage); if( rc!=SQLITE_OK ) goto write_err; aPage[j] = SWB(newPgno); - rc = sqliteDbWriteOvfl(pCur->pDb, newPgno, newPage, nData, pData); + newPage[0] = SWB(BLOCK_MAGIC | BLOCK_OVERFLOW); + rc = sqliteDbWriteOvfl(pCur->pDb, newPage, nData, pData); if( rc!=SQLITE_OK ) goto write_err; available -= 1; j++; @@ -1022,57 +1066,11 @@ write_err: } /* -** The cursor is pointing to a particular entry of an index page -** when this routine is called. This routine frees everything that -** is on the page that the index entry points to. -*/ -static int sqliteDbPruneTree(DbCursor *pCur){ - int i, idx; - u32 *aPage; - int from, to, limit, n; - int rc; - - i = pCur->nLevel-1; - assert( i>=0 && i<MAX_LEVEL ); - idx = pCur->aLevel[i].idx; - aPage = pCur->aLevel[i].aPage; - assert( SWB(aPage[0])==BLOCK_MAGIC|BLOCK_INDEX ); - assert( idx>=3 && idx<SQLITE_PAGE_SIZE/sizeof(u32) ); - n = SWB(aPage[2]); - assert( n>=2 && n<=SQLITE_PAGE_SIZE/2*sizeof(u32)-2 ); - sqliteDbDropPage(pCur->pDb, SWB(aPage[idx+1]); - to = idx; - from = idx+2; - limit = n*2 + 3; - while( from<limit ){ - aPage[to++] = aPage[from++]; - } - n--; - if( n==1 ){ - u32 oldPgno, *oldPage; - oldPgno = SWB(aPage[4]); - rc = sqlitePgGet(pCur->pDb->pPgr, oldPgno, &oldPage); - if( rc!=SQLITE_OK ){ - return rc; /* Do something smarter here */ - } - memcpy(aPage, oldPage, SQLITE_PAGE_SIZE); - oldPage[0] = SWB(BLOCK_MAGIC|BLOCK_OVERFLOW); - oldPage[1] = 0; - sqliteDbDropPage(pCur->pDb, oldPgno); - sqlitePgUnref(oldPage); - }else{ - aPage[2] = SWB(n); - } - sqlitePgTouch(aPage); - return SQLITE_OK; -} - -/* ** Delete the entry that the cursor points to. */ int sqliteDbCursorDelete(DbCursor *pCur){ int i, idx; - int from, to; + int from, to, limit, n; int entrySize; u32 *aPage; if( !pCur->onEntry ) return SQLITE_NOTFOUND; @@ -1113,5 +1111,37 @@ int sqliteDbCursorDelete(DbCursor *pCur){ */ sqliteDbResetCursor(pCur, pCur->nLevel-1); - return sqliteDbPruneTree(pCur); + i = pCur->nLevel-1; + assert( i>=0 && i<MAX_LEVEL ); + idx = pCur->aLevel[i].idx; + aPage = pCur->aLevel[i].aPage; + assert( SWB(aPage[0])==BLOCK_MAGIC|BLOCK_INDEX ); + assert( idx>=3 && idx<SQLITE_PAGE_SIZE/sizeof(u32) ); + n = SWB(aPage[2]); + assert( n>=2 && n<=SQLITE_PAGE_SIZE/2*sizeof(u32)-2 ); + sqliteDbDropPage(pCur->pDb, SWB(aPage[idx+1]); + to = idx; + from = idx+2; + limit = n*2 + 3; + while( from<limit ){ + aPage[to++] = aPage[from++]; + } + n--; + if( n==1 ){ + u32 oldPgno, *oldPage; + oldPgno = SWB(aPage[4]); + rc = sqlitePgGet(pCur->pDb->pPgr, oldPgno, &oldPage); + if( rc!=SQLITE_OK ){ + return rc; /* Do something smarter here */ + } + memcpy(aPage, oldPage, SQLITE_PAGE_SIZE); + oldPage[0] = SWB(BLOCK_MAGIC|BLOCK_OVERFLOW); + oldPage[1] = 0; + sqliteDbDropPage(pCur->pDb, oldPgno); + sqlitePgUnref(oldPage); + }else{ + aPage[2] = SWB(n); + } + sqlitePgTouch(aPage); + return SQLITE_OK; } @@ -21,7 +21,7 @@ ** http://www.hwaci.com/drh/ ** ************************************************************************* -** $Id: pg.c,v 1.2 2001/01/20 19:52:49 drh Exp $ +** $Id: pg.c,v 1.3 2001/01/21 00:58:08 drh Exp $ */ #include <assert.h> #include <sys/types.h> @@ -38,10 +38,6 @@ # define TRACE(X) printf X; fflush(stdout); #endif -#ifndef SQLITE_IOERR -# define SQLITE_IOERR SQLITE_ERROR -#endif - /* ** Hash table sizes */ @@ -21,7 +21,7 @@ ** http://www.hwaci.com/drh/ ** ************************************************************************* -** $Id: pg.h,v 1.2 2001/01/20 19:52:49 drh Exp $ +** $Id: pg.h,v 1.3 2001/01/21 00:58:09 drh Exp $ */ typedef struct Pgr Pgr; @@ -36,5 +36,5 @@ int sqlitePgRollback(Pgr*); int sqlitePgGet(Pgr*, u32 pgno, void **); int sqlitePgUnref(void*); int sqlitePgTouch(void*); -int sqlitePgAlloc(Pgr*, u32*); +int sqlitePgCount(Pgr*, u32*); u32 sqlitePgNum(void*); |