From: drh Date: Thu, 13 Dec 2018 21:05:45 +0000 (+0000) Subject: Fix a problem in sqlite3BtreeDelete() in which deleting an entry from a X-Git-Tag: version-3.27.0~297 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=1641f11f4c365aa17e2415d1f8018e3b66df0628;p=thirdparty%2Fsqlite.git Fix a problem in sqlite3BtreeDelete() in which deleting an entry from a corrupt database can leave a btree page with zero cells. FossilOrigin-Name: 682053d1e603c21b8085c39db618a39b23ec8d2c4d822fd19634db0e03038ea2 --- diff --git a/Makefile.in b/Makefile.in index 69371076fe..3d9a566505 100644 --- a/Makefile.in +++ b/Makefile.in @@ -1190,6 +1190,7 @@ TESTFIXTURE_FLAGS += -DSQLITE_SERIES_CONSTRAINT_VERIFY=1 TESTFIXTURE_FLAGS += -DSQLITE_DEFAULT_PAGE_SIZE=1024 TESTFIXTURE_FLAGS += -DSQLITE_ENABLE_STMTVTAB TESTFIXTURE_FLAGS += -DSQLITE_ENABLE_DBPAGE_VTAB +TESTFIXTURE_FLAGS += -DSQLITE_ENABLE_DESERIALIZE TESTFIXTURE_SRC0 = $(TESTSRC2) libsqlite3.la TESTFIXTURE_SRC1 = sqlite3.c diff --git a/Makefile.msc b/Makefile.msc index f5d47240f5..179215ecf4 100644 --- a/Makefile.msc +++ b/Makefile.msc @@ -2298,6 +2298,7 @@ TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) -DSQLITE_DEFAULT_PAGE_SIZE=1024 TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) -DSQLITE_ENABLE_STMTVTAB=1 TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) -DSQLITE_ENABLE_DBPAGE_VTAB=1 TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) -DSQLITE_ENABLE_JSON1=1 +TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) -DSQLITE_ENABLE_DESERIALIZE=1 TESTFIXTURE_FLAGS = $(TESTFIXTURE_FLAGS) $(TEST_CCONV_OPTS) TESTFIXTURE_SRC0 = $(TESTEXT) $(TESTSRC2) diff --git a/manifest b/manifest index f2901a3880..d90f60545b 100644 --- a/manifest +++ b/manifest @@ -1,10 +1,10 @@ -C Add\sthe\s"decode_hexdb"\sTCL\scommand\sto\stestfixture.\s\sAdd\sthe\sdbfuzz001.test\nmodule\sto\sdemonstration\show\sto\suse\sdecode_hexdb\sto\sdeserialize\sa\sdbtotxt\ndatabase\sdescription\sfor\suse\sin\sa\scorruption\stest. -D 2018-12-13T20:49:43.663 +C Fix\sa\sproblem\sin\ssqlite3BtreeDelete()\sin\swhich\sdeleting\san\sentry\sfrom\sa\ncorrupt\sdatabase\scan\sleave\sa\sbtree\spage\swith\szero\scells. +D 2018-12-13T21:05:45.342 F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1 F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea -F Makefile.in 2f1b61ac62689ca4e9cbff9fdb359578ea37ddd9252355ec0b7b9700ad56fe90 +F Makefile.in d8b254f8bb81bab43c340d70d17dc3babab40fcc8a348c8255881f780a45fee6 F Makefile.linux-gcc 7bc79876b875010e8c8f9502eb935ca92aa3c434 -F Makefile.msc 2ef13d6845b899eaaa6122c69b74175656a97e26666567af795f4cfe41b7a673 +F Makefile.msc 3c4c7e94419ff28cb68850188c9d153b343aed4c5ebed5965426232ed67ff9d9 F README.md 377233394b905d3b2e2b33741289e093bc93f2e7adbe00923b2c5958c9a9edee F VERSION 453e2f4529ca208196d5567db28d549d7151f79efd33f6e6cfe6e613e583a0be F aclocal.m4 a5c22d164aff7ed549d53a90fa56d56955281f50 @@ -448,7 +448,7 @@ F src/auth.c 0fac71038875693a937e506bceb492c5f136dd7b1249fbd4ae70b4e8da14f9df F src/backup.c 78d3cecfbe28230a3a9a1793e2ead609f469be43e8f486ca996006be551857ab F src/bitvec.c 17ea48eff8ba979f1f5b04cc484c7bb2be632f33 F src/btmutex.c 8acc2f464ee76324bf13310df5692a262b801808984c1b79defb2503bbafadb6 -F src/btree.c 4377d0d9a0b969c30b2bc343a12140a53ba6ab0dbf34c1686f232e67d87a557b +F src/btree.c d4bf14ab64339017db65a17c70a3b3d5edf39e5ec5373921133407a56c3e50e5 F src/btree.h febb2e817be499570b7a2e32a9bbb4b607a9234f6b84bb9ae84916d4806e96f2 F src/btreeInt.h 620ab4c7235f43572cf3ac2ac8723cbdf68073be4d29da24897c7b77dda5fd96 F src/build.c ef9d7dc73e40dd9d10c28848343e21e8bc1baaab92cfb75eda893fff4fbf6b55 @@ -773,7 +773,7 @@ F test/dataversion1.test 6e5e86ac681f0782e766ebcb56c019ae001522d114e0e111e5ebf68 F test/date.test 9b73bbeb1b82d9c1f44dec5cf563bf7da58d2373 F test/date2.test 74c234bece1b016e94dd4ef9c8cc7a199a8806c0e2291cab7ba64bace6350b10 F test/dbfuzz.c 73047c920d6210e5912c87cdffd9a1c281d4252e -F test/dbfuzz001.test 4c3952c8ecef5fa9e099f0fa461cea6b810e75da7647a41a5ad12cd5ac68accf +F test/dbfuzz001.test 24d24dbdbf3deb8a61921ecb36ecebb51248047195e209a2909613114c950c84 F test/dbfuzz2-seed1.db e6225c6f3d7b63f9c5b6867146a5f329d997ab105bee64644dc2b3a2f2aebaee F test/dbfuzz2.c b8ed9b32a1f287505e55970e55203bedcb9170f137ecefa2254033c9faccdfba F test/dbpage.test 650234ba683b9d82b899c6c51439819787e7609f17a0cc40e0080a7b6443bc38 @@ -1787,7 +1787,7 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93 F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0 -P 7ffa9858162774cba03a565a7b65135d9e8bfea726af1a29de6898f66c4b1261 -R 4be37804fa8bc77480b40b0d2da6c083 +P 1f583c53f3b7318c69f6e235934d97ef9493278feeab0837217076d7d071c35b +R bdea9a4eb87ba8aa256dc24af3d20da1 U drh -Z a0d1cca2acec8898665f02aaf70dc018 +Z 2389e6a9c76519655c1cfe39d2b8ef15 diff --git a/manifest.uuid b/manifest.uuid index fe345672e7..d63fa51aed 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -1f583c53f3b7318c69f6e235934d97ef9493278feeab0837217076d7d071c35b \ No newline at end of file +682053d1e603c21b8085c39db618a39b23ec8d2c4d822fd19634db0e03038ea2 \ No newline at end of file diff --git a/src/btree.c b/src/btree.c index 9046a72d32..d8b03a0ec6 100644 --- a/src/btree.c +++ b/src/btree.c @@ -8623,6 +8623,7 @@ int sqlite3BtreeDelete(BtCursor *pCur, u8 flags){ if( bPreserve ){ if( !pPage->leaf || (pPage->nFree+cellSizePtr(pPage,pCell)+2)>(int)(pBt->usableSize*2/3) + || pPage->nCell==1 /* See dbfuzz001.test for a test case */ ){ /* A b-tree rebalance will be required after deleting this entry. ** Save the cursor key. */ diff --git a/test/dbfuzz001.test b/test/dbfuzz001.test index 0a4894ffbc..bb9ab7e73c 100644 --- a/test/dbfuzz001.test +++ b/test/dbfuzz001.test @@ -19,6 +19,9 @@ ifcapable !deserialize { return } +# In the following database file, there is 384 bytes of free space +# on page 8 that does not appear on the freeblock list. +# do_test dbfuzz001-100 { sqlite3 db {} db deserialize [decode_hexdb { @@ -167,4 +170,14 @@ do_test dbfuzz001-100 { db eval {PRAGMA integrity_check} } {/Fragmentation of 384 bytes reported as 0 on page 8/} +# The DELETE query below deletes the very last cell from page 8. +# Prior to a certain fix to sqlite3BtreeDelete() and because of the +# corruption to the freeblock list on page 8, this would fail to +# cause a rebalance operation, which would leave the btree in a weird +# state that would lead to segfaults and or assertion faults. +# +do_execsql_test dbfuzz001-110 { + DELETE FROM t3 WHERE x IS NOT NULL AND +rowid=6; +} {} + finish_test