From: dan Date: Tue, 13 Dec 2011 19:03:34 +0000 (+0000) Subject: Add a hard limit to the number of chunks a multiplexed database may consist of if... X-Git-Tag: mountain-lion~8^2~39^2~2 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=27e69643cf81eb991dc5051c67857325c73220e2;p=thirdparty%2Fsqlite.git Add a hard limit to the number of chunks a multiplexed database may consist of if ENABLE_8_3_NAMES is defined. FossilOrigin-Name: 43a1264088c57bf598787b7a9f5d7a2536603d67 --- diff --git a/manifest b/manifest index 3dc07e0bd5..82b9fafa49 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Change\sthe\sSQLITE_EXTRA_INIT\sroutine\sto\stake\sa\ssingle\sargument\swhich\sis\sa\npointer\sto\sa\sstring.\s\sCall\sSQLITE_EXTRA_INIT\swith\sa\sNULL\sargument.\nFixes\sto\smultiplexor\sto\streat\sthe\sVFS\sproperly\sin\scorner\scases.\s\sFix\sthe\ninitialization\sof\smultiplex3.test. -D 2011-12-13T18:22:38.364 +C Add\sa\shard\slimit\sto\sthe\snumber\sof\schunks\sa\smultiplexed\sdatabase\smay\sconsist\sof\sif\sENABLE_8_3_NAMES\sis\sdefined. +D 2011-12-13T19:03:34.498 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5b4a3e12a850b021547e43daf886b25133b44c07 F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -214,7 +214,7 @@ F src/test_intarray.h 489edb9068bb926583445cb02589344961054207 F src/test_journal.c 03313c693cca72959dcaaf79f8d76f21c01e19ff F src/test_loadext.c df586c27176e3c2cb2e099c78da67bf14379a56e F src/test_malloc.c 8d416f29ad8573f32601f6056c9d2b17472e9ad5 -F src/test_multiplex.c c8cfaa7fa15494454a39c7e79241760d5fbe2c0c +F src/test_multiplex.c 10f881e4508976d970569fe0e7779bfec17907e5 F src/test_multiplex.h e99c571bc4968b7a9363b661481f3934bfead61d F src/test_mutex.c a6bd7b9cf6e19d989e31392b06ac8d189f0d573e F src/test_onefile.c 40cf9e212a377a6511469384a64b01e6e34b2eec @@ -606,7 +606,7 @@ F test/misc6.test 953cc693924d88e6117aeba16f46f0bf5abede91 F test/misc7.test eafaa41b9133d7a2ded4641bbe5f340731d35a52 F test/misuse.test ba4fb5d1a6101d1c171ea38b3c613d0661c83054 F test/multiplex.test 8bc3c71f73fe833bc8a659d454d320044a33b5da -F test/multiplex2.test 7e507a63f3981731556224b23646d29013b98c03 +F test/multiplex2.test 896ff138d27688b68c894b8166606454ce915793 F test/multiplex3.test e17b73e904dbd789de37192b6b94424e6f847bc3 F test/mutex1.test 78b2b9bb320e51d156c4efdb71b99b051e7a4b41 F test/mutex2.test bfeaeac2e73095b2ac32285d2756e3a65e681660 @@ -978,7 +978,7 @@ F tool/tostr.awk e75472c2f98dd76e06b8c9c1367f4ab07e122d06 F tool/vdbe-compress.tcl d70ea6d8a19e3571d7ab8c9b75cba86d1173ff0f F tool/warnings-clang.sh 9f406d66e750e8ac031c63a9ef3248aaa347ef2a F tool/warnings.sh fbc018d67fd7395f440c28f33ef0f94420226381 -P c7de6f683d0fec62bc138b4a53b5cccc80c736c3 -R c2c58817769bc21d103f97b44c17e047 -U drh -Z e8a8ea3bf562796b70179d1fa7b7b6fa +P 8e65b9132530e46c62bd1352bfc2e9c29f57af5f +R 72e3acbb02cd24af246addd5a37e5bd0 +U dan +Z bb7ad67fc331d74f2be1df794e13fcc3 diff --git a/manifest.uuid b/manifest.uuid index 8aab40e318..97f853f6e5 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -8e65b9132530e46c62bd1352bfc2e9c29f57af5f \ No newline at end of file +43a1264088c57bf598787b7a9f5d7a2536603d67 \ No newline at end of file diff --git a/src/test_multiplex.c b/src/test_multiplex.c index 0208d2d98d..85b63b48f4 100644 --- a/src/test_multiplex.c +++ b/src/test_multiplex.c @@ -81,6 +81,8 @@ #define sqlite3_mutex_notheld(X) ((void)(X),1) #endif /* SQLITE_THREADSAFE==0 */ +#define SQLITE_MULTIPLEX_JOURNAL_8_3_OFFSET 400 + /************************ Shim Definitions ******************************/ @@ -97,7 +99,7 @@ #endif /* This used to be the default limit on number of chunks, but -** it is no longer enforced. There is currently no limit to the +** it is no longer enforced. There is currently no limit to the ** number of chunks. ** ** May be changed by calling the xFileControl() interface. @@ -244,7 +246,7 @@ static int multiplexSubFilename(multiplexGroup *pGroup, int iChunk){ ** 003 and so forth. To avoid name collisions, add 100 to the ** extensions of journal files so that they are 101, 102, 103, .... */ - iChunk += 100; + iChunk += SQLITE_MULTIPLEX_JOURNAL_8_3_OFFSET; } #endif sqlite3_snprintf(4,&z[n],"%03d",iChunk); @@ -264,6 +266,18 @@ static sqlite3_file *multiplexSubOpen( ){ sqlite3_file *pSubOpen = 0; sqlite3_vfs *pOrigVfs = gMultiplex.pOrigVfs; /* Real VFS */ + +#ifdef SQLITE_ENABLE_8_3_NAMES + /* If JOURNAL_8_3_OFFSET is set to (say) 500, then any overflow files are + ** part of a database journal are named db.501, db.502, and so on. A + ** database may therefore not grow to larger than 500 chunks. Attempting + ** to open chunk 501 indicates the database is full. */ + if( iChunk>=SQLITE_MULTIPLEX_JOURNAL_8_3_OFFSET ){ + *rc = SQLITE_FULL; + return 0; + } +#endif + *rc = multiplexSubFilename(pGroup, iChunk); if( (*rc)==SQLITE_OK && (pSubOpen = pGroup->aReal[iChunk].p)==0 ){ pSubOpen = sqlite3_malloc( pOrigVfs->szOsFile ); @@ -633,7 +647,7 @@ static int multiplexWrite( rc = pSubOpen->pMethods->xWrite(pSubOpen, pBuf, iAmt, iOfst); } }else{ - while( iAmt > 0 ){ + while( rc==SQLITE_OK && iAmt>0 ){ int i = (int)(iOfst / pGroup->szChunk); sqlite3_file *pSubOpen = multiplexSubOpen(pGroup, i, &rc, NULL); if( pSubOpen ){ @@ -643,13 +657,9 @@ static int multiplexWrite( iAmt -= extra; rc = pSubOpen->pMethods->xWrite(pSubOpen, pBuf, iAmt, iOfst % pGroup->szChunk); - if( rc!=SQLITE_OK ) break; pBuf = (char *)pBuf + iAmt; iOfst += iAmt; iAmt = extra; - }else{ - rc = SQLITE_IOERR_WRITE; - break; } } } diff --git a/test/multiplex2.test b/test/multiplex2.test index b3a1656b02..bf5791fe88 100644 --- a/test/multiplex2.test +++ b/test/multiplex2.test @@ -14,6 +14,7 @@ set testdir [file dirname $argv0] source $testdir/tester.tcl source $testdir/malloc_common.tcl source $testdir/lock_common.tcl +set testprefix multiplex2 db close do_multiclient_test tn { @@ -46,10 +47,10 @@ do_multiclient_test tn { SELECT count(*) FROM t1; } - do_test multiplex-1.$tn.1 { sql1 { SELECT count(*) FROM t1 } } 512 - do_test multiplex-1.$tn.2 { sql2 { SELECT count(*) FROM t1 } } 512 + do_test 1.$tn.1 { sql1 { SELECT count(*) FROM t1 } } 512 + do_test 1.$tn.2 { sql2 { SELECT count(*) FROM t1 } } 512 sql2 { DELETE FROM t1 ; VACUUM } - do_test multiplex-1.$tn.3 { sql1 { SELECT count(*) FROM t1 } } 0 + do_test 1.$tn.3 { sql1 { SELECT count(*) FROM t1 } } 0 sql1 { INSERT INTO t1 VALUES(randomblob(10), randomblob(4000)); -- 1 @@ -65,8 +66,54 @@ do_multiclient_test tn { SELECT count(*) FROM t1; } - do_test multiplex-1.$tn.4 { sql2 { SELECT count(*) FROM t1 } } 512 + do_test 1.$tn.4 { sql2 { SELECT count(*) FROM t1 } } 512 } +catch {db close} +foreach f [glob -nocomplain test.*] { forcedelete $f } + +ifcapable 8_3_names { + sqlite3 db test.db -vfs multiplex + sqlite3_multiplex_control db main chunk_size [expr 256*1024] + + # Insert 512 * 256K (128MB) of data. If each row is around 4K, this means + # we need 32768 rows. + do_catchsql_test 2.1 { + CREATE TABLE t1(a, b); + INSERT INTO t1 VALUES(randomblob(10), randomblob(4000)); -- 1 + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 2 + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 4 + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 8 + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 16 + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 32 + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 64 + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 128 + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 256 + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 512 + + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 1K + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 2K + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 4K + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 8K + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 16K + INSERT INTO t1 SELECT randomblob(10), randomblob(4000) FROM t1; -- 32K + + } {1 {database or disk is full}} + + do_execsql_test 2.2 { + UPDATE t1 SET a=randomblob(9), b=randomblob(3900); + PRAGMA integrity_check; + } ok + + db close + sqlite3 db test.db -vfs multiplex + sqlite3_multiplex_control db main chunk_size [expr 256*1024] + + do_execsql_test 2.3 { + PRAGMA integrity_check; + } ok +} + +catch { db close } catch { sqlite3_multiplex_shutdown } finish_test