Fossil SCM
Update the built-in SQLite to the second 3.18.0 beta.
Commit
c8a4300267fdf1b70d7817a1588db5589774f0fcdde074b59ff01bfde0a13d16
Parent
a99c9ffec2cf627…
2 files changed
+189
-102
+1
-1
+189
-102
| --- src/sqlite3.c | ||
| +++ src/sqlite3.c | ||
| @@ -398,11 +398,11 @@ | ||
| 398 | 398 | ** [sqlite3_libversion_number()], [sqlite3_sourceid()], |
| 399 | 399 | ** [sqlite_version()] and [sqlite_source_id()]. |
| 400 | 400 | */ |
| 401 | 401 | #define SQLITE_VERSION "3.18.0" |
| 402 | 402 | #define SQLITE_VERSION_NUMBER 3018000 |
| 403 | -#define SQLITE_SOURCE_ID "2017-03-20 13:03:39 2aa22509e7c8a1f09b16e4544c95d0b77503daed1f83106ccc18dee8bd9487a4" | |
| 403 | +#define SQLITE_SOURCE_ID "2017-03-23 23:44:55 476088482024e411e2549b1697cdaf0124294c79d43f508c71c4eb66906a56fc" | |
| 404 | 404 | |
| 405 | 405 | /* |
| 406 | 406 | ** CAPI3REF: Run-Time Library Version Numbers |
| 407 | 407 | ** KEYWORDS: sqlite3_version sqlite3_sourceid |
| 408 | 408 | ** |
| @@ -20855,49 +20855,27 @@ | ||
| 20855 | 20855 | /* |
| 20856 | 20856 | ** Initialize this module. |
| 20857 | 20857 | */ |
| 20858 | 20858 | static int sqlite3MemInit(void *NotUsed){ |
| 20859 | 20859 | #if defined(__APPLE__) && !defined(SQLITE_WITHOUT_ZONEMALLOC) |
| 20860 | + int cpuCount; | |
| 20861 | + size_t len; | |
| 20860 | 20862 | if( _sqliteZone_ ){ |
| 20861 | 20863 | return SQLITE_OK; |
| 20862 | 20864 | } |
| 20863 | -#ifndef SQLITE_MIGHT_BE_SINGLE_CORE | |
| 20864 | - /* If not compiled with the SQLITE_MIGHT_BE_SINGLE_CORE flag, assume | |
| 20865 | - ** that multiple cores are always available. This is the default case. | |
| 20866 | - */ | |
| 20867 | - _sqliteZone_ = malloc_default_zone(); | |
| 20868 | -#else | |
| 20869 | - /* With the SQLITE_MIGHT_BE_SINGLE_CORE compile-time option, check the | |
| 20870 | - ** number of cores. Different malloc() strategies are used for single-core and | |
| 20871 | - ** multi-core machines. | |
| 20872 | - */ | |
| 20873 | - { | |
| 20874 | - int cpuCount; | |
| 20875 | - size_t len; | |
| 20876 | - len = sizeof(cpuCount); | |
| 20877 | - /* One usually wants to use hw.acctivecpu for MT decisions, but not here */ | |
| 20878 | - sysctlbyname("hw.ncpu", &cpuCount, &len, NULL, 0); | |
| 20879 | - if( cpuCount>1 ){ | |
| 20880 | - /* defer MT decisions to system malloc */ | |
| 20881 | - _sqliteZone_ = malloc_default_zone(); | |
| 20882 | - }else{ | |
| 20883 | - /* only 1 core, use our own zone to contention over global locks, | |
| 20884 | - ** e.g. we have our own dedicated locks */ | |
| 20885 | - bool success; | |
| 20886 | - malloc_zone_t* newzone = malloc_create_zone(4096, 0); | |
| 20887 | - malloc_set_zone_name(newzone, "Sqlite_Heap"); | |
| 20888 | - do{ | |
| 20889 | - success = OSAtomicCompareAndSwapPtrBarrier(NULL, newzone, | |
| 20890 | - (void * volatile *)&_sqliteZone_); | |
| 20891 | - }while(!_sqliteZone_); | |
| 20892 | - if( !success ){ | |
| 20893 | - /* somebody registered a zone first */ | |
| 20894 | - malloc_destroy_zone(newzone); | |
| 20895 | - } | |
| 20896 | - } | |
| 20897 | - } | |
| 20898 | -#endif /* SQLITE_MIGHT_BE_SINGLE_CORE */ | |
| 20865 | + len = sizeof(cpuCount); | |
| 20866 | + /* One usually wants to use hw.acctivecpu for MT decisions, but not here */ | |
| 20867 | + sysctlbyname("hw.ncpu", &cpuCount, &len, NULL, 0); | |
| 20868 | + if( cpuCount>1 ){ | |
| 20869 | + /* defer MT decisions to system malloc */ | |
| 20870 | + _sqliteZone_ = malloc_default_zone(); | |
| 20871 | + }else{ | |
| 20872 | + /* only 1 core, use our own zone to contention over global locks, | |
| 20873 | + ** e.g. we have our own dedicated locks */ | |
| 20874 | + _sqliteZone_ = malloc_create_zone(4096, 0); | |
| 20875 | + malloc_set_zone_name(_sqliteZone_, "Sqlite_Heap"); | |
| 20876 | + } | |
| 20899 | 20877 | #endif /* defined(__APPLE__) && !defined(SQLITE_WITHOUT_ZONEMALLOC) */ |
| 20900 | 20878 | UNUSED_PARAMETER(NotUsed); |
| 20901 | 20879 | return SQLITE_OK; |
| 20902 | 20880 | } |
| 20903 | 20881 | |
| @@ -25445,16 +25423,17 @@ | ||
| 25445 | 25423 | } |
| 25446 | 25424 | if( precision<etBUFSIZE-10-etBUFSIZE/3 ){ |
| 25447 | 25425 | nOut = etBUFSIZE; |
| 25448 | 25426 | zOut = buf; |
| 25449 | 25427 | }else{ |
| 25450 | - nOut = precision + 10 + precision/3; | |
| 25451 | - zOut = zExtra = sqlite3Malloc( nOut ); | |
| 25428 | + u64 n = (u64)precision + 10 + precision/3; | |
| 25429 | + zOut = zExtra = sqlite3Malloc( n ); | |
| 25452 | 25430 | if( zOut==0 ){ |
| 25453 | 25431 | setStrAccumError(pAccum, STRACCUM_NOMEM); |
| 25454 | 25432 | return; |
| 25455 | 25433 | } |
| 25434 | + nOut = (int)n; | |
| 25456 | 25435 | } |
| 25457 | 25436 | bufpt = &zOut[nOut-1]; |
| 25458 | 25437 | if( xtype==etORDINAL ){ |
| 25459 | 25438 | static const char zOrd[] = "thstndrd"; |
| 25460 | 25439 | int x = (int)(longvalue % 10); |
| @@ -85151,11 +85130,15 @@ | ||
| 85151 | 85130 | char *z = sqlite3VdbeExpandSql(p, zTrace); |
| 85152 | 85131 | x(db->pTraceArg, z); |
| 85153 | 85132 | sqlite3_free(z); |
| 85154 | 85133 | }else |
| 85155 | 85134 | #endif |
| 85156 | - { | |
| 85135 | + if( db->nVdbeExec>1 ){ | |
| 85136 | + char *z = sqlite3MPrintf(db, "-- %s", zTrace); | |
| 85137 | + (void)db->xTrace(SQLITE_TRACE_STMT, db->pTraceArg, p, z); | |
| 85138 | + sqlite3DbFree(db, z); | |
| 85139 | + }else{ | |
| 85157 | 85140 | (void)db->xTrace(SQLITE_TRACE_STMT, db->pTraceArg, p, zTrace); |
| 85158 | 85141 | } |
| 85159 | 85142 | } |
| 85160 | 85143 | #ifdef SQLITE_USE_FCNTL_TRACE |
| 85161 | 85144 | zTrace = (pOp->p4.z ? pOp->p4.z : p->zSql); |
| @@ -97881,11 +97864,11 @@ | ||
| 97881 | 97864 | Index *pPk = sqlite3PrimaryKeyIndex(pIdx->pTable); |
| 97882 | 97865 | int j, k, regKey; |
| 97883 | 97866 | regKey = sqlite3GetTempRange(pParse, pPk->nKeyCol); |
| 97884 | 97867 | for(j=0; j<pPk->nKeyCol; j++){ |
| 97885 | 97868 | k = sqlite3ColumnOfIndex(pIdx, pPk->aiColumn[j]); |
| 97886 | - assert( k>=0 && k<pTab->nCol ); | |
| 97869 | + assert( k>=0 && k<pIdx->nColumn ); | |
| 97887 | 97870 | sqlite3VdbeAddOp3(v, OP_Column, iIdxCur, k, regKey+j); |
| 97888 | 97871 | VdbeComment((v, "%s", pTab->aCol[pPk->aiColumn[j]].zName)); |
| 97889 | 97872 | } |
| 97890 | 97873 | sqlite3VdbeAddOp3(v, OP_MakeRecord, regKey, pPk->nKeyCol, regRowid); |
| 97891 | 97874 | sqlite3ReleaseTempRange(pParse, regKey, pPk->nKeyCol); |
| @@ -110785,12 +110768,10 @@ | ||
| 110785 | 110768 | ** might change the definition of a collation sequence and then run |
| 110786 | 110769 | ** a VACUUM command. In that case keys may not be written in strictly |
| 110787 | 110770 | ** sorted order. */ |
| 110788 | 110771 | for(i=0; i<pSrcIdx->nColumn; i++){ |
| 110789 | 110772 | const char *zColl = pSrcIdx->azColl[i]; |
| 110790 | - assert( sqlite3_stricmp(sqlite3StrBINARY, zColl)!=0 | |
| 110791 | - || sqlite3StrBINARY==zColl ); | |
| 110792 | 110773 | if( sqlite3_stricmp(sqlite3StrBINARY, zColl) ) break; |
| 110793 | 110774 | } |
| 110794 | 110775 | if( i==pSrcIdx->nColumn ){ |
| 110795 | 110776 | idxInsFlags = OPFLAG_USESEEKRESULT; |
| 110796 | 110777 | sqlite3VdbeAddOp3(v, OP_Last, iDest, 0, -1); |
| @@ -145575,12 +145556,13 @@ | ||
| 145575 | 145556 | /* |
| 145576 | 145557 | ** Read a 64-bit variable-length integer from memory starting at p[0]. |
| 145577 | 145558 | ** Return the number of bytes read, or 0 on error. |
| 145578 | 145559 | ** The value is stored in *v. |
| 145579 | 145560 | */ |
| 145580 | -SQLITE_PRIVATE int sqlite3Fts3GetVarint(const char *p, sqlite_int64 *v){ | |
| 145581 | - const char *pStart = p; | |
| 145561 | +SQLITE_PRIVATE int sqlite3Fts3GetVarint(const char *pBuf, sqlite_int64 *v){ | |
| 145562 | + const unsigned char *p = (const unsigned char*)pBuf; | |
| 145563 | + const unsigned char *pStart = p; | |
| 145582 | 145564 | u32 a; |
| 145583 | 145565 | u64 b; |
| 145584 | 145566 | int shift; |
| 145585 | 145567 | |
| 145586 | 145568 | GETVARINT_INIT(a, p, 0, 0x00, 0x80, *v, 1); |
| @@ -146623,11 +146605,13 @@ | ||
| 146623 | 146605 | /* Fill in the azColumn array */ |
| 146624 | 146606 | for(iCol=0; iCol<nCol; iCol++){ |
| 146625 | 146607 | char *z; |
| 146626 | 146608 | int n = 0; |
| 146627 | 146609 | z = (char *)sqlite3Fts3NextToken(aCol[iCol], &n); |
| 146628 | - memcpy(zCsr, z, n); | |
| 146610 | + if( n>0 ){ | |
| 146611 | + memcpy(zCsr, z, n); | |
| 146612 | + } | |
| 146629 | 146613 | zCsr[n] = '\0'; |
| 146630 | 146614 | sqlite3Fts3Dequote(zCsr); |
| 146631 | 146615 | p->azColumn[iCol] = zCsr; |
| 146632 | 146616 | zCsr += n+1; |
| 146633 | 146617 | assert( zCsr <= &((char *)p)[nByte] ); |
| @@ -160263,15 +160247,18 @@ | ||
| 160263 | 160247 | |
| 160264 | 160248 | /* |
| 160265 | 160249 | ** Convert the text beginning at *pz into an integer and return |
| 160266 | 160250 | ** its value. Advance *pz to point to the first character past |
| 160267 | 160251 | ** the integer. |
| 160252 | +** | |
| 160253 | +** This function used for parameters to merge= and incrmerge= | |
| 160254 | +** commands. | |
| 160268 | 160255 | */ |
| 160269 | 160256 | static int fts3Getint(const char **pz){ |
| 160270 | 160257 | const char *z = *pz; |
| 160271 | 160258 | int i = 0; |
| 160272 | - while( (*z)>='0' && (*z)<='9' ) i = 10*i + *(z++) - '0'; | |
| 160259 | + while( (*z)>='0' && (*z)<='9' && i<214748363 ) i = 10*i + *(z++) - '0'; | |
| 160273 | 160260 | *pz = z; |
| 160274 | 160261 | return i; |
| 160275 | 160262 | } |
| 160276 | 160263 | |
| 160277 | 160264 | /* |
| @@ -162833,20 +162820,20 @@ | ||
| 162833 | 162820 | const char *zIn, /* Array of characters to make exceptions */ |
| 162834 | 162821 | int nIn /* Length of z in bytes */ |
| 162835 | 162822 | ){ |
| 162836 | 162823 | const unsigned char *z = (const unsigned char *)zIn; |
| 162837 | 162824 | const unsigned char *zTerm = &z[nIn]; |
| 162838 | - int iCode; | |
| 162825 | + unsigned int iCode; | |
| 162839 | 162826 | int nEntry = 0; |
| 162840 | 162827 | |
| 162841 | 162828 | assert( bAlnum==0 || bAlnum==1 ); |
| 162842 | 162829 | |
| 162843 | 162830 | while( z<zTerm ){ |
| 162844 | 162831 | READ_UTF8(z, zTerm, iCode); |
| 162845 | - assert( (sqlite3FtsUnicodeIsalnum(iCode) & 0xFFFFFFFE)==0 ); | |
| 162846 | - if( sqlite3FtsUnicodeIsalnum(iCode)!=bAlnum | |
| 162847 | - && sqlite3FtsUnicodeIsdiacritic(iCode)==0 | |
| 162832 | + assert( (sqlite3FtsUnicodeIsalnum((int)iCode) & 0xFFFFFFFE)==0 ); | |
| 162833 | + if( sqlite3FtsUnicodeIsalnum((int)iCode)!=bAlnum | |
| 162834 | + && sqlite3FtsUnicodeIsdiacritic((int)iCode)==0 | |
| 162848 | 162835 | ){ |
| 162849 | 162836 | nEntry++; |
| 162850 | 162837 | } |
| 162851 | 162838 | } |
| 162852 | 162839 | |
| @@ -162859,17 +162846,17 @@ | ||
| 162859 | 162846 | nNew = p->nException; |
| 162860 | 162847 | |
| 162861 | 162848 | z = (const unsigned char *)zIn; |
| 162862 | 162849 | while( z<zTerm ){ |
| 162863 | 162850 | READ_UTF8(z, zTerm, iCode); |
| 162864 | - if( sqlite3FtsUnicodeIsalnum(iCode)!=bAlnum | |
| 162865 | - && sqlite3FtsUnicodeIsdiacritic(iCode)==0 | |
| 162851 | + if( sqlite3FtsUnicodeIsalnum((int)iCode)!=bAlnum | |
| 162852 | + && sqlite3FtsUnicodeIsdiacritic((int)iCode)==0 | |
| 162866 | 162853 | ){ |
| 162867 | 162854 | int i, j; |
| 162868 | - for(i=0; i<nNew && aNew[i]<iCode; i++); | |
| 162855 | + for(i=0; i<nNew && aNew[i]<(int)iCode; i++); | |
| 162869 | 162856 | for(j=nNew; j>i; j--) aNew[j] = aNew[j-1]; |
| 162870 | - aNew[i] = iCode; | |
| 162857 | + aNew[i] = (int)iCode; | |
| 162871 | 162858 | nNew++; |
| 162872 | 162859 | } |
| 162873 | 162860 | } |
| 162874 | 162861 | p->aiException = aNew; |
| 162875 | 162862 | p->nException = nNew; |
| @@ -163015,11 +163002,11 @@ | ||
| 163015 | 163002 | int *piEnd, /* OUT: Ending offset of token */ |
| 163016 | 163003 | int *piPos /* OUT: Position integer of token */ |
| 163017 | 163004 | ){ |
| 163018 | 163005 | unicode_cursor *pCsr = (unicode_cursor *)pC; |
| 163019 | 163006 | unicode_tokenizer *p = ((unicode_tokenizer *)pCsr->base.pTokenizer); |
| 163020 | - int iCode = 0; | |
| 163007 | + unsigned int iCode = 0; | |
| 163021 | 163008 | char *zOut; |
| 163022 | 163009 | const unsigned char *z = &pCsr->aInput[pCsr->iOff]; |
| 163023 | 163010 | const unsigned char *zStart = z; |
| 163024 | 163011 | const unsigned char *zEnd; |
| 163025 | 163012 | const unsigned char *zTerm = &pCsr->aInput[pCsr->nInput]; |
| @@ -163027,11 +163014,11 @@ | ||
| 163027 | 163014 | /* Scan past any delimiter characters before the start of the next token. |
| 163028 | 163015 | ** Return SQLITE_DONE early if this takes us all the way to the end of |
| 163029 | 163016 | ** the input. */ |
| 163030 | 163017 | while( z<zTerm ){ |
| 163031 | 163018 | READ_UTF8(z, zTerm, iCode); |
| 163032 | - if( unicodeIsAlnum(p, iCode) ) break; | |
| 163019 | + if( unicodeIsAlnum(p, (int)iCode) ) break; | |
| 163033 | 163020 | zStart = z; |
| 163034 | 163021 | } |
| 163035 | 163022 | if( zStart>=zTerm ) return SQLITE_DONE; |
| 163036 | 163023 | |
| 163037 | 163024 | zOut = pCsr->zToken; |
| @@ -163047,20 +163034,20 @@ | ||
| 163047 | 163034 | pCsr->nAlloc += 64; |
| 163048 | 163035 | } |
| 163049 | 163036 | |
| 163050 | 163037 | /* Write the folded case of the last character read to the output */ |
| 163051 | 163038 | zEnd = z; |
| 163052 | - iOut = sqlite3FtsUnicodeFold(iCode, p->bRemoveDiacritic); | |
| 163039 | + iOut = sqlite3FtsUnicodeFold((int)iCode, p->bRemoveDiacritic); | |
| 163053 | 163040 | if( iOut ){ |
| 163054 | 163041 | WRITE_UTF8(zOut, iOut); |
| 163055 | 163042 | } |
| 163056 | 163043 | |
| 163057 | 163044 | /* If the cursor is not at EOF, read the next character */ |
| 163058 | 163045 | if( z>=zTerm ) break; |
| 163059 | 163046 | READ_UTF8(z, zTerm, iCode); |
| 163060 | - }while( unicodeIsAlnum(p, iCode) | |
| 163061 | - || sqlite3FtsUnicodeIsdiacritic(iCode) | |
| 163047 | + }while( unicodeIsAlnum(p, (int)iCode) | |
| 163048 | + || sqlite3FtsUnicodeIsdiacritic((int)iCode) | |
| 163062 | 163049 | ); |
| 163063 | 163050 | |
| 163064 | 163051 | /* Set the output variables and return. */ |
| 163065 | 163052 | pCsr->iOff = (int)(z - pCsr->aInput); |
| 163066 | 163053 | *paToken = pCsr->zToken; |
| @@ -163220,13 +163207,13 @@ | ||
| 163220 | 163207 | }; |
| 163221 | 163208 | static const unsigned int aAscii[4] = { |
| 163222 | 163209 | 0xFFFFFFFF, 0xFC00FFFF, 0xF8000001, 0xF8000001, |
| 163223 | 163210 | }; |
| 163224 | 163211 | |
| 163225 | - if( c<128 ){ | |
| 163226 | - return ( (aAscii[c >> 5] & (1 << (c & 0x001F)))==0 ); | |
| 163227 | - }else if( c<(1<<22) ){ | |
| 163212 | + if( (unsigned int)c<128 ){ | |
| 163213 | + return ( (aAscii[c >> 5] & ((unsigned int)1 << (c & 0x001F)))==0 ); | |
| 163214 | + }else if( (unsigned int)c<(1<<22) ){ | |
| 163228 | 163215 | unsigned int key = (((unsigned int)c)<<10) | 0x000003FF; |
| 163229 | 163216 | int iRes = 0; |
| 163230 | 163217 | int iHi = sizeof(aEntry)/sizeof(aEntry[0]) - 1; |
| 163231 | 163218 | int iLo = 0; |
| 163232 | 163219 | while( iHi>=iLo ){ |
| @@ -163415,20 +163402,21 @@ | ||
| 163415 | 163402 | 65514, 65521, 65527, 65528, 65529, |
| 163416 | 163403 | }; |
| 163417 | 163404 | |
| 163418 | 163405 | int ret = c; |
| 163419 | 163406 | |
| 163420 | - assert( c>=0 ); | |
| 163421 | 163407 | assert( sizeof(unsigned short)==2 && sizeof(unsigned char)==1 ); |
| 163422 | 163408 | |
| 163423 | 163409 | if( c<128 ){ |
| 163424 | 163410 | if( c>='A' && c<='Z' ) ret = c + ('a' - 'A'); |
| 163425 | 163411 | }else if( c<65536 ){ |
| 163412 | + const struct TableEntry *p; | |
| 163426 | 163413 | int iHi = sizeof(aEntry)/sizeof(aEntry[0]) - 1; |
| 163427 | 163414 | int iLo = 0; |
| 163428 | 163415 | int iRes = -1; |
| 163429 | 163416 | |
| 163417 | + assert( c>aEntry[0].iCode ); | |
| 163430 | 163418 | while( iHi>=iLo ){ |
| 163431 | 163419 | int iTest = (iHi + iLo) / 2; |
| 163432 | 163420 | int cmp = (c - aEntry[iTest].iCode); |
| 163433 | 163421 | if( cmp>=0 ){ |
| 163434 | 163422 | iRes = iTest; |
| @@ -163435,18 +163423,16 @@ | ||
| 163435 | 163423 | iLo = iTest+1; |
| 163436 | 163424 | }else{ |
| 163437 | 163425 | iHi = iTest-1; |
| 163438 | 163426 | } |
| 163439 | 163427 | } |
| 163440 | - assert( iRes<0 || c>=aEntry[iRes].iCode ); | |
| 163441 | - | |
| 163442 | - if( iRes>=0 ){ | |
| 163443 | - const struct TableEntry *p = &aEntry[iRes]; | |
| 163444 | - if( c<(p->iCode + p->nRange) && 0==(0x01 & p->flags & (p->iCode ^ c)) ){ | |
| 163445 | - ret = (c + (aiOff[p->flags>>1])) & 0x0000FFFF; | |
| 163446 | - assert( ret>0 ); | |
| 163447 | - } | |
| 163428 | + | |
| 163429 | + assert( iRes>=0 && c>=aEntry[iRes].iCode ); | |
| 163430 | + p = &aEntry[iRes]; | |
| 163431 | + if( c<(p->iCode + p->nRange) && 0==(0x01 & p->flags & (p->iCode ^ c)) ){ | |
| 163432 | + ret = (c + (aiOff[p->flags>>1])) & 0x0000FFFF; | |
| 163433 | + assert( ret>0 ); | |
| 163448 | 163434 | } |
| 163449 | 163435 | |
| 163450 | 163436 | if( bRemoveDiacritic ) ret = remove_diacritic(ret); |
| 163451 | 163437 | } |
| 163452 | 163438 | |
| @@ -163919,19 +163905,19 @@ | ||
| 163919 | 163905 | #elif SQLITE_BYTEORDER==4321 |
| 163920 | 163906 | i64 x; |
| 163921 | 163907 | memcpy(&x, p, 8); |
| 163922 | 163908 | return x; |
| 163923 | 163909 | #else |
| 163924 | - return ( | |
| 163925 | - (((i64)p[0]) << 56) + | |
| 163926 | - (((i64)p[1]) << 48) + | |
| 163927 | - (((i64)p[2]) << 40) + | |
| 163928 | - (((i64)p[3]) << 32) + | |
| 163929 | - (((i64)p[4]) << 24) + | |
| 163930 | - (((i64)p[5]) << 16) + | |
| 163931 | - (((i64)p[6]) << 8) + | |
| 163932 | - (((i64)p[7]) << 0) | |
| 163910 | + return (i64)( | |
| 163911 | + (((u64)p[0]) << 56) + | |
| 163912 | + (((u64)p[1]) << 48) + | |
| 163913 | + (((u64)p[2]) << 40) + | |
| 163914 | + (((u64)p[3]) << 32) + | |
| 163915 | + (((u64)p[4]) << 24) + | |
| 163916 | + (((u64)p[5]) << 16) + | |
| 163917 | + (((u64)p[6]) << 8) + | |
| 163918 | + (((u64)p[7]) << 0) | |
| 163933 | 163919 | ); |
| 163934 | 163920 | #endif |
| 163935 | 163921 | } |
| 163936 | 163922 | |
| 163937 | 163923 | /* |
| @@ -178936,26 +178922,28 @@ | ||
| 178936 | 178922 | /* Bit values for the JsonNode.jnFlag field |
| 178937 | 178923 | */ |
| 178938 | 178924 | #define JNODE_RAW 0x01 /* Content is raw, not JSON encoded */ |
| 178939 | 178925 | #define JNODE_ESCAPE 0x02 /* Content is text with \ escapes */ |
| 178940 | 178926 | #define JNODE_REMOVE 0x04 /* Do not output */ |
| 178941 | -#define JNODE_REPLACE 0x08 /* Replace with JsonNode.iVal */ | |
| 178942 | -#define JNODE_APPEND 0x10 /* More ARRAY/OBJECT entries at u.iAppend */ | |
| 178943 | -#define JNODE_LABEL 0x20 /* Is a label of an object */ | |
| 178927 | +#define JNODE_REPLACE 0x08 /* Replace with JsonNode.u.iReplace */ | |
| 178928 | +#define JNODE_PATCH 0x10 /* Patch with JsonNode.u.pPatch */ | |
| 178929 | +#define JNODE_APPEND 0x20 /* More ARRAY/OBJECT entries at u.iAppend */ | |
| 178930 | +#define JNODE_LABEL 0x40 /* Is a label of an object */ | |
| 178944 | 178931 | |
| 178945 | 178932 | |
| 178946 | 178933 | /* A single node of parsed JSON |
| 178947 | 178934 | */ |
| 178948 | 178935 | struct JsonNode { |
| 178949 | 178936 | u8 eType; /* One of the JSON_ type values */ |
| 178950 | 178937 | u8 jnFlags; /* JNODE flags */ |
| 178951 | - u8 iVal; /* Replacement value when JNODE_REPLACE */ | |
| 178952 | 178938 | u32 n; /* Bytes of content, or number of sub-nodes */ |
| 178953 | 178939 | union { |
| 178954 | 178940 | const char *zJContent; /* Content for INT, REAL, and STRING */ |
| 178955 | 178941 | u32 iAppend; /* More terms for ARRAY and OBJECT */ |
| 178956 | 178942 | u32 iKey; /* Key for ARRAY objects in json_tree() */ |
| 178943 | + u32 iReplace; /* Replacement content for JNODE_REPLACE */ | |
| 178944 | + JsonNode *pPatch; /* Node chain of patch for JNODE_PATCH */ | |
| 178957 | 178945 | } u; |
| 178958 | 178946 | }; |
| 178959 | 178947 | |
| 178960 | 178948 | /* A completely parsed JSON string |
| 178961 | 178949 | */ |
| @@ -179208,10 +179196,17 @@ | ||
| 179208 | 179196 | static void jsonRenderNode( |
| 179209 | 179197 | JsonNode *pNode, /* The node to render */ |
| 179210 | 179198 | JsonString *pOut, /* Write JSON here */ |
| 179211 | 179199 | sqlite3_value **aReplace /* Replacement values */ |
| 179212 | 179200 | ){ |
| 179201 | + if( pNode->jnFlags & (JNODE_REPLACE|JNODE_PATCH) ){ | |
| 179202 | + if( pNode->jnFlags & JNODE_REPLACE ){ | |
| 179203 | + jsonAppendValue(pOut, aReplace[pNode->u.iReplace]); | |
| 179204 | + return; | |
| 179205 | + } | |
| 179206 | + pNode = pNode->u.pPatch; | |
| 179207 | + } | |
| 179213 | 179208 | switch( pNode->eType ){ |
| 179214 | 179209 | default: { |
| 179215 | 179210 | assert( pNode->eType==JSON_NULL ); |
| 179216 | 179211 | jsonAppendRaw(pOut, "null", 4); |
| 179217 | 179212 | break; |
| @@ -179239,16 +179234,11 @@ | ||
| 179239 | 179234 | case JSON_ARRAY: { |
| 179240 | 179235 | u32 j = 1; |
| 179241 | 179236 | jsonAppendChar(pOut, '['); |
| 179242 | 179237 | for(;;){ |
| 179243 | 179238 | while( j<=pNode->n ){ |
| 179244 | - if( pNode[j].jnFlags & (JNODE_REMOVE|JNODE_REPLACE) ){ | |
| 179245 | - if( pNode[j].jnFlags & JNODE_REPLACE ){ | |
| 179246 | - jsonAppendSeparator(pOut); | |
| 179247 | - jsonAppendValue(pOut, aReplace[pNode[j].iVal]); | |
| 179248 | - } | |
| 179249 | - }else{ | |
| 179239 | + if( (pNode[j].jnFlags & JNODE_REMOVE)==0 ){ | |
| 179250 | 179240 | jsonAppendSeparator(pOut); |
| 179251 | 179241 | jsonRenderNode(&pNode[j], pOut, aReplace); |
| 179252 | 179242 | } |
| 179253 | 179243 | j += jsonNodeSize(&pNode[j]); |
| 179254 | 179244 | } |
| @@ -179266,15 +179256,11 @@ | ||
| 179266 | 179256 | while( j<=pNode->n ){ |
| 179267 | 179257 | if( (pNode[j+1].jnFlags & JNODE_REMOVE)==0 ){ |
| 179268 | 179258 | jsonAppendSeparator(pOut); |
| 179269 | 179259 | jsonRenderNode(&pNode[j], pOut, aReplace); |
| 179270 | 179260 | jsonAppendChar(pOut, ':'); |
| 179271 | - if( pNode[j+1].jnFlags & JNODE_REPLACE ){ | |
| 179272 | - jsonAppendValue(pOut, aReplace[pNode[j+1].iVal]); | |
| 179273 | - }else{ | |
| 179274 | - jsonRenderNode(&pNode[j+1], pOut, aReplace); | |
| 179275 | - } | |
| 179261 | + jsonRenderNode(&pNode[j+1], pOut, aReplace); | |
| 179276 | 179262 | } |
| 179277 | 179263 | j += 1 + jsonNodeSize(&pNode[j+1]); |
| 179278 | 179264 | } |
| 179279 | 179265 | if( (pNode->jnFlags & JNODE_APPEND)==0 ) break; |
| 179280 | 179266 | pNode = &pNode[pNode->u.iAppend]; |
| @@ -179497,11 +179483,10 @@ | ||
| 179497 | 179483 | return jsonParseAddNodeExpand(pParse, eType, n, zContent); |
| 179498 | 179484 | } |
| 179499 | 179485 | p = &pParse->aNode[pParse->nNode]; |
| 179500 | 179486 | p->eType = (u8)eType; |
| 179501 | 179487 | p->jnFlags = 0; |
| 179502 | - p->iVal = 0; | |
| 179503 | 179488 | p->n = n; |
| 179504 | 179489 | p->u.zJContent = zContent; |
| 179505 | 179490 | return pParse->nNode++; |
| 179506 | 179491 | } |
| 179507 | 179492 | |
| @@ -180154,10 +180139,111 @@ | ||
| 180154 | 180139 | sqlite3_result_subtype(ctx, JSON_SUBTYPE); |
| 180155 | 180140 | } |
| 180156 | 180141 | jsonReset(&jx); |
| 180157 | 180142 | jsonParseReset(&x); |
| 180158 | 180143 | } |
| 180144 | + | |
| 180145 | +/* This is the RFC 7396 MergePatch algorithm. | |
| 180146 | +*/ | |
| 180147 | +static JsonNode *jsonMergePatch( | |
| 180148 | + JsonParse *pParse, /* The JSON parser that contains the TARGET */ | |
| 180149 | + int iTarget, /* Node of the TARGET in pParse */ | |
| 180150 | + JsonNode *pPatch /* The PATCH */ | |
| 180151 | +){ | |
| 180152 | + u32 i, j; | |
| 180153 | + u32 iRoot; | |
| 180154 | + JsonNode *pTarget; | |
| 180155 | + if( pPatch->eType!=JSON_OBJECT ){ | |
| 180156 | + return pPatch; | |
| 180157 | + } | |
| 180158 | + assert( iTarget>=0 && iTarget<pParse->nNode ); | |
| 180159 | + pTarget = &pParse->aNode[iTarget]; | |
| 180160 | + assert( (pPatch->jnFlags & JNODE_APPEND)==0 ); | |
| 180161 | + if( pTarget->eType!=JSON_OBJECT ){ | |
| 180162 | + for(i=2; i<=pPatch->n; i += jsonNodeSize(&pPatch[i])+1){ | |
| 180163 | + if( pPatch[i].eType==JSON_NULL ){ | |
| 180164 | + pPatch[i].jnFlags |= JNODE_REMOVE; | |
| 180165 | + } | |
| 180166 | + } | |
| 180167 | + return pPatch; | |
| 180168 | + } | |
| 180169 | + iRoot = iTarget; | |
| 180170 | + for(i=1; i<pPatch->n; i += jsonNodeSize(&pPatch[i+1])+1){ | |
| 180171 | + int nKey; | |
| 180172 | + const char *zKey; | |
| 180173 | + assert( pPatch[i].eType==JSON_STRING ); | |
| 180174 | + assert( pPatch[i].jnFlags & JNODE_LABEL ); | |
| 180175 | + nKey = pPatch[i].n; | |
| 180176 | + zKey = pPatch[i].u.zJContent; | |
| 180177 | + assert( (pPatch[i].jnFlags & JNODE_RAW)==0 ); | |
| 180178 | + for(j=1; j<pTarget->n; j += jsonNodeSize(&pTarget[j+1])+1 ){ | |
| 180179 | + assert( pTarget[j].eType==JSON_STRING ); | |
| 180180 | + assert( pTarget[j].jnFlags & JNODE_LABEL ); | |
| 180181 | + assert( (pPatch[i].jnFlags & JNODE_RAW)==0 ); | |
| 180182 | + if( pTarget[j].n==nKey && strncmp(pTarget[j].u.zJContent,zKey,nKey)==0 ){ | |
| 180183 | + if( pTarget[j+1].jnFlags & (JNODE_REMOVE|JNODE_PATCH) ) break; | |
| 180184 | + if( pPatch[i+1].eType==JSON_NULL ){ | |
| 180185 | + pTarget[j+1].jnFlags |= JNODE_REMOVE; | |
| 180186 | + }else{ | |
| 180187 | + JsonNode *pNew = jsonMergePatch(pParse, iTarget+j+1, &pPatch[i+1]); | |
| 180188 | + if( pNew==0 ) return 0; | |
| 180189 | + pTarget = &pParse->aNode[iTarget]; | |
| 180190 | + if( pNew!=&pTarget[j+1] ){ | |
| 180191 | + pTarget[j+1].u.pPatch = pNew; | |
| 180192 | + pTarget[j+1].jnFlags |= JNODE_PATCH; | |
| 180193 | + } | |
| 180194 | + } | |
| 180195 | + break; | |
| 180196 | + } | |
| 180197 | + } | |
| 180198 | + if( j>=pTarget->n && pPatch[i+1].eType!=JSON_NULL ){ | |
| 180199 | + int iStart, iPatch; | |
| 180200 | + iStart = jsonParseAddNode(pParse, JSON_OBJECT, 2, 0); | |
| 180201 | + jsonParseAddNode(pParse, JSON_STRING, nKey, zKey); | |
| 180202 | + iPatch = jsonParseAddNode(pParse, JSON_TRUE, 0, 0); | |
| 180203 | + if( pParse->oom ) return 0; | |
| 180204 | + pTarget = &pParse->aNode[iTarget]; | |
| 180205 | + pParse->aNode[iRoot].jnFlags |= JNODE_APPEND; | |
| 180206 | + pParse->aNode[iRoot].u.iAppend = iStart - iRoot; | |
| 180207 | + iRoot = iStart; | |
| 180208 | + pParse->aNode[iPatch].jnFlags |= JNODE_PATCH; | |
| 180209 | + pParse->aNode[iPatch].u.pPatch = &pPatch[i+1]; | |
| 180210 | + } | |
| 180211 | + } | |
| 180212 | + return pTarget; | |
| 180213 | +} | |
| 180214 | + | |
| 180215 | +/* | |
| 180216 | +** Implementation of the json_mergepatch(JSON1,JSON2) function. Return a JSON | |
| 180217 | +** object that is the result of running the RFC 7396 MergePatch() algorithm | |
| 180218 | +** on the two arguments. | |
| 180219 | +*/ | |
| 180220 | +static void jsonPatchFunc( | |
| 180221 | + sqlite3_context *ctx, | |
| 180222 | + int argc, | |
| 180223 | + sqlite3_value **argv | |
| 180224 | +){ | |
| 180225 | + JsonParse x; /* The JSON that is being patched */ | |
| 180226 | + JsonParse y; /* The patch */ | |
| 180227 | + JsonNode *pResult; /* The result of the merge */ | |
| 180228 | + | |
| 180229 | + if( jsonParse(&x, ctx, (const char*)sqlite3_value_text(argv[0])) ) return; | |
| 180230 | + if( jsonParse(&y, ctx, (const char*)sqlite3_value_text(argv[1])) ){ | |
| 180231 | + jsonParseReset(&x); | |
| 180232 | + return; | |
| 180233 | + } | |
| 180234 | + pResult = jsonMergePatch(&x, 0, y.aNode); | |
| 180235 | + assert( pResult!=0 || x.oom ); | |
| 180236 | + if( pResult ){ | |
| 180237 | + jsonReturnJson(pResult, ctx, 0); | |
| 180238 | + }else{ | |
| 180239 | + sqlite3_result_error_nomem(ctx); | |
| 180240 | + } | |
| 180241 | + jsonParseReset(&x); | |
| 180242 | + jsonParseReset(&y); | |
| 180243 | +} | |
| 180244 | + | |
| 180159 | 180245 | |
| 180160 | 180246 | /* |
| 180161 | 180247 | ** Implementation of the json_object(NAME,VALUE,...) function. Return a JSON |
| 180162 | 180248 | ** object that contains all name/value given in arguments. Or if any name |
| 180163 | 180249 | ** is not a string or if any value is a BLOB, throw an error. |
| @@ -180258,15 +180344,15 @@ | ||
| 180258 | 180344 | zPath = (const char*)sqlite3_value_text(argv[i]); |
| 180259 | 180345 | pNode = jsonLookup(&x, zPath, 0, ctx); |
| 180260 | 180346 | if( x.nErr ) goto replace_err; |
| 180261 | 180347 | if( pNode ){ |
| 180262 | 180348 | pNode->jnFlags |= (u8)JNODE_REPLACE; |
| 180263 | - pNode->iVal = (u8)(i+1); | |
| 180349 | + pNode->u.iReplace = i + 1; | |
| 180264 | 180350 | } |
| 180265 | 180351 | } |
| 180266 | 180352 | if( x.aNode[0].jnFlags & JNODE_REPLACE ){ |
| 180267 | - sqlite3_result_value(ctx, argv[x.aNode[0].iVal]); | |
| 180353 | + sqlite3_result_value(ctx, argv[x.aNode[0].u.iReplace]); | |
| 180268 | 180354 | }else{ |
| 180269 | 180355 | jsonReturnJson(x.aNode, ctx, argv); |
| 180270 | 180356 | } |
| 180271 | 180357 | replace_err: |
| 180272 | 180358 | jsonParseReset(&x); |
| @@ -180312,15 +180398,15 @@ | ||
| 180312 | 180398 | goto jsonSetDone; |
| 180313 | 180399 | }else if( x.nErr ){ |
| 180314 | 180400 | goto jsonSetDone; |
| 180315 | 180401 | }else if( pNode && (bApnd || bIsSet) ){ |
| 180316 | 180402 | pNode->jnFlags |= (u8)JNODE_REPLACE; |
| 180317 | - pNode->iVal = (u8)(i+1); | |
| 180403 | + pNode->u.iReplace = i + 1; | |
| 180318 | 180404 | } |
| 180319 | 180405 | } |
| 180320 | 180406 | if( x.aNode[0].jnFlags & JNODE_REPLACE ){ |
| 180321 | - sqlite3_result_value(ctx, argv[x.aNode[0].iVal]); | |
| 180407 | + sqlite3_result_value(ctx, argv[x.aNode[0].u.iReplace]); | |
| 180322 | 180408 | }else{ |
| 180323 | 180409 | jsonReturnJson(x.aNode, ctx, argv); |
| 180324 | 180410 | } |
| 180325 | 180411 | jsonSetDone: |
| 180326 | 180412 | jsonParseReset(&x); |
| @@ -180959,10 +181045,11 @@ | ||
| 180959 | 181045 | { "json_array_length", 1, 0, jsonArrayLengthFunc }, |
| 180960 | 181046 | { "json_array_length", 2, 0, jsonArrayLengthFunc }, |
| 180961 | 181047 | { "json_extract", -1, 0, jsonExtractFunc }, |
| 180962 | 181048 | { "json_insert", -1, 0, jsonSetFunc }, |
| 180963 | 181049 | { "json_object", -1, 0, jsonObjectFunc }, |
| 181050 | + { "json_patch", 2, 0, jsonPatchFunc }, | |
| 180964 | 181051 | { "json_quote", 1, 0, jsonQuoteFunc }, |
| 180965 | 181052 | { "json_remove", -1, 0, jsonRemoveFunc }, |
| 180966 | 181053 | { "json_replace", -1, 0, jsonReplaceFunc }, |
| 180967 | 181054 | { "json_set", -1, 1, jsonSetFunc }, |
| 180968 | 181055 | { "json_type", 1, 0, jsonTypeFunc }, |
| @@ -198120,11 +198207,11 @@ | ||
| 198120 | 198207 | int nArg, /* Number of args */ |
| 198121 | 198208 | sqlite3_value **apUnused /* Function arguments */ |
| 198122 | 198209 | ){ |
| 198123 | 198210 | assert( nArg==0 ); |
| 198124 | 198211 | UNUSED_PARAM2(nArg, apUnused); |
| 198125 | - sqlite3_result_text(pCtx, "fts5: 2017-03-18 13:59:46 4e6a03d9e12b120d15946b025f97a97697cb8e8af543c238ffda220c9e3f28f4", -1, SQLITE_TRANSIENT); | |
| 198212 | + sqlite3_result_text(pCtx, "fts5: 2017-03-23 23:44:55 476088482024e411e2549b1697cdaf0124294c79d43f508c71c4eb66906a56fc", -1, SQLITE_TRANSIENT); | |
| 198126 | 198213 | } |
| 198127 | 198214 | |
| 198128 | 198215 | static int fts5Init(sqlite3 *db){ |
| 198129 | 198216 | static const sqlite3_module fts5Mod = { |
| 198130 | 198217 | /* iVersion */ 2, |
| 198131 | 198218 |
| --- src/sqlite3.c | |
| +++ src/sqlite3.c | |
| @@ -398,11 +398,11 @@ | |
| 398 | ** [sqlite3_libversion_number()], [sqlite3_sourceid()], |
| 399 | ** [sqlite_version()] and [sqlite_source_id()]. |
| 400 | */ |
| 401 | #define SQLITE_VERSION "3.18.0" |
| 402 | #define SQLITE_VERSION_NUMBER 3018000 |
| 403 | #define SQLITE_SOURCE_ID "2017-03-20 13:03:39 2aa22509e7c8a1f09b16e4544c95d0b77503daed1f83106ccc18dee8bd9487a4" |
| 404 | |
| 405 | /* |
| 406 | ** CAPI3REF: Run-Time Library Version Numbers |
| 407 | ** KEYWORDS: sqlite3_version sqlite3_sourceid |
| 408 | ** |
| @@ -20855,49 +20855,27 @@ | |
| 20855 | /* |
| 20856 | ** Initialize this module. |
| 20857 | */ |
| 20858 | static int sqlite3MemInit(void *NotUsed){ |
| 20859 | #if defined(__APPLE__) && !defined(SQLITE_WITHOUT_ZONEMALLOC) |
| 20860 | if( _sqliteZone_ ){ |
| 20861 | return SQLITE_OK; |
| 20862 | } |
| 20863 | #ifndef SQLITE_MIGHT_BE_SINGLE_CORE |
| 20864 | /* If not compiled with the SQLITE_MIGHT_BE_SINGLE_CORE flag, assume |
| 20865 | ** that multiple cores are always available. This is the default case. |
| 20866 | */ |
| 20867 | _sqliteZone_ = malloc_default_zone(); |
| 20868 | #else |
| 20869 | /* With the SQLITE_MIGHT_BE_SINGLE_CORE compile-time option, check the |
| 20870 | ** number of cores. Different malloc() strategies are used for single-core and |
| 20871 | ** multi-core machines. |
| 20872 | */ |
| 20873 | { |
| 20874 | int cpuCount; |
| 20875 | size_t len; |
| 20876 | len = sizeof(cpuCount); |
| 20877 | /* One usually wants to use hw.acctivecpu for MT decisions, but not here */ |
| 20878 | sysctlbyname("hw.ncpu", &cpuCount, &len, NULL, 0); |
| 20879 | if( cpuCount>1 ){ |
| 20880 | /* defer MT decisions to system malloc */ |
| 20881 | _sqliteZone_ = malloc_default_zone(); |
| 20882 | }else{ |
| 20883 | /* only 1 core, use our own zone to contention over global locks, |
| 20884 | ** e.g. we have our own dedicated locks */ |
| 20885 | bool success; |
| 20886 | malloc_zone_t* newzone = malloc_create_zone(4096, 0); |
| 20887 | malloc_set_zone_name(newzone, "Sqlite_Heap"); |
| 20888 | do{ |
| 20889 | success = OSAtomicCompareAndSwapPtrBarrier(NULL, newzone, |
| 20890 | (void * volatile *)&_sqliteZone_); |
| 20891 | }while(!_sqliteZone_); |
| 20892 | if( !success ){ |
| 20893 | /* somebody registered a zone first */ |
| 20894 | malloc_destroy_zone(newzone); |
| 20895 | } |
| 20896 | } |
| 20897 | } |
| 20898 | #endif /* SQLITE_MIGHT_BE_SINGLE_CORE */ |
| 20899 | #endif /* defined(__APPLE__) && !defined(SQLITE_WITHOUT_ZONEMALLOC) */ |
| 20900 | UNUSED_PARAMETER(NotUsed); |
| 20901 | return SQLITE_OK; |
| 20902 | } |
| 20903 | |
| @@ -25445,16 +25423,17 @@ | |
| 25445 | } |
| 25446 | if( precision<etBUFSIZE-10-etBUFSIZE/3 ){ |
| 25447 | nOut = etBUFSIZE; |
| 25448 | zOut = buf; |
| 25449 | }else{ |
| 25450 | nOut = precision + 10 + precision/3; |
| 25451 | zOut = zExtra = sqlite3Malloc( nOut ); |
| 25452 | if( zOut==0 ){ |
| 25453 | setStrAccumError(pAccum, STRACCUM_NOMEM); |
| 25454 | return; |
| 25455 | } |
| 25456 | } |
| 25457 | bufpt = &zOut[nOut-1]; |
| 25458 | if( xtype==etORDINAL ){ |
| 25459 | static const char zOrd[] = "thstndrd"; |
| 25460 | int x = (int)(longvalue % 10); |
| @@ -85151,11 +85130,15 @@ | |
| 85151 | char *z = sqlite3VdbeExpandSql(p, zTrace); |
| 85152 | x(db->pTraceArg, z); |
| 85153 | sqlite3_free(z); |
| 85154 | }else |
| 85155 | #endif |
| 85156 | { |
| 85157 | (void)db->xTrace(SQLITE_TRACE_STMT, db->pTraceArg, p, zTrace); |
| 85158 | } |
| 85159 | } |
| 85160 | #ifdef SQLITE_USE_FCNTL_TRACE |
| 85161 | zTrace = (pOp->p4.z ? pOp->p4.z : p->zSql); |
| @@ -97881,11 +97864,11 @@ | |
| 97881 | Index *pPk = sqlite3PrimaryKeyIndex(pIdx->pTable); |
| 97882 | int j, k, regKey; |
| 97883 | regKey = sqlite3GetTempRange(pParse, pPk->nKeyCol); |
| 97884 | for(j=0; j<pPk->nKeyCol; j++){ |
| 97885 | k = sqlite3ColumnOfIndex(pIdx, pPk->aiColumn[j]); |
| 97886 | assert( k>=0 && k<pTab->nCol ); |
| 97887 | sqlite3VdbeAddOp3(v, OP_Column, iIdxCur, k, regKey+j); |
| 97888 | VdbeComment((v, "%s", pTab->aCol[pPk->aiColumn[j]].zName)); |
| 97889 | } |
| 97890 | sqlite3VdbeAddOp3(v, OP_MakeRecord, regKey, pPk->nKeyCol, regRowid); |
| 97891 | sqlite3ReleaseTempRange(pParse, regKey, pPk->nKeyCol); |
| @@ -110785,12 +110768,10 @@ | |
| 110785 | ** might change the definition of a collation sequence and then run |
| 110786 | ** a VACUUM command. In that case keys may not be written in strictly |
| 110787 | ** sorted order. */ |
| 110788 | for(i=0; i<pSrcIdx->nColumn; i++){ |
| 110789 | const char *zColl = pSrcIdx->azColl[i]; |
| 110790 | assert( sqlite3_stricmp(sqlite3StrBINARY, zColl)!=0 |
| 110791 | || sqlite3StrBINARY==zColl ); |
| 110792 | if( sqlite3_stricmp(sqlite3StrBINARY, zColl) ) break; |
| 110793 | } |
| 110794 | if( i==pSrcIdx->nColumn ){ |
| 110795 | idxInsFlags = OPFLAG_USESEEKRESULT; |
| 110796 | sqlite3VdbeAddOp3(v, OP_Last, iDest, 0, -1); |
| @@ -145575,12 +145556,13 @@ | |
| 145575 | /* |
| 145576 | ** Read a 64-bit variable-length integer from memory starting at p[0]. |
| 145577 | ** Return the number of bytes read, or 0 on error. |
| 145578 | ** The value is stored in *v. |
| 145579 | */ |
| 145580 | SQLITE_PRIVATE int sqlite3Fts3GetVarint(const char *p, sqlite_int64 *v){ |
| 145581 | const char *pStart = p; |
| 145582 | u32 a; |
| 145583 | u64 b; |
| 145584 | int shift; |
| 145585 | |
| 145586 | GETVARINT_INIT(a, p, 0, 0x00, 0x80, *v, 1); |
| @@ -146623,11 +146605,13 @@ | |
| 146623 | /* Fill in the azColumn array */ |
| 146624 | for(iCol=0; iCol<nCol; iCol++){ |
| 146625 | char *z; |
| 146626 | int n = 0; |
| 146627 | z = (char *)sqlite3Fts3NextToken(aCol[iCol], &n); |
| 146628 | memcpy(zCsr, z, n); |
| 146629 | zCsr[n] = '\0'; |
| 146630 | sqlite3Fts3Dequote(zCsr); |
| 146631 | p->azColumn[iCol] = zCsr; |
| 146632 | zCsr += n+1; |
| 146633 | assert( zCsr <= &((char *)p)[nByte] ); |
| @@ -160263,15 +160247,18 @@ | |
| 160263 | |
| 160264 | /* |
| 160265 | ** Convert the text beginning at *pz into an integer and return |
| 160266 | ** its value. Advance *pz to point to the first character past |
| 160267 | ** the integer. |
| 160268 | */ |
| 160269 | static int fts3Getint(const char **pz){ |
| 160270 | const char *z = *pz; |
| 160271 | int i = 0; |
| 160272 | while( (*z)>='0' && (*z)<='9' ) i = 10*i + *(z++) - '0'; |
| 160273 | *pz = z; |
| 160274 | return i; |
| 160275 | } |
| 160276 | |
| 160277 | /* |
| @@ -162833,20 +162820,20 @@ | |
| 162833 | const char *zIn, /* Array of characters to make exceptions */ |
| 162834 | int nIn /* Length of z in bytes */ |
| 162835 | ){ |
| 162836 | const unsigned char *z = (const unsigned char *)zIn; |
| 162837 | const unsigned char *zTerm = &z[nIn]; |
| 162838 | int iCode; |
| 162839 | int nEntry = 0; |
| 162840 | |
| 162841 | assert( bAlnum==0 || bAlnum==1 ); |
| 162842 | |
| 162843 | while( z<zTerm ){ |
| 162844 | READ_UTF8(z, zTerm, iCode); |
| 162845 | assert( (sqlite3FtsUnicodeIsalnum(iCode) & 0xFFFFFFFE)==0 ); |
| 162846 | if( sqlite3FtsUnicodeIsalnum(iCode)!=bAlnum |
| 162847 | && sqlite3FtsUnicodeIsdiacritic(iCode)==0 |
| 162848 | ){ |
| 162849 | nEntry++; |
| 162850 | } |
| 162851 | } |
| 162852 | |
| @@ -162859,17 +162846,17 @@ | |
| 162859 | nNew = p->nException; |
| 162860 | |
| 162861 | z = (const unsigned char *)zIn; |
| 162862 | while( z<zTerm ){ |
| 162863 | READ_UTF8(z, zTerm, iCode); |
| 162864 | if( sqlite3FtsUnicodeIsalnum(iCode)!=bAlnum |
| 162865 | && sqlite3FtsUnicodeIsdiacritic(iCode)==0 |
| 162866 | ){ |
| 162867 | int i, j; |
| 162868 | for(i=0; i<nNew && aNew[i]<iCode; i++); |
| 162869 | for(j=nNew; j>i; j--) aNew[j] = aNew[j-1]; |
| 162870 | aNew[i] = iCode; |
| 162871 | nNew++; |
| 162872 | } |
| 162873 | } |
| 162874 | p->aiException = aNew; |
| 162875 | p->nException = nNew; |
| @@ -163015,11 +163002,11 @@ | |
| 163015 | int *piEnd, /* OUT: Ending offset of token */ |
| 163016 | int *piPos /* OUT: Position integer of token */ |
| 163017 | ){ |
| 163018 | unicode_cursor *pCsr = (unicode_cursor *)pC; |
| 163019 | unicode_tokenizer *p = ((unicode_tokenizer *)pCsr->base.pTokenizer); |
| 163020 | int iCode = 0; |
| 163021 | char *zOut; |
| 163022 | const unsigned char *z = &pCsr->aInput[pCsr->iOff]; |
| 163023 | const unsigned char *zStart = z; |
| 163024 | const unsigned char *zEnd; |
| 163025 | const unsigned char *zTerm = &pCsr->aInput[pCsr->nInput]; |
| @@ -163027,11 +163014,11 @@ | |
| 163027 | /* Scan past any delimiter characters before the start of the next token. |
| 163028 | ** Return SQLITE_DONE early if this takes us all the way to the end of |
| 163029 | ** the input. */ |
| 163030 | while( z<zTerm ){ |
| 163031 | READ_UTF8(z, zTerm, iCode); |
| 163032 | if( unicodeIsAlnum(p, iCode) ) break; |
| 163033 | zStart = z; |
| 163034 | } |
| 163035 | if( zStart>=zTerm ) return SQLITE_DONE; |
| 163036 | |
| 163037 | zOut = pCsr->zToken; |
| @@ -163047,20 +163034,20 @@ | |
| 163047 | pCsr->nAlloc += 64; |
| 163048 | } |
| 163049 | |
| 163050 | /* Write the folded case of the last character read to the output */ |
| 163051 | zEnd = z; |
| 163052 | iOut = sqlite3FtsUnicodeFold(iCode, p->bRemoveDiacritic); |
| 163053 | if( iOut ){ |
| 163054 | WRITE_UTF8(zOut, iOut); |
| 163055 | } |
| 163056 | |
| 163057 | /* If the cursor is not at EOF, read the next character */ |
| 163058 | if( z>=zTerm ) break; |
| 163059 | READ_UTF8(z, zTerm, iCode); |
| 163060 | }while( unicodeIsAlnum(p, iCode) |
| 163061 | || sqlite3FtsUnicodeIsdiacritic(iCode) |
| 163062 | ); |
| 163063 | |
| 163064 | /* Set the output variables and return. */ |
| 163065 | pCsr->iOff = (int)(z - pCsr->aInput); |
| 163066 | *paToken = pCsr->zToken; |
| @@ -163220,13 +163207,13 @@ | |
| 163220 | }; |
| 163221 | static const unsigned int aAscii[4] = { |
| 163222 | 0xFFFFFFFF, 0xFC00FFFF, 0xF8000001, 0xF8000001, |
| 163223 | }; |
| 163224 | |
| 163225 | if( c<128 ){ |
| 163226 | return ( (aAscii[c >> 5] & (1 << (c & 0x001F)))==0 ); |
| 163227 | }else if( c<(1<<22) ){ |
| 163228 | unsigned int key = (((unsigned int)c)<<10) | 0x000003FF; |
| 163229 | int iRes = 0; |
| 163230 | int iHi = sizeof(aEntry)/sizeof(aEntry[0]) - 1; |
| 163231 | int iLo = 0; |
| 163232 | while( iHi>=iLo ){ |
| @@ -163415,20 +163402,21 @@ | |
| 163415 | 65514, 65521, 65527, 65528, 65529, |
| 163416 | }; |
| 163417 | |
| 163418 | int ret = c; |
| 163419 | |
| 163420 | assert( c>=0 ); |
| 163421 | assert( sizeof(unsigned short)==2 && sizeof(unsigned char)==1 ); |
| 163422 | |
| 163423 | if( c<128 ){ |
| 163424 | if( c>='A' && c<='Z' ) ret = c + ('a' - 'A'); |
| 163425 | }else if( c<65536 ){ |
| 163426 | int iHi = sizeof(aEntry)/sizeof(aEntry[0]) - 1; |
| 163427 | int iLo = 0; |
| 163428 | int iRes = -1; |
| 163429 | |
| 163430 | while( iHi>=iLo ){ |
| 163431 | int iTest = (iHi + iLo) / 2; |
| 163432 | int cmp = (c - aEntry[iTest].iCode); |
| 163433 | if( cmp>=0 ){ |
| 163434 | iRes = iTest; |
| @@ -163435,18 +163423,16 @@ | |
| 163435 | iLo = iTest+1; |
| 163436 | }else{ |
| 163437 | iHi = iTest-1; |
| 163438 | } |
| 163439 | } |
| 163440 | assert( iRes<0 || c>=aEntry[iRes].iCode ); |
| 163441 | |
| 163442 | if( iRes>=0 ){ |
| 163443 | const struct TableEntry *p = &aEntry[iRes]; |
| 163444 | if( c<(p->iCode + p->nRange) && 0==(0x01 & p->flags & (p->iCode ^ c)) ){ |
| 163445 | ret = (c + (aiOff[p->flags>>1])) & 0x0000FFFF; |
| 163446 | assert( ret>0 ); |
| 163447 | } |
| 163448 | } |
| 163449 | |
| 163450 | if( bRemoveDiacritic ) ret = remove_diacritic(ret); |
| 163451 | } |
| 163452 | |
| @@ -163919,19 +163905,19 @@ | |
| 163919 | #elif SQLITE_BYTEORDER==4321 |
| 163920 | i64 x; |
| 163921 | memcpy(&x, p, 8); |
| 163922 | return x; |
| 163923 | #else |
| 163924 | return ( |
| 163925 | (((i64)p[0]) << 56) + |
| 163926 | (((i64)p[1]) << 48) + |
| 163927 | (((i64)p[2]) << 40) + |
| 163928 | (((i64)p[3]) << 32) + |
| 163929 | (((i64)p[4]) << 24) + |
| 163930 | (((i64)p[5]) << 16) + |
| 163931 | (((i64)p[6]) << 8) + |
| 163932 | (((i64)p[7]) << 0) |
| 163933 | ); |
| 163934 | #endif |
| 163935 | } |
| 163936 | |
| 163937 | /* |
| @@ -178936,26 +178922,28 @@ | |
| 178936 | /* Bit values for the JsonNode.jnFlag field |
| 178937 | */ |
| 178938 | #define JNODE_RAW 0x01 /* Content is raw, not JSON encoded */ |
| 178939 | #define JNODE_ESCAPE 0x02 /* Content is text with \ escapes */ |
| 178940 | #define JNODE_REMOVE 0x04 /* Do not output */ |
| 178941 | #define JNODE_REPLACE 0x08 /* Replace with JsonNode.iVal */ |
| 178942 | #define JNODE_APPEND 0x10 /* More ARRAY/OBJECT entries at u.iAppend */ |
| 178943 | #define JNODE_LABEL 0x20 /* Is a label of an object */ |
| 178944 | |
| 178945 | |
| 178946 | /* A single node of parsed JSON |
| 178947 | */ |
| 178948 | struct JsonNode { |
| 178949 | u8 eType; /* One of the JSON_ type values */ |
| 178950 | u8 jnFlags; /* JNODE flags */ |
| 178951 | u8 iVal; /* Replacement value when JNODE_REPLACE */ |
| 178952 | u32 n; /* Bytes of content, or number of sub-nodes */ |
| 178953 | union { |
| 178954 | const char *zJContent; /* Content for INT, REAL, and STRING */ |
| 178955 | u32 iAppend; /* More terms for ARRAY and OBJECT */ |
| 178956 | u32 iKey; /* Key for ARRAY objects in json_tree() */ |
| 178957 | } u; |
| 178958 | }; |
| 178959 | |
| 178960 | /* A completely parsed JSON string |
| 178961 | */ |
| @@ -179208,10 +179196,17 @@ | |
| 179208 | static void jsonRenderNode( |
| 179209 | JsonNode *pNode, /* The node to render */ |
| 179210 | JsonString *pOut, /* Write JSON here */ |
| 179211 | sqlite3_value **aReplace /* Replacement values */ |
| 179212 | ){ |
| 179213 | switch( pNode->eType ){ |
| 179214 | default: { |
| 179215 | assert( pNode->eType==JSON_NULL ); |
| 179216 | jsonAppendRaw(pOut, "null", 4); |
| 179217 | break; |
| @@ -179239,16 +179234,11 @@ | |
| 179239 | case JSON_ARRAY: { |
| 179240 | u32 j = 1; |
| 179241 | jsonAppendChar(pOut, '['); |
| 179242 | for(;;){ |
| 179243 | while( j<=pNode->n ){ |
| 179244 | if( pNode[j].jnFlags & (JNODE_REMOVE|JNODE_REPLACE) ){ |
| 179245 | if( pNode[j].jnFlags & JNODE_REPLACE ){ |
| 179246 | jsonAppendSeparator(pOut); |
| 179247 | jsonAppendValue(pOut, aReplace[pNode[j].iVal]); |
| 179248 | } |
| 179249 | }else{ |
| 179250 | jsonAppendSeparator(pOut); |
| 179251 | jsonRenderNode(&pNode[j], pOut, aReplace); |
| 179252 | } |
| 179253 | j += jsonNodeSize(&pNode[j]); |
| 179254 | } |
| @@ -179266,15 +179256,11 @@ | |
| 179266 | while( j<=pNode->n ){ |
| 179267 | if( (pNode[j+1].jnFlags & JNODE_REMOVE)==0 ){ |
| 179268 | jsonAppendSeparator(pOut); |
| 179269 | jsonRenderNode(&pNode[j], pOut, aReplace); |
| 179270 | jsonAppendChar(pOut, ':'); |
| 179271 | if( pNode[j+1].jnFlags & JNODE_REPLACE ){ |
| 179272 | jsonAppendValue(pOut, aReplace[pNode[j+1].iVal]); |
| 179273 | }else{ |
| 179274 | jsonRenderNode(&pNode[j+1], pOut, aReplace); |
| 179275 | } |
| 179276 | } |
| 179277 | j += 1 + jsonNodeSize(&pNode[j+1]); |
| 179278 | } |
| 179279 | if( (pNode->jnFlags & JNODE_APPEND)==0 ) break; |
| 179280 | pNode = &pNode[pNode->u.iAppend]; |
| @@ -179497,11 +179483,10 @@ | |
| 179497 | return jsonParseAddNodeExpand(pParse, eType, n, zContent); |
| 179498 | } |
| 179499 | p = &pParse->aNode[pParse->nNode]; |
| 179500 | p->eType = (u8)eType; |
| 179501 | p->jnFlags = 0; |
| 179502 | p->iVal = 0; |
| 179503 | p->n = n; |
| 179504 | p->u.zJContent = zContent; |
| 179505 | return pParse->nNode++; |
| 179506 | } |
| 179507 | |
| @@ -180154,10 +180139,111 @@ | |
| 180154 | sqlite3_result_subtype(ctx, JSON_SUBTYPE); |
| 180155 | } |
| 180156 | jsonReset(&jx); |
| 180157 | jsonParseReset(&x); |
| 180158 | } |
| 180159 | |
| 180160 | /* |
| 180161 | ** Implementation of the json_object(NAME,VALUE,...) function. Return a JSON |
| 180162 | ** object that contains all name/value given in arguments. Or if any name |
| 180163 | ** is not a string or if any value is a BLOB, throw an error. |
| @@ -180258,15 +180344,15 @@ | |
| 180258 | zPath = (const char*)sqlite3_value_text(argv[i]); |
| 180259 | pNode = jsonLookup(&x, zPath, 0, ctx); |
| 180260 | if( x.nErr ) goto replace_err; |
| 180261 | if( pNode ){ |
| 180262 | pNode->jnFlags |= (u8)JNODE_REPLACE; |
| 180263 | pNode->iVal = (u8)(i+1); |
| 180264 | } |
| 180265 | } |
| 180266 | if( x.aNode[0].jnFlags & JNODE_REPLACE ){ |
| 180267 | sqlite3_result_value(ctx, argv[x.aNode[0].iVal]); |
| 180268 | }else{ |
| 180269 | jsonReturnJson(x.aNode, ctx, argv); |
| 180270 | } |
| 180271 | replace_err: |
| 180272 | jsonParseReset(&x); |
| @@ -180312,15 +180398,15 @@ | |
| 180312 | goto jsonSetDone; |
| 180313 | }else if( x.nErr ){ |
| 180314 | goto jsonSetDone; |
| 180315 | }else if( pNode && (bApnd || bIsSet) ){ |
| 180316 | pNode->jnFlags |= (u8)JNODE_REPLACE; |
| 180317 | pNode->iVal = (u8)(i+1); |
| 180318 | } |
| 180319 | } |
| 180320 | if( x.aNode[0].jnFlags & JNODE_REPLACE ){ |
| 180321 | sqlite3_result_value(ctx, argv[x.aNode[0].iVal]); |
| 180322 | }else{ |
| 180323 | jsonReturnJson(x.aNode, ctx, argv); |
| 180324 | } |
| 180325 | jsonSetDone: |
| 180326 | jsonParseReset(&x); |
| @@ -180959,10 +181045,11 @@ | |
| 180959 | { "json_array_length", 1, 0, jsonArrayLengthFunc }, |
| 180960 | { "json_array_length", 2, 0, jsonArrayLengthFunc }, |
| 180961 | { "json_extract", -1, 0, jsonExtractFunc }, |
| 180962 | { "json_insert", -1, 0, jsonSetFunc }, |
| 180963 | { "json_object", -1, 0, jsonObjectFunc }, |
| 180964 | { "json_quote", 1, 0, jsonQuoteFunc }, |
| 180965 | { "json_remove", -1, 0, jsonRemoveFunc }, |
| 180966 | { "json_replace", -1, 0, jsonReplaceFunc }, |
| 180967 | { "json_set", -1, 1, jsonSetFunc }, |
| 180968 | { "json_type", 1, 0, jsonTypeFunc }, |
| @@ -198120,11 +198207,11 @@ | |
| 198120 | int nArg, /* Number of args */ |
| 198121 | sqlite3_value **apUnused /* Function arguments */ |
| 198122 | ){ |
| 198123 | assert( nArg==0 ); |
| 198124 | UNUSED_PARAM2(nArg, apUnused); |
| 198125 | sqlite3_result_text(pCtx, "fts5: 2017-03-18 13:59:46 4e6a03d9e12b120d15946b025f97a97697cb8e8af543c238ffda220c9e3f28f4", -1, SQLITE_TRANSIENT); |
| 198126 | } |
| 198127 | |
| 198128 | static int fts5Init(sqlite3 *db){ |
| 198129 | static const sqlite3_module fts5Mod = { |
| 198130 | /* iVersion */ 2, |
| 198131 |
| --- src/sqlite3.c | |
| +++ src/sqlite3.c | |
| @@ -398,11 +398,11 @@ | |
| 398 | ** [sqlite3_libversion_number()], [sqlite3_sourceid()], |
| 399 | ** [sqlite_version()] and [sqlite_source_id()]. |
| 400 | */ |
| 401 | #define SQLITE_VERSION "3.18.0" |
| 402 | #define SQLITE_VERSION_NUMBER 3018000 |
| 403 | #define SQLITE_SOURCE_ID "2017-03-23 23:44:55 476088482024e411e2549b1697cdaf0124294c79d43f508c71c4eb66906a56fc" |
| 404 | |
| 405 | /* |
| 406 | ** CAPI3REF: Run-Time Library Version Numbers |
| 407 | ** KEYWORDS: sqlite3_version sqlite3_sourceid |
| 408 | ** |
| @@ -20855,49 +20855,27 @@ | |
| 20855 | /* |
| 20856 | ** Initialize this module. |
| 20857 | */ |
| 20858 | static int sqlite3MemInit(void *NotUsed){ |
| 20859 | #if defined(__APPLE__) && !defined(SQLITE_WITHOUT_ZONEMALLOC) |
| 20860 | int cpuCount; |
| 20861 | size_t len; |
| 20862 | if( _sqliteZone_ ){ |
| 20863 | return SQLITE_OK; |
| 20864 | } |
| 20865 | len = sizeof(cpuCount); |
| 20866 | /* One usually wants to use hw.acctivecpu for MT decisions, but not here */ |
| 20867 | sysctlbyname("hw.ncpu", &cpuCount, &len, NULL, 0); |
| 20868 | if( cpuCount>1 ){ |
| 20869 | /* defer MT decisions to system malloc */ |
| 20870 | _sqliteZone_ = malloc_default_zone(); |
| 20871 | }else{ |
| 20872 | /* only 1 core, use our own zone to contention over global locks, |
| 20873 | ** e.g. we have our own dedicated locks */ |
| 20874 | _sqliteZone_ = malloc_create_zone(4096, 0); |
| 20875 | malloc_set_zone_name(_sqliteZone_, "Sqlite_Heap"); |
| 20876 | } |
| 20877 | #endif /* defined(__APPLE__) && !defined(SQLITE_WITHOUT_ZONEMALLOC) */ |
| 20878 | UNUSED_PARAMETER(NotUsed); |
| 20879 | return SQLITE_OK; |
| 20880 | } |
| 20881 | |
| @@ -25445,16 +25423,17 @@ | |
| 25423 | } |
| 25424 | if( precision<etBUFSIZE-10-etBUFSIZE/3 ){ |
| 25425 | nOut = etBUFSIZE; |
| 25426 | zOut = buf; |
| 25427 | }else{ |
| 25428 | u64 n = (u64)precision + 10 + precision/3; |
| 25429 | zOut = zExtra = sqlite3Malloc( n ); |
| 25430 | if( zOut==0 ){ |
| 25431 | setStrAccumError(pAccum, STRACCUM_NOMEM); |
| 25432 | return; |
| 25433 | } |
| 25434 | nOut = (int)n; |
| 25435 | } |
| 25436 | bufpt = &zOut[nOut-1]; |
| 25437 | if( xtype==etORDINAL ){ |
| 25438 | static const char zOrd[] = "thstndrd"; |
| 25439 | int x = (int)(longvalue % 10); |
| @@ -85151,11 +85130,15 @@ | |
| 85130 | char *z = sqlite3VdbeExpandSql(p, zTrace); |
| 85131 | x(db->pTraceArg, z); |
| 85132 | sqlite3_free(z); |
| 85133 | }else |
| 85134 | #endif |
| 85135 | if( db->nVdbeExec>1 ){ |
| 85136 | char *z = sqlite3MPrintf(db, "-- %s", zTrace); |
| 85137 | (void)db->xTrace(SQLITE_TRACE_STMT, db->pTraceArg, p, z); |
| 85138 | sqlite3DbFree(db, z); |
| 85139 | }else{ |
| 85140 | (void)db->xTrace(SQLITE_TRACE_STMT, db->pTraceArg, p, zTrace); |
| 85141 | } |
| 85142 | } |
| 85143 | #ifdef SQLITE_USE_FCNTL_TRACE |
| 85144 | zTrace = (pOp->p4.z ? pOp->p4.z : p->zSql); |
| @@ -97881,11 +97864,11 @@ | |
| 97864 | Index *pPk = sqlite3PrimaryKeyIndex(pIdx->pTable); |
| 97865 | int j, k, regKey; |
| 97866 | regKey = sqlite3GetTempRange(pParse, pPk->nKeyCol); |
| 97867 | for(j=0; j<pPk->nKeyCol; j++){ |
| 97868 | k = sqlite3ColumnOfIndex(pIdx, pPk->aiColumn[j]); |
| 97869 | assert( k>=0 && k<pIdx->nColumn ); |
| 97870 | sqlite3VdbeAddOp3(v, OP_Column, iIdxCur, k, regKey+j); |
| 97871 | VdbeComment((v, "%s", pTab->aCol[pPk->aiColumn[j]].zName)); |
| 97872 | } |
| 97873 | sqlite3VdbeAddOp3(v, OP_MakeRecord, regKey, pPk->nKeyCol, regRowid); |
| 97874 | sqlite3ReleaseTempRange(pParse, regKey, pPk->nKeyCol); |
| @@ -110785,12 +110768,10 @@ | |
| 110768 | ** might change the definition of a collation sequence and then run |
| 110769 | ** a VACUUM command. In that case keys may not be written in strictly |
| 110770 | ** sorted order. */ |
| 110771 | for(i=0; i<pSrcIdx->nColumn; i++){ |
| 110772 | const char *zColl = pSrcIdx->azColl[i]; |
| 110773 | if( sqlite3_stricmp(sqlite3StrBINARY, zColl) ) break; |
| 110774 | } |
| 110775 | if( i==pSrcIdx->nColumn ){ |
| 110776 | idxInsFlags = OPFLAG_USESEEKRESULT; |
| 110777 | sqlite3VdbeAddOp3(v, OP_Last, iDest, 0, -1); |
| @@ -145575,12 +145556,13 @@ | |
| 145556 | /* |
| 145557 | ** Read a 64-bit variable-length integer from memory starting at p[0]. |
| 145558 | ** Return the number of bytes read, or 0 on error. |
| 145559 | ** The value is stored in *v. |
| 145560 | */ |
| 145561 | SQLITE_PRIVATE int sqlite3Fts3GetVarint(const char *pBuf, sqlite_int64 *v){ |
| 145562 | const unsigned char *p = (const unsigned char*)pBuf; |
| 145563 | const unsigned char *pStart = p; |
| 145564 | u32 a; |
| 145565 | u64 b; |
| 145566 | int shift; |
| 145567 | |
| 145568 | GETVARINT_INIT(a, p, 0, 0x00, 0x80, *v, 1); |
| @@ -146623,11 +146605,13 @@ | |
| 146605 | /* Fill in the azColumn array */ |
| 146606 | for(iCol=0; iCol<nCol; iCol++){ |
| 146607 | char *z; |
| 146608 | int n = 0; |
| 146609 | z = (char *)sqlite3Fts3NextToken(aCol[iCol], &n); |
| 146610 | if( n>0 ){ |
| 146611 | memcpy(zCsr, z, n); |
| 146612 | } |
| 146613 | zCsr[n] = '\0'; |
| 146614 | sqlite3Fts3Dequote(zCsr); |
| 146615 | p->azColumn[iCol] = zCsr; |
| 146616 | zCsr += n+1; |
| 146617 | assert( zCsr <= &((char *)p)[nByte] ); |
| @@ -160263,15 +160247,18 @@ | |
| 160247 | |
| 160248 | /* |
| 160249 | ** Convert the text beginning at *pz into an integer and return |
| 160250 | ** its value. Advance *pz to point to the first character past |
| 160251 | ** the integer. |
| 160252 | ** |
| 160253 | ** This function used for parameters to merge= and incrmerge= |
| 160254 | ** commands. |
| 160255 | */ |
| 160256 | static int fts3Getint(const char **pz){ |
| 160257 | const char *z = *pz; |
| 160258 | int i = 0; |
| 160259 | while( (*z)>='0' && (*z)<='9' && i<214748363 ) i = 10*i + *(z++) - '0'; |
| 160260 | *pz = z; |
| 160261 | return i; |
| 160262 | } |
| 160263 | |
| 160264 | /* |
| @@ -162833,20 +162820,20 @@ | |
| 162820 | const char *zIn, /* Array of characters to make exceptions */ |
| 162821 | int nIn /* Length of z in bytes */ |
| 162822 | ){ |
| 162823 | const unsigned char *z = (const unsigned char *)zIn; |
| 162824 | const unsigned char *zTerm = &z[nIn]; |
| 162825 | unsigned int iCode; |
| 162826 | int nEntry = 0; |
| 162827 | |
| 162828 | assert( bAlnum==0 || bAlnum==1 ); |
| 162829 | |
| 162830 | while( z<zTerm ){ |
| 162831 | READ_UTF8(z, zTerm, iCode); |
| 162832 | assert( (sqlite3FtsUnicodeIsalnum((int)iCode) & 0xFFFFFFFE)==0 ); |
| 162833 | if( sqlite3FtsUnicodeIsalnum((int)iCode)!=bAlnum |
| 162834 | && sqlite3FtsUnicodeIsdiacritic((int)iCode)==0 |
| 162835 | ){ |
| 162836 | nEntry++; |
| 162837 | } |
| 162838 | } |
| 162839 | |
| @@ -162859,17 +162846,17 @@ | |
| 162846 | nNew = p->nException; |
| 162847 | |
| 162848 | z = (const unsigned char *)zIn; |
| 162849 | while( z<zTerm ){ |
| 162850 | READ_UTF8(z, zTerm, iCode); |
| 162851 | if( sqlite3FtsUnicodeIsalnum((int)iCode)!=bAlnum |
| 162852 | && sqlite3FtsUnicodeIsdiacritic((int)iCode)==0 |
| 162853 | ){ |
| 162854 | int i, j; |
| 162855 | for(i=0; i<nNew && aNew[i]<(int)iCode; i++); |
| 162856 | for(j=nNew; j>i; j--) aNew[j] = aNew[j-1]; |
| 162857 | aNew[i] = (int)iCode; |
| 162858 | nNew++; |
| 162859 | } |
| 162860 | } |
| 162861 | p->aiException = aNew; |
| 162862 | p->nException = nNew; |
| @@ -163015,11 +163002,11 @@ | |
| 163002 | int *piEnd, /* OUT: Ending offset of token */ |
| 163003 | int *piPos /* OUT: Position integer of token */ |
| 163004 | ){ |
| 163005 | unicode_cursor *pCsr = (unicode_cursor *)pC; |
| 163006 | unicode_tokenizer *p = ((unicode_tokenizer *)pCsr->base.pTokenizer); |
| 163007 | unsigned int iCode = 0; |
| 163008 | char *zOut; |
| 163009 | const unsigned char *z = &pCsr->aInput[pCsr->iOff]; |
| 163010 | const unsigned char *zStart = z; |
| 163011 | const unsigned char *zEnd; |
| 163012 | const unsigned char *zTerm = &pCsr->aInput[pCsr->nInput]; |
| @@ -163027,11 +163014,11 @@ | |
| 163014 | /* Scan past any delimiter characters before the start of the next token. |
| 163015 | ** Return SQLITE_DONE early if this takes us all the way to the end of |
| 163016 | ** the input. */ |
| 163017 | while( z<zTerm ){ |
| 163018 | READ_UTF8(z, zTerm, iCode); |
| 163019 | if( unicodeIsAlnum(p, (int)iCode) ) break; |
| 163020 | zStart = z; |
| 163021 | } |
| 163022 | if( zStart>=zTerm ) return SQLITE_DONE; |
| 163023 | |
| 163024 | zOut = pCsr->zToken; |
| @@ -163047,20 +163034,20 @@ | |
| 163034 | pCsr->nAlloc += 64; |
| 163035 | } |
| 163036 | |
| 163037 | /* Write the folded case of the last character read to the output */ |
| 163038 | zEnd = z; |
| 163039 | iOut = sqlite3FtsUnicodeFold((int)iCode, p->bRemoveDiacritic); |
| 163040 | if( iOut ){ |
| 163041 | WRITE_UTF8(zOut, iOut); |
| 163042 | } |
| 163043 | |
| 163044 | /* If the cursor is not at EOF, read the next character */ |
| 163045 | if( z>=zTerm ) break; |
| 163046 | READ_UTF8(z, zTerm, iCode); |
| 163047 | }while( unicodeIsAlnum(p, (int)iCode) |
| 163048 | || sqlite3FtsUnicodeIsdiacritic((int)iCode) |
| 163049 | ); |
| 163050 | |
| 163051 | /* Set the output variables and return. */ |
| 163052 | pCsr->iOff = (int)(z - pCsr->aInput); |
| 163053 | *paToken = pCsr->zToken; |
| @@ -163220,13 +163207,13 @@ | |
| 163207 | }; |
| 163208 | static const unsigned int aAscii[4] = { |
| 163209 | 0xFFFFFFFF, 0xFC00FFFF, 0xF8000001, 0xF8000001, |
| 163210 | }; |
| 163211 | |
| 163212 | if( (unsigned int)c<128 ){ |
| 163213 | return ( (aAscii[c >> 5] & ((unsigned int)1 << (c & 0x001F)))==0 ); |
| 163214 | }else if( (unsigned int)c<(1<<22) ){ |
| 163215 | unsigned int key = (((unsigned int)c)<<10) | 0x000003FF; |
| 163216 | int iRes = 0; |
| 163217 | int iHi = sizeof(aEntry)/sizeof(aEntry[0]) - 1; |
| 163218 | int iLo = 0; |
| 163219 | while( iHi>=iLo ){ |
| @@ -163415,20 +163402,21 @@ | |
| 163402 | 65514, 65521, 65527, 65528, 65529, |
| 163403 | }; |
| 163404 | |
| 163405 | int ret = c; |
| 163406 | |
| 163407 | assert( sizeof(unsigned short)==2 && sizeof(unsigned char)==1 ); |
| 163408 | |
| 163409 | if( c<128 ){ |
| 163410 | if( c>='A' && c<='Z' ) ret = c + ('a' - 'A'); |
| 163411 | }else if( c<65536 ){ |
| 163412 | const struct TableEntry *p; |
| 163413 | int iHi = sizeof(aEntry)/sizeof(aEntry[0]) - 1; |
| 163414 | int iLo = 0; |
| 163415 | int iRes = -1; |
| 163416 | |
| 163417 | assert( c>aEntry[0].iCode ); |
| 163418 | while( iHi>=iLo ){ |
| 163419 | int iTest = (iHi + iLo) / 2; |
| 163420 | int cmp = (c - aEntry[iTest].iCode); |
| 163421 | if( cmp>=0 ){ |
| 163422 | iRes = iTest; |
| @@ -163435,18 +163423,16 @@ | |
| 163423 | iLo = iTest+1; |
| 163424 | }else{ |
| 163425 | iHi = iTest-1; |
| 163426 | } |
| 163427 | } |
| 163428 | |
| 163429 | assert( iRes>=0 && c>=aEntry[iRes].iCode ); |
| 163430 | p = &aEntry[iRes]; |
| 163431 | if( c<(p->iCode + p->nRange) && 0==(0x01 & p->flags & (p->iCode ^ c)) ){ |
| 163432 | ret = (c + (aiOff[p->flags>>1])) & 0x0000FFFF; |
| 163433 | assert( ret>0 ); |
| 163434 | } |
| 163435 | |
| 163436 | if( bRemoveDiacritic ) ret = remove_diacritic(ret); |
| 163437 | } |
| 163438 | |
| @@ -163919,19 +163905,19 @@ | |
| 163905 | #elif SQLITE_BYTEORDER==4321 |
| 163906 | i64 x; |
| 163907 | memcpy(&x, p, 8); |
| 163908 | return x; |
| 163909 | #else |
| 163910 | return (i64)( |
| 163911 | (((u64)p[0]) << 56) + |
| 163912 | (((u64)p[1]) << 48) + |
| 163913 | (((u64)p[2]) << 40) + |
| 163914 | (((u64)p[3]) << 32) + |
| 163915 | (((u64)p[4]) << 24) + |
| 163916 | (((u64)p[5]) << 16) + |
| 163917 | (((u64)p[6]) << 8) + |
| 163918 | (((u64)p[7]) << 0) |
| 163919 | ); |
| 163920 | #endif |
| 163921 | } |
| 163922 | |
| 163923 | /* |
| @@ -178936,26 +178922,28 @@ | |
| 178922 | /* Bit values for the JsonNode.jnFlag field |
| 178923 | */ |
| 178924 | #define JNODE_RAW 0x01 /* Content is raw, not JSON encoded */ |
| 178925 | #define JNODE_ESCAPE 0x02 /* Content is text with \ escapes */ |
| 178926 | #define JNODE_REMOVE 0x04 /* Do not output */ |
| 178927 | #define JNODE_REPLACE 0x08 /* Replace with JsonNode.u.iReplace */ |
| 178928 | #define JNODE_PATCH 0x10 /* Patch with JsonNode.u.pPatch */ |
| 178929 | #define JNODE_APPEND 0x20 /* More ARRAY/OBJECT entries at u.iAppend */ |
| 178930 | #define JNODE_LABEL 0x40 /* Is a label of an object */ |
| 178931 | |
| 178932 | |
| 178933 | /* A single node of parsed JSON |
| 178934 | */ |
| 178935 | struct JsonNode { |
| 178936 | u8 eType; /* One of the JSON_ type values */ |
| 178937 | u8 jnFlags; /* JNODE flags */ |
| 178938 | u32 n; /* Bytes of content, or number of sub-nodes */ |
| 178939 | union { |
| 178940 | const char *zJContent; /* Content for INT, REAL, and STRING */ |
| 178941 | u32 iAppend; /* More terms for ARRAY and OBJECT */ |
| 178942 | u32 iKey; /* Key for ARRAY objects in json_tree() */ |
| 178943 | u32 iReplace; /* Replacement content for JNODE_REPLACE */ |
| 178944 | JsonNode *pPatch; /* Node chain of patch for JNODE_PATCH */ |
| 178945 | } u; |
| 178946 | }; |
| 178947 | |
| 178948 | /* A completely parsed JSON string |
| 178949 | */ |
| @@ -179208,10 +179196,17 @@ | |
| 179196 | static void jsonRenderNode( |
| 179197 | JsonNode *pNode, /* The node to render */ |
| 179198 | JsonString *pOut, /* Write JSON here */ |
| 179199 | sqlite3_value **aReplace /* Replacement values */ |
| 179200 | ){ |
| 179201 | if( pNode->jnFlags & (JNODE_REPLACE|JNODE_PATCH) ){ |
| 179202 | if( pNode->jnFlags & JNODE_REPLACE ){ |
| 179203 | jsonAppendValue(pOut, aReplace[pNode->u.iReplace]); |
| 179204 | return; |
| 179205 | } |
| 179206 | pNode = pNode->u.pPatch; |
| 179207 | } |
| 179208 | switch( pNode->eType ){ |
| 179209 | default: { |
| 179210 | assert( pNode->eType==JSON_NULL ); |
| 179211 | jsonAppendRaw(pOut, "null", 4); |
| 179212 | break; |
| @@ -179239,16 +179234,11 @@ | |
| 179234 | case JSON_ARRAY: { |
| 179235 | u32 j = 1; |
| 179236 | jsonAppendChar(pOut, '['); |
| 179237 | for(;;){ |
| 179238 | while( j<=pNode->n ){ |
| 179239 | if( (pNode[j].jnFlags & JNODE_REMOVE)==0 ){ |
| 179240 | jsonAppendSeparator(pOut); |
| 179241 | jsonRenderNode(&pNode[j], pOut, aReplace); |
| 179242 | } |
| 179243 | j += jsonNodeSize(&pNode[j]); |
| 179244 | } |
| @@ -179266,15 +179256,11 @@ | |
| 179256 | while( j<=pNode->n ){ |
| 179257 | if( (pNode[j+1].jnFlags & JNODE_REMOVE)==0 ){ |
| 179258 | jsonAppendSeparator(pOut); |
| 179259 | jsonRenderNode(&pNode[j], pOut, aReplace); |
| 179260 | jsonAppendChar(pOut, ':'); |
| 179261 | jsonRenderNode(&pNode[j+1], pOut, aReplace); |
| 179262 | } |
| 179263 | j += 1 + jsonNodeSize(&pNode[j+1]); |
| 179264 | } |
| 179265 | if( (pNode->jnFlags & JNODE_APPEND)==0 ) break; |
| 179266 | pNode = &pNode[pNode->u.iAppend]; |
| @@ -179497,11 +179483,10 @@ | |
| 179483 | return jsonParseAddNodeExpand(pParse, eType, n, zContent); |
| 179484 | } |
| 179485 | p = &pParse->aNode[pParse->nNode]; |
| 179486 | p->eType = (u8)eType; |
| 179487 | p->jnFlags = 0; |
| 179488 | p->n = n; |
| 179489 | p->u.zJContent = zContent; |
| 179490 | return pParse->nNode++; |
| 179491 | } |
| 179492 | |
| @@ -180154,10 +180139,111 @@ | |
| 180139 | sqlite3_result_subtype(ctx, JSON_SUBTYPE); |
| 180140 | } |
| 180141 | jsonReset(&jx); |
| 180142 | jsonParseReset(&x); |
| 180143 | } |
| 180144 | |
| 180145 | /* This is the RFC 7396 MergePatch algorithm. |
| 180146 | */ |
| 180147 | static JsonNode *jsonMergePatch( |
| 180148 | JsonParse *pParse, /* The JSON parser that contains the TARGET */ |
| 180149 | int iTarget, /* Node of the TARGET in pParse */ |
| 180150 | JsonNode *pPatch /* The PATCH */ |
| 180151 | ){ |
| 180152 | u32 i, j; |
| 180153 | u32 iRoot; |
| 180154 | JsonNode *pTarget; |
| 180155 | if( pPatch->eType!=JSON_OBJECT ){ |
| 180156 | return pPatch; |
| 180157 | } |
| 180158 | assert( iTarget>=0 && iTarget<pParse->nNode ); |
| 180159 | pTarget = &pParse->aNode[iTarget]; |
| 180160 | assert( (pPatch->jnFlags & JNODE_APPEND)==0 ); |
| 180161 | if( pTarget->eType!=JSON_OBJECT ){ |
| 180162 | for(i=2; i<=pPatch->n; i += jsonNodeSize(&pPatch[i])+1){ |
| 180163 | if( pPatch[i].eType==JSON_NULL ){ |
| 180164 | pPatch[i].jnFlags |= JNODE_REMOVE; |
| 180165 | } |
| 180166 | } |
| 180167 | return pPatch; |
| 180168 | } |
| 180169 | iRoot = iTarget; |
| 180170 | for(i=1; i<pPatch->n; i += jsonNodeSize(&pPatch[i+1])+1){ |
| 180171 | int nKey; |
| 180172 | const char *zKey; |
| 180173 | assert( pPatch[i].eType==JSON_STRING ); |
| 180174 | assert( pPatch[i].jnFlags & JNODE_LABEL ); |
| 180175 | nKey = pPatch[i].n; |
| 180176 | zKey = pPatch[i].u.zJContent; |
| 180177 | assert( (pPatch[i].jnFlags & JNODE_RAW)==0 ); |
| 180178 | for(j=1; j<pTarget->n; j += jsonNodeSize(&pTarget[j+1])+1 ){ |
| 180179 | assert( pTarget[j].eType==JSON_STRING ); |
| 180180 | assert( pTarget[j].jnFlags & JNODE_LABEL ); |
| 180181 | assert( (pPatch[i].jnFlags & JNODE_RAW)==0 ); |
| 180182 | if( pTarget[j].n==nKey && strncmp(pTarget[j].u.zJContent,zKey,nKey)==0 ){ |
| 180183 | if( pTarget[j+1].jnFlags & (JNODE_REMOVE|JNODE_PATCH) ) break; |
| 180184 | if( pPatch[i+1].eType==JSON_NULL ){ |
| 180185 | pTarget[j+1].jnFlags |= JNODE_REMOVE; |
| 180186 | }else{ |
| 180187 | JsonNode *pNew = jsonMergePatch(pParse, iTarget+j+1, &pPatch[i+1]); |
| 180188 | if( pNew==0 ) return 0; |
| 180189 | pTarget = &pParse->aNode[iTarget]; |
| 180190 | if( pNew!=&pTarget[j+1] ){ |
| 180191 | pTarget[j+1].u.pPatch = pNew; |
| 180192 | pTarget[j+1].jnFlags |= JNODE_PATCH; |
| 180193 | } |
| 180194 | } |
| 180195 | break; |
| 180196 | } |
| 180197 | } |
| 180198 | if( j>=pTarget->n && pPatch[i+1].eType!=JSON_NULL ){ |
| 180199 | int iStart, iPatch; |
| 180200 | iStart = jsonParseAddNode(pParse, JSON_OBJECT, 2, 0); |
| 180201 | jsonParseAddNode(pParse, JSON_STRING, nKey, zKey); |
| 180202 | iPatch = jsonParseAddNode(pParse, JSON_TRUE, 0, 0); |
| 180203 | if( pParse->oom ) return 0; |
| 180204 | pTarget = &pParse->aNode[iTarget]; |
| 180205 | pParse->aNode[iRoot].jnFlags |= JNODE_APPEND; |
| 180206 | pParse->aNode[iRoot].u.iAppend = iStart - iRoot; |
| 180207 | iRoot = iStart; |
| 180208 | pParse->aNode[iPatch].jnFlags |= JNODE_PATCH; |
| 180209 | pParse->aNode[iPatch].u.pPatch = &pPatch[i+1]; |
| 180210 | } |
| 180211 | } |
| 180212 | return pTarget; |
| 180213 | } |
| 180214 | |
| 180215 | /* |
| 180216 | ** Implementation of the json_mergepatch(JSON1,JSON2) function. Return a JSON |
| 180217 | ** object that is the result of running the RFC 7396 MergePatch() algorithm |
| 180218 | ** on the two arguments. |
| 180219 | */ |
| 180220 | static void jsonPatchFunc( |
| 180221 | sqlite3_context *ctx, |
| 180222 | int argc, |
| 180223 | sqlite3_value **argv |
| 180224 | ){ |
| 180225 | JsonParse x; /* The JSON that is being patched */ |
| 180226 | JsonParse y; /* The patch */ |
| 180227 | JsonNode *pResult; /* The result of the merge */ |
| 180228 | |
| 180229 | if( jsonParse(&x, ctx, (const char*)sqlite3_value_text(argv[0])) ) return; |
| 180230 | if( jsonParse(&y, ctx, (const char*)sqlite3_value_text(argv[1])) ){ |
| 180231 | jsonParseReset(&x); |
| 180232 | return; |
| 180233 | } |
| 180234 | pResult = jsonMergePatch(&x, 0, y.aNode); |
| 180235 | assert( pResult!=0 || x.oom ); |
| 180236 | if( pResult ){ |
| 180237 | jsonReturnJson(pResult, ctx, 0); |
| 180238 | }else{ |
| 180239 | sqlite3_result_error_nomem(ctx); |
| 180240 | } |
| 180241 | jsonParseReset(&x); |
| 180242 | jsonParseReset(&y); |
| 180243 | } |
| 180244 | |
| 180245 | |
| 180246 | /* |
| 180247 | ** Implementation of the json_object(NAME,VALUE,...) function. Return a JSON |
| 180248 | ** object that contains all name/value given in arguments. Or if any name |
| 180249 | ** is not a string or if any value is a BLOB, throw an error. |
| @@ -180258,15 +180344,15 @@ | |
| 180344 | zPath = (const char*)sqlite3_value_text(argv[i]); |
| 180345 | pNode = jsonLookup(&x, zPath, 0, ctx); |
| 180346 | if( x.nErr ) goto replace_err; |
| 180347 | if( pNode ){ |
| 180348 | pNode->jnFlags |= (u8)JNODE_REPLACE; |
| 180349 | pNode->u.iReplace = i + 1; |
| 180350 | } |
| 180351 | } |
| 180352 | if( x.aNode[0].jnFlags & JNODE_REPLACE ){ |
| 180353 | sqlite3_result_value(ctx, argv[x.aNode[0].u.iReplace]); |
| 180354 | }else{ |
| 180355 | jsonReturnJson(x.aNode, ctx, argv); |
| 180356 | } |
| 180357 | replace_err: |
| 180358 | jsonParseReset(&x); |
| @@ -180312,15 +180398,15 @@ | |
| 180398 | goto jsonSetDone; |
| 180399 | }else if( x.nErr ){ |
| 180400 | goto jsonSetDone; |
| 180401 | }else if( pNode && (bApnd || bIsSet) ){ |
| 180402 | pNode->jnFlags |= (u8)JNODE_REPLACE; |
| 180403 | pNode->u.iReplace = i + 1; |
| 180404 | } |
| 180405 | } |
| 180406 | if( x.aNode[0].jnFlags & JNODE_REPLACE ){ |
| 180407 | sqlite3_result_value(ctx, argv[x.aNode[0].u.iReplace]); |
| 180408 | }else{ |
| 180409 | jsonReturnJson(x.aNode, ctx, argv); |
| 180410 | } |
| 180411 | jsonSetDone: |
| 180412 | jsonParseReset(&x); |
| @@ -180959,10 +181045,11 @@ | |
| 181045 | { "json_array_length", 1, 0, jsonArrayLengthFunc }, |
| 181046 | { "json_array_length", 2, 0, jsonArrayLengthFunc }, |
| 181047 | { "json_extract", -1, 0, jsonExtractFunc }, |
| 181048 | { "json_insert", -1, 0, jsonSetFunc }, |
| 181049 | { "json_object", -1, 0, jsonObjectFunc }, |
| 181050 | { "json_patch", 2, 0, jsonPatchFunc }, |
| 181051 | { "json_quote", 1, 0, jsonQuoteFunc }, |
| 181052 | { "json_remove", -1, 0, jsonRemoveFunc }, |
| 181053 | { "json_replace", -1, 0, jsonReplaceFunc }, |
| 181054 | { "json_set", -1, 1, jsonSetFunc }, |
| 181055 | { "json_type", 1, 0, jsonTypeFunc }, |
| @@ -198120,11 +198207,11 @@ | |
| 198207 | int nArg, /* Number of args */ |
| 198208 | sqlite3_value **apUnused /* Function arguments */ |
| 198209 | ){ |
| 198210 | assert( nArg==0 ); |
| 198211 | UNUSED_PARAM2(nArg, apUnused); |
| 198212 | sqlite3_result_text(pCtx, "fts5: 2017-03-23 23:44:55 476088482024e411e2549b1697cdaf0124294c79d43f508c71c4eb66906a56fc", -1, SQLITE_TRANSIENT); |
| 198213 | } |
| 198214 | |
| 198215 | static int fts5Init(sqlite3 *db){ |
| 198216 | static const sqlite3_module fts5Mod = { |
| 198217 | /* iVersion */ 2, |
| 198218 |
+1
-1
| --- src/sqlite3.h | ||
| +++ src/sqlite3.h | ||
| @@ -121,11 +121,11 @@ | ||
| 121 | 121 | ** [sqlite3_libversion_number()], [sqlite3_sourceid()], |
| 122 | 122 | ** [sqlite_version()] and [sqlite_source_id()]. |
| 123 | 123 | */ |
| 124 | 124 | #define SQLITE_VERSION "3.18.0" |
| 125 | 125 | #define SQLITE_VERSION_NUMBER 3018000 |
| 126 | -#define SQLITE_SOURCE_ID "2017-03-20 13:03:39 2aa22509e7c8a1f09b16e4544c95d0b77503daed1f83106ccc18dee8bd9487a4" | |
| 126 | +#define SQLITE_SOURCE_ID "2017-03-23 23:44:55 476088482024e411e2549b1697cdaf0124294c79d43f508c71c4eb66906a56fc" | |
| 127 | 127 | |
| 128 | 128 | /* |
| 129 | 129 | ** CAPI3REF: Run-Time Library Version Numbers |
| 130 | 130 | ** KEYWORDS: sqlite3_version sqlite3_sourceid |
| 131 | 131 | ** |
| 132 | 132 |
| --- src/sqlite3.h | |
| +++ src/sqlite3.h | |
| @@ -121,11 +121,11 @@ | |
| 121 | ** [sqlite3_libversion_number()], [sqlite3_sourceid()], |
| 122 | ** [sqlite_version()] and [sqlite_source_id()]. |
| 123 | */ |
| 124 | #define SQLITE_VERSION "3.18.0" |
| 125 | #define SQLITE_VERSION_NUMBER 3018000 |
| 126 | #define SQLITE_SOURCE_ID "2017-03-20 13:03:39 2aa22509e7c8a1f09b16e4544c95d0b77503daed1f83106ccc18dee8bd9487a4" |
| 127 | |
| 128 | /* |
| 129 | ** CAPI3REF: Run-Time Library Version Numbers |
| 130 | ** KEYWORDS: sqlite3_version sqlite3_sourceid |
| 131 | ** |
| 132 |
| --- src/sqlite3.h | |
| +++ src/sqlite3.h | |
| @@ -121,11 +121,11 @@ | |
| 121 | ** [sqlite3_libversion_number()], [sqlite3_sourceid()], |
| 122 | ** [sqlite_version()] and [sqlite_source_id()]. |
| 123 | */ |
| 124 | #define SQLITE_VERSION "3.18.0" |
| 125 | #define SQLITE_VERSION_NUMBER 3018000 |
| 126 | #define SQLITE_SOURCE_ID "2017-03-23 23:44:55 476088482024e411e2549b1697cdaf0124294c79d43f508c71c4eb66906a56fc" |
| 127 | |
| 128 | /* |
| 129 | ** CAPI3REF: Run-Time Library Version Numbers |
| 130 | ** KEYWORDS: sqlite3_version sqlite3_sourceid |
| 131 | ** |
| 132 |