Many hyperlinks are disabled.
Use anonymous login
to enable hyperlinks.
Overview
Comment: | Correct subtle timing issues in the win32lock test cases and in the lock_win32_file Tcl command. Also, eliminate superfluous MSVC compiler warnings. |
---|---|
Downloads: | Tarball | ZIP archive |
Timelines: | family | ancestors | descendants | both | winopen-retry-logic |
Files: | files | file ages | folders |
SHA1: |
7baf02946e14eb889d864984ff3b3822 |
User & Date: | mistachkin 2011-08-02 23:34:00.968 |
Context
2011-08-02
| ||
23:45 | Add explanatory comment to the win32lock-2.2 test case. (Closed-Leaf check-in: 4cb17881d9 user: mistachkin tags: winopen-retry-logic) | |
23:34 | Correct subtle timing issues in the win32lock test cases and in the lock_win32_file Tcl command. Also, eliminate superfluous MSVC compiler warnings. (check-in: 7baf02946e user: mistachkin tags: winopen-retry-logic) | |
20:19 | Fix missing info exists check for win32lock-2.2 (the one previously applied to win32lock-1.2). (check-in: 8a52698e64 user: mistachkin tags: winopen-retry-logic) | |
Changes
Changes to Makefile.msc.
︙ | ︙ | |||
39 40 41 42 43 44 45 46 47 48 49 50 51 52 | # Define -DNDEBUG to compile without debugging (i.e., for production usage) # Omitting the define will cause extra debugging code to be inserted and # includes extra comments when "EXPLAIN stmt" is used. # TCC = $(TCC) -DNDEBUG # The locations of the Tcl header and library files. Also, the library that # non-stubs enabled programs using Tcl must link against. These variables # (TCLINCDIR, TCLLIBDIR, and LIBTCL) may be overridden via the environment # prior to running nmake in order to match the actual installed location and # version on this machine. # !if "$(TCLINCDIR)" == "" | > > > > > | 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 | # Define -DNDEBUG to compile without debugging (i.e., for production usage) # Omitting the define will cause extra debugging code to be inserted and # includes extra comments when "EXPLAIN stmt" is used. # TCC = $(TCC) -DNDEBUG # # Prevent warnings about "insecure" runtime library functions being used. # TCC = $(TCC) -D_CRT_SECURE_NO_DEPRECATE -D_CRT_SECURE_NO_WARNINGS # The locations of the Tcl header and library files. Also, the library that # non-stubs enabled programs using Tcl must link against. These variables # (TCLINCDIR, TCLLIBDIR, and LIBTCL) may be overridden via the environment # prior to running nmake in order to match the actual installed location and # version on this machine. # !if "$(TCLINCDIR)" == "" |
︙ | ︙ |
Changes to src/test1.c.
︙ | ︙ | |||
5641 5642 5643 5644 5645 5646 5647 5648 5649 5650 5651 5652 5653 5654 5655 5656 5657 5658 5659 5660 5661 5662 5663 5664 5665 5666 5667 5668 5669 | #if SQLITE_OS_WIN /* ** Information passed from the main thread into the windows file locker ** background thread. */ struct win32FileLocker { HANDLE h; /* Handle of the file to be locked */ int delay1; /* Delay before locking */ int delay2; /* Delay before unlocking */ int ok; /* Finished ok */ int err; /* True if an error occurs */ }; #endif #if SQLITE_OS_WIN /* ** The background thread that does file locking. */ static void win32_file_locker(void *pAppData){ struct win32FileLocker *p = (struct win32FileLocker*)pAppData; if( p->delay1 ) Sleep(p->delay1); if( LockFile(p->h, 0, 0, 100000000, 0) ){ Sleep(p->delay2); UnlockFile(p->h, 0, 0, 100000000, 0); p->ok = 1; }else{ p->err = 1; | > > > > > > > > | 5641 5642 5643 5644 5645 5646 5647 5648 5649 5650 5651 5652 5653 5654 5655 5656 5657 5658 5659 5660 5661 5662 5663 5664 5665 5666 5667 5668 5669 5670 5671 5672 5673 5674 5675 5676 5677 | #if SQLITE_OS_WIN /* ** Information passed from the main thread into the windows file locker ** background thread. */ struct win32FileLocker { char *evName; /* Name of event to signal thread startup */ HANDLE h; /* Handle of the file to be locked */ int delay1; /* Delay before locking */ int delay2; /* Delay before unlocking */ int ok; /* Finished ok */ int err; /* True if an error occurs */ }; #endif #if SQLITE_OS_WIN /* ** The background thread that does file locking. */ static void win32_file_locker(void *pAppData){ struct win32FileLocker *p = (struct win32FileLocker*)pAppData; if( p->evName ){ HANDLE ev = OpenEvent(EVENT_MODIFY_STATE, FALSE, p->evName); if ( ev ){ SetEvent(ev); CloseHandle(ev); } } if( p->delay1 ) Sleep(p->delay1); if( LockFile(p->h, 0, 0, 100000000, 0) ){ Sleep(p->delay2); UnlockFile(p->h, 0, 0, 100000000, 0); p->ok = 1; }else{ p->err = 1; |
︙ | ︙ | |||
5684 5685 5686 5687 5688 5689 5690 | */ static int win32_file_lock( void * clientData, Tcl_Interp *interp, int objc, Tcl_Obj *CONST objv[] ){ | | > > > < | 5692 5693 5694 5695 5696 5697 5698 5699 5700 5701 5702 5703 5704 5705 5706 5707 5708 5709 5710 5711 5712 5713 5714 5715 5716 5717 | */ static int win32_file_lock( void * clientData, Tcl_Interp *interp, int objc, Tcl_Obj *CONST objv[] ){ static struct win32FileLocker x = { "win32_file_lock", 0, 0, 0, 0, 0 }; const char *zFilename; char zBuf[200]; int retry = 0; HANDLE ev; DWORD wResult; if( objc!=4 && objc!=1 ){ Tcl_WrongNumArgs(interp, 1, objv, "FILENAME DELAY1 DELAY2"); return TCL_ERROR; } if( objc==1 ){ sqlite3_snprintf(sizeof(zBuf), zBuf, "%d %d %d %d %d", x.ok, x.err, x.delay1, x.delay2, x.h); Tcl_AppendResult(interp, zBuf, (char*)0); return TCL_OK; } while( x.h && retry<30 ){ retry++; |
︙ | ︙ | |||
5716 5717 5718 5719 5720 5721 5722 5723 5724 5725 5726 5727 5728 5729 5730 5731 5732 | zFilename = Tcl_GetString(objv[1]); x.h = CreateFile(zFilename, GENERIC_READ|GENERIC_WRITE, FILE_SHARE_READ|FILE_SHARE_WRITE, 0, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0); if( !x.h ){ Tcl_AppendResult(interp, "cannot open file: ", zFilename, (char*)0); return TCL_ERROR; } _beginthread(win32_file_locker, 0, (void*)&x); Sleep(0); return TCL_OK; } #endif /* ** optimization_control DB OPT BOOLEAN | > > > > > > > > > > > > | 5726 5727 5728 5729 5730 5731 5732 5733 5734 5735 5736 5737 5738 5739 5740 5741 5742 5743 5744 5745 5746 5747 5748 5749 5750 5751 5752 5753 5754 | zFilename = Tcl_GetString(objv[1]); x.h = CreateFile(zFilename, GENERIC_READ|GENERIC_WRITE, FILE_SHARE_READ|FILE_SHARE_WRITE, 0, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0); if( !x.h ){ Tcl_AppendResult(interp, "cannot open file: ", zFilename, (char*)0); return TCL_ERROR; } ev = CreateEvent(NULL, TRUE, FALSE, x.evName); if ( !ev ){ Tcl_AppendResult(interp, "cannot create event: ", x.evName, (char*)0); return TCL_ERROR; } _beginthread(win32_file_locker, 0, (void*)&x); Sleep(0); if ( (wResult = WaitForSingleObject(ev, 10000))!=WAIT_OBJECT_0 ){ sqlite3_snprintf(sizeof(zBuf), zBuf, "0x%x", wResult); Tcl_AppendResult(interp, "wait failed: ", zBuf, (char*)0); CloseHandle(ev); return TCL_ERROR; } CloseHandle(ev); return TCL_OK; } #endif /* ** optimization_control DB OPT BOOLEAN |
︙ | ︙ |
Changes to test/win32lock.test.
︙ | ︙ | |||
37 38 39 40 41 42 43 | INSERT INTO t1 VALUES(3,randomblob(25000)); INSERT INTO t1 VALUES(4,randomblob(12500)); SELECT x, length(y) FROM t1 ORDER BY rowid; } } {1 100000 2 50000 3 25000 4 12500} unset -nocomplain delay1 rc msg | < < > > > > < > > | < > | < > | > > > | < > > | < > | < > | > | 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 | INSERT INTO t1 VALUES(3,randomblob(25000)); INSERT INTO t1 VALUES(4,randomblob(12500)); SELECT x, length(y) FROM t1 ORDER BY rowid; } } {1 100000 2 50000 3 25000 4 12500} unset -nocomplain delay1 rc msg set old_pending_byte [sqlite3_test_control_pending_byte 0x40000000] set win32_lock_ok [list] set win32_lock_error [list] set delay1 25 while {1} { lock_win32_file test.db 0 $::delay1 set ::log {} set rc [catch {db eval {SELECT x, length(y) FROM t1 ORDER BY rowid}} msg] if {$rc} { lappend win32_lock_error $::delay1 do_test win32lock-1.2-$delay1-error { set ::msg } {disk I/O error} } else { lappend win32_lock_ok $::delay1 do_test win32lock-1.2-$delay1-ok { set ::msg } {1 100000 2 50000 3 25000 4 12500} if {[info exists ::log] && $::log!=""} { do_test win32lock-1.2-$delay1-log1 { regsub {\d+} $::log # x set x } {{delayed #ms for lock/sharing conflict}} } } if {[llength $win32_lock_ok] && [llength $win32_lock_error]} break incr delay1 25 sqlite3_sleep 10 } do_test win32lock-2.0 { file_control_win32_av_retry db -1 -1 } {0 10 25} do_test win32lock-2.1 { file_control_win32_av_retry db 1 1 } {0 1 1} set win32_lock_ok [list] set win32_lock_error [list] set delay1 1 while {1} { lock_win32_file test.db 0 $::delay1 set ::log {} set rc [catch {db eval {SELECT x, length(y) FROM t1 ORDER BY rowid}} msg] if {$rc} { lappend win32_lock_error $::delay1 do_test win32lock-2.2-$delay1-error { set ::msg } {disk I/O error} } else { lappend win32_lock_ok $::delay1 do_test win32lock-2.2-$delay1-ok { set ::msg } {1 100000 2 50000 3 25000 4 12500} if {[info exists ::log] && $::log!=""} { do_test win32lock-2.2-$delay1-log1 { regsub {\d+} $::log # x set x } {{delayed #ms for lock/sharing conflict}} } } if {[llength $win32_lock_ok] && [llength $win32_lock_error]} break incr delay1 1 sqlite3_sleep 10 } file_control_win32_av_retry db 10 25 sqlite3_test_control_pending_byte $old_pending_byte sqlite3_shutdown test_sqlite3_log sqlite3_initialize |
︙ | ︙ |