From: danielk1977 Date: Fri, 19 Dec 2008 16:31:11 +0000 (+0000) Subject: Add some crash-tests for savepoint. Fix a bug revealed by these tests. (CVS 6043) X-Git-Tag: version-3.6.10~141 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=488af099729fbc01f469002659fe873655d03f7b;p=thirdparty%2Fsqlite.git Add some crash-tests for savepoint. Fix a bug revealed by these tests. (CVS 6043) FossilOrigin-Name: 6f36c16678b6e3baa5a9d9ceba1a756a8034f3e1 --- diff --git a/manifest b/manifest index a2a91e46a7..1f2b42f904 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\sthe\sfile\sext/fts3/README.syntax,\scontaining\sdocumentation\sdescribing\sthe\stwo\squery\ssyntaxes\snow\ssupported\sby\sfts3.\s(CVS\s6042) -D 2008-12-19T11:37:39 +C Add\ssome\scrash-tests\sfor\ssavepoint.\sFix\sa\sbug\srevealed\sby\sthese\stests.\s(CVS\s6043) +D 2008-12-19T16:31:11 F Makefile.arm-wince-mingw32ce-gcc fcd5e9cd67fe88836360bb4f9ef4cb7f8e2fb5a0 F Makefile.in f7e4c81c347b04f7b0f1c1b081a168645d7b8af7 F Makefile.linux-gcc d53183f4aa6a9192d249731c90dbdffbd2c68654 @@ -142,7 +142,7 @@ F src/os_common.h 24525d8b7bce66c374dfc1810a6c9043f3359b60 F src/os_os2.c bed77dc26e3a95ce4a204936b9a1ca6fe612fcc5 F src/os_unix.c 96b4a6e87335ba943455740f311b4dfb63f26756 F src/os_win.c 496e3ceb499aedc63622a89ef76f7af2dd902709 -F src/pager.c fa8a93afc5374ccb7345fc46cfd959d31fd2bde3 +F src/pager.c 7760272fb2c508ab5db63790f76e5a6be5e29932 F src/pager.h 7191294438881eb4d13eedade97891e8dc993905 F src/parse.y 4d0e33a702dc3ea7b69d8ae1914b3fbd32e46057 F src/pcache.c 16dc8da6e6ba6250f8dfd9ee46036db1cbceedc6 @@ -481,7 +481,7 @@ F test/pragma2.test 5364893491b9231dd170e3459bfc2e2342658b47 F test/printf.test 262a5acd3158f788e9bdf7f18d718f3af32ff6ef F test/progress.test 5b075c3c790c7b2a61419bc199db87aaf48b8301 x F test/ptrchng.test ef1aa72d6cf35a2bbd0869a649b744e9d84977fc -F test/quick.test 5ef986df012628262ad4183cd8c28f0361911387 +F test/quick.test a244cd60117c07afaba2223bb025fd482ca13290 F test/quote.test 215897dbe8de1a6f701265836d6601cc6ed103e6 F test/randexpr1.tcl 40dec52119ed3a2b8b2a773bce24b63a3a746459 F test/randexpr1.test 1084050991e9ba22c1c10edd8d84673b501cc25a @@ -494,6 +494,7 @@ F test/safety.test b69e2b2dd5d52a3f78e216967086884bbc1a09c6 F test/savepoint.test 24b7d67971c0b7a8d22ba1cabbfd846e72f21594 F test/savepoint2.test 65fed3f179cff053e0a75864b1afc13e100fce1f F test/savepoint3.test b3c9aa5af3f777ccb8b9e15597c75c93eb5bc369 +F test/savepoint4.test 327937672df4511d8a61fd20fd6f21661119a45b F test/schema.test a8b000723375fd42c68d310091bdbd744fde647c F test/schema2.test 35e1c9696443d6694c8980c411497c2b5190d32e F test/select1.test d0a4cad954fd41c030ec16ffbd2d08a4c0548742 @@ -682,7 +683,7 @@ F tool/speedtest16.c c8a9c793df96db7e4933f0852abb7a03d48f2e81 F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e -P dcc8935fa0ccf86648c22818823bf1daef8f3939 -R 2c8851f424af14764a8787efe4f3aaed +P ed81ad5a5d22304a4d96e778e8e9094f74c461c0 +R 8635252259ed45c0604b104373f9fbca U danielk1977 -Z 187a31047d8fbeda35b637c188a3f06e +Z 13ba02f495748ab97267c0a69d578609 diff --git a/manifest.uuid b/manifest.uuid index 9f3b77ecbc..fc7ec4e231 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -ed81ad5a5d22304a4d96e778e8e9094f74c461c0 \ No newline at end of file +6f36c16678b6e3baa5a9d9ceba1a756a8034f3e1 \ No newline at end of file diff --git a/src/pager.c b/src/pager.c index b005a230a6..eac099ec1d 100644 --- a/src/pager.c +++ b/src/pager.c @@ -18,7 +18,7 @@ ** file simultaneously, or one process from reading the database while ** another is writing. ** -** @(#) $Id: pager.c,v 1.517 2008/12/18 18:31:39 danielk1977 Exp $ +** @(#) $Id: pager.c,v 1.518 2008/12/19 16:31:11 danielk1977 Exp $ */ #ifndef SQLITE_OMIT_DISKIO #include "sqliteInt.h" @@ -1153,6 +1153,7 @@ static int pager_playback_one_page( /* The temp storage must be allocated at this point */ assert( aData ); + assert( isMainJrnl || pDone ); rc = read32bits(jfd, offset, &pgno); if( rc!=SQLITE_OK ) return rc; @@ -1240,7 +1241,25 @@ static int pager_playback_one_page( if( pPager->xReiniter ){ pPager->xReiniter(pPg); } - if( isMainJrnl ){ + if( isMainJrnl && (!pDone || pPager->journalOff<=pPager->journalHdr) ){ + /* If the contents of this page were just restored from the main + ** journal file, then its content must be as they were when the + ** transaction was first opened. In this case we can mark the page + ** as clean, since there will be no need to write it out to the. + ** + ** There is one exception to this rule. If the page is being rolled + ** back as part of a savepoint (or statement) rollback from an + ** unsynced portion of the main journal file, then it is not safe + ** to mark the page as clean. This is because marking the page as + ** clean will clear the PGHDR_NEED_SYNC flag. Since the page is + ** already in the journal file (recorded in Pager.pInJournal) and + ** the PGHDR_NEED_SYNC flag is cleared, if the page is written to + ** again within this transaction, it will be marked as dirty but + ** the PGHDR_NEED_SYNC flag will not be set. It could then potentially + ** be written out into the database file before its journal file + ** segment is synced. If a crash occurs during or following this, + ** database corruption may ensue. + */ sqlite3PcacheMakeClean(pPg); } #ifdef SQLITE_CHECK_PAGES diff --git a/test/quick.test b/test/quick.test index ff7fd2d977..123bbaad53 100644 --- a/test/quick.test +++ b/test/quick.test @@ -6,7 +6,7 @@ #*********************************************************************** # This file runs all tests. # -# $Id: quick.test,v 1.89 2008/12/12 17:56:16 drh Exp $ +# $Id: quick.test,v 1.90 2008/12/19 16:31:12 danielk1977 Exp $ proc lshift {lvar} { upvar $lvar l @@ -69,6 +69,7 @@ set EXCLUDE { onefile.test permutations.test quick.test + savepoint4.test select9.test soak.test speed1.test diff --git a/test/savepoint4.test b/test/savepoint4.test new file mode 100644 index 0000000000..ebb3786220 --- /dev/null +++ b/test/savepoint4.test @@ -0,0 +1,80 @@ +# 2008 December 15 +# +# 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: savepoint4.test,v 1.1 2008/12/19 16:31:12 danielk1977 Exp $ + +set testdir [file dirname $argv0] +source $testdir/tester.tcl + + +proc signature {} { + return [db eval {SELECT count(*), md5sum(x) FROM t3}] +} + +expr srand(0) + +do_test savepoint4-1 { + execsql { + PRAGMA cache_size=10; + BEGIN; + CREATE TABLE t3(x TEXT); + INSERT INTO t3 VALUES(randstr(10,400)); + INSERT INTO t3 VALUES(randstr(10,400)); + INSERT INTO t3 SELECT randstr(10,400) FROM t3; + INSERT INTO t3 SELECT randstr(10,400) FROM t3; + INSERT INTO t3 SELECT randstr(10,400) FROM t3; + INSERT INTO t3 SELECT randstr(10,400) FROM t3; + INSERT INTO t3 SELECT randstr(10,400) FROM t3; + INSERT INTO t3 SELECT randstr(10,400) FROM t3; + INSERT INTO t3 SELECT randstr(10,400) FROM t3; + INSERT INTO t3 SELECT randstr(10,400) FROM t3; + INSERT INTO t3 SELECT randstr(10,400) FROM t3; + COMMIT; + SELECT count(*) FROM t3; + } +} {1024} + + +unset -nocomplain ::sig + +for {set ii 1} {$ii<25} {incr ii} { + set ::sig [signature] + + set crashed 1 + for {set iDelay 1} {$crashed} {incr iDelay} { + do_test savepoint4-$ii.1.$iDelay { + set ret [crashsql -delay $iDelay -file test.db-journal { + PRAGMA cache_size = 20; + SAVEPOINT one; + DELETE FROM t3 WHERE random()%2==0; + SAVEPOINT two; + INSERT INTO t3 SELECT randstr(10,10)||x FROM t3; + ROLLBACK TO two; + UPDATE t3 SET x = randstr(10, 400) WHERE random()%10; + RELEASE two; + ROLLBACK TO one; + }] + signature + } $::sig + set crashed [lindex $ret 0] + integrity_check savepoint4-$ii.1.$iDelay.integrity + } + + do_test savepoint4-$ii.2 { + execsql { + DELETE FROM t3 WHERE random()%10==0; + INSERT INTO t3 SELECT randstr(10,10)||x FROM t3 WHERE random()%9==0; + } + } {} +} + +finish_test +