diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/os_win.c | 19 | ||||
-rw-r--r-- | src/printf.c | 1 | ||||
-rw-r--r-- | src/shell.c | 8 | ||||
-rw-r--r-- | src/sqlite.h.in | 7 | ||||
-rw-r--r-- | src/test1.c | 50 | ||||
-rw-r--r-- | src/where.c | 6 | ||||
-rw-r--r-- | src/whereInt.h | 1 |
7 files changed, 84 insertions, 8 deletions
diff --git a/src/os_win.c b/src/os_win.c index 36fb9f690..5c246a858 100644 --- a/src/os_win.c +++ b/src/os_win.c @@ -2927,8 +2927,16 @@ static int winLock(sqlite3_file *id, int locktype){ ** If you are using this code as a model for alternative VFSes, do not ** copy this retry logic. It is a hack intended for Windows only. */ + lastErrno = osGetLastError(); OSTRACE(("LOCK-PENDING-FAIL file=%p, count=%d, result=%d\n", pFile->h, cnt, res)); + if( lastErrno==ERROR_INVALID_HANDLE ){ + pFile->lastErrno = lastErrno; + rc = SQLITE_IOERR_LOCK; + OSTRACE(("LOCK-FAIL file=%p, count=%d, rc=%s\n", + pFile->h, cnt, sqlite3ErrName(rc))); + return rc; + } if( cnt ) sqlite3_win32_sleep(1); } gotPendingLock = res; @@ -3172,6 +3180,17 @@ static int winFileControl(sqlite3_file *id, int op, void *pArg){ OSTRACE(("FCNTL file=%p, rc=SQLITE_OK\n", pFile->h)); return SQLITE_OK; } +#ifdef SQLITE_TEST + case SQLITE_FCNTL_WIN32_SET_HANDLE: { + LPHANDLE phFile = (LPHANDLE)pArg; + HANDLE hOldFile = pFile->h; + pFile->h = *phFile; + *phFile = hOldFile; + OSTRACE(("FCNTL oldFile=%p, newFile=%p, rc=SQLITE_OK\n", + hOldFile, pFile->h)); + return SQLITE_OK; + } +#endif case SQLITE_FCNTL_TEMPFILENAME: { char *zTFile = 0; int rc = winGetTempname(pFile->pVfs, &zTFile); diff --git a/src/printf.c b/src/printf.c index 01209c042..37910804d 100644 --- a/src/printf.c +++ b/src/printf.c @@ -756,6 +756,7 @@ static int sqlite3StrAccumEnlarge(StrAccum *p, int N){ zNew = sqlite3_realloc(zOld, p->nAlloc); } if( zNew ){ + assert( p->zText!=0 || p->nChar==0 ); if( zOld==0 && p->nChar>0 ) memcpy(zNew, p->zText, p->nChar); p->zText = zNew; }else{ diff --git a/src/shell.c b/src/shell.c index 5daadbeaf..63517fdd1 100644 --- a/src/shell.c +++ b/src/shell.c @@ -2425,8 +2425,8 @@ static int do_meta_command(char *zLine, struct callback_data *p){ }else if( c=='i' && strncmp(azArg[0], "import", n)==0 ){ - char *zTable = azArg[2]; /* Insert data into this table */ - char *zFile = azArg[1]; /* Name of file to extra content from */ + char *zTable; /* Insert data into this table */ + char *zFile; /* Name of file to extra content from */ sqlite3_stmt *pStmt = NULL; /* A statement */ int nCol; /* Number of columns in the table */ int nByte; /* Number of bytes in an SQL string */ @@ -2441,6 +2441,8 @@ static int do_meta_command(char *zLine, struct callback_data *p){ fprintf(stderr, "Usage: .import FILE TABLE\n"); goto meta_command_exit; } + zFile = azArg[1]; + zTable = azArg[2]; seenInterrupt = 0; memset(&sCsv, 0, sizeof(sCsv)); open_db(p, 0); @@ -2998,7 +3000,7 @@ static int do_meta_command(char *zLine, struct callback_data *p){ zCmd = sqlite3_mprintf(strchr(azArg[i],' ')==0?"%z %s":"%z \"%s\"", zCmd, azArg[i]); } - system(zCmd); + (void)system(zCmd); sqlite3_free(zCmd); }else diff --git a/src/sqlite.h.in b/src/sqlite.h.in index dc45899cf..47b81d198 100644 --- a/src/sqlite.h.in +++ b/src/sqlite.h.in @@ -942,6 +942,12 @@ struct sqlite3_io_methods { ** on whether or not the file has been renamed, moved, or deleted since it ** was first opened. ** +** <li>[[SQLITE_FCNTL_WIN32_SET_HANDLE]] +** The [SQLITE_FCNTL_WIN32_SET_HANDLE] opcode is used for debugging. This +** opcode causes the xFileControl method to swap the file handle with the one +** pointed to by the pArg argument. This capability is used during testing +** and only needs to be supported when SQLITE_TEST is defined. +** ** </ul> */ #define SQLITE_FCNTL_LOCKSTATE 1 @@ -965,6 +971,7 @@ struct sqlite3_io_methods { #define SQLITE_FCNTL_HAS_MOVED 20 #define SQLITE_FCNTL_SYNC 21 #define SQLITE_FCNTL_COMMIT_PHASETWO 22 +#define SQLITE_FCNTL_WIN32_SET_HANDLE 23 /* ** CAPI3REF: Mutex Handle diff --git a/src/test1.c b/src/test1.c index ab51ddafa..3872207cb 100644 --- a/src/test1.c +++ b/src/test1.c @@ -117,6 +117,16 @@ int getDbPointer(Tcl_Interp *interp, const char *zA, sqlite3 **ppDb){ return TCL_OK; } +#if SQLITE_OS_WIN +/* +** Decode a Win32 HANDLE object. +*/ +int getWin32Handle(Tcl_Interp *interp, const char *zA, LPHANDLE phFile){ + *phFile = (HANDLE)sqlite3TestTextToPtr(zA); + return TCL_OK; +} +#endif + extern const char *sqlite3ErrName(int); #define t1ErrorName sqlite3ErrName @@ -5250,6 +5260,7 @@ static int file_control_lockproxy_test( return TCL_OK; } +#if SQLITE_OS_WIN /* ** tclcmd: file_control_win32_av_retry DB NRETRY DELAY ** @@ -5284,6 +5295,42 @@ static int file_control_win32_av_retry( } /* +** tclcmd: file_control_win32_set_handle DB HANDLE +** +** This TCL command runs the sqlite3_file_control interface with +** the SQLITE_FCNTL_WIN32_SET_HANDLE opcode. +*/ +static int file_control_win32_set_handle( + ClientData clientData, /* Pointer to sqlite3_enable_XXX function */ + Tcl_Interp *interp, /* The TCL interpreter that invoked this command */ + int objc, /* Number of arguments */ + Tcl_Obj *CONST objv[] /* Command arguments */ +){ + sqlite3 *db; + int rc; + HANDLE hFile = NULL; + char z[100]; + + if( objc!=3 ){ + Tcl_AppendResult(interp, "wrong # args: should be \"", + Tcl_GetStringFromObj(objv[0], 0), " DB HANDLE", 0); + return TCL_ERROR; + } + if( getDbPointer(interp, Tcl_GetString(objv[1]), &db) ){ + return TCL_ERROR; + } + if( getWin32Handle(interp, Tcl_GetString(objv[2]), &hFile) ){ + return TCL_ERROR; + } + rc = sqlite3_file_control(db, NULL, SQLITE_FCNTL_WIN32_SET_HANDLE, + (void*)&hFile); + sqlite3_snprintf(sizeof(z), z, "%d %p", rc, (void*)hFile); + Tcl_AppendResult(interp, z, (char*)0); + return TCL_OK; +} +#endif + +/* ** tclcmd: file_control_persist_wal DB PERSIST-FLAG ** ** This TCL command runs the sqlite3_file_control interface with @@ -6633,7 +6680,10 @@ int Sqlitetest1_Init(Tcl_Interp *interp){ { "file_control_lockproxy_test", file_control_lockproxy_test, 0 }, { "file_control_chunksize_test", file_control_chunksize_test, 0 }, { "file_control_sizehint_test", file_control_sizehint_test, 0 }, +#if SQLITE_OS_WIN { "file_control_win32_av_retry", file_control_win32_av_retry, 0 }, + { "file_control_win32_set_handle", file_control_win32_set_handle, 0 }, +#endif { "file_control_persist_wal", file_control_persist_wal, 0 }, { "file_control_powersafe_overwrite",file_control_powersafe_overwrite,0}, { "file_control_vfsname", file_control_vfsname, 0 }, diff --git a/src/where.c b/src/where.c index 25c1c0414..f914004b2 100644 --- a/src/where.c +++ b/src/where.c @@ -4286,7 +4286,6 @@ static int whereLoopAddBtreeIndex( testcase( eOp & WO_IN ); pNew->nOut += pTerm->truthProb; pNew->nOut -= nIn; - pNew->wsFlags |= WHERE_LIKELIHOOD; }else{ #ifdef SQLITE_ENABLE_STAT3_OR_STAT4 tRowcnt nOut = 0; @@ -4295,7 +4294,6 @@ static int whereLoopAddBtreeIndex( && pNew->u.btree.nEq<=pProbe->nSampleCol && OptimizationEnabled(db, SQLITE_Stat3) && ((eOp & WO_IN)==0 || !ExprHasProperty(pTerm->pExpr, EP_xIsSelect)) - && (pNew->wsFlags & WHERE_LIKELIHOOD)==0 ){ Expr *pExpr = pTerm->pExpr; if( (eOp & (WO_EQ|WO_ISNULL))!=0 ){ @@ -5297,7 +5295,7 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ /* TUNING: For simple queries, only the best path is tracked. ** For 2-way joins, the 5 best paths are followed. ** For joins of 3 or more tables, track the 10 best paths */ - mxChoice = (nLoop==1) ? 1 : (nLoop==2 ? 5 : 10); + mxChoice = (nLoop<=1) ? 1 : (nLoop==2 ? 5 : 10); assert( nLoop<=pWInfo->pTabList->nSrc ); WHERETRACE(0x002, ("---- begin solver\n")); @@ -5327,7 +5325,7 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ aFrom[0].isOrdered = 0; nOrderBy = 0; }else{ - aFrom[0].isOrdered = -1; + aFrom[0].isOrdered = nLoop>0 ? -1 : 1; nOrderBy = pWInfo->pOrderBy->nExpr; } diff --git a/src/whereInt.h b/src/whereInt.h index 010cd6e8a..72e7530db 100644 --- a/src/whereInt.h +++ b/src/whereInt.h @@ -458,4 +458,3 @@ struct WhereInfo { #define WHERE_AUTO_INDEX 0x00004000 /* Uses an ephemeral index */ #define WHERE_SKIPSCAN 0x00008000 /* Uses the skip-scan algorithm */ #define WHERE_UNQ_WANTED 0x00010000 /* WHERE_ONEROW would have been helpful*/ -#define WHERE_LIKELIHOOD 0x00020000 /* A likelihood() is affecting nOut */ |