From 57a140946f6f7508e64d91b5ae8671f3cab073a0 Mon Sep 17 00:00:00 2001 From: dan Date: Thu, 26 Mar 2015 11:55:03 +0000 Subject: [PATCH 01/53] Optimize cases where all the sorter is sorting a set of records that all begin with integer values, or that all begin with text values to be compared using BINARY. FossilOrigin-Name: ce5ad17c25cf2f8274ce304c51e4421faae0b32b --- manifest | 17 ++++++++++------- manifest.uuid | 2 +- src/vdbesort.c | 51 +++++++++++++++++++++++++++++++++++++++++++++++--- 3 files changed, 59 insertions(+), 11 deletions(-) diff --git a/manifest b/manifest index 6fdfb0ad40..65ccebc2d0 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Change\san\sunreachable\sbranch\sinto\san\sassert(). -D 2015-03-25T18:29:10.982 +C Optimize\scases\swhere\sall\sthe\ssorter\sis\ssorting\sa\sset\sof\srecords\sthat\sall\sbegin\swith\sinteger\svalues,\sor\sthat\sall\sbegin\swith\stext\svalues\sto\sbe\scompared\susing\sBINARY. +D 2015-03-26T11:55:03.488 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 88a3e6261286db378fdffa1124cad11b3c05f5bb F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -300,7 +300,7 @@ F src/vdbeapi.c 583d56b129dd27f12bed518270de9ebe521e6a75 F src/vdbeaux.c 413dc496248ac18eb0c19e35e86bb1ffd47b8907 F src/vdbeblob.c 4f2e8e075d238392df98c5e03a64342465b03f90 F src/vdbemem.c c0dc81285b7571b0a31c40f17846fe2397ec1cd9 -F src/vdbesort.c 919717d7599fa31d343ec28bffd0f9e91a4ff5f6 +F src/vdbesort.c a8d82ed4b09f3b1f5390c7546a9bcad72d483abf F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 F src/vtab.c 62d49237bd8f3be4863815a39387b0f9897fa5e1 F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb @@ -1247,7 +1247,10 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 37866b4d483296ab9b7fcb9f5486695d4c2b8ddd -R 6f3611ab9d4988693f727ae20dc9c9e5 -U drh -Z 3f028f44e21ab0b1619e9687cba7cf7a +P fb076b28c36975ff2e41440f22fe5de115c195da +R 1e1c6c1ab8dfb515d00c85e16ae436f0 +T *branch * sorter-opt +T *sym-sorter-opt * +T -sym-trunk * +U dan +Z 9752268c90db4ae1847219cb63314e99 diff --git a/manifest.uuid b/manifest.uuid index 849f782137..dfa9f94353 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -fb076b28c36975ff2e41440f22fe5de115c195da \ No newline at end of file +ce5ad17c25cf2f8274ce304c51e4421faae0b32b \ No newline at end of file diff --git a/src/vdbesort.c b/src/vdbesort.c index bbdafa8230..4faeebf963 100644 --- a/src/vdbesort.c +++ b/src/vdbesort.c @@ -298,6 +298,7 @@ struct SortSubtask { UnpackedRecord *pUnpacked; /* Space to unpack a record */ SorterList list; /* List for thread to write to a PMA */ int nPMA; /* Number of PMAs currently in file */ + RecordCompare xCompare; /* Compare function to use */ SorterFile file; /* Temp file for level-0 PMAs */ SorterFile file2; /* Space for other PMAs */ }; @@ -328,9 +329,13 @@ struct VdbeSorter { u8 bUseThreads; /* True to use background threads */ u8 iPrev; /* Previous thread used to flush PMA */ u8 nTask; /* Size of aTask[] array */ + u8 typeMask; SortSubtask aTask[1]; /* One or more subtasks */ }; +#define SORTER_TYPE_INTEGER 0x01 +#define SORTER_TYPE_TEXT 0x02 + /* ** An instance of the following object is used to read records out of a ** PMA, in sorted order. The next key to be read is cached in nKey/aKey. @@ -765,7 +770,7 @@ static int vdbeSorterCompare( if( pKey2 ){ sqlite3VdbeRecordUnpack(pTask->pSorter->pKeyInfo, nKey2, pKey2, r2); } - return sqlite3VdbeRecordCompare(nKey1, pKey1, r2); + return pTask->xCompare(nKey1, pKey1, r2); } /* @@ -835,9 +840,13 @@ int sqlite3VdbeSorterInit( pSorter->pKeyInfo = pKeyInfo = (KeyInfo*)((u8*)pSorter + sz); memcpy(pKeyInfo, pCsr->pKeyInfo, szKeyInfo); pKeyInfo->db = 0; - if( nField && nWorker==0 ) pKeyInfo->nField = nField; + if( nField && nWorker==0 ){ + pKeyInfo->nXField += (pKeyInfo->nField - nField); + pKeyInfo->nField = nField; + } pSorter->pgsz = pgsz = sqlite3BtreeGetPageSize(db->aDb[0].pBt); pSorter->nTask = nWorker + 1; + pSorter->iPrev = nWorker-1; pSorter->bUseThreads = (pSorter->nTask>1); pSorter->db = db; for(i=0; inTask; i++){ @@ -863,6 +872,10 @@ int sqlite3VdbeSorterInit( if( !pSorter->list.aMemory ) rc = SQLITE_NOMEM; } } + + if( (pKeyInfo->nField+pKeyInfo->nXField)<13 && pKeyInfo->aColl[0]==0 ){ + pSorter->typeMask = SORTER_TYPE_INTEGER | SORTER_TYPE_TEXT; + } } return rc; @@ -1182,6 +1195,13 @@ static int vdbeSortAllocUnpacked(SortSubtask *pTask){ if( pFree==0 ) return SQLITE_NOMEM; pTask->pUnpacked->nField = pTask->pSorter->pKeyInfo->nField; pTask->pUnpacked->errCode = 0; + if( pTask->pSorter->pKeyInfo->aSortOrder[0] ){ + pTask->pUnpacked->r1 = 1; + pTask->pUnpacked->r2 = -1; + }else{ + pTask->pUnpacked->r1 = -1; + pTask->pUnpacked->r2 = 1; + } } return SQLITE_OK; } @@ -1235,12 +1255,20 @@ static int vdbeSorterSort(SortSubtask *pTask, SorterList *pList){ rc = vdbeSortAllocUnpacked(pTask); if( rc!=SQLITE_OK ) return rc; + p = pList->pList; + if( pTask->pSorter->typeMask==0 ){ + pTask->xCompare = sqlite3VdbeRecordCompare; + }else{ + UnpackedRecord *pRec = pTask->pUnpacked; + sqlite3VdbeRecordUnpack(pTask->pSorter->pKeyInfo, p->nVal, SRVAL(p), pRec); + pTask->xCompare = sqlite3VdbeFindCompare(pRec); + } + aSlot = (SorterRecord **)sqlite3MallocZero(64 * sizeof(SorterRecord *)); if( !aSlot ){ return SQLITE_NOMEM; } - p = pList->pList; while( p ){ SorterRecord *pNext; if( pList->aMemory ){ @@ -1602,6 +1630,16 @@ int sqlite3VdbeSorterWrite( int bFlush; /* True to flush contents of memory to PMA */ int nReq; /* Bytes of memory required */ int nPMA; /* Bytes of PMA space required */ + int t; /* serial type of first record field */ + + getVarint32((const u8*)&pVal->z[1], t); + if( t>0 && t<10 && t!=7 ){ + pSorter->typeMask &= SORTER_TYPE_INTEGER; + }else if( t & 0x01 ){ + pSorter->typeMask &= SORTER_TYPE_TEXT; + }else{ + pSorter->typeMask = 0; + } assert( pSorter ); @@ -2288,6 +2326,13 @@ static int vdbeSorterSetupMerge(VdbeSorter *pSorter){ MergeEngine *pMain = 0; #if SQLITE_MAX_WORKER_THREADS sqlite3 *db = pTask0->pSorter->db; + RecordCompare xCompare = (pSorter->typeMask==0 ? + sqlite3VdbeRecordCompare : pSorter->aTask[0].xCompare + ); + int i; + for(i=0; inTask; i++){ + pSorter->aTask[i].xCompare = xCompare; + } #endif rc = vdbeSorterMergeTreeBuild(pSorter, &pMain); From a9d9111c4aa590e197878515c7a9de526ef6feb9 Mon Sep 17 00:00:00 2001 From: dan Date: Sat, 28 Mar 2015 19:56:41 +0000 Subject: [PATCH 02/53] Further optimizations for sorting records that begin with integer or text values. FossilOrigin-Name: 24fe9f25d64ee516633fed1ae7ebc21554aa69ca --- manifest | 15 ++-- manifest.uuid | 2 +- src/vdbesort.c | 187 ++++++++++++++++++++++++++++++++++++++++--------- 3 files changed, 159 insertions(+), 45 deletions(-) diff --git a/manifest b/manifest index 65ccebc2d0..aba8fb17d1 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Optimize\scases\swhere\sall\sthe\ssorter\sis\ssorting\sa\sset\sof\srecords\sthat\sall\sbegin\swith\sinteger\svalues,\sor\sthat\sall\sbegin\swith\stext\svalues\sto\sbe\scompared\susing\sBINARY. -D 2015-03-26T11:55:03.488 +C Further\soptimizations\sfor\ssorting\srecords\sthat\sbegin\swith\sinteger\sor\stext\svalues. +D 2015-03-28T19:56:41.373 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 88a3e6261286db378fdffa1124cad11b3c05f5bb F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -300,7 +300,7 @@ F src/vdbeapi.c 583d56b129dd27f12bed518270de9ebe521e6a75 F src/vdbeaux.c 413dc496248ac18eb0c19e35e86bb1ffd47b8907 F src/vdbeblob.c 4f2e8e075d238392df98c5e03a64342465b03f90 F src/vdbemem.c c0dc81285b7571b0a31c40f17846fe2397ec1cd9 -F src/vdbesort.c a8d82ed4b09f3b1f5390c7546a9bcad72d483abf +F src/vdbesort.c b3d16bbd66ff8d26b42670a8aa5dfda0e0d2e45e F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 F src/vtab.c 62d49237bd8f3be4863815a39387b0f9897fa5e1 F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb @@ -1247,10 +1247,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P fb076b28c36975ff2e41440f22fe5de115c195da -R 1e1c6c1ab8dfb515d00c85e16ae436f0 -T *branch * sorter-opt -T *sym-sorter-opt * -T -sym-trunk * +P ce5ad17c25cf2f8274ce304c51e4421faae0b32b +R 5a4cff4b803c75214d0e7f89bc9331f1 U dan -Z 9752268c90db4ae1847219cb63314e99 +Z 8e7d5cc07144236ce8ed9e6cb6b634d0 diff --git a/manifest.uuid b/manifest.uuid index dfa9f94353..1d45093594 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -ce5ad17c25cf2f8274ce304c51e4421faae0b32b \ No newline at end of file +24fe9f25d64ee516633fed1ae7ebc21554aa69ca \ No newline at end of file diff --git a/src/vdbesort.c b/src/vdbesort.c index 4faeebf963..b8ef783a06 100644 --- a/src/vdbesort.c +++ b/src/vdbesort.c @@ -291,6 +291,7 @@ struct MergeEngine { ** after the thread has finished are not dire. So we don't worry about ** memory barriers and such here. */ +typedef int (*SorterCompare)(SortSubtask*,int*,const void*,int,const void*,int); struct SortSubtask { SQLiteThread *pThread; /* Background thread, if any */ int bDone; /* Set if thread is finished but not joined */ @@ -298,11 +299,12 @@ struct SortSubtask { UnpackedRecord *pUnpacked; /* Space to unpack a record */ SorterList list; /* List for thread to write to a PMA */ int nPMA; /* Number of PMAs currently in file */ - RecordCompare xCompare; /* Compare function to use */ + SorterCompare xCompare; /* Compare function to use */ SorterFile file; /* Temp file for level-0 PMAs */ SorterFile file2; /* Space for other PMAs */ }; + /* ** Main sorter structure. A single instance of this is allocated for each ** sorter cursor created by the VDBE. @@ -747,30 +749,136 @@ static int vdbePmaReaderInit( return rc; } - /* ** Compare key1 (buffer pKey1, size nKey1 bytes) with key2 (buffer pKey2, ** size nKey2 bytes). Use (pTask->pKeyInfo) for the collation sequences ** used by the comparison. Return the result of the comparison. ** -** Before returning, object (pTask->pUnpacked) is populated with the -** unpacked version of key2. Or, if pKey2 is passed a NULL pointer, then it -** is assumed that the (pTask->pUnpacked) structure already contains the -** unpacked key to use as key2. +** If IN/OUT parameter *pbKey2Cached is true when this function is called, +** it is assumed that (pTask->pUnpacked) contains the unpacked version +** of key2. If it is false, (pTask->pUnpacked) is populated with the unpacked +** version of key2 and *pbKey2Cached set to true before returning. ** ** If an OOM error is encountered, (pTask->pUnpacked->error_rc) is set ** to SQLITE_NOMEM. */ static int vdbeSorterCompare( SortSubtask *pTask, /* Subtask context (for pKeyInfo) */ + int *pbKey2Cached, /* True if pTask->pUnpacked is pKey2 */ const void *pKey1, int nKey1, /* Left side of comparison */ const void *pKey2, int nKey2 /* Right side of comparison */ ){ UnpackedRecord *r2 = pTask->pUnpacked; - if( pKey2 ){ + if( !*pbKey2Cached ){ sqlite3VdbeRecordUnpack(pTask->pSorter->pKeyInfo, nKey2, pKey2, r2); + *pbKey2Cached = 1; } - return pTask->xCompare(nKey1, pKey1, r2); + return sqlite3VdbeRecordCompare(nKey1, pKey1, r2); +} + +/* +** A specially optimized version of vdbeSorterCompare() that assumes that +** the first field of each key is a TEXT value and that the collation +** sequence to compare them with is BINARY. +*/ +static int vdbeSorterCompareText( + SortSubtask *pTask, /* Subtask context (for pKeyInfo) */ + int *pbKey2Cached, /* True if pTask->pUnpacked is pKey2 */ + const void *pKey1, int nKey1, /* Left side of comparison */ + const void *pKey2, int nKey2 /* Right side of comparison */ +){ + const u8 * const p1 = (const u8 * const)pKey1; + const u8 * const p2 = (const u8 * const)pKey2; + const u8 * const v1 = &p1[ p1[0] ]; /* Pointer to value 1 */ + const u8 * const v2 = &p2[ p2[0] ]; /* Pointer to value 2 */ + + int n1; + int n2; + int res; + + getVarint32(&p1[1], n1); n1 = (n1 - 13) / 2; + getVarint32(&p2[1], n2); n2 = (n2 - 13) / 2; + res = memcmp(v1, v2, MIN(n1, n2)); + if( res==0 ){ + res = n1 - n2; + } + + if( res==0 ){ + if( pTask->pSorter->pKeyInfo->nField>1 ){ + res = vdbeSorterCompare(pTask, pbKey2Cached, pKey1, nKey1, pKey2, nKey2); + } + }else{ + if( pTask->pSorter->pKeyInfo->aSortOrder[0] ){ + res = res * -1; + } + } + + return res; +} + +/* +** A specially optimized version of vdbeSorterCompare() that assumes that +** the first field of each key is an INTEGER value. +*/ +static int vdbeSorterCompareInt( + SortSubtask *pTask, /* Subtask context (for pKeyInfo) */ + int *pbKey2Cached, /* True if pTask->pUnpacked is pKey2 */ + const void *pKey1, int nKey1, /* Left side of comparison */ + const void *pKey2, int nKey2 /* Right side of comparison */ +){ + const u8 * const p1 = (const u8 * const)pKey1; + const u8 * const p2 = (const u8 * const)pKey2; + const int s1 = p1[1]; /* Left hand serial type */ + const int s2 = p2[1]; /* Right hand serial type */ + const u8 * const v1 = &p1[ p1[0] ]; /* Pointer to value 1 */ + const u8 * const v2 = &p2[ p2[0] ]; /* Pointer to value 2 */ + int res; /* Return value */ + + assert( (s1>0 && s1<7) || s1==8 || s1==9 ); + assert( (s2>0 && s2<7) || s2==8 || s2==9 ); + + if( s1>7 && s2>7 ){ + res = s1 - s2; + }else{ + if( s1==s2 ){ + if( (*v1 ^ *v2) & 0x80 ){ + /* The two values have different signs */ + res = (*v1 & 0x80) ? -1 : +1; + }else{ + /* The two values have the same sign. Compare using memcmp(). */ + static const u8 aLen[] = {0, 1, 2, 3, 4, 6, 8 }; + int i; + res = 0; + for(i=0; i7 ){ + res = +1; + }else if( s1>7 ){ + res = -1; + }else{ + res = s1 - s2; + } + + if( res>0 ){ + if( *v1 & 0x80 ) res = -1; + }else if( res<0 ){ + if( *v2 & 0x80 ) res = +1; + } + } + } + + if( res==0 ){ + if( pTask->pSorter->pKeyInfo->nField>1 ){ + res = vdbeSorterCompare(pTask, pbKey2Cached, pKey1, nKey1, pKey2, nKey2); + } + }else if( pTask->pSorter->pKeyInfo->aSortOrder[0] ){ + res = res * -1; + } + + return res; } /* @@ -873,7 +981,9 @@ int sqlite3VdbeSorterInit( } } - if( (pKeyInfo->nField+pKeyInfo->nXField)<13 && pKeyInfo->aColl[0]==0 ){ + if( (pKeyInfo->nField+pKeyInfo->nXField)<13 + && (pKeyInfo->aColl[0]==0 || pKeyInfo->aColl[0]==db->pDfltColl) + ){ pSorter->typeMask = SORTER_TYPE_INTEGER | SORTER_TYPE_TEXT; } } @@ -1219,28 +1329,42 @@ static void vdbeSorterMerge( ){ SorterRecord *pFinal = 0; SorterRecord **pp = &pFinal; - void *pVal2 = p2 ? SRVAL(p2) : 0; + int bCached = 0; while( p1 && p2 ){ int res; - res = vdbeSorterCompare(pTask, SRVAL(p1), p1->nVal, pVal2, p2->nVal); + res = pTask->xCompare( + pTask, &bCached, SRVAL(p1), p1->nVal, SRVAL(p2), p2->nVal + ); + if( res<=0 ){ *pp = p1; pp = &p1->u.pNext; p1 = p1->u.pNext; - pVal2 = 0; }else{ *pp = p2; - pp = &p2->u.pNext; + pp = &p2->u.pNext; p2 = p2->u.pNext; - if( p2==0 ) break; - pVal2 = SRVAL(p2); + bCached = 0; } } *pp = p1 ? p1 : p2; *ppOut = pFinal; } +/* +** Return the SorterCompare function to compare values collected by the +** sorter object passed as the only argument. +*/ +static SorterCompare vdbeSorterGetCompare(VdbeSorter *p){ + if( p->typeMask==SORTER_TYPE_INTEGER ){ + return vdbeSorterCompareInt; + }else if( p->typeMask==SORTER_TYPE_TEXT ){ + return vdbeSorterCompareText; + } + return vdbeSorterCompare; +} + /* ** Sort the linked list of records headed at pTask->pList. Return ** SQLITE_OK if successful, or an SQLite error code (i.e. SQLITE_NOMEM) if @@ -1256,13 +1380,7 @@ static int vdbeSorterSort(SortSubtask *pTask, SorterList *pList){ if( rc!=SQLITE_OK ) return rc; p = pList->pList; - if( pTask->pSorter->typeMask==0 ){ - pTask->xCompare = sqlite3VdbeRecordCompare; - }else{ - UnpackedRecord *pRec = pTask->pUnpacked; - sqlite3VdbeRecordUnpack(pTask->pSorter->pKeyInfo, p->nVal, SRVAL(p), pRec); - pTask->xCompare = sqlite3VdbeFindCompare(pRec); - } + pTask->xCompare = vdbeSorterGetCompare(pTask->pSorter); aSlot = (SorterRecord **)sqlite3MallocZero(64 * sizeof(SorterRecord *)); if( !aSlot ){ @@ -1482,13 +1600,12 @@ static int vdbeMergeEngineStep( int i; /* Index of aTree[] to recalculate */ PmaReader *pReadr1; /* First PmaReader to compare */ PmaReader *pReadr2; /* Second PmaReader to compare */ - u8 *pKey2; /* To pReadr2->aKey, or 0 if record cached */ + int bCached = 0; /* Find the first two PmaReaders to compare. The one that was just ** advanced (iPrev) and the one next to it in the array. */ pReadr1 = &pMerger->aReadr[(iPrev & 0xFFFE)]; pReadr2 = &pMerger->aReadr[(iPrev | 0x0001)]; - pKey2 = pReadr2->aKey; for(i=(pMerger->nTree+iPrev)/2; i>0; i=i/2){ /* Compare pReadr1 and pReadr2. Store the result in variable iRes. */ @@ -1498,8 +1615,8 @@ static int vdbeMergeEngineStep( }else if( pReadr2->pFd==0 ){ iRes = -1; }else{ - iRes = vdbeSorterCompare(pTask, - pReadr1->aKey, pReadr1->nKey, pKey2, pReadr2->nKey + iRes = pTask->xCompare(pTask, &bCached, + pReadr1->aKey, pReadr1->nKey, pReadr2->aKey, pReadr2->nKey ); } @@ -1521,9 +1638,9 @@ static int vdbeMergeEngineStep( if( iRes<0 || (iRes==0 && pReadr1aTree[i] = (int)(pReadr1 - pMerger->aReadr); pReadr2 = &pMerger->aReadr[ pMerger->aTree[i ^ 0x0001] ]; - pKey2 = pReadr2->aKey; + bCached = 0; }else{ - if( pReadr1->pFd ) pKey2 = 0; + bCached = (pReadr1->pFd!=0); pMerger->aTree[i] = (int)(pReadr2 - pMerger->aReadr); pReadr1 = &pMerger->aReadr[ pMerger->aTree[i ^ 0x0001] ]; } @@ -1635,7 +1752,7 @@ int sqlite3VdbeSorterWrite( getVarint32((const u8*)&pVal->z[1], t); if( t>0 && t<10 && t!=7 ){ pSorter->typeMask &= SORTER_TYPE_INTEGER; - }else if( t & 0x01 ){ + }else if( t>10 && (t & 0x01) ){ pSorter->typeMask &= SORTER_TYPE_TEXT; }else{ pSorter->typeMask = 0; @@ -1905,10 +2022,12 @@ static void vdbeMergeEngineCompare( }else if( p2->pFd==0 ){ iRes = i1; }else{ + SortSubtask *pTask = pMerger->pTask; + int bCached = 0; int res; - assert( pMerger->pTask->pUnpacked!=0 ); /* from vdbeSortSubtaskMain() */ - res = vdbeSorterCompare( - pMerger->pTask, p1->aKey, p1->nKey, p2->aKey, p2->nKey + assert( pTask->pUnpacked!=0 ); /* from vdbeSortSubtaskMain() */ + res = pTask->xCompare( + pTask, &bCached, p1->aKey, p1->nKey, p2->aKey, p2->nKey ); if( res<=0 ){ iRes = i1; @@ -2326,10 +2445,8 @@ static int vdbeSorterSetupMerge(VdbeSorter *pSorter){ MergeEngine *pMain = 0; #if SQLITE_MAX_WORKER_THREADS sqlite3 *db = pTask0->pSorter->db; - RecordCompare xCompare = (pSorter->typeMask==0 ? - sqlite3VdbeRecordCompare : pSorter->aTask[0].xCompare - ); int i; + SorterCompare xCompare = vdbeSorterGetCompare(pSorter); for(i=0; inTask; i++){ pSorter->aTask[i].xCompare = xCompare; } From d2e1191929c9cdceebfcf46bcaf18d03ea4d47be Mon Sep 17 00:00:00 2001 From: dan Date: Mon, 30 Mar 2015 09:58:38 +0000 Subject: [PATCH 03/53] Remove some unnecessary code from vdbesort.c. FossilOrigin-Name: b58191e91736b1d978db4127f22867dfe2302f7c --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/vdbesort.c | 7 ------- 3 files changed, 7 insertions(+), 14 deletions(-) diff --git a/manifest b/manifest index aba8fb17d1..a3ffa9b4e0 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Further\soptimizations\sfor\ssorting\srecords\sthat\sbegin\swith\sinteger\sor\stext\svalues. -D 2015-03-28T19:56:41.373 +C Remove\ssome\sunnecessary\scode\sfrom\svdbesort.c. +D 2015-03-30T09:58:38.613 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 88a3e6261286db378fdffa1124cad11b3c05f5bb F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -300,7 +300,7 @@ F src/vdbeapi.c 583d56b129dd27f12bed518270de9ebe521e6a75 F src/vdbeaux.c 413dc496248ac18eb0c19e35e86bb1ffd47b8907 F src/vdbeblob.c 4f2e8e075d238392df98c5e03a64342465b03f90 F src/vdbemem.c c0dc81285b7571b0a31c40f17846fe2397ec1cd9 -F src/vdbesort.c b3d16bbd66ff8d26b42670a8aa5dfda0e0d2e45e +F src/vdbesort.c f283b28d9d1bbaf9c4467c1275ab2146ed868ec9 F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 F src/vtab.c 62d49237bd8f3be4863815a39387b0f9897fa5e1 F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb @@ -1247,7 +1247,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P ce5ad17c25cf2f8274ce304c51e4421faae0b32b -R 5a4cff4b803c75214d0e7f89bc9331f1 +P 24fe9f25d64ee516633fed1ae7ebc21554aa69ca +R 7cd5cef35d63d5a82a586382f49d8e50 U dan -Z 8e7d5cc07144236ce8ed9e6cb6b634d0 +Z 51fc974a93f39baea754c6fb429251e1 diff --git a/manifest.uuid b/manifest.uuid index 1d45093594..698dbf4147 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -24fe9f25d64ee516633fed1ae7ebc21554aa69ca \ No newline at end of file +b58191e91736b1d978db4127f22867dfe2302f7c \ No newline at end of file diff --git a/src/vdbesort.c b/src/vdbesort.c index b8ef783a06..b6483b9ee7 100644 --- a/src/vdbesort.c +++ b/src/vdbesort.c @@ -1305,13 +1305,6 @@ static int vdbeSortAllocUnpacked(SortSubtask *pTask){ if( pFree==0 ) return SQLITE_NOMEM; pTask->pUnpacked->nField = pTask->pSorter->pKeyInfo->nField; pTask->pUnpacked->errCode = 0; - if( pTask->pSorter->pKeyInfo->aSortOrder[0] ){ - pTask->pUnpacked->r1 = 1; - pTask->pUnpacked->r2 = -1; - }else{ - pTask->pUnpacked->r1 = -1; - pTask->pUnpacked->r2 = 1; - } } return SQLITE_OK; } From 7004f3f6a311398f00d856b359d7389b72f802de Mon Sep 17 00:00:00 2001 From: dan Date: Mon, 30 Mar 2015 12:06:26 +0000 Subject: [PATCH 04/53] Improve performance of multi-field sorts where the first field has a low cardinality. FossilOrigin-Name: 601e7b6b8e6bfabda03b70f75094c9014e3a3c49 --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/vdbe.h | 1 + src/vdbeaux.c | 8 ++++---- src/vdbesort.c | 27 +++++++++++++++++++++++++-- 5 files changed, 39 insertions(+), 15 deletions(-) diff --git a/manifest b/manifest index a3ffa9b4e0..a7a78bf354 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\ssome\sunnecessary\scode\sfrom\svdbesort.c. -D 2015-03-30T09:58:38.613 +C Improve\sperformance\sof\smulti-field\ssorts\swhere\sthe\sfirst\sfield\shas\sa\slow\scardinality. +D 2015-03-30T12:06:26.995 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 88a3e6261286db378fdffa1124cad11b3c05f5bb F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -294,13 +294,13 @@ F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 98a7627ca48ad3265b6940915a1d08355eb3fc7e F src/vacuum.c 9460b9de7b2d4e34b0d374894aa6c8a0632be8ec F src/vdbe.c bbfede5a8a6908b3ddcd55fdb0b2301288dd4754 -F src/vdbe.h 6fc69d9c5e146302c56e163cb4b31d1ee64a18c3 +F src/vdbe.h 7e538ecf47dccb307ea2d087c3ddc2dd8d70e79d F src/vdbeInt.h 9cbaa84f53ddd2d09a0cf61a94337a3a035d08a0 F src/vdbeapi.c 583d56b129dd27f12bed518270de9ebe521e6a75 -F src/vdbeaux.c 413dc496248ac18eb0c19e35e86bb1ffd47b8907 +F src/vdbeaux.c a20504ae52392459fa08402fda3f195f19d7c79d F src/vdbeblob.c 4f2e8e075d238392df98c5e03a64342465b03f90 F src/vdbemem.c c0dc81285b7571b0a31c40f17846fe2397ec1cd9 -F src/vdbesort.c f283b28d9d1bbaf9c4467c1275ab2146ed868ec9 +F src/vdbesort.c 7b3684665ea51d642b0e664fa4d0b0d08d61d80c F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 F src/vtab.c 62d49237bd8f3be4863815a39387b0f9897fa5e1 F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb @@ -1247,7 +1247,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 24fe9f25d64ee516633fed1ae7ebc21554aa69ca -R 7cd5cef35d63d5a82a586382f49d8e50 +P b58191e91736b1d978db4127f22867dfe2302f7c +R ce44a3d54ad53a02b61fed80311cecef U dan -Z 51fc974a93f39baea754c6fb429251e1 +Z 8753c6822202b0898d8492105ecdb751 diff --git a/manifest.uuid b/manifest.uuid index 698dbf4147..2a8f64fa3a 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -b58191e91736b1d978db4127f22867dfe2302f7c \ No newline at end of file +601e7b6b8e6bfabda03b70f75094c9014e3a3c49 \ No newline at end of file diff --git a/src/vdbe.h b/src/vdbe.h index b715241b41..bb597b68d7 100644 --- a/src/vdbe.h +++ b/src/vdbe.h @@ -213,6 +213,7 @@ int sqlite3MemCompare(const Mem*, const Mem*, const CollSeq*); void sqlite3VdbeRecordUnpack(KeyInfo*,int,const void*,UnpackedRecord*); int sqlite3VdbeRecordCompare(int,const void*,UnpackedRecord*); +int sqlite3VdbeRecordCompareWithSkip(int, const void *, UnpackedRecord *, int); UnpackedRecord *sqlite3VdbeAllocUnpackedRecord(KeyInfo *, char *, int, char **); typedef int (*RecordCompare)(int,const void*,UnpackedRecord*); diff --git a/src/vdbeaux.c b/src/vdbeaux.c index 9c5d9acca9..1c10bab0b8 100644 --- a/src/vdbeaux.c +++ b/src/vdbeaux.c @@ -3585,7 +3585,7 @@ static i64 vdbeRecordDecodeInt(u32 serial_type, const u8 *aKey){ ** pPKey2->errCode is set to SQLITE_NOMEM and, if it is not NULL, the ** malloc-failed flag set on database handle (pPKey2->pKeyInfo->db). */ -static int vdbeRecordCompareWithSkip( +int sqlite3VdbeRecordCompareWithSkip( int nKey1, const void *pKey1, /* Left key */ UnpackedRecord *pPKey2, /* Right key */ int bSkip /* If true, skip the first field */ @@ -3771,7 +3771,7 @@ int sqlite3VdbeRecordCompare( int nKey1, const void *pKey1, /* Left key */ UnpackedRecord *pPKey2 /* Right key */ ){ - return vdbeRecordCompareWithSkip(nKey1, pKey1, pPKey2, 0); + return sqlite3VdbeRecordCompareWithSkip(nKey1, pKey1, pPKey2, 0); } @@ -3859,7 +3859,7 @@ static int vdbeRecordCompareInt( }else if( pPKey2->nField>1 ){ /* The first fields of the two keys are equal. Compare the trailing ** fields. */ - res = vdbeRecordCompareWithSkip(nKey1, pKey1, pPKey2, 1); + res = sqlite3VdbeRecordCompareWithSkip(nKey1, pKey1, pPKey2, 1); }else{ /* The first fields of the two keys are equal and there are no trailing ** fields. Return pPKey2->default_rc in this case. */ @@ -3907,7 +3907,7 @@ static int vdbeRecordCompareString( res = nStr - pPKey2->aMem[0].n; if( res==0 ){ if( pPKey2->nField>1 ){ - res = vdbeRecordCompareWithSkip(nKey1, pKey1, pPKey2, 1); + res = sqlite3VdbeRecordCompareWithSkip(nKey1, pKey1, pPKey2, 1); }else{ res = pPKey2->default_rc; } diff --git a/src/vdbesort.c b/src/vdbesort.c index b6483b9ee7..547dce2e65 100644 --- a/src/vdbesort.c +++ b/src/vdbesort.c @@ -749,6 +749,25 @@ static int vdbePmaReaderInit( return rc; } +/* +** A version of vdbeSorterCompare() that assumes that it has already been +** determined that the first field of key1 is equal to the first field of +** key2. +*/ +static int vdbeSorterCompareTail( + SortSubtask *pTask, /* Subtask context (for pKeyInfo) */ + int *pbKey2Cached, /* True if pTask->pUnpacked is pKey2 */ + const void *pKey1, int nKey1, /* Left side of comparison */ + const void *pKey2, int nKey2 /* Right side of comparison */ +){ + UnpackedRecord *r2 = pTask->pUnpacked; + if( *pbKey2Cached==0 ){ + sqlite3VdbeRecordUnpack(pTask->pSorter->pKeyInfo, nKey2, pKey2, r2); + *pbKey2Cached = 1; + } + return sqlite3VdbeRecordCompareWithSkip(nKey1, pKey1, r2, 1); +} + /* ** Compare key1 (buffer pKey1, size nKey1 bytes) with key2 (buffer pKey2, ** size nKey2 bytes). Use (pTask->pKeyInfo) for the collation sequences @@ -805,7 +824,9 @@ static int vdbeSorterCompareText( if( res==0 ){ if( pTask->pSorter->pKeyInfo->nField>1 ){ - res = vdbeSorterCompare(pTask, pbKey2Cached, pKey1, nKey1, pKey2, nKey2); + res = vdbeSorterCompareTail( + pTask, pbKey2Cached, pKey1, nKey1, pKey2, nKey2 + ); } }else{ if( pTask->pSorter->pKeyInfo->aSortOrder[0] ){ @@ -872,7 +893,9 @@ static int vdbeSorterCompareInt( if( res==0 ){ if( pTask->pSorter->pKeyInfo->nField>1 ){ - res = vdbeSorterCompare(pTask, pbKey2Cached, pKey1, nKey1, pKey2, nKey2); + res = vdbeSorterCompareTail( + pTask, pbKey2Cached, pKey1, nKey1, pKey2, nKey2 + ); } }else if( pTask->pSorter->pKeyInfo->aSortOrder[0] ){ res = res * -1; From b18e60b3e43270773c163d7b6424b904fb9ffb9a Mon Sep 17 00:00:00 2001 From: dan Date: Wed, 1 Apr 2015 16:18:00 +0000 Subject: [PATCH 05/53] Reduce the CPU used by CREATE INDEX statements by taking better advantage of the fact that keys are inserted in sorted order. FossilOrigin-Name: 592cdc5d7254be7032aa9c0b03405a74ca060b51 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/build.c | 3 ++- src/vdbe.c | 3 ++- 4 files changed, 12 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index a7a78bf354..be112fc01e 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Improve\sperformance\sof\smulti-field\ssorts\swhere\sthe\sfirst\sfield\shas\sa\slow\scardinality. -D 2015-03-30T12:06:26.995 +C Reduce\sthe\sCPU\sused\sby\sCREATE\sINDEX\sstatements\sby\staking\sbetter\sadvantage\sof\sthe\sfact\sthat\skeys\sare\sinserted\sin\ssorted\sorder. +D 2015-04-01T16:18:00.779 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 88a3e6261286db378fdffa1124cad11b3c05f5bb F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -176,7 +176,7 @@ F src/btmutex.c 45a968cc85afed9b5e6cf55bf1f42f8d18107f79 F src/btree.c 4f305e554d7d207375c3e29ab0335bd5a473a125 F src/btree.h 969adc948e89e449220ff0ff724c94bb2a52e9f1 F src/btreeInt.h 2bfefc01875d8da066504c233ec259fcb3b2ef72 -F src/build.c 0419bba592c22f6d00e6d57a2ca7136720d02c1a +F src/build.c 9103f5cd8f4071dc0c44a3312956e53f5b7f52c8 F src/callback.c 7b44ce59674338ad48b0e84e7b72f935ea4f68b0 F src/complete.c 198a0066ba60ab06fc00fba1998d870a4d575463 F src/ctime.c 98f89724adc891a1a4c655bee04e33e716e05887 @@ -293,7 +293,7 @@ F src/update.c 3c4ecc282accf12d39edb8d524cf089645e55a13 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 98a7627ca48ad3265b6940915a1d08355eb3fc7e F src/vacuum.c 9460b9de7b2d4e34b0d374894aa6c8a0632be8ec -F src/vdbe.c bbfede5a8a6908b3ddcd55fdb0b2301288dd4754 +F src/vdbe.c a9d916abb1e22355a81b0e72040917ba33c87ed7 F src/vdbe.h 7e538ecf47dccb307ea2d087c3ddc2dd8d70e79d F src/vdbeInt.h 9cbaa84f53ddd2d09a0cf61a94337a3a035d08a0 F src/vdbeapi.c 583d56b129dd27f12bed518270de9ebe521e6a75 @@ -1247,7 +1247,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P b58191e91736b1d978db4127f22867dfe2302f7c -R ce44a3d54ad53a02b61fed80311cecef +P 601e7b6b8e6bfabda03b70f75094c9014e3a3c49 +R 151febe3c42a1563a662898adadb6b2d U dan -Z 8753c6822202b0898d8492105ecdb751 +Z 37e9d6c37bda7e19a2c8ebf1573e150d diff --git a/manifest.uuid b/manifest.uuid index 2a8f64fa3a..6bc7a444cf 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -601e7b6b8e6bfabda03b70f75094c9014e3a3c49 \ No newline at end of file +592cdc5d7254be7032aa9c0b03405a74ca060b51 \ No newline at end of file diff --git a/src/build.c b/src/build.c index fcf96bd42c..11c790d311 100644 --- a/src/build.c +++ b/src/build.c @@ -2763,7 +2763,8 @@ static void sqlite3RefillIndex(Parse *pParse, Index *pIndex, int memRootPage){ addr2 = sqlite3VdbeCurrentAddr(v); } sqlite3VdbeAddOp3(v, OP_SorterData, iSorter, regRecord, iIdx); - sqlite3VdbeAddOp3(v, OP_IdxInsert, iIdx, regRecord, 1); + sqlite3VdbeAddOp3(v, OP_Last, iIdx, 0, -1); + sqlite3VdbeAddOp3(v, OP_IdxInsert, iIdx, regRecord, 0); sqlite3VdbeChangeP5(v, OPFLAG_USESEEKRESULT); sqlite3ReleaseTempReg(pParse, regRecord); sqlite3VdbeAddOp2(v, OP_SorterNext, iSorter, addr2); VdbeCoverage(v); diff --git a/src/vdbe.c b/src/vdbe.c index ec5e6d7442..150b2c150f 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -4480,7 +4480,7 @@ case OP_NullRow: { break; } -/* Opcode: Last P1 P2 * * * +/* Opcode: Last P1 P2 P3 * * ** ** The next use of the Rowid or Column or Prev instruction for P1 ** will refer to the last entry in the database table or index. @@ -4507,6 +4507,7 @@ case OP_Last: { /* jump */ pC->nullRow = (u8)res; pC->deferredMoveto = 0; pC->cacheStatus = CACHE_STALE; + pC->seekResult = pOp->p3; #ifdef SQLITE_DEBUG pC->seekOp = OP_Last; #endif From e34162b14f24aae2b478b917ceb6f516289ac39a Mon Sep 17 00:00:00 2001 From: dan Date: Wed, 1 Apr 2015 18:20:25 +0000 Subject: [PATCH 06/53] When vacuuming an index that uses no collations other than BINARY, assume that the order of index entries will not be changed by the VACUUM. FossilOrigin-Name: e403460b96814ac8cb976d58b27939b3bd3c61f9 --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/insert.c | 48 ++++++++++++++++++++++++++++++++++++++++-------- src/sqliteInt.h | 1 + src/vacuum.c | 4 ++++ 5 files changed, 54 insertions(+), 17 deletions(-) diff --git a/manifest b/manifest index be112fc01e..16584352e7 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Reduce\sthe\sCPU\sused\sby\sCREATE\sINDEX\sstatements\sby\staking\sbetter\sadvantage\sof\sthe\sfact\sthat\skeys\sare\sinserted\sin\ssorted\sorder. -D 2015-04-01T16:18:00.779 +C When\svacuuming\san\sindex\sthat\suses\sno\scollations\sother\sthan\sBINARY,\sassume\sthat\sthe\sorder\sof\sindex\sentries\swill\snot\sbe\schanged\sby\sthe\sVACUUM. +D 2015-04-01T18:20:25.537 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 88a3e6261286db378fdffa1124cad11b3c05f5bb F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -190,7 +190,7 @@ F src/global.c 4f77cadbc5427d00139ba43d0f3979804cbb700e F src/hash.c 4263fbc955f26c2e8cdc0cf214bc42435aa4e4f5 F src/hash.h c8f3c31722cf3277d03713909761e152a5b81094 F src/hwtime.h d32741c8f4df852c7d959236615444e2b1063b08 -F src/insert.c 5b9243a33726008cc4132897d2be371db12a13be +F src/insert.c 1cc9dc4e939b5dd4a74ac4a3222b89e66b074210 F src/journal.c b4124532212b6952f42eb2c12fa3c25701d8ba8d F src/legacy.c ba1863ea58c4c840335a84ec276fc2b25e22bc4e F src/lempar.c 7274c97d24bb46631e504332ccd3bd1b37841770 @@ -235,7 +235,7 @@ F src/shell.c 3ae1e53878d2804fe77b8c8f1f6ca287a0e5d80e F src/sqlite.h.in 278602140d49575e8708e643161f4263e428a02a F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d -F src/sqliteInt.h bedf15914c09bfb5fe3ec4e3f211a4a6fc42cd33 +F src/sqliteInt.h df0ee3545220b8687d8640d433d1417b31e1675a F src/sqliteLimit.h 216557999cb45f2e3578ed53ebefe228d779cb46 F src/status.c f266ad8a2892d659b74f0f50cb6a88b6e7c12179 F src/table.c e7a09215315a978057fb42c640f890160dbcc45e @@ -292,7 +292,7 @@ F src/trigger.c 25571661fdeae8c7f975ff40ffec205520a3f92f F src/update.c 3c4ecc282accf12d39edb8d524cf089645e55a13 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 98a7627ca48ad3265b6940915a1d08355eb3fc7e -F src/vacuum.c 9460b9de7b2d4e34b0d374894aa6c8a0632be8ec +F src/vacuum.c 2ddd5cad2a7b9cef7f9e431b8c7771634c6b1701 F src/vdbe.c a9d916abb1e22355a81b0e72040917ba33c87ed7 F src/vdbe.h 7e538ecf47dccb307ea2d087c3ddc2dd8d70e79d F src/vdbeInt.h 9cbaa84f53ddd2d09a0cf61a94337a3a035d08a0 @@ -1247,7 +1247,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 601e7b6b8e6bfabda03b70f75094c9014e3a3c49 -R 151febe3c42a1563a662898adadb6b2d +P 592cdc5d7254be7032aa9c0b03405a74ca060b51 +R d93391642538d3e00eae6a1c718cf53f U dan -Z 37e9d6c37bda7e19a2c8ebf1573e150d +Z 6ea2b15ffbb091b1ac11e4173c1e9ec7 diff --git a/manifest.uuid b/manifest.uuid index 6bc7a444cf..180597c5c9 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -592cdc5d7254be7032aa9c0b03405a74ca060b51 \ No newline at end of file +e403460b96814ac8cb976d58b27939b3bd3c61f9 \ No newline at end of file diff --git a/src/insert.c b/src/insert.c index a5c3f3e92d..f8ae4d7d3c 100644 --- a/src/insert.c +++ b/src/insert.c @@ -1765,6 +1765,7 @@ static int xferOptimization( int onError, /* How to handle constraint errors */ int iDbDest /* The database of pDest */ ){ + sqlite3 *db = pParse->db; ExprList *pEList; /* The result set of the SELECT */ Table *pSrc; /* The table in the FROM clause of SELECT */ Index *pSrcIdx, *pDestIdx; /* Source and destination indices */ @@ -1912,11 +1913,11 @@ static int xferOptimization( ** the extra complication to make this rule less restrictive is probably ** not worth the effort. Ticket [6284df89debdfa61db8073e062908af0c9b6118e] */ - if( (pParse->db->flags & SQLITE_ForeignKeys)!=0 && pDest->pFKey!=0 ){ + if( (db->flags & SQLITE_ForeignKeys)!=0 && pDest->pFKey!=0 ){ return 0; } #endif - if( (pParse->db->flags & SQLITE_CountRows)!=0 ){ + if( (db->flags & SQLITE_CountRows)!=0 ){ return 0; /* xfer opt does not play well with PRAGMA count_changes */ } @@ -1927,7 +1928,7 @@ static int xferOptimization( #ifdef SQLITE_TEST sqlite3_xferopt_count++; #endif - iDbSrc = sqlite3SchemaToIndex(pParse->db, pSrc->pSchema); + iDbSrc = sqlite3SchemaToIndex(db, pSrc->pSchema); v = sqlite3GetVdbe(pParse); sqlite3CodeVerifySchema(pParse, iDbSrc); iSrc = pParse->nTab++; @@ -1937,14 +1938,18 @@ static int xferOptimization( regRowid = sqlite3GetTempReg(pParse); sqlite3OpenTable(pParse, iDest, iDbDest, pDest, OP_OpenWrite); assert( HasRowid(pDest) || destHasUniqueIdx ); - if( (pDest->iPKey<0 && pDest->pIndex!=0) /* (1) */ + if( (db->flags & SQLITE_Vacuum)==0 && ( + (pDest->iPKey<0 && pDest->pIndex!=0) /* (1) */ || destHasUniqueIdx /* (2) */ || (onError!=OE_Abort && onError!=OE_Rollback) /* (3) */ - ){ + )){ /* In some circumstances, we are able to run the xfer optimization - ** only if the destination table is initially empty. This code makes - ** that determination. Conditions under which the destination must - ** be empty: + ** only if the destination table is initially empty. Unless the + ** SQLITE_Vacuum flag is set, this block generates code to make + ** that determination. If SQLITE_Vacuum is set, then the destination + ** table is always empty. + ** + ** Conditions under which the destination must be empty: ** ** (1) There is no INTEGER PRIMARY KEY but there are indices. ** (If the destination is not initially empty, the rowid fields @@ -1987,6 +1992,7 @@ static int xferOptimization( sqlite3TableLock(pParse, iDbSrc, pSrc->tnum, 0, pSrc->zName); } for(pDestIdx=pDest->pIndex; pDestIdx; pDestIdx=pDestIdx->pNext){ + u8 useSeekResult = 0; for(pSrcIdx=pSrc->pIndex; ALWAYS(pSrcIdx); pSrcIdx=pSrcIdx->pNext){ if( xferCompatibleIndex(pDestIdx, pSrcIdx) ) break; } @@ -2000,7 +2006,33 @@ static int xferOptimization( VdbeComment((v, "%s", pDestIdx->zName)); addr1 = sqlite3VdbeAddOp2(v, OP_Rewind, iSrc, 0); VdbeCoverage(v); sqlite3VdbeAddOp2(v, OP_RowKey, iSrc, regData); + if( db->flags & SQLITE_Vacuum ){ + /* This INSERT command is part of a VACUUM operation, which guarantees + ** that the destination table is empty. If all indexed columns use + ** collation sequence BINARY, then it can also be assumed that the + ** index will be populated by inserting keys in strictly sorted + ** order. In this case, instead of seeking within the b-tree as part + ** of every OP_IdxInsert opcode, an OP_Last is added before the + ** OP_IdxInsert to seek to the point within the b-tree where each key + ** should be inserted. This is faster. + ** + ** If any of the indexed columns use a collation sequence other than + ** BINARY, this optimization is disabled. This is because the user + ** might change the definition of a collation sequence and then run + ** a VACUUM command. In that case keys may not be written in strictly + ** sorted order. */ + int i; + for(i=0; inColumn; i++){ + char *zColl = pSrcIdx->azColl[i]; + if( zColl && sqlite3_stricmp("BINARY", zColl) ) break; + } + if( i==pSrcIdx->nColumn ){ + useSeekResult = OPFLAG_USESEEKRESULT; + sqlite3VdbeAddOp3(v, OP_Last, iDest, 0, -1); + } + } sqlite3VdbeAddOp3(v, OP_IdxInsert, iDest, regData, 1); + sqlite3VdbeChangeP5(v, useSeekResult); sqlite3VdbeAddOp2(v, OP_Next, iSrc, addr1+1); VdbeCoverage(v); sqlite3VdbeJumpHere(v, addr1); sqlite3VdbeAddOp2(v, OP_Close, iSrc, 0); diff --git a/src/sqliteInt.h b/src/sqliteInt.h index 9df6d1bc4e..5e49bf58ff 100644 --- a/src/sqliteInt.h +++ b/src/sqliteInt.h @@ -1226,6 +1226,7 @@ struct sqlite3 { #define SQLITE_DeferFKs 0x01000000 /* Defer all FK constraints */ #define SQLITE_QueryOnly 0x02000000 /* Disable database changes */ #define SQLITE_VdbeEQP 0x04000000 /* Debug EXPLAIN QUERY PLAN */ +#define SQLITE_Vacuum 0x08000000 /* Currently in a VACUUM */ /* diff --git a/src/vacuum.c b/src/vacuum.c index dca43e217e..adc802e60b 100644 --- a/src/vacuum.c +++ b/src/vacuum.c @@ -250,6 +250,8 @@ int sqlite3RunVacuum(char **pzErrMsg, sqlite3 *db){ ** an "INSERT INTO vacuum_db.xxx SELECT * FROM main.xxx;" to copy ** the contents to the temporary database. */ + assert( (db->flags & SQLITE_Vacuum)==0 ); + db->flags |= SQLITE_Vacuum; rc = execExecSql(db, pzErrMsg, "SELECT 'INSERT INTO vacuum_db.' || quote(name) " "|| ' SELECT * FROM main.' || quote(name) || ';'" @@ -257,6 +259,8 @@ int sqlite3RunVacuum(char **pzErrMsg, sqlite3 *db){ "WHERE type = 'table' AND name!='sqlite_sequence' " " AND coalesce(rootpage,1)>0" ); + assert( (db->flags & SQLITE_Vacuum)!=0 ); + db->flags &= ~SQLITE_Vacuum; if( rc!=SQLITE_OK ) goto end_of_vacuum; /* Copy over the sequence table From 29f1a19cd96e8d7f72366492986cce2053df0deb Mon Sep 17 00:00:00 2001 From: dan Date: Thu, 2 Apr 2015 09:06:21 +0000 Subject: [PATCH 07/53] Fix a problem in vdbesort.c to do with caching unpacked records. FossilOrigin-Name: 80a00539506c95443165a781d1d869205057ca6c --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/vdbesort.c | 2 +- 3 files changed, 8 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 8108693bf7..f9ce3a510d 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Merge\slatest\strunk\schanges\swith\sthis\sbranch. -D 2015-04-01T18:22:26.384 +C Fix\sa\sproblem\sin\svdbesort.c\sto\sdo\swith\scaching\sunpacked\srecords. +D 2015-04-02T09:06:21.116 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 00d12636df7a5b08af09116bcd6c7bfd49b8b3b4 F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -300,7 +300,7 @@ F src/vdbeapi.c 583d56b129dd27f12bed518270de9ebe521e6a75 F src/vdbeaux.c a20504ae52392459fa08402fda3f195f19d7c79d F src/vdbeblob.c 4f2e8e075d238392df98c5e03a64342465b03f90 F src/vdbemem.c c0dc81285b7571b0a31c40f17846fe2397ec1cd9 -F src/vdbesort.c 7b3684665ea51d642b0e664fa4d0b0d08d61d80c +F src/vdbesort.c 74a41fcd3adc22bc47ede68443d0b3e26ae13bb8 F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 F src/vtab.c 62d49237bd8f3be4863815a39387b0f9897fa5e1 F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb @@ -1248,7 +1248,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P e403460b96814ac8cb976d58b27939b3bd3c61f9 30011ad2f55cfcacaf23a58ebcc17b17a7b9355e -R 768d1278a2c7aae9e472dc5791f2f6a1 +P 4621b2eef8be6d944f87de097bd11c649fe43333 +R 0796456518338cd116674974cfde4890 U dan -Z 2045741c9810a18232145862154fc073 +Z 0cef8df18e8711c69cda8f5613bc4995 diff --git a/manifest.uuid b/manifest.uuid index a5a195f19f..0941cff2b9 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -4621b2eef8be6d944f87de097bd11c649fe43333 \ No newline at end of file +80a00539506c95443165a781d1d869205057ca6c \ No newline at end of file diff --git a/src/vdbesort.c b/src/vdbesort.c index 547dce2e65..f4b995c88a 100644 --- a/src/vdbesort.c +++ b/src/vdbesort.c @@ -1656,7 +1656,7 @@ static int vdbeMergeEngineStep( pReadr2 = &pMerger->aReadr[ pMerger->aTree[i ^ 0x0001] ]; bCached = 0; }else{ - bCached = (pReadr1->pFd!=0); + if( pReadr1->pFd ) bCached = 0; pMerger->aTree[i] = (int)(pReadr2 - pMerger->aReadr); pReadr1 = &pMerger->aReadr[ pMerger->aTree[i ^ 0x0001] ]; } From 50c7bb67f0e23c0b9618c7d488e234fb789505c3 Mon Sep 17 00:00:00 2001 From: drh Date: Thu, 9 Apr 2015 11:24:03 +0000 Subject: [PATCH 08/53] Remove a variable initializion to silence a harmless compiler warning. FossilOrigin-Name: 79861adbef8998c0f23e160543af8212d5546cd0 --- manifest | 15 ++++++--------- manifest.uuid | 2 +- src/complete.c | 2 +- 3 files changed, 8 insertions(+), 11 deletions(-) diff --git a/manifest b/manifest index e3dc7c37f3..2af0d5f0d6 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Version\s3.8.9 -D 2015-04-08T12:16:33.323 +C Remove\sa\svariable\sinitializion\sto\ssilence\sa\sharmless\scompiler\swarning. +D 2015-04-09T11:24:03.589 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 00d12636df7a5b08af09116bcd6c7bfd49b8b3b4 F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -178,7 +178,7 @@ F src/btree.h 969adc948e89e449220ff0ff724c94bb2a52e9f1 F src/btreeInt.h 973a22a6fd61350b454ad614832b1f0a5e25a1e4 F src/build.c 0419bba592c22f6d00e6d57a2ca7136720d02c1a F src/callback.c 7b44ce59674338ad48b0e84e7b72f935ea4f68b0 -F src/complete.c 198a0066ba60ab06fc00fba1998d870a4d575463 +F src/complete.c a5cf5b4b56390cfb7b8636e8f7ddef90258dd575 F src/ctime.c 98f89724adc891a1a4c655bee04e33e716e05887 F src/date.c e4d50b3283696836ec1036b695ead9a19e37a5ac F src/delete.c 37964e6c1d73ff49cbea9ff690c9605fb15f600e @@ -1249,10 +1249,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 8e4ac2ce24415926247961b00a62425ae85d6ffb -R 5875861747bb686954783d9ce4259b86 -T +bgcolor * #d0c0ff -T +sym-release * -T +sym-version-3.8.9 * +P 8a8ffc862e96f57aa698f93de10dee28e69f6e09 +R 94d9923532f03d2c01923395a653f609 U drh -Z 05045ab8d5dbbaefca88cc23b8dca09c +Z 1ec7205940b0e152091a81dfbeda06fb diff --git a/manifest.uuid b/manifest.uuid index a38b33773e..acb9c7faab 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -8a8ffc862e96f57aa698f93de10dee28e69f6e09 \ No newline at end of file +79861adbef8998c0f23e160543af8212d5546cd0 \ No newline at end of file diff --git a/src/complete.c b/src/complete.c index f7a35cc6f3..a12184e64d 100644 --- a/src/complete.c +++ b/src/complete.c @@ -269,7 +269,7 @@ int sqlite3_complete(const char *zSql){ int sqlite3_complete16(const void *zSql){ sqlite3_value *pVal; char const *zSql8; - int rc = SQLITE_NOMEM; + int rc; #ifndef SQLITE_OMIT_AUTOINIT rc = sqlite3_initialize(); From d62c0f4c2daa03886116576b65866bfedb2e6ed6 Mon Sep 17 00:00:00 2001 From: drh Date: Thu, 9 Apr 2015 13:34:29 +0000 Subject: [PATCH 09/53] Add the "sqldiff" utility program. FossilOrigin-Name: 88da5bf5d2c4f848dbd4b5ffb1539abfbbdaff18 --- Makefile.in | 3 + Makefile.msc | 3 + main.mk | 4 + manifest | 17 +- manifest.uuid | 2 +- tool/sqldiff.c | 783 +++++++++++++++++++++++++++++++++++++++++++++++++ 6 files changed, 803 insertions(+), 9 deletions(-) create mode 100644 tool/sqldiff.c diff --git a/Makefile.in b/Makefile.in index 2177488f9b..295a6bc9c1 100644 --- a/Makefile.in +++ b/Makefile.in @@ -536,6 +536,9 @@ sqlite3$(TEXE): $(TOP)/src/shell.c libsqlite3.la sqlite3.h -o $@ $(TOP)/src/shell.c libsqlite3.la \ $(LIBREADLINE) $(TLIBS) -rpath "$(libdir)" +sqldiff$(EXE): $(TOP)/tool/sqldiff.c sqlite3.c sqlite3.h + $(LTLINK) -o $@ $(TOP)/tool/sqldiff.c sqlite3.c $(TLIBS) + mptester$(EXE): sqlite3.c $(TOP)/mptest/mptest.c $(LTLINK) -o $@ -I. $(TOP)/mptest/mptest.c sqlite3.c \ $(TLIBS) -rpath "$(libdir)" diff --git a/Makefile.msc b/Makefile.msc index 5330f8962f..b49a3eb0e1 100644 --- a/Makefile.msc +++ b/Makefile.msc @@ -1154,6 +1154,9 @@ sqlite3.exe: $(TOP)\src\shell.c $(SHELL_CORE_DEP) $(LIBRESOBJS) sqlite3.h $(LTLINK) $(SHELL_COMPILE_OPTS) $(READLINE_FLAGS) $(TOP)\src\shell.c \ /link /pdb:sqlite3sh.pdb $(LTLINKOPTS) $(SHELL_LINK_OPTS) $(LTLIBPATHS) $(LIBRESOBJS) $(LIBREADLINE) $(LTLIBS) $(TLIBS) +sqldiff.exe: $(TOP)\tool\sqldiff.c sqlite3.c sqlite3.h + $(LTLINK) $(TOP)\tool\sqldiff.c sqlite3.c + mptester.exe: $(TOP)\mptest\mptest.c $(SHELL_CORE_DEP) $(LIBRESOBJS) sqlite3.h $(LTLINK) $(SHELL_COMPILE_OPTS) $(TOP)\mptest\mptest.c \ /link $(LTLINKOPTS) $(LTLIBPATHS) $(SHELL_LINK_OPTS) $(LIBRESOBJS) $(LIBREADLINE) $(LTLIBS) $(TLIBS) diff --git a/main.mk b/main.mk index 57bb35c486..c5328dc6c7 100644 --- a/main.mk +++ b/main.mk @@ -404,6 +404,10 @@ sqlite3$(EXE): $(TOP)/src/shell.c libsqlite3.a sqlite3.h $(TOP)/src/shell.c \ libsqlite3.a $(LIBREADLINE) $(TLIBS) $(THREADLIB) +sqldiff$(EXE): $(TOP)/tool/sqldiff.c sqlite3.c sqlite3.h + $(TCCX) -o sqldiff$(EXE) -DSQLITE_THREADSAFE=0 \ + $(TOP)/tool/sqldiff.c sqlite3.c $(TLIBS) $(THREADLIB) + mptester$(EXE): sqlite3.c $(TOP)/mptest/mptest.c $(TCCX) -o $@ -I. $(TOP)/mptest/mptest.c sqlite3.c \ $(TLIBS) $(THREADLIB) diff --git a/manifest b/manifest index 2af0d5f0d6..bcddd8c661 100644 --- a/manifest +++ b/manifest @@ -1,9 +1,9 @@ -C Remove\sa\svariable\sinitializion\sto\ssilence\sa\sharmless\scompiler\swarning. -D 2015-04-09T11:24:03.589 +C Add\sthe\s"sqldiff"\sutility\sprogram. +D 2015-04-09T13:34:29.580 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f -F Makefile.in 00d12636df7a5b08af09116bcd6c7bfd49b8b3b4 +F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 -F Makefile.msc a8d817fa486d8c88dfbd19ae6a6567d9d350de39 +F Makefile.msc fa6a6de11af800d89f86e8a4266fd40a46008347 F Makefile.vxworks e1b65dea203f054e71653415bd8f96dcaed47858 F README.md d58e3bebc0a4145e0f2a87994015fdb575a8e866 F VERSION 319eb1ced4b4d17a67730f2b7b85f15c1346cb60 @@ -152,7 +152,7 @@ F ext/userauth/userauth.c 5fa3bdb492f481bbc1709fc83c91ebd13460c69e F install-sh 9d4de14ab9fb0facae2f48780b874848cbf2f895 x F ltmain.sh 3ff0879076df340d2e23ae905484d8c15d5fdea8 F magic.txt 8273bf49ba3b0c8559cb2774495390c31fd61c60 -F main.mk 997eee18387a3e69394f2f948c9c6ccf079655a4 +F main.mk ddffac494a82d42772df9fe30d3a78acf4f7cb41 F mkopcodec.awk c2ff431854d702cdd2d779c9c0d1f58fa16fa4ea F mkopcodeh.awk c6b3fa301db6ef7ac916b14c60868aeaec1337b5 F mkso.sh fd21c06b063bb16a5d25deea1752c2da6ac3ed83 @@ -1239,6 +1239,7 @@ F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e F tool/split-sqlite3c.tcl d9be87f1c340285a3e081eb19b4a247981ed290c +F tool/sqldiff.c 9c1c1e0aef974f1ad52aa720440a8a105d24d6f0 F tool/stack_usage.tcl f8e71b92cdb099a147dad572375595eae55eca43 F tool/symbols-mingw.sh 4dbcea7e74768305384c9fd2ed2b41bbf9f0414d F tool/symbols.sh fec58532668296d7c7dc48be9c87f75ccdb5814f @@ -1249,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 8a8ffc862e96f57aa698f93de10dee28e69f6e09 -R 94d9923532f03d2c01923395a653f609 +P 79861adbef8998c0f23e160543af8212d5546cd0 +R 55392413d804c3fa91206c94bb3d11f7 U drh -Z 1ec7205940b0e152091a81dfbeda06fb +Z a808bd48a859f116c92ef95210be5fe3 diff --git a/manifest.uuid b/manifest.uuid index acb9c7faab..32da2f232b 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -79861adbef8998c0f23e160543af8212d5546cd0 \ No newline at end of file +88da5bf5d2c4f848dbd4b5ffb1539abfbbdaff18 \ No newline at end of file diff --git a/tool/sqldiff.c b/tool/sqldiff.c new file mode 100644 index 0000000000..9aa68caaa9 --- /dev/null +++ b/tool/sqldiff.c @@ -0,0 +1,783 @@ +/* +** 2015-04-06 +** +** 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. +** +************************************************************************* +** +** This is a utility problem that computes the differences in content +** between two SQLite databases. +*/ +#include +#include +#include +#include +#include +#include "sqlite3.h" + +/* +** All global variables are gathered into the "g" singleton. +*/ +struct GlobalVars { + const char *zArgv0; /* Name of program */ + int bSchemaOnly; /* Only show schema differences */ + unsigned fDebug; /* Debug flags */ + sqlite3 *db; /* The database connection */ +} g; + +/* +** Allowed values for g.fDebug +*/ +#define DEBUG_COLUMN_NAMES 0x000001 +#define DEBUG_DIFF_SQL 0x000002 + +/* +** Dynamic string object +*/ +typedef struct Str Str; +struct Str { + char *z; /* Text of the string */ + int nAlloc; /* Bytes allocated in z[] */ + int nUsed; /* Bytes actually used in z[] */ +}; + +/* +** Initialize a Str object +*/ +static void strInit(Str *p){ + p->z = 0; + p->nAlloc = 0; + p->nUsed = 0; +} + +/* +** Print an error resulting from faulting command-line arguments and +** abort the program. +*/ +static void cmdlineError(const char *zFormat, ...){ + va_list ap; + fprintf(stderr, "%s: ", g.zArgv0); + va_start(ap, zFormat); + vfprintf(stderr, zFormat, ap); + va_end(ap); + fprintf(stderr, "\n\"%s --help\" for more help\n", g.zArgv0); + exit(1); +} + +/* +** Print an error message for an error that occurs at runtime, then +** abort the program. +*/ +static void runtimeError(const char *zFormat, ...){ + va_list ap; + fprintf(stderr, "%s: ", g.zArgv0); + va_start(ap, zFormat); + vfprintf(stderr, zFormat, ap); + va_end(ap); + fprintf(stderr, "\n"); + exit(1); +} + +/* +** Free all memory held by a Str object +*/ +static void strFree(Str *p){ + sqlite3_free(p->z); + strInit(p); +} + +/* +** Add formatted text to the end of a Str object +*/ +static void strPrintf(Str *p, const char *zFormat, ...){ + int nNew; + for(;;){ + if( p->z ){ + va_list ap; + va_start(ap, zFormat); + sqlite3_vsnprintf(p->nAlloc-p->nUsed, p->z+p->nUsed, zFormat, ap); + va_end(ap); + nNew = (int)strlen(p->z + p->nUsed); + }else{ + nNew = p->nAlloc; + } + if( p->nUsed+nNew < p->nAlloc-1 ){ + p->nUsed += nNew; + break; + } + p->nAlloc = p->nAlloc*2 + 1000; + p->z = sqlite3_realloc(p->z, p->nAlloc); + if( p->z==0 ) runtimeError("out of memory"); + } +} + + + +/* Safely quote an SQL identifier. Use the minimum amount of transformation +** necessary to allow the string to be used with %s. +** +** Space to hold the returned string is obtained from sqlite3_malloc(). The +** caller is responsible for ensuring this space is freed when no longer +** needed. +*/ +static char *safeId(const char *zId){ + /* All SQLite keywords, in alphabetical order */ + static const char *azKeywords[] = { + "ABORT", "ACTION", "ADD", "AFTER", "ALL", "ALTER", "ANALYZE", "AND", "AS", + "ASC", "ATTACH", "AUTOINCREMENT", "BEFORE", "BEGIN", "BETWEEN", "BY", + "CASCADE", "CASE", "CAST", "CHECK", "COLLATE", "COLUMN", "COMMIT", + "CONFLICT", "CONSTRAINT", "CREATE", "CROSS", "CURRENT_DATE", + "CURRENT_TIME", "CURRENT_TIMESTAMP", "DATABASE", "DEFAULT", "DEFERRABLE", + "DEFERRED", "DELETE", "DESC", "DETACH", "DISTINCT", "DROP", "EACH", + "ELSE", "END", "ESCAPE", "EXCEPT", "EXCLUSIVE", "EXISTS", "EXPLAIN", + "FAIL", "FOR", "FOREIGN", "FROM", "FULL", "GLOB", "GROUP", "HAVING", "IF", + "IGNORE", "IMMEDIATE", "IN", "INDEX", "INDEXED", "INITIALLY", "INNER", + "INSERT", "INSTEAD", "INTERSECT", "INTO", "IS", "ISNULL", "JOIN", "KEY", + "LEFT", "LIKE", "LIMIT", "MATCH", "NATURAL", "NO", "NOT", "NOTNULL", + "NULL", "OF", "OFFSET", "ON", "OR", "ORDER", "OUTER", "PLAN", "PRAGMA", + "PRIMARY", "QUERY", "RAISE", "RECURSIVE", "REFERENCES", "REGEXP", + "REINDEX", "RELEASE", "RENAME", "REPLACE", "RESTRICT", "RIGHT", + "ROLLBACK", "ROW", "SAVEPOINT", "SELECT", "SET", "TABLE", "TEMP", + "TEMPORARY", "THEN", "TO", "TRANSACTION", "TRIGGER", "UNION", "UNIQUE", + "UPDATE", "USING", "VACUUM", "VALUES", "VIEW", "VIRTUAL", "WHEN", "WHERE", + "WITH", "WITHOUT", + }; + int lwr, upr, mid, c, i, x; + for(i=x=0; (c = zId[i])!=0; i++){ + if( !isalpha(c) && c!='_' ){ + if( i>0 && isdigit(c) ){ + x++; + }else{ + return sqlite3_mprintf("\"%w\"", zId); + } + } + } + if( x ) return sqlite3_mprintf("%s", zId); + lwr = 0; + upr = sizeof(azKeywords)/sizeof(azKeywords[0]) - 1; + while( lwr<=upr ){ + mid = (lwr+upr)/2; + c = sqlite3_stricmp(azKeywords[mid], zId); + if( c==0 ) return sqlite3_mprintf("\"%w\"", zId); + if( c<0 ){ + lwr = mid+1; + }else{ + upr = mid-1; + } + } + return sqlite3_mprintf("%s", zId); +} + +/* +** Prepare a new SQL statement. Print an error and abort if anything +** goes wrong. +*/ +static sqlite3_stmt *db_vprepare(const char *zFormat, va_list ap){ + char *zSql; + int rc; + sqlite3_stmt *pStmt; + + zSql = sqlite3_vmprintf(zFormat, ap); + if( zSql==0 ) runtimeError("out of memory"); + rc = sqlite3_prepare_v2(g.db, zSql, -1, &pStmt, 0); + if( rc ){ + runtimeError("SQL statement error: %s\n\"%s\"", sqlite3_errmsg(g.db), + zSql); + } + sqlite3_free(zSql); + return pStmt; +} +static sqlite3_stmt *db_prepare(const char *zFormat, ...){ + va_list ap; + sqlite3_stmt *pStmt; + va_start(ap, zFormat); + pStmt = db_vprepare(zFormat, ap); + va_end(ap); + return pStmt; +} + +/* +** Free a list of strings +*/ +static void namelistFree(char **az){ + if( az ){ + int i; + for(i=0; az[i]; i++) sqlite3_free(az[i]); + sqlite3_free(az); + } +} + +/* +** Return a list of column names for the table zDb.zTab. Space to +** old the list is obtained from malloc() and should released by calling +** namelistFree() when no longer needed. +** +** Primary key columns are listed first, followed by data columns. The +** "primary key" in the previous sentence is the true primary key - the +** rowid or INTEGER PRIMARY KEY for ordinary tables or the declared +** PRIMARY KEY for WITHOUT ROWID tables. The number of columns in the +** primary key is returned in *pNPkey. +** +** If the table is a rowid table for which the rowid is inaccessible, +** then this routine returns a NULL pointer. +** +** Examples: +** CREATE TABLE t1(a INT UNIQUE, b INTEGER, c TEXT, PRIMARY KEY(c)); +** *pnPKey = 1; +** az = { "rowid", "a", "b", "c", 0 } +** +** CREATE TABLE t2(a INT UNIQUE, b INTEGER, c TEXT, PRIMARY KEY(b)); +** *pnPKey = 1; +** az = { "b", "a", "c", 0 } +** +** CREATE TABLE t3(x,y,z,PRIMARY KEY(y,z)); +** *pnPKey = 1 +** az = { "rowid", "x", "y", "z", 0 } +** +** CREATE TABLE t4(x,y,z,PRIMARY KEY(y,z)) WITHOUT ROWID; +** *pnPKey = 2 +** az = { "y", "z", "x", 0 } +** +** CREATE TABLE t5(rowid,_rowid_,oid); +** az = 0 // The rowid is not accessible +*/ +static char **columnNames(const char *zDb, const char *zTab, int *pnPKey){ + char **az = 0; + int naz = 0; + sqlite3_stmt *pStmt; + char *zPkIdxName = 0; /* Name of the PRIMARY KEY index */ + int truePk = 0; /* PRAGMA table_info indentifies the true PK */ + int nPK = 0; /* Number of PRIMARY KEY columns */ + int i, j; + + pStmt = db_prepare("PRAGMA %s.index_list=%Q", zDb, zTab); + while( SQLITE_ROW==sqlite3_step(pStmt) ){ + if( sqlite3_stricmp((const char*)sqlite3_column_text(pStmt,3),"pk")==0 ){ + zPkIdxName = sqlite3_mprintf("%s", sqlite3_column_text(pStmt, 1)); + break; + } + } + sqlite3_finalize(pStmt); + if( zPkIdxName ){ + int nKey = 0; + int nCol = 0; + truePk = 0; + pStmt = db_prepare("PRAGMA %s.index_xinfo=%Q", zDb, zPkIdxName); + while( SQLITE_ROW==sqlite3_step(pStmt) ){ + nCol++; + if( sqlite3_column_int(pStmt,5) ){ nKey++; continue; } + if( sqlite3_column_int(pStmt,1)>=0 ) truePk = 1; + } + if( nCol==nKey ) truePk = 1; + if( truePk ){ + nPK = nKey; + }else{ + nPK = 1; + } + sqlite3_finalize(pStmt); + sqlite3_free(zPkIdxName); + }else{ + truePk = 1; + nPK = 1; + } + *pnPKey = nPK; + naz = nPK; + az = sqlite3_malloc( sizeof(char*)*(nPK+1) ); + if( az==0 ) runtimeError("out of memory"); + memset(az, 0, sizeof(char*)*(nPK+1)); + pStmt = db_prepare("PRAGMA %s.table_info=%Q", zDb, zTab); + while( SQLITE_ROW==sqlite3_step(pStmt) ){ + int iPKey; + if( truePk && (iPKey = sqlite3_column_int(pStmt,5))>0 ){ + az[iPKey-1] = safeId((char*)sqlite3_column_text(pStmt,1)); + }else{ + az = sqlite3_realloc(az, sizeof(char*)*(naz+2) ); + if( az==0 ) runtimeError("out of memory"); + az[naz++] = safeId((char*)sqlite3_column_text(pStmt,1)); + } + } + sqlite3_finalize(pStmt); + if( az ) az[naz] = 0; + if( az[0]==0 ){ + const char *azRowid[] = { "rowid", "_rowid_", "oid" }; + for(i=0; i=naz ){ + az[0] = sqlite3_mprintf("%s", azRowid[i]); + break; + } + } + if( az[0]==0 ){ + for(i=1; inPk2 ){ + zSep = "SELECT "; + for(i=0; i Date: Thu, 9 Apr 2015 13:40:18 +0000 Subject: [PATCH 10/53] Fix comment typos in the sqldiff.c utility program. FossilOrigin-Name: 32ab2bb990746a84f5944e3cf428fb2dff3628da --- manifest | 12 ++++++------ manifest.uuid | 2 +- tool/sqldiff.c | 6 +++--- 3 files changed, 10 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index bcddd8c661..f4f4fa2b88 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\sthe\s"sqldiff"\sutility\sprogram. -D 2015-04-09T13:34:29.580 +C Fix\scomment\stypos\sin\sthe\ssqldiff.c\sutility\sprogram. +D 2015-04-09T13:40:18.767 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -1239,7 +1239,7 @@ F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e F tool/split-sqlite3c.tcl d9be87f1c340285a3e081eb19b4a247981ed290c -F tool/sqldiff.c 9c1c1e0aef974f1ad52aa720440a8a105d24d6f0 +F tool/sqldiff.c a28d17d824bc80940c2d67b2cf85a387c461dc97 F tool/stack_usage.tcl f8e71b92cdb099a147dad572375595eae55eca43 F tool/symbols-mingw.sh 4dbcea7e74768305384c9fd2ed2b41bbf9f0414d F tool/symbols.sh fec58532668296d7c7dc48be9c87f75ccdb5814f @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 79861adbef8998c0f23e160543af8212d5546cd0 -R 55392413d804c3fa91206c94bb3d11f7 +P 88da5bf5d2c4f848dbd4b5ffb1539abfbbdaff18 +R df929ff4fd13763291be7acc0214ee00 U drh -Z a808bd48a859f116c92ef95210be5fe3 +Z 41493ba4ef878730b46175333abd9329 diff --git a/manifest.uuid b/manifest.uuid index 32da2f232b..91e566d270 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -88da5bf5d2c4f848dbd4b5ffb1539abfbbdaff18 \ No newline at end of file +32ab2bb990746a84f5944e3cf428fb2dff3628da \ No newline at end of file diff --git a/tool/sqldiff.c b/tool/sqldiff.c index 9aa68caaa9..2b982e914a 100644 --- a/tool/sqldiff.c +++ b/tool/sqldiff.c @@ -214,14 +214,14 @@ static void namelistFree(char **az){ /* ** Return a list of column names for the table zDb.zTab. Space to -** old the list is obtained from malloc() and should released by calling -** namelistFree() when no longer needed. +** hold the list is obtained from sqlite3_malloc() and should released +** using namelistFree() when no longer needed. ** ** Primary key columns are listed first, followed by data columns. The ** "primary key" in the previous sentence is the true primary key - the ** rowid or INTEGER PRIMARY KEY for ordinary tables or the declared ** PRIMARY KEY for WITHOUT ROWID tables. The number of columns in the -** primary key is returned in *pNPkey. +** primary key is returned in *pnPkey. ** ** If the table is a rowid table for which the rowid is inaccessible, ** then this routine returns a NULL pointer. From 3875becf3559a1129da2eca84491f11ab7b308d8 Mon Sep 17 00:00:00 2001 From: drh Date: Thu, 9 Apr 2015 16:30:56 +0000 Subject: [PATCH 11/53] Remove two pointless assert() statements. This should silence harmless compiler warnings reported at [https://bugzilla.mozilla.org/show_bug.cgi?id=1152845] FossilOrigin-Name: 83b342a44ffc9ea07dc4d59f2866cefc68ee4f13 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/build.c | 1 - src/trigger.c | 1 - 4 files changed, 8 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index f4f4fa2b88..a4817bdb6c 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\scomment\stypos\sin\sthe\ssqldiff.c\sutility\sprogram. -D 2015-04-09T13:40:18.767 +C Remove\stwo\spointless\sassert()\sstatements.\s\sThis\sshould\ssilence\sharmless\ncompiler\swarnings\sreported\sat\s\n[https://bugzilla.mozilla.org/show_bug.cgi?id=1152845] +D 2015-04-09T16:30:56.502 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -176,7 +176,7 @@ F src/btmutex.c 45a968cc85afed9b5e6cf55bf1f42f8d18107f79 F src/btree.c 2caf598165f3608fde8abac2b243826616ce54b7 F src/btree.h 969adc948e89e449220ff0ff724c94bb2a52e9f1 F src/btreeInt.h 973a22a6fd61350b454ad614832b1f0a5e25a1e4 -F src/build.c 0419bba592c22f6d00e6d57a2ca7136720d02c1a +F src/build.c 4a6d573cd5f77812f32d343134b429046946d560 F src/callback.c 7b44ce59674338ad48b0e84e7b72f935ea4f68b0 F src/complete.c a5cf5b4b56390cfb7b8636e8f7ddef90258dd575 F src/ctime.c 98f89724adc891a1a4c655bee04e33e716e05887 @@ -288,7 +288,7 @@ F src/test_vfstrace.c bab9594adc976cbe696ff3970728830b4c5ed698 F src/test_wsd.c 41cadfd9d97fe8e3e4e44f61a4a8ccd6f7ca8fe9 F src/threads.c 6bbcc9fe50c917864d48287b4792d46d6e873481 F src/tokenize.c a8d270b06e5f709930f7b67cf70a847969cb5bf3 -F src/trigger.c 25571661fdeae8c7f975ff40ffec205520a3f92f +F src/trigger.c 69a91bed7c94e46223e37ffccfeeb35e34b999ac F src/update.c 3c4ecc282accf12d39edb8d524cf089645e55a13 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 98a7627ca48ad3265b6940915a1d08355eb3fc7e @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 88da5bf5d2c4f848dbd4b5ffb1539abfbbdaff18 -R df929ff4fd13763291be7acc0214ee00 +P 32ab2bb990746a84f5944e3cf428fb2dff3628da +R 37f01a89c55b4805b0a5cf101a377c7c U drh -Z 41493ba4ef878730b46175333abd9329 +Z 80169060600c5dd4d547a3dab7f7d969 diff --git a/manifest.uuid b/manifest.uuid index 91e566d270..341851e55f 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -32ab2bb990746a84f5944e3cf428fb2dff3628da \ No newline at end of file +83b342a44ffc9ea07dc4d59f2866cefc68ee4f13 \ No newline at end of file diff --git a/src/build.c b/src/build.c index fcf96bd42c..e01e2427f1 100644 --- a/src/build.c +++ b/src/build.c @@ -3776,7 +3776,6 @@ void sqlite3SrcListIndexedBy(Parse *pParse, SrcList *p, Token *pIndexedBy){ void sqlite3SrcListShiftJoinType(SrcList *p){ if( p ){ int i; - assert( p->a || p->nSrc==0 ); for(i=p->nSrc-1; i>0; i--){ p->a[i].jointype = p->a[i-1].jointype; } diff --git a/src/trigger.c b/src/trigger.c index d2e7b5a1e6..ed152d2a8a 100644 --- a/src/trigger.c +++ b/src/trigger.c @@ -680,7 +680,6 @@ static SrcList *targetSrcList( pSrc = sqlite3SrcListAppend(pParse->db, 0, &pStep->target, 0); if( pSrc ){ assert( pSrc->nSrc>0 ); - assert( pSrc->a!=0 ); iDb = sqlite3SchemaToIndex(pParse->db, pStep->pTrig->pSchema); if( iDb==0 || iDb>=2 ){ sqlite3 *db = pParse->db; From a37591cdd10ead51ed87a43aeeb9f83312636fd1 Mon Sep 17 00:00:00 2001 From: drh Date: Thu, 9 Apr 2015 18:14:03 +0000 Subject: [PATCH 12/53] Add the --primarykey option to the sqldiff tool, which causes it to use the schema-defined PRIMARY KEY. FossilOrigin-Name: 5063f9070afde9374ea0f2bc338fee840d8b3dd4 --- manifest | 12 +++--- manifest.uuid | 2 +- tool/sqldiff.c | 112 ++++++++++++++++++++++++++++++++----------------- 3 files changed, 80 insertions(+), 46 deletions(-) diff --git a/manifest b/manifest index a4817bdb6c..d6f8442010 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\stwo\spointless\sassert()\sstatements.\s\sThis\sshould\ssilence\sharmless\ncompiler\swarnings\sreported\sat\s\n[https://bugzilla.mozilla.org/show_bug.cgi?id=1152845] -D 2015-04-09T16:30:56.502 +C Add\sthe\s--primarykey\soption\sto\sthe\ssqldiff\stool,\swhich\scauses\sit\sto\suse\sthe\nschema-defined\sPRIMARY\sKEY. +D 2015-04-09T18:14:03.130 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -1239,7 +1239,7 @@ F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e F tool/split-sqlite3c.tcl d9be87f1c340285a3e081eb19b4a247981ed290c -F tool/sqldiff.c a28d17d824bc80940c2d67b2cf85a387c461dc97 +F tool/sqldiff.c 9334ebc767dda9e02b904d4cbbd31cf8aaba3ca5 F tool/stack_usage.tcl f8e71b92cdb099a147dad572375595eae55eca43 F tool/symbols-mingw.sh 4dbcea7e74768305384c9fd2ed2b41bbf9f0414d F tool/symbols.sh fec58532668296d7c7dc48be9c87f75ccdb5814f @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 32ab2bb990746a84f5944e3cf428fb2dff3628da -R 37f01a89c55b4805b0a5cf101a377c7c +P 83b342a44ffc9ea07dc4d59f2866cefc68ee4f13 +R 80b4d61d5d12e62d07bcaa502c23a21f U drh -Z 80169060600c5dd4d547a3dab7f7d969 +Z 965913d93d231505652de01e91883fad diff --git a/manifest.uuid b/manifest.uuid index 341851e55f..fda938f72a 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -83b342a44ffc9ea07dc4d59f2866cefc68ee4f13 \ No newline at end of file +5063f9070afde9374ea0f2bc338fee840d8b3dd4 \ No newline at end of file diff --git a/tool/sqldiff.c b/tool/sqldiff.c index 2b982e914a..28b66b2c37 100644 --- a/tool/sqldiff.c +++ b/tool/sqldiff.c @@ -26,6 +26,7 @@ struct GlobalVars { const char *zArgv0; /* Name of program */ int bSchemaOnly; /* Only show schema differences */ + int bSchemaPK; /* Use the schema-defined PK, not the true PK */ unsigned fDebug; /* Debug flags */ sqlite3 *db; /* The database connection */ } g; @@ -217,27 +218,34 @@ static void namelistFree(char **az){ ** hold the list is obtained from sqlite3_malloc() and should released ** using namelistFree() when no longer needed. ** -** Primary key columns are listed first, followed by data columns. The -** "primary key" in the previous sentence is the true primary key - the -** rowid or INTEGER PRIMARY KEY for ordinary tables or the declared -** PRIMARY KEY for WITHOUT ROWID tables. The number of columns in the -** primary key is returned in *pnPkey. +** Primary key columns are listed first, followed by data columns. +** The number of columns in the primary key is returned in *pnPkey. ** -** If the table is a rowid table for which the rowid is inaccessible, +** Normally, the "primary key" in the previous sentence is the true +** primary key - the rowid or INTEGER PRIMARY KEY for ordinary tables +** or the declared PRIMARY KEY for WITHOUT ROWID tables. However, if +** the g.bSchemaPK flag is set, then the schema-defined PRIMARY KEY is +** used in all cases. In that case, entries that have NULL values in +** any of their primary key fields will be excluded from the analysis. +** +** If the primary key for a table is the rowid but rowid is inaccessible, ** then this routine returns a NULL pointer. ** ** Examples: ** CREATE TABLE t1(a INT UNIQUE, b INTEGER, c TEXT, PRIMARY KEY(c)); ** *pnPKey = 1; -** az = { "rowid", "a", "b", "c", 0 } +** az = { "rowid", "a", "b", "c", 0 } // Normal case +** az = { "c", "a", "b", 0 } // g.bSchemaPK==1 ** ** CREATE TABLE t2(a INT UNIQUE, b INTEGER, c TEXT, PRIMARY KEY(b)); ** *pnPKey = 1; ** az = { "b", "a", "c", 0 } ** ** CREATE TABLE t3(x,y,z,PRIMARY KEY(y,z)); -** *pnPKey = 1 -** az = { "rowid", "x", "y", "z", 0 } +** *pnPKey = 1 // Normal case +** az = { "rowid", "x", "y", "z", 0 } // Normal case +** *pnPKey = 2 // g.bSchemaPK==1 +** az = { "y", "x", "z", 0 } // g.bSchemaPK==1 ** ** CREATE TABLE t4(x,y,z,PRIMARY KEY(y,z)) WITHOUT ROWID; ** *pnPKey = 2 @@ -247,50 +255,72 @@ static void namelistFree(char **az){ ** az = 0 // The rowid is not accessible */ static char **columnNames(const char *zDb, const char *zTab, int *pnPKey){ - char **az = 0; - int naz = 0; - sqlite3_stmt *pStmt; + char **az = 0; /* List of column names to be returned */ + int naz = 0; /* Number of entries in az[] */ + sqlite3_stmt *pStmt; /* SQL statement being run */ char *zPkIdxName = 0; /* Name of the PRIMARY KEY index */ - int truePk = 0; /* PRAGMA table_info indentifies the true PK */ + int truePk = 0; /* PRAGMA table_info indentifies the PK to use */ int nPK = 0; /* Number of PRIMARY KEY columns */ - int i, j; + int i, j; /* Loop counters */ - pStmt = db_prepare("PRAGMA %s.index_list=%Q", zDb, zTab); - while( SQLITE_ROW==sqlite3_step(pStmt) ){ - if( sqlite3_stricmp((const char*)sqlite3_column_text(pStmt,3),"pk")==0 ){ - zPkIdxName = sqlite3_mprintf("%s", sqlite3_column_text(pStmt, 1)); - break; - } - } - sqlite3_finalize(pStmt); - if( zPkIdxName ){ - int nKey = 0; - int nCol = 0; - truePk = 0; - pStmt = db_prepare("PRAGMA %s.index_xinfo=%Q", zDb, zPkIdxName); + if( g.bSchemaPK==0 ){ + /* Normal case: Figure out what the true primary key is for the table. + ** * For WITHOUT ROWID tables, the true primary key is the same as + ** the schema PRIMARY KEY, which is guaranteed to be present. + ** * For rowid tables with an INTEGER PRIMARY KEY, the true primary + ** key is the INTEGER PRIMARY KEY. + ** * For all other rowid tables, the rowid is the true primary key. + */ + pStmt = db_prepare("PRAGMA %s.index_list=%Q", zDb, zTab); while( SQLITE_ROW==sqlite3_step(pStmt) ){ - nCol++; - if( sqlite3_column_int(pStmt,5) ){ nKey++; continue; } - if( sqlite3_column_int(pStmt,1)>=0 ) truePk = 1; - } - if( nCol==nKey ) truePk = 1; - if( truePk ){ - nPK = nKey; - }else{ - nPK = 1; + if( sqlite3_stricmp((const char*)sqlite3_column_text(pStmt,3),"pk")==0 ){ + zPkIdxName = sqlite3_mprintf("%s", sqlite3_column_text(pStmt, 1)); + break; + } } sqlite3_finalize(pStmt); - sqlite3_free(zPkIdxName); + if( zPkIdxName ){ + int nKey = 0; + int nCol = 0; + truePk = 0; + pStmt = db_prepare("PRAGMA %s.index_xinfo=%Q", zDb, zPkIdxName); + while( SQLITE_ROW==sqlite3_step(pStmt) ){ + nCol++; + if( sqlite3_column_int(pStmt,5) ){ nKey++; continue; } + if( sqlite3_column_int(pStmt,1)>=0 ) truePk = 1; + } + if( nCol==nKey ) truePk = 1; + if( truePk ){ + nPK = nKey; + }else{ + nPK = 1; + } + sqlite3_finalize(pStmt); + sqlite3_free(zPkIdxName); + }else{ + truePk = 1; + nPK = 1; + } + pStmt = db_prepare("PRAGMA %s.table_info=%Q", zDb, zTab); }else{ + /* The g.bSchemaPK==1 case: Use whatever primary key is declared + ** in the schema. The "rowid" will still be used as the primary key + ** if the table definition does not contain a PRIMARY KEY. + */ + nPK = 0; + pStmt = db_prepare("PRAGMA %s.table_info=%Q", zDb, zTab); + while( SQLITE_ROW==sqlite3_step(pStmt) ){ + if( sqlite3_column_int(pStmt,5)>0 ) nPK++; + } + sqlite3_reset(pStmt); + if( nPK==0 ) nPK = 1; truePk = 1; - nPK = 1; } *pnPKey = nPK; naz = nPK; az = sqlite3_malloc( sizeof(char*)*(nPK+1) ); if( az==0 ) runtimeError("out of memory"); memset(az, 0, sizeof(char*)*(nPK+1)); - pStmt = db_prepare("PRAGMA %s.table_info=%Q", zDb, zTab); while( SQLITE_ROW==sqlite3_step(pStmt) ){ int iPKey; if( truePk && (iPKey = sqlite3_column_int(pStmt,5))>0 ){ @@ -692,6 +722,7 @@ static void showHelp(void){ printf( "Output SQL text that would transform DB1 into DB2.\n" "Options:\n" +" --primarykey Use schema-defined PRIMARY KEYs\n" " --schema Show only differences in the schema\n" " --table TAB Show only differences in table TAB\n" ); @@ -720,6 +751,9 @@ int main(int argc, char **argv){ showHelp(); return 0; }else + if( strcmp(z,"primarykey")==0 ){ + g.bSchemaPK = 1; + }else if( strcmp(z,"schema")==0 ){ g.bSchemaOnly = 1; }else From 2139d252ddcaeb2e162b04694b912cb0b2148d4f Mon Sep 17 00:00:00 2001 From: drh Date: Thu, 9 Apr 2015 19:39:54 +0000 Subject: [PATCH 13/53] Fix incorrect column names in UPDATE statements generated by the sqldiff utility. FossilOrigin-Name: ee53b46011852e27db23708387fe1e918cc8284c --- manifest | 12 ++++++------ manifest.uuid | 2 +- tool/sqldiff.c | 2 +- 3 files changed, 8 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index d6f8442010..5b339e5c39 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\sthe\s--primarykey\soption\sto\sthe\ssqldiff\stool,\swhich\scauses\sit\sto\suse\sthe\nschema-defined\sPRIMARY\sKEY. -D 2015-04-09T18:14:03.130 +C Fix\sincorrect\scolumn\snames\sin\sUPDATE\sstatements\sgenerated\sby\sthe\ssqldiff\nutility. +D 2015-04-09T19:39:54.853 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -1239,7 +1239,7 @@ F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e F tool/split-sqlite3c.tcl d9be87f1c340285a3e081eb19b4a247981ed290c -F tool/sqldiff.c 9334ebc767dda9e02b904d4cbbd31cf8aaba3ca5 +F tool/sqldiff.c 050763654cb28d23c4d9516deb348c8632e432cd F tool/stack_usage.tcl f8e71b92cdb099a147dad572375595eae55eca43 F tool/symbols-mingw.sh 4dbcea7e74768305384c9fd2ed2b41bbf9f0414d F tool/symbols.sh fec58532668296d7c7dc48be9c87f75ccdb5814f @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 83b342a44ffc9ea07dc4d59f2866cefc68ee4f13 -R 80b4d61d5d12e62d07bcaa502c23a21f +P 5063f9070afde9374ea0f2bc338fee840d8b3dd4 +R b81a13af06affec3f4deb7b3b6092ef8 U drh -Z 965913d93d231505652de01e91883fad +Z 7a24354f8d3816810c976cc3a62d01ee diff --git a/manifest.uuid b/manifest.uuid index fda938f72a..56fcea9bbf 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -5063f9070afde9374ea0f2bc338fee840d8b3dd4 \ No newline at end of file +ee53b46011852e27db23708387fe1e918cc8284c \ No newline at end of file diff --git a/tool/sqldiff.c b/tool/sqldiff.c index 28b66b2c37..53c5977ed4 100644 --- a/tool/sqldiff.c +++ b/tool/sqldiff.c @@ -658,7 +658,7 @@ static void diff_one_table(const char *zTab){ zSep = " SET"; for(i=nPk+1; i Date: Fri, 10 Apr 2015 07:55:07 +0000 Subject: [PATCH 14/53] Do not allow virtual table constructors to be called recursively. FossilOrigin-Name: 0a72726da21581ab16cb3e964bd825b8f2e931e4 --- ext/fts3/fts3.c | 8 ++++++-- manifest | 18 +++++++++--------- manifest.uuid | 2 +- src/vtab.c | 33 +++++++++++++++++++++++++-------- test/fts4content.test | 18 ++++++++++++++++-- 5 files changed, 57 insertions(+), 22 deletions(-) diff --git a/ext/fts3/fts3.c b/ext/fts3/fts3.c index 7a15379b83..42b9663a1b 100644 --- a/ext/fts3/fts3.c +++ b/ext/fts3/fts3.c @@ -1019,7 +1019,8 @@ static int fts3ContentColumns( const char *zTbl, /* Name of content table */ const char ***pazCol, /* OUT: Malloc'd array of column names */ int *pnCol, /* OUT: Size of array *pazCol */ - int *pnStr /* OUT: Bytes of string content */ + int *pnStr, /* OUT: Bytes of string content */ + char **pzErr /* OUT: error message */ ){ int rc = SQLITE_OK; /* Return code */ char *zSql; /* "SELECT *" statement on zTbl */ @@ -1030,6 +1031,9 @@ static int fts3ContentColumns( rc = SQLITE_NOMEM; }else{ rc = sqlite3_prepare(db, zSql, -1, &pStmt, 0); + if( rc!=SQLITE_OK ){ + *pzErr = sqlite3_mprintf("%s", sqlite3_errmsg(db)); + } } sqlite3_free(zSql); @@ -1281,7 +1285,7 @@ static int fts3InitVtab( if( nCol==0 ){ sqlite3_free((void*)aCol); aCol = 0; - rc = fts3ContentColumns(db, argv[1], zContent, &aCol, &nCol, &nString); + rc = fts3ContentColumns(db, argv[1], zContent,&aCol,&nCol,&nString,pzErr); /* If a languageid= option was specified, remove the language id ** column from the aCol[] array. */ diff --git a/manifest b/manifest index 5b339e5c39..b5170f2282 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sincorrect\scolumn\snames\sin\sUPDATE\sstatements\sgenerated\sby\sthe\ssqldiff\nutility. -D 2015-04-09T19:39:54.853 +C Do\snot\sallow\svirtual\stable\sconstructors\sto\sbe\scalled\srecursively. +D 2015-04-10T07:55:07.186 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -78,7 +78,7 @@ F ext/fts3/README.content fdc666a70d5257a64fee209f97cf89e0e6e32b51 F ext/fts3/README.syntax a19711dc5458c20734b8e485e75fb1981ec2427a F ext/fts3/README.tokenizers e0a8b81383ea60d0334d274fadf305ea14a8c314 F ext/fts3/README.txt 8c18f41574404623b76917b9da66fcb0ab38328d -F ext/fts3/fts3.c 23bd9d37a777342f5c22a648e9b4b005dde9e58f +F ext/fts3/fts3.c 57d863c3bd360e575ecc293570af7c9b0bdd2209 F ext/fts3/fts3.h 3a10a0af180d502cecc50df77b1b22df142817fe F ext/fts3/fts3Int.h 394858c12a17740f7a1f6bd372c4606d4425a8d1 F ext/fts3/fts3_aux.c 5c211e17a64885faeb16b9ba7772f9d5445c2365 @@ -302,7 +302,7 @@ F src/vdbeblob.c 4f2e8e075d238392df98c5e03a64342465b03f90 F src/vdbemem.c c0dc81285b7571b0a31c40f17846fe2397ec1cd9 F src/vdbesort.c 919717d7599fa31d343ec28bffd0f9e91a4ff5f6 F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 -F src/vtab.c 62d49237bd8f3be4863815a39387b0f9897fa5e1 +F src/vtab.c ff722a886ed61e2e2889ee221b0a4f6dcaabb8e1 F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb F src/wal.c 878c8e1a51cb2ec45c395d26b7d5cd9e1a098e4a F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 @@ -606,7 +606,7 @@ F test/fts3tok_err.test 52273cd193b9036282f7bacb43da78c6be87418d F test/fts3varint.test 752c08ed5d32c5d7dc211b056f4ed68a76b7e36e F test/fts4aa.test 10aac8e9d62c7357590acfabe3fad01e9a9ce1cb F test/fts4check.test 74d77f6cdb768ac49df5afda575cef14ae3d239a -F test/fts4content.test 2e7252557d6d24afa101d9ba1de710d6140e6d06 +F test/fts4content.test abb0c77bc3da3df64fec72e00844d2257a90025d F test/fts4docid.test e33c383cfbdff0284685604d256f347a18fdbf01 F test/fts4growth.test df10fde9f47cf5c71861e63fd8efcd573c4f7e53 F test/fts4growth2.test 2f063be1902a73cd087355837c52fed42ac11a5d @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 5063f9070afde9374ea0f2bc338fee840d8b3dd4 -R b81a13af06affec3f4deb7b3b6092ef8 -U drh -Z 7a24354f8d3816810c976cc3a62d01ee +P ee53b46011852e27db23708387fe1e918cc8284c +R 7e9242555b174ae9f2c42129917fe80c +U dan +Z a71357da8ab26f740f6d9ebc28389132 diff --git a/manifest.uuid b/manifest.uuid index 56fcea9bbf..6d3ce3f223 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -ee53b46011852e27db23708387fe1e918cc8284c \ No newline at end of file +0a72726da21581ab16cb3e964bd825b8f2e931e4 \ No newline at end of file diff --git a/src/vtab.c b/src/vtab.c index 23f49bafce..d17aa147de 100644 --- a/src/vtab.c +++ b/src/vtab.c @@ -24,6 +24,8 @@ struct VtabCtx { VTable *pVTable; /* The virtual table being constructed */ Table *pTab; /* The Table object to which the virtual table belongs */ + VtabCtx *pPrior; /* Parent context (if any) */ + int bDeclared; /* True after sqlite3_declare_vtab() is called */ }; /* @@ -487,15 +489,27 @@ static int vtabCallConstructor( int (*xConstruct)(sqlite3*,void*,int,const char*const*,sqlite3_vtab**,char**), char **pzErr ){ - VtabCtx sCtx, *pPriorCtx; + VtabCtx sCtx; VTable *pVTable; int rc; const char *const*azArg = (const char *const*)pTab->azModuleArg; int nArg = pTab->nModuleArg; char *zErr = 0; - char *zModuleName = sqlite3MPrintf(db, "%s", pTab->zName); + char *zModuleName; int iDb; + VtabCtx *pCtx; + /* Check that the virtual-table is not already being initialized */ + for(pCtx=db->pVtabCtx; pCtx; pCtx=pCtx->pPrior){ + if( pCtx->pTab==pTab ){ + *pzErr = sqlite3MPrintf(db, + "vtable constructor called recursively: %s", pTab->zName + ); + return SQLITE_LOCKED; + } + } + + zModuleName = sqlite3MPrintf(db, "%s", pTab->zName); if( !zModuleName ){ return SQLITE_NOMEM; } @@ -516,11 +530,13 @@ static int vtabCallConstructor( assert( xConstruct ); sCtx.pTab = pTab; sCtx.pVTable = pVTable; - pPriorCtx = db->pVtabCtx; + sCtx.pPrior = db->pVtabCtx; + sCtx.bDeclared = 0; db->pVtabCtx = &sCtx; rc = xConstruct(db, pMod->pAux, nArg, azArg, &pVTable->pVtab, &zErr); - db->pVtabCtx = pPriorCtx; + db->pVtabCtx = sCtx.pPrior; if( rc==SQLITE_NOMEM ) db->mallocFailed = 1; + assert( sCtx.pTab==pTab ); if( SQLITE_OK!=rc ){ if( zErr==0 ){ @@ -536,7 +552,7 @@ static int vtabCallConstructor( memset(pVTable->pVtab, 0, sizeof(pVTable->pVtab[0])); pVTable->pVtab->pModule = pMod->pModule; pVTable->nRef = 1; - if( sCtx.pTab ){ + if( sCtx.bDeclared==0 ){ const char *zFormat = "vtable constructor did not declare schema: %s"; *pzErr = sqlite3MPrintf(db, zFormat, pTab->zName); sqlite3VtabUnlock(pVTable); @@ -706,8 +722,8 @@ int sqlite3VtabCallCreate(sqlite3 *db, int iDb, const char *zTab, char **pzErr){ ** virtual table module. */ int sqlite3_declare_vtab(sqlite3 *db, const char *zCreateTable){ + VtabCtx *pCtx = db->pVtabCtx; Parse *pParse; - int rc = SQLITE_OK; Table *pTab; char *zErr = 0; @@ -718,11 +734,12 @@ int sqlite3_declare_vtab(sqlite3 *db, const char *zCreateTable){ } #endif sqlite3_mutex_enter(db->mutex); - if( !db->pVtabCtx || !(pTab = db->pVtabCtx->pTab) ){ + if( !pCtx || pCtx->bDeclared ){ sqlite3Error(db, SQLITE_MISUSE); sqlite3_mutex_leave(db->mutex); return SQLITE_MISUSE_BKPT; } + pTab = pCtx->pTab; assert( (pTab->tabFlags & TF_Virtual)!=0 ); pParse = sqlite3StackAllocZero(db, sizeof(*pParse)); @@ -745,7 +762,7 @@ int sqlite3_declare_vtab(sqlite3 *db, const char *zCreateTable){ pParse->pNewTable->nCol = 0; pParse->pNewTable->aCol = 0; } - db->pVtabCtx->pTab = 0; + pCtx->bDeclared = 1; }else{ sqlite3ErrorWithMsg(db, SQLITE_ERROR, (zErr ? "%s" : 0), zErr); sqlite3DbFree(db, zErr); diff --git a/test/fts4content.test b/test/fts4content.test index 6b2cd3cc8e..481c6ec008 100644 --- a/test/fts4content.test +++ b/test/fts4content.test @@ -48,6 +48,9 @@ ifcapable !fts3 { # # 9.* - Test using content=xxx where xxx is a virtual table. # +# 11.* - Test that circular references (e.g. "t1(content=t1)") are +# detected. +# do_execsql_test 1.1.1 { CREATE TABLE t1(a, b, c); @@ -406,7 +409,7 @@ do_execsql_test 5.1.7 { # do_catchsql_test 6.1.1 { CREATE VIRTUAL TABLE ft7 USING fts4(content=t7); -} {1 {vtable constructor failed: ft7}} +} {1 {no such table: main.t7}} do_execsql_test 6.2.1 { CREATE TABLE t7(one, two); @@ -433,7 +436,7 @@ do_execsql_test 6.2.3 { } do_catchsql_test 6.2.4 { SELECT * FROM ft7; -} {1 {vtable constructor failed: ft7}} +} {1 {no such table: main.t7}} do_execsql_test 6.2.5 { CREATE TABLE t7(x, y); INSERT INTO t7 VALUES('A B', 'B A'); @@ -622,4 +625,15 @@ do_execsql_test 10.7 { {...c d [e] f g...} } +#------------------------------------------------------------------------- +# Test cases 11.* +# +reset_db + +do_catchsql_test 11.1 { + CREATE VIRTUAL TABLE x1 USING fts4(content=x1); +} {1 {vtable constructor called recursively: x1}} + + finish_test + From e918aaba981efb7ec5cca88ca8ae4d509ca84367 Mon Sep 17 00:00:00 2001 From: drh Date: Fri, 10 Apr 2015 12:04:57 +0000 Subject: [PATCH 15/53] Fix foreign key CASCADE for cases where the parent key is an INTEGER PRIMARY KEY and the parent table contains other columns named "rowid", "_rowid_", and "oid". FossilOrigin-Name: ed3cbaab6ad49b0cb5b17e44def26c866919387a --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/fkey.c | 3 ++- test/fkey2.test | 4 ++-- 4 files changed, 13 insertions(+), 12 deletions(-) diff --git a/manifest b/manifest index b5170f2282..b70c671a51 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Do\snot\sallow\svirtual\stable\sconstructors\sto\sbe\scalled\srecursively. -D 2015-04-10T07:55:07.186 +C Fix\sforeign\skey\sCASCADE\sfor\scases\swhere\sthe\sparent\skey\sis\san\sINTEGER\sPRIMARY\nKEY\sand\sthe\sparent\stable\scontains\sother\scolumns\snamed\s"rowid",\s"_rowid_",\nand\s"oid". +D 2015-04-10T12:04:57.414 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -184,7 +184,7 @@ F src/date.c e4d50b3283696836ec1036b695ead9a19e37a5ac F src/delete.c 37964e6c1d73ff49cbea9ff690c9605fb15f600e F src/expr.c d09dac67d53c78880ba31d56e8ba2be3a6490553 F src/fault.c 160a0c015b6c2629d3899ed2daf63d75754a32bb -F src/fkey.c e0444b61bed271a76840cbe6182df93a9baa3f12 +F src/fkey.c 3343d551a8d810782257244fb33f2ce191493c39 F src/func.c 1414c24c873c48796ad45942257a179a423ba42f F src/global.c 4f77cadbc5427d00139ba43d0f3979804cbb700e F src/hash.c 4263fbc955f26c2e8cdc0cf214bc42435aa4e4f5 @@ -505,7 +505,7 @@ F test/fallocate.test 3e979af17dfa7e5e9dda5eba1a696c04fa9d47f7 F test/filectrl.test 14fa712e42c4cb791e09dfd58a6a03efb47ef13a F test/filefmt.test cb34663f126cbc2d358af552dcaf5c72769b0146 F test/fkey1.test e1d1fa84cde579185ea01358436839703e415a5b -F test/fkey2.test 1db212cda86b0d3ce72714001f7b6381c321341c +F test/fkey2.test 223c624e7eccee21e89c98d4d127ac88d774b940 F test/fkey3.test 76d475c80b84ee7a5d062e56ccb6ea68882e2b49 F test/fkey4.test 86446017011273aad8f9a99c1a65019e7bd9ca9d F test/fkey5.test 56bcb5a6e8b725b17febc267fb041a6695e86853 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P ee53b46011852e27db23708387fe1e918cc8284c -R 7e9242555b174ae9f2c42129917fe80c -U dan -Z a71357da8ab26f740f6d9ebc28389132 +P 0a72726da21581ab16cb3e964bd825b8f2e931e4 +R b2dde8f542352409005b61e29f91d905 +U drh +Z 7c6c1370c12f07a8520590c209ac9901 diff --git a/manifest.uuid b/manifest.uuid index 6d3ce3f223..33b43c8925 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -0a72726da21581ab16cb3e964bd825b8f2e931e4 \ No newline at end of file +ed3cbaab6ad49b0cb5b17e44def26c866919387a \ No newline at end of file diff --git a/src/fkey.c b/src/fkey.c index fa148ba6a3..3e4b752e86 100644 --- a/src/fkey.c +++ b/src/fkey.c @@ -1184,7 +1184,8 @@ static Trigger *fkActionTrigger( iFromCol = aiCol ? aiCol[i] : pFKey->aCol[0].iFrom; assert( iFromCol>=0 ); - tToCol.z = pIdx ? pTab->aCol[pIdx->aiColumn[i]].zName : "oid"; + assert( pIdx!=0 || (pTab->iPKey>=0 && pTab->iPKeynCol) ); + tToCol.z = pTab->aCol[pIdx ? pIdx->aiColumn[i] : pTab->iPKey].zName; tFromCol.z = pFKey->pFrom->aCol[iFromCol].zName; tToCol.n = sqlite3Strlen30(tToCol.z); diff --git a/test/fkey2.test b/test/fkey2.test index 53b90dc91c..8b2871e5a6 100644 --- a/test/fkey2.test +++ b/test/fkey2.test @@ -746,10 +746,10 @@ do_test fkey2-10.2.2 { drop_all_tables do_test fkey2-11.1.1 { execsql { - CREATE TABLE t1(a INTEGER PRIMARY KEY, b); + CREATE TABLE t1(a INTEGER PRIMARY KEY, b, rowid, _rowid_, oid); CREATE TABLE t2(c, d, FOREIGN KEY(c) REFERENCES t1(a) ON UPDATE CASCADE); - INSERT INTO t1 VALUES(10, 100); + INSERT INTO t1 VALUES(10, 100, 'abc', 'def', 'ghi'); INSERT INTO t2 VALUES(10, 100); UPDATE t1 SET a = 15; SELECT * FROM t2; From 4e23536e56f283bd8cf0d787dd9e76e7176435f0 Mon Sep 17 00:00:00 2001 From: dan Date: Fri, 10 Apr 2015 16:05:33 +0000 Subject: [PATCH 16/53] In sqlite3_declare_vtab(), avoid accessing the database structure until after the "api-armour" safety-check has completed and the db mutex has been obtained. FossilOrigin-Name: 860e4f8a94901d451fac3954960c1d2f589e8882 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/vtab.c | 3 ++- 3 files changed, 10 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index b70c671a51..a4b1b68367 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sforeign\skey\sCASCADE\sfor\scases\swhere\sthe\sparent\skey\sis\san\sINTEGER\sPRIMARY\nKEY\sand\sthe\sparent\stable\scontains\sother\scolumns\snamed\s"rowid",\s"_rowid_",\nand\s"oid". -D 2015-04-10T12:04:57.414 +C In\ssqlite3_declare_vtab(),\savoid\saccessing\sthe\sdatabase\sstructure\suntil\safter\sthe\s"api-armour"\ssafety-check\shas\scompleted\sand\sthe\sdb\smutex\shas\sbeen\sobtained. +D 2015-04-10T16:05:33.033 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -302,7 +302,7 @@ F src/vdbeblob.c 4f2e8e075d238392df98c5e03a64342465b03f90 F src/vdbemem.c c0dc81285b7571b0a31c40f17846fe2397ec1cd9 F src/vdbesort.c 919717d7599fa31d343ec28bffd0f9e91a4ff5f6 F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 -F src/vtab.c ff722a886ed61e2e2889ee221b0a4f6dcaabb8e1 +F src/vtab.c 9ca557215e8591ceb66e0b7c0a579c6df1e54b2d F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb F src/wal.c 878c8e1a51cb2ec45c395d26b7d5cd9e1a098e4a F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 0a72726da21581ab16cb3e964bd825b8f2e931e4 -R b2dde8f542352409005b61e29f91d905 -U drh -Z 7c6c1370c12f07a8520590c209ac9901 +P ed3cbaab6ad49b0cb5b17e44def26c866919387a +R f962720dd8c90d63a1a200cd065fa312 +U dan +Z 666766483214acd3a759f5cb43f45fc3 diff --git a/manifest.uuid b/manifest.uuid index 33b43c8925..909c5925c5 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -ed3cbaab6ad49b0cb5b17e44def26c866919387a \ No newline at end of file +860e4f8a94901d451fac3954960c1d2f589e8882 \ No newline at end of file diff --git a/src/vtab.c b/src/vtab.c index d17aa147de..9629a00dcb 100644 --- a/src/vtab.c +++ b/src/vtab.c @@ -722,7 +722,7 @@ int sqlite3VtabCallCreate(sqlite3 *db, int iDb, const char *zTab, char **pzErr){ ** virtual table module. */ int sqlite3_declare_vtab(sqlite3 *db, const char *zCreateTable){ - VtabCtx *pCtx = db->pVtabCtx; + VtabCtx *pCtx; Parse *pParse; int rc = SQLITE_OK; Table *pTab; @@ -734,6 +734,7 @@ int sqlite3_declare_vtab(sqlite3 *db, const char *zCreateTable){ } #endif sqlite3_mutex_enter(db->mutex); + pCtx = db->pVtabCtx; if( !pCtx || pCtx->bDeclared ){ sqlite3Error(db, SQLITE_MISUSE); sqlite3_mutex_leave(db->mutex); From 83e63dc3857dbb2220090ef0cd3541cef2189aa3 Mon Sep 17 00:00:00 2001 From: drh Date: Fri, 10 Apr 2015 19:41:18 +0000 Subject: [PATCH 17/53] Work toward adding the --changeset option to the sqldiff utility program. Changes are incomplete. This is an incremental check-in. FossilOrigin-Name: 463e38d765f9d055b63792a8ea15c3782657b07f --- manifest | 17 ++++--- manifest.uuid | 2 +- tool/sqldiff.c | 126 ++++++++++++++++++++++++++++++++++++++++++++++++- 3 files changed, 135 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index a4b1b68367..c7c3d03725 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C In\ssqlite3_declare_vtab(),\savoid\saccessing\sthe\sdatabase\sstructure\suntil\safter\sthe\s"api-armour"\ssafety-check\shas\scompleted\sand\sthe\sdb\smutex\shas\sbeen\sobtained. -D 2015-04-10T16:05:33.033 +C Work\stoward\sadding\sthe\s--changeset\soption\sto\sthe\ssqldiff\sutility\sprogram.\nChanges\sare\sincomplete.\s\sThis\sis\san\sincremental\scheck-in. +D 2015-04-10T19:41:18.818 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -1239,7 +1239,7 @@ F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e F tool/split-sqlite3c.tcl d9be87f1c340285a3e081eb19b4a247981ed290c -F tool/sqldiff.c 050763654cb28d23c4d9516deb348c8632e432cd +F tool/sqldiff.c 3e6f54359a070089ed0d11456e8868dcd3f20e94 F tool/stack_usage.tcl f8e71b92cdb099a147dad572375595eae55eca43 F tool/symbols-mingw.sh 4dbcea7e74768305384c9fd2ed2b41bbf9f0414d F tool/symbols.sh fec58532668296d7c7dc48be9c87f75ccdb5814f @@ -1250,7 +1250,10 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P ed3cbaab6ad49b0cb5b17e44def26c866919387a -R f962720dd8c90d63a1a200cd065fa312 -U dan -Z 666766483214acd3a759f5cb43f45fc3 +P 860e4f8a94901d451fac3954960c1d2f589e8882 +R 6c8da3b8e133d42c3c0048f2d2a47a98 +T *branch * sqldiff-changeset +T *sym-sqldiff-changeset * +T -sym-trunk * +U drh +Z b58ac33ed90e0dd7edcdd56b18b68a1d diff --git a/manifest.uuid b/manifest.uuid index 909c5925c5..324240a04b 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -860e4f8a94901d451fac3954960c1d2f589e8882 \ No newline at end of file +463e38d765f9d055b63792a8ea15c3782657b07f \ No newline at end of file diff --git a/tool/sqldiff.c b/tool/sqldiff.c index 53c5977ed4..2b46353535 100644 --- a/tool/sqldiff.c +++ b/tool/sqldiff.c @@ -714,6 +714,113 @@ end_diff_one_table: return; } +/* +** Generate a CHANGESET for all differences from main.zTab to aux.zTab. +*/ +static void changeset_one_table(const char *zTab, FILE *out){ + sqlite3_stmt *pStmt; /* SQL statment */ + char *zId = safeId(zTab); /* Escaped name of the table */ + char **azCol = 0; /* List of escaped column names */ + int nCol = 0; /* Number of columns */ + int *aiFlg = 0; /* 0 if column is not part of PK */ + int *aiPk = 0; /* Column numbers for each PK column */ + int nPk = 0; /* Number of PRIMARY KEY columns */ + Str sql; /* SQL for the diff query */ + int i; /* Loop counter */ + const char *zSep; /* List separator */ + + pStmt = db_prepare( + "SELECT A.sql=B.sql FROM main.sqlite_master A, aux.sqlite_master B" + " WHERE A.name=%Q AND B.name=%Q", zTab, zTab + ); + if( SQLITE_ROW==sqlite3_step(pStmt) ){ + if( sqlite3_column_int(pStmt,0)==0 ){ + runtimeError("schema changes for table %s", safeId(zTab)); + } + }else{ + runtimeError("table %s missing from one or both databases", safeId(zTab)); + } + sqlite3_finalize(pStmt); + pStmt = db_prepare("PRAGMA main.table_info=%Q", zTab); + while( SQLITE_ROW==sqlite3_step(pStmt) ){ + nCol++; + azCol = sqlite3_realloc(azCol, sizeof(char*)*nCol); + if( azCol==0 ) runtimeError("out of memory"); + aiFlg = sqlite3_realloc(aiFlg, sizeof(int)*nCol); + if( aiFlg==0 ) runtimeError("out of memory"); + azCol[nCol-1] = safeId((const char*)sqlite3_column_text(pStmt,1)); + aiFlg[nCol-1] = i = sqlite3_column_int(pStmt,5); + if( i>0 ){ + if( i>nPk ){ + nPk = i; + aiPk = sqlite3_realloc(aiPk, sizeof(int)*nPk); + if( aiPk==0 ) runtimeError("out of memory"); + } + aiPk[i-1] = nCol-1; + } + } + sqlite3_finalize(pStmt); + if( nPk==0 ) goto end_changeset_one_table; + strInit(&sql); + if( nCol>nPk ){ + strPrintf(&sql, "SELECT 1"); /* Changes to non-PK columns */ + for(i=0; i0 ) sqlite3_free(azCol[--nCol]); + sqlite3_free(azCol); + sqlite3_free(aiPk); + sqlite3_free(zId); +} + /* ** Print sketchy documentation for this utility program */ @@ -722,6 +829,7 @@ static void showHelp(void){ printf( "Output SQL text that would transform DB1 into DB2.\n" "Options:\n" +" --changeset FILE Write a CHANGESET into FILE\n" " --primarykey Use schema-defined PRIMARY KEYs\n" " --schema Show only differences in the schema\n" " --table TAB Show only differences in table TAB\n" @@ -737,6 +845,7 @@ int main(int argc, char **argv){ char *zSql; sqlite3_stmt *pStmt; char *zTab = 0; + FILE *out = 0; g.zArgv0 = argv[0]; for(i=1; i Date: Fri, 10 Apr 2015 21:16:11 +0000 Subject: [PATCH 18/53] Minor build enhancements for MSVC. FossilOrigin-Name: 40c417a7efb17221cec4a0a703863854bcab8db2 --- Makefile.msc | 6 ++++-- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/msvc.h | 1 + 4 files changed, 14 insertions(+), 11 deletions(-) diff --git a/Makefile.msc b/Makefile.msc index b49a3eb0e1..7ea110e7dd 100644 --- a/Makefile.msc +++ b/Makefile.msc @@ -42,8 +42,8 @@ DYNAMIC_SHELL = 0 # !IFNDEF NO_WARN !IF $(USE_FULLWARN)!=0 -NO_WARN = -wd4054 -wd4055 -wd4100 -wd4127 -wd4152 -wd4189 -wd4206 -wd4210 -NO_WARN = $(NO_WARN) -wd4232 -wd4244 -wd4305 -wd4306 -wd4702 -wd4706 +NO_WARN = -wd4054 -wd4055 -wd4100 -wd4127 -wd4130 -wd4152 -wd4189 -wd4206 +NO_WARN = $(NO_WARN) -wd4210 -wd4232 -wd4244 -wd4305 -wd4306 -wd4702 -wd4706 !ENDIF !ENDIF @@ -453,11 +453,13 @@ RCC = $(RCC) -I$(TOP)\ext\rtree # options are necessary in order to allow debugging symbols to # work correctly with Visual Studio when using the amalgamation. # +!IFNDEF MKSQLITE3C_ARGS !IF $(DEBUG)>1 MKSQLITE3C_ARGS = --linemacros !ELSE MKSQLITE3C_ARGS = !ENDIF +!ENDIF # Define -DNDEBUG to compile without debugging (i.e., for production usage) # Omitting the define will cause extra debugging code to be inserted and diff --git a/manifest b/manifest index a4b1b68367..d9f7505d75 100644 --- a/manifest +++ b/manifest @@ -1,9 +1,9 @@ -C In\ssqlite3_declare_vtab(),\savoid\saccessing\sthe\sdatabase\sstructure\suntil\safter\sthe\s"api-armour"\ssafety-check\shas\scompleted\sand\sthe\sdb\smutex\shas\sbeen\sobtained. -D 2015-04-10T16:05:33.033 +C Minor\sbuild\senhancements\sfor\sMSVC. +D 2015-04-10T21:16:11.659 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 -F Makefile.msc fa6a6de11af800d89f86e8a4266fd40a46008347 +F Makefile.msc 0078f5781538e07ea38683439f38d5f5ab79ab6e F Makefile.vxworks e1b65dea203f054e71653415bd8f96dcaed47858 F README.md d58e3bebc0a4145e0f2a87994015fdb575a8e866 F VERSION 319eb1ced4b4d17a67730f2b7b85f15c1346cb60 @@ -203,7 +203,7 @@ F src/mem2.c f1940d9e91948dd6a908fbb9ce3835c36b5d83c3 F src/mem3.c 61c9d47b792908c532ca3a62b999cf21795c6534 F src/mem5.c 61eeb90134f9a5be6c2e68d8daae7628b25953fb F src/memjournal.c 3eb2c0b51adbd869cb6a44780323f05fa904dc85 -F src/msvc.h e78002098966e39b2fd9915bd70b7bc3ec8398b7 +F src/msvc.h d9ba56c6851227ab44b3f228a35f3f5772296495 F src/mutex.c 19bf9acba69ca2f367c3761080f8a9f0cf4670a8 F src/mutex.h 779d588e3b7756ec3ecf7d78cde1d84aba414f85 F src/mutex_noop.c 529bab0743c3321c940f32c3464de494fd38cfa9 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P ed3cbaab6ad49b0cb5b17e44def26c866919387a -R f962720dd8c90d63a1a200cd065fa312 -U dan -Z 666766483214acd3a759f5cb43f45fc3 +P 860e4f8a94901d451fac3954960c1d2f589e8882 +R d724f3837aa2139b84d99a7758232948 +U mistachkin +Z add6515d666dc387abaf063a7b8f0157 diff --git a/manifest.uuid b/manifest.uuid index 909c5925c5..5d2f5e3cb5 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -860e4f8a94901d451fac3954960c1d2f589e8882 \ No newline at end of file +40c417a7efb17221cec4a0a703863854bcab8db2 \ No newline at end of file diff --git a/src/msvc.h b/src/msvc.h index 4508e6941f..01ebf2b46f 100644 --- a/src/msvc.h +++ b/src/msvc.h @@ -20,6 +20,7 @@ #pragma warning(disable : 4055) #pragma warning(disable : 4100) #pragma warning(disable : 4127) +#pragma warning(disable : 4130) #pragma warning(disable : 4152) #pragma warning(disable : 4189) #pragma warning(disable : 4206) From 4a33507f60067a91786065a082a28fd781753aa3 Mon Sep 17 00:00:00 2001 From: drh Date: Sat, 11 Apr 2015 02:08:48 +0000 Subject: [PATCH 19/53] Detect and report oversized records constructed from multiple zeroblobs. FossilOrigin-Name: 9e139afd92116ebc593114ed63b57c8f469653f6 --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/vdbe.c | 4 ++-- test/zeroblob.test | 9 +++++++++ 4 files changed, 20 insertions(+), 11 deletions(-) diff --git a/manifest b/manifest index d9f7505d75..71aafa2cb1 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Minor\sbuild\senhancements\sfor\sMSVC. -D 2015-04-10T21:16:11.659 +C Detect\sand\sreport\soversized\srecords\sconstructed\sfrom\smultiple\szeroblobs. +D 2015-04-11T02:08:48.265 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -293,7 +293,7 @@ F src/update.c 3c4ecc282accf12d39edb8d524cf089645e55a13 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 98a7627ca48ad3265b6940915a1d08355eb3fc7e F src/vacuum.c 9460b9de7b2d4e34b0d374894aa6c8a0632be8ec -F src/vdbe.c 86ae6f4774410868af41bd839b72b7081ff03e78 +F src/vdbe.c 06cc2cf42daf8b0c397f69a6fb1818124f3cd93a F src/vdbe.h 6fc69d9c5e146302c56e163cb4b31d1ee64a18c3 F src/vdbeInt.h 9cbaa84f53ddd2d09a0cf61a94337a3a035d08a0 F src/vdbeapi.c 583d56b129dd27f12bed518270de9ebe521e6a75 @@ -1194,7 +1194,7 @@ F test/without_rowid4.test 4e08bcbaee0399f35d58b5581881e7a6243d458a F test/without_rowid5.test 61256715b686359df48ca1742db50cc7e3e7b862 F test/without_rowid6.test db0dbf03c49030aa3c1ba5f618620334bd2baf5f F test/wordcount.c 9915e06cb33d8ca8109b8700791afe80d305afda -F test/zeroblob.test caaecfb4f908f7bc086ed238668049f96774d688 +F test/zeroblob.test fb3c0e4ab172d386954deda24c03f500e121d80d F test/zerodamage.test cf6748bad89553cc1632be51a6f54e487e4039ac F tool/build-all-msvc.bat 72e05bc8deca39a547884485c086b915f50a91ed x F tool/build-shell.sh 950f47c6174f1eea171319438b93ba67ff5bf367 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 860e4f8a94901d451fac3954960c1d2f589e8882 -R d724f3837aa2139b84d99a7758232948 -U mistachkin -Z add6515d666dc387abaf063a7b8f0157 +P 40c417a7efb17221cec4a0a703863854bcab8db2 +R fd7ff5723f566045f2ba0751ddce0467 +U drh +Z f6419661cff2a502b477cceb45bb8fdd diff --git a/manifest.uuid b/manifest.uuid index 5d2f5e3cb5..c8b77b78ce 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -40c417a7efb17221cec4a0a703863854bcab8db2 \ No newline at end of file +9e139afd92116ebc593114ed63b57c8f469653f6 \ No newline at end of file diff --git a/src/vdbe.c b/src/vdbe.c index f2de90d14c..8e7247a1e8 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -2578,7 +2578,7 @@ case OP_MakeRecord: { u64 nData; /* Number of bytes of data space */ int nHdr; /* Number of bytes of header space */ i64 nByte; /* Data space required for this record */ - int nZero; /* Number of zero bytes at the end of the record */ + i64 nZero; /* Number of zero bytes at the end of the record */ int nVarint; /* Number of bytes in a varint */ u32 serial_type; /* Type field */ Mem *pData0; /* First field to be combined into the record */ @@ -2670,7 +2670,7 @@ case OP_MakeRecord: { if( nVarintdb->aLimit[SQLITE_LIMIT_LENGTH] ){ + if( nByte+nZero>db->aLimit[SQLITE_LIMIT_LENGTH] ){ goto too_big; } diff --git a/test/zeroblob.test b/test/zeroblob.test index f4a1950836..e70fd0b748 100644 --- a/test/zeroblob.test +++ b/test/zeroblob.test @@ -255,5 +255,14 @@ do_test zeroblob-9.8 { db eval {SELECT zeroblob(2) IN (zeroblob(2))} } {1} +# Oversized zeroblob records +# +do_test zeroblob-10.1 { + db eval { + CREATE TABLE t10(a,b,c); + } + catchsql {INSERT INTO t10 VALUES(zeroblob(1e9),zeroblob(1e9),zeroblob(1e9))} +} {1 {string or blob too big}} + finish_test From 2813bde0280a022b7adb2f1d79033aa8de7358a5 Mon Sep 17 00:00:00 2001 From: dan Date: Sat, 11 Apr 2015 11:44:27 +0000 Subject: [PATCH 20/53] Do not assume an index contains unique entries unless it is declared UNIQUE and NOT NULL is specified for all columns. Fix for [7b4fee9f6c]. FossilOrigin-Name: e3b1f625518edc0e925116668dca5d25c3232b59 --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/where.c | 2 +- test/null.test | 17 +++++++++++++++++ 4 files changed, 27 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index 71aafa2cb1..55283a01c9 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Detect\sand\sreport\soversized\srecords\sconstructed\sfrom\smultiple\szeroblobs. -D 2015-04-11T02:08:48.265 +C Do\snot\sassume\san\sindex\scontains\sunique\sentries\sunless\sit\sis\sdeclared\sUNIQUE\sand\sNOT\sNULL\sis\sspecified\sfor\sall\scolumns.\sFix\sfor\s[7b4fee9f6c]. +D 2015-04-11T11:44:27.202 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -307,7 +307,7 @@ F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb F src/wal.c 878c8e1a51cb2ec45c395d26b7d5cd9e1a098e4a F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 85d832efa5ef57de542db7f430b72fecd3af8b38 +F src/where.c bd435b75b9de53e11b5eb561540e395041ac0cba F src/whereInt.h cbe4aa57326998d89e7698ca65bb7c28541d483c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -768,7 +768,7 @@ F test/notify1.test 669b2b743618efdc18ca4b02f45423d5d2304abf F test/notify2.test 2ecabaa1305083856b7c39cf32816b612740c161 F test/notify3.test 10ff25cde502e72a92053a2f215d64bece4ef934 F test/notnull.test f8fcf58669ddba79274daa2770d61dfad8274f62 -F test/null.test a8b09b8ed87852742343b33441a9240022108993 +F test/null.test 0dcce4f04284ec66108c503327ad6d224c0752b3 F test/numcast.test 5d126f7f581432e86a90d1e35cac625164aec4a1 F test/openv2.test 0d3040974bf402e19b7df4b783e447289d7ab394 F test/orderby1.test eb246e377612b21a418fbea57047ba8ea88aaa6b @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 40c417a7efb17221cec4a0a703863854bcab8db2 -R fd7ff5723f566045f2ba0751ddce0467 -U drh -Z f6419661cff2a502b477cceb45bb8fdd +P 9e139afd92116ebc593114ed63b57c8f469653f6 +R cb22563425ec3fdd92f04af95791ab8d +U dan +Z a8ae95b3c171e79da5c1dd8c91dd053d diff --git a/manifest.uuid b/manifest.uuid index c8b77b78ce..1f18603ac6 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -9e139afd92116ebc593114ed63b57c8f469653f6 \ No newline at end of file +e3b1f625518edc0e925116668dca5d25c3232b59 \ No newline at end of file diff --git a/src/where.c b/src/where.c index 921e683d98..a96d9e5add 100644 --- a/src/where.c +++ b/src/where.c @@ -4781,7 +4781,7 @@ static int whereLoopAddBtreeIndex( }else if( eOp & (WO_EQ) ){ pNew->wsFlags |= WHERE_COLUMN_EQ; if( iCol<0 || (nInMul==0 && pNew->u.btree.nEq==pProbe->nKeyCol-1) ){ - if( iCol>=0 && !IsUniqueIndex(pProbe) ){ + if( iCol>=0 && pProbe->uniqNotNull==0 ){ pNew->wsFlags |= WHERE_UNQ_WANTED; }else{ pNew->wsFlags |= WHERE_ONEROW; diff --git a/test/null.test b/test/null.test index f3782a7531..e8eeb9740b 100644 --- a/test/null.test +++ b/test/null.test @@ -278,6 +278,23 @@ do_test null-8.15 { } } {1} +do_execsql_test null-9.1 { + CREATE TABLE t5(a, b, c); + CREATE UNIQUE INDEX t5ab ON t5(a, b); + + INSERT INTO t5 VALUES(1, NULL, 'one'); + INSERT INTO t5 VALUES(1, NULL, 'i'); + INSERT INTO t5 VALUES(NULL, 'x', 'two'); + INSERT INTO t5 VALUES(NULL, 'x', 'ii'); +} + +do_execsql_test null-9.2 { + SELECT * FROM t5 WHERE a = 1 AND b IS NULL; +} {1 {} one 1 {} i} + +do_execsql_test null-9.3 { + SELECT * FROM t5 WHERE a IS NULL AND b = 'x'; +} {{} x two {} x ii} finish_test From 8aad8c482ce0eac0fb9245722d2a63ea490d6818 Mon Sep 17 00:00:00 2001 From: dan Date: Sat, 11 Apr 2015 11:53:39 +0000 Subject: [PATCH 21/53] Update tests in whereD.test to account for the change in the previous commit. FossilOrigin-Name: da49700ca148d91e1b8863c2eb6ee79144e83ac9 --- manifest | 12 ++++++------ manifest.uuid | 2 +- test/whereD.test | 14 +++++++------- 3 files changed, 14 insertions(+), 14 deletions(-) diff --git a/manifest b/manifest index 55283a01c9..378036e42a 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Do\snot\sassume\san\sindex\scontains\sunique\sentries\sunless\sit\sis\sdeclared\sUNIQUE\sand\sNOT\sNULL\sis\sspecified\sfor\sall\scolumns.\sFix\sfor\s[7b4fee9f6c]. -D 2015-04-11T11:44:27.202 +C Update\stests\sin\swhereD.test\sto\saccount\sfor\sthe\schange\sin\sthe\sprevious\scommit. +D 2015-04-11T11:53:39.984 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -1171,7 +1171,7 @@ F test/where9.test 729c3ba9b47e8f9f1aab96bae7dad2a524f1d1a2 F test/whereA.test 4d253178d135ec46d1671e440cd8f2b916aa6e6b F test/whereB.test 0def95db3bdec220a731c7e4bec5930327c1d8c5 F test/whereC.test d6f4ecd4fa2d9429681a5b22a25d2bda8e86ab8a -F test/whereD.test fd9120e262f9da3c45940f52aefeef4d15b904e5 +F test/whereD.test 9eba1f9b18e5b19a0b0bcaae5e8c037260195f2b F test/whereE.test b3a055eef928c992b0a33198a7b8dc10eea5ad2f F test/whereF.test 5b2ba0dbe8074aa13e416b37c753991f0a2492d7 F test/whereG.test 69f5ec4b15760a8c860f80e2d55525669390aab3 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 9e139afd92116ebc593114ed63b57c8f469653f6 -R cb22563425ec3fdd92f04af95791ab8d +P e3b1f625518edc0e925116668dca5d25c3232b59 +R 7890e1f1fdfc32123135ecc1b57978ea U dan -Z a8ae95b3c171e79da5c1dd8c91dd053d +Z 68688658f813a09121106ccdd49ce975 diff --git a/manifest.uuid b/manifest.uuid index 1f18603ac6..f330c7ddcf 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -e3b1f625518edc0e925116668dca5d25c3232b59 \ No newline at end of file +da49700ca148d91e1b8863c2eb6ee79144e83ac9 \ No newline at end of file diff --git a/test/whereD.test b/test/whereD.test index db993040b0..17fdac7017 100644 --- a/test/whereD.test +++ b/test/whereD.test @@ -129,11 +129,11 @@ do_execsql_test 3.0 { do_searchcount_test 3.1 { SELECT a, b FROM t3 WHERE (a=1 AND b='one') OR (a=2 AND b='two') -} {1 one 2 two search 2} +} {1 one 2 two search 4} do_searchcount_test 3.2 { SELECT a, c FROM t3 WHERE (a=1 AND b='one') OR (a=2 AND b='two') -} {1 i 2 ii search 4} +} {1 i 2 ii search 6} do_searchcount_test 3.4.1 { SELECT y FROM t4 WHERE x='a' @@ -142,24 +142,24 @@ do_searchcount_test 3.4.2 { SELECT a, b FROM t3 WHERE (a=1 AND b=(SELECT y FROM t4 WHERE x='a')) OR (a=2 AND b='two') -} {1 one 2 two search 4} +} {1 one 2 two search 6} do_searchcount_test 3.4.3 { SELECT a, b FROM t3 WHERE (a=2 AND b='two') OR (a=1 AND b=(SELECT y FROM t4 WHERE x='a')) -} {2 two 1 one search 4} +} {2 two 1 one search 6} do_searchcount_test 3.4.4 { SELECT a, b FROM t3 WHERE (a=2 AND b=(SELECT y FROM t4 WHERE x='b')) OR (a=1 AND b=(SELECT y FROM t4 WHERE x='a')) -} {2 two 1 one search 6} +} {2 two 1 one search 8} do_searchcount_test 3.5.1 { SELECT a, b FROM t3 WHERE (a=1 AND b='one') OR rowid=4 -} {1 one 2 two search 2} +} {1 one 2 two search 3} do_searchcount_test 3.5.2 { SELECT a, c FROM t3 WHERE (a=1 AND b='one') OR rowid=4 -} {1 i 2 ii search 2} +} {1 i 2 ii search 3} # Ticket [d02e1406a58ea02d] (2012-10-04) # LEFT JOIN with an OR in the ON clause causes segfault From 697e5dba801332f9e412868c593b8f58fc713844 Mon Sep 17 00:00:00 2001 From: drh Date: Sat, 11 Apr 2015 12:07:40 +0000 Subject: [PATCH 22/53] First complete attempt to generate a working changeset. Still contains bugs. FossilOrigin-Name: 5611fa9bd5b8fd762d16ce9b0853c2e779a1a1b7 --- manifest | 15 ++++----- manifest.uuid | 2 +- tool/sqldiff.c | 87 ++++++++++++++++++++++++++++++++++++++++++++++---- 3 files changed, 87 insertions(+), 17 deletions(-) diff --git a/manifest b/manifest index c7c3d03725..f2c0b806d6 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Work\stoward\sadding\sthe\s--changeset\soption\sto\sthe\ssqldiff\sutility\sprogram.\nChanges\sare\sincomplete.\s\sThis\sis\san\sincremental\scheck-in. -D 2015-04-10T19:41:18.818 +C First\scomplete\sattempt\sto\sgenerate\sa\sworking\schangeset.\s\sStill\scontains\sbugs. +D 2015-04-11T12:07:40.414 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -1239,7 +1239,7 @@ F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e F tool/split-sqlite3c.tcl d9be87f1c340285a3e081eb19b4a247981ed290c -F tool/sqldiff.c 3e6f54359a070089ed0d11456e8868dcd3f20e94 +F tool/sqldiff.c ed945df30d962d15d26188e33f7c5431cf197487 F tool/stack_usage.tcl f8e71b92cdb099a147dad572375595eae55eca43 F tool/symbols-mingw.sh 4dbcea7e74768305384c9fd2ed2b41bbf9f0414d F tool/symbols.sh fec58532668296d7c7dc48be9c87f75ccdb5814f @@ -1250,10 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 860e4f8a94901d451fac3954960c1d2f589e8882 -R 6c8da3b8e133d42c3c0048f2d2a47a98 -T *branch * sqldiff-changeset -T *sym-sqldiff-changeset * -T -sym-trunk * +P 463e38d765f9d055b63792a8ea15c3782657b07f +R c7ffcaee222b675f0ec3e43f31931e14 U drh -Z b58ac33ed90e0dd7edcdd56b18b68a1d +Z c4472641aefb50d8b597b0b444fecd27 diff --git a/manifest.uuid b/manifest.uuid index 324240a04b..4657a0c7e9 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -463e38d765f9d055b63792a8ea15c3782657b07f \ No newline at end of file +5611fa9bd5b8fd762d16ce9b0853c2e779a1a1b7 \ No newline at end of file diff --git a/tool/sqldiff.c b/tool/sqldiff.c index 2b46353535..d166174440 100644 --- a/tool/sqldiff.c +++ b/tool/sqldiff.c @@ -714,6 +714,31 @@ end_diff_one_table: return; } +/* +** Write a 64-bit signed integer as a varint onto out +*/ +static void putsVarint(FILE *out, sqlite3_uint64 v){ + int i, n; + unsigned char buf[12], p[12]; + if( v & (((sqlite3_uint64)0xff000000)<<32) ){ + p[8] = (unsigned char)v; + v >>= 8; + for(i=7; i>=0; i--){ + p[i] = (unsigned char)((v & 0x7f) | 0x80); + v >>= 7; + } + fwrite(p, 8, 1, out); + }else{ + n = 9; + do{ + p[n--] = (unsigned char)((v & 0x7f) | 0x80); + v >>= 7; + }while( v!=0 ); + buf[9] &= 0x7f; + fwrite(buf+n+1, 9-n, 1, out); + } +} + /* ** Generate a CHANGESET for all differences from main.zTab to aux.zTab. */ @@ -726,7 +751,7 @@ static void changeset_one_table(const char *zTab, FILE *out){ int *aiPk = 0; /* Column numbers for each PK column */ int nPk = 0; /* Number of PRIMARY KEY columns */ Str sql; /* SQL for the diff query */ - int i; /* Loop counter */ + int i, j; /* Loop counters */ const char *zSep; /* List separator */ pStmt = db_prepare( @@ -763,7 +788,7 @@ static void changeset_one_table(const char *zTab, FILE *out){ if( nPk==0 ) goto end_changeset_one_table; strInit(&sql); if( nCol>nPk ){ - strPrintf(&sql, "SELECT 1"); /* Changes to non-PK columns */ + strPrintf(&sql, "SELECT %d", SQLITE_UPDATE); for(i=0; i=0; j-=8) putc((uX>>j)&0xff, out); + break; + case SQLITE_FLOAT: + rX = sqlite3_column_int64(pStmt,i); + memcpy(&uX, &rX, 8); + for(j=56; j>=0; j-=8) putc((uX>>j)&0xff, out); + break; + case SQLITE_TEXT: + iX = sqlite3_column_bytes(pStmt,i); + putsVarint(out, (sqlite3_uint64)iX); + fwrite(sqlite3_column_text(pStmt,i),1,iX,out); + break; + case SQLITE_BLOB: + iX = sqlite3_column_bytes(pStmt,i); + putsVarint(out, (sqlite3_uint64)iX); + fwrite(sqlite3_column_blob(pStmt,i),1,iX,out); + break; + case SQLITE_NULL: + break; + } + } + } + sqlite3_finalize(pStmt); end_changeset_one_table: while( nCol>0 ) sqlite3_free(azCol[--nCol]); From 6e42ce44db4d367c64c704f953e575d0f42310e5 Mon Sep 17 00:00:00 2001 From: drh Date: Sat, 11 Apr 2015 13:48:01 +0000 Subject: [PATCH 23/53] The --changeset option now appears to be working. FossilOrigin-Name: 1a2e2803920dcf64190d81d8a487d6c3c9bb28ee --- manifest | 12 ++-- manifest.uuid | 2 +- tool/sqldiff.c | 161 +++++++++++++++++++++++++++++++++++-------------- 3 files changed, 124 insertions(+), 51 deletions(-) diff --git a/manifest b/manifest index f2c0b806d6..336a1877e9 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C First\scomplete\sattempt\sto\sgenerate\sa\sworking\schangeset.\s\sStill\scontains\sbugs. -D 2015-04-11T12:07:40.414 +C The\s--changeset\soption\snow\sappears\sto\sbe\sworking. +D 2015-04-11T13:48:01.693 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -1239,7 +1239,7 @@ F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e F tool/split-sqlite3c.tcl d9be87f1c340285a3e081eb19b4a247981ed290c -F tool/sqldiff.c ed945df30d962d15d26188e33f7c5431cf197487 +F tool/sqldiff.c 51c05cc1435507736b8b5a41a0498016041b3e48 F tool/stack_usage.tcl f8e71b92cdb099a147dad572375595eae55eca43 F tool/symbols-mingw.sh 4dbcea7e74768305384c9fd2ed2b41bbf9f0414d F tool/symbols.sh fec58532668296d7c7dc48be9c87f75ccdb5814f @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 463e38d765f9d055b63792a8ea15c3782657b07f -R c7ffcaee222b675f0ec3e43f31931e14 +P 5611fa9bd5b8fd762d16ce9b0853c2e779a1a1b7 +R 907cf695d8fcffe3003a321f9aace7fc U drh -Z c4472641aefb50d8b597b0b444fecd27 +Z 3b5f839006775d8054dcfb8aab08f0fa diff --git a/manifest.uuid b/manifest.uuid index 4657a0c7e9..a5255d3652 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -5611fa9bd5b8fd762d16ce9b0853c2e779a1a1b7 \ No newline at end of file +1a2e2803920dcf64190d81d8a487d6c3c9bb28ee \ No newline at end of file diff --git a/tool/sqldiff.c b/tool/sqldiff.c index d166174440..4455c582ef 100644 --- a/tool/sqldiff.c +++ b/tool/sqldiff.c @@ -719,7 +719,7 @@ end_diff_one_table: */ static void putsVarint(FILE *out, sqlite3_uint64 v){ int i, n; - unsigned char buf[12], p[12]; + unsigned char p[12]; if( v & (((sqlite3_uint64)0xff000000)<<32) ){ p[8] = (unsigned char)v; v >>= 8; @@ -734,8 +734,45 @@ static void putsVarint(FILE *out, sqlite3_uint64 v){ p[n--] = (unsigned char)((v & 0x7f) | 0x80); v >>= 7; }while( v!=0 ); - buf[9] &= 0x7f; - fwrite(buf+n+1, 9-n, 1, out); + p[9] &= 0x7f; + fwrite(p+n+1, 9-n, 1, out); + } +} + +/* +** Write an SQLite value onto out. +*/ +static void putValue(FILE *out, sqlite3_value *pVal){ + int iDType = sqlite3_value_type(pVal); + sqlite3_int64 iX; + double rX; + sqlite3_uint64 uX; + int j; + + putc(iDType, out); + switch( iDType ){ + case SQLITE_INTEGER: + iX = sqlite3_value_int64(pVal); + memcpy(&uX, &iX, 8); + for(j=56; j>=0; j-=8) putc((uX>>j)&0xff, out); + break; + case SQLITE_FLOAT: + rX = sqlite3_value_int64(pVal); + memcpy(&uX, &rX, 8); + for(j=56; j>=0; j-=8) putc((uX>>j)&0xff, out); + break; + case SQLITE_TEXT: + iX = sqlite3_value_bytes(pVal); + putsVarint(out, (sqlite3_uint64)iX); + fwrite(sqlite3_value_text(pVal),1,iX,out); + break; + case SQLITE_BLOB: + iX = sqlite3_value_bytes(pVal); + putsVarint(out, (sqlite3_uint64)iX); + fwrite(sqlite3_value_blob(pVal),1,iX,out); + break; + case SQLITE_NULL: + break; } } @@ -751,7 +788,7 @@ static void changeset_one_table(const char *zTab, FILE *out){ int *aiPk = 0; /* Column numbers for each PK column */ int nPk = 0; /* Number of PRIMARY KEY columns */ Str sql; /* SQL for the diff query */ - int i, j; /* Loop counters */ + int i, k; /* Loop counters */ const char *zSep; /* List separator */ pStmt = db_prepare( @@ -789,8 +826,14 @@ static void changeset_one_table(const char *zTab, FILE *out){ strInit(&sql); if( nCol>nPk ){ strPrintf(&sql, "SELECT %d", SQLITE_UPDATE); - for(i=0; i=0; j-=8) putc((uX>>j)&0xff, out); - break; - case SQLITE_FLOAT: - rX = sqlite3_column_int64(pStmt,i); - memcpy(&uX, &rX, 8); - for(j=56; j>=0; j-=8) putc((uX>>j)&0xff, out); - break; - case SQLITE_TEXT: - iX = sqlite3_column_bytes(pStmt,i); - putsVarint(out, (sqlite3_uint64)iX); - fwrite(sqlite3_column_text(pStmt,i),1,iX,out); - break; - case SQLITE_BLOB: - iX = sqlite3_column_bytes(pStmt,i); - putsVarint(out, (sqlite3_uint64)iX); - fwrite(sqlite3_column_blob(pStmt,i),1,iX,out); - break; - case SQLITE_NULL: - break; + switch( sqlite3_column_int(pStmt,0) ){ + case SQLITE_UPDATE: { + for(k=1, i=0; i Date: Sat, 11 Apr 2015 20:20:29 +0000 Subject: [PATCH 24/53] Fix a problem with sorting large amounts of partially ordered data. FossilOrigin-Name: acca97efda86a0c020854d2dd9da16f5879986b1 --- manifest | 17 ++++++++--------- manifest.uuid | 2 +- src/vdbesort.c | 9 ++------- test/orderby1.test | 29 +++++++++++++++++++++++++++++ 4 files changed, 40 insertions(+), 17 deletions(-) diff --git a/manifest b/manifest index 871fd87da4..e73c590925 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\sthe\s--changeset\soption\sto\sthe\ssqldiff\sutility\sprogram,\sfor\sgenerating\na\ssessions\schangeset\sfile\sinstead\sof\san\sSQL\sdiff. -D 2015-04-11T13:49:16.216 +C Fix\sa\sproblem\swith\ssorting\slarge\samounts\sof\spartially\sordered\sdata. +D 2015-04-11T20:20:29.810 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -300,7 +300,7 @@ F src/vdbeapi.c 583d56b129dd27f12bed518270de9ebe521e6a75 F src/vdbeaux.c 413dc496248ac18eb0c19e35e86bb1ffd47b8907 F src/vdbeblob.c 4f2e8e075d238392df98c5e03a64342465b03f90 F src/vdbemem.c c0dc81285b7571b0a31c40f17846fe2397ec1cd9 -F src/vdbesort.c 919717d7599fa31d343ec28bffd0f9e91a4ff5f6 +F src/vdbesort.c a9d39d99969462908f50d09918791883c5b067ab F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 F src/vtab.c 9ca557215e8591ceb66e0b7c0a579c6df1e54b2d F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb @@ -771,7 +771,7 @@ F test/notnull.test f8fcf58669ddba79274daa2770d61dfad8274f62 F test/null.test 0dcce4f04284ec66108c503327ad6d224c0752b3 F test/numcast.test 5d126f7f581432e86a90d1e35cac625164aec4a1 F test/openv2.test 0d3040974bf402e19b7df4b783e447289d7ab394 -F test/orderby1.test eb246e377612b21a418fbea57047ba8ea88aaa6b +F test/orderby1.test d69a2c99c023c85b014ece2cf691caec16a40d6d F test/orderby2.test bc11009f7cd99d96b1b11e57b199b00633eb5b04 F test/orderby3.test 8619d06a3debdcd80a27c0fdea5c40b468854b99 F test/orderby4.test 4d39bfbaaa3ae64d026ca2ff166353d2edca4ba4 @@ -1250,8 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P da49700ca148d91e1b8863c2eb6ee79144e83ac9 1a2e2803920dcf64190d81d8a487d6c3c9bb28ee -R c078ada2bdea31973177a0bd82842009 -T +closed 1a2e2803920dcf64190d81d8a487d6c3c9bb28ee -U drh -Z 157b78d075c326a9e01bf8b58e910074 +P f9a3a8391c28cf13d76ec54f471735d35059acea +R 20d1ab6a886883435eefbe113ce65f82 +U dan +Z 26f0ad0889bc54d15cfec6237366d6c5 diff --git a/manifest.uuid b/manifest.uuid index 76f7b8530a..89b4e6fdf1 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -f9a3a8391c28cf13d76ec54f471735d35059acea \ No newline at end of file +acca97efda86a0c020854d2dd9da16f5879986b1 \ No newline at end of file diff --git a/src/vdbesort.c b/src/vdbesort.c index bbdafa8230..869ff4f2a3 100644 --- a/src/vdbesort.c +++ b/src/vdbesort.c @@ -887,30 +887,24 @@ static void vdbeSorterRecordFree(sqlite3 *db, SorterRecord *pRecord){ */ static void vdbeSortSubtaskCleanup(sqlite3 *db, SortSubtask *pTask){ sqlite3DbFree(db, pTask->pUnpacked); - pTask->pUnpacked = 0; #if SQLITE_MAX_WORKER_THREADS>0 /* pTask->list.aMemory can only be non-zero if it was handed memory ** from the main thread. That only occurs SQLITE_MAX_WORKER_THREADS>0 */ if( pTask->list.aMemory ){ sqlite3_free(pTask->list.aMemory); - pTask->list.aMemory = 0; }else #endif { assert( pTask->list.aMemory==0 ); vdbeSorterRecordFree(0, pTask->list.pList); } - pTask->list.pList = 0; if( pTask->file.pFd ){ sqlite3OsCloseFree(pTask->file.pFd); - pTask->file.pFd = 0; - pTask->file.iEof = 0; } if( pTask->file2.pFd ){ sqlite3OsCloseFree(pTask->file2.pFd); - pTask->file2.pFd = 0; - pTask->file2.iEof = 0; } + memset(pTask, 0, sizeof(SortSubtask)); } #ifdef SQLITE_DEBUG_SORTER_THREADS @@ -1090,6 +1084,7 @@ void sqlite3VdbeSorterReset(sqlite3 *db, VdbeSorter *pSorter){ for(i=0; inTask; i++){ SortSubtask *pTask = &pSorter->aTask[i]; vdbeSortSubtaskCleanup(db, pTask); + pTask->pSorter = pSorter; } if( pSorter->list.aMemory==0 ){ vdbeSorterRecordFree(0, pSorter->list.pList); diff --git a/test/orderby1.test b/test/orderby1.test index 6674e32220..164c3f25db 100644 --- a/test/orderby1.test +++ b/test/orderby1.test @@ -495,5 +495,34 @@ do_execsql_test 7.0 { SELECT * FROM t7 WHERE a=?1 ORDER BY rowid; } {~/ORDER BY/} +#------------------------------------------------------------------------- +# Test a partial sort large enough to cause the sorter to spill data +# to disk. +# +reset_db +do_execsql_test 8.0 { + PRAGMA cache_size = 5; + CREATE TABLE t1(a, b); + CREATE INDEX i1 ON t1(a); +} + +do_eqp_test 8.1 { + SELECT * FROM t1 ORDER BY a, b; +} { + 0 0 0 {SCAN TABLE t1 USING INDEX i1} + 0 0 0 {USE TEMP B-TREE FOR RIGHT PART OF ORDER BY} +} + +do_execsql_test 8.2 { + WITH cnt(i) AS ( + SELECT 1 UNION ALL SELECT i+1 FROM cnt WHERE i<10000 + ) + INSERT INTO t1 SELECT i%2, randomblob(500) FROM cnt; +} + +do_test 8.3 { + db eval { SELECT * FROM t1 ORDER BY a, b } { incr res $a } + set res +} 5000 finish_test From 11b04817785a3d23789ca80829cc598840878946 Mon Sep 17 00:00:00 2001 From: drh Date: Sun, 12 Apr 2015 01:22:04 +0000 Subject: [PATCH 25/53] Avoid problems when a query has a GROUP BY and an ORDER BY but no FROM clause. FossilOrigin-Name: e527d96a1e098ade4e9d124b630a8c2ea2ac9b36 --- manifest | 16 ++++++++-------- manifest.uuid | 2 +- src/where.c | 2 +- test/orderby1.test | 3 +++ 4 files changed, 13 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index 17f4391705..7967b35884 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Optimizations\sfor\sVACUUM,\sCREATE\sINDEX\sand\ssome\scases\sof\sORDER\sBY. -D 2015-04-11T20:44:28.726 +C Avoid\sproblems\swhen\sa\squery\shas\sa\sGROUP\sBY\sand\san\sORDER\sBY\sbut\sno\sFROM\sclause. +D 2015-04-12T01:22:04.580 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -307,7 +307,7 @@ F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb F src/wal.c 878c8e1a51cb2ec45c395d26b7d5cd9e1a098e4a F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c bd435b75b9de53e11b5eb561540e395041ac0cba +F src/where.c 9952e4749f481707595692f2f13d3ce3b64ffdc8 F src/whereInt.h cbe4aa57326998d89e7698ca65bb7c28541d483c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -771,7 +771,7 @@ F test/notnull.test f8fcf58669ddba79274daa2770d61dfad8274f62 F test/null.test 0dcce4f04284ec66108c503327ad6d224c0752b3 F test/numcast.test 5d126f7f581432e86a90d1e35cac625164aec4a1 F test/openv2.test 0d3040974bf402e19b7df4b783e447289d7ab394 -F test/orderby1.test d69a2c99c023c85b014ece2cf691caec16a40d6d +F test/orderby1.test 870e150450437d3980badbde3d0166b81d9e33f6 F test/orderby2.test bc11009f7cd99d96b1b11e57b199b00633eb5b04 F test/orderby3.test 8619d06a3debdcd80a27c0fdea5c40b468854b99 F test/orderby4.test 4d39bfbaaa3ae64d026ca2ff166353d2edca4ba4 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P acca97efda86a0c020854d2dd9da16f5879986b1 cf7590f607d94a120385576b538484ca738349e2 -R 4a3267783e1ce12038a61c7c4ca15ba8 -U dan -Z 05508ac040af16f75cf3f23dcdb1072a +P 79326d6eece926fd1c148b29f0b726208d8b44c0 +R b8a99417c5276ad65ad7b525e5ae16a3 +U drh +Z ba0a0070ee213de4cf49a8279f3da0ad diff --git a/manifest.uuid b/manifest.uuid index 695e755462..df7dea6773 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -79326d6eece926fd1c148b29f0b726208d8b44c0 \ No newline at end of file +e527d96a1e098ade4e9d124b630a8c2ea2ac9b36 \ No newline at end of file diff --git a/src/where.c b/src/where.c index a96d9e5add..42e950e41e 100644 --- a/src/where.c +++ b/src/where.c @@ -6241,7 +6241,7 @@ static int wherePathSolver(WhereInfo *pWInfo, LogEst nRowEst){ pWInfo->revMask = pFrom->revLoop; } if( (pWInfo->wctrlFlags & WHERE_SORTBYGROUP) - && pWInfo->nOBSat==pWInfo->pOrderBy->nExpr + && pWInfo->nOBSat==pWInfo->pOrderBy->nExpr && nLoop>0 ){ Bitmask revMask = 0; int nOrder = wherePathSatisfiesOrderBy(pWInfo, pWInfo->pOrderBy, diff --git a/test/orderby1.test b/test/orderby1.test index 164c3f25db..3e785c54e4 100644 --- a/test/orderby1.test +++ b/test/orderby1.test @@ -463,6 +463,9 @@ do_execsql_test 5.1 { do_execsql_test 5.2 { SELECT 5 UNION ALL SELECT 3 ORDER BY 1 } {3 5} +do_execsql_test 5.3 { + SELECT 986 AS x GROUP BY X ORDER BY X +} {986} # The following test (originally derived from a single test within fuzz.test) # verifies that a PseudoTable cursor is not closed prematurely in a deeply From f932f7145ede311a79a15197841c2706af5bc71c Mon Sep 17 00:00:00 2001 From: drh Date: Sun, 12 Apr 2015 17:35:27 +0000 Subject: [PATCH 26/53] Fix a problem with a stale Select.pWith pointer when a CTE is used together with a compound query and an ORDER BY clause. FossilOrigin-Name: 9a453f52a2b30595891604ede7d4acf61c2736a1 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/select.c | 1 + test/with1.test | 6 ++++++ 4 files changed, 15 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 7967b35884..5478452884 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Avoid\sproblems\swhen\sa\squery\shas\sa\sGROUP\sBY\sand\san\sORDER\sBY\sbut\sno\sFROM\sclause. -D 2015-04-12T01:22:04.580 +C Fix\sa\sproblem\swith\sa\sstale\sSelect.pWith\spointer\swhen\sa\sCTE\sis\sused\stogether\nwith\sa\scompound\squery\sand\san\sORDER\sBY\sclause. +D 2015-04-12T17:35:27.113 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -230,7 +230,7 @@ F src/printf.c 8ae1fa9d30c1200a9268a390ba9e9cea9197b27a F src/random.c ba2679f80ec82c4190062d756f22d0c358180696 F src/resolve.c 41aa91af56d960e9414ce1d7c17cfb68e0d1c6cb F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e -F src/select.c c28c52e353287434fac8473e56ee4be848d12c9d +F src/select.c 117e0f9ac9254a6f7472fac5144eba21ba0b2ec1 F src/shell.c 84a1593bd86aaa14f4da8a8f9b16fbc239d262aa F src/sqlite.h.in 278602140d49575e8708e643161f4263e428a02a F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad @@ -1184,7 +1184,7 @@ F test/wild001.test bca33f499866f04c24510d74baf1e578d4e44b1c F test/win32heap.test ea19770974795cff26e11575e12d422dbd16893c F test/win32lock.test fbf107c91d8f5512be5a5b87c4c42ab9fdd54972 F test/win32longpath.test 169c75a3b2e43481f4a62122510210c67b08f26d -F test/with1.test 9df5cd8a62148b3d9ef8597aea563e3863018bcd +F test/with1.test a86bf7f9288ba759a25ee57221d3bffaca36032a F test/with2.test ee227a663586aa09771cafd4fa269c5217eaf775 F test/withM.test e97f2a8c506ab3ea9eab94e6f6072f6cc924c991 F test/without_rowid1.test 7862e605753c8d25329f665fa09072e842183151 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 79326d6eece926fd1c148b29f0b726208d8b44c0 -R b8a99417c5276ad65ad7b525e5ae16a3 +P e527d96a1e098ade4e9d124b630a8c2ea2ac9b36 +R f469da7981f7e5a80ef00c68d565b4fb U drh -Z ba0a0070ee213de4cf49a8279f3da0ad +Z 637f476e29fbab1d809f7d30402eeba5 diff --git a/manifest.uuid b/manifest.uuid index df7dea6773..cdf3e1131c 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -e527d96a1e098ade4e9d124b630a8c2ea2ac9b36 \ No newline at end of file +9a453f52a2b30595891604ede7d4acf61c2736a1 \ No newline at end of file diff --git a/src/select.c b/src/select.c index 90aaa842a6..930a099e80 100644 --- a/src/select.c +++ b/src/select.c @@ -3883,6 +3883,7 @@ static int convertCompoundSelectToSubquery(Walker *pWalker, Select *p){ pNew->pOrderBy = 0; p->pPrior = 0; p->pNext = 0; + p->pWith = 0; p->selFlags &= ~SF_Compound; assert( (p->selFlags & SF_Converted)==0 ); p->selFlags |= SF_Converted; diff --git a/test/with1.test b/test/with1.test index ad88a67c22..80892d2642 100644 --- a/test/with1.test +++ b/test/with1.test @@ -843,4 +843,10 @@ do_catchsql_test 13.3 { SELECT i FROM c; } {1 {table c has 1 values for 2 columns}} +# 2015-04-12 +# +do_execsql_test 14.1 { + WITH x AS (SELECT * FROM t) SELECT 0 EXCEPT SELECT 0 ORDER BY 1 COLLATE binary; +} {} + finish_test From 9dc225ef1c4ad4db3e518b1ba6a2ce4480865f98 Mon Sep 17 00:00:00 2001 From: drh Date: Sun, 12 Apr 2015 21:28:50 +0000 Subject: [PATCH 27/53] Update the version number to 3.8.10 because of the new sort optimizations from check-in [79326d6eec]. FossilOrigin-Name: bd2cfa1d72368db91064bace298df3d77d9963e6 --- VERSION | 2 +- configure | 18 +++++++++--------- manifest | 14 +++++++------- manifest.uuid | 2 +- 4 files changed, 18 insertions(+), 18 deletions(-) diff --git a/VERSION b/VERSION index 203e6d5c9a..d20cc2bf02 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -3.8.9 +3.8.10 diff --git a/configure b/configure index d259324bdd..9a3d102a8a 100755 --- a/configure +++ b/configure @@ -1,6 +1,6 @@ #! /bin/sh # Guess values for system-dependent variables and create Makefiles. -# Generated by GNU Autoconf 2.62 for sqlite 3.8.9. +# Generated by GNU Autoconf 2.62 for sqlite 3.8.10. # # Copyright (C) 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2000, 2001, # 2002, 2003, 2004, 2005, 2006, 2007, 2008 Free Software Foundation, Inc. @@ -743,8 +743,8 @@ SHELL=${CONFIG_SHELL-/bin/sh} # Identity of this package. PACKAGE_NAME='sqlite' PACKAGE_TARNAME='sqlite' -PACKAGE_VERSION='3.8.9' -PACKAGE_STRING='sqlite 3.8.9' +PACKAGE_VERSION='3.8.10' +PACKAGE_STRING='sqlite 3.8.10' PACKAGE_BUGREPORT='' # Factoring default headers for most tests. @@ -1481,7 +1481,7 @@ if test "$ac_init_help" = "long"; then # Omit some internal or obsolete options to make the list less imposing. # This message is too long to be a string in the A/UX 3.1 sh. cat <<_ACEOF -\`configure' configures sqlite 3.8.9 to adapt to many kinds of systems. +\`configure' configures sqlite 3.8.10 to adapt to many kinds of systems. Usage: $0 [OPTION]... [VAR=VALUE]... @@ -1546,7 +1546,7 @@ fi if test -n "$ac_init_help"; then case $ac_init_help in - short | recursive ) echo "Configuration of sqlite 3.8.9:";; + short | recursive ) echo "Configuration of sqlite 3.8.10:";; esac cat <<\_ACEOF @@ -1660,7 +1660,7 @@ fi test -n "$ac_init_help" && exit $ac_status if $ac_init_version; then cat <<\_ACEOF -sqlite configure 3.8.9 +sqlite configure 3.8.10 generated by GNU Autoconf 2.62 Copyright (C) 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2000, 2001, @@ -1674,7 +1674,7 @@ cat >config.log <<_ACEOF This file contains any messages produced by compilers while running configure, to aid debugging if configure makes a mistake. -It was created by sqlite $as_me 3.8.9, which was +It was created by sqlite $as_me 3.8.10, which was generated by GNU Autoconf 2.62. Invocation command line was $ $0 $@ @@ -13953,7 +13953,7 @@ exec 6>&1 # report actual input values of CONFIG_FILES etc. instead of their # values after options handling. ac_log=" -This file was extended by sqlite $as_me 3.8.9, which was +This file was extended by sqlite $as_me 3.8.10, which was generated by GNU Autoconf 2.62. Invocation command line was CONFIG_FILES = $CONFIG_FILES @@ -14006,7 +14006,7 @@ Report bugs to ." _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_cs_version="\\ -sqlite config.status 3.8.9 +sqlite config.status 3.8.10 configured by $0, generated by GNU Autoconf 2.62, with options \\"`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`\\" diff --git a/manifest b/manifest index 5478452884..4a1c19474e 100644 --- a/manifest +++ b/manifest @@ -1,12 +1,12 @@ -C Fix\sa\sproblem\swith\sa\sstale\sSelect.pWith\spointer\swhen\sa\sCTE\sis\sused\stogether\nwith\sa\scompound\squery\sand\san\sORDER\sBY\sclause. -D 2015-04-12T17:35:27.113 +C Update\sthe\sversion\snumber\sto\s3.8.10\sbecause\sof\sthe\snew\ssort\soptimizations\sfrom\scheck-in\s[79326d6eec]. +D 2015-04-12T21:28:50.540 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 F Makefile.msc 0078f5781538e07ea38683439f38d5f5ab79ab6e F Makefile.vxworks e1b65dea203f054e71653415bd8f96dcaed47858 F README.md d58e3bebc0a4145e0f2a87994015fdb575a8e866 -F VERSION 319eb1ced4b4d17a67730f2b7b85f15c1346cb60 +F VERSION 2e244662b71e6e68a5c29b014ebc5b7564f4cc5a F aclocal.m4 a5c22d164aff7ed549d53a90fa56d56955281f50 F addopcodes.awk 9eb448a552d5c0185cf62c463f9c173cedae3811 F art/sqlite370.eps aa97a671332b432a54e1d74ff5e8775be34200c2 @@ -38,7 +38,7 @@ F autoconf/tea/win/rules.vc c511f222b80064096b705dbeb97060ee1d6b6d63 F config.guess 226d9a188c6196f3033ffc651cbc9dcee1a42977 F config.h.in 42b71ad3fe21c9e88fa59e8458ca1a6bc72eb0c0 F config.sub 9ebe4c3b3dab6431ece34f16828b594fb420da55 -F configure 8b18c2378805a1d8aaca85d293671f450dd3c723 x +F configure 2ea5f5b58dd106da449ab598ab6e515339d7fa2a x F configure.ac 0b775d383c536bbaafc1e46dd3cbb81a7ea11aeb F contrib/sqlitecon.tcl 210a913ad63f9f991070821e599d600bd913e0ad F doc/lemon.html 334dbf6621b8fb8790297ec1abf3cfa4621709d1 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P e527d96a1e098ade4e9d124b630a8c2ea2ac9b36 -R f469da7981f7e5a80ef00c68d565b4fb +P 9a453f52a2b30595891604ede7d4acf61c2736a1 +R 4a2a023e9382e5658a5d290bebd20330 U drh -Z 637f476e29fbab1d809f7d30402eeba5 +Z 3fe3cb8d2199de920836663cd4df5373 diff --git a/manifest.uuid b/manifest.uuid index cdf3e1131c..d0ccf9d2b0 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -9a453f52a2b30595891604ede7d4acf61c2736a1 \ No newline at end of file +bd2cfa1d72368db91064bace298df3d77d9963e6 \ No newline at end of file From 4a614e9013478d98c1bfe1014f8d7a978c3c378d Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 13 Apr 2015 12:45:58 +0000 Subject: [PATCH 28/53] Remove an unreachable branch from the vdbeSorterCompareInt() routine. FossilOrigin-Name: f666ef06869f4fb655c43daacf5034c17575d951 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/vdbesort.c | 3 ++- 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 4a1c19474e..40ccc22361 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Update\sthe\sversion\snumber\sto\s3.8.10\sbecause\sof\sthe\snew\ssort\soptimizations\sfrom\scheck-in\s[79326d6eec]. -D 2015-04-12T21:28:50.540 +C Remove\san\sunreachable\sbranch\sfrom\sthe\svdbeSorterCompareInt()\sroutine. +D 2015-04-13T12:45:58.929 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -300,7 +300,7 @@ F src/vdbeapi.c 583d56b129dd27f12bed518270de9ebe521e6a75 F src/vdbeaux.c a20504ae52392459fa08402fda3f195f19d7c79d F src/vdbeblob.c 4f2e8e075d238392df98c5e03a64342465b03f90 F src/vdbemem.c c0dc81285b7571b0a31c40f17846fe2397ec1cd9 -F src/vdbesort.c 5a729a15fb46b1759e13be49a10441172628e593 +F src/vdbesort.c 2e7f683464fd5db3be4beaa1ff2d39e24fcb64b8 F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 F src/vtab.c 9ca557215e8591ceb66e0b7c0a579c6df1e54b2d F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 9a453f52a2b30595891604ede7d4acf61c2736a1 -R 4a2a023e9382e5658a5d290bebd20330 +P bd2cfa1d72368db91064bace298df3d77d9963e6 +R b8f08800d49097dd7ac4eb07d7ead02a U drh -Z 3fe3cb8d2199de920836663cd4df5373 +Z b7397c89c618aad1f80f88c7af5c800c diff --git a/manifest.uuid b/manifest.uuid index d0ccf9d2b0..660e0945e6 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -bd2cfa1d72368db91064bace298df3d77d9963e6 \ No newline at end of file +f666ef06869f4fb655c43daacf5034c17575d951 \ No newline at end of file diff --git a/src/vdbesort.c b/src/vdbesort.c index 14803c0b3e..4d9ef90cdc 100644 --- a/src/vdbesort.c +++ b/src/vdbesort.c @@ -882,10 +882,11 @@ static int vdbeSorterCompareInt( }else{ res = s1 - s2; } + assert( res!=0 ); if( res>0 ){ if( *v1 & 0x80 ) res = -1; - }else if( res<0 ){ + }else{ if( *v2 & 0x80 ) res = +1; } } From ab06b0e5be8377fc510fcde3c2d1de773a97942d Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 13 Apr 2015 14:03:54 +0000 Subject: [PATCH 29/53] Remove an unreachable branch from the VACUUM logic. FossilOrigin-Name: 65ace4b062d9454a296c5a1aa7ea7316b1507ad4 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/insert.c | 3 ++- 3 files changed, 9 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 40ccc22361..cf166dc945 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\san\sunreachable\sbranch\sfrom\sthe\svdbeSorterCompareInt()\sroutine. -D 2015-04-13T12:45:58.929 +C Remove\san\sunreachable\sbranch\sfrom\sthe\sVACUUM\slogic. +D 2015-04-13T14:03:54.116 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -190,7 +190,7 @@ F src/global.c 4f77cadbc5427d00139ba43d0f3979804cbb700e F src/hash.c 4263fbc955f26c2e8cdc0cf214bc42435aa4e4f5 F src/hash.h c8f3c31722cf3277d03713909761e152a5b81094 F src/hwtime.h d32741c8f4df852c7d959236615444e2b1063b08 -F src/insert.c 1cc9dc4e939b5dd4a74ac4a3222b89e66b074210 +F src/insert.c 305dd3f9539d0affa4bf1c14cc7dffb34867e040 F src/journal.c b4124532212b6952f42eb2c12fa3c25701d8ba8d F src/legacy.c ba1863ea58c4c840335a84ec276fc2b25e22bc4e F src/lempar.c 7274c97d24bb46631e504332ccd3bd1b37841770 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P bd2cfa1d72368db91064bace298df3d77d9963e6 -R b8f08800d49097dd7ac4eb07d7ead02a +P f666ef06869f4fb655c43daacf5034c17575d951 +R 13ae6f8a2a03926d32aaccc1e7fe4f0a U drh -Z b7397c89c618aad1f80f88c7af5c800c +Z 18a3bd532998a4429c86c5536067680b diff --git a/manifest.uuid b/manifest.uuid index 660e0945e6..c6033ca289 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -f666ef06869f4fb655c43daacf5034c17575d951 \ No newline at end of file +65ace4b062d9454a296c5a1aa7ea7316b1507ad4 \ No newline at end of file diff --git a/src/insert.c b/src/insert.c index f8ae4d7d3c..fc8895bbd6 100644 --- a/src/insert.c +++ b/src/insert.c @@ -2024,7 +2024,8 @@ static int xferOptimization( int i; for(i=0; inColumn; i++){ char *zColl = pSrcIdx->azColl[i]; - if( zColl && sqlite3_stricmp("BINARY", zColl) ) break; + assert( zColl!=0 ); + if( sqlite3_stricmp("BINARY", zColl) ) break; } if( i==pSrcIdx->nColumn ){ useSeekResult = OPFLAG_USESEEKRESULT; From 481ecd95d0e4386094e1eaa2d1512998d6d7fbdd Mon Sep 17 00:00:00 2001 From: dan Date: Mon, 13 Apr 2015 14:08:27 +0000 Subject: [PATCH 30/53] Test that if the definition of a collation sequence is changed and VACUUM run, the new database contains records sorted in the (new) correct order. FossilOrigin-Name: ce6eaac10a190b26b87bfe75918e2ef58fd7a3f9 --- manifest | 14 +++++++------- manifest.uuid | 2 +- test/vacuum2.test | 20 ++++++++++++++++++++ 3 files changed, 28 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index cf166dc945..1207568ae7 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\san\sunreachable\sbranch\sfrom\sthe\sVACUUM\slogic. -D 2015-04-13T14:03:54.116 +C Test\sthat\sif\sthe\sdefinition\sof\sa\scollation\ssequence\sis\schanged\sand\sVACUUM\srun,\sthe\snew\sdatabase\scontains\srecords\ssorted\sin\sthe\s(new)\scorrect\sorder. +D 2015-04-13T14:08:27.490 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -1107,7 +1107,7 @@ F test/uri.test 23662b7b61958b0f0e47082de7d06341ccf85d5b F test/userauth01.test e740a2697a7b40d7c5003a7d7edaee16acd349a9 F test/utf16align.test 54cd35a27c005a9b6e7815d887718780b6a462ae F test/vacuum.test ce91c39f7f91a4273bf620efad21086b5aa6ef1d -F test/vacuum2.test af432e6e3bfc0ea20a80cb86a03c7d9876d38324 +F test/vacuum2.test aa048abee196c16c9ba308465494009057b79f9b F test/vacuum3.test 77ecdd54592b45a0bcb133339f99f1ae0ae94d0d F test/vacuum4.test d3f8ecff345f166911568f397d2432c16d2867d9 F test/varint.test ab7b110089a08b9926ed7390e7e97bdefeb74102 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P f666ef06869f4fb655c43daacf5034c17575d951 -R 13ae6f8a2a03926d32aaccc1e7fe4f0a -U drh -Z 18a3bd532998a4429c86c5536067680b +P 65ace4b062d9454a296c5a1aa7ea7316b1507ad4 +R 10297fb20a52d4dc7c571adcebaddc36 +U dan +Z 0a6c3062817beaba9c93ab9bd5dcc5e3 diff --git a/manifest.uuid b/manifest.uuid index c6033ca289..fcea990f8f 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -65ace4b062d9454a296c5a1aa7ea7316b1507ad4 \ No newline at end of file +ce6eaac10a190b26b87bfe75918e2ef58fd7a3f9 \ No newline at end of file diff --git a/test/vacuum2.test b/test/vacuum2.test index b3bfab3022..0350c8ec42 100644 --- a/test/vacuum2.test +++ b/test/vacuum2.test @@ -15,6 +15,7 @@ set testdir [file dirname $argv0] source $testdir/tester.tcl +set testprefix vacuum2 # Do not use a codec for tests in this file, as the database file is # manipulated directly using tcl scripts (using the [hexio_write] command). @@ -227,5 +228,24 @@ do_test vacuum2-5.4 { lappend res2 $res } {1 2 3 4 5 6 7 8 9 10 {1 {cannot VACUUM - SQL statements in progress}}} +#------------------------------------------------------------------------- +# Check that if the definition of a collation sequence is changed and +# VACUUM run, records are store in the (new) correct order following the +# VACUUM. Even if the modified collation is attached to a PK of a WITHOUT +# ROWID table. + +proc cmp {lhs rhs} { string compare $lhs $rhs } +db collate cmp cmp +do_execsql_test 6.0 { + CREATE TABLE t6(x PRIMARY KEY COLLATE cmp, y) WITHOUT ROWID; + CREATE INDEX t6y ON t6(y); + INSERT INTO t6 VALUES('i', 'one'); + INSERT INTO t6 VALUES('ii', 'one'); + INSERT INTO t6 VALUES('iii', 'one'); +} +integrity_check 6.1 +proc cmp {lhs rhs} { string compare $rhs $lhs } +do_execsql_test 6.2 VACUUM +integrity_check 6.3 finish_test From c01501a3861944d8027a5e620e420238db9bcc2c Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 13 Apr 2015 14:44:01 +0000 Subject: [PATCH 31/53] Remove a faulty assert() from the btree balancing logic. FossilOrigin-Name: d06669d968c8f6af8799fbfeabadaab68b9b8db8 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/btree.c | 1 - 3 files changed, 8 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 1207568ae7..bddc4cadc4 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Test\sthat\sif\sthe\sdefinition\sof\sa\scollation\ssequence\sis\schanged\sand\sVACUUM\srun,\sthe\snew\sdatabase\scontains\srecords\ssorted\sin\sthe\s(new)\scorrect\sorder. -D 2015-04-13T14:08:27.490 +C Remove\sa\sfaulty\sassert()\sfrom\sthe\sbtree\sbalancing\slogic. +D 2015-04-13T14:44:01.870 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -173,7 +173,7 @@ F src/auth.c b56c78ebe40a2110fd361379f7e8162d23f92240 F src/backup.c ff743689c4d6c5cb55ad42ed9d174b2b3e71f1e3 F src/bitvec.c 19a4ba637bd85f8f63fc8c9bae5ade9fb05ec1cb F src/btmutex.c 45a968cc85afed9b5e6cf55bf1f42f8d18107f79 -F src/btree.c 2caf598165f3608fde8abac2b243826616ce54b7 +F src/btree.c 67648f6532c2da79d3b3fb6853aa1a0c3ba0e1ad F src/btree.h 969adc948e89e449220ff0ff724c94bb2a52e9f1 F src/btreeInt.h 973a22a6fd61350b454ad614832b1f0a5e25a1e4 F src/build.c fa4795bc795077388aa4e746e1b25ef97bc10489 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 65ace4b062d9454a296c5a1aa7ea7316b1507ad4 -R 10297fb20a52d4dc7c571adcebaddc36 -U dan -Z 0a6c3062817beaba9c93ab9bd5dcc5e3 +P ce6eaac10a190b26b87bfe75918e2ef58fd7a3f9 +R bac46adba95b910001781f1715fe4531 +U drh +Z 344080508147bb8eb54111c6b1e074c7 diff --git a/manifest.uuid b/manifest.uuid index fcea990f8f..3daf8bbf88 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -ce6eaac10a190b26b87bfe75918e2ef58fd7a3f9 \ No newline at end of file +d06669d968c8f6af8799fbfeabadaab68b9b8db8 \ No newline at end of file diff --git a/src/btree.c b/src/btree.c index 789796d55a..9faf624235 100644 --- a/src/btree.c +++ b/src/btree.c @@ -6735,7 +6735,6 @@ static int balance_nonroot( }else if( iParentIdx==i ){ nxDiv = i-2+bBulk; }else{ - assert( bBulk==0 ); nxDiv = iParentIdx-1; } i = 2-bBulk; From 1fe0af200db60257a744104e7f264e8fd29729ac Mon Sep 17 00:00:00 2001 From: dan Date: Mon, 13 Apr 2015 17:43:43 +0000 Subject: [PATCH 32/53] Add a comment to wal.c to explain why a race condition is safe. FossilOrigin-Name: bc33af866403c23d548dd4705675315810d52d7f --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/wal.c | 8 ++++++++ 3 files changed, 16 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index bddc4cadc4..12b1e15e95 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\sa\sfaulty\sassert()\sfrom\sthe\sbtree\sbalancing\slogic. -D 2015-04-13T14:44:01.870 +C Add\sa\scomment\sto\swal.c\sto\sexplain\swhy\sa\srace\scondition\sis\ssafe. +D 2015-04-13T17:43:43.335 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -304,7 +304,7 @@ F src/vdbesort.c 2e7f683464fd5db3be4beaa1ff2d39e24fcb64b8 F src/vdbetrace.c 7e4222955e07dd707a2f360c0eb73452be1cb010 F src/vtab.c 9ca557215e8591ceb66e0b7c0a579c6df1e54b2d F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb -F src/wal.c 878c8e1a51cb2ec45c395d26b7d5cd9e1a098e4a +F src/wal.c 753995db83247f20361a8e8a874990b21a75abd9 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 F src/where.c 9952e4749f481707595692f2f13d3ce3b64ffdc8 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P ce6eaac10a190b26b87bfe75918e2ef58fd7a3f9 -R bac46adba95b910001781f1715fe4531 -U drh -Z 344080508147bb8eb54111c6b1e074c7 +P d06669d968c8f6af8799fbfeabadaab68b9b8db8 +R 90c9a3885d268edb8b0fe9dee7687f08 +U dan +Z a7fde54970dc241049366741c468ca23 diff --git a/manifest.uuid b/manifest.uuid index 3daf8bbf88..c0be3fa5e7 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -d06669d968c8f6af8799fbfeabadaab68b9b8db8 \ No newline at end of file +bc33af866403c23d548dd4705675315810d52d7f \ No newline at end of file diff --git a/src/wal.c b/src/wal.c index 558adbcad2..df3c8cb94e 100644 --- a/src/wal.c +++ b/src/wal.c @@ -1730,6 +1730,14 @@ static int walCheckpoint( mxSafeFrame = pWal->hdr.mxFrame; mxPage = pWal->hdr.nPage; for(i=1; iaReadMark[i]; if( mxSafeFrame>y ){ assert( y<=pWal->hdr.mxFrame ); From 27a348c7a0f26ea3037d0e8256f73a62dab84d31 Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 13 Apr 2015 19:14:06 +0000 Subject: [PATCH 33/53] Remove the out2-prerelease VDBE opcode property and its associated code, for a 0.5% performance improvement. FossilOrigin-Name: e29c7f2c910dac07f0f92dfef5e0e743141954eb --- manifest | 16 ++++----- manifest.uuid | 2 +- mkopcodeh.awk | 27 ++++++-------- src/vdbe.c | 97 +++++++++++++++++++++++++++++++-------------------- 4 files changed, 79 insertions(+), 63 deletions(-) diff --git a/manifest b/manifest index 12b1e15e95..acc5ea4f99 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\sa\scomment\sto\swal.c\sto\sexplain\swhy\sa\srace\scondition\sis\ssafe. -D 2015-04-13T17:43:43.335 +C Remove\sthe\sout2-prerelease\sVDBE\sopcode\sproperty\sand\sits\sassociated\scode,\nfor\sa\s0.5%\sperformance\simprovement. +D 2015-04-13T19:14:06.003 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -154,7 +154,7 @@ F ltmain.sh 3ff0879076df340d2e23ae905484d8c15d5fdea8 F magic.txt 8273bf49ba3b0c8559cb2774495390c31fd61c60 F main.mk ddffac494a82d42772df9fe30d3a78acf4f7cb41 F mkopcodec.awk c2ff431854d702cdd2d779c9c0d1f58fa16fa4ea -F mkopcodeh.awk c6b3fa301db6ef7ac916b14c60868aeaec1337b5 +F mkopcodeh.awk d5e22023b5238985bb54a72d33e0ac71fe4f8a32 F mkso.sh fd21c06b063bb16a5d25deea1752c2da6ac3ed83 F mptest/config01.test 3c6adcbc50b991866855f1977ff172eb6d901271 F mptest/config02.test 4415dfe36c48785f751e16e32c20b077c28ae504 @@ -293,7 +293,7 @@ F src/update.c 3c4ecc282accf12d39edb8d524cf089645e55a13 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 98a7627ca48ad3265b6940915a1d08355eb3fc7e F src/vacuum.c 2ddd5cad2a7b9cef7f9e431b8c7771634c6b1701 -F src/vdbe.c c4bd96912f8837777bfe5762d310767ed628b442 +F src/vdbe.c 584abb81e4abf9dd51a9a2e71f680289bd0c019b F src/vdbe.h 7e538ecf47dccb307ea2d087c3ddc2dd8d70e79d F src/vdbeInt.h 9cbaa84f53ddd2d09a0cf61a94337a3a035d08a0 F src/vdbeapi.c 583d56b129dd27f12bed518270de9ebe521e6a75 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P d06669d968c8f6af8799fbfeabadaab68b9b8db8 -R 90c9a3885d268edb8b0fe9dee7687f08 -U dan -Z a7fde54970dc241049366741c468ca23 +P bc33af866403c23d548dd4705675315810d52d7f +R 6ac0695a2f1b9d518c2805dcc9a01314 +U drh +Z 453362d5fdffab6ea02dce6dd25e18dd diff --git a/manifest.uuid b/manifest.uuid index c0be3fa5e7..5adaa0dcc9 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -bc33af866403c23d548dd4705675315810d52d7f \ No newline at end of file +e29c7f2c910dac07f0f92dfef5e0e743141954eb \ No newline at end of file diff --git a/mkopcodeh.awk b/mkopcodeh.awk index babfdc68d3..94db75e607 100644 --- a/mkopcodeh.awk +++ b/mkopcodeh.awk @@ -72,7 +72,6 @@ sub("\r","",name) op[name] = -1 # op[x] holds the numeric value for OP symbol x jump[name] = 0 - out2_prerelease[name] = 0 in1[name] = 0 in2[name] = 0 in3[name] = 0 @@ -92,8 +91,6 @@ sub(",","",x) if(x=="jump"){ jump[name] = 1 - }else if(x=="out2-prerelease"){ - out2_prerelease[name] = 1 }else if(x=="in1"){ in1[name] = 1 }else if(x=="in2"){ @@ -194,13 +191,12 @@ END { name = def[i] a0 = a1 = a2 = a3 = a4 = a5 = a6 = a7 = 0 if( jump[name] ) a0 = 1; - if( out2_prerelease[name] ) a1 = 2; - if( in1[name] ) a2 = 4; - if( in2[name] ) a3 = 8; - if( in3[name] ) a4 = 16; - if( out2[name] ) a5 = 32; - if( out3[name] ) a6 = 64; - bv[i] = a0+a1+a2+a3+a4+a5+a6+a7; + if( in1[name] ) a2 = 2; + if( in2[name] ) a3 = 4; + if( in3[name] ) a4 = 8; + if( out2[name] ) a5 = 16; + if( out3[name] ) a6 = 32; + bv[i] = a0+a1+a2+a3+a4+a5+a6; } print "\n" print "/* Properties such as \"out2\" or \"jump\" that are specified in" @@ -208,12 +204,11 @@ END { print "** are encoded into bitvectors as follows:" print "*/" print "#define OPFLG_JUMP 0x0001 /* jump: P2 holds jmp target */" - print "#define OPFLG_OUT2_PRERELEASE 0x0002 /* out2-prerelease: */" - print "#define OPFLG_IN1 0x0004 /* in1: P1 is an input */" - print "#define OPFLG_IN2 0x0008 /* in2: P2 is an input */" - print "#define OPFLG_IN3 0x0010 /* in3: P3 is an input */" - print "#define OPFLG_OUT2 0x0020 /* out2: P2 is an output */" - print "#define OPFLG_OUT3 0x0040 /* out3: P3 is an output */" + print "#define OPFLG_IN1 0x0002 /* in1: P1 is an input */" + print "#define OPFLG_IN2 0x0004 /* in2: P2 is an input */" + print "#define OPFLG_IN3 0x0008 /* in3: P3 is an input */" + print "#define OPFLG_OUT2 0x0010 /* out2: P2 is an output */" + print "#define OPFLG_OUT3 0x0020 /* out3: P3 is an output */" print "#define OPFLG_INITIALIZER {\\" for(i=0; i<=max; i++){ if( i%8==0 ) printf("/* %3d */",i) diff --git a/src/vdbe.c b/src/vdbe.c index 22b313756c..8492f8cc09 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -514,6 +514,21 @@ static int checkSavepointCount(sqlite3 *db){ } #endif +/* +** Return the register of pOp->p2 after first preparing it to be +** overwritten with an integer value. +*/ +static Mem *out2Prerelease(Vdbe *p, VdbeOp *pOp){ + Mem *pOut; + assert( pOp->p2>0 ); + assert( pOp->p2<=(p->nMem-p->nCursor) ); + pOut = &p->aMem[pOp->p2]; + memAboutToChange(p, pOut); + if( VdbeMemDynamic(pOut) ) sqlite3VdbeMemSetNull(pOut); + pOut->flags = MEM_Int; + return pOut; +} + /* ** Execute as much of a VDBE program as we can. @@ -633,23 +648,9 @@ int sqlite3VdbeExec( } #endif - /* On any opcode with the "out2-prerelease" tag, free any - ** external allocations out of mem[p2] and set mem[p2] to be - ** an undefined integer. Opcodes will either fill in the integer - ** value or convert mem[p2] to a different type. - */ - assert( pOp->opflags==sqlite3OpcodeProperty[pOp->opcode] ); - if( pOp->opflags & OPFLG_OUT2_PRERELEASE ){ - assert( pOp->p2>0 ); - assert( pOp->p2<=(p->nMem-p->nCursor) ); - pOut = &aMem[pOp->p2]; - memAboutToChange(p, pOut); - if( VdbeMemDynamic(pOut) ) sqlite3VdbeMemSetNull(pOut); - pOut->flags = MEM_Int; - } - /* Sanity checking on other operands */ #ifdef SQLITE_DEBUG + assert( pOp->opflags==sqlite3OpcodeProperty[pOp->opcode] ); if( (pOp->opflags & OPFLG_IN1)!=0 ){ assert( pOp->p1>0 ); assert( pOp->p1<=(p->nMem-p->nCursor) ); @@ -705,7 +706,7 @@ int sqlite3VdbeExec( ** ** Other keywords in the comment that follows each case are used to ** construct the OPFLG_INITIALIZER value that initializes opcodeProperty[]. -** Keywords include: in1, in2, in3, out2_prerelease, out2, out3. See +** Keywords include: in1, in2, in3, out2, out3. See ** the mkopcodeh.awk script for additional information. ** ** Documentation about VDBE opcodes is generated by scanning this file @@ -979,7 +980,8 @@ case OP_Halt: { ** ** The 32-bit integer value P1 is written into register P2. */ -case OP_Integer: { /* out2-prerelease */ +case OP_Integer: { /* out2 */ + pOut = out2Prerelease(p, pOp); pOut->u.i = pOp->p1; break; } @@ -990,7 +992,8 @@ case OP_Integer: { /* out2-prerelease */ ** P4 is a pointer to a 64-bit integer value. ** Write that value into register P2. */ -case OP_Int64: { /* out2-prerelease */ +case OP_Int64: { /* out2 */ + pOut = out2Prerelease(p, pOp); assert( pOp->p4.pI64!=0 ); pOut->u.i = *pOp->p4.pI64; break; @@ -1003,7 +1006,8 @@ case OP_Int64: { /* out2-prerelease */ ** P4 is a pointer to a 64-bit floating point value. ** Write that value into register P2. */ -case OP_Real: { /* same as TK_FLOAT, out2-prerelease */ +case OP_Real: { /* same as TK_FLOAT, out2 */ + pOut = out2Prerelease(p, pOp); pOut->flags = MEM_Real; assert( !sqlite3IsNaN(*pOp->p4.pReal) ); pOut->u.r = *pOp->p4.pReal; @@ -1019,8 +1023,9 @@ case OP_Real: { /* same as TK_FLOAT, out2-prerelease */ ** this transformation, the length of string P4 is computed and stored ** as the P1 parameter. */ -case OP_String8: { /* same as TK_STRING, out2-prerelease */ +case OP_String8: { /* same as TK_STRING, out2 */ assert( pOp->p4.z!=0 ); + pOut = out2Prerelease(p, pOp); pOp->opcode = OP_String; pOp->p1 = sqlite3Strlen30(pOp->p4.z); @@ -1057,8 +1062,9 @@ case OP_String8: { /* same as TK_STRING, out2-prerelease */ ** the same sequence of bytes, it is merely interpreted as a BLOB instead ** of a string, as if it had been CAST. */ -case OP_String: { /* out2-prerelease */ +case OP_String: { /* out2 */ assert( pOp->p4.z!=0 ); + pOut = out2Prerelease(p, pOp); pOut->flags = MEM_Str|MEM_Static|MEM_Term; pOut->z = pOp->p4.z; pOut->n = pOp->p1; @@ -1086,9 +1092,10 @@ case OP_String: { /* out2-prerelease */ ** NULL values will not compare equal even if SQLITE_NULLEQ is set on ** OP_Ne or OP_Eq. */ -case OP_Null: { /* out2-prerelease */ +case OP_Null: { /* out2 */ int cnt; u16 nullFlag; + pOut = out2Prerelease(p, pOp); cnt = pOp->p3-pOp->p2; assert( pOp->p3<=(p->nMem-p->nCursor) ); pOut->flags = nullFlag = pOp->p1 ? (MEM_Null|MEM_Cleared) : MEM_Null; @@ -1123,8 +1130,9 @@ case OP_SoftNull: { ** P4 points to a blob of data P1 bytes long. Store this ** blob in register P2. */ -case OP_Blob: { /* out2-prerelease */ +case OP_Blob: { /* out2 */ assert( pOp->p1 <= SQLITE_MAX_LENGTH ); + pOut = out2Prerelease(p, pOp); sqlite3VdbeMemSetStr(pOut, pOp->p4.z, pOp->p1, 0, 0); pOut->enc = encoding; UPDATE_MAX_BLOBSIZE(pOut); @@ -1139,7 +1147,7 @@ case OP_Blob: { /* out2-prerelease */ ** If the parameter is named, then its name appears in P4. ** The P4 value is used by sqlite3_bind_parameter_name(). */ -case OP_Variable: { /* out2-prerelease */ +case OP_Variable: { /* out2 */ Mem *pVar; /* Value being transferred */ assert( pOp->p1>0 && pOp->p1<=p->nVar ); @@ -1148,6 +1156,7 @@ case OP_Variable: { /* out2-prerelease */ if( sqlite3VdbeMemTooBig(pVar) ){ goto too_big; } + pOut = out2Prerelease(p, pOp); sqlite3VdbeMemShallowCopy(pOut, pVar, MEM_Static); UPDATE_MAX_BLOBSIZE(pOut); break; @@ -2721,7 +2730,7 @@ case OP_MakeRecord: { ** opened by cursor P1 in register P2 */ #ifndef SQLITE_OMIT_BTREECOUNT -case OP_Count: { /* out2-prerelease */ +case OP_Count: { /* out2 */ i64 nEntry; BtCursor *pCrsr; @@ -2729,6 +2738,7 @@ case OP_Count: { /* out2-prerelease */ assert( pCrsr ); nEntry = 0; /* Not needed. Only used to silence a warning. */ rc = sqlite3BtreeCount(pCrsr, &nEntry); + pOut = out2Prerelease(p, pOp); pOut->u.i = nEntry; break; } @@ -3117,7 +3127,7 @@ case OP_Transaction: { ** must be started or there must be an open cursor) before ** executing this instruction. */ -case OP_ReadCookie: { /* out2-prerelease */ +case OP_ReadCookie: { /* out2 */ int iMeta; int iDb; int iCookie; @@ -3131,6 +3141,7 @@ case OP_ReadCookie: { /* out2-prerelease */ assert( DbMaskTest(p->btreeMask, iDb) ); sqlite3BtreeGetMeta(db->aDb[iDb].pBt, iCookie, (u32 *)&iMeta); + pOut = out2Prerelease(p, pOp); pOut->u.i = iMeta; break; } @@ -3951,9 +3962,10 @@ case OP_NotExists: { /* jump, in3 */ ** The sequence number on the cursor is incremented after this ** instruction. */ -case OP_Sequence: { /* out2-prerelease */ +case OP_Sequence: { /* out2 */ assert( pOp->p1>=0 && pOp->p1nCursor ); assert( p->apCsr[pOp->p1]!=0 ); + pOut = out2Prerelease(p, pOp); pOut->u.i = p->apCsr[pOp->p1]->seqCount++; break; } @@ -3974,7 +3986,7 @@ case OP_Sequence: { /* out2-prerelease */ ** generated record number. This P3 mechanism is used to help implement the ** AUTOINCREMENT feature. */ -case OP_NewRowid: { /* out2-prerelease */ +case OP_NewRowid: { /* out2 */ i64 v; /* The new rowid */ VdbeCursor *pC; /* Cursor of table to get the new rowid */ int res; /* Result of an sqlite3BtreeLast() */ @@ -3984,6 +3996,7 @@ case OP_NewRowid: { /* out2-prerelease */ v = 0; res = 0; + pOut = out2Prerelease(p, pOp); assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); @@ -4428,12 +4441,13 @@ case OP_RowData: { ** be a separate OP_VRowid opcode for use with virtual tables, but this ** one opcode now works for both table types. */ -case OP_Rowid: { /* out2-prerelease */ +case OP_Rowid: { /* out2 */ VdbeCursor *pC; i64 v; sqlite3_vtab *pVtab; const sqlite3_module *pModule; + pOut = out2Prerelease(p, pOp); assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); @@ -4808,11 +4822,12 @@ case OP_IdxDelete: { ** ** See also: Rowid, MakeRecord. */ -case OP_IdxRowid: { /* out2-prerelease */ +case OP_IdxRowid: { /* out2 */ BtCursor *pCrsr; VdbeCursor *pC; i64 rowid; + pOut = out2Prerelease(p, pOp); assert( pOp->p1>=0 && pOp->p1nCursor ); pC = p->apCsr[pOp->p1]; assert( pC!=0 ); @@ -4951,11 +4966,12 @@ case OP_IdxGE: { /* jump */ ** ** See also: Clear */ -case OP_Destroy: { /* out2-prerelease */ +case OP_Destroy: { /* out2 */ int iMoved; int iDb; assert( p->readOnly==0 ); + pOut = out2Prerelease(p, pOp); pOut->flags = MEM_Null; if( db->nVdbeRead > db->nVDestroy+1 ){ rc = SQLITE_LOCKED; @@ -5064,12 +5080,13 @@ case OP_ResetSorter: { ** ** See documentation on OP_CreateTable for additional information. */ -case OP_CreateIndex: /* out2-prerelease */ -case OP_CreateTable: { /* out2-prerelease */ +case OP_CreateIndex: /* out2 */ +case OP_CreateTable: { /* out2 */ int pgno; int flags; Db *pDb; + pOut = out2Prerelease(p, pOp); pgno = 0; assert( pOp->p1>=0 && pOp->p1nDb ); assert( DbMaskTest(p->btreeMask, pOp->p1) ); @@ -5505,9 +5522,10 @@ case OP_Program: { /* jump */ ** the value of the P1 argument to the value of the P1 argument to the ** calling OP_Program instruction. */ -case OP_Param: { /* out2-prerelease */ +case OP_Param: { /* out2 */ VdbeFrame *pFrame; Mem *pIn; + pOut = out2Prerelease(p, pOp); pFrame = p->pFrame; pIn = &pFrame->aMem[pOp->p1 + pFrame->aOp[pFrame->pc].p1]; sqlite3VdbeMemShallowCopy(pOut, pIn, MEM_Ephem); @@ -5814,7 +5832,7 @@ case OP_Checkpoint: { ** ** Write a string containing the final journal-mode to register P2. */ -case OP_JournalMode: { /* out2-prerelease */ +case OP_JournalMode: { /* out2 */ Btree *pBt; /* Btree to change journal mode of */ Pager *pPager; /* Pager associated with pBt */ int eNew; /* New journal mode */ @@ -5823,6 +5841,7 @@ case OP_JournalMode: { /* out2-prerelease */ const char *zFilename; /* Name of database file for pPager */ #endif + pOut = out2Prerelease(p, pOp); eNew = pOp->p3; assert( eNew==PAGER_JOURNALMODE_DELETE || eNew==PAGER_JOURNALMODE_TRUNCATE @@ -6378,7 +6397,8 @@ case OP_VUpdate: { ** ** Write the current number of pages in database P1 to memory cell P2. */ -case OP_Pagecount: { /* out2-prerelease */ +case OP_Pagecount: { /* out2 */ + pOut = out2Prerelease(p, pOp); pOut->u.i = sqlite3BtreeLastPage(db->aDb[pOp->p1].pBt); break; } @@ -6394,10 +6414,11 @@ case OP_Pagecount: { /* out2-prerelease */ ** ** Store the maximum page count after the change in register P2. */ -case OP_MaxPgcnt: { /* out2-prerelease */ +case OP_MaxPgcnt: { /* out2 */ unsigned int newMax; Btree *pBt; + pOut = out2Prerelease(p, pOp); pBt = db->aDb[pOp->p1].pBt; newMax = 0; if( pOp->p3 ){ @@ -6503,7 +6524,7 @@ default: { /* This is really OP_Noop and OP_Explain */ #ifdef SQLITE_DEBUG if( db->flags & SQLITE_VdbeTrace ){ if( rc!=0 ) printf("rc=%d\n",rc); - if( pOp->opflags & (OPFLG_OUT2_PRERELEASE|OPFLG_OUT2) ){ + if( pOp->opflags & (OPFLG_OUT2) ){ registerTrace(pOp->p2, &aMem[pOp->p2]); } if( pOp->opflags & OPFLG_OUT3 ){ From f56fa4676e26c07b9ae45248e987e380743ce623 Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 13 Apr 2015 21:39:54 +0000 Subject: [PATCH 34/53] Omit the "pc" or "program counter" variable from the VDBE loop for 0.6% performance increase. FossilOrigin-Name: d2f10c41a832f520de13cf8315be22e66552f8e1 --- manifest | 12 +-- manifest.uuid | 2 +- src/vdbe.c | 215 +++++++++++++++++++++++--------------------------- 3 files changed, 105 insertions(+), 124 deletions(-) diff --git a/manifest b/manifest index acc5ea4f99..9ca1e537a7 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\sthe\sout2-prerelease\sVDBE\sopcode\sproperty\sand\sits\sassociated\scode,\nfor\sa\s0.5%\sperformance\simprovement. -D 2015-04-13T19:14:06.003 +C Omit\sthe\s"pc"\sor\s"program\scounter"\svariable\sfrom\sthe\sVDBE\sloop\sfor\s0.6%\nperformance\sincrease. +D 2015-04-13T21:39:54.858 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -293,7 +293,7 @@ F src/update.c 3c4ecc282accf12d39edb8d524cf089645e55a13 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c F src/util.c 98a7627ca48ad3265b6940915a1d08355eb3fc7e F src/vacuum.c 2ddd5cad2a7b9cef7f9e431b8c7771634c6b1701 -F src/vdbe.c 584abb81e4abf9dd51a9a2e71f680289bd0c019b +F src/vdbe.c 3f3afd12d4794cb51fe13dc948b1172a5eb71a94 F src/vdbe.h 7e538ecf47dccb307ea2d087c3ddc2dd8d70e79d F src/vdbeInt.h 9cbaa84f53ddd2d09a0cf61a94337a3a035d08a0 F src/vdbeapi.c 583d56b129dd27f12bed518270de9ebe521e6a75 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P bc33af866403c23d548dd4705675315810d52d7f -R 6ac0695a2f1b9d518c2805dcc9a01314 +P e29c7f2c910dac07f0f92dfef5e0e743141954eb +R 264d755a27d6975322da35a6d51f72d4 U drh -Z 453362d5fdffab6ea02dce6dd25e18dd +Z 01e6d8b5894e3dcd9945571fd6cd1cd0 diff --git a/manifest.uuid b/manifest.uuid index 5adaa0dcc9..28f820dc76 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -e29c7f2c910dac07f0f92dfef5e0e743141954eb \ No newline at end of file +d2f10c41a832f520de13cf8315be22e66552f8e1 \ No newline at end of file diff --git a/src/vdbe.c b/src/vdbe.c index 8492f8cc09..3bd4222c8b 100644 --- a/src/vdbe.c +++ b/src/vdbe.c @@ -537,9 +537,8 @@ static Mem *out2Prerelease(Vdbe *p, VdbeOp *pOp){ int sqlite3VdbeExec( Vdbe *p /* The VDBE */ ){ - int pc=0; /* The program counter */ Op *aOp = p->aOp; /* Copy of p->aOp */ - Op *pOp; /* Current operation */ + Op *pOp = aOp; /* Current operation */ int rc = SQLITE_OK; /* Value to return */ sqlite3 *db = p->db; /* The database */ u8 resetSchemaOnFault = 0; /* Reset schema after an error if positive */ @@ -615,23 +614,22 @@ int sqlite3VdbeExec( } sqlite3EndBenignMalloc(); #endif - for(pc=p->pc; rc==SQLITE_OK; pc++){ - assert( pc>=0 && pcnOp ); + for(pOp=&aOp[p->pc]; rc==SQLITE_OK; pOp++){ + assert( pOp>=aOp && pOp<&aOp[p->nOp]); if( db->mallocFailed ) goto no_mem; #ifdef VDBE_PROFILE start = sqlite3Hwtime(); #endif nVmStep++; - pOp = &aOp[pc]; #ifdef SQLITE_ENABLE_STMT_SCANSTATUS - if( p->anExec ) p->anExec[pc]++; + if( p->anExec ) p->anExec[(int)(pOp-aOp)]++; #endif /* Only allow tracing if SQLITE_DEBUG is defined. */ #ifdef SQLITE_DEBUG if( db->flags & SQLITE_VdbeTrace ){ - sqlite3VdbePrintOp(stdout, pc, pOp); + sqlite3VdbePrintOp(stdout, (int)(pOp - aOp), pOp); } #endif @@ -734,7 +732,8 @@ int sqlite3VdbeExec( ** to the current line should be indented for EXPLAIN output. */ case OP_Goto: { /* jump */ - pc = pOp->p2 - 1; +jump_to_p2_and_check_for_interrupt: + pOp = &aOp[pOp->p2 - 1]; /* Opcodes that are used as the bottom of a loop (OP_Next, OP_Prev, ** OP_VNext, OP_RowSetNext, or OP_SorterNext) all jump here upon @@ -779,9 +778,13 @@ case OP_Gosub: { /* jump */ assert( VdbeMemDynamic(pIn1)==0 ); memAboutToChange(p, pIn1); pIn1->flags = MEM_Int; - pIn1->u.i = pc; + pIn1->u.i = (int)(pOp-aOp); REGISTER_TRACE(pOp->p1, pIn1); - pc = pOp->p2 - 1; + + /* Most jump operations do a goto to this spot in order to update + ** the pOp pointer. */ +jump_to_p2: + pOp = &aOp[pOp->p2 - 1]; break; } @@ -793,7 +796,7 @@ case OP_Gosub: { /* jump */ case OP_Return: { /* in1 */ pIn1 = &aMem[pOp->p1]; assert( pIn1->flags==MEM_Int ); - pc = (int)pIn1->u.i; + pOp = &aOp[pIn1->u.i]; pIn1->flags = MEM_Undefined; break; } @@ -817,7 +820,7 @@ case OP_InitCoroutine: { /* jump */ assert( !VdbeMemDynamic(pOut) ); pOut->u.i = pOp->p3 - 1; pOut->flags = MEM_Int; - if( pOp->p2 ) pc = pOp->p2 - 1; + if( pOp->p2 ) goto jump_to_p2; break; } @@ -837,7 +840,7 @@ case OP_EndCoroutine: { /* in1 */ pCaller = &aOp[pIn1->u.i]; assert( pCaller->opcode==OP_Yield ); assert( pCaller->p2>=0 && pCaller->p2nOp ); - pc = pCaller->p2 - 1; + pOp = &aOp[pCaller->p2 - 1]; pIn1->flags = MEM_Undefined; break; } @@ -861,9 +864,9 @@ case OP_Yield: { /* in1, jump */ assert( VdbeMemDynamic(pIn1)==0 ); pIn1->flags = MEM_Int; pcDest = (int)pIn1->u.i; - pIn1->u.i = pc; + pIn1->u.i = (int)(pOp - aOp); REGISTER_TRACE(pOp->p1, pIn1); - pc = pcDest; + pOp = &aOp[pcDest]; break; } @@ -914,30 +917,34 @@ case OP_HaltIfNull: { /* in3 */ case OP_Halt: { const char *zType; const char *zLogFmt; + VdbeFrame *pFrame; + int pcx; + pcx = (int)(pOp - aOp); if( pOp->p1==SQLITE_OK && p->pFrame ){ /* Halt the sub-program. Return control to the parent frame. */ - VdbeFrame *pFrame = p->pFrame; + pFrame = p->pFrame; p->pFrame = pFrame->pParent; p->nFrame--; sqlite3VdbeSetChanges(db, p->nChange); - pc = sqlite3VdbeFrameRestore(pFrame); + pcx = sqlite3VdbeFrameRestore(pFrame); lastRowid = db->lastRowid; if( pOp->p2==OE_Ignore ){ - /* Instruction pc is the OP_Program that invoked the sub-program + /* Instruction pcx is the OP_Program that invoked the sub-program ** currently being halted. If the p2 instruction of this OP_Halt ** instruction is set to OE_Ignore, then the sub-program is throwing ** an IGNORE exception. In this case jump to the address specified ** as the p2 of the calling OP_Program. */ - pc = p->aOp[pc].p2-1; + pcx = p->aOp[pcx].p2-1; } aOp = p->aOp; aMem = p->aMem; + pOp = &aOp[pcx]; break; } p->rc = pOp->p1; p->errorAction = (u8)pOp->p2; - p->pc = pc; + p->pc = pcx; if( p->rc ){ if( pOp->p5 ){ static const char * const azType[] = { "NOT NULL", "UNIQUE", "CHECK", @@ -961,7 +968,7 @@ case OP_Halt: { }else{ sqlite3SetString(&p->zErrMsg, db, "%s constraint failed", zType); } - sqlite3_log(pOp->p1, zLogFmt, pc, p->zSql, p->zErrMsg); + sqlite3_log(pOp->p1, zLogFmt, pcx, p->zSql, p->zErrMsg); } rc = sqlite3VdbeHalt(p); assert( rc==SQLITE_BUSY || rc==SQLITE_OK || rc==SQLITE_ERROR ); @@ -972,6 +979,7 @@ case OP_Halt: { assert( rc==SQLITE_OK || db->nDeferredCons>0 || db->nDeferredImmCons>0 ); rc = p->rc ? SQLITE_ERROR : SQLITE_DONE; } + pOp = &aOp[pcx]; goto vdbe_return; } @@ -1333,7 +1341,7 @@ case OP_ResultRow: { /* Return SQLITE_ROW */ - p->pc = pc + 1; + p->pc = (int)(pOp - aOp) + 1; rc = SQLITE_ROW; goto vdbe_return; } @@ -1579,7 +1587,7 @@ case OP_Function: { assert( pOp->p4type==P4_FUNCDEF ); ctx.pFunc = pOp->p4.pFunc; - ctx.iOp = pc; + ctx.iOp = (int)(pOp - aOp); ctx.pVdbe = p; MemSetTypeFlag(ctx.pOut, MEM_Null); ctx.fErrorOrAux = 0; @@ -1593,7 +1601,7 @@ case OP_Function: { sqlite3SetString(&p->zErrMsg, db, "%s", sqlite3_value_text(ctx.pOut)); rc = ctx.isError; } - sqlite3VdbeDeleteAuxData(p, pc, pOp->p1); + sqlite3VdbeDeleteAuxData(p, (int)(pOp - aOp), pOp->p1); } /* Copy the result of the function into register P3 */ @@ -1722,8 +1730,7 @@ case OP_MustBeInt: { /* jump, in1 */ rc = SQLITE_MISMATCH; goto abort_due_to_error; }else{ - pc = pOp->p2 - 1; - break; + goto jump_to_p2; } } } @@ -1909,7 +1916,7 @@ case OP_Ge: { /* same as TK_GE, jump, in1, in3 */ }else{ VdbeBranchTaken(2,3); if( pOp->p5 & SQLITE_JUMPIFNULL ){ - pc = pOp->p2-1; + goto jump_to_p2; } } break; @@ -1961,6 +1968,12 @@ case OP_Ge: { /* same as TK_GE, jump, in1, in3 */ default: res = res>=0; break; } + /* Undo any changes made by applyAffinity() to the input registers. */ + assert( (pIn1->flags & MEM_Dyn) == (flags1 & MEM_Dyn) ); + pIn1->flags = flags1; + assert( (pIn3->flags & MEM_Dyn) == (flags3 & MEM_Dyn) ); + pIn3->flags = flags3; + if( pOp->p5 & SQLITE_STOREP2 ){ pOut = &aMem[pOp->p2]; memAboutToChange(p, pOut); @@ -1970,14 +1983,9 @@ case OP_Ge: { /* same as TK_GE, jump, in1, in3 */ }else{ VdbeBranchTaken(res!=0, (pOp->p5 & SQLITE_NULLEQ)?2:3); if( res ){ - pc = pOp->p2-1; + goto jump_to_p2; } } - /* Undo any changes made by applyAffinity() to the input registers. */ - assert( (pIn1->flags & MEM_Dyn) == (flags1 & MEM_Dyn) ); - pIn1->flags = flags1; - assert( (pIn3->flags & MEM_Dyn) == (flags3 & MEM_Dyn) ); - pIn3->flags = flags3; break; } @@ -2072,11 +2080,11 @@ case OP_Compare: { */ case OP_Jump: { /* jump */ if( iCompare<0 ){ - pc = pOp->p1 - 1; VdbeBranchTaken(0,3); + VdbeBranchTaken(0,3); pOp = &aOp[pOp->p1 - 1]; }else if( iCompare==0 ){ - pc = pOp->p2 - 1; VdbeBranchTaken(1,3); + VdbeBranchTaken(1,3); pOp = &aOp[pOp->p2 - 1]; }else{ - pc = pOp->p3 - 1; VdbeBranchTaken(2,3); + VdbeBranchTaken(2,3); pOp = &aOp[pOp->p3 - 1]; } break; } @@ -2186,7 +2194,7 @@ case OP_Once: { /* jump */ assert( pOp->p1nOnceFlag ); VdbeBranchTaken(p->aOnceFlag[pOp->p1]!=0, 2); if( p->aOnceFlag[pOp->p1] ){ - pc = pOp->p2-1; + goto jump_to_p2; }else{ p->aOnceFlag[pOp->p1] = 1; } @@ -2221,7 +2229,7 @@ case OP_IfNot: { /* jump, in1 */ } VdbeBranchTaken(c!=0, 2); if( c ){ - pc = pOp->p2-1; + goto jump_to_p2; } break; } @@ -2235,7 +2243,7 @@ case OP_IsNull: { /* same as TK_ISNULL, jump, in1 */ pIn1 = &aMem[pOp->p1]; VdbeBranchTaken( (pIn1->flags & MEM_Null)!=0, 2); if( (pIn1->flags & MEM_Null)!=0 ){ - pc = pOp->p2 - 1; + goto jump_to_p2; } break; } @@ -2249,7 +2257,7 @@ case OP_NotNull: { /* same as TK_NOTNULL, jump, in1 */ pIn1 = &aMem[pOp->p1]; VdbeBranchTaken( (pIn1->flags & MEM_Null)==0, 2); if( (pIn1->flags & MEM_Null)==0 ){ - pc = pOp->p2 - 1; + goto jump_to_p2; } break; } @@ -2852,7 +2860,7 @@ case OP_Savepoint: { } db->autoCommit = 1; if( sqlite3VdbeHalt(p)==SQLITE_BUSY ){ - p->pc = pc; + p->pc = (int)(pOp - aOp); db->autoCommit = 0; p->rc = rc = SQLITE_BUSY; goto vdbe_return; @@ -2971,7 +2979,7 @@ case OP_AutoCommit: { }else{ db->autoCommit = (u8)desiredAutoCommit; if( sqlite3VdbeHalt(p)==SQLITE_BUSY ){ - p->pc = pc; + p->pc = (int)(pOp - aOp); db->autoCommit = (u8)(1-desiredAutoCommit); p->rc = rc = SQLITE_BUSY; goto vdbe_return; @@ -3048,7 +3056,7 @@ case OP_Transaction: { if( pBt ){ rc = sqlite3BtreeBeginTrans(pBt, pOp->p2); if( rc==SQLITE_BUSY ){ - p->pc = pc; + p->pc = (int)(pOp - aOp); p->rc = rc = SQLITE_BUSY; goto vdbe_return; } @@ -3463,7 +3471,7 @@ case OP_SequenceTest: { pC = p->apCsr[pOp->p1]; assert( pC->pSorter ); if( (pC->seqCount++)==0 ){ - pc = pOp->p2 - 1; + goto jump_to_p2; } break; } @@ -3640,7 +3648,7 @@ case OP_SeekGT: { /* jump, in3 */ if( (pIn3->flags & MEM_Real)==0 ){ /* If the P3 value cannot be converted into any kind of a number, ** then the seek is not possible, so jump to P2 */ - pc = pOp->p2 - 1; VdbeBranchTaken(1,2); + VdbeBranchTaken(1,2); goto jump_to_p2; break; } @@ -3731,7 +3739,7 @@ case OP_SeekGT: { /* jump, in3 */ assert( pOp->p2>0 ); VdbeBranchTaken(res!=0,2); if( res ){ - pc = pOp->p2 - 1; + goto jump_to_p2; } break; } @@ -3825,6 +3833,7 @@ case OP_NoConflict: /* jump, in3 */ case OP_NotFound: /* jump, in3 */ case OP_Found: { /* jump, in3 */ int alreadyExists; + int takeJump; int ii; VdbeCursor *pC; int res; @@ -3847,7 +3856,7 @@ case OP_Found: { /* jump, in3 */ pIn3 = &aMem[pOp->p3]; assert( pC->pCursor!=0 ); assert( pC->isTable==0 ); - pFree = 0; /* Not needed. Only used to suppress a compiler warning. */ + pFree = 0; if( pOp->p4.i>0 ){ r.pKeyInfo = pC->pKeyInfo; r.nField = (u16)pOp->p4.i; @@ -3870,21 +3879,20 @@ case OP_Found: { /* jump, in3 */ sqlite3VdbeRecordUnpack(pC->pKeyInfo, pIn3->n, pIn3->z, pIdxKey); } pIdxKey->default_rc = 0; + takeJump = 0; if( pOp->opcode==OP_NoConflict ){ /* For the OP_NoConflict opcode, take the jump if any of the ** input fields are NULL, since any key with a NULL will not ** conflict */ for(ii=0; iinField; ii++){ if( pIdxKey->aMem[ii].flags & MEM_Null ){ - pc = pOp->p2 - 1; VdbeBranchTaken(1,2); + takeJump = 1; break; } } } rc = sqlite3BtreeMovetoUnpacked(pC->pCursor, pIdxKey, 0, 0, &res); - if( pOp->p4.i==0 ){ - sqlite3DbFree(db, pFree); - } + sqlite3DbFree(db, pFree); if( rc!=SQLITE_OK ){ break; } @@ -3895,10 +3903,10 @@ case OP_Found: { /* jump, in3 */ pC->cacheStatus = CACHE_STALE; if( pOp->opcode==OP_Found ){ VdbeBranchTaken(alreadyExists!=0,2); - if( alreadyExists ) pc = pOp->p2 - 1; + if( alreadyExists ) goto jump_to_p2; }else{ - VdbeBranchTaken(alreadyExists==0,2); - if( !alreadyExists ) pc = pOp->p2 - 1; + VdbeBranchTaken(takeJump||alreadyExists==0,2); + if( takeJump || !alreadyExists ) goto jump_to_p2; } break; } @@ -3947,10 +3955,8 @@ case OP_NotExists: { /* jump, in3 */ pC->cacheStatus = CACHE_STALE; pC->deferredMoveto = 0; VdbeBranchTaken(res!=0,2); - if( res!=0 ){ - pc = pOp->p2 - 1; - } pC->seekResult = res; + if( res!=0 ) goto jump_to_p2; break; } @@ -4310,9 +4316,7 @@ case OP_SorterCompare: { res = 0; rc = sqlite3VdbeSorterCompare(pC, pIn3, nKeyCol, &res); VdbeBranchTaken(res!=0,2); - if( res ){ - pc = pOp->p2-1; - } + if( res ) goto jump_to_p2; break; }; @@ -4533,7 +4537,7 @@ case OP_Last: { /* jump */ #endif if( pOp->p2>0 ){ VdbeBranchTaken(res!=0,2); - if( res ) pc = pOp->p2 - 1; + if( res ) goto jump_to_p2; } break; } @@ -4597,9 +4601,7 @@ case OP_Rewind: { /* jump */ pC->nullRow = (u8)res; assert( pOp->p2>0 && pOp->p2nOp ); VdbeBranchTaken(res!=0,2); - if( res ){ - pc = pOp->p2 - 1; - } + if( res ) goto jump_to_p2; break; } @@ -4710,11 +4712,11 @@ next_tail: VdbeBranchTaken(res==0,2); if( res==0 ){ pC->nullRow = 0; - pc = pOp->p2 - 1; p->aCounter[pOp->p5]++; #ifdef SQLITE_TEST sqlite3_search_count++; #endif + goto jump_to_p2_and_check_for_interrupt; }else{ pC->nullRow = 1; } @@ -4940,9 +4942,7 @@ case OP_IdxGE: { /* jump */ res++; } VdbeBranchTaken(res>0,2); - if( res>0 ){ - pc = pOp->p2 - 1 ; - } + if( res>0 ) goto jump_to_p2; break; } @@ -5312,12 +5312,12 @@ case OP_RowSetRead: { /* jump, in1, out3 */ ){ /* The boolean index is empty */ sqlite3VdbeMemSetNull(pIn1); - pc = pOp->p2 - 1; VdbeBranchTaken(1,2); + goto jump_to_p2_and_check_for_interrupt; }else{ /* A value was pulled from the index */ - sqlite3VdbeMemSetInt64(&aMem[pOp->p3], val); VdbeBranchTaken(0,2); + sqlite3VdbeMemSetInt64(&aMem[pOp->p3], val); } goto check_for_interrupt; } @@ -5368,10 +5368,7 @@ case OP_RowSetTest: { /* jump, in1, in3 */ if( iSet ){ exists = sqlite3RowSetTest(pIn1->u.pRowSet, iSet, pIn3->u.i); VdbeBranchTaken(exists!=0,2); - if( exists ){ - pc = pOp->p2 - 1; - break; - } + if( exists ) goto jump_to_p2; } if( iSet>=0 ){ sqlite3RowSetInsert(pIn1->u.pRowSet, pIn3->u.i); @@ -5460,7 +5457,7 @@ case OP_Program: { /* jump */ pFrame->v = p; pFrame->nChildMem = nMem; pFrame->nChildCsr = pProgram->nCsr; - pFrame->pc = pc; + pFrame->pc = (int)(pOp - aOp); pFrame->aMem = p->aMem; pFrame->nMem = p->nMem; pFrame->apCsr = p->apCsr; @@ -5483,7 +5480,7 @@ case OP_Program: { /* jump */ pFrame = pRt->u.pFrame; assert( pProgram->nMem+pProgram->nCsr==pFrame->nChildMem ); assert( pProgram->nCsr==pFrame->nChildCsr ); - assert( pc==pFrame->pc ); + assert( (int)(pOp - aOp)==pFrame->pc ); } p->nFrame++; @@ -5504,7 +5501,7 @@ case OP_Program: { /* jump */ #ifdef SQLITE_ENABLE_STMT_SCANSTATUS p->anExec = 0; #endif - pc = -1; + pOp = &aOp[-1]; memset(p->aOnceFlag, 0, p->nOnceFlag); break; @@ -5569,10 +5566,10 @@ case OP_FkCounter: { case OP_FkIfZero: { /* jump */ if( pOp->p1 ){ VdbeBranchTaken(db->nDeferredCons==0 && db->nDeferredImmCons==0, 2); - if( db->nDeferredCons==0 && db->nDeferredImmCons==0 ) pc = pOp->p2-1; + if( db->nDeferredCons==0 && db->nDeferredImmCons==0 ) goto jump_to_p2; }else{ VdbeBranchTaken(p->nFkConstraint==0 && db->nDeferredImmCons==0, 2); - if( p->nFkConstraint==0 && db->nDeferredImmCons==0 ) pc = pOp->p2-1; + if( p->nFkConstraint==0 && db->nDeferredImmCons==0 ) goto jump_to_p2; } break; } @@ -5623,9 +5620,7 @@ case OP_IfPos: { /* jump, in1 */ pIn1 = &aMem[pOp->p1]; assert( pIn1->flags&MEM_Int ); VdbeBranchTaken( pIn1->u.i>0, 2); - if( pIn1->u.i>0 ){ - pc = pOp->p2 - 1; - } + if( pIn1->u.i>0 ) goto jump_to_p2; break; } @@ -5640,9 +5635,7 @@ case OP_IfNeg: { /* jump, in1 */ assert( pIn1->flags&MEM_Int ); pIn1->u.i += pOp->p3; VdbeBranchTaken(pIn1->u.i<0, 2); - if( pIn1->u.i<0 ){ - pc = pOp->p2 - 1; - } + if( pIn1->u.i<0 ) goto jump_to_p2; break; } @@ -5659,7 +5652,7 @@ case OP_IfNotZero: { /* jump, in1 */ VdbeBranchTaken(pIn1->u.i<0, 2); if( pIn1->u.i ){ pIn1->u.i += pOp->p3; - pc = pOp->p2 - 1; + goto jump_to_p2; } break; } @@ -5675,9 +5668,7 @@ case OP_DecrJumpZero: { /* jump, in1 */ assert( pIn1->flags&MEM_Int ); pIn1->u.i--; VdbeBranchTaken(pIn1->u.i==0, 2); - if( pIn1->u.i==0 ){ - pc = pOp->p2 - 1; - } + if( pIn1->u.i==0 ) goto jump_to_p2; break; } @@ -5693,9 +5684,7 @@ case OP_JumpZeroIncr: { /* jump, in1 */ pIn1 = &aMem[pOp->p1]; assert( pIn1->flags&MEM_Int ); VdbeBranchTaken(pIn1->u.i==0, 2); - if( (pIn1->u.i++)==0 ){ - pc = pOp->p2 - 1; - } + if( (pIn1->u.i++)==0 ) goto jump_to_p2; break; } @@ -5737,7 +5726,7 @@ case OP_AggStep: { ctx.pOut = &t; ctx.isError = 0; ctx.pVdbe = p; - ctx.iOp = pc; + ctx.iOp = (int)(pOp - aOp); ctx.skipFlag = 0; (ctx.pFunc->xStep)(&ctx, n, apVal); /* IMP: R-24505-23230 */ if( ctx.isError ){ @@ -5958,8 +5947,8 @@ case OP_IncrVacuum: { /* jump */ rc = sqlite3BtreeIncrVacuum(pBt); VdbeBranchTaken(rc==SQLITE_DONE,2); if( rc==SQLITE_DONE ){ - pc = pOp->p2 - 1; rc = SQLITE_OK; + goto jump_to_p2; } break; } @@ -6169,25 +6158,19 @@ case OP_VFilter: { /* jump */ iQuery = (int)pQuery->u.i; /* Invoke the xFilter method */ - { - res = 0; - apArg = p->apArg; - for(i = 0; ixFilter(pVtabCursor, iQuery, pOp->p4.z, nArg, apArg); - sqlite3VtabImportErrmsg(p, pVtab); - if( rc==SQLITE_OK ){ - res = pModule->xEof(pVtabCursor); - } - VdbeBranchTaken(res!=0,2); - if( res ){ - pc = pOp->p2 - 1; - } + res = 0; + apArg = p->apArg; + for(i = 0; ixFilter(pVtabCursor, iQuery, pOp->p4.z, nArg, apArg); + sqlite3VtabImportErrmsg(p, pVtab); + if( rc==SQLITE_OK ){ + res = pModule->xEof(pVtabCursor); } pCur->nullRow = 0; - + VdbeBranchTaken(res!=0,2); + if( res ) goto jump_to_p2; break; } #endif /* SQLITE_OMIT_VIRTUALTABLE */ @@ -6274,7 +6257,7 @@ case OP_VNext: { /* jump */ VdbeBranchTaken(!res,2); if( !res ){ /* If there is data, jump to P2 */ - pc = pOp->p2 - 1; + goto jump_to_p2_and_check_for_interrupt; } goto check_for_interrupt; } @@ -6447,9 +6430,6 @@ case OP_Init: { /* jump */ char *zTrace; char *z; - if( pOp->p2 ){ - pc = pOp->p2 - 1; - } #ifndef SQLITE_OMIT_TRACE if( db->xTrace && !p->doingRerun @@ -6477,6 +6457,7 @@ case OP_Init: { /* jump */ } #endif /* SQLITE_DEBUG */ #endif /* SQLITE_OMIT_TRACE */ + if( pOp->p2 ) goto jump_to_p2; break; } @@ -6519,7 +6500,7 @@ default: { /* This is really OP_Noop and OP_Explain */ ** the evaluator loop. So we can leave it out when NDEBUG is defined. */ #ifndef NDEBUG - assert( pc>=-1 && pcnOp ); + assert( pOp>=&aOp[-1] && pOp<&aOp[p->nOp] ); #ifdef SQLITE_DEBUG if( db->flags & SQLITE_VdbeTrace ){ @@ -6543,7 +6524,7 @@ vdbe_error_halt: p->rc = rc; testcase( sqlite3GlobalConfig.xLog!=0 ); sqlite3_log(rc, "statement aborts at %d: [%s] %s", - pc, p->zSql, p->zErrMsg); + (int)(pOp - aOp), p->zSql, p->zErrMsg); sqlite3VdbeHalt(p); if( rc==SQLITE_IOERR_NOMEM ) db->mallocFailed = 1; rc = SQLITE_ERROR; From 2647dfa2928aaa3907680d55c1df94b1d8c40eea Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 13 Apr 2015 22:26:55 +0000 Subject: [PATCH 35/53] On a DETACH statement, keep all schemas intact except fo the one that is being detached, and thus avoid unnecessary schema reparsing. FossilOrigin-Name: 661db19b34566642dd44ee4cff4ebc093cb8a552 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/attach.c | 2 +- 3 files changed, 8 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 9ca1e537a7..924612731f 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Omit\sthe\s"pc"\sor\s"program\scounter"\svariable\sfrom\sthe\sVDBE\sloop\sfor\s0.6%\nperformance\sincrease. -D 2015-04-13T21:39:54.858 +C On\sa\sDETACH\sstatement,\skeep\sall\sschemas\sintact\sexcept\sfo\sthe\sone\sthat\sis\nbeing\sdetached,\sand\sthus\savoid\sunnecessary\sschema\sreparsing. +D 2015-04-13T22:26:55.617 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -168,7 +168,7 @@ F sqlite3.1 fc7ad8990fc8409983309bb80de8c811a7506786 F sqlite3.pc.in 48fed132e7cb71ab676105d2a4dc77127d8c1f3a F src/alter.c d23d6b6991f66b383934f137fd4384d93fb98c81 F src/analyze.c 91540f835163d5369ccbae78e2e6c74d0dd53c1d -F src/attach.c 880f9b8641a829c563e52dd13c452ce457ae4dd8 +F src/attach.c 3c1053a4cf1c3ca05c8c1d74a94cb688d763cef2 F src/auth.c b56c78ebe40a2110fd361379f7e8162d23f92240 F src/backup.c ff743689c4d6c5cb55ad42ed9d174b2b3e71f1e3 F src/bitvec.c 19a4ba637bd85f8f63fc8c9bae5ade9fb05ec1cb @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P e29c7f2c910dac07f0f92dfef5e0e743141954eb -R 264d755a27d6975322da35a6d51f72d4 +P d2f10c41a832f520de13cf8315be22e66552f8e1 +R 49212af07046904ea6b82f6ec3cc0926 U drh -Z 01e6d8b5894e3dcd9945571fd6cd1cd0 +Z b2d6c204725accd9dcc524641d192884 diff --git a/manifest.uuid b/manifest.uuid index 28f820dc76..c643643efb 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -d2f10c41a832f520de13cf8315be22e66552f8e1 \ No newline at end of file +661db19b34566642dd44ee4cff4ebc093cb8a552 \ No newline at end of file diff --git a/src/attach.c b/src/attach.c index 7e35fa67c6..11296d02ad 100644 --- a/src/attach.c +++ b/src/attach.c @@ -298,7 +298,7 @@ static void detachFunc( sqlite3BtreeClose(pDb->pBt); pDb->pBt = 0; pDb->pSchema = 0; - sqlite3ResetAllSchemasOfConnection(db); + sqlite3CollapseDatabaseArray(db); return; detach_error: From 6bca6511666674870a081f05eec9f708ac1ce072 Mon Sep 17 00:00:00 2001 From: drh Date: Mon, 13 Apr 2015 23:05:28 +0000 Subject: [PATCH 36/53] Add #ifdef magic for HAVE_GETHOSTUUID so that the build will hopefully now work on more verions of MacOS with SQLITE_ENABLE_LOCKING_STYLE turned on. FossilOrigin-Name: 211411d02c0729c9af0e3cc7e4910db2e7e0d08e --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/os_unix.c | 16 ++++++++++++++-- 3 files changed, 21 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 924612731f..148ae45ff6 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C On\sa\sDETACH\sstatement,\skeep\sall\sschemas\sintact\sexcept\sfo\sthe\sone\sthat\sis\nbeing\sdetached,\sand\sthus\savoid\sunnecessary\sschema\sreparsing. -D 2015-04-13T22:26:55.617 +C Add\s#ifdef\smagic\sfor\sHAVE_GETHOSTUUID\sso\sthat\sthe\sbuild\swill\shopefully\snow\nwork\son\smore\sverions\sof\sMacOS\swith\sSQLITE_ENABLE_LOCKING_STYLE\sturned\son. +D 2015-04-13T23:05:28.978 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -214,7 +214,7 @@ F src/os.c 8fd25588eeba74068d41102d26810e216999b6c8 F src/os.h 3e57a24e2794a94d3cf2342c6d9a884888cd96bf F src/os_common.h 92815ed65f805560b66166e3583470ff94478f04 F src/os_setup.h c9d4553b5aaa6f73391448b265b89bed0b890faa -F src/os_unix.c 25b80a3d167da44226a2084dc9e89a6cb1f02e2e +F src/os_unix.c 5ed7e2e453c2980909a6b2c80dc55764b50819a8 F src/os_win.c 03d27be3a20048ef52a648d5f0a15f5edda9f2a3 F src/os_win.h eb7a47aa17b26b77eb97e4823f20a00b8bda12ca F src/pager.c 4120a49ecd37697e28f5ed807f470b9c0b88410c @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P d2f10c41a832f520de13cf8315be22e66552f8e1 -R 49212af07046904ea6b82f6ec3cc0926 +P 661db19b34566642dd44ee4cff4ebc093cb8a552 +R 8591357f8b00a438bdaa3b5a16ff0e3f U drh -Z b2d6c204725accd9dcc524641d192884 +Z d2025877377cf6ead9db7636c81d5974 diff --git a/manifest.uuid b/manifest.uuid index c643643efb..8657041788 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -661db19b34566642dd44ee4cff4ebc093cb8a552 \ No newline at end of file +211411d02c0729c9af0e3cc7e4910db2e7e0d08e \ No newline at end of file diff --git a/src/os_unix.c b/src/os_unix.c index 1d867d7cd8..188c025336 100644 --- a/src/os_unix.c +++ b/src/os_unix.c @@ -91,6 +91,17 @@ # include #endif /* SQLITE_ENABLE_LOCKING_STYLE */ +#if defined(__APPLE__) && ((__MAC_OS_X_VERSION_MIN_REQUIRED > 1050) || \ + (__IPHONE_OS_VERSION_MIN_REQUIRED > 2000)) +# if (!defined(TARGET_OS_EMBEDDED) || (TARGET_OS_EMBEDDED==0)) \ + && (!defined(TARGET_IPHONE_SIMULATOR) || (TARGET_IPHONE_SIMULATOR==0)) +# define HAVE_GETHOSTUUID 1 +# else +# warning "gethostuuid() is disabled." +# endif +#endif + + #if OS_VXWORKS # include # include @@ -6602,8 +6613,10 @@ int sqlite3_hostid_num = 0; #define PROXY_HOSTIDLEN 16 /* conch file host id length */ +#ifdef HAVE_GETHOSTUUID /* Not always defined in the headers as it ought to be */ extern int gethostuuid(uuid_t id, const struct timespec *wait); +#endif /* get the host ID via gethostuuid(), pHostID must point to PROXY_HOSTIDLEN ** bytes of writable memory. @@ -6611,8 +6624,7 @@ extern int gethostuuid(uuid_t id, const struct timespec *wait); static int proxyGetHostID(unsigned char *pHostID, int *pError){ assert(PROXY_HOSTIDLEN == sizeof(uuid_t)); memset(pHostID, 0, PROXY_HOSTIDLEN); -# if defined(__APPLE__) && ((__MAC_OS_X_VERSION_MIN_REQUIRED > 1050) || \ - (__IPHONE_OS_VERSION_MIN_REQUIRED > 2000)) +#ifdef HAVE_GETHOSTUUID { struct timespec timeout = {1, 0}; /* 1 sec timeout */ if( gethostuuid(pHostID, &timeout) ){ From d9a0a9a0c6db9ac1d224ff886f89a09af720088f Mon Sep 17 00:00:00 2001 From: drh Date: Tue, 14 Apr 2015 15:14:06 +0000 Subject: [PATCH 37/53] Update API documentation to identify many functions as methods on objects. No changes to code. FossilOrigin-Name: b549cbcee1c11f9ffedf763ca672b125eac87bfe --- manifest | 12 +++--- manifest.uuid | 2 +- src/sqlite.h.in | 100 ++++++++++++++++++++++++++++++++++++++++++------ 3 files changed, 95 insertions(+), 19 deletions(-) diff --git a/manifest b/manifest index 148ae45ff6..c795bef110 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\s#ifdef\smagic\sfor\sHAVE_GETHOSTUUID\sso\sthat\sthe\sbuild\swill\shopefully\snow\nwork\son\smore\sverions\sof\sMacOS\swith\sSQLITE_ENABLE_LOCKING_STYLE\sturned\son. -D 2015-04-13T23:05:28.978 +C Update\sAPI\sdocumentation\sto\sidentify\smany\sfunctions\sas\smethods\son\sobjects.\nNo\schanges\sto\scode. +D 2015-04-14T15:14:06.177 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -232,7 +232,7 @@ F src/resolve.c 41aa91af56d960e9414ce1d7c17cfb68e0d1c6cb F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e F src/select.c 117e0f9ac9254a6f7472fac5144eba21ba0b2ec1 F src/shell.c 84a1593bd86aaa14f4da8a8f9b16fbc239d262aa -F src/sqlite.h.in 278602140d49575e8708e643161f4263e428a02a +F src/sqlite.h.in ca27603a36fcacdaac5a19d8ee35aaff8ce8516f F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad F src/sqlite3ext.h 17d487c3c91b0b8c584a32fbeb393f6f795eea7d F src/sqliteInt.h 90b7bfd89d7307cd0750663da419ba4bb81e7379 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 661db19b34566642dd44ee4cff4ebc093cb8a552 -R 8591357f8b00a438bdaa3b5a16ff0e3f +P 211411d02c0729c9af0e3cc7e4910db2e7e0d08e +R 32297e2ca295bdee2feb4a534c04bc42 U drh -Z d2025877377cf6ead9db7636c81d5974 +Z 358af9cd25fc843b833aaa97a1900951 diff --git a/manifest.uuid b/manifest.uuid index 8657041788..5721ce9565 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -211411d02c0729c9af0e3cc7e4910db2e7e0d08e \ No newline at end of file +b549cbcee1c11f9ffedf763ca672b125eac87bfe \ No newline at end of file diff --git a/src/sqlite.h.in b/src/sqlite.h.in index acc3c51404..163bc69fe7 100644 --- a/src/sqlite.h.in +++ b/src/sqlite.h.in @@ -270,6 +270,7 @@ typedef sqlite_uint64 sqlite3_uint64; /* ** CAPI3REF: Closing A Database Connection +** DESTRUCTOR: sqlite3 ** ** ^The sqlite3_close() and sqlite3_close_v2() routines are destructors ** for the [sqlite3] object. @@ -321,6 +322,7 @@ typedef int (*sqlite3_callback)(void*,int,char**, char**); /* ** CAPI3REF: One-Step Query Execution Interface +** METHOD: sqlite3 ** ** The sqlite3_exec() interface is a convenience wrapper around ** [sqlite3_prepare_v2()], [sqlite3_step()], and [sqlite3_finalize()], @@ -1378,6 +1380,7 @@ int sqlite3_config(int, ...); /* ** CAPI3REF: Configure database connections +** METHOD: sqlite3 ** ** The sqlite3_db_config() interface is used to make configuration ** changes to a [database connection]. The interface is similar to @@ -1875,6 +1878,7 @@ struct sqlite3_mem_methods { /* ** CAPI3REF: Enable Or Disable Extended Result Codes +** METHOD: sqlite3 ** ** ^The sqlite3_extended_result_codes() routine enables or disables the ** [extended result codes] feature of SQLite. ^The extended result @@ -1884,6 +1888,7 @@ int sqlite3_extended_result_codes(sqlite3*, int onoff); /* ** CAPI3REF: Last Insert Rowid +** METHOD: sqlite3 ** ** ^Each entry in most SQLite tables (except for [WITHOUT ROWID] tables) ** has a unique 64-bit signed @@ -1935,6 +1940,7 @@ sqlite3_int64 sqlite3_last_insert_rowid(sqlite3*); /* ** CAPI3REF: Count The Number Of Rows Modified +** METHOD: sqlite3 ** ** ^This function returns the number of rows modified, inserted or ** deleted by the most recently completed INSERT, UPDATE or DELETE @@ -1987,6 +1993,7 @@ int sqlite3_changes(sqlite3*); /* ** CAPI3REF: Total Number Of Rows Modified +** METHOD: sqlite3 ** ** ^This function returns the total number of rows inserted, modified or ** deleted by all [INSERT], [UPDATE] or [DELETE] statements completed @@ -2010,6 +2017,7 @@ int sqlite3_total_changes(sqlite3*); /* ** CAPI3REF: Interrupt A Long-Running Query +** METHOD: sqlite3 ** ** ^This function causes any pending database operation to abort and ** return at its earliest opportunity. This routine is typically @@ -2086,6 +2094,7 @@ int sqlite3_complete16(const void *sql); /* ** CAPI3REF: Register A Callback To Handle SQLITE_BUSY Errors ** KEYWORDS: {busy-handler callback} {busy handler} +** METHOD: sqlite3 ** ** ^The sqlite3_busy_handler(D,X,P) routine sets a callback function X ** that might be invoked with argument P whenever @@ -2145,6 +2154,7 @@ int sqlite3_busy_handler(sqlite3*, int(*)(void*,int), void*); /* ** CAPI3REF: Set A Busy Timeout +** METHOD: sqlite3 ** ** ^This routine sets a [sqlite3_busy_handler | busy handler] that sleeps ** for a specified amount of time when a table is locked. ^The handler @@ -2167,6 +2177,7 @@ int sqlite3_busy_timeout(sqlite3*, int ms); /* ** CAPI3REF: Convenience Routines For Running Queries +** METHOD: sqlite3 ** ** This is a legacy interface that is preserved for backwards compatibility. ** Use of this interface is not recommended. @@ -2502,6 +2513,7 @@ void sqlite3_randomness(int N, void *P); /* ** CAPI3REF: Compile-Time Authorization Callbacks +** METHOD: sqlite3 ** ** ^This routine registers an authorizer callback with a particular ** [database connection], supplied in the first argument. @@ -2658,6 +2670,7 @@ int sqlite3_set_authorizer( /* ** CAPI3REF: Tracing And Profiling Functions +** METHOD: sqlite3 ** ** These routines register callback functions that can be used for ** tracing and profiling the execution of SQL statements. @@ -2690,6 +2703,7 @@ SQLITE_EXPERIMENTAL void *sqlite3_profile(sqlite3*, /* ** CAPI3REF: Query Progress Callbacks +** METHOD: sqlite3 ** ** ^The sqlite3_progress_handler(D,N,X,P) interface causes the callback ** function X to be invoked periodically during long running calls to @@ -2723,6 +2737,7 @@ void sqlite3_progress_handler(sqlite3*, int, int(*)(void*), void*); /* ** CAPI3REF: Opening A New Database Connection +** CONSTRUCTOR: sqlite3 ** ** ^These routines open an SQLite database file as specified by the ** filename argument. ^The filename argument is interpreted as UTF-8 for @@ -3008,6 +3023,7 @@ sqlite3_int64 sqlite3_uri_int64(const char*, const char*, sqlite3_int64); /* ** CAPI3REF: Error Codes And Messages +** METHOD: sqlite3 ** ** ^If the most recent sqlite3_* API call associated with ** [database connection] D failed, then the sqlite3_errcode(D) interface @@ -3053,33 +3069,34 @@ const void *sqlite3_errmsg16(sqlite3*); const char *sqlite3_errstr(int); /* -** CAPI3REF: SQL Statement Object +** CAPI3REF: Prepared Statement Object ** KEYWORDS: {prepared statement} {prepared statements} ** -** An instance of this object represents a single SQL statement. -** This object is variously known as a "prepared statement" or a -** "compiled SQL statement" or simply as a "statement". +** An instance of this object represents a single SQL statement that +** has been compiled into binary form and is ready to be evaluated. ** -** The life of a statement object goes something like this: +** Think of each SQL statement as a separate computer program. The +** original SQL text is source code. A prepared statement object +** is the compiled object code. All SQL must be converted into a +** prepared statement before it can be run. +** +** The life-cycle of a prepared statement object usually goes like this: ** **
    -**
  1. Create the object using [sqlite3_prepare_v2()] or a related -** function. -**
  2. Bind values to [host parameters] using the sqlite3_bind_*() +**
  3. Create the prepared statement object using [sqlite3_prepare_v2()]. +**
  4. Bind values to [parameters] using the sqlite3_bind_*() ** interfaces. **
  5. Run the SQL by calling [sqlite3_step()] one or more times. -**
  6. Reset the statement using [sqlite3_reset()] then go back +**
  7. Reset the prepared statement using [sqlite3_reset()] then go back ** to step 2. Do this zero or more times. **
  8. Destroy the object using [sqlite3_finalize()]. **
-** -** Refer to documentation on individual methods above for additional -** information. */ typedef struct sqlite3_stmt sqlite3_stmt; /* ** CAPI3REF: Run-time Limits +** METHOD: sqlite3 ** ** ^(This interface allows the size of various constructs to be limited ** on a connection by connection basis. The first parameter is the @@ -3191,6 +3208,8 @@ int sqlite3_limit(sqlite3*, int id, int newVal); /* ** CAPI3REF: Compiling An SQL Statement ** KEYWORDS: {SQL statement compiler} +** METHOD: sqlite3 +** CONSTRUCTOR: sqlite3_stmt ** ** To execute an SQL query, it must first be compiled into a byte-code ** program using one of these routines. @@ -3298,6 +3317,7 @@ int sqlite3_prepare16_v2( /* ** CAPI3REF: Retrieving Statement SQL +** METHOD: sqlite3_stmt ** ** ^This interface can be used to retrieve a saved copy of the original ** SQL text used to create a [prepared statement] if that statement was @@ -3307,6 +3327,7 @@ const char *sqlite3_sql(sqlite3_stmt *pStmt); /* ** CAPI3REF: Determine If An SQL Statement Writes The Database +** METHOD: sqlite3_stmt ** ** ^The sqlite3_stmt_readonly(X) interface returns true (non-zero) if ** and only if the [prepared statement] X makes no direct changes to @@ -3338,6 +3359,7 @@ int sqlite3_stmt_readonly(sqlite3_stmt *pStmt); /* ** CAPI3REF: Determine If A Prepared Statement Has Been Reset +** METHOD: sqlite3_stmt ** ** ^The sqlite3_stmt_busy(S) interface returns true (non-zero) if the ** [prepared statement] S has been stepped at least once using @@ -3412,6 +3434,7 @@ typedef struct sqlite3_context sqlite3_context; ** CAPI3REF: Binding Values To Prepared Statements ** KEYWORDS: {host parameter} {host parameters} {host parameter name} ** KEYWORDS: {SQL parameter} {SQL parameters} {parameter binding} +** METHOD: sqlite3_stmt ** ** ^(In the SQL statement text input to [sqlite3_prepare_v2()] and its variants, ** literals may be replaced by a [parameter] that matches one of following @@ -3530,6 +3553,7 @@ int sqlite3_bind_zeroblob(sqlite3_stmt*, int, int n); /* ** CAPI3REF: Number Of SQL Parameters +** METHOD: sqlite3_stmt ** ** ^This routine can be used to find the number of [SQL parameters] ** in a [prepared statement]. SQL parameters are tokens of the @@ -3550,6 +3574,7 @@ int sqlite3_bind_parameter_count(sqlite3_stmt*); /* ** CAPI3REF: Name Of A Host Parameter +** METHOD: sqlite3_stmt ** ** ^The sqlite3_bind_parameter_name(P,N) interface returns ** the name of the N-th [SQL parameter] in the [prepared statement] P. @@ -3577,6 +3602,7 @@ const char *sqlite3_bind_parameter_name(sqlite3_stmt*, int); /* ** CAPI3REF: Index Of A Parameter With A Given Name +** METHOD: sqlite3_stmt ** ** ^Return the index of an SQL parameter given its name. ^The ** index value returned is suitable for use as the second @@ -3593,6 +3619,7 @@ int sqlite3_bind_parameter_index(sqlite3_stmt*, const char *zName); /* ** CAPI3REF: Reset All Bindings On A Prepared Statement +** METHOD: sqlite3_stmt ** ** ^Contrary to the intuition of many, [sqlite3_reset()] does not reset ** the [sqlite3_bind_blob | bindings] on a [prepared statement]. @@ -3602,6 +3629,7 @@ int sqlite3_clear_bindings(sqlite3_stmt*); /* ** CAPI3REF: Number Of Columns In A Result Set +** METHOD: sqlite3_stmt ** ** ^Return the number of columns in the result set returned by the ** [prepared statement]. ^This routine returns 0 if pStmt is an SQL @@ -3613,6 +3641,7 @@ int sqlite3_column_count(sqlite3_stmt *pStmt); /* ** CAPI3REF: Column Names In A Result Set +** METHOD: sqlite3_stmt ** ** ^These routines return the name assigned to a particular column ** in the result set of a [SELECT] statement. ^The sqlite3_column_name() @@ -3642,6 +3671,7 @@ const void *sqlite3_column_name16(sqlite3_stmt*, int N); /* ** CAPI3REF: Source Of Data In A Query Result +** METHOD: sqlite3_stmt ** ** ^These routines provide a means to determine the database, table, and ** table column that is the origin of a particular result column in @@ -3694,6 +3724,7 @@ const void *sqlite3_column_origin_name16(sqlite3_stmt*,int); /* ** CAPI3REF: Declared Datatype Of A Query Result +** METHOD: sqlite3_stmt ** ** ^(The first parameter is a [prepared statement]. ** If this statement is a [SELECT] statement and the Nth column of the @@ -3726,6 +3757,7 @@ const void *sqlite3_column_decltype16(sqlite3_stmt*,int); /* ** CAPI3REF: Evaluate An SQL Statement +** METHOD: sqlite3_stmt ** ** After a [prepared statement] has been prepared using either ** [sqlite3_prepare_v2()] or [sqlite3_prepare16_v2()] or one of the legacy @@ -3805,6 +3837,7 @@ int sqlite3_step(sqlite3_stmt*); /* ** CAPI3REF: Number of columns in a result set +** METHOD: sqlite3_stmt ** ** ^The sqlite3_data_count(P) interface returns the number of columns in the ** current row of the result set of [prepared statement] P. @@ -3858,6 +3891,7 @@ int sqlite3_data_count(sqlite3_stmt *pStmt); /* ** CAPI3REF: Result Values From A Query ** KEYWORDS: {column access functions} +** METHOD: sqlite3_stmt ** ** These routines form the "result set" interface. ** @@ -4030,6 +4064,7 @@ sqlite3_value *sqlite3_column_value(sqlite3_stmt*, int iCol); /* ** CAPI3REF: Destroy A Prepared Statement Object +** DESTRUCTOR: sqlite3_stmt ** ** ^The sqlite3_finalize() function is called to delete a [prepared statement]. ** ^If the most recent evaluation of the statement encountered no errors @@ -4057,6 +4092,7 @@ int sqlite3_finalize(sqlite3_stmt *pStmt); /* ** CAPI3REF: Reset A Prepared Statement Object +** METHOD: sqlite3_stmt ** ** The sqlite3_reset() function is called to reset a [prepared statement] ** object back to its initial state, ready to be re-executed. @@ -4086,6 +4122,7 @@ int sqlite3_reset(sqlite3_stmt *pStmt); ** KEYWORDS: {function creation routines} ** KEYWORDS: {application-defined SQL function} ** KEYWORDS: {application-defined SQL functions} +** METHOD: sqlite3 ** ** ^These functions (collectively known as "function creation routines") ** are used to add SQL functions or aggregates or to redefine the behavior @@ -4255,6 +4292,7 @@ SQLITE_DEPRECATED int sqlite3_memory_alarm(void(*)(void*,sqlite3_int64,int), /* ** CAPI3REF: Obtaining SQL Function Parameter Values +** METHOD: sqlite3_value ** ** The C-language implementation of SQL functions and aggregates uses ** this set of interface routines to access the parameter values on @@ -4313,6 +4351,7 @@ int sqlite3_value_numeric_type(sqlite3_value*); /* ** CAPI3REF: Obtain Aggregate Function Context +** METHOD: sqlite3_context ** ** Implementations of aggregate SQL functions use this ** routine to allocate memory for storing their state. @@ -4357,6 +4396,7 @@ void *sqlite3_aggregate_context(sqlite3_context*, int nBytes); /* ** CAPI3REF: User Data For Functions +** METHOD: sqlite3_context ** ** ^The sqlite3_user_data() interface returns a copy of ** the pointer that was the pUserData parameter (the 5th parameter) @@ -4371,6 +4411,7 @@ void *sqlite3_user_data(sqlite3_context*); /* ** CAPI3REF: Database Connection For Functions +** METHOD: sqlite3_context ** ** ^The sqlite3_context_db_handle() interface returns a copy of ** the pointer to the [database connection] (the 1st parameter) @@ -4382,6 +4423,7 @@ sqlite3 *sqlite3_context_db_handle(sqlite3_context*); /* ** CAPI3REF: Function Auxiliary Data +** METHOD: sqlite3_context ** ** These functions may be used by (non-aggregate) SQL functions to ** associate metadata with argument values. If the same value is passed to @@ -4454,6 +4496,7 @@ typedef void (*sqlite3_destructor_type)(void*); /* ** CAPI3REF: Setting The Result Of An SQL Function +** METHOD: sqlite3_context ** ** These routines are used by the xFunc or xFinal callbacks that ** implement SQL functions and aggregates. See @@ -4589,6 +4632,7 @@ void sqlite3_result_zeroblob(sqlite3_context*, int n); /* ** CAPI3REF: Define New Collating Sequences +** METHOD: sqlite3 ** ** ^These functions add, remove, or modify a [collation] associated ** with the [database connection] specified as the first argument. @@ -4691,6 +4735,7 @@ int sqlite3_create_collation16( /* ** CAPI3REF: Collation Needed Callbacks +** METHOD: sqlite3 ** ** ^To avoid having to register all collation sequences before a database ** can be used, a single callback function may be registered with the @@ -4898,6 +4943,7 @@ SQLITE_EXTERN char *sqlite3_data_directory; /* ** CAPI3REF: Test For Auto-Commit Mode ** KEYWORDS: {autocommit mode} +** METHOD: sqlite3 ** ** ^The sqlite3_get_autocommit() interface returns non-zero or ** zero if the given database connection is or is not in autocommit mode, @@ -4920,6 +4966,7 @@ int sqlite3_get_autocommit(sqlite3*); /* ** CAPI3REF: Find The Database Handle Of A Prepared Statement +** METHOD: sqlite3_stmt ** ** ^The sqlite3_db_handle interface returns the [database connection] handle ** to which a [prepared statement] belongs. ^The [database connection] @@ -4932,6 +4979,7 @@ sqlite3 *sqlite3_db_handle(sqlite3_stmt*); /* ** CAPI3REF: Return The Filename For A Database Connection +** METHOD: sqlite3 ** ** ^The sqlite3_db_filename(D,N) interface returns a pointer to a filename ** associated with database N of connection D. ^The main database file @@ -4948,6 +4996,7 @@ const char *sqlite3_db_filename(sqlite3 *db, const char *zDbName); /* ** CAPI3REF: Determine if a database is read-only +** METHOD: sqlite3 ** ** ^The sqlite3_db_readonly(D,N) interface returns 1 if the database N ** of connection D is read-only, 0 if it is read/write, or -1 if N is not @@ -4957,6 +5006,7 @@ int sqlite3_db_readonly(sqlite3 *db, const char *zDbName); /* ** CAPI3REF: Find the next prepared statement +** METHOD: sqlite3 ** ** ^This interface returns a pointer to the next [prepared statement] after ** pStmt associated with the [database connection] pDb. ^If pStmt is NULL @@ -4972,6 +5022,7 @@ sqlite3_stmt *sqlite3_next_stmt(sqlite3 *pDb, sqlite3_stmt *pStmt); /* ** CAPI3REF: Commit And Rollback Notification Callbacks +** METHOD: sqlite3 ** ** ^The sqlite3_commit_hook() interface registers a callback ** function to be invoked whenever a transaction is [COMMIT | committed]. @@ -5021,6 +5072,7 @@ void *sqlite3_rollback_hook(sqlite3*, void(*)(void *), void*); /* ** CAPI3REF: Data Change Notification Callbacks +** METHOD: sqlite3 ** ** ^The sqlite3_update_hook() interface registers a callback function ** with the [database connection] identified by the first argument @@ -5127,6 +5179,7 @@ int sqlite3_release_memory(int); /* ** CAPI3REF: Free Memory Used By A Database Connection +** METHOD: sqlite3 ** ** ^The sqlite3_db_release_memory(D) interface attempts to free as much heap ** memory as possible from database connection D. Unlike the @@ -5204,6 +5257,7 @@ SQLITE_DEPRECATED void sqlite3_soft_heap_limit(int N); /* ** CAPI3REF: Extract Metadata About A Column Of A Table +** METHOD: sqlite3 ** ** ^(The sqlite3_table_column_metadata(X,D,T,C,....) routine returns ** information about column C of table T in database D @@ -5282,6 +5336,7 @@ int sqlite3_table_column_metadata( /* ** CAPI3REF: Load An Extension +** METHOD: sqlite3 ** ** ^This interface loads an SQLite extension library from the named file. ** @@ -5323,6 +5378,7 @@ int sqlite3_load_extension( /* ** CAPI3REF: Enable Or Disable Extension Loading +** METHOD: sqlite3 ** ** ^So as not to open security holes in older applications that are ** unprepared to deal with [extension loading], and as a means of disabling @@ -5572,6 +5628,7 @@ struct sqlite3_index_info { /* ** CAPI3REF: Register A Virtual Table Implementation +** METHOD: sqlite3 ** ** ^These routines are used to register a new [virtual table module] name. ** ^Module names must be registered before @@ -5668,6 +5725,7 @@ int sqlite3_declare_vtab(sqlite3*, const char *zSQL); /* ** CAPI3REF: Overload A Function For A Virtual Table +** METHOD: sqlite3 ** ** ^(Virtual tables can provide alternative implementations of functions ** using the [xFindFunction] method of the [virtual table module]. @@ -5710,6 +5768,8 @@ typedef struct sqlite3_blob sqlite3_blob; /* ** CAPI3REF: Open A BLOB For Incremental I/O +** METHOD: sqlite3 +** CONSTRUCTOR: sqlite3_blob ** ** ^(This interfaces opens a [BLOB handle | handle] to the BLOB located ** in row iRow, column zColumn, table zTable in database zDb; @@ -5791,6 +5851,7 @@ int sqlite3_blob_open( /* ** CAPI3REF: Move a BLOB Handle to a New Row +** METHOD: sqlite3_blob ** ** ^This function is used to move an existing blob handle so that it points ** to a different row of the same database table. ^The new row is identified @@ -5815,6 +5876,7 @@ SQLITE_EXPERIMENTAL int sqlite3_blob_reopen(sqlite3_blob *, sqlite3_int64); /* ** CAPI3REF: Close A BLOB Handle +** DESTRUCTOR: sqlite3_blob ** ** ^This function closes an open [BLOB handle]. ^(The BLOB handle is closed ** unconditionally. Even if this routine returns an error code, the @@ -5837,6 +5899,7 @@ int sqlite3_blob_close(sqlite3_blob *); /* ** CAPI3REF: Return The Size Of An Open BLOB +** METHOD: sqlite3_blob ** ** ^Returns the size in bytes of the BLOB accessible via the ** successfully opened [BLOB handle] in its only argument. ^The @@ -5852,6 +5915,7 @@ int sqlite3_blob_bytes(sqlite3_blob *); /* ** CAPI3REF: Read Data From A BLOB Incrementally +** METHOD: sqlite3_blob ** ** ^(This function is used to read data from an open [BLOB handle] into a ** caller-supplied buffer. N bytes of data are copied into buffer Z @@ -5880,6 +5944,7 @@ int sqlite3_blob_read(sqlite3_blob *, void *Z, int N, int iOffset); /* ** CAPI3REF: Write Data Into A BLOB Incrementally +** METHOD: sqlite3_blob ** ** ^(This function is used to write data into an open [BLOB handle] from a ** caller-supplied buffer. N bytes of data are copied from the buffer Z @@ -6207,6 +6272,7 @@ int sqlite3_mutex_notheld(sqlite3_mutex*); /* ** CAPI3REF: Retrieve the mutex for a database connection +** METHOD: sqlite3 ** ** ^This interface returns a pointer the [sqlite3_mutex] object that ** serializes access to the [database connection] given in the argument @@ -6218,6 +6284,7 @@ sqlite3_mutex *sqlite3_db_mutex(sqlite3*); /* ** CAPI3REF: Low-Level Control Of Database Files +** METHOD: sqlite3 ** ** ^The [sqlite3_file_control()] interface makes a direct call to the ** xFileControl method for the [sqlite3_io_methods] object associated @@ -6434,6 +6501,7 @@ int sqlite3_status64( /* ** CAPI3REF: Database Connection Status +** METHOD: sqlite3 ** ** ^This interface is used to retrieve runtime status information ** about a single [database connection]. ^The first argument is the @@ -6562,6 +6630,7 @@ int sqlite3_db_status(sqlite3*, int op, int *pCur, int *pHiwtr, int resetFlg); /* ** CAPI3REF: Prepared Statement Status +** METHOD: sqlite3_stmt ** ** ^(Each prepared statement maintains various ** [SQLITE_STMTSTATUS counters] that measure the number @@ -7065,6 +7134,7 @@ int sqlite3_backup_pagecount(sqlite3_backup *p); /* ** CAPI3REF: Unlock Notification +** METHOD: sqlite3 ** ** ^When running in shared-cache mode, a database operation may fail with ** an [SQLITE_LOCKED] error if the required locks on the shared-cache or @@ -7235,6 +7305,7 @@ void sqlite3_log(int iErrCode, const char *zFormat, ...); /* ** CAPI3REF: Write-Ahead Log Commit Hook +** METHOD: sqlite3 ** ** ^The [sqlite3_wal_hook()] function is used to register a callback that ** is invoked each time data is committed to a database in wal mode. @@ -7274,6 +7345,7 @@ void *sqlite3_wal_hook( /* ** CAPI3REF: Configure an auto-checkpoint +** METHOD: sqlite3 ** ** ^The [sqlite3_wal_autocheckpoint(D,N)] is a wrapper around ** [sqlite3_wal_hook()] that causes any database on [database connection] D @@ -7304,6 +7376,7 @@ int sqlite3_wal_autocheckpoint(sqlite3 *db, int N); /* ** CAPI3REF: Checkpoint a database +** METHOD: sqlite3 ** ** ^(The sqlite3_wal_checkpoint(D,X) is equivalent to ** [sqlite3_wal_checkpoint_v2](D,X,[SQLITE_CHECKPOINT_PASSIVE],0,0).)^ @@ -7325,6 +7398,7 @@ int sqlite3_wal_checkpoint(sqlite3 *db, const char *zDb); /* ** CAPI3REF: Checkpoint a database +** METHOD: sqlite3 ** ** ^(The sqlite3_wal_checkpoint_v2(D,X,M,L,C) interface runs a checkpoint ** operation on database X of [database connection] D in mode M. Status @@ -7579,6 +7653,7 @@ int sqlite3_vtab_on_conflict(sqlite3 *); /* ** CAPI3REF: Prepared Statement Scan Status +** METHOD: sqlite3_stmt ** ** This interface returns information about the predicted and measured ** performance for pStmt. Advanced applications can use this @@ -7616,6 +7691,7 @@ SQLITE_EXPERIMENTAL int sqlite3_stmt_scanstatus( /* ** CAPI3REF: Zero Scan-Status Counters +** METHOD: sqlite3_stmt ** ** ^Zero all [sqlite3_stmt_scanstatus()] related event counters. ** From 8a1cd765dfae89bb23a8ce61101f299d8a225334 Mon Sep 17 00:00:00 2001 From: drh Date: Tue, 14 Apr 2015 19:01:08 +0000 Subject: [PATCH 38/53] Add the --summary option to the sqldiff command-line tool. FossilOrigin-Name: 88b22761c59b06fa86c57f8d22a46046ad17d5d5 --- manifest | 12 +-- manifest.uuid | 2 +- tool/sqldiff.c | 238 ++++++++++++++++++++++++++++++++++++++----------- 3 files changed, 192 insertions(+), 60 deletions(-) diff --git a/manifest b/manifest index c795bef110..821eb96f29 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Update\sAPI\sdocumentation\sto\sidentify\smany\sfunctions\sas\smethods\son\sobjects.\nNo\schanges\sto\scode. -D 2015-04-14T15:14:06.177 +C Add\sthe\s--summary\soption\sto\sthe\ssqldiff\scommand-line\stool. +D 2015-04-14T19:01:08.549 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -1239,7 +1239,7 @@ F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e F tool/split-sqlite3c.tcl d9be87f1c340285a3e081eb19b4a247981ed290c -F tool/sqldiff.c 51c05cc1435507736b8b5a41a0498016041b3e48 +F tool/sqldiff.c 5c16cf3a1f566873abbdecac0d13a6691437564f F tool/stack_usage.tcl f8e71b92cdb099a147dad572375595eae55eca43 F tool/symbols-mingw.sh 4dbcea7e74768305384c9fd2ed2b41bbf9f0414d F tool/symbols.sh fec58532668296d7c7dc48be9c87f75ccdb5814f @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 211411d02c0729c9af0e3cc7e4910db2e7e0d08e -R 32297e2ca295bdee2feb4a534c04bc42 +P b549cbcee1c11f9ffedf763ca672b125eac87bfe +R 64950626ad311356247b51bbef2cd09d U drh -Z 358af9cd25fc843b833aaa97a1900951 +Z 2d35d7a2b23bff60413bdff46818cee3 diff --git a/manifest.uuid b/manifest.uuid index 5721ce9565..674f6cdaa2 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -b549cbcee1c11f9ffedf763ca672b125eac87bfe \ No newline at end of file +88b22761c59b06fa86c57f8d22a46046ad17d5d5 \ No newline at end of file diff --git a/tool/sqldiff.c b/tool/sqldiff.c index 4455c582ef..c7b59400df 100644 --- a/tool/sqldiff.c +++ b/tool/sqldiff.c @@ -356,18 +356,18 @@ static char **columnNames(const char *zDb, const char *zTab, int *pnPKey){ /* ** Print the sqlite3_value X as an SQL literal. */ -static void printQuoted(sqlite3_value *X){ +static void printQuoted(FILE *out, sqlite3_value *X){ switch( sqlite3_value_type(X) ){ case SQLITE_FLOAT: { double r1; char zBuf[50]; r1 = sqlite3_value_double(X); sqlite3_snprintf(sizeof(zBuf), zBuf, "%!.15g", r1); - printf("%s", zBuf); + fprintf(out, "%s", zBuf); break; } case SQLITE_INTEGER: { - printf("%lld", sqlite3_value_int64(X)); + fprintf(out, "%lld", sqlite3_value_int64(X)); break; } case SQLITE_BLOB: { @@ -375,13 +375,13 @@ static void printQuoted(sqlite3_value *X){ int nBlob = sqlite3_value_bytes(X); if( zBlob ){ int i; - printf("x'"); + fprintf(out, "x'"); for(i=0; i Date: Wed, 15 Apr 2015 04:10:50 +0000 Subject: [PATCH 39/53] An oversize hex literal can cause a parsing error while generating code for constants that are factored out of the main body of the VDBE program. So allow for that case. FossilOrigin-Name: a084690b4fcabba20d9770ebf3a014dda84e2954 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/build.c | 2 +- test/hexlit.test | 5 +++++ 4 files changed, 14 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 821eb96f29..70d58da81f 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\sthe\s--summary\soption\sto\sthe\ssqldiff\scommand-line\stool. -D 2015-04-14T19:01:08.549 +C An\soversize\shex\sliteral\scan\scause\sa\sparsing\serror\swhile\sgenerating\scode\sfor\nconstants\sthat\sare\sfactored\sout\sof\sthe\smain\sbody\sof\sthe\sVDBE\sprogram.\s\sSo\nallow\sfor\sthat\scase. +D 2015-04-15T04:10:50.814 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -176,7 +176,7 @@ F src/btmutex.c 45a968cc85afed9b5e6cf55bf1f42f8d18107f79 F src/btree.c 67648f6532c2da79d3b3fb6853aa1a0c3ba0e1ad F src/btree.h 969adc948e89e449220ff0ff724c94bb2a52e9f1 F src/btreeInt.h 973a22a6fd61350b454ad614832b1f0a5e25a1e4 -F src/build.c fa4795bc795077388aa4e746e1b25ef97bc10489 +F src/build.c 01b969b20a44a3d9620e597d9af8242348123540 F src/callback.c 7b44ce59674338ad48b0e84e7b72f935ea4f68b0 F src/complete.c a5cf5b4b56390cfb7b8636e8f7ddef90258dd575 F src/ctime.c 98f89724adc891a1a4c655bee04e33e716e05887 @@ -633,7 +633,7 @@ F test/fuzz_malloc.test 328f70aaca63adf29b4c6f06505ed0cf57ca7c26 F test/fuzzer1.test d4c52aaf3ef923da293a2653cfab33d02f718a36 F test/fuzzerfault.test 8792cd77fd5bce765b05d0c8e01b9edcf8af8536 F test/genesis.tcl 1e2e2e8e5cc4058549a154ff1892fe5c9de19f98 -F test/hexlit.test f9ecde8145bfc2341573473256c74ae37a200497 +F test/hexlit.test 1d312fa816dfd3650a3bb488093bc09a0c927f67 F test/hook.test 162d7cef7a2d2b04839fe14402934e6a1b79442f F test/icu.test 70df4faca133254c042d02ae342c0a141f2663f4 F test/imposter1.test c3f1db2d3db2c24611a6596a3fc0ffc14f1466c8 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P b549cbcee1c11f9ffedf763ca672b125eac87bfe -R 64950626ad311356247b51bbef2cd09d +P 88b22761c59b06fa86c57f8d22a46046ad17d5d5 +R a0a6eb36c09cbd9c15f1359867fe74af U drh -Z 2d35d7a2b23bff60413bdff46818cee3 +Z 7045f923a68da4f66662aff61189246b diff --git a/manifest.uuid b/manifest.uuid index 674f6cdaa2..81075d42b9 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -88b22761c59b06fa86c57f8d22a46046ad17d5d5 \ No newline at end of file +a084690b4fcabba20d9770ebf3a014dda84e2954 \ No newline at end of file diff --git a/src/build.c b/src/build.c index 9d8465561f..3021ad4e51 100644 --- a/src/build.c +++ b/src/build.c @@ -226,7 +226,7 @@ void sqlite3FinishCoding(Parse *pParse){ /* Get the VDBE program ready for execution */ - if( v && ALWAYS(pParse->nErr==0) && !db->mallocFailed ){ + if( v && pParse->nErr==0 && !db->mallocFailed ){ assert( pParse->iCacheLevel==0 ); /* Disables and re-enables match */ /* A minimum of one cursor is required if autoincrement is used * See ticket [a696379c1f08866] */ diff --git a/test/hexlit.test b/test/hexlit.test index 10909e6f4c..2edd458e89 100644 --- a/test/hexlit.test +++ b/test/hexlit.test @@ -109,6 +109,11 @@ do_execsql_test hexlit-301 { do_catchsql_test hexlist-400 { SELECT 0x10000000000000000; } {1 {hex literal too big: 0x10000000000000000}} +do_catchsql_test hexlist-410 { + DROP TABLE IF EXISTS t1; + CREATE TABLE t1(x); + INSERT INTO t1 VALUES(1+0x10000000000000000); +} {1 {hex literal too big: 0x10000000000000000}} finish_test From 311efc70a74a01d22b4d90c87490cda41b0b110a Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 04:20:58 +0000 Subject: [PATCH 40/53] Add a test case for what was formerly thought to be an unreachable condition: when the LHS of an OR operator contains an error and the RHS contains an IN operator. FossilOrigin-Name: 3872742591add4e94033484c2844e7d7ab69674b --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/expr.c | 2 +- test/in.test | 6 ++++++ 4 files changed, 15 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 70d58da81f..8ac7986648 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C An\soversize\shex\sliteral\scan\scause\sa\sparsing\serror\swhile\sgenerating\scode\sfor\nconstants\sthat\sare\sfactored\sout\sof\sthe\smain\sbody\sof\sthe\sVDBE\sprogram.\s\sSo\nallow\sfor\sthat\scase. -D 2015-04-15T04:10:50.814 +C Add\sa\stest\scase\sfor\swhat\swas\sformerly\sthought\sto\sbe\san\sunreachable\scondition:\nwhen\sthe\sLHS\sof\san\sOR\soperator\scontains\san\serror\sand\sthe\sRHS\scontains\san\sIN\noperator. +D 2015-04-15T04:20:58.065 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -182,7 +182,7 @@ F src/complete.c a5cf5b4b56390cfb7b8636e8f7ddef90258dd575 F src/ctime.c 98f89724adc891a1a4c655bee04e33e716e05887 F src/date.c e4d50b3283696836ec1036b695ead9a19e37a5ac F src/delete.c 37964e6c1d73ff49cbea9ff690c9605fb15f600e -F src/expr.c d09dac67d53c78880ba31d56e8ba2be3a6490553 +F src/expr.c aba4f0547aac1fcbd965d548ab2e36efd5a4481c F src/fault.c 160a0c015b6c2629d3899ed2daf63d75754a32bb F src/fkey.c 3343d551a8d810782257244fb33f2ce191493c39 F src/func.c 1414c24c873c48796ad45942257a179a423ba42f @@ -637,7 +637,7 @@ F test/hexlit.test 1d312fa816dfd3650a3bb488093bc09a0c927f67 F test/hook.test 162d7cef7a2d2b04839fe14402934e6a1b79442f F test/icu.test 70df4faca133254c042d02ae342c0a141f2663f4 F test/imposter1.test c3f1db2d3db2c24611a6596a3fc0ffc14f1466c8 -F test/in.test 047c4671328e9032ab95666a67021adbbd36e98e +F test/in.test b52fa96bcf6cebc5c8829c822315d0f87af9c6c2 F test/in2.test 5d4c61d17493c832f7d2d32bef785119e87bde75 F test/in3.test 3cbf58c87f4052cee3a58b37b6389777505aa0c0 F test/in4.test d2b38cba404bc4320f4fe1b595b3d163f212c068 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 88b22761c59b06fa86c57f8d22a46046ad17d5d5 -R a0a6eb36c09cbd9c15f1359867fe74af +P a084690b4fcabba20d9770ebf3a014dda84e2954 +R fcf0b4147f04a74e05def15e3b1a56b8 U drh -Z 7045f923a68da4f66662aff61189246b +Z 041867bd4c7c23a09c20a9ae6f8ff29f diff --git a/manifest.uuid b/manifest.uuid index 81075d42b9..f94b10f78e 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -a084690b4fcabba20d9770ebf3a014dda84e2954 \ No newline at end of file +3872742591add4e94033484c2844e7d7ab69674b \ No newline at end of file diff --git a/src/expr.c b/src/expr.c index e6ac0f6796..6a30755aa5 100644 --- a/src/expr.c +++ b/src/expr.c @@ -1691,7 +1691,7 @@ int sqlite3FindInIndex(Parse *pParse, Expr *pX, u32 inFlags, int *prRhsHasNull){ ** ephemeral table. */ p = (ExprHasProperty(pX, EP_xIsSelect) ? pX->x.pSelect : 0); - if( ALWAYS(pParse->nErr==0) && isCandidateForInOpt(p) ){ + if( pParse->nErr==0 && isCandidateForInOpt(p) ){ sqlite3 *db = pParse->db; /* Database connection */ Table *pTab; /* Table . */ Expr *pExpr; /* Expression */ diff --git a/test/in.test b/test/in.test index 515e598c12..de38c22456 100644 --- a/test/in.test +++ b/test/in.test @@ -615,6 +615,12 @@ do_test in-13.14 { } } {} +do_test in-13.15 { + catchsql { + SELECT 0 WHERE (SELECT 0,0) OR (0 IN (1,2)); + } +} {1 {only a single result allowed for a SELECT that is part of an expression}} + do_test in-13.X { db nullvalue "" From 0ec68f845c1ab87995f8956c2617c7017809a963 Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 04:51:28 +0000 Subject: [PATCH 41/53] When doing the (dubious) conversion of double-quoted identifier into string literal for MySQL compatibility, be sure to also clear the iTable value from the Expr entry to avoid an assert. FossilOrigin-Name: d7211b68107ea669de39e0aa81a1be40901e1487 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/resolve.c | 1 + test/misc1.test | 5 +++++ 4 files changed, 14 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index 8ac7986648..c64b26440d 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Add\sa\stest\scase\sfor\swhat\swas\sformerly\sthought\sto\sbe\san\sunreachable\scondition:\nwhen\sthe\sLHS\sof\san\sOR\soperator\scontains\san\serror\sand\sthe\sRHS\scontains\san\sIN\noperator. -D 2015-04-15T04:20:58.065 +C When\sdoing\sthe\s(dubious)\sconversion\sof\sdouble-quoted\sidentifier\sinto\sstring\nliteral\sfor\sMySQL\scompatibility,\sbe\ssure\sto\salso\sclear\sthe\siTable\svalue\sfrom\nthe\sExpr\sentry\sto\savoid\san\sassert. +D 2015-04-15T04:51:28.676 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -228,7 +228,7 @@ F src/pragma.h 09c89bca58e9a44de2116cc8272b8d454657129f F src/prepare.c 173a5a499138451b2561614ecb87d78f9f4644b9 F src/printf.c 8ae1fa9d30c1200a9268a390ba9e9cea9197b27a F src/random.c ba2679f80ec82c4190062d756f22d0c358180696 -F src/resolve.c 41aa91af56d960e9414ce1d7c17cfb68e0d1c6cb +F src/resolve.c 7bd67ded824a2fe8b356cd45e053d9c94b1874c2 F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e F src/select.c 117e0f9ac9254a6f7472fac5144eba21ba0b2ec1 F src/shell.c 84a1593bd86aaa14f4da8a8f9b16fbc239d262aa @@ -743,7 +743,7 @@ F test/minmax.test 42fbad0e81afaa6e0de41c960329f2b2c3526efd F test/minmax2.test b44bae787fc7b227597b01b0ca5575c7cb54d3bc F test/minmax3.test cc1e8b010136db0d01a6f2a29ba5a9f321034354 F test/minmax4.test 936941484ebdceb8adec7c86b6cd9b6e5e897c1f -F test/misc1.test f3f59b3941c84a10860c06c07e86ad367a74ec92 +F test/misc1.test 9abcae9a0b8785d6fa92925dbb19c309ae9ea077 F test/misc2.test 00d7de54eda90e237fc9a38b9e5ccc769ebf6d4d F test/misc3.test cf3dda47d5dda3e53fc5804a100d3c82be736c9d F test/misc4.test 9c078510fbfff05a9869a0b6d8b86a623ad2c4f6 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P a084690b4fcabba20d9770ebf3a014dda84e2954 -R fcf0b4147f04a74e05def15e3b1a56b8 +P 3872742591add4e94033484c2844e7d7ab69674b +R 3d936303913ff5357294410059be6467 U drh -Z 041867bd4c7c23a09c20a9ae6f8ff29f +Z adb676b9f25e7eed8c83dbf9762c49f4 diff --git a/manifest.uuid b/manifest.uuid index f94b10f78e..f2359bbae0 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -3872742591add4e94033484c2844e7d7ab69674b \ No newline at end of file +d7211b68107ea669de39e0aa81a1be40901e1487 \ No newline at end of file diff --git a/src/resolve.c b/src/resolve.c index a7b14cd005..d66de27958 100644 --- a/src/resolve.c +++ b/src/resolve.c @@ -460,6 +460,7 @@ static int lookupName( if( cnt==0 && zTab==0 && ExprHasProperty(pExpr,EP_DblQuoted) ){ pExpr->op = TK_STRING; pExpr->pTab = 0; + pExpr->iTable = -1; return WRC_Prune; } diff --git a/test/misc1.test b/test/misc1.test index 0f4881fb61..1b98eafc6a 100644 --- a/test/misc1.test +++ b/test/misc1.test @@ -639,4 +639,9 @@ do_catchsql_test misc1-21.2 { VALUES(0,0x0MATCH#0; } {1 {near ";": syntax error}} +# 2015-04-15 +do_execsql_test misc1-22.1 { + SELECT ""+3 FROM (SELECT ""+5); +} {3} + finish_test From 1978d171cb1f64765b18c81ad3d8bde62c2d434c Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 05:20:44 +0000 Subject: [PATCH 42/53] When adding the implied "LIMIT 1" to the end of a scalar subquery, make sure that subquery is not a VALUES-only query as such queries cannot deal with LIMIT clauses. FossilOrigin-Name: 7c27310bdf6b4af44a0811a2787ed64966d720d2 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/expr.c | 1 + test/select4.test | 7 +++++++ 4 files changed, 16 insertions(+), 8 deletions(-) diff --git a/manifest b/manifest index c64b26440d..3a48ca3967 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C When\sdoing\sthe\s(dubious)\sconversion\sof\sdouble-quoted\sidentifier\sinto\sstring\nliteral\sfor\sMySQL\scompatibility,\sbe\ssure\sto\salso\sclear\sthe\siTable\svalue\sfrom\nthe\sExpr\sentry\sto\savoid\san\sassert. -D 2015-04-15T04:51:28.676 +C When\sadding\sthe\simplied\s"LIMIT\s1"\sto\sthe\send\sof\sa\sscalar\ssubquery,\smake\ssure\nthat\ssubquery\sis\snot\sa\sVALUES-only\squery\sas\ssuch\squeries\scannot\sdeal\swith\nLIMIT\sclauses. +D 2015-04-15T05:20:44.109 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -182,7 +182,7 @@ F src/complete.c a5cf5b4b56390cfb7b8636e8f7ddef90258dd575 F src/ctime.c 98f89724adc891a1a4c655bee04e33e716e05887 F src/date.c e4d50b3283696836ec1036b695ead9a19e37a5ac F src/delete.c 37964e6c1d73ff49cbea9ff690c9605fb15f600e -F src/expr.c aba4f0547aac1fcbd965d548ab2e36efd5a4481c +F src/expr.c 8800584340a9b4f4c0ca55c360de751c6da0b11a F src/fault.c 160a0c015b6c2629d3899ed2daf63d75754a32bb F src/fkey.c 3343d551a8d810782257244fb33f2ce191493c39 F src/func.c 1414c24c873c48796ad45942257a179a423ba42f @@ -839,7 +839,7 @@ F test/securedel2.test 2d54c28e46eb1fd6902089958b20b1b056c6f1c5 F test/select1.test fc2a61f226a649393664ad54bc5376631801517c F test/select2.test 352480e0e9c66eda9c3044e412abdf5be0215b56 F test/select3.test 2ce595f8fb8e2ac10071d3b4e424cadd4634a054 -F test/select4.test e20e8ce47b558de80616102ef273704cf0d48a3b +F test/select4.test af938bb5f55c6f3925047fc7cd837c894566f5db F test/select5.test e758b8ef94f69b111df4cb819008856655dcd535 F test/select6.test 39eac4a5c03650b2b473c532882273283ee8b7a0 F test/select7.test 7fd2ef598cfabb6b9ff6ac13973b91d0527df49d @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 3872742591add4e94033484c2844e7d7ab69674b -R 3d936303913ff5357294410059be6467 +P d7211b68107ea669de39e0aa81a1be40901e1487 +R 880c9defd1fb09406a80bcc7ed2c9c3e U drh -Z adb676b9f25e7eed8c83dbf9762c49f4 +Z 868124641765b45b984dc6b337325865 diff --git a/manifest.uuid b/manifest.uuid index f2359bbae0..783f8ed725 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -d7211b68107ea669de39e0aa81a1be40901e1487 \ No newline at end of file +7c27310bdf6b4af44a0811a2787ed64966d720d2 \ No newline at end of file diff --git a/src/expr.c b/src/expr.c index 6a30755aa5..77eb35aa74 100644 --- a/src/expr.c +++ b/src/expr.c @@ -2016,6 +2016,7 @@ int sqlite3CodeSubselect( pSel->pLimit = sqlite3PExpr(pParse, TK_INTEGER, 0, 0, &sqlite3IntTokens[1]); pSel->iLimit = 0; + pSel->selFlags &= ~SF_AllValues; if( sqlite3Select(pParse, pSel, &dest) ){ return 0; } diff --git a/test/select4.test b/test/select4.test index 47a44081f4..71171def33 100644 --- a/test/select4.test +++ b/test/select4.test @@ -863,5 +863,12 @@ do_execsql_test select4-14.8 { do_execsql_test select4-14.9 { SELECT * FROM t14 UNION ALL VALUES(3,2,1),(2,3,1),(1,2,3),(2,1,3); } {1 2 3 4 5 6 3 2 1 2 3 1 1 2 3 2 1 3} +do_execsql_test select4-14.10 { + SELECT (VALUES(1),(2),(3),(4)) +} {1} +do_execsql_test select4-14.11 { + SELECT (SELECT 1 UNION ALL SELECT 2 UNION ALL SELECT 3 UNION ALL SELECT 4) +} {1} + finish_test From 65df68e8c56bf3b79a31a7a1e853f4067998e207 Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 05:31:02 +0000 Subject: [PATCH 43/53] Correctly deal with an unknown collating sequence on an indexed DISTINCT query. FossilOrigin-Name: a0b6e2fed3e95cf78ed0515c6e4da7510af4e86a --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/where.c | 2 +- test/collate3.test | 7 ++++++- 4 files changed, 15 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index 3a48ca3967..2b31601281 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C When\sadding\sthe\simplied\s"LIMIT\s1"\sto\sthe\send\sof\sa\sscalar\ssubquery,\smake\ssure\nthat\ssubquery\sis\snot\sa\sVALUES-only\squery\sas\ssuch\squeries\scannot\sdeal\swith\nLIMIT\sclauses. -D 2015-04-15T05:20:44.109 +C Correctly\sdeal\swith\san\sunknown\scollating\ssequence\son\san\sindexed\sDISTINCT\squery. +D 2015-04-15T05:31:02.899 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -307,7 +307,7 @@ F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb F src/wal.c 753995db83247f20361a8e8a874990b21a75abd9 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 9952e4749f481707595692f2f13d3ce3b64ffdc8 +F src/where.c 8a05434f5a75a38c64c45e316b00167ba0fd7ad3 F src/whereInt.h cbe4aa57326998d89e7698ca65bb7c28541d483c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -401,7 +401,7 @@ F test/closure01.test b1703ba40639cfc9b295cf478d70739415eec6a4 F test/coalesce.test cee0dccb9fbd2d494b77234bccf9dc6c6786eb91 F test/collate1.test 7fcfe78f9613dc4a7e247d6bd27749955f108741 F test/collate2.test 9aaa410a00734e48bcb27f3872617d6f69b2a621 -F test/collate3.test 79558a286362cb9ed603c6fa543f1cda7f563f0f +F test/collate3.test 89defc49983ddfbf0a0555aca8c0521a676f56a5 F test/collate4.test f04d5168685f2eef637ecfa2d4ddf8ec0d600177 F test/collate5.test 65d928034d30d2d263a80f6359f7549ee1598ec6 F test/collate6.test 8be65a182abaac8011a622131486dafb8076e907 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P d7211b68107ea669de39e0aa81a1be40901e1487 -R 880c9defd1fb09406a80bcc7ed2c9c3e +P 7c27310bdf6b4af44a0811a2787ed64966d720d2 +R 97d8aa531c1ae9c06ffcd147c2fe4f6f U drh -Z 868124641765b45b984dc6b337325865 +Z 3a34d92eb0e2b45ff65d57bcfcec8b05 diff --git a/manifest.uuid b/manifest.uuid index 783f8ed725..4b837de064 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -7c27310bdf6b4af44a0811a2787ed64966d720d2 \ No newline at end of file +a0b6e2fed3e95cf78ed0515c6e4da7510af4e86a \ No newline at end of file diff --git a/src/where.c b/src/where.c index 42e950e41e..e1c5f4ecaa 100644 --- a/src/where.c +++ b/src/where.c @@ -1532,7 +1532,7 @@ static int findIndexCol( && p->iTable==iBase ){ CollSeq *pColl = sqlite3ExprCollSeq(pParse, pList->a[i].pExpr); - if( ALWAYS(pColl) && 0==sqlite3StrICmp(pColl->zName, zColl) ){ + if( pColl && 0==sqlite3StrICmp(pColl->zName, zColl) ){ return i; } } diff --git a/test/collate3.test b/test/collate3.test index 2c051cb9a7..99640d05b8 100644 --- a/test/collate3.test +++ b/test/collate3.test @@ -32,7 +32,7 @@ source $testdir/tester.tcl # do_test collate3-1.0 { execsql { - CREATE TABLE collate3t1(c1); + CREATE TABLE collate3t1(c1 UNIQUE); } } {} do_test collate3-1.1 { @@ -40,6 +40,11 @@ do_test collate3-1.1 { SELECT * FROM collate3t1 ORDER BY 1 collate garbage; } } {1 {no such collation sequence: garbage}} +do_test collate3-1.1.2 { + catchsql { + SELECT DISTINCT c1 COLLATE garbage FROM collate3t1; + } +} {1 {no such collation sequence: garbage}} do_test collate3-1.2 { catchsql { CREATE TABLE collate3t2(c1 collate garbage); From 3457338ced7a521be2fb0aab1808648128a3d43e Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 05:38:35 +0000 Subject: [PATCH 44/53] Fix a faulty assert() in the sqlite3StrAccumAppend() routine. FossilOrigin-Name: 998cfdb8dcda2cac94b83326751e16dcef8b267f --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/printf.c | 2 +- test/printf2.test | 3 +++ 4 files changed, 12 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 2b31601281..94e960af32 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Correctly\sdeal\swith\san\sunknown\scollating\ssequence\son\san\sindexed\sDISTINCT\squery. -D 2015-04-15T05:31:02.899 +C Fix\sa\sfaulty\sassert()\sin\sthe\ssqlite3StrAccumAppend()\sroutine. +D 2015-04-15T05:38:35.928 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -226,7 +226,7 @@ F src/pcache1.c 69d137620a305f814398bd29a0c998038c0695e9 F src/pragma.c ac4f3f856b4234e85f55b0f069698a4766011100 F src/pragma.h 09c89bca58e9a44de2116cc8272b8d454657129f F src/prepare.c 173a5a499138451b2561614ecb87d78f9f4644b9 -F src/printf.c 8ae1fa9d30c1200a9268a390ba9e9cea9197b27a +F src/printf.c 08fa675c200aac29e561c6153f91f909ed17612f F src/random.c ba2679f80ec82c4190062d756f22d0c358180696 F src/resolve.c 7bd67ded824a2fe8b356cd45e053d9c94b1874c2 F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e @@ -798,7 +798,7 @@ F test/pragma.test ad99d05e411c7687302124be56f3b362204be041 F test/pragma2.test f624a496a95ee878e81e59961eade66d5c00c028 F test/pragma3.test 6f849ccffeee7e496d2f2b5e74152306c0b8757c F test/printf.test b3ff34e73d59124140eaf89f7672e21bc2ca5fcc -F test/printf2.test b4acd4bf8734243257f01ddefa17c4fb090acc8a +F test/printf2.test 0b61566dd1c0f0b802f59dffa228c5dc5aa6b054 F test/progress.test a282973d1d17f08071bc58a77d6b80f2a81c354d F test/ptrchng.test ef1aa72d6cf35a2bbd0869a649b744e9d84977fc F test/queryonly.test 5f653159e0f552f0552d43259890c1089391dcca @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 7c27310bdf6b4af44a0811a2787ed64966d720d2 -R 97d8aa531c1ae9c06ffcd147c2fe4f6f +P a0b6e2fed3e95cf78ed0515c6e4da7510af4e86a +R bd008e3cfd1613a5e1f1a28458fbfaad U drh -Z 3a34d92eb0e2b45ff65d57bcfcec8b05 +Z cf565eb6ae4e94564c05e7f944eb18e5 diff --git a/manifest.uuid b/manifest.uuid index 4b837de064..1adef81d5f 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -a0b6e2fed3e95cf78ed0515c6e4da7510af4e86a \ No newline at end of file +998cfdb8dcda2cac94b83326751e16dcef8b267f \ No newline at end of file diff --git a/src/printf.c b/src/printf.c index 9714fa1565..1a978dc5ca 100644 --- a/src/printf.c +++ b/src/printf.c @@ -826,7 +826,7 @@ static void SQLITE_NOINLINE enlargeAndAppend(StrAccum *p, const char *z, int N){ ** size of the memory allocation for StrAccum if necessary. */ void sqlite3StrAccumAppend(StrAccum *p, const char *z, int N){ - assert( z!=0 ); + assert( z!=0 || N==0 ); assert( p->zText!=0 || p->nChar==0 || p->accError ); assert( N>=0 ); assert( p->accError==0 || p->nAlloc==0 ); diff --git a/test/printf2.test b/test/printf2.test index 21deeb779d..fb031bd68f 100644 --- a/test/printf2.test +++ b/test/printf2.test @@ -58,6 +58,9 @@ do_execsql_test printf2-1.10 { do_execsql_test printf2-1.11 { SELECT printf('%lld%n',314159.2653,'hi'); } {314159} +do_execsql_test printf2-1.12 { + SELECT printf('%n',0); +} {{}} # EVIDENCE-OF: R-17002-27534 The %z format is interchangeable with %s. # From 6456b7710c1ff87a5a6b6f58a8d1471a16553434 Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 05:57:50 +0000 Subject: [PATCH 45/53] Correctly handle COLLATE operators applied to COLLATE operators in an ORDER BY clause. FossilOrigin-Name: 9e1f837b08facbc7a2b6196770599a58233e725c --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/resolve.c | 8 +++++--- test/collate1.test | 18 ++++++++++++++++-- 4 files changed, 29 insertions(+), 13 deletions(-) diff --git a/manifest b/manifest index 94e960af32..355bd09e61 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sa\sfaulty\sassert()\sin\sthe\ssqlite3StrAccumAppend()\sroutine. -D 2015-04-15T05:38:35.928 +C Correctly\shandle\sCOLLATE\soperators\sapplied\sto\sCOLLATE\soperators\sin\san\nORDER\sBY\sclause. +D 2015-04-15T05:57:50.327 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -228,7 +228,7 @@ F src/pragma.h 09c89bca58e9a44de2116cc8272b8d454657129f F src/prepare.c 173a5a499138451b2561614ecb87d78f9f4644b9 F src/printf.c 08fa675c200aac29e561c6153f91f909ed17612f F src/random.c ba2679f80ec82c4190062d756f22d0c358180696 -F src/resolve.c 7bd67ded824a2fe8b356cd45e053d9c94b1874c2 +F src/resolve.c 03fe2a8640b7f1477e6cbca6f3bc1b5549263a47 F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e F src/select.c 117e0f9ac9254a6f7472fac5144eba21ba0b2ec1 F src/shell.c 84a1593bd86aaa14f4da8a8f9b16fbc239d262aa @@ -399,7 +399,7 @@ F test/check.test 5831ddb6f2c687782eaf2e1a07b6e17f24c4f763 F test/close.test 340bd24cc58b16c6bc01967402755027c37eb815 F test/closure01.test b1703ba40639cfc9b295cf478d70739415eec6a4 F test/coalesce.test cee0dccb9fbd2d494b77234bccf9dc6c6786eb91 -F test/collate1.test 7fcfe78f9613dc4a7e247d6bd27749955f108741 +F test/collate1.test 08c18e7512a5a32c97938854263fa15362eeb846 F test/collate2.test 9aaa410a00734e48bcb27f3872617d6f69b2a621 F test/collate3.test 89defc49983ddfbf0a0555aca8c0521a676f56a5 F test/collate4.test f04d5168685f2eef637ecfa2d4ddf8ec0d600177 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P a0b6e2fed3e95cf78ed0515c6e4da7510af4e86a -R bd008e3cfd1613a5e1f1a28458fbfaad +P 998cfdb8dcda2cac94b83326751e16dcef8b267f +R 365a6b3d3d3943322095f384b9ee1504 U drh -Z cf565eb6ae4e94564c05e7f944eb18e5 +Z eaf1d275b82a1bdf74f8de064c4444e7 diff --git a/manifest.uuid b/manifest.uuid index 1adef81d5f..a0184f5e23 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -998cfdb8dcda2cac94b83326751e16dcef8b267f \ No newline at end of file +9e1f837b08facbc7a2b6196770599a58233e725c \ No newline at end of file diff --git a/src/resolve.c b/src/resolve.c index d66de27958..aa4cddfef2 100644 --- a/src/resolve.c +++ b/src/resolve.c @@ -994,9 +994,11 @@ static int resolveCompoundOrderBy( if( pItem->pExpr==pE ){ pItem->pExpr = pNew; }else{ - assert( pItem->pExpr->op==TK_COLLATE ); - assert( pItem->pExpr->pLeft==pE ); - pItem->pExpr->pLeft = pNew; + Expr *pParent = pItem->pExpr; + assert( pParent->op==TK_COLLATE ); + while( pParent->pLeft->op==TK_COLLATE ) pParent = pParent->pLeft; + assert( pParent->pLeft==pE ); + pParent->pLeft = pNew; } sqlite3ExprDelete(db, pE); pItem->u.x.iOrderByCol = (u16)iCol; diff --git a/test/collate1.test b/test/collate1.test index 0716ac743f..7cf5698454 100644 --- a/test/collate1.test +++ b/test/collate1.test @@ -385,6 +385,20 @@ do_execsql_test 6.8 { SELECT x, y FROM c1 ORDER BY y COLLATE """"""""; } {2 abb 1 ABC 4 WXY 3 wxz} +# 2015-04-15: Nested COLLATE operators +# +do_execsql_test 7.0 { + SELECT 'abc' UNION ALL SELECT 'DEF' + ORDER BY 1 COLLATE nocase COLLATE nocase COLLATE nocase COLLATE nocase; +} {abc DEF} +do_execsql_test 7.1 { + SELECT 'abc' UNION ALL SELECT 'DEF' + ORDER BY 1 COLLATE nocase COLLATE nocase COLLATE nocase COLLATE binary; +} {DEF abc} +do_execsql_test 7.2 { + SELECT 'abc' UNION ALL SELECT 'DEF' + ORDER BY 1 COLLATE binary COLLATE binary COLLATE binary COLLATE nocase; +} {abc DEF} + + finish_test - - From a43f02efc613826511132be78c9445e239f91ddd Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 06:45:13 +0000 Subject: [PATCH 46/53] Fix a faulty assert() statement in the name resolver associated with the optimization that converts compound selects with ORDER BY COLLATE into subqueries. FossilOrigin-Name: c72324ef9243946550ae3d974826502b1cc5eb10 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/resolve.c | 2 +- test/selectE.test | 5 +++++ 4 files changed, 14 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 355bd09e61..b179c36ad3 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Correctly\shandle\sCOLLATE\soperators\sapplied\sto\sCOLLATE\soperators\sin\san\nORDER\sBY\sclause. -D 2015-04-15T05:57:50.327 +C Fix\sa\sfaulty\sassert()\sstatement\sin\sthe\sname\sresolver\sassociated\swith\sthe\noptimization\sthat\sconverts\scompound\sselects\swith\sORDER\sBY\sCOLLATE\sinto\nsubqueries. +D 2015-04-15T06:45:13.856 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -228,7 +228,7 @@ F src/pragma.h 09c89bca58e9a44de2116cc8272b8d454657129f F src/prepare.c 173a5a499138451b2561614ecb87d78f9f4644b9 F src/printf.c 08fa675c200aac29e561c6153f91f909ed17612f F src/random.c ba2679f80ec82c4190062d756f22d0c358180696 -F src/resolve.c 03fe2a8640b7f1477e6cbca6f3bc1b5549263a47 +F src/resolve.c 66cfe49a9c3b449ef13b89a8c47036a4ed167eab F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e F src/select.c 117e0f9ac9254a6f7472fac5144eba21ba0b2ec1 F src/shell.c 84a1593bd86aaa14f4da8a8f9b16fbc239d262aa @@ -849,7 +849,7 @@ F test/selectA.test e452bdb975f488ea46d091382a9185b5853ed2c7 F test/selectB.test 954e4e49cf1f896d61794e440669e03a27ceea25 F test/selectC.test 871fb55d884d3de5943c4057ebd22c2459e71977 F test/selectD.test b0f02a04ef7737decb24e08be2c39b9664b43394 -F test/selectE.test fc02a1eb04c8eb537091482644b7d778ae8759b7 +F test/selectE.test a8730ca330fcf40ace158f134f4fe0eb00c7edbf F test/selectF.test 21c94e6438f76537b72532fa9fd4710cdd455fc3 F test/selectG.test e8600e379589e85e9fefd2fe4d44a4cdd63f6982 F test/server1.test 46803bd3fe8b99b30dbc5ff38ffc756f5c13a118 @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 998cfdb8dcda2cac94b83326751e16dcef8b267f -R 365a6b3d3d3943322095f384b9ee1504 +P 9e1f837b08facbc7a2b6196770599a58233e725c +R d99053241fb4278349e47e2aa3bd86a0 U drh -Z eaf1d275b82a1bdf74f8de064c4444e7 +Z d2955d105f5f67e57ae3e9b26664c585 diff --git a/manifest.uuid b/manifest.uuid index a0184f5e23..3d0d30286b 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -9e1f837b08facbc7a2b6196770599a58233e725c \ No newline at end of file +c72324ef9243946550ae3d974826502b1cc5eb10 \ No newline at end of file diff --git a/src/resolve.c b/src/resolve.c index aa4cddfef2..6294ba26e1 100644 --- a/src/resolve.c +++ b/src/resolve.c @@ -1198,7 +1198,7 @@ static int resolveSelectStep(Walker *pWalker, Select *p){ ** after the names have been resolved. */ if( p->selFlags & SF_Converted ){ Select *pSub = p->pSrc->a[0].pSelect; - assert( p->pSrc->nSrc==1 && isCompound==0 && p->pOrderBy ); + assert( p->pSrc->nSrc==1 && p->pOrderBy ); assert( pSub->pPrior && pSub->pOrderBy==0 ); pSub->pOrderBy = p->pOrderBy; p->pOrderBy = 0; diff --git a/test/selectE.test b/test/selectE.test index d7592bbbc5..1cabeff370 100644 --- a/test/selectE.test +++ b/test/selectE.test @@ -92,4 +92,9 @@ do_test selectE-2.2 { } } {} +do_catchsql_test selectE-3.1 { + SELECT 1 EXCEPT SELECT 2 ORDER BY 1 COLLATE nocase EXCEPT SELECT 3; +} {1 {ORDER BY clause should come after EXCEPT not before}} + + finish_test From 3dc4cc66b3a7ff48cff042751a5e9eee41b08f24 Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 07:10:25 +0000 Subject: [PATCH 47/53] Change the multiSelectOrderBy() routine to return non-zero if there has been any prior error. FossilOrigin-Name: 14784c317bff05dd0a74e2596432dfd12c139391 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/select.c | 2 +- test/select4.test | 5 +++++ 4 files changed, 14 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index b179c36ad3..8fb373a6c9 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sa\sfaulty\sassert()\sstatement\sin\sthe\sname\sresolver\sassociated\swith\sthe\noptimization\sthat\sconverts\scompound\sselects\swith\sORDER\sBY\sCOLLATE\sinto\nsubqueries. -D 2015-04-15T06:45:13.856 +C Change\sthe\smultiSelectOrderBy()\sroutine\sto\sreturn\snon-zero\sif\sthere\shas\nbeen\sany\sprior\serror. +D 2015-04-15T07:10:25.034 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -230,7 +230,7 @@ F src/printf.c 08fa675c200aac29e561c6153f91f909ed17612f F src/random.c ba2679f80ec82c4190062d756f22d0c358180696 F src/resolve.c 66cfe49a9c3b449ef13b89a8c47036a4ed167eab F src/rowset.c eccf6af6d620aaa4579bd3b72c1b6395d9e9fa1e -F src/select.c 117e0f9ac9254a6f7472fac5144eba21ba0b2ec1 +F src/select.c 93260bc9e7e0e6dfe1b7cb8815b0ed4cad8be9e3 F src/shell.c 84a1593bd86aaa14f4da8a8f9b16fbc239d262aa F src/sqlite.h.in ca27603a36fcacdaac5a19d8ee35aaff8ce8516f F src/sqlite3.rc 992c9f5fb8285ae285d6be28240a7e8d3a7f2bad @@ -839,7 +839,7 @@ F test/securedel2.test 2d54c28e46eb1fd6902089958b20b1b056c6f1c5 F test/select1.test fc2a61f226a649393664ad54bc5376631801517c F test/select2.test 352480e0e9c66eda9c3044e412abdf5be0215b56 F test/select3.test 2ce595f8fb8e2ac10071d3b4e424cadd4634a054 -F test/select4.test af938bb5f55c6f3925047fc7cd837c894566f5db +F test/select4.test 16fa1cafb942f42294ec85cbb78954c2f2d15a44 F test/select5.test e758b8ef94f69b111df4cb819008856655dcd535 F test/select6.test 39eac4a5c03650b2b473c532882273283ee8b7a0 F test/select7.test 7fd2ef598cfabb6b9ff6ac13973b91d0527df49d @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 9e1f837b08facbc7a2b6196770599a58233e725c -R d99053241fb4278349e47e2aa3bd86a0 +P c72324ef9243946550ae3d974826502b1cc5eb10 +R a18a17a9c69cd2c9e7e0fb3024e1e22e U drh -Z d2955d105f5f67e57ae3e9b26664c585 +Z 56fd45c34ac20b50b5d25609e083b049 diff --git a/manifest.uuid b/manifest.uuid index 3d0d30286b..b9b981e38f 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -c72324ef9243946550ae3d974826502b1cc5eb10 \ No newline at end of file +14784c317bff05dd0a74e2596432dfd12c139391 \ No newline at end of file diff --git a/src/select.c b/src/select.c index 930a099e80..bed1f80be0 100644 --- a/src/select.c +++ b/src/select.c @@ -3071,7 +3071,7 @@ static int multiSelectOrderBy( /*** TBD: Insert subroutine calls to close cursors on incomplete **** subqueries ****/ explainComposite(pParse, p->op, iSub1, iSub2, 0); - return SQLITE_OK; + return pParse->nErr!=0; } #endif diff --git a/test/select4.test b/test/select4.test index 71171def33..2f3ddbe96a 100644 --- a/test/select4.test +++ b/test/select4.test @@ -799,6 +799,11 @@ do_test select4-11.15 { SELECT x FROM t2 } } {1 {SELECTs to the left and right of UNION do not have the same number of result columns}} +do_test select4-11.16 { + catchsql { + INSERT INTO t2(rowid) VALUES(2) UNION SELECT 3,4 UNION SELECT 5,6 ORDER BY 1; + } +} {1 {SELECTs to the left and right of UNION do not have the same number of result columns}} do_test select4-12.1 { sqlite3 db2 :memory: From 1b6789697d13ab232b99f8064b0d106c6b5184a0 Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 07:19:27 +0000 Subject: [PATCH 48/53] Remove an incorrect ALWAYS() from the table_info pragma. FossilOrigin-Name: 0e087c0183bc7a758cf2a1d39158bc24fde833a2 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/pragma.c | 2 +- test/pragma.test | 10 ++++++++++ 4 files changed, 19 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 8fb373a6c9..82ef7926f4 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Change\sthe\smultiSelectOrderBy()\sroutine\sto\sreturn\snon-zero\sif\sthere\shas\nbeen\sany\sprior\serror. -D 2015-04-15T07:10:25.034 +C Remove\san\sincorrect\sALWAYS()\sfrom\sthe\stable_info\spragma. +D 2015-04-15T07:19:27.406 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -223,7 +223,7 @@ F src/parse.y 1299c66e7b1707322ccd8af43a359b8fb0d46d72 F src/pcache.c 10539fb959849ad6efff80050541cab3d25089d4 F src/pcache.h b44658c9c932d203510279439d891a2a83e12ba8 F src/pcache1.c 69d137620a305f814398bd29a0c998038c0695e9 -F src/pragma.c ac4f3f856b4234e85f55b0f069698a4766011100 +F src/pragma.c 3965ae4e82bed39fb97ce04c5fe18c9bc3ee6a88 F src/pragma.h 09c89bca58e9a44de2116cc8272b8d454657129f F src/prepare.c 173a5a499138451b2561614ecb87d78f9f4644b9 F src/printf.c 08fa675c200aac29e561c6153f91f909ed17612f @@ -794,7 +794,7 @@ F test/pcache.test b09104b03160aca0d968d99e8cd2c5b1921a993d F test/pcache2.test a83efe2dec0d392f814bfc998def1d1833942025 F test/percentile.test 4243af26b8f3f4555abe166f723715a1f74c77ff F test/permutations.test f9cc1dd987986c9d4949211c7a4ed55ec9aecba1 -F test/pragma.test ad99d05e411c7687302124be56f3b362204be041 +F test/pragma.test e6605ce89c66db930aef561e43a22281a09ffc66 F test/pragma2.test f624a496a95ee878e81e59961eade66d5c00c028 F test/pragma3.test 6f849ccffeee7e496d2f2b5e74152306c0b8757c F test/printf.test b3ff34e73d59124140eaf89f7672e21bc2ca5fcc @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P c72324ef9243946550ae3d974826502b1cc5eb10 -R a18a17a9c69cd2c9e7e0fb3024e1e22e +P 14784c317bff05dd0a74e2596432dfd12c139391 +R 275812afa820df20388de5de5b05e3ce U drh -Z 56fd45c34ac20b50b5d25609e083b049 +Z c974cc37b6f1891bf4b4ede9ca413ca2 diff --git a/manifest.uuid b/manifest.uuid index b9b981e38f..a860fba913 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -14784c317bff05dd0a74e2596432dfd12c139391 \ No newline at end of file +0e087c0183bc7a758cf2a1d39158bc24fde833a2 \ No newline at end of file diff --git a/src/pragma.c b/src/pragma.c index ef11d5840f..8f6ac64754 100644 --- a/src/pragma.c +++ b/src/pragma.c @@ -1041,7 +1041,7 @@ void sqlite3Pragma( }else if( pPk==0 ){ k = 1; }else{ - for(k=1; ALWAYS(k<=pTab->nCol) && pPk->aiColumn[k-1]!=i; k++){} + for(k=1; k<=pTab->nCol && pPk->aiColumn[k-1]!=i; k++){} } sqlite3VdbeAddOp2(v, OP_Integer, k, 6); sqlite3VdbeAddOp2(v, OP_ResultRow, 1, 6); diff --git a/test/pragma.test b/test/pragma.test index d164702643..e8a53f442d 100644 --- a/test/pragma.test +++ b/test/pragma.test @@ -752,6 +752,16 @@ do_test pragma-6.7 { {3 four REAL 0 X'abcdef' 0} \ {4 five {} 0 CURRENT_TIME 0} \ ] +do_test pragma-6.8 { + execsql { + CREATE TABLE t68(a,b,c,PRIMARY KEY(a,b,a,c)); + PRAGMA table_info(t68); + } +} [concat \ + {0 a {} 0 {} 1} \ + {1 b {} 0 {} 2} \ + {2 c {} 0 {} 4} \ +] } ;# ifcapable schema_pragmas # Miscellaneous tests # From 29031837c19e371ae6056e2dc3efb03f3f7895b4 Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 07:34:25 +0000 Subject: [PATCH 49/53] Remove an incorrect ALWAYS() from the automatic index generator. FossilOrigin-Name: eeb4bd06bf69e411736cc6077d1d64af6bd8fb09 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/where.c | 2 +- test/autoindex1.test | 7 +++++++ 4 files changed, 16 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index 82ef7926f4..f61d8e0c34 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\san\sincorrect\sALWAYS()\sfrom\sthe\stable_info\spragma. -D 2015-04-15T07:19:27.406 +C Remove\san\sincorrect\sALWAYS()\sfrom\sthe\sautomatic\sindex\sgenerator. +D 2015-04-15T07:34:25.165 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -307,7 +307,7 @@ F src/vxworks.h c18586c8edc1bddbc15c004fa16aeb1e1342b4fb F src/wal.c 753995db83247f20361a8e8a874990b21a75abd9 F src/wal.h df01efe09c5cb8c8e391ff1715cca294f89668a4 F src/walker.c c253b95b4ee44b21c406e2a1052636c31ea27804 -F src/where.c 8a05434f5a75a38c64c45e316b00167ba0fd7ad3 +F src/where.c 8ba8ff31dc9bf1b69fe771d35d8764d5a1efd310 F src/whereInt.h cbe4aa57326998d89e7698ca65bb7c28541d483c F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2 F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2 @@ -349,7 +349,7 @@ F test/auth.test 855233ef26eb3601b6886567ea4e326c72959360 F test/auth2.test 264c6af53cad9aba5218c68bbe18036e39007bfa F test/auth3.test 5cfa94ed90c6617c42b7ba4b133fd79678b251c7 F test/autoinc.test c58912526998a39e11f66b533e23cfabea7f25b7 -F test/autoindex1.test 7008c9f604141fdabe31b7bb95b5ff31b518251f +F test/autoindex1.test 14b63a9f1e405fe6d5bfc8c8d00249c2ebaf13ea F test/autoindex2.test af7e595c6864cc6ef5fc38d5db579a3e34940cb8 F test/autoindex3.test a3be0d1a53a7d2edff208a5e442312957047e972 F test/autoindex4.test 49d3cd791a9baa16fb461d7ea3de80d019a819cf @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 14784c317bff05dd0a74e2596432dfd12c139391 -R 275812afa820df20388de5de5b05e3ce +P 0e087c0183bc7a758cf2a1d39158bc24fde833a2 +R 45168c2ae417f665e937b47961f47d47 U drh -Z c974cc37b6f1891bf4b4ede9ca413ca2 +Z fe2feaff56a77a679eecea2f54332501 diff --git a/manifest.uuid b/manifest.uuid index a860fba913..2e89d53bd1 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -0e087c0183bc7a758cf2a1d39158bc24fde833a2 \ No newline at end of file +eeb4bd06bf69e411736cc6077d1d64af6bd8fb09 \ No newline at end of file diff --git a/src/where.c b/src/where.c index e1c5f4ecaa..3467a68626 100644 --- a/src/where.c +++ b/src/where.c @@ -1806,7 +1806,7 @@ static void constructAutomaticIndex( idxCols |= cMask; pIdx->aiColumn[n] = pTerm->u.leftColumn; pColl = sqlite3BinaryCompareCollSeq(pParse, pX->pLeft, pX->pRight); - pIdx->azColl[n] = ALWAYS(pColl) ? pColl->zName : "BINARY"; + pIdx->azColl[n] = pColl ? pColl->zName : "BINARY"; n++; } } diff --git a/test/autoindex1.test b/test/autoindex1.test index c5ce42c1d4..e2b8b1529e 100644 --- a/test/autoindex1.test +++ b/test/autoindex1.test @@ -512,5 +512,12 @@ do_execsql_test autoindex1-901 { WHERE t1.x IN (1,2,3); } {/USING AUTOMATIC COVERING INDEX/} +# 2015-04-15: A NULL CollSeq pointer in automatic index creation. +# +do_execsql_test autoindex1-920 { + CREATE TABLE t920(x); + INSERT INTO t920 VALUES(3),(4),(5); + SELECT * FROM t920,(SELECT 0 FROM t920),(VALUES(9)) WHERE 5 IN (x); +} {5 0 9 5 0 9 5 0 9} finish_test From 347bdc39a70e092247a3fc0c3e4e99aef24d92fe Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 07:57:27 +0000 Subject: [PATCH 50/53] Fix the error message generator for illegal token errors so that it does not leak memory if it immediately follows another erroneous SQL statement. FossilOrigin-Name: 3576973f8b88b6109fbefdebfa53468ffa137009 --- manifest | 12 ++++++------ manifest.uuid | 2 +- src/tokenize.c | 4 +--- 3 files changed, 8 insertions(+), 10 deletions(-) diff --git a/manifest b/manifest index f61d8e0c34..983d068c58 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\san\sincorrect\sALWAYS()\sfrom\sthe\sautomatic\sindex\sgenerator. -D 2015-04-15T07:34:25.165 +C Fix\sthe\serror\smessage\sgenerator\sfor\sillegal\stoken\serrors\sso\sthat\sit\sdoes\snot\nleak\smemory\sif\sit\simmediately\sfollows\sanother\serroneous\sSQL\sstatement. +D 2015-04-15T07:57:27.369 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -287,7 +287,7 @@ F src/test_vfs.c b7e6831e6fcf04c5090accff30640ec5c9630739 F src/test_vfstrace.c bab9594adc976cbe696ff3970728830b4c5ed698 F src/test_wsd.c 41cadfd9d97fe8e3e4e44f61a4a8ccd6f7ca8fe9 F src/threads.c 6bbcc9fe50c917864d48287b4792d46d6e873481 -F src/tokenize.c a8d270b06e5f709930f7b67cf70a847969cb5bf3 +F src/tokenize.c 2b93d338833be43cba93644562e85a24ff3d97d1 F src/trigger.c 69a91bed7c94e46223e37ffccfeeb35e34b999ac F src/update.c 3c4ecc282accf12d39edb8d524cf089645e55a13 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 0e087c0183bc7a758cf2a1d39158bc24fde833a2 -R 45168c2ae417f665e937b47961f47d47 +P eeb4bd06bf69e411736cc6077d1d64af6bd8fb09 +R a12d30eac869033c520f48032e05590c U drh -Z fe2feaff56a77a679eecea2f54332501 +Z d83a0172461932509217291c59869b0d diff --git a/manifest.uuid b/manifest.uuid index 2e89d53bd1..ff52dd674e 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -eeb4bd06bf69e411736cc6077d1d64af6bd8fb09 \ No newline at end of file +3576973f8b88b6109fbefdebfa53468ffa137009 \ No newline at end of file diff --git a/src/tokenize.c b/src/tokenize.c index 5068742f31..a4d20c8641 100644 --- a/src/tokenize.c +++ b/src/tokenize.c @@ -430,10 +430,8 @@ int sqlite3RunParser(Parse *pParse, const char *zSql, char **pzErrMsg){ break; } case TK_ILLEGAL: { - sqlite3DbFree(db, *pzErrMsg); - *pzErrMsg = sqlite3MPrintf(db, "unrecognized token: \"%T\"", + sqlite3ErrorMsg(pParse, "unrecognized token: \"%T\"", &pParse->sLastToken); - nErr++; goto abort_parse; } case TK_SEMI: { From 2deb12be2beea8ef9f392db2bba6fab1239b9e0c Mon Sep 17 00:00:00 2001 From: dan Date: Wed, 15 Apr 2015 08:20:50 +0000 Subject: [PATCH 51/53] Fix a problem causing an assert() to fail if a snippet containing 0 tokens was requested from fts3. FossilOrigin-Name: eafd0a1e3f25f38d551603f177ff4634cf79de77 --- ext/fts3/fts3.c | 2 ++ manifest | 16 ++++++++-------- manifest.uuid | 2 +- test/fts3snippet.test | 19 +++++++++++++++++++ 4 files changed, 30 insertions(+), 9 deletions(-) diff --git a/ext/fts3/fts3.c b/ext/fts3/fts3.c index 42b9663a1b..eb62c195df 100644 --- a/ext/fts3/fts3.c +++ b/ext/fts3/fts3.c @@ -3527,6 +3527,8 @@ static void fts3SnippetFunc( } if( !zEllipsis || !zEnd || !zStart ){ sqlite3_result_error_nomem(pContext); + }else if( nToken==0 ){ + sqlite3_result_text(pContext, "", -1, SQLITE_STATIC); }else if( SQLITE_OK==fts3CursorSeek(pContext, pCsr) ){ sqlite3Fts3Snippet(pContext, pCsr, zStart, zEnd, zEllipsis, iCol, nToken); } diff --git a/manifest b/manifest index 983d068c58..f9c5dae3b3 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sthe\serror\smessage\sgenerator\sfor\sillegal\stoken\serrors\sso\sthat\sit\sdoes\snot\nleak\smemory\sif\sit\simmediately\sfollows\sanother\serroneous\sSQL\sstatement. -D 2015-04-15T07:57:27.369 +C Fix\sa\sproblem\scausing\san\sassert()\sto\sfail\sif\sa\ssnippet\scontaining\s0\stokens\swas\srequested\sfrom\sfts3. +D 2015-04-15T08:20:50.158 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -78,7 +78,7 @@ F ext/fts3/README.content fdc666a70d5257a64fee209f97cf89e0e6e32b51 F ext/fts3/README.syntax a19711dc5458c20734b8e485e75fb1981ec2427a F ext/fts3/README.tokenizers e0a8b81383ea60d0334d274fadf305ea14a8c314 F ext/fts3/README.txt 8c18f41574404623b76917b9da66fcb0ab38328d -F ext/fts3/fts3.c 57d863c3bd360e575ecc293570af7c9b0bdd2209 +F ext/fts3/fts3.c ed6624d7c5fb5aee5d47f884b2d184169fa7a7d4 F ext/fts3/fts3.h 3a10a0af180d502cecc50df77b1b22df142817fe F ext/fts3/fts3Int.h 394858c12a17740f7a1f6bd372c4606d4425a8d1 F ext/fts3/fts3_aux.c 5c211e17a64885faeb16b9ba7772f9d5445c2365 @@ -599,7 +599,7 @@ F test/fts3prefix2.test e1f0a822ca661dced7f12ce392e14eaf65609dce F test/fts3query.test c838b18f2b859e15fd31c64be3d79ef1556803ca F test/fts3rnd.test 1320d8826a845e38a96e769562bf83d7a92a15d0 F test/fts3shared.test 57e26a801f21027b7530da77db54286a6fe4997e -F test/fts3snippet.test 03c2f3be7d3b7c8bb105ed237f204833392bd57f +F test/fts3snippet.test 63dbd687d5bf5191f1b8e6a0977aa9c1e28a7004 F test/fts3sort.test ed34c716a11cc2009a35210e84ad5f9c102362ca F test/fts3tok1.test c551043de056b0b1582a54e878991f57bad074bc F test/fts3tok_err.test 52273cd193b9036282f7bacb43da78c6be87418d @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P eeb4bd06bf69e411736cc6077d1d64af6bd8fb09 -R a12d30eac869033c520f48032e05590c -U drh -Z d83a0172461932509217291c59869b0d +P 3576973f8b88b6109fbefdebfa53468ffa137009 +R 3265dd5ed99bf273b3517690abeeedc9 +U dan +Z a6b618f03dfa759db2c6c3b930aa2a83 diff --git a/manifest.uuid b/manifest.uuid index ff52dd674e..e0df72f85f 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -3576973f8b88b6109fbefdebfa53468ffa137009 \ No newline at end of file +eafd0a1e3f25f38d551603f177ff4634cf79de77 \ No newline at end of file diff --git a/test/fts3snippet.test b/test/fts3snippet.test index e97db586e6..4e1d123b2f 100644 --- a/test/fts3snippet.test +++ b/test/fts3snippet.test @@ -538,6 +538,25 @@ do_execsql_test 3.4 { SELECT snippet(t3) FROM t3 WHERE t3 MATCH 'one OR two OR three'; } {{[one two three]}} +#------------------------------------------------------------------------- +# Request a snippet 0 tokens in size. This is always an empty string. +do_execsql_test 4.1 { + CREATE VIRTUAL TABLE t4 USING fts4; + INSERT INTO t4 VALUES('a b c d'); + SELECT snippet(t4, '[', ']', '...', 0, 0) FROM t4 WHERE t4 MATCH 'b'; +} {{}} + +do_test 4.2 { + set x35 [string trim [string repeat "x " 35]] + execsql "INSERT INTO t4 VALUES('$x35 E $x35 F $x35 G $x35');" + llength [db one { + SELECT snippet(t4, '', '', '', 0, 64) FROM t4 WHERE t4 MATCH 'E' + }] +} {64} + + + + set sqlite_fts3_enable_parentheses 0 finish_test From 0be0cf672183a6767439657e0312e4b388a2d7c8 Mon Sep 17 00:00:00 2001 From: drh Date: Wed, 15 Apr 2015 08:37:42 +0000 Subject: [PATCH 52/53] Remove a branch that became unreachable due to one of the earlier check-ins today. FossilOrigin-Name: fa0956edf866f48f448967836709a3ad822ff917 --- manifest | 14 +++++++------- manifest.uuid | 2 +- src/tokenize.c | 3 ++- 3 files changed, 10 insertions(+), 9 deletions(-) diff --git a/manifest b/manifest index f9c5dae3b3..5fed9110db 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sa\sproblem\scausing\san\sassert()\sto\sfail\sif\sa\ssnippet\scontaining\s0\stokens\swas\srequested\sfrom\sfts3. -D 2015-04-15T08:20:50.158 +C Remove\sa\sbranch\sthat\sbecame\sunreachable\sdue\sto\sone\sof\sthe\searlier\scheck-ins\ntoday. +D 2015-04-15T08:37:42.853 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -287,7 +287,7 @@ F src/test_vfs.c b7e6831e6fcf04c5090accff30640ec5c9630739 F src/test_vfstrace.c bab9594adc976cbe696ff3970728830b4c5ed698 F src/test_wsd.c 41cadfd9d97fe8e3e4e44f61a4a8ccd6f7ca8fe9 F src/threads.c 6bbcc9fe50c917864d48287b4792d46d6e873481 -F src/tokenize.c 2b93d338833be43cba93644562e85a24ff3d97d1 +F src/tokenize.c a8234a67577308935cdf13e618cd66556f5f45d1 F src/trigger.c 69a91bed7c94e46223e37ffccfeeb35e34b999ac F src/update.c 3c4ecc282accf12d39edb8d524cf089645e55a13 F src/utf.c fc6b889ba0779b7722634cdeaa25f1930d93820c @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P 3576973f8b88b6109fbefdebfa53468ffa137009 -R 3265dd5ed99bf273b3517690abeeedc9 -U dan -Z a6b618f03dfa759db2c6c3b930aa2a83 +P eafd0a1e3f25f38d551603f177ff4634cf79de77 +R cd3636389f675a46c2832548029faa61 +U drh +Z 0baf8e6f8836d6dbdde447c335370222 diff --git a/manifest.uuid b/manifest.uuid index e0df72f85f..0fa4f22d90 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -eafd0a1e3f25f38d551603f177ff4634cf79de77 \ No newline at end of file +fa0956edf866f48f448967836709a3ad822ff917 \ No newline at end of file diff --git a/src/tokenize.c b/src/tokenize.c index a4d20c8641..2f8fd98ede 100644 --- a/src/tokenize.c +++ b/src/tokenize.c @@ -449,7 +449,8 @@ int sqlite3RunParser(Parse *pParse, const char *zSql, char **pzErrMsg){ } } abort_parse: - if( zSql[i]==0 && nErr==0 && pParse->rc==SQLITE_OK ){ + assert( nErr==0 ); + if( zSql[i]==0 && pParse->rc==SQLITE_OK ){ if( lastTokenParsed!=TK_SEMI ){ sqlite3Parser(pEngine, TK_SEMI, pParse->sLastToken, pParse); pParse->zTail = &zSql[i]; From 0d01ec8de83b4e0d7523d67c5f92a44f0ba79b8e Mon Sep 17 00:00:00 2001 From: dan Date: Wed, 15 Apr 2015 09:16:39 +0000 Subject: [PATCH 53/53] Remove an incorrect assert() statement from sqlite3Fts3Dequote(). FossilOrigin-Name: bd06eeb8d06237dc2d54d8a03e8bf525cb811c9e --- ext/fts3/fts3.c | 9 ++++++++- ext/fts3/fts3Int.h | 5 +++++ manifest | 18 +++++++++--------- manifest.uuid | 2 +- test/fts3tok1.test | 10 ++++++++++ 5 files changed, 33 insertions(+), 11 deletions(-) diff --git a/ext/fts3/fts3.c b/ext/fts3/fts3.c index eb62c195df..eab8ad63ad 100644 --- a/ext/fts3/fts3.c +++ b/ext/fts3/fts3.c @@ -313,6 +313,13 @@ static int fts3EvalStart(Fts3Cursor *pCsr); static int fts3TermSegReaderCursor( Fts3Cursor *, const char *, int, int, Fts3MultiSegReader **); +#ifndef SQLITE_AMALGAMATION +# if defined(SQLITE_DEBUG) +int sqlite3Fts3Always(int b) { assert( b ); return b; } +int sqlite3Fts3Never(int b) { assert( !b ); return b; } +# endif +#endif + /* ** Write a 64-bit variable-length integer to memory starting at p[0]. ** The length of data written will be between 1 and FTS3_VARINT_MAX bytes. @@ -422,7 +429,7 @@ void sqlite3Fts3Dequote(char *z){ /* If the first byte was a '[', then the close-quote character is a ']' */ if( quote=='[' ) quote = ']'; - while( ALWAYS(z[iIn]) ){ + while( z[iIn] ){ if( z[iIn]==quote ){ if( z[iIn+1]!=quote ) break; z[iOut++] = quote; diff --git a/ext/fts3/fts3Int.h b/ext/fts3/fts3Int.h index 1b8b7bd97e..8285f8aaf5 100644 --- a/ext/fts3/fts3Int.h +++ b/ext/fts3/fts3Int.h @@ -134,6 +134,11 @@ SQLITE_EXTENSION_INIT3 #ifdef SQLITE_COVERAGE_TEST # define ALWAYS(x) (1) # define NEVER(X) (0) +#elif defined(SQLITE_DEBUG) +# define ALWAYS(x) sqlite3Fts3Always((x)!=0) +# define NEVER(x) sqlite3Fts3Never((x)!=0) +int sqlite3Fts3Always(int b); +int sqlite3Fts3Never(int b); #else # define ALWAYS(x) (x) # define NEVER(x) (x) diff --git a/manifest b/manifest index 5fed9110db..7337ec7673 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Remove\sa\sbranch\sthat\sbecame\sunreachable\sdue\sto\sone\sof\sthe\searlier\scheck-ins\ntoday. -D 2015-04-15T08:37:42.853 +C Remove\san\sincorrect\sassert()\sstatement\sfrom\ssqlite3Fts3Dequote(). +D 2015-04-15T09:16:39.633 F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f F Makefile.in 5f78b1ab81b64e7c57a75d170832443e66c0880a F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23 @@ -78,9 +78,9 @@ F ext/fts3/README.content fdc666a70d5257a64fee209f97cf89e0e6e32b51 F ext/fts3/README.syntax a19711dc5458c20734b8e485e75fb1981ec2427a F ext/fts3/README.tokenizers e0a8b81383ea60d0334d274fadf305ea14a8c314 F ext/fts3/README.txt 8c18f41574404623b76917b9da66fcb0ab38328d -F ext/fts3/fts3.c ed6624d7c5fb5aee5d47f884b2d184169fa7a7d4 +F ext/fts3/fts3.c 4bd75289875b63c04f943d6ed7c31737da99cd74 F ext/fts3/fts3.h 3a10a0af180d502cecc50df77b1b22df142817fe -F ext/fts3/fts3Int.h 394858c12a17740f7a1f6bd372c4606d4425a8d1 +F ext/fts3/fts3Int.h 3626655d6ba903a3919bb44e1c38e5f0f9d6be82 F ext/fts3/fts3_aux.c 5c211e17a64885faeb16b9ba7772f9d5445c2365 F ext/fts3/fts3_expr.c 40123785eaa3ebd4c45c9b23407cc44ac0c49905 F ext/fts3/fts3_hash.c 29b986e43f4e9dd40110eafa377dc0d63c422c60 @@ -601,7 +601,7 @@ F test/fts3rnd.test 1320d8826a845e38a96e769562bf83d7a92a15d0 F test/fts3shared.test 57e26a801f21027b7530da77db54286a6fe4997e F test/fts3snippet.test 63dbd687d5bf5191f1b8e6a0977aa9c1e28a7004 F test/fts3sort.test ed34c716a11cc2009a35210e84ad5f9c102362ca -F test/fts3tok1.test c551043de056b0b1582a54e878991f57bad074bc +F test/fts3tok1.test 178c050199af8c05299b1ad572514ce1c54b7827 F test/fts3tok_err.test 52273cd193b9036282f7bacb43da78c6be87418d F test/fts3varint.test 752c08ed5d32c5d7dc211b056f4ed68a76b7e36e F test/fts4aa.test 10aac8e9d62c7357590acfabe3fad01e9a9ce1cb @@ -1250,7 +1250,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1 F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4 F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32 F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f -P eafd0a1e3f25f38d551603f177ff4634cf79de77 -R cd3636389f675a46c2832548029faa61 -U drh -Z 0baf8e6f8836d6dbdde447c335370222 +P fa0956edf866f48f448967836709a3ad822ff917 +R ae90fdb352a7af37163dde65a0adec8a +U dan +Z a5cd9462fba20ef05f7047cbd877b3d9 diff --git a/manifest.uuid b/manifest.uuid index 0fa4f22d90..6c106f0137 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -fa0956edf866f48f448967836709a3ad822ff917 \ No newline at end of file +bd06eeb8d06237dc2d54d8a03e8bf525cb811c9e \ No newline at end of file diff --git a/test/fts3tok1.test b/test/fts3tok1.test index e6fbbe10a2..09b07e9db1 100644 --- a/test/fts3tok1.test +++ b/test/fts3tok1.test @@ -110,5 +110,15 @@ do_catchsql_test 2.1 { SELECT * FROM t4; } {1 {SQL logic error or missing database}} +do_catchsql_test 2.2 { + CREATE VIRTUAL TABLE t USING fts4(tokenize=simple""); +} {0 {}} + +ifcapable fts3_unicode { + do_catchsql_test 2.3 { + CREATE VIRTUAL TABLE u USING fts4(tokenize=unicode61""); + } {1 {unknown tokenizer}} +} + finish_test