-C Avoid\sleaking\spage\sreferences\safter\san\sIO\serror\sis\sencountered.\s(CVS\s5082)
-D 2008-05-05T15:26:51
+C If\san\sIO\serror\soccurs\swhile\slocking\sthe\sdatabase\sand\schecking\sthe\scache\svalidity,\sunlock\sthe\sdatabase\sbefore\sreturning.\sTicket\s#3030.\s(CVS\s5083)
+D 2008-05-05T16:23:55
F Makefile.arm-wince-mingw32ce-gcc ac5f7b2cef0cd850d6f755ba6ee4ab961b1fadf7
F Makefile.in 25b3282a4ac39388632c2fb0e044ff494d490952
F Makefile.linux-gcc d53183f4aa6a9192d249731c90dbdffbd2c68654
F src/os_os2.c 41015b3fa91568761eb10cbf6ca27a0624ba0bda
F src/os_unix.c 8cf512c4321c3114f053dc9eaae394db2dc03ebe
F src/os_win.c 3a60bddd07ea6f8adb2314dd5996ac97b988f403
-F src/pager.c 2d495e9a439e7f5db12f02cd8efe6ae417bff26a
+F src/pager.c 5ac6728cf575afd87f8c5afe88bb768d3a641e34
F src/pager.h 4f051fd856de6fd3c19aef5f82eace54122b9173
F src/parse.y fc4bd35c6088901f7c8daead26c6fb11c87d22e7
F src/pragma.c 2e4bb2e76e48a32750529fdc4bfe86ac5f54e01b
F test/tclsqlite.test 3dfb48f46de4353376fad835390b493ba066b4dc
F test/tempdb.test b88ac8a19823cf771d742bf61eef93ef337c06b1
F test/temptable.test 19b851b9e3e64d91e9867619b2a3f5fffee6e125
-F test/tester.tcl 3f476ad2a7d8532b8de3ad7b0ed95995ee78f45b
+F test/tester.tcl 392890469221c2410759bb048bef99f5e20741a6
F test/thread001.test 8fbd9559da0bbdc273e00318c7fd66c162020af7
F test/thread002.test 2c4ad2c386f60f6fe268cd91c769ee35b3c1fd0b
F test/thread1.test 776c9e459b75ba905193b351926ac4019b049f35
F www/vdbe.tcl 87a31ace769f20d3627a64fa1fade7fed47b90d0
F www/version3.tcl 890248cf7b70e60c383b0e84d77d5132b3ead42b
F www/whentouse.tcl fc46eae081251c3c181bd79c5faef8195d7991a5
-P 2275fc6ee06b17da5808cecfa5570ac6439eaf74
-R 6d76420da4b019df82bc43b649a5cfb1
+P 198c395b01140ef48b6913c00188ba7168bfb081
+R 6e0e093a0f17c8e821e8c74c11e266a3
U danielk1977
-Z 562dc8fb914e4c15e377eee1cc4d777b
+Z 67d910e4d419f070999a506a26c6b1be
-198c395b01140ef48b6913c00188ba7168bfb081
\ No newline at end of file
+4ad1809192b616d1c12499825bcd0967dea76864
\ No newline at end of file
** file simultaneously, or one process from reading the database while
** another is writing.
**
-** @(#) $Id: pager.c,v 1.438 2008/05/01 17:16:53 drh Exp $
+** @(#) $Id: pager.c,v 1.439 2008/05/05 16:23:55 danielk1977 Exp $
*/
#ifndef SQLITE_OMIT_DISKIO
#include "sqliteInt.h"
if( !pPager->noReadlock ){
rc = pager_wait_on_lock(pPager, SHARED_LOCK);
if( rc!=SQLITE_OK ){
+ assert( pPager->state==PAGER_UNLOCK );
return pager_error(pPager, rc);
}
assert( pPager->state>=SHARED_LOCK );
*/
rc = hasHotJournal(pPager);
if( rc<0 ){
- return SQLITE_IOERR_NOMEM;
+ rc = SQLITE_IOERR_NOMEM;
+ goto failed;
}
if( rc==1 || isHot ){
/* Get an EXCLUSIVE lock on the database file. At this point it is
if( pPager->state<EXCLUSIVE_LOCK ){
rc = sqlite3OsLock(pPager->fd, EXCLUSIVE_LOCK);
if( rc!=SQLITE_OK ){
- pager_unlock(pPager);
- return pager_error(pPager, rc);
+ rc = pager_error(pPager, rc);
+ goto failed;
}
pPager->state = PAGER_EXCLUSIVE;
}
}
}
if( rc!=SQLITE_OK ){
- pager_unlock(pPager);
- switch( rc ){
- case SQLITE_NOMEM:
- case SQLITE_IOERR_UNLOCK:
- case SQLITE_IOERR_NOMEM:
- return rc;
- default:
- return SQLITE_BUSY;
+ if( rc!=SQLITE_NOMEM && rc!=SQLITE_IOERR_UNLOCK
+ && rc!=SQLITE_IOERR_NOMEM
+ ){
+ rc = SQLITE_BUSY;
}
+ goto failed;
}
pPager->journalOpen = 1;
pPager->journalStarted = 0;
*/
rc = pager_playback(pPager, 1);
if( rc!=SQLITE_OK ){
- return pager_error(pPager, rc);
+ rc = pager_error(pPager, rc);
+ goto failed;
}
assert(pPager->state==PAGER_SHARED ||
(pPager->exclusiveMode && pPager->state>PAGER_SHARED)
sqlite3PagerPagecount(pPager);
if( pPager->errCode ){
- return pPager->errCode;
+ rc = pPager->errCode;
+ goto failed;
}
if( pPager->dbSize>0 ){
IOTRACE(("CKVERS %p %d\n", pPager, sizeof(dbFileVers)));
rc = sqlite3OsRead(pPager->fd, &dbFileVers, sizeof(dbFileVers), 24);
if( rc!=SQLITE_OK ){
- return rc;
+ goto failed;
}
}else{
memset(dbFileVers, 0, sizeof(dbFileVers));
}
}
+ failed:
+ if( rc!=SQLITE_OK ){
+ /* pager_unlock() is a no-op for exclusive mode and in-memory databases. */
+ pager_unlock(pPager);
+ }
return rc;
}
# This file implements some common TCL routines used for regression
# testing the SQLite library
#
-# $Id: tester.tcl,v 1.117 2008/05/05 15:26:51 danielk1977 Exp $
+# $Id: tester.tcl,v 1.118 2008/05/05 16:23:55 danielk1977 Exp $
#
# What for user input before continuing. This gives an opportunity
expr { ($s && !$r && !$q) || (!$s && $r && $q) }
} {1}
+ # Check that no page references were leaked. There should be
+ # a single reference if there is still an active transaction,
+ # or zero otherwise.
+ #
if {$::go && $::sqlite_io_error_hardhit && $::ioerropts(-ckrefcount)} {
- # Check that no page references were leaked. There should be
- # a single reference if there is still an active transaction,
- # or zero otherwise.
do_test $testname.$n.4 {
set bt [btree_from_db db]
db_enter db
} [expr {[sqlite3_get_autocommit db]?0:1}]
}
+ # If there is an open database handle and no open transaction,
+ # and the pager is not running in exclusive-locking mode,
+ # check that the pager is in "unlocked" state. Theoretically,
+ # if a call to xUnlock() failed due to an IO error the underlying
+ # file may still be locked.
+ #
+ ifcapable pragma {
+ if { [info commands db] ne ""
+ && [db one {pragma locking_mode}] eq "normal"
+ && [sqlite3_get_autocommit db]
+ } {
+ do_test $testname.$n.5 {
+ set bt [btree_from_db db]
+ db_enter db
+ array set stats [btree_pager_stats $bt]
+ db_leave db
+ set stats(state)
+ } 0
+ }
+ }
+
# If an IO error occured, then the checksum of the database should
# be the same as before the script that caused the IO error was run.
+ #
if {$::go && $::sqlite_io_error_hardhit && $::ioerropts(-cksum)} {
do_test $testname.$n.5 {
catch {db close}