Compare commits
72 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| d49a37a8ef | |||
| 86732babe3 | |||
| 228a52d973 | |||
| 6117a17323 | |||
| d1c472dab6 | |||
| b008e4d744 | |||
| 367b8d7aa7 | |||
| 9a50f4c72a | |||
| f0578823dd | |||
| 23d3f5d661 | |||
| e2b7a7693e | |||
| cfee884e73 | |||
| 5e81e9fdae | |||
| 905d4729d3 | |||
| 018dbb17a8 | |||
| 5c0666d9e3 | |||
| 5f419b3bba | |||
| e4079e1fc5 | |||
| ebc6408484 | |||
| 818a3b5486 | |||
| 7971b7fe92 | |||
| 91f34eab2d | |||
| 9d30c8ff8f | |||
| ec39707fe6 | |||
| d79cd92b23 | |||
| a51ddb1ed7 | |||
| b19131a8c6 | |||
| 2829df082c | |||
| e7579a53fb | |||
| edf8a7bf57 | |||
| 1116b1785c | |||
| c5b35ae567 | |||
| 37d296a717 | |||
| 5776ee5cf5 | |||
| 7ca1347f59 | |||
| b7fc7c8556 | |||
| e39f388eb1 | |||
| 8c9bcb2328 | |||
| e47d5ca737 | |||
| af9b58b335 | |||
| ed09dddece | |||
| 14e3e22773 | |||
| 6d2566dfc2 | |||
| 572b0dddee | |||
| aa16c603ab | |||
| 4b48c72721 | |||
| 9d70284022 | |||
| ec722c1088 | |||
| e691dcb506 | |||
| 97b0250599 | |||
| 70738712de | |||
| 91f473b5cc | |||
| 130dbc3d96 | |||
| 2ad35d980b | |||
| b42eb3571c | |||
| 8cce6b8310 | |||
| d44c617ad4 | |||
| fab5b07395 | |||
| 51a75aaa76 | |||
| e087a7c35b | |||
| cd9cb85a41 | |||
| 477f1f12e2 | |||
| 01a3b6b1b2 | |||
| 945a3527d5 | |||
| 3f3f2c7357 | |||
| fbb9a5b1e3 | |||
| 685b2ee0c3 | |||
| acf6e08d20 | |||
| c204d81a6c | |||
| fa50834914 | |||
| d5deb6b3c4 | |||
| e2ba6df9f0 |
+22
-18
@@ -308,6 +308,18 @@
|
||||
SQLITE_EXTENSION_INIT1
|
||||
#endif
|
||||
|
||||
/*
|
||||
** The following are copied from sqliteInt.h.
|
||||
**
|
||||
** Constants for the largest and smallest possible 64-bit signed integers.
|
||||
** These macros are designed to work correctly on both 32-bit and 64-bit
|
||||
** compilers.
|
||||
*/
|
||||
#ifndef SQLITE_AMALGAMATION
|
||||
# define LARGEST_INT64 (0xffffffff|(((sqlite3_int64)0x7fffffff)<<32))
|
||||
# define SMALLEST_INT64 (((sqlite3_int64)-1) - LARGEST_INT64)
|
||||
#endif
|
||||
|
||||
static int fts3EvalNext(Fts3Cursor *pCsr);
|
||||
static int fts3EvalStart(Fts3Cursor *pCsr);
|
||||
static int fts3TermSegReaderCursor(
|
||||
@@ -2086,10 +2098,11 @@ static void fts3ColumnlistCopy(char **pp, char **ppPoslist){
|
||||
}
|
||||
|
||||
/*
|
||||
** Value used to signify the end of an position-list. This is safe because
|
||||
** it is not possible to have a document with 2^31 terms.
|
||||
** Value used to signify the end of an position-list. This must be
|
||||
** as large or larger than any value that might appear on the
|
||||
** position-list, even a position list that has been corrupted.
|
||||
*/
|
||||
#define POSITION_LIST_END 0x7fffffff
|
||||
#define POSITION_LIST_END LARGEST_INT64
|
||||
|
||||
/*
|
||||
** This function is used to help parse position-lists. When this function is
|
||||
@@ -2165,14 +2178,14 @@ static int fts3PoslistMerge(
|
||||
fts3GetVarint32(&p1[1], &iCol1);
|
||||
if( iCol1==0 ) return FTS_CORRUPT_VTAB;
|
||||
}
|
||||
else if( *p1==POS_END ) iCol1 = POSITION_LIST_END;
|
||||
else if( *p1==POS_END ) iCol1 = 0x7fffffff;
|
||||
else iCol1 = 0;
|
||||
|
||||
if( *p2==POS_COLUMN ){
|
||||
fts3GetVarint32(&p2[1], &iCol2);
|
||||
if( iCol2==0 ) return FTS_CORRUPT_VTAB;
|
||||
}
|
||||
else if( *p2==POS_END ) iCol2 = POSITION_LIST_END;
|
||||
else if( *p2==POS_END ) iCol2 = 0x7fffffff;
|
||||
else iCol2 = 0;
|
||||
|
||||
if( iCol1==iCol2 ){
|
||||
@@ -2474,7 +2487,8 @@ static void fts3PutDeltaVarint3(
|
||||
iWrite = *piPrev - iVal;
|
||||
}
|
||||
assert( *pbFirst || *piPrev==0 );
|
||||
assert( *pbFirst==0 || iWrite>0 );
|
||||
assert_fts3_nc( *pbFirst==0 || iWrite>0 );
|
||||
assert( *pbFirst==0 || iWrite>=0 );
|
||||
*pp += sqlite3Fts3PutVarint(*pp, iWrite);
|
||||
*piPrev = iVal;
|
||||
*pbFirst = 1;
|
||||
@@ -2580,6 +2594,8 @@ static int fts3DoclistOrMerge(
|
||||
fts3PoslistCopy(&p, &p2);
|
||||
fts3GetDeltaVarint3(&p2, pEnd2, bDescDoclist, &i2);
|
||||
}
|
||||
|
||||
assert( (p-aOut)<=((p1?(p1-a1):n1)+(p2?(p2-a2):n2)+FTS3_VARINT_MAX-1) );
|
||||
}
|
||||
|
||||
if( rc!=SQLITE_OK ){
|
||||
@@ -3179,18 +3195,6 @@ static int fts3NextMethod(sqlite3_vtab_cursor *pCursor){
|
||||
return rc;
|
||||
}
|
||||
|
||||
/*
|
||||
** The following are copied from sqliteInt.h.
|
||||
**
|
||||
** Constants for the largest and smallest possible 64-bit signed integers.
|
||||
** These macros are designed to work correctly on both 32-bit and 64-bit
|
||||
** compilers.
|
||||
*/
|
||||
#ifndef SQLITE_AMALGAMATION
|
||||
# define LARGEST_INT64 (0xffffffff|(((sqlite3_int64)0x7fffffff)<<32))
|
||||
# define SMALLEST_INT64 (((sqlite3_int64)-1) - LARGEST_INT64)
|
||||
#endif
|
||||
|
||||
/*
|
||||
** If the numeric type of argument pVal is "integer", then return it
|
||||
** converted to a 64-bit signed integer. Otherwise, return a copy of
|
||||
|
||||
@@ -3797,14 +3797,14 @@ static int nodeReaderInit(NodeReader *p, const char *aNode, int nNode){
|
||||
p->nNode = nNode;
|
||||
|
||||
/* Figure out if this is a leaf or an internal node. */
|
||||
if( p->aNode[0] ){
|
||||
if( aNode && aNode[0] ){
|
||||
/* An internal node. */
|
||||
p->iOff = 1 + sqlite3Fts3GetVarint(&p->aNode[1], &p->iChild);
|
||||
}else{
|
||||
p->iOff = 1;
|
||||
}
|
||||
|
||||
return nodeReaderNext(p);
|
||||
return aNode ? nodeReaderNext(p) : SQLITE_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -4296,8 +4296,8 @@ static int fts3IncrmergeLoad(
|
||||
NodeReader reader;
|
||||
pNode = &pWriter->aNodeWriter[i];
|
||||
|
||||
rc = nodeReaderInit(&reader, pNode->block.a, pNode->block.n);
|
||||
if( reader.aNode ){
|
||||
if( pNode->block.a){
|
||||
rc = nodeReaderInit(&reader, pNode->block.a, pNode->block.n);
|
||||
while( reader.aNode && rc==SQLITE_OK ) rc = nodeReaderNext(&reader);
|
||||
blobGrowBuffer(&pNode->key, reader.term.n, &rc);
|
||||
if( rc==SQLITE_OK ){
|
||||
|
||||
@@ -695,6 +695,7 @@ int sqlite3Fts5ExprEof(Fts5Expr*);
|
||||
i64 sqlite3Fts5ExprRowid(Fts5Expr*);
|
||||
|
||||
void sqlite3Fts5ExprFree(Fts5Expr*);
|
||||
int sqlite3Fts5ExprAnd(Fts5Expr **pp1, Fts5Expr *p2);
|
||||
|
||||
/* Called during startup to register a UDF with SQLite */
|
||||
int sqlite3Fts5ExprInit(Fts5Global*, sqlite3*);
|
||||
|
||||
@@ -683,7 +683,7 @@ int sqlite3Fts5ConfigDeclareVtab(Fts5Config *pConfig){
|
||||
rc = sqlite3_declare_vtab(pConfig->db, zSql);
|
||||
sqlite3_free(zSql);
|
||||
}
|
||||
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
||||
@@ -309,6 +309,42 @@ void sqlite3Fts5ExprFree(Fts5Expr *p){
|
||||
}
|
||||
}
|
||||
|
||||
int sqlite3Fts5ExprAnd(Fts5Expr **pp1, Fts5Expr *p2){
|
||||
Fts5Parse sParse;
|
||||
memset(&sParse, 0, sizeof(sParse));
|
||||
|
||||
if( *pp1 ){
|
||||
Fts5Expr *p1 = *pp1;
|
||||
int nPhrase = p1->nPhrase + p2->nPhrase;
|
||||
|
||||
p1->pRoot = sqlite3Fts5ParseNode(&sParse, FTS5_AND, p1->pRoot, p2->pRoot,0);
|
||||
p2->pRoot = 0;
|
||||
|
||||
if( sParse.rc==SQLITE_OK ){
|
||||
Fts5ExprPhrase **ap = (Fts5ExprPhrase**)sqlite3_realloc(
|
||||
p1->apExprPhrase, nPhrase * sizeof(Fts5ExprPhrase*)
|
||||
);
|
||||
if( ap==0 ){
|
||||
sParse.rc = SQLITE_NOMEM;
|
||||
}else{
|
||||
int i;
|
||||
memmove(&ap[p2->nPhrase], ap, p1->nPhrase*sizeof(Fts5ExprPhrase*));
|
||||
for(i=0; i<p2->nPhrase; i++){
|
||||
ap[i] = p2->apExprPhrase[i];
|
||||
}
|
||||
p1->nPhrase = nPhrase;
|
||||
p1->apExprPhrase = ap;
|
||||
}
|
||||
}
|
||||
sqlite3_free(p2->apExprPhrase);
|
||||
sqlite3_free(p2);
|
||||
}else{
|
||||
*pp1 = p2;
|
||||
}
|
||||
|
||||
return sParse.rc;
|
||||
}
|
||||
|
||||
/*
|
||||
** Argument pTerm must be a synonym iterator. Return the current rowid
|
||||
** that it points to.
|
||||
|
||||
@@ -713,7 +713,7 @@ static void fts5DataRelease(Fts5Data *pData){
|
||||
static Fts5Data *fts5LeafRead(Fts5Index *p, i64 iRowid){
|
||||
Fts5Data *pRet = fts5DataRead(p, iRowid);
|
||||
if( pRet ){
|
||||
if( pRet->szLeaf>pRet->nn ){
|
||||
if( pRet->nn<4 || pRet->szLeaf>pRet->nn ){
|
||||
p->rc = FTS5_CORRUPT;
|
||||
fts5DataRelease(pRet);
|
||||
pRet = 0;
|
||||
|
||||
+162
-104
@@ -465,17 +465,39 @@ static void fts5SetUniqueFlag(sqlite3_index_info *pIdxInfo){
|
||||
** Implementation of the xBestIndex method for FTS5 tables. Within the
|
||||
** WHERE constraint, it searches for the following:
|
||||
**
|
||||
** 1. A MATCH constraint against the special column.
|
||||
** 1. A MATCH constraint against the table column.
|
||||
** 2. A MATCH constraint against the "rank" column.
|
||||
** 3. An == constraint against the rowid column.
|
||||
** 4. A < or <= constraint against the rowid column.
|
||||
** 5. A > or >= constraint against the rowid column.
|
||||
** 3. A MATCH constraint against some other column.
|
||||
** 4. An == constraint against the rowid column.
|
||||
** 5. A < or <= constraint against the rowid column.
|
||||
** 6. A > or >= constraint against the rowid column.
|
||||
**
|
||||
** Within the ORDER BY, either:
|
||||
** Within the ORDER BY, the following are supported:
|
||||
**
|
||||
** 5. ORDER BY rank [ASC|DESC]
|
||||
** 6. ORDER BY rowid [ASC|DESC]
|
||||
**
|
||||
** Information for the xFilter call is passed via both the idxNum and
|
||||
** idxStr variables. Specifically, idxNum is a bitmask of the following
|
||||
** flags used to encode the ORDER BY clause:
|
||||
**
|
||||
** FTS5_BI_ORDER_RANK
|
||||
** FTS5_BI_ORDER_ROWID
|
||||
** FTS5_BI_ORDER_DESC
|
||||
**
|
||||
** idxStr is used to encode data from the WHERE clause. For each argument
|
||||
** passed to the xFilter method, the following is appended to idxStr:
|
||||
**
|
||||
** Match against table column: "m"
|
||||
** Match against rank column: "r"
|
||||
** Match against other column: "<column-number>"
|
||||
** Equality constraint against the rowid: "="
|
||||
** A < or <= against the rowid: "<"
|
||||
** A > or >= against the rowid: ">"
|
||||
**
|
||||
** This function ensures that there is at most one "r" or "=". And that if
|
||||
** there exists an "=" then there is no "<" or ">".
|
||||
**
|
||||
** Costs are assigned as follows:
|
||||
**
|
||||
** a) If an unusable MATCH operator is present in the WHERE clause, the
|
||||
@@ -503,32 +525,18 @@ static int fts5BestIndexMethod(sqlite3_vtab *pVTab, sqlite3_index_info *pInfo){
|
||||
Fts5Config *pConfig = pTab->pConfig;
|
||||
const int nCol = pConfig->nCol;
|
||||
int idxFlags = 0; /* Parameter passed through to xFilter() */
|
||||
int bHasMatch;
|
||||
int iNext;
|
||||
int i;
|
||||
|
||||
struct Constraint {
|
||||
int op; /* Mask against sqlite3_index_constraint.op */
|
||||
int fts5op; /* FTS5 mask for idxFlags */
|
||||
int iCol; /* 0==rowid, 1==tbl, 2==rank */
|
||||
int omit; /* True to omit this if found */
|
||||
int iConsIndex; /* Index in pInfo->aConstraint[] */
|
||||
} aConstraint[] = {
|
||||
{SQLITE_INDEX_CONSTRAINT_MATCH|SQLITE_INDEX_CONSTRAINT_EQ,
|
||||
FTS5_BI_MATCH, 1, 1, -1},
|
||||
{SQLITE_INDEX_CONSTRAINT_MATCH|SQLITE_INDEX_CONSTRAINT_EQ,
|
||||
FTS5_BI_RANK, 2, 1, -1},
|
||||
{SQLITE_INDEX_CONSTRAINT_EQ, FTS5_BI_ROWID_EQ, 0, 0, -1},
|
||||
{SQLITE_INDEX_CONSTRAINT_LT|SQLITE_INDEX_CONSTRAINT_LE,
|
||||
FTS5_BI_ROWID_LE, 0, 0, -1},
|
||||
{SQLITE_INDEX_CONSTRAINT_GT|SQLITE_INDEX_CONSTRAINT_GE,
|
||||
FTS5_BI_ROWID_GE, 0, 0, -1},
|
||||
};
|
||||
char *idxStr;
|
||||
int iIdxStr = 0;
|
||||
int iCons = 0;
|
||||
|
||||
int bSeenEq = 0;
|
||||
int bSeenGt = 0;
|
||||
int bSeenLt = 0;
|
||||
int bSeenMatch = 0;
|
||||
int bSeenRank = 0;
|
||||
|
||||
int aColMap[3];
|
||||
aColMap[0] = -1;
|
||||
aColMap[1] = nCol;
|
||||
aColMap[2] = nCol+1;
|
||||
|
||||
assert( SQLITE_INDEX_CONSTRAINT_EQ<SQLITE_INDEX_CONSTRAINT_MATCH );
|
||||
assert( SQLITE_INDEX_CONSTRAINT_GT<SQLITE_INDEX_CONSTRAINT_MATCH );
|
||||
@@ -543,40 +551,78 @@ static int fts5BestIndexMethod(sqlite3_vtab *pVTab, sqlite3_index_info *pInfo){
|
||||
return SQLITE_ERROR;
|
||||
}
|
||||
|
||||
/* Set idxFlags flags for all WHERE clause terms that will be used. */
|
||||
idxStr = (char*)sqlite3_malloc(pInfo->nConstraint * 6 + 1);
|
||||
if( idxStr==0 ) return SQLITE_NOMEM;
|
||||
pInfo->idxStr = idxStr;
|
||||
pInfo->needToFreeIdxStr = 1;
|
||||
|
||||
for(i=0; i<pInfo->nConstraint; i++){
|
||||
struct sqlite3_index_constraint *p = &pInfo->aConstraint[i];
|
||||
int iCol = p->iColumn;
|
||||
|
||||
if( (p->op==SQLITE_INDEX_CONSTRAINT_MATCH && iCol>=0 && iCol<=nCol)
|
||||
|| (p->op==SQLITE_INDEX_CONSTRAINT_EQ && iCol==nCol)
|
||||
if( p->op==SQLITE_INDEX_CONSTRAINT_MATCH
|
||||
|| (p->op==SQLITE_INDEX_CONSTRAINT_EQ && iCol>=nCol)
|
||||
){
|
||||
/* A MATCH operator or equivalent */
|
||||
if( p->usable ){
|
||||
idxFlags = (idxFlags & 0xFFFF) | FTS5_BI_MATCH | (iCol << 16);
|
||||
aConstraint[0].iConsIndex = i;
|
||||
}else{
|
||||
if( p->usable==0 || iCol<0 ){
|
||||
/* As there exists an unusable MATCH constraint this is an
|
||||
** unusable plan. Set a prohibitively high cost. */
|
||||
pInfo->estimatedCost = 1e50;
|
||||
assert( iIdxStr < pInfo->nConstraint*6 + 1 );
|
||||
idxStr[iIdxStr] = 0;
|
||||
return SQLITE_OK;
|
||||
}else{
|
||||
if( iCol==nCol+1 ){
|
||||
if( bSeenRank ) continue;
|
||||
idxStr[iIdxStr++] = 'r';
|
||||
bSeenRank = 1;
|
||||
}else{
|
||||
bSeenMatch = 1;
|
||||
idxStr[iIdxStr++] = 'm';
|
||||
if( iCol<nCol ){
|
||||
sqlite3_snprintf(6, &idxStr[iIdxStr], "%d", iCol);
|
||||
idxStr += strlen(&idxStr[iIdxStr]);
|
||||
assert( idxStr[iIdxStr]=='\0' );
|
||||
}
|
||||
}
|
||||
pInfo->aConstraintUsage[i].argvIndex = ++iCons;
|
||||
pInfo->aConstraintUsage[i].omit = 1;
|
||||
}
|
||||
}else if( p->op<=SQLITE_INDEX_CONSTRAINT_MATCH ){
|
||||
int j;
|
||||
for(j=1; j<ArraySize(aConstraint); j++){
|
||||
struct Constraint *pC = &aConstraint[j];
|
||||
if( iCol==aColMap[pC->iCol] && (p->op & pC->op) && p->usable ){
|
||||
pC->iConsIndex = i;
|
||||
idxFlags |= pC->fts5op;
|
||||
}
|
||||
else if( p->usable && bSeenEq==0
|
||||
&& p->op==SQLITE_INDEX_CONSTRAINT_EQ && iCol<0
|
||||
){
|
||||
idxStr[iIdxStr++] = '=';
|
||||
bSeenEq = 1;
|
||||
pInfo->aConstraintUsage[i].argvIndex = ++iCons;
|
||||
}
|
||||
}
|
||||
|
||||
if( bSeenEq==0 ){
|
||||
for(i=0; i<pInfo->nConstraint; i++){
|
||||
struct sqlite3_index_constraint *p = &pInfo->aConstraint[i];
|
||||
if( p->iColumn<0 && p->usable ){
|
||||
int op = p->op;
|
||||
if( op==SQLITE_INDEX_CONSTRAINT_LT || op==SQLITE_INDEX_CONSTRAINT_LE ){
|
||||
if( bSeenLt ) continue;
|
||||
idxStr[iIdxStr++] = '<';
|
||||
pInfo->aConstraintUsage[i].argvIndex = ++iCons;
|
||||
bSeenLt = 1;
|
||||
}else
|
||||
if( op==SQLITE_INDEX_CONSTRAINT_GT || op==SQLITE_INDEX_CONSTRAINT_GE ){
|
||||
if( bSeenGt ) continue;
|
||||
idxStr[iIdxStr++] = '>';
|
||||
pInfo->aConstraintUsage[i].argvIndex = ++iCons;
|
||||
bSeenGt = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
idxStr[iIdxStr] = '\0';
|
||||
|
||||
/* Set idxFlags flags for the ORDER BY clause */
|
||||
if( pInfo->nOrderBy==1 ){
|
||||
int iSort = pInfo->aOrderBy[0].iColumn;
|
||||
if( iSort==(pConfig->nCol+1) && BitFlagTest(idxFlags, FTS5_BI_MATCH) ){
|
||||
if( iSort==(pConfig->nCol+1) && bSeenMatch ){
|
||||
idxFlags |= FTS5_BI_ORDER_RANK;
|
||||
}else if( iSort==-1 ){
|
||||
idxFlags |= FTS5_BI_ORDER_ROWID;
|
||||
@@ -590,26 +636,15 @@ static int fts5BestIndexMethod(sqlite3_vtab *pVTab, sqlite3_index_info *pInfo){
|
||||
}
|
||||
|
||||
/* Calculate the estimated cost based on the flags set in idxFlags. */
|
||||
bHasMatch = BitFlagTest(idxFlags, FTS5_BI_MATCH);
|
||||
if( BitFlagTest(idxFlags, FTS5_BI_ROWID_EQ) ){
|
||||
pInfo->estimatedCost = bHasMatch ? 100.0 : 10.0;
|
||||
if( bHasMatch==0 ) fts5SetUniqueFlag(pInfo);
|
||||
}else if( BitFlagAllTest(idxFlags, FTS5_BI_ROWID_LE|FTS5_BI_ROWID_GE) ){
|
||||
pInfo->estimatedCost = bHasMatch ? 500.0 : 250000.0;
|
||||
}else if( BitFlagTest(idxFlags, FTS5_BI_ROWID_LE|FTS5_BI_ROWID_GE) ){
|
||||
pInfo->estimatedCost = bHasMatch ? 750.0 : 750000.0;
|
||||
if( bSeenEq ){
|
||||
pInfo->estimatedCost = bSeenMatch ? 100.0 : 10.0;
|
||||
if( bSeenMatch==0 ) fts5SetUniqueFlag(pInfo);
|
||||
}else if( bSeenLt && bSeenGt ){
|
||||
pInfo->estimatedCost = bSeenMatch ? 500.0 : 250000.0;
|
||||
}else if( bSeenLt || bSeenGt ){
|
||||
pInfo->estimatedCost = bSeenMatch ? 750.0 : 750000.0;
|
||||
}else{
|
||||
pInfo->estimatedCost = bHasMatch ? 1000.0 : 1000000.0;
|
||||
}
|
||||
|
||||
/* Assign argvIndex values to each constraint in use. */
|
||||
iNext = 1;
|
||||
for(i=0; i<ArraySize(aConstraint); i++){
|
||||
struct Constraint *pC = &aConstraint[i];
|
||||
if( pC->iConsIndex>=0 ){
|
||||
pInfo->aConstraintUsage[pC->iConsIndex].argvIndex = iNext++;
|
||||
pInfo->aConstraintUsage[pC->iConsIndex].omit = (unsigned char)pC->omit;
|
||||
}
|
||||
pInfo->estimatedCost = bSeenMatch ? 1000.0 : 1000000.0;
|
||||
}
|
||||
|
||||
pInfo->idxNum = idxFlags;
|
||||
@@ -1132,7 +1167,7 @@ static i64 fts5GetRowidLimit(sqlite3_value *pVal, i64 iDefault){
|
||||
static int fts5FilterMethod(
|
||||
sqlite3_vtab_cursor *pCursor, /* The cursor used for this query */
|
||||
int idxNum, /* Strategy index */
|
||||
const char *zUnused, /* Unused */
|
||||
const char *idxStr, /* Unused */
|
||||
int nVal, /* Number of elements in apVal */
|
||||
sqlite3_value **apVal /* Arguments for the indexing scheme */
|
||||
){
|
||||
@@ -1140,19 +1175,17 @@ static int fts5FilterMethod(
|
||||
Fts5Config *pConfig = pTab->p.pConfig;
|
||||
Fts5Cursor *pCsr = (Fts5Cursor*)pCursor;
|
||||
int rc = SQLITE_OK; /* Error code */
|
||||
int iVal = 0; /* Counter for apVal[] */
|
||||
int bDesc; /* True if ORDER BY [rank|rowid] DESC */
|
||||
int bOrderByRank; /* True if ORDER BY rank */
|
||||
sqlite3_value *pMatch = 0; /* <tbl> MATCH ? expression (or NULL) */
|
||||
sqlite3_value *pRank = 0; /* rank MATCH ? expression (or NULL) */
|
||||
sqlite3_value *pRowidEq = 0; /* rowid = ? expression (or NULL) */
|
||||
sqlite3_value *pRowidLe = 0; /* rowid <= ? expression (or NULL) */
|
||||
sqlite3_value *pRowidGe = 0; /* rowid >= ? expression (or NULL) */
|
||||
int iCol; /* Column on LHS of MATCH operator */
|
||||
char **pzErrmsg = pConfig->pzErrmsg;
|
||||
|
||||
UNUSED_PARAM(zUnused);
|
||||
UNUSED_PARAM(nVal);
|
||||
int i;
|
||||
int iIdxStr = 0;
|
||||
Fts5Expr *pExpr = 0;
|
||||
|
||||
if( pCsr->ePlan ){
|
||||
fts5FreeCursorComponents(pCsr);
|
||||
@@ -1165,23 +1198,60 @@ static int fts5FilterMethod(
|
||||
assert( pCsr->pRank==0 );
|
||||
assert( pCsr->zRank==0 );
|
||||
assert( pCsr->zRankArgs==0 );
|
||||
assert( pTab->pSortCsr==0 || nVal==0 );
|
||||
|
||||
assert( pzErrmsg==0 || pzErrmsg==&pTab->p.base.zErrMsg );
|
||||
pConfig->pzErrmsg = &pTab->p.base.zErrMsg;
|
||||
|
||||
/* Decode the arguments passed through to this function.
|
||||
**
|
||||
** Note: The following set of if(...) statements must be in the same
|
||||
** order as the corresponding entries in the struct at the top of
|
||||
** fts5BestIndexMethod(). */
|
||||
if( BitFlagTest(idxNum, FTS5_BI_MATCH) ) pMatch = apVal[iVal++];
|
||||
if( BitFlagTest(idxNum, FTS5_BI_RANK) ) pRank = apVal[iVal++];
|
||||
if( BitFlagTest(idxNum, FTS5_BI_ROWID_EQ) ) pRowidEq = apVal[iVal++];
|
||||
if( BitFlagTest(idxNum, FTS5_BI_ROWID_LE) ) pRowidLe = apVal[iVal++];
|
||||
if( BitFlagTest(idxNum, FTS5_BI_ROWID_GE) ) pRowidGe = apVal[iVal++];
|
||||
iCol = (idxNum>>16);
|
||||
assert( iCol>=0 && iCol<=pConfig->nCol );
|
||||
assert( iVal==nVal );
|
||||
/* Decode the arguments passed through to this function. */
|
||||
for(i=0; i<nVal; i++){
|
||||
switch( idxStr[iIdxStr++] ){
|
||||
case 'r':
|
||||
pRank = apVal[i];
|
||||
break;
|
||||
case 'm': {
|
||||
const char *zText = (const char*)sqlite3_value_text(apVal[i]);
|
||||
if( zText==0 ) zText = "";
|
||||
|
||||
if( idxStr[iIdxStr]>='0' && idxStr[iIdxStr]<='9' ){
|
||||
iCol = 0;
|
||||
do{
|
||||
iCol = iCol*10 + (idxStr[iIdxStr]-'0');
|
||||
iIdxStr++;
|
||||
}while( idxStr[iIdxStr]>='0' && idxStr[iIdxStr]<='9' );
|
||||
}else{
|
||||
iCol = pConfig->nCol;
|
||||
}
|
||||
|
||||
if( zText[0]=='*' ){
|
||||
/* The user has issued a query of the form "MATCH '*...'". This
|
||||
** indicates that the MATCH expression is not a full text query,
|
||||
** but a request for an internal parameter. */
|
||||
rc = fts5SpecialMatch(pTab, pCsr, &zText[1]);
|
||||
goto filter_out;
|
||||
}else{
|
||||
char **pzErr = &pTab->p.base.zErrMsg;
|
||||
rc = sqlite3Fts5ExprNew(pConfig, iCol, zText, &pExpr, pzErr);
|
||||
if( rc==SQLITE_OK ){
|
||||
rc = sqlite3Fts5ExprAnd(&pCsr->pExpr, pExpr);
|
||||
pExpr = 0;
|
||||
}
|
||||
if( rc!=SQLITE_OK ) goto filter_out;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
case '=':
|
||||
pRowidEq = apVal[i];
|
||||
break;
|
||||
case '<':
|
||||
pRowidLe = apVal[i];
|
||||
break;
|
||||
default: assert( idxStr[iIdxStr-1]=='>' );
|
||||
pRowidGe = apVal[i];
|
||||
break;
|
||||
}
|
||||
}
|
||||
bOrderByRank = ((idxNum & FTS5_BI_ORDER_RANK) ? 1 : 0);
|
||||
pCsr->bDesc = bDesc = ((idxNum & FTS5_BI_ORDER_DESC) ? 1 : 0);
|
||||
|
||||
@@ -1208,7 +1278,7 @@ static int fts5FilterMethod(
|
||||
** (pCursor) is used to execute the query issued by function
|
||||
** fts5CursorFirstSorted() above. */
|
||||
assert( pRowidEq==0 && pRowidLe==0 && pRowidGe==0 && pRank==0 );
|
||||
assert( nVal==0 && pMatch==0 && bOrderByRank==0 && bDesc==0 );
|
||||
assert( nVal==0 && bOrderByRank==0 && bDesc==0 );
|
||||
assert( pCsr->iLastRowid==LARGEST_INT64 );
|
||||
assert( pCsr->iFirstRowid==SMALLEST_INT64 );
|
||||
if( pTab->pSortCsr->bDesc ){
|
||||
@@ -1221,29 +1291,15 @@ static int fts5FilterMethod(
|
||||
pCsr->ePlan = FTS5_PLAN_SOURCE;
|
||||
pCsr->pExpr = pTab->pSortCsr->pExpr;
|
||||
rc = fts5CursorFirst(pTab, pCsr, bDesc);
|
||||
}else if( pMatch ){
|
||||
const char *zExpr = (const char*)sqlite3_value_text(apVal[0]);
|
||||
if( zExpr==0 ) zExpr = "";
|
||||
|
||||
}else if( pCsr->pExpr ){
|
||||
rc = fts5CursorParseRank(pConfig, pCsr, pRank);
|
||||
if( rc==SQLITE_OK ){
|
||||
if( zExpr[0]=='*' ){
|
||||
/* The user has issued a query of the form "MATCH '*...'". This
|
||||
** indicates that the MATCH expression is not a full text query,
|
||||
** but a request for an internal parameter. */
|
||||
rc = fts5SpecialMatch(pTab, pCsr, &zExpr[1]);
|
||||
if( bOrderByRank ){
|
||||
pCsr->ePlan = FTS5_PLAN_SORTED_MATCH;
|
||||
rc = fts5CursorFirstSorted(pTab, pCsr, bDesc);
|
||||
}else{
|
||||
char **pzErr = &pTab->p.base.zErrMsg;
|
||||
rc = sqlite3Fts5ExprNew(pConfig, iCol, zExpr, &pCsr->pExpr, pzErr);
|
||||
if( rc==SQLITE_OK ){
|
||||
if( bOrderByRank ){
|
||||
pCsr->ePlan = FTS5_PLAN_SORTED_MATCH;
|
||||
rc = fts5CursorFirstSorted(pTab, pCsr, bDesc);
|
||||
}else{
|
||||
pCsr->ePlan = FTS5_PLAN_MATCH;
|
||||
rc = fts5CursorFirst(pTab, pCsr, bDesc);
|
||||
}
|
||||
}
|
||||
pCsr->ePlan = FTS5_PLAN_MATCH;
|
||||
rc = fts5CursorFirst(pTab, pCsr, bDesc);
|
||||
}
|
||||
}
|
||||
}else if( pConfig->zContent==0 ){
|
||||
@@ -1260,7 +1316,7 @@ static int fts5FilterMethod(
|
||||
);
|
||||
if( rc==SQLITE_OK ){
|
||||
if( pCsr->ePlan==FTS5_PLAN_ROWID ){
|
||||
sqlite3_bind_value(pCsr->pStmt, 1, apVal[0]);
|
||||
sqlite3_bind_value(pCsr->pStmt, 1, pRowidEq);
|
||||
}else{
|
||||
sqlite3_bind_int64(pCsr->pStmt, 1, pCsr->iFirstRowid);
|
||||
sqlite3_bind_int64(pCsr->pStmt, 2, pCsr->iLastRowid);
|
||||
@@ -1269,6 +1325,8 @@ static int fts5FilterMethod(
|
||||
}
|
||||
}
|
||||
|
||||
filter_out:
|
||||
sqlite3Fts5ExprFree(pExpr);
|
||||
pConfig->pzErrmsg = pzErrmsg;
|
||||
return rc;
|
||||
}
|
||||
|
||||
@@ -9693,6 +9693,87 @@ do_catchsql_test 65.1 {
|
||||
SELECT ( MATCH (t1,591)) FROM t1 WHERE t1 MATCH 'e*eŸ'
|
||||
} {1 {database disk image is malformed}}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
#
|
||||
reset_db
|
||||
do_test 66.0 {
|
||||
sqlite3 db {}
|
||||
db deserialize [decode_hexdb {
|
||||
.open --hexdb
|
||||
| size 28672 pagesize 4096 filename crash-37cecb4e784e9f.db
|
||||
| page 1 offset 0
|
||||
| 0: 53 51 4c 69 74 65 20 66 6f 72 6d 61 74 20 33 00 SQLite format 3.
|
||||
| 16: 10 00 01 01 00 40 20 20 00 00 00 00 00 00 00 07 .....@ ........
|
||||
| 96: 00 00 00 00 0d 00 00 00 07 0d d2 00 0f c4 0f 6d ...............m
|
||||
| 112: 0f 02 0e ab 0e 4e 0d f6 0d d2 00 00 00 00 00 00 .....N..........
|
||||
| 3536: 00 00 22 07 06 17 11 11 01 31 74 61 62 6c 65 74 .........1tablet
|
||||
| 3552: 32 74 32 07 43 52 45 41 54 45 20 54 41 42 4c 45 2t2.CREATE TABLE
|
||||
| 3568: 20 74 32 28 78 29 56 06 06 17 1f 1f 01 7d 74 61 t2(x)V.......ta
|
||||
| 3584: 62 6c 65 74 31 5f 63 6f 6e 66 69 67 74 31 5f 63 blet1_configt1_c
|
||||
| 3600: 6f 6e 66 69 67 06 43 52 45 41 54 45 20 54 41 42 onfig.CREATE TAB
|
||||
| 3616: 4c 45 20 27 74 31 5f 63 6f 6e 66 69 67 27 28 6b LE 't1_config'(k
|
||||
| 3632: 20 50 52 49 4d 41 52 59 20 4b 45 59 2c 20 76 29 PRIMARY KEY, v)
|
||||
| 3648: 20 57 49 54 48 4f 55 54 20 52 4f 57 49 44 5b 05 WITHOUT ROWID[.
|
||||
| 3664: 07 17 21 21 01 81 01 74 61 62 6c 65 74 31 5f 64 ..!!...tablet1_d
|
||||
| 3680: 6f 63 73 69 7a 65 74 31 5f 64 6f 63 73 69 7a 65 ocsizet1_docsize
|
||||
| 3696: 05 43 52 45 41 54 45 20 54 41 42 4c 45 20 27 74 .CREATE TABLE 't
|
||||
| 3712: 31 5f 64 6f 63 73 69 7a 65 27 28 69 64 20 49 4e 1_docsize'(id IN
|
||||
| 3728: 54 45 47 45 52 20 50 52 49 4d 41 52 59 20 4b 45 TEGER PRIMARY KE
|
||||
| 3744: 59 2c 20 73 7a 20 42 4c 4f 42 29 55 04 06 17 21 Y, sz BLOB)U...!
|
||||
| 3760: 21 01 77 74 61 62 6c 65 74 31 5f 63 6f 6e 74 65 !.wtablet1_conte
|
||||
| 3776: 6e 74 74 31 5f 63 6f 6e 74 65 6e 74 04 43 52 45 ntt1_content.CRE
|
||||
| 3792: 41 54 45 20 54 41 42 4c 45 20 27 74 31 5f 63 6f ATE TABLE 't1_co
|
||||
| 3808: 6e 74 65 6e 74 27 28 69 64 20 49 4e 54 45 47 45 ntent'(id INTEGE
|
||||
| 3824: 52 20 50 52 49 4d 41 52 59 20 4b 45 59 2c 20 63 R PRIMARY KEY, c
|
||||
| 3840: 30 29 69 03 07 17 19 19 01 81 2d 74 61 62 6c 65 0)i.......-table
|
||||
| 3856: 74 31 5f 69 64 78 74 31 5f 69 64 78 03 43 52 45 t1_idxt1_idx.CRE
|
||||
| 3872: 41 54 45 20 54 41 42 4c 45 20 27 74 31 5f 69 64 ATE TABLE 't1_id
|
||||
| 3888: 78 27 28 73 65 67 69 64 2c 20 74 65 72 6d 2c 20 x'(segid, term,
|
||||
| 3904: 70 67 6e 6f 2c 20 50 52 49 4d 41 52 59 20 4b 45 pgno, PRIMARY KE
|
||||
| 3920: 59 28 73 65 67 69 64 2c 20 74 65 72 6d 29 29 20 Y(segid, term))
|
||||
| 3936: 57 49 54 48 4f 55 54 20 52 4f 57 49 44 55 02 07 WITHOUT ROWIDU..
|
||||
| 3952: 17 1b 1b 01 81 01 74 61 62 6c 65 74 31 5f 64 61 ......tablet1_da
|
||||
| 3968: 74 61 74 31 5f 64 61 74 61 02 43 52 45 41 54 45 tat1_data.CREATE
|
||||
| 3984: 20 54 41 42 4c 45 20 27 74 31 5f 64 61 74 61 27 TABLE 't1_data'
|
||||
| 4000: 28 69 64 20 49 4e 54 45 47 45 52 20 50 52 49 4d (id INTEGER PRIM
|
||||
| 4016: 41 52 49 20 4b 45 59 2c 20 62 6c 6f 63 6b 20 42 ARI KEY, block B
|
||||
| 4032: 4c 4f 42 29 3a 01 06 17 11 11 08 63 74 61 62 6c LOB):......ctabl
|
||||
| 4048: 65 74 31 74 31 43 52 45 41 54 45 20 56 49 52 54 et1t1CREATE VIRT
|
||||
| 4064: 55 41 4c 20 54 41 42 4c 45 20 74 31 20 55 53 49 UAL TABLE t1 USI
|
||||
| 4080: 4e 47 20 66 74 73 35 28 63 6f 6e 74 65 6e 74 29 NG fts5(content)
|
||||
| page 2 offset 4096
|
||||
| 0: 0d 00 00 00 03 0f bd 00 0f e8 0f ef 0f bd 00 01 ................
|
||||
| 4016: 00 00 00 00 00 00 00 00 00 00 00 00 00 24 84 80 .............$..
|
||||
| 4032: 80 80 80 01 03 00 4e 00 00 00 1e 06 30 61 62 61 ......N.....0aba
|
||||
| 4048: 63 6b 01 02 02 04 02 66 74 02 02 02 04 04 6e 64 ck.....ft.....nd
|
||||
| 4064: 6f 6e 03 02 02 04 0a 07 05 01 03 00 10 03 03 0f on..............
|
||||
| 4080: 0a 03 00 24 00 00 00 00 01 01 01 00 01 00 01 01 ...$............
|
||||
| page 3 offset 8192
|
||||
| 0: 0a 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
|
||||
| 4080: 00 00 00 00 00 00 00 00 00 00 05 04 09 0c 01 02 ................
|
||||
| page 4 offset 12288
|
||||
| 0: 0d 00 00 00 03 0f e0 00 0f f6 0f ec 0f e0 00 00 ................
|
||||
| 4064: 0a 03 03 00 1b 61 62 61 6e 64 6f 6e 08 02 03 00 .....abandon....
|
||||
| 4080: 17 61 62 61 66 74 08 01 03 00 17 61 62 61 63 6b .abaft.....aback
|
||||
| page 5 offset 16384
|
||||
| 0: 0d 00 00 00 03 0f ee 00 0f fa 0f f4 0f ee 00 00 ................
|
||||
| 4064: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 04 03 ................
|
||||
| 4080: 03 00 0e 01 04 02 03 00 0e 01 04 01 03 00 0e 01 ................
|
||||
| page 6 offset 20480
|
||||
| 0: 0a 00 00 01 01 0f f4 00 0f f4 00 00 00 00 00 00 ................
|
||||
| 4080: 00 00 00 00 0b 03 1b 01 76 65 72 73 69 6f 6e 04 ........version.
|
||||
| page 7 offset 24576
|
||||
| 0: 0d 00 00 00 03 0f d6 00 0f f4 0f e1 0f d6 00 00 ................
|
||||
| 4048: 00 00 00 00 00 00 09 01 52 1b 72 65 62 75 69 6c ........R.rebuil
|
||||
| 4064: 64 11 02 02 2b 69 6e 74 65 67 72 69 74 79 2d 63 d...+integrity-c
|
||||
| 4080: 68 65 63 6b 0a 01 02 1d 6f 70 74 69 6d 69 7a 65 heck....optimize
|
||||
| end crash-37cecb4e784e9f.db
|
||||
}]} {}
|
||||
|
||||
do_catchsql_test 66.1 {
|
||||
INSERT INTO t1(t1) VALUES('integrity-check');
|
||||
} {1 {database disk image is malformed}}
|
||||
|
||||
|
||||
|
||||
sqlite3_fts5_may_be_corrupt 0
|
||||
|
||||
@@ -147,5 +147,27 @@ do_faultsim_test 5.1 -faults oom* -body {
|
||||
faultsim_test_result {0 {1 4}}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
# Test OOM injection in a query with two MATCH expressions
|
||||
#
|
||||
reset_db
|
||||
do_execsql_test 6.0 {
|
||||
CREATE VIRTUAL TABLE t1 USING fts5(a);
|
||||
INSERT INTO t1 VALUES('a b c d'); -- 1
|
||||
INSERT INTO t1 VALUES('d a b c'); -- 2
|
||||
INSERT INTO t1 VALUES('c d a b'); -- 3
|
||||
INSERT INTO t1 VALUES('b c d a'); -- 4
|
||||
}
|
||||
do_faultsim_test 6.1 -faults oom* -body {
|
||||
execsql { SELECT rowid FROM t1 WHERE t1 MATCH 'a' AND t1 MATCH 'b' }
|
||||
} -test {
|
||||
faultsim_test_result {0 {1 2 3 4}}
|
||||
}
|
||||
do_faultsim_test 6.2 -faults oom* -body {
|
||||
execsql { SELECT rowid FROM t1 WHERE t1 MATCH 'a OR b' AND t1 MATCH 'c OR d' }
|
||||
} -test {
|
||||
faultsim_test_result {0 {1 2 3 4}}
|
||||
}
|
||||
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -0,0 +1,99 @@
|
||||
# 2014 September 13
|
||||
#
|
||||
# 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 file implements regression tests for SQLite library. The
|
||||
# focus of this script is testing the FTS5 module.
|
||||
#
|
||||
|
||||
source [file join [file dirname [info script]] fts5_common.tcl]
|
||||
set testprefix fts5multi
|
||||
|
||||
# If SQLITE_ENABLE_FTS5 is not defined, omit this file.
|
||||
ifcapable !fts5 {
|
||||
finish_test
|
||||
return
|
||||
}
|
||||
|
||||
fts5_aux_test_functions db
|
||||
|
||||
do_execsql_test 1.0 {
|
||||
CREATE VIRTUAL TABLE t1 USING fts5(a, b, c);
|
||||
INSERT INTO t1 VALUES('gg bb bb' ,'gg ff gg' ,'ii ii');
|
||||
INSERT INTO t1 VALUES('dd dd hh kk','jj' ,'aa');
|
||||
INSERT INTO t1 VALUES('kk gg ee' ,'hh cc' ,'hh jj aa cc');
|
||||
INSERT INTO t1 VALUES('hh' ,'bb jj cc' ,'kk ii');
|
||||
INSERT INTO t1 VALUES('kk dd kk ii','aa ee aa' ,'ee');
|
||||
INSERT INTO t1 VALUES('ee' ,'ff gg kk aa','ee ff ee');
|
||||
INSERT INTO t1 VALUES('ff jj' ,'gg ee' ,'kk ee gg kk');
|
||||
INSERT INTO t1 VALUES('ff ee dd hh','kk ee' ,'gg dd');
|
||||
INSERT INTO t1 VALUES('bb' ,'aa' ,'bb aa');
|
||||
INSERT INTO t1 VALUES('hh cc bb' ,'ff bb' ,'cc');
|
||||
INSERT INTO t1 VALUES('jj' ,'ff dd bb aa','dd dd ff ff');
|
||||
INSERT INTO t1 VALUES('ff dd gg dd','gg aa bb ff','cc');
|
||||
INSERT INTO t1 VALUES('ff aa cc jj','kk' ,'ii dd');
|
||||
INSERT INTO t1 VALUES('jj dd' ,'cc' ,'ii hh ee aa');
|
||||
INSERT INTO t1 VALUES('ff ii hh' ,'dd' ,'gg');
|
||||
INSERT INTO t1 VALUES('ff dd gg hh','hh' ,'ff dd');
|
||||
INSERT INTO t1 VALUES('cc cc' ,'ff dd ff' ,'bb');
|
||||
INSERT INTO t1 VALUES('ii' ,'bb ii' ,'jj kk');
|
||||
INSERT INTO t1 VALUES('ff hh' ,'hh bb' ,'bb dd ee');
|
||||
INSERT INTO t1 VALUES('jj kk' ,'jj' ,'gg ff cc');
|
||||
INSERT INTO t1 VALUES('dd kk' ,'ii gg' ,'dd');
|
||||
INSERT INTO t1 VALUES('cc' ,'aa ff' ,'ii');
|
||||
INSERT INTO t1 VALUES('bb ff bb ii','bb kk bb aa','hh ff ii dd');
|
||||
INSERT INTO t1 VALUES('aa' ,'ee bb jj jj','dd');
|
||||
INSERT INTO t1 VALUES('kk dd cc' ,'aa jj' ,'ee aa ff');
|
||||
INSERT INTO t1 VALUES('aa gg aa' ,'jj' ,'ii kk hh gg');
|
||||
INSERT INTO t1 VALUES('ff hh aa' ,'jj ii' ,'hh dd bb jj');
|
||||
INSERT INTO t1 VALUES('hh' ,'aa gg kk' ,'bb ee');
|
||||
INSERT INTO t1 VALUES('bb' ,'ee' ,'gg');
|
||||
INSERT INTO t1 VALUES('dd kk' ,'kk bb aa' ,'ee');
|
||||
}
|
||||
|
||||
foreach {tn c1 e1 c2 e2} {
|
||||
1 t1 aa t1 bb
|
||||
2 a aa b bb
|
||||
3 a "aa OR bb OR cc" b "jj OR ii OR hh"
|
||||
4 t1 "aa AND bb" t1 "cc"
|
||||
5 c "kk" b "aa OR bb OR cc OR dd OR ee"
|
||||
} {
|
||||
if {$c1=="t1"} {
|
||||
set lhs "( $e1 )"
|
||||
} else {
|
||||
set lhs "$c1 : ( $e1 )"
|
||||
}
|
||||
if {$c2=="t1"} {
|
||||
set rhs "( $e2 )"
|
||||
} else {
|
||||
set rhs "$c2 : ( $e2 )"
|
||||
}
|
||||
|
||||
set q1 "t1 MATCH '($lhs) AND ($rhs)'"
|
||||
set q2 "$c1 MATCH '$e1' AND $c2 MATCH '$e2'"
|
||||
|
||||
set ret [execsql "SELECT rowid FROM t1 WHERE $q1"]
|
||||
set N [llength $ret]
|
||||
do_execsql_test 1.$tn.1.($N) "SELECT rowid FROM t1 WHERE $q2" $ret
|
||||
|
||||
set ret [execsql "SELECT fts5_test_poslist(t1) FROM t1 WHERE $q1"]
|
||||
do_execsql_test 1.$tn.2.($N) "
|
||||
SELECT fts5_test_poslist(t1) FROM t1 WHERE $q2
|
||||
" $ret
|
||||
}
|
||||
|
||||
do_catchsql_test 2.1.1 {
|
||||
SELECT rowid FROM t1 WHERE t1 MATCH '(NOT' AND t1 MATCH 'aa bb';
|
||||
} {1 {fts5: syntax error near "NOT"}}
|
||||
do_catchsql_test 2.1.2 {
|
||||
SELECT rowid FROM t1 WHERE t1 MATCH 'aa bb' AND t1 MATCH '(NOT';
|
||||
} {1 {fts5: syntax error near "NOT"}}
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -31,7 +31,7 @@ do_eqp_test 1.1 {
|
||||
} {
|
||||
QUERY PLAN
|
||||
|--SCAN TABLE t1
|
||||
`--SCAN TABLE f1 VIRTUAL TABLE INDEX 65537:
|
||||
`--SCAN TABLE f1 VIRTUAL TABLE INDEX 0:m
|
||||
}
|
||||
|
||||
do_eqp_test 1.2 {
|
||||
@@ -46,7 +46,7 @@ do_eqp_test 1.3 {
|
||||
SELECT * FROM f1 WHERE f1 MATCH ? ORDER BY ff
|
||||
} {
|
||||
QUERY PLAN
|
||||
|--SCAN TABLE f1 VIRTUAL TABLE INDEX 65537:
|
||||
|--SCAN TABLE f1 VIRTUAL TABLE INDEX 0:m
|
||||
`--USE TEMP B-TREE FOR ORDER BY
|
||||
}
|
||||
|
||||
@@ -60,6 +60,6 @@ do_eqp_test 1.4 {
|
||||
|
||||
do_eqp_test 1.5 {
|
||||
SELECT * FROM f1 WHERE rank MATCH ?
|
||||
} {SCAN TABLE f1 VIRTUAL TABLE INDEX 2:}
|
||||
} {SCAN TABLE f1 VIRTUAL TABLE INDEX 0:r}
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -467,4 +467,17 @@ do_execsql_test 21.3 {
|
||||
SELECT rowid FROM x1($doc);
|
||||
} {11112}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
do_execsql_test 22.0 {
|
||||
CREATE VIRTUAL TABLE x1 USING fts5(x);
|
||||
INSERT INTO x1(x) VALUES('a b c');
|
||||
INSERT INTO x1(x) VALUES('x y z');
|
||||
INSERT INTO x1(x) VALUES('c b a');
|
||||
INSERT INTO x1(x) VALUES('z y x');
|
||||
}
|
||||
|
||||
do_catchsql_test 22.1 {SELECT * FROM x1('')} {1 {fts5: syntax error near ""}}
|
||||
do_catchsql_test 22.2 {SELECT * FROM x1(NULL)} {1 {fts5: syntax error near ""}}
|
||||
|
||||
finish_test
|
||||
|
||||
+1
-1
@@ -24,7 +24,7 @@
|
||||
**
|
||||
** static int aX[] = { 53, 9, 17, 2231, 4, 99 };
|
||||
** int i = sqlite3_bind_parameter_index(pStmt, "$ptr");
|
||||
** sqlite3_bind_value(pStmt, i, aX, "carray", 0);
|
||||
** sqlite3_bind_pointer(pStmt, i, aX, "carray", 0);
|
||||
**
|
||||
** There is an optional third parameter to determine the datatype of
|
||||
** the C-language array. Allowed values of the third parameter are
|
||||
|
||||
+17
-9
@@ -1820,7 +1820,7 @@ static void jsonArrayStep(
|
||||
if( pStr->zBuf==0 ){
|
||||
jsonInit(pStr, ctx);
|
||||
jsonAppendChar(pStr, '[');
|
||||
}else{
|
||||
}else if( pStr->nUsed>1 ){
|
||||
jsonAppendChar(pStr, ',');
|
||||
pStr->pCtx = ctx;
|
||||
}
|
||||
@@ -1868,9 +1868,11 @@ static void jsonGroupInverse(
|
||||
int argc,
|
||||
sqlite3_value **argv
|
||||
){
|
||||
int i;
|
||||
unsigned int i;
|
||||
int inStr = 0;
|
||||
int nNest = 0;
|
||||
char *z;
|
||||
char c;
|
||||
JsonString *pStr;
|
||||
UNUSED_PARAM(argc);
|
||||
UNUSED_PARAM(argv);
|
||||
@@ -1881,12 +1883,18 @@ static void jsonGroupInverse(
|
||||
if( NEVER(!pStr) ) return;
|
||||
#endif
|
||||
z = pStr->zBuf;
|
||||
for(i=1; z[i]!=',' || inStr; i++){
|
||||
assert( i<pStr->nUsed );
|
||||
if( z[i]=='"' ){
|
||||
for(i=1; (c = z[i])!=',' || inStr || nNest; i++){
|
||||
if( i>=pStr->nUsed ){
|
||||
pStr->nUsed = 1;
|
||||
return;
|
||||
}
|
||||
if( c=='"' ){
|
||||
inStr = !inStr;
|
||||
}else if( z[i]=='\\' ){
|
||||
}else if( c=='\\' ){
|
||||
i++;
|
||||
}else if( !inStr ){
|
||||
if( c=='{' || c=='[' ) nNest++;
|
||||
if( c=='}' || c==']' ) nNest--;
|
||||
}
|
||||
}
|
||||
pStr->nUsed -= i;
|
||||
@@ -1916,7 +1924,7 @@ static void jsonObjectStep(
|
||||
if( pStr->zBuf==0 ){
|
||||
jsonInit(pStr, ctx);
|
||||
jsonAppendChar(pStr, '{');
|
||||
}else{
|
||||
}else if( pStr->nUsed>1 ){
|
||||
jsonAppendChar(pStr, ',');
|
||||
pStr->pCtx = ctx;
|
||||
}
|
||||
@@ -2504,14 +2512,14 @@ int sqlite3Json1Init(sqlite3 *db){
|
||||
#endif
|
||||
for(i=0; i<sizeof(aFunc)/sizeof(aFunc[0]) && rc==SQLITE_OK; i++){
|
||||
rc = sqlite3_create_function(db, aFunc[i].zName, aFunc[i].nArg,
|
||||
SQLITE_UTF8 | SQLITE_DETERMINISTIC,
|
||||
SQLITE_UTF8 | SQLITE_DETERMINISTIC,
|
||||
(void*)&aFunc[i].flag,
|
||||
aFunc[i].xFunc, 0, 0);
|
||||
}
|
||||
#ifndef SQLITE_OMIT_WINDOWFUNC
|
||||
for(i=0; i<sizeof(aAgg)/sizeof(aAgg[0]) && rc==SQLITE_OK; i++){
|
||||
rc = sqlite3_create_window_function(db, aAgg[i].zName, aAgg[i].nArg,
|
||||
SQLITE_UTF8 | SQLITE_DETERMINISTIC, 0,
|
||||
SQLITE_SUBTYPE | SQLITE_UTF8 | SQLITE_DETERMINISTIC, 0,
|
||||
aAgg[i].xStep, aAgg[i].xFinal,
|
||||
aAgg[i].xValue, jsonGroupInverse, 0);
|
||||
}
|
||||
|
||||
@@ -0,0 +1,165 @@
|
||||
# 2014 August 30
|
||||
#
|
||||
# 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.
|
||||
#
|
||||
#***********************************************************************
|
||||
#
|
||||
|
||||
source [file join [file dirname [info script]] rbu_common.tcl]
|
||||
set ::testprefix rbu1
|
||||
|
||||
forcedelete test.db2
|
||||
do_execsql_test 1.0 {
|
||||
CREATE TABLE t1(a INTEGER, b, c, PRIMARY KEY(a));
|
||||
CREATE INDEX t1b ON t1(b); -- root=3
|
||||
CREATE INDEX t1c ON t1(c); -- root=4
|
||||
|
||||
ATTACH 'test.db2' AS 'rbu';
|
||||
CREATE TABLE rbu.data_t1(a, b, c, rbu_control);
|
||||
INSERT INTO data_t1 VALUES(1, 1, 1, 0);
|
||||
INSERT INTO data_t1 VALUES(2, 2, 2, 0);
|
||||
INSERT INTO data_t1 VALUES(3, 3, 3, 0);
|
||||
}
|
||||
|
||||
do_test 1.1 {
|
||||
sqlite3_test_control SQLITE_TESTCTRL_IMPOSTER db main 1 3
|
||||
execsql {
|
||||
CREATE TABLE imp1(b, id, PRIMARY KEY(b, id)) WITHOUT ROWID;
|
||||
INSERT INTO imp1 VALUES(2, 2);
|
||||
}
|
||||
sqlite3_test_control SQLITE_TESTCTRL_IMPOSTER db main 0 3
|
||||
} {}
|
||||
|
||||
db close
|
||||
sqlite3 db test.db
|
||||
|
||||
do_test 1.2 {
|
||||
sqlite3_test_control SQLITE_TESTCTRL_IMPOSTER db main 1 4
|
||||
execsql {
|
||||
CREATE TABLE imp1(b, id, PRIMARY KEY(b, id)) WITHOUT ROWID;
|
||||
INSERT INTO imp1 VALUES(3, 3);
|
||||
}
|
||||
sqlite3_test_control SQLITE_TESTCTRL_IMPOSTER db main 0 4
|
||||
} {}
|
||||
db close
|
||||
db_save
|
||||
|
||||
sqlite3 db test.db
|
||||
do_catchsql_test 1.3 { PRAGMA integrity_check } {0 {{wrong # of entries in index t1c} {wrong # of entries in index t1b}}}
|
||||
db close
|
||||
|
||||
do_test 1.4 {
|
||||
sqlite3rbu rbu test.db test.db2
|
||||
while 1 {
|
||||
set rc [rbu step]
|
||||
if {$rc!="SQLITE_OK"} break
|
||||
}
|
||||
list [catch { rbu close } msg] $msg
|
||||
} {1 {SQLITE_CONSTRAINT - UNIQUE constraint failed: t1.b, t1.a}}
|
||||
|
||||
db_restore
|
||||
sqlite3 db test.db2
|
||||
do_execsql_test 1.5 {
|
||||
PRAGMA writable_schema = 1;
|
||||
CREATE TABLE sqlite_rbu_replace_hack('v');
|
||||
}
|
||||
db close
|
||||
|
||||
do_test 1.6 {
|
||||
sqlite3rbu rbu test.db test.db2
|
||||
while 1 {
|
||||
set rc [rbu step]
|
||||
if {$rc!="SQLITE_OK"} break
|
||||
}
|
||||
list [catch { rbu close } msg] $msg
|
||||
} {0 SQLITE_DONE}
|
||||
|
||||
sqlite3 db test.db
|
||||
do_execsql_test 1.7 {
|
||||
PRAGMA integrity_check;
|
||||
SELECT count(*) FROM t1;
|
||||
} {ok 3}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
|
||||
reset_db
|
||||
forcedelete test.db2
|
||||
do_execsql_test 2.0 {
|
||||
CREATE TABLE t1(a, b, c, PRIMARY KEY(a, b));
|
||||
CREATE INDEX t1c ON t1(c); -- root=4
|
||||
|
||||
ATTACH 'test.db2' AS 'rbu';
|
||||
CREATE TABLE rbu.data_t1(a, b, c, rbu_control);
|
||||
INSERT INTO data_t1 VALUES(1, 1, 1, 0);
|
||||
INSERT INTO data_t1 VALUES(2, 2, 2, 0);
|
||||
INSERT INTO data_t1 VALUES(3, 3, 3, 0);
|
||||
}
|
||||
|
||||
do_test 2.1 {
|
||||
sqlite3_test_control SQLITE_TESTCTRL_IMPOSTER db main 1 3
|
||||
execsql {
|
||||
CREATE TABLE imp1(a, b, id, PRIMARY KEY(b, id)) WITHOUT ROWID;
|
||||
INSERT INTO imp1 VALUES(2, 2, 2);
|
||||
}
|
||||
sqlite3_test_control SQLITE_TESTCTRL_IMPOSTER db main 0 3
|
||||
} {}
|
||||
|
||||
db close
|
||||
sqlite3 db test.db
|
||||
|
||||
do_test 2.2 {
|
||||
sqlite3_test_control SQLITE_TESTCTRL_IMPOSTER db main 1 4
|
||||
execsql {
|
||||
CREATE TABLE imp1(c, id, PRIMARY KEY(c, id)) WITHOUT ROWID;
|
||||
INSERT INTO imp1 VALUES(3, 3);
|
||||
}
|
||||
sqlite3_test_control SQLITE_TESTCTRL_IMPOSTER db main 0 4
|
||||
} {}
|
||||
db close
|
||||
db_save
|
||||
|
||||
sqlite3 db test.db
|
||||
do_catchsql_test 2.3 { PRAGMA integrity_check } {0 {{wrong # of entries in index t1c} {wrong # of entries in index sqlite_autoindex_t1_1}}}
|
||||
db close
|
||||
|
||||
do_test 2.4 {
|
||||
sqlite3rbu rbu test.db test.db2
|
||||
while 1 {
|
||||
set rc [rbu step]
|
||||
if {$rc!="SQLITE_OK"} break
|
||||
}
|
||||
list [catch { rbu close } msg] $msg
|
||||
} {1 {SQLITE_CONSTRAINT - UNIQUE constraint failed: t1.a, t1.b}}
|
||||
|
||||
db_restore
|
||||
sqlite3 db test.db2
|
||||
do_execsql_test 2.5 {
|
||||
PRAGMA writable_schema = 1;
|
||||
CREATE TABLE sqlite_rbu_replace_hack('v');
|
||||
}
|
||||
db close
|
||||
|
||||
do_test 2.6 {
|
||||
sqlite3rbu rbu test.db test.db2
|
||||
while 1 {
|
||||
set rc [rbu step]
|
||||
if {$rc!="SQLITE_OK"} break
|
||||
}
|
||||
list [catch { rbu close } msg] $msg
|
||||
} {0 SQLITE_DONE}
|
||||
|
||||
sqlite3 db test.db
|
||||
do_execsql_test 2.7 {
|
||||
PRAGMA integrity_check;
|
||||
SELECT count(*) FROM t1;
|
||||
} {ok 3}
|
||||
|
||||
|
||||
|
||||
finish_test
|
||||
|
||||
+28
-3
@@ -103,6 +103,8 @@
|
||||
# define RBU_ENABLE_DELTA_CKSUM 0
|
||||
#endif
|
||||
|
||||
#define RBU_REPLACE_HACK_TABLE "sqlite_rbu_replace_hack"
|
||||
|
||||
/*
|
||||
** Swap two objects of type TYPE.
|
||||
*/
|
||||
@@ -376,6 +378,7 @@ struct sqlite3rbu {
|
||||
char *zRbu; /* Path to rbu db */
|
||||
char *zState; /* Path to state db (or NULL if zRbu) */
|
||||
char zStateDb[5]; /* Db name for state ("stat" or "main") */
|
||||
int bRbuReplaceHack; /* Do the REPLACE hack */
|
||||
int rc; /* Value returned by last rbu_step() call */
|
||||
char *zErrmsg; /* Error message if rc!=SQLITE_OK */
|
||||
int nStep; /* Rows processed for current object */
|
||||
@@ -2350,7 +2353,10 @@ static int rbuObjIterPrepareAll(
|
||||
if( p->rc==SQLITE_OK ){
|
||||
p->rc = prepareFreeAndCollectError(
|
||||
p->dbMain, &pIter->pInsert, &p->zErrmsg,
|
||||
sqlite3_mprintf("INSERT INTO \"rbu_imp_%w\" VALUES(%s)", zTbl, zBind)
|
||||
sqlite3_mprintf("%s INTO \"rbu_imp_%w\" VALUES(%s)",
|
||||
p->bRbuReplaceHack ? "REPLACE" : "INSERT",
|
||||
zTbl, zBind
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
@@ -2442,7 +2448,8 @@ static int rbuObjIterPrepareAll(
|
||||
if( p->rc==SQLITE_OK ){
|
||||
p->rc = prepareFreeAndCollectError(p->dbMain, &pIter->pInsert, pz,
|
||||
sqlite3_mprintf(
|
||||
"INSERT INTO \"%s%w\"(%s%s) VALUES(%s)",
|
||||
"%s INTO \"%s%w\"(%s%s) VALUES(%s)",
|
||||
p->bRbuReplaceHack ? "REPLACE" : "INSERT",
|
||||
zWrite, zTbl, zCollist, (bRbuRowid ? ", _rowid_" : ""), zBindings
|
||||
)
|
||||
);
|
||||
@@ -2725,7 +2732,7 @@ static RbuState *rbuLoadState(sqlite3rbu *p){
|
||||
break;
|
||||
|
||||
case RBU_STATE_OALSZ:
|
||||
pRet->iOalSz = (u32)sqlite3_column_int64(pStmt, 1);
|
||||
pRet->iOalSz = sqlite3_column_int64(pStmt, 1);
|
||||
break;
|
||||
|
||||
case RBU_STATE_PHASEONESTEP:
|
||||
@@ -2744,6 +2751,24 @@ static RbuState *rbuLoadState(sqlite3rbu *p){
|
||||
rc2 = sqlite3_finalize(pStmt);
|
||||
if( rc==SQLITE_OK ) rc = rc2;
|
||||
|
||||
/* If this is not a vacuum operation, search for the special table
|
||||
** "sqlite_rbu_replace_hack". Set the flag if it is found.
|
||||
*/
|
||||
if( rc==SQLITE_OK && !rbuIsVacuum(p) ){
|
||||
sqlite3_stmt *pQuery = 0;
|
||||
rc = prepareFreeAndCollectError(p->dbRbu, &pQuery, &p->zErrmsg,
|
||||
sqlite3_mprintf("SELECT 1 FROM main.sqlite_master WHERE name='%s'",
|
||||
RBU_REPLACE_HACK_TABLE
|
||||
)
|
||||
);
|
||||
if( rc==SQLITE_OK ){
|
||||
if( sqlite3_step(pQuery)==SQLITE_ROW ){
|
||||
p->bRbuReplaceHack = 1;
|
||||
}
|
||||
rc = sqlite3_finalize(pQuery);
|
||||
}
|
||||
}
|
||||
|
||||
p->rc = rc;
|
||||
return pRet;
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
C Ensure\sthe\scolumns\sof\sviews\sand\ssub-selects\sin\sthe\sFROM\sclause\sof\sa\sselect\sare\salways\sassigned\simplicit\scollation\ssequences,\sjust\sas\stable\scolumns\sare.\sPossible\sfix\sfor\s[a7debbe0].
|
||||
D 2019-09-09T19:49:42.715
|
||||
C Fix\san\sRBU\sproblem\swith\srestarting\san\supdate\safter\sthe\s*-oal\sfile\sis\salready\slarger\sthan\s4GiB.
|
||||
D 2021-08-11T18:56:49.597
|
||||
F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
|
||||
F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
|
||||
F LICENSE.md df5091916dbb40e6e9686186587125e1b2ff51f022cc334e886c19a0e9982724
|
||||
@@ -81,7 +81,7 @@ F ext/fts3/README.content fdc666a70d5257a64fee209f97cf89e0e6e32b51
|
||||
F ext/fts3/README.syntax a19711dc5458c20734b8e485e75fb1981ec2427a
|
||||
F ext/fts3/README.tokenizers b92bdeb8b46503f0dd301d364efc5ef59ef9fa8e2758b8e742f39fa93a2e422d
|
||||
F ext/fts3/README.txt 8c18f41574404623b76917b9da66fcb0ab38328d
|
||||
F ext/fts3/fts3.c 33958a8c05a6c22bf559fedb1176ad1f313a7b42ccf5f0c0bcc8a88609e58d60
|
||||
F ext/fts3/fts3.c a01da95e840a6ddb14d0a14b35c9017a8b034b08511ca97af716f00df102fb3f
|
||||
F ext/fts3/fts3.h 3a10a0af180d502cecc50df77b1b22df142817fe
|
||||
F ext/fts3/fts3Int.h 74384e28b778a057f1467529715668b98f3f12f52eeb564fd6ae1e894125c00c
|
||||
F ext/fts3/fts3_aux.c 96708c8b3a7d9b8ca1b68ea2b7e503e283f20e95f145becadedfad096dbd0f34
|
||||
@@ -99,7 +99,7 @@ F ext/fts3/fts3_tokenizer.h 64c6ef6c5272c51ebe60fc607a896e84288fcbc3
|
||||
F ext/fts3/fts3_tokenizer1.c 5c98225a53705e5ee34824087478cf477bdb7004
|
||||
F ext/fts3/fts3_unicode.c 4b9af6151c29b35ed09574937083cece7c31e911f69615e168a39677569b684d
|
||||
F ext/fts3/fts3_unicode2.c 416eb7e1e81142703520d284b768ca2751d40e31fa912cae24ba74860532bf0f
|
||||
F ext/fts3/fts3_write.c 6efc4cd7dc554df06c35bfd3335503838645806a78fc33137a55eb97a8b2f3b2
|
||||
F ext/fts3/fts3_write.c 13582783abedf905e6946ce95edff7103c07810fb03a9c3b40212d21a3efa09c
|
||||
F ext/fts3/fts3speed.tcl b54caf6a18d38174f1a6e84219950d85e98bb1e9
|
||||
F ext/fts3/mkfts3amal.tcl 252ecb7fe6467854f2aa237bf2c390b74e71f100
|
||||
F ext/fts3/tool/fts3cov.sh c331d006359456cf6f8f953e37f2b9c7d568f3863f00bb5f7eb87fea4ac01b73
|
||||
@@ -110,14 +110,14 @@ F ext/fts3/unicode/mkunicode.tcl bf7fcaa6d68e6d38223467983785d054f1cff4d9e3905dd
|
||||
F ext/fts3/unicode/parseunicode.tcl a981bd6466d12dd17967515801c3ff23f74a281be1a03cf1e6f52a6959fc77eb
|
||||
F ext/fts5/extract_api_docs.tcl a36e54ec777172ddd3f9a88daf593b00848368e0
|
||||
F ext/fts5/fts5.h 7c9da96f2b9dcfa4dd94081fb2d87ec418d8cdb35b25df56756c334b6b558fd7
|
||||
F ext/fts5/fts5Int.h d87fb17d12296613cdec2d1f4213ecd8840d3deb34837b6d3889b830d06baac4
|
||||
F ext/fts5/fts5Int.h 0ec19a906a54c0e53f8a380c0ff70f11a866aa259490bc13aa39f8d2491800fd
|
||||
F ext/fts5/fts5_aux.c dcc627d8b6e3fc773db528ff67b39955dab7b51628f9dba8e15849e5bedfd7fa
|
||||
F ext/fts5/fts5_buffer.c 5a5fe0159752c0fb0a5a93c722e9db2662822709490769d482b76a6dc8aaca70
|
||||
F ext/fts5/fts5_config.c d7523cba5e66da077233c023aecbc3e6a37978ff75a18131c5ab5b1229d5bac7
|
||||
F ext/fts5/fts5_expr.c 840c88d55e78083a5e61a35968df877712ae28791b347eced1e98e3b337d2d3c
|
||||
F ext/fts5/fts5_config.c 606a29f2962a8f4508923e6ad833974b32a3ab4093f63fd6de0fb33a87eed54c
|
||||
F ext/fts5/fts5_expr.c 5661fe64f4f5a499710df9561075de84b743f01e808af46df4130a9ec343a0fd
|
||||
F ext/fts5/fts5_hash.c 1cc0095646f5f3b46721aa112fb4f9bf29ae175cb5338f89dcec66ed97acfe75
|
||||
F ext/fts5/fts5_index.c b062bdb836e195656aac8d6684e943585cff4bf7d7c593c80cb67c3b6cfef7ee
|
||||
F ext/fts5/fts5_main.c 15dc14ea594ff2ea183f5e79c8f6fea14640ac7c4bd5d93ad1d506a4db80c998
|
||||
F ext/fts5/fts5_index.c 6601d085d8e8cf4750ee49e2e1d18907582cc0aab78233d3b21bc240ba76a199
|
||||
F ext/fts5/fts5_main.c bf637030722badf06667d28f7159e4c209dbafd7aa76c33f387104b78ad147e1
|
||||
F ext/fts5/fts5_storage.c 801b4e3cd33786a60a07b6b01f86d0fbdf7e68325054e08d17176293a8081e99
|
||||
F ext/fts5/fts5_tcl.c 39bcbae507f594aad778172fa914cad0f585bf92fd3b078c686e249282db0d95
|
||||
F ext/fts5/fts5_test_mi.c 08c11ec968148d4cb4119d96d819f8c1f329812c568bac3684f5464be177d3ee
|
||||
@@ -157,7 +157,7 @@ F ext/fts5/test/fts5connect.test 08030168fc96fc278fa81f28654fb7e90566f33aff269c0
|
||||
F ext/fts5/test/fts5content.test 9517cc527a8e8a33949652d5c7b5e251f8c3d5ae3f23f01d4320e30f29a0336b
|
||||
F ext/fts5/test/fts5corrupt.test 77ae6f41a7eba10620efb921cf7dbe218b0ef232b04519deb43581cb17a57ebe
|
||||
F ext/fts5/test/fts5corrupt2.test 7453752ba12ce91690c469a6449d412561cc604b1dec994e16ab132952e7805f
|
||||
F ext/fts5/test/fts5corrupt3.test f326d70e08acffcbd8a551edd72b5723db7d3a902d288d958014c81a111cae21
|
||||
F ext/fts5/test/fts5corrupt3.test e188a43cecb3ff53b6236f862f82b2ec36962b9e39f20cb620dfa07aed70afa4
|
||||
F ext/fts5/test/fts5corrupt4.test ea805c4d7c68b5f185b9db5d2060a7ae5875339738dd48203c92162f41e7ca91
|
||||
F ext/fts5/test/fts5delete.test cbf87e3b8867c4d5cfcaed975c7475fd3f99d072bce2075fcedf43d1f82af775
|
||||
F ext/fts5/test/fts5detail.test 31b240dbf6d44ac3507e2f8b65f29fdc12465ffd531212378c7ce1066766f54e
|
||||
@@ -176,7 +176,7 @@ F ext/fts5/test/fts5fault7.test 0acbec416edb24b8881f154e99c31e9ccf73f539cfcd1640
|
||||
F ext/fts5/test/fts5fault8.test 318238659d35f82ad215ecb57ca4c87486ea85d45dbeedaee42f148ff5105ee2
|
||||
F ext/fts5/test/fts5fault9.test 098e6b894bbdf9b2192f994a30f4043673fb3f338b6b8ab1624c704422f39119
|
||||
F ext/fts5/test/fts5faultA.test be4487576bff8c22cee6597d1893b312f306504a8c6ccd3c53ca85af12290c8c
|
||||
F ext/fts5/test/fts5faultB.test e6d04f9ea7b21be1d89abb8df2cb4baf65b0453b744d5a805fcd3ef45ff86a7e
|
||||
F ext/fts5/test/fts5faultB.test d606bdb8e81aaeb6f41de3fc9fc7ae315733f0903fbff05cf54f5b045b729ab5
|
||||
F ext/fts5/test/fts5faultD.test cc5d1225556e356615e719c612e845d41bff7d5a
|
||||
F ext/fts5/test/fts5first.test 3fcf2365c00a15fc9704233674789a3b95131d12de18a9b996159f6909dc8079
|
||||
F ext/fts5/test/fts5full.test 49b565da02918c06e58f51f0b953b0302b96f155aa68baba24782b81570685e2
|
||||
@@ -190,12 +190,13 @@ F ext/fts5/test/fts5matchinfo.test 79129ff6c9a2d86943b287a5a8caa7ee639f6dcf004d8
|
||||
F ext/fts5/test/fts5merge.test e92a8db28b45931e7a9c7b1bbd36101692759d00274df74d83fd29d25d53b3a6
|
||||
F ext/fts5/test/fts5merge2.test 3ebad1a59d6ad3fb66eff6523a09e95dc6367cbefb3cd73196801dea0425c8e2
|
||||
F ext/fts5/test/fts5misc.test 5becd134b66f7370042968a2b127b92ea7748e249f16cb6a996f450812e89eec
|
||||
F ext/fts5/test/fts5multi.test a15bc91cdb717492e6e1b66fec1c356cb57386b980c7ba5af1915f97fe878581
|
||||
F ext/fts5/test/fts5multiclient.test 5ff811c028d6108045ffef737f1e9f05028af2458e456c0937c1d1b8dea56d45
|
||||
F ext/fts5/test/fts5near.test 211477940142d733ac04fad97cb24095513ab2507073a99c2765c3ddd2ef58bd
|
||||
F ext/fts5/test/fts5onepass.test f9b7d9b2c334900c6542a869760290e2ab5382af8fbd618834bf1fcc3e7b84da
|
||||
F ext/fts5/test/fts5optimize.test 36a752d24c818792032e4ff502936fc9cc5ef938721696396fdc79214b2717f1
|
||||
F ext/fts5/test/fts5phrase.test 13e5d8e9083077b3d9c74315b3c92ec723cc6eb37c8155e0bfe1bba00559f07b
|
||||
F ext/fts5/test/fts5plan.test 00dc4c974938b509db7cb3680407f068ee6e9cc824f492f68cb741a7b679fe41
|
||||
F ext/fts5/test/fts5plan.test 771b999d161e24fd803ce0290adb7c6e7c9b9cc2c6a0adb344813fb89473aa32
|
||||
F ext/fts5/test/fts5porter.test 8d08010c28527db66bc3feebd2b8767504aaeb9b101a986342fa7833d49d0d15
|
||||
F ext/fts5/test/fts5porter2.test 0d251a673f02fa13ca7f011654873b3add20745f7402f108600a23e52d8c7457
|
||||
F ext/fts5/test/fts5prefix.test a0fa67b06650f2deaa7bf27745899d94e0fb547ad9ecbd08bfad98c04912c056
|
||||
@@ -204,7 +205,7 @@ F ext/fts5/test/fts5rank.test c9fd4a1e36b4fa92d572ec13d846469b97da249d1c2f7fd3ee
|
||||
F ext/fts5/test/fts5rebuild.test 55d6f17715cddbf825680dd6551efbc72ed916d8cf1cde40a46fc5d785b451e7
|
||||
F ext/fts5/test/fts5restart.test 835ecc8f449e3919f72509ab58056d0cedca40d1fe04108ccf8ac4c2ba41f415
|
||||
F ext/fts5/test/fts5rowid.test b8790ec170a8dc1942a15aef3db926a5f3061b1ff171013003d8297203a20ad6
|
||||
F ext/fts5/test/fts5simple.test 313ad28ef38ebe25f0a1673dd18f2fac446e25feb15bbb0c223a65ea00594f72
|
||||
F ext/fts5/test/fts5simple.test a298670508c1458b88ce6030440f26a30673931884eb5f4094ac1773b3ba217b
|
||||
F ext/fts5/test/fts5simple2.test 258a1b0c590409bfa5271e872c79572b319d2a56554d0585f68f146a0da603f0
|
||||
F ext/fts5/test/fts5simple3.test d5c74a9d3ca71bd5dd5cacb7c55b86ea12cdddfc8b1910e3de2995206898380f
|
||||
F ext/fts5/test/fts5synonym.test 1651815b8008de170e8e600dcacc17521d765482ea8f074ae82cfa870d8bb7fb
|
||||
@@ -281,7 +282,7 @@ F ext/misc/anycollseq.c 5ffdfde9829eeac52219136ad6aa7cd9a4edb3b15f4f2532de52f4a2
|
||||
F ext/misc/appendvfs.c 3777f22ec1057dc4e5fd89f2fbddcc7a29fbeef1ad038c736c54411bb1967af7
|
||||
F ext/misc/blobio.c a867c4c4617f6ec223a307ebfe0eabb45e0992f74dd47722b96f3e631c0edb2a
|
||||
F ext/misc/btreeinfo.c 4f0ebf278f46e68e6306c667917766cebc5550fd35d5de17847988e22892d4d2
|
||||
F ext/misc/carray.c ed96c218ea940b85c9a274c4d9c59fe9491c299147a38a8bba537687bd6c6005
|
||||
F ext/misc/carray.c 91e9a7f512fda934894bed30464552fffa7d3073b5be04189ae0bd0c59f26bfd
|
||||
F ext/misc/closure.c dbfd8543b2a017ae6b1a5843986b22ddf99ff126ec9634a2f4047cd14c85c243
|
||||
F ext/misc/completion.c cec672d40604075bb341a7f11ac48393efdcd90a979269b8fe7977ea62d0547f
|
||||
F ext/misc/compress.c dd4f8a6d0baccff3c694757db5b430f3bbd821d8686d1fc24df55cf9f035b189
|
||||
@@ -294,7 +295,7 @@ F ext/misc/fileio.c 288e7230e0fe464d71b0694e2d8bdd3a353118ac2e31da3964b95f460f09
|
||||
F ext/misc/fossildelta.c 7708651072eb5620ab21bbfb518d184f27b2c29c0131b09b9a2d8852a8016430
|
||||
F ext/misc/fuzzer.c c4e27daf41433a64cad5265cd27dbcb891147e9994d0422200ce81ce9a54b625
|
||||
F ext/misc/ieee754.c f190d0cc5182529acb15babd177781be1ac1718c
|
||||
F ext/misc/json1.c 71ce4e39793b743fc7e4790bc3bab15598e95cab57ad8da4326fa640ae5e5310
|
||||
F ext/misc/json1.c 66ccdfa63283adb2c015019b431eeee1f5af40a78d9aad10afd22c2c6db0e3b0
|
||||
F ext/misc/memstat.c 3017a0832c645c0f8c773435620d663855f04690172316bd127270d1a7523d4d
|
||||
F ext/misc/memtrace.c 7c0d115d2ef716ad0ba632c91e05bd119cb16c1aedf3bec9f06196ead2d5537b
|
||||
F ext/misc/memvfs.c ab36f49e02ebcdf85a1e08dc4d8599ea8f343e073ac9e0bca18a98b7e1ec9567
|
||||
@@ -352,6 +353,7 @@ F ext/rbu/rbufault2.test c81327a3ac2c385b9b954db3644d4e0df93eeebfc3de9f1f29975a1
|
||||
F ext/rbu/rbufault3.test b2fcc9db5c982b869f67d1d4688d8cb515d5b92f58011fff95665f2e62cec179
|
||||
F ext/rbu/rbufault4.test 03d2849c3df7d7bd14a622e789ff049e5080edd34a79cd432e01204db2a5930a
|
||||
F ext/rbu/rbufts.test 0ae8d1da191c75bd776b86e24456db0fb6e97b7c944259fae5407ea55d23c31d
|
||||
F ext/rbu/rbuhack.test 95e7b35e58d5b2a8d182dde1a404949edf077c07485e6c2bce8a7f582941e729
|
||||
F ext/rbu/rbumisc.test 329986cf5dd51890c4eb906c2f960ebb773a79a64bed90f506b7c417825b37eb
|
||||
F ext/rbu/rbumulti.test 5fb139058f37ddc5a113c5b93238de915b769b7792de41b44c983bc7c18cf5b9
|
||||
F ext/rbu/rbupartial.test f25df014b8dbe3c5345851fba6e66f79ab237f57dc201b2d5f0dbae658ae5a4c
|
||||
@@ -364,7 +366,7 @@ F ext/rbu/rbuvacuum.test 55e101e90168c2b31df6c9638fe73dc7f7cc666b6142266d1563697
|
||||
F ext/rbu/rbuvacuum2.test b8e5b51dc8b2c0153373d024c0936be3f66f9234acbd6d0baab0869d56b14e6b
|
||||
F ext/rbu/rbuvacuum3.test 8addd82e4b83b4c93fa47428eae4fd0dbf410f8512c186f38e348feb49ba03dc
|
||||
F ext/rbu/rbuvacuum4.test a78898e438a44803eb2bc897ba3323373c9f277418e2d6d76e90f2f1dbccfd10
|
||||
F ext/rbu/sqlite3rbu.c f3a3e09f575157052813be667d6ab3b54f47fb02e6e1c9f767ad7bb8f1fb90b3
|
||||
F ext/rbu/sqlite3rbu.c d175cbd98baba39cdea85df1de376277ab207ef1e4af8071aa1c208bb4fccc84
|
||||
F ext/rbu/sqlite3rbu.h 1dc88ab7bd32d0f15890ea08d23476c4198d3da3056985403991f8c9cd389812
|
||||
F ext/rbu/test_rbu.c 03f6f177096a5f822d68d8e4069ad8907fe572c62ff2d19b141f59742821828a
|
||||
F ext/repair/README.md 92f5e8aae749a4dae14f02eea8e1bb42d4db2b6ce5e83dbcdd6b1446997e0c15
|
||||
@@ -468,7 +470,7 @@ F src/btmutex.c 8acc2f464ee76324bf13310df5692a262b801808984c1b79defb2503bbafadb6
|
||||
F src/btree.c fdc4389b271bca30138db27dc2dfb9f52c2a7baaa44845aaf31a3c54663d837f
|
||||
F src/btree.h c11446f07ec0e9dc85af8041cb0855c52f5359c8b2a43e47e02a685282504d89
|
||||
F src/btreeInt.h 6111c15868b90669f79081039d19e7ea8674013f907710baa3c814dc3f8bfd3f
|
||||
F src/build.c da5d5d82eb53cb004e9120277cfe93a9c3dd294871eae3d728ebd0faee84d969
|
||||
F src/build.c 4814d55abb5553ac82763f6df9e185503d913f912cc0abea00965bb02912cc2d
|
||||
F src/callback.c 25dda5e1c2334a367b94a64077b1d06b2553369f616261ca6783c48bcb6bda73
|
||||
F src/complete.c a3634ab1e687055cd002e11b8f43eb75c17da23e
|
||||
F src/ctime.c 1b0724e66f95f33b160b1af85caaf9cceb325d22abf39bd24df4f54a73982251
|
||||
@@ -476,19 +478,19 @@ F src/date.c e1d8ac7102f3f283e63e13867acb0efa33861cf34f0faf4cdbaf9fa7a1eb7041
|
||||
F src/dbpage.c 135eb3b5e74f9ef74bde5cec2571192c90c86984fa534c88bf4a055076fa19b7
|
||||
F src/dbstat.c c12833de69cb655751487d2c5a59607e36be1c58ba1f4bd536609909ad47b319
|
||||
F src/delete.c d08c9e01a2664afd12edcfa3a9c6578517e8ff8735f35509582693adbe0edeaf
|
||||
F src/expr.c 10d90c4676047a75276446779d18fb3f7d3a1f9debc8b322e3772d2bd51f52ff
|
||||
F src/expr.c 1e9a6da29e3e13c14783891e867e19a54e2731c6a9b58d011cc4f3b4742a59e4
|
||||
F src/fault.c 460f3e55994363812d9d60844b2a6de88826e007
|
||||
F src/fkey.c 6b79f4c2447691aa9ac86e2a6a774b65f3b3dd053d4220a4893051a0de20f82e
|
||||
F src/func.c 4ee36219698d50d672a28eca4adb0fd6b92e607a1883d318315e0d2fd5044467
|
||||
F src/global.c d7a7a45a78ffe01302d61c271ed50474ef1b9d2d23bf17a46a58c8a1926424ee
|
||||
F src/func.c ed33e38cd642058182a31a3f518f2e34f4bbe53aa483335705c153c4d3e50b12
|
||||
F src/global.c a1a8d698762ddd9a1543aac26c1e0029b20fcc3fcb56bfa41ec8cea2368f2798
|
||||
F src/hash.c 8d7dda241d0ebdafb6ffdeda3149a412d7df75102cecfc1021c98d6219823b19
|
||||
F src/hash.h 9d56a9079d523b648774c1784b74b89bd93fac7b365210157482e4319a468f38
|
||||
F src/hwtime.h 747c1bbe9df21a92e9c50f3bbec1de841dc5e5da
|
||||
F src/in-operator.md 10cd8f4bcd225a32518407c2fb2484089112fd71
|
||||
F src/insert.c 40557ebd69f4115e7a273f9304a8ab637a47ce44f3c6923396928f023967b5e8
|
||||
F src/legacy.c d7874bc885906868cd51e6c2156698f2754f02d9eee1bae2d687323c3ca8e5aa
|
||||
F src/loadext.c a045bb3425a9a633cc0f78e93d9beda6866f4c0f15bfdee735aba7c6b39f5cc4
|
||||
F src/main.c 51c55eb579eac4180bfcc6242741084710911350d2cd0c3fdd0f9fde55442128
|
||||
F src/loadext.c 4ddc65ae13c0d93db0ceedc8b14a28c8c260513448b0eb8c5a2ac375e3b6a85d
|
||||
F src/main.c 3851950717170ade4f6d718c18c6c7400ef5994c2a654679af2cff2ffd0fb2b9
|
||||
F src/malloc.c 0f9da2a66b230a5785af94b9672126845099b57b70a32c987d04ac28c69da990
|
||||
F src/mem0.c 6a55ebe57c46ca1a7d98da93aaa07f99f1059645
|
||||
F src/mem1.c c12a42539b1ba105e3707d0e628ad70e611040d8f5e38cf942cee30c867083de
|
||||
@@ -499,7 +501,7 @@ F src/memdb.c 02a5fcec19b9d40dd449ca802dc1b2e8f93f255fbf2a886277a3c3800d8d35db
|
||||
F src/memjournal.c 7561c01c90958f3ba9bc6cb2d857123d932bdfa5539ea34427a0957b2e35154d
|
||||
F src/msvc.h 3a15918220367a8876be3fa4f2abe423a861491e84b864fb2b7426bf022a28f8
|
||||
F src/mutex.c bae36f8af32c22ad80bbf0ccebec63c252b6a2b86e4d3e42672ff287ebf4a604
|
||||
F src/mutex.h 779d588e3b7756ec3ecf7d78cde1d84aba414f85
|
||||
F src/mutex.h a7b2293c48db5f27007c3bdb21d438873637d12658f5a0bf8ad025bb96803c4a
|
||||
F src/mutex_noop.c 9d4309c075ba9cc7249e19412d3d62f7f94839c4
|
||||
F src/mutex_unix.c aaf9ebc3f89df28483c52208497a99a02cc3650011422fc9d4c57e4392f7fe58
|
||||
F src/mutex_w32.c 7670d770c94bbfe8289bec9d7f1394c5a00a57c37f892aab6b6612d085255235
|
||||
@@ -508,12 +510,12 @@ F src/os.c 20f7b32c1e8839999fa7e79756a6cdc3041b44d7fc635c25a1b9399180d1fbd9
|
||||
F src/os.h 48388821692e87da174ea198bf96b1b2d9d83be5dfc908f673ee21fafbe0d432
|
||||
F src/os_common.h b2f4707a603e36811d9b1a13278bffd757857b85
|
||||
F src/os_setup.h 0dbaea40a7d36bf311613d31342e0b99e2536586
|
||||
F src/os_unix.c 4ec5b1305ced509ca52c4c0cb3aeabed2ed3972147b4090cf94eb31d48caeb53
|
||||
F src/os_unix.c a76a75f179cb233d54e505c3e0c84832224cfe5dfb3ee470bdcaf1ed29da57ab
|
||||
F src/os_win.c 035a813cbd17f355bdcad7ab894af214a9c13a1db8aeac902365350b98cd45a7
|
||||
F src/os_win.h 7b073010f1451abe501be30d12f6bc599824944a
|
||||
F src/pager.c 422fd8cfa59fb9173eff36a95878904a0eeb0dcc62ba49350acc8b1e51c4dc7b
|
||||
F src/pager.h 217921e81eb5fe455caa5cda96061959706bcdd29ddb57166198645ef7822ac3
|
||||
F src/parse.y 6f284f7488ad9db9ae2762161e52bec2e9609462b98a3354fcc6e0ce7aa7be8d
|
||||
F src/parse.y 50bfcb34be7320dd0cb875021a93ae6451c8f0b083f21b71934a1a3a9108015a
|
||||
F src/pcache.c 385ff064bca69789d199a98e2169445dc16e4291fa807babd61d4890c3b34177
|
||||
F src/pcache.h 4f87acd914cef5016fae3030343540d75f5b85a1877eed1a2a19b9f284248586
|
||||
F src/pcache1.c 62714cbd1b7299a6e6a27a587b66b4fd3a836a84e1181e7f96f5c34a50917848
|
||||
@@ -522,19 +524,19 @@ F src/pragma.h 40962d65b645bb3f08c1f4c456effd01c6e7f073f68ea25177e0c95e181cff75
|
||||
F src/prepare.c 132484635a30f873ee7eccd47f93ed1932503863b93b28423b42332d81adffaf
|
||||
F src/printf.c 9be6945837c839ba57837b4bc3af349eba630920fa5532aa518816defe42a7d4
|
||||
F src/random.c 80f5d666f23feb3e6665a6ce04c7197212a88384
|
||||
F src/resolve.c 9891cf5fd155bb199f8b1ff5d1429b9f70484487f4c455bba94348d4cb6f829f
|
||||
F src/resolve.c e021be0c1c4a2125fa38aabcd8dbb764bf5b2c889a948c30d3708430ec6ccd00
|
||||
F src/rowset.c d977b011993aaea002cab3e0bb2ce50cf346000dff94e944d547b989f4b1fe93
|
||||
F src/select.c 8685adae94dffa6e4542e2194e491d69e27d5b79fe72b219e9255b08e56eaf76
|
||||
F src/shell.c.in e5fb91505f29ae9458cabf1a63bbd1faf6b4b34eabca33d0f75a06aacecca21b
|
||||
F src/sqlite.h.in 50fc0914ccd347437db9a0278a47d7541df3a45eb6e641e9680750c6f98dad27
|
||||
F src/select.c f509982c96bb24ccf57a0155fbe1e6184e0b8fb8866a04397dc41baa400e5240
|
||||
F src/shell.c.in d70bcf630c4073eaa994fa74be98886c781918e794cb8b562be8df10f018e274
|
||||
F src/sqlite.h.in 5725a6b20190a1e8d662077a1c1c8ea889ad7be90dd803f914c2de226f5fe6ab
|
||||
F src/sqlite3.rc 5121c9e10c3964d5755191c80dd1180c122fc3a8
|
||||
F src/sqlite3ext.h cef696ce3293242c67b2339763608427bf72ee66f1f3a05389ac2a7b46001c31
|
||||
F src/sqliteInt.h b1fca535f01f02ae6927dd44e760c6ab54c7a181e88f813d16b55a1bc95d13c0
|
||||
F src/sqliteInt.h 246740eab76d3ac87f856f8d979567089e8749104c12932143a6ba570e38e415
|
||||
F src/sqliteLimit.h 1513bfb7b20378aa0041e7022d04acb73525de35b80b252f1b83fedb4de6a76b
|
||||
F src/status.c 46e7aec11f79dad50965a5ca5fa9de009f7d6bde08be2156f1538a0a296d4d0e
|
||||
F src/table.c b46ad567748f24a326d9de40e5b9659f96ffff34
|
||||
F src/tclsqlite.c 50c93be3e1c03b4e6cf6756e5197afcfe7f5cd0497d83a7ac317cde09e19b290
|
||||
F src/test1.c 8ce455da8dcec886a0e1e608da0fee7de67c8195b14517a8824a2a40c2d11fbf
|
||||
F src/test1.c 17e1395cbddeb9226b756d723a7566b45b43b99a5f9f55afb4ff70888de6ad6f
|
||||
F src/test2.c 3efb99ab7f1fc8d154933e02ae1378bac9637da5
|
||||
F src/test3.c 61798bb0d38b915067a8c8e03f5a534b431181f802659a6616f9b4ff7d872644
|
||||
F src/test4.c 405834f6a93ec395cc4c9bb8ecebf7c3d8079e7ca16ae65e82d01afd229694bb
|
||||
@@ -555,7 +557,7 @@ F src/test_demovfs.c 86142ba864d4297d54c5b2e972e74f3141ae4b30f05b3a95824184ed2d3
|
||||
F src/test_devsym.c 6109b45c3db3ef7b002320947ed448c027356ab8b885156ff535fd8684d4a571
|
||||
F src/test_fs.c ba1e1dc18fd3159fdba0b9c4256f14032159785320dfbd6776eb9973cb75d480
|
||||
F src/test_func.c 181f992e5495644434c4f0e3cc72362a78c295eb2cf3ff4d02498b8bde7aa276
|
||||
F src/test_hexio.c 1d4469ca61ab202a1fcec6543f584d2407205e8d
|
||||
F src/test_hexio.c d170d0e1a6431afdeac086a250d2595078288c2257615d37949355361399bcaa
|
||||
F src/test_init.c 4413c211a94b62157ca4c145b3f27c497f03c664
|
||||
F src/test_intarray.c 39b4181662a0f33a427748d87218e7578d913e683dc27eab7098bb41617cac71
|
||||
F src/test_intarray.h d57ae92f420cda25e22790dac474d60961bd0c500cbaa3338a05152d4a669ef7
|
||||
@@ -589,20 +591,20 @@ F src/test_window.c cdae419fdcea5bad6dcd9368c685abdad6deb59e9fc8b84b153de513d394
|
||||
F src/test_wsd.c 41cadfd9d97fe8e3e4e44f61a4a8ccd6f7ca8fe9
|
||||
F src/threads.c 4ae07fa022a3dc7c5beb373cf744a85d3c5c6c3c
|
||||
F src/tokenize.c d3615f0cbe4db5949503bf5916f3cd4fa5de855d5b4ef560f3b6dd5629423a1e
|
||||
F src/treeview.c fc8c6c0a8a26afb3a97e3f844d65403dd27cf1450baf4415034fa4ccf00c4d7e
|
||||
F src/treeview.c fddeb413159c3eeeaea3f496172f121cf3695606c461dc4e6dcee51417952df5
|
||||
F src/trigger.c 845ccc08f60716c58aa28fe6470385c18ef8c4e1d88c93dcf449bc13d464eb2e
|
||||
F src/update.c 7f05fad5e145248a00048aeb0bac78b8fdb4ed17216e14a6eb24c55596e87ee7
|
||||
F src/upsert.c 710c91bb13e3c3fed5b6fe17cb13e09560bdd003ad8b8c51e6b16c80cfc48b10
|
||||
F src/utf.c 2f0fac345c7660d5c5bd3df9e9d8d33d4c27f366bcfb09e07443064d751a0507
|
||||
F src/util.c fffdfa627be74d69ef425f92db124e7148af449bb8a3286e79577c42bca84061
|
||||
F src/vacuum.c 82dcec9e7b1afa980288718ad11bc499651c722d7b9f32933c4d694d91cb6ebf
|
||||
F src/vdbe.c 145e417fda9377a809d9c754d4098de9a9620aec1bc3e4d2d4ca8f8d525dace3
|
||||
F src/vdbe.c 7f43ed8e055a4290535d2e4520d33f0ac6cc00ef76a0c099e4c6bd85be74a6b9
|
||||
F src/vdbe.h 3f2b571e702e77e6bf031f0236e554aedfae643e991f69000320f481408455cf
|
||||
F src/vdbeInt.h e95de5129124d77f01439e6635012adfaf23c0017bff47296126143cf18bd0c6
|
||||
F src/vdbeapi.c 95001d0f84ee3cda344fed98ca0d7961deb4fc836b83495630d0af1f7cc4789e
|
||||
F src/vdbeaux.c 7ccf418141df1c7f87b0d69510523ae522abbe47c769d1b2c15120e88fac3eb9
|
||||
F src/vdbeblob.c 253ed82894924c362a7fa3079551d3554cd1cdace39aa833da77d3bc67e7c1b1
|
||||
F src/vdbemem.c 920285c3b7f5c64369e02da437dab71e9e91862df9c486541c14633739f91d75
|
||||
F src/vdbemem.c d8e10d1773806105e62094c4ede0a4684f46caaf07667a45e6d461e94306b530
|
||||
F src/vdbesort.c da75f505aba230060ce6472605a4aa6494f73eeb1071e1cc2643c3d4035e671b
|
||||
F src/vdbetrace.c fa3bf238002f0bbbdfb66cc8afb0cea284ff9f148d6439bc1f6f2b4c3b7143f0
|
||||
F src/vtab.c 5a0b7193d586991b3db30e343d6b59959906bfe8658a6a0a85709b20ca50bb49
|
||||
@@ -610,13 +612,13 @@ F src/vxworks.h d2988f4e5a61a4dfe82c6524dd3d6e4f2ce3cdb9
|
||||
F src/wal.c bbd6838bd79c0a32144d482fb0b6a9d2d1a252fb3b16d5005ec30f2f80413b0d
|
||||
F src/wal.h 606292549f5a7be50b6227bd685fa76e3a4affad71bb8ac5ce4cb5c79f6a176a
|
||||
F src/walker.c d5a94907dcac990e31976be9dc769d17f6a806782593d6aec9d760ee01ec22cd
|
||||
F src/where.c 9685d5988b79b93ebbe46941fbdb60d14861bb0fe3f9126117ef1753acc69b64
|
||||
F src/where.c 9f3f23efc45934e7b7ea6c0c1042420b73053e7c3264feef6faf9ce6fbd5df61
|
||||
F src/whereInt.h 2c6bae136a7c0be6ff75dc36950d1968c67d005c8e51d7a9d77cb996bb4843d9
|
||||
F src/wherecode.c 535c8e228478fd971b9a5b6cb6773995b0fbf7020d5989508a5094ce5b8cd95b
|
||||
F src/whereexpr.c b3bbae199e7acd8d0fa822c9a29cbb822ef2b3d84d68de55a3d60b013f5d5da4
|
||||
F src/window.c b1e56b1281538b5cdd796b4f6c6281549bef6f977aab63e2493704a2a9f31937
|
||||
F src/whereexpr.c 05c283d26aa9c3f5d1bf13a5f6a573b43295b9db280eff18e26f97d7d7f119b4
|
||||
F src/window.c 064f251451c8e2a1c76b6269229d911a651e119c6a5f522b6eaebf8dc8714041
|
||||
F test/8_3_names.test ebbb5cd36741350040fd28b432ceadf495be25b2
|
||||
F test/affinity2.test da465d3d490ab24ef64f7715b5953343a4967762b9350b29eb1462879ff3fb9e
|
||||
F test/affinity2.test ce1aafc86e110685b324e9a763eab4f2a73f737842ec3b687bd965867de90627
|
||||
F test/affinity3.test 6a101af2fc945ce2912f6fe54dd646018551710d
|
||||
F test/aggerror.test a867e273ef9e3d7919f03ef4f0e8c0d2767944f2
|
||||
F test/aggnested.test 12106f0748e8e9bfc1a8e6840e203e051eae06a26ed13fc9fd5db108a8d6db54
|
||||
@@ -768,8 +770,8 @@ F test/corruptH.test 79801d97ec5c2f9f3c87739aa1ec2eb786f96454
|
||||
F test/corruptI.test a17bbf54fdde78d43cf3cc34b0057719fd4a173a3d824285b67dc5257c064c7b
|
||||
F test/corruptJ.test 4d5ccc4bf959464229a836d60142831ef76a5aa4
|
||||
F test/corruptK.test 5b4212fe346699831c5ad559a62c54e11c0611bdde1ea8423a091f9c01aa32af
|
||||
F test/corruptL.test 865cb75ed971b72b5ee9ad9017befee6bd38794011cae69f00676d82c5a5dd69
|
||||
F test/corruptM.test 04a4061b1979283851953217e411187be79e50f5e5e3ef340c3f8e564173aae1
|
||||
F test/corruptL.test dfad96373bf9264d73039315ea6013994b90bf6776847adc7ec06b6fad3c04b2
|
||||
F test/corruptM.test 7d574320e08c1b36caa3e47262061f186367d593a7e305d35f15289cc2c3e067
|
||||
F test/cost.test 51f4fcaae6e78ad5a57096831259ed6c760e2ac6876836e91c00030fad385b34
|
||||
F test/count.test cb2e0f934c6eb33670044520748d2ecccd46259c
|
||||
F test/countofview.test e17d6e6688cf74f22783c9ec6e788c0790ee4fbbaee713affd00b1ac0bb39b86
|
||||
@@ -858,7 +860,7 @@ F test/extraquick.test cb254400bd42bfb777ff675356aabf3287978f79
|
||||
F test/fallocate.test 37a62e396a68eeede8f8d2ecf23573a80faceb630788d314d0a073d862616717
|
||||
F test/filectrl.test 6e871c2d35dead1d9a88e176e8d2ca094fec6bb3
|
||||
F test/filefmt.test f393e80c4b8d493b7a7f8f3809a8425bbf4292af1f5140f01cb1427798a2bbd4
|
||||
F test/filter1.test 94a6d26588db0e4e7305e1f0985a99405e98dd034dc393dd6264603eed6645d4
|
||||
F test/filter1.test c2f34e58ee82a60c3ee9b5b4c4f2004ec2f529dff2f473706eeffa684cbb6719
|
||||
F test/filter2.tcl 44e525497ce07382915f01bd29ffd0fa49dab3adb87253b5e5103ba8f93393e8
|
||||
F test/filter2.test 485cf95d1f6d6ceee5632201ca52a71868599836f430cdee42e5f7f14666e30a
|
||||
F test/filterfault.test c08fb491d698e8df6c122c98f7db1c65ffcfcad2c1ab0e07fa8a5be1b34eaa8b
|
||||
@@ -936,7 +938,7 @@ F test/fts3conf.test c84bbaec81281c1788aa545ac6e78a6bd6cde2bdbbce2da261690e3659f
|
||||
F test/fts3corrupt.test 46b9ddda7f6588fd5a5b1f4bb4fc0618dc45010e7dddb8a3a188baf3197177ae
|
||||
F test/fts3corrupt2.test bf55c3fa0b0dc8ea1c0fe5543623bd27714585da6a129038fd6999fe3b0d25f3
|
||||
F test/fts3corrupt3.test 0d5b69a0998b4adf868cc301fc78f3d0707745f1d984ce044c205cdb764b491f
|
||||
F test/fts3corrupt4.test d5389e14950e57333bfc972f262c90b5ba0e864a958df9e437e3aacd3a5570a7
|
||||
F test/fts3corrupt4.test 545c50e70d1fe922b6efef12019a92829832f52993c5421086489ce72bde2251
|
||||
F test/fts3corrupt5.test 0549f85ec4bd22e992f645f13c59b99d652f2f5e643dac75568bfd23a6db7ed5
|
||||
F test/fts3cov.test cb932743da52a1c79a1ab8983e26c8121cf02263d6ff16e1f642e6f9b8348338
|
||||
F test/fts3d.test 2bd8c97bcb9975f2334147173b4872505b6a41359a4f9068960a36afe07a679f
|
||||
@@ -984,9 +986,11 @@ F test/fts4merge.test 1096e30b58ad616bd502141bfe5bfe4c3a518df89e958d41a5ed1ce322
|
||||
F test/fts4merge2.test 5faa558d1b672f82b847d2a337465fa745e46891
|
||||
F test/fts4merge3.test 8d9ccb4a3d41c4c617a149d6c4b13ad02de797d0
|
||||
F test/fts4merge4.test d895b1057a7798b67e03455d0fa50e9ea836c47b
|
||||
F test/fts4merge5.test 69932d85cda8a1c4dcfb742865900ed8fbda51724b8cf9a45bbe226dfd06c596
|
||||
F test/fts4noti.test 5553d7bb2e20bf4a06b23e849352efc022ce6309
|
||||
F test/fts4onepass.test d69ddc4ee3415e40b0c5d1d0408488a87614d4f63ba9c44f3e52db541d6b7cc7
|
||||
F test/fts4opt.test 0fd0cc84000743ff2a883b9b84b4a5be07249f0ba790c8848a757164cdd46b2a
|
||||
F test/fts4record.test a48508f69a84c9287c8019d3a1ae712f5730d8335ffaf8e2101e691d078950bb
|
||||
F test/fts4rename.test 15fd9985c2bce6dea20da2245b22029ec89bd4710ed317c4c53abbe3cfd0c880
|
||||
F test/fts4umlaut.test fcaca4471de7e78c9d1f7e8976e3e8704d7d8ad979d57a739d00f3f757380429
|
||||
F test/fts4unicode.test ceca76422abc251818cb25dabe33d3c3970da5f7c90e1540f190824e6b3a7c95
|
||||
@@ -1012,7 +1016,7 @@ F test/fuzzdata4.db b502c7d5498261715812dd8b3c2005bad08b3a26e6489414bd13926cd3e4
|
||||
F test/fuzzdata5.db e35f64af17ec48926481cfaf3b3855e436bd40d1cfe2d59a9474cb4b748a52a5
|
||||
F test/fuzzdata6.db 92a80e4afc172c24f662a10a612d188fb272de4a9bd19e017927c95f737de6d7
|
||||
F test/fuzzdata7.db e7a86fd83dda151d160445d542e32e5c6019c541b3a74c2a525b6ac640639711
|
||||
F test/fuzzdata8.db dc52be9b732f5bc1cdc0db0ff5b8e69b87bc8989b13a94eb8acaef63897a007c
|
||||
F test/fuzzdata8.db c75b0fd1d28c262f9c3a9428393ff9c420ea5bdbe0b33c557a971915a94bab71
|
||||
F test/fuzzer1.test 3d4c4b7e547aba5e5511a2991e3e3d07166cfbb8
|
||||
F test/fuzzer2.test a85ef814ce071293bce1ad8dffa217cbbaad4c14
|
||||
F test/fuzzerfault.test 8792cd77fd5bce765b05d0c8e01b9edcf8af8536
|
||||
@@ -1053,7 +1057,7 @@ F test/index7.test 1d764c0cca45f5a76150b08e127ccc8d52492cfa788b5fafed4be784a351b
|
||||
F test/index8.test bc2e3db70e8e62459aaa1bd7e4a9b39664f8f9d7
|
||||
F test/index9.test 0aa3e509dddf81f93380396e40e9bb386904c1054924ba8fa9bcdfe85a8e7721
|
||||
F test/indexedby.test a52c8c6abfae4fbfb51d99440de4ca1840dbacc606b05e29328a2a8ba7cd914e
|
||||
F test/indexexpr1.test fb56f0b9a9d147b38979d154176f150b5e45fdd5d0162fab639a7f9478134fa3
|
||||
F test/indexexpr1.test c26c8b352311c1deb30642cd0379e5cb94e416c7e9e0885e92d9e01554df2db9
|
||||
F test/indexexpr2.test b580f378423bca443ffab47ada677203cfcf8a60f48a8aa20065f27c8f7739b5
|
||||
F test/indexfault.test 98d78a8ff1f5335628b62f886a1cb7c7dac1ef6d48fa39c51ec871c87dce9811
|
||||
F test/init.test 15c823093fdabbf7b531fe22cf037134d09587a7
|
||||
@@ -1063,7 +1067,7 @@ F test/insert3.test 1b7db95a03ad9c5013fdf7d6722b6cd66ee55e30
|
||||
F test/insert4.test 7802ada6ba8738661b9f6c0e26858d3375b40cc7180289fd350644cd7a08fec9
|
||||
F test/insert5.test 394f96728d1258f406fe5f5aeb0aaf29487c39a6
|
||||
F test/insertfault.test ac63d14ea3b49c573673a572f4014b9117383a03e497c58f308b5c776e4a7f74
|
||||
F test/instr.test 9a8802f28437d8ade53fedfc47b2ca599b4e48ba
|
||||
F test/instr.test 107df2b9b74a4b59315916b575590a08f2a714de0754abe541f10a0971d0a2a4
|
||||
F test/instrfault.test 0f870b218ea17cd477bb19ed330eecdb460dd53a
|
||||
F test/intarray.test bb976b0b3df0ebb6a2eddfb61768280440e672beba5460ed49679ea984ccf440
|
||||
F test/interrupt.test 16ea879ec728cb76414c148c5f24afd5d1f91054
|
||||
@@ -1101,7 +1105,7 @@ F test/laststmtchanges.test ae613f53819206b3222771828d024154d51db200
|
||||
F test/lemon-test01.y 58b764610fd934e189ffbb0bbfa33d171b9cb06019b55bdc04d090d6767e11d7
|
||||
F test/like.test 3d702d79bf871fa32985b1ce334294c587e3948d3ab972001e811a58577e8b3c
|
||||
F test/like2.test 3b2ee13149ba4a8a60b59756f4e5d345573852da
|
||||
F test/like3.test 62bf82ac674b7d4126e73532e1ad96cdcd8e1752a4ed90b28a6f98305f5a66aa
|
||||
F test/like3.test 4f940ad275c006319950054a7a65661f476772171b82b6fdf795e4dda36f246f
|
||||
F test/limit.test 0c99a27a87b14c646a9d583c7c89fd06c352663e
|
||||
F test/limit2.test 9409b033284642a859fafc95f29a5a6a557bd57c1f0d7c3f554bd64ed69df77e
|
||||
F test/loadext.test faa4f6eed07a5aac35d57fdd7bc07f8fc82464cfd327567c10cf0ba3c86cde04
|
||||
@@ -1200,6 +1204,7 @@ F test/orderby6.test 8b38138ab0972588240b3fca0985d2e400432859
|
||||
F test/orderby7.test 3d1383d52ade5b9eb3a173b3147fdd296f0202da
|
||||
F test/orderby8.test 23ef1a5d72bd3adcc2f65561c654295d1b8047bd
|
||||
F test/orderby9.test 87fb9548debcc2cd141c5299002dd94672fa76a3
|
||||
F test/orderbyA.test df608e59efc2ef50c1eddf1a773b272de3252e9401bfec86d04b52fd973866d5
|
||||
F test/oserror.test 1fc9746b83d778e70d115049747ba19c7fba154afce7cc165b09feb6ca6abbc5
|
||||
F test/ossfuzz.c 18af635fa73d12a109b305faca727a734c1fa28a421b161d9d15c5a84a4998a2
|
||||
F test/ossshell.c f125c5bd16e537a2549aa579b328dd1c59905e7ab1338dfc210e755bb7b69f17
|
||||
@@ -1217,9 +1222,9 @@ F test/parser1.test 6ccdf5e459a5dc4673d3273dc311a7e9742ca952dd0551a6a6320d27035c
|
||||
F test/pcache.test c8acbedd3b6fd0f9a7ca887a83b11d24a007972b
|
||||
F test/pcache2.test af7f3deb1a819f77a6d0d81534e97d1cf62cd442
|
||||
F test/percentile.test 4243af26b8f3f4555abe166f723715a1f74c77ff
|
||||
F test/permutations.test 4282fb00e5ac0f8c2cd1be62652f6da4ac03ce3c58b7d785fa17f4684492a0e0
|
||||
F test/permutations.test 8587800fe1a0eb01456a3f4500b821e54e3347e78acf11dbf05f4990530f6cee
|
||||
F test/pg_common.tcl 222a1bad1c41c308fa366313cd7b51b3be7e9b21c8736a421b974ac941693b54
|
||||
F test/pragma.test cf066fe0f7f5d49f4758de4986407b8676c61aaa7871599340d64f42a8edc352
|
||||
F test/pragma.test 59becdfd720b80d463ab750f69f7118fde10dfd556aa5d554f3bf6b7e5ea7533
|
||||
F test/pragma2.test e5d5c176360c321344249354c0c16aec46214c9f
|
||||
F test/pragma3.test 8300aa9c63cff1027006ca34bf413a148abbd6dcd471fa9a1ded322fe18c0df9
|
||||
F test/pragma4.test 1cb4b32f1a304ed9e291d7c4d49c91c2c8dc1b9450e6d2c1198b2cc895d40d77
|
||||
@@ -1245,8 +1250,8 @@ F test/recover.test ccb8c2623902a92ebb76770edd075cb4f75a4760bb7afde38026572c6e79
|
||||
F test/regexp1.test 497ea812f264d12b6198d6e50a76be4a1973a9d8
|
||||
F test/regexp2.test 40e894223b3d6672655481493f1be12012f2b33c
|
||||
F test/reindex.test cd9d6021729910ece82267b4f5e1b5ac2911a7566c43b43c176a6a4732e2118d
|
||||
F test/releasetest.tcl 968fc1e8fd23e113fb8a04379747f3a9f2c12d207b2de85aeff5a825962e1cd7 x
|
||||
F test/releasetest_data.tcl 4f55292d7e3e7995754373612a16b71f41be22dfded3a0375ccaf65c465d3765
|
||||
F test/releasetest.tcl fb76d8fcc95ac29d6356cd9e52b726ab9e43a24082897618dfbcb7c2b0049153 x
|
||||
F test/releasetest_data.tcl 9919fc6ac5bc92f8878fecfd1840db15999f660a6c9f609240b41aa62b885c88
|
||||
F test/resetdb.test 8062cf10a09d8c048f8de7711e94571c38b38168db0e5877ba7561789e5eeb2b
|
||||
F test/resolver01.test f4022acafda7f4d40eca94dbf16bc5fc4ac30ceb
|
||||
F test/rollback.test 06680159bc6746d0f26276e339e3ae2f951c64812468308838e0a3362d911eaa
|
||||
@@ -1413,6 +1418,7 @@ F test/threadtest3.c 38a612ea62854349ed66372f330a40d73c5cf956
|
||||
F test/threadtest4.c c1e67136ceb6c7ec8184e56ac61db28f96bd2925
|
||||
F test/time-wordcount.sh 8e0b0f8109367827ad5d58f5cc849705731e4b90
|
||||
F test/tkt-02a8e81d44.test 6c80d9c7514e2a42d4918bf87bf6bc54f379110c
|
||||
F test/tkt-18458b1a.test c543c4b8e8c7c2200579a635e72c15bc374a92d44eddb1d588d4fdeca9cca532
|
||||
F test/tkt-26ff0c2d1e.test c15bec890c4d226c0da2f35ff30f9e84c169cfef90e73a8cb5cec11d723dfa96
|
||||
F test/tkt-2a5629202f.test 0521bd25658428baa26665aa53ffed9367d33af2
|
||||
F test/tkt-2d1a5c67d.test be1326f3061caec85085f4c9ee4490561ca037c0
|
||||
@@ -1422,7 +1428,7 @@ F test/tkt-313723c356.test 4b306ad45c736cedf2f5221f6155b92143244b6d
|
||||
F test/tkt-385a5b56b9.test 5204a7cba0e28c99df0acbf95af5e1af4d32965a7a14de6eccebf949607618b1
|
||||
F test/tkt-38cb5df375.test f3cc8671f1eb604d4ae9cf886ed4366bec656678
|
||||
F test/tkt-3998683a16.test 6d1d04d551ed1704eb3396ca87bb9ccc8c5c1eb7
|
||||
F test/tkt-3a77c9714e.test b08bca26de1140bdf004a37716582a43d7bd8be8
|
||||
F test/tkt-3a77c9714e.test 90e3e8455ee945a4076d4c44062b8845708af24a880355328fe7008f2047c9f0
|
||||
F test/tkt-3fe897352e.test 27e26eb0f1811aeba4d65aba43a4c52e99da5e70
|
||||
F test/tkt-4a03edc4c8.test 91c0e135888cdc3d4eea82406a44b05c8c1648d0
|
||||
F test/tkt-4c86b126f2.test cbcc611becd0396890169ab23102dd70048bbc9a
|
||||
@@ -1448,12 +1454,12 @@ F test/tkt-9a8b09f8e6.test b2ef151d0984b2ebf237760dbeaa50724e5a0667
|
||||
F test/tkt-9d68c883.test 16f7cb96781ba579bc2e19bb14b4ad609d9774b6
|
||||
F test/tkt-9f2eb3abac.test cb6123ac695a08b4454c3792fbe85108f67fabf8
|
||||
F test/tkt-a7b7803e.test 159ef554234fa1f9fb318c751b284bd1cf858da4
|
||||
F test/tkt-a7debbe0.test 27b977fea9d42021d9ef67e5811bdc56fd0b9599517e0244c528dddd3264ed4e
|
||||
F test/tkt-a7debbe0.test 65a647034e3416d068f81e7d86fffc07edfae371c70b8761714edb56ec1c7521
|
||||
F test/tkt-a8a0d2996a.test 002e1cde8fc30c39611b52cf981c88200b858765748556822da72e0d32fac73e
|
||||
F test/tkt-b1d3a2e531.test 8f7576e41ca179289ee1a8fee28386fd8e4b0550
|
||||
F test/tkt-b351d95f9.test d14a503c414c5c58fdde3e80f9a3cfef986498c0
|
||||
F test/tkt-b72787b1.test a95e8cdad0b98af1853ac7f0afd4ab27b77bf5f3
|
||||
F test/tkt-b75a9ca6b0.test 1bc0381538fd21f96a10dbabc10ffc51b5b2e5f412d34bae571273ca784003d7
|
||||
F test/tkt-b75a9ca6b0.test ade89229d853a67a21bbd5e6e1e787a8f9d21f19908d1b7fca6bf3d4d5aa0767
|
||||
F test/tkt-ba7cbfaedc.test b4c0deccc12aeb55cfdb57935b16b5d67c5a9877
|
||||
F test/tkt-bd484a090c.test 60460bf946f79a79712b71f202eda501ca99b898
|
||||
F test/tkt-bdc6bbbb38.test fc38bb09bdd440e3513a1f5f98fc60a075182d7d
|
||||
@@ -1672,7 +1678,7 @@ F test/walslow.test c05c68d4dc2700a982f89133ce103a1a84cc285f
|
||||
F test/walthread.test 14b20fcfa6ae152f5d8e12f5dc8a8a724b7ef189f5d8ef1e2ceab79f2af51747
|
||||
F test/walvfs.test f1accd66c876e3a0f6b4bef5b18d13411062d0ff0a0016e32bb41570474e99fc
|
||||
F test/wapp.tcl b440cd8cf57953d3a49e7ee81e6a18f18efdaf113b69f7d8482b0710a64566ec
|
||||
F test/wapptest.tcl 3090239c59379d41e1a0644feb6683082fdb86edfab0c668973f8003f22c0e5d x
|
||||
F test/wapptest.tcl 3cca775aede0591756a1fc0da55bbb3715d8c363873fd2cfdd4d555b0a4af57d x
|
||||
F test/where.test 19c709c9f0f6ed12c23f909f6592aa55fba34269d5a2898537aa27a22b9ce650
|
||||
F test/where2.test 478d2170637b9211f593120648858593bf2445a1
|
||||
F test/where3.test 2341a294e17193a6b1699ea7f192124a5286ca6acfcc3f4b06d16c931fbcda2c
|
||||
@@ -1703,8 +1709,8 @@ F test/win32lock.test fbf107c91d8f5512be5a5b87c4c42ab9fdd54972
|
||||
F test/win32longpath.test 169c75a3b2e43481f4a62122510210c67b08f26d
|
||||
F test/win32nolock.test ac4f08811a562e45a5755e661f45ca85892bdbbc
|
||||
F test/window1.test 376a7c9c5b9df9868d92a6d9d455262e1b769f4410b19006f5f8c5507c2a7ed7
|
||||
F test/window2.tcl a44834af6267be6e14882311ef8790bf5047f1b9bc25685ee1762d48dc24f1e7
|
||||
F test/window2.test 2f3ae63e171dce7f2ac29a41020f4da413b1d7bdaba48ee124fd336b152e34c5
|
||||
F test/window2.tcl 66db96fd9fd202bc31ee7f8ce7904cb469564864cff3f74e009bfef8102333f4
|
||||
F test/window2.test af2a001ded703bb8f2474fb0edfef170d5aba00f5c1f2aa9f65935b5da13df90
|
||||
F test/window3.tcl acea6e86a4324a210fd608d06741010ca83ded9fde438341cb978c49928faf03
|
||||
F test/window3.test e9959a993c8a71e96433be8daaa1827d78b8921e4f12debd7bdbeb3c856ef3cb
|
||||
F test/window4.tcl d732df0e81beedc0ba8a563ade68611d322d27303ad0c0c8e4444107c39e84ec
|
||||
@@ -1715,8 +1721,9 @@ F test/window7.tcl 6a1210f05d40ec89c22960213a22cd3f98d4e2f2eb20646c83c8c30d4d761
|
||||
F test/window7.test 1d31276961ae7801edc72173edaf7593e3cbc79c06d1f1f09e20d8418af403cd
|
||||
F test/window8.tcl f2711aa3571e4e6b0dad98db8d95fd6cb8d9db0c92bbdf535f153b07606a1ce2
|
||||
F test/window8.test c4331b27a6f66d69fa8f8bab10cc731db1a81d293ae108a68f7c3487fa94e65b
|
||||
F test/window9.test 20a6b590be718b6bc98a5356d4396d6cdf19329c547da084fa225b92d68e1693
|
||||
F test/window9.test ae8be07be05a5a4c8ead1818ac5d45f278b8dd456e589d67f24270b0070c35a0
|
||||
F test/windowA.test 6d63dc1260daa17141a55007600581778523a8b420629f1282d2acfc36af23be
|
||||
F test/windowB.test 7a983ea1cc1cf72be7f378e4b32f6cb2d73014c5cd8b25aaee825164cd4269e5
|
||||
F test/windowerr.tcl f5acd6fbc210d7b5546c0e879d157888455cd4a17a1d3f28f07c1c8a387019e0
|
||||
F test/windowerr.test a8b752402109c15aa1c5efe1b93ccb0ce1ef84fa964ae1cd6684dd0b3cc1819b
|
||||
F test/windowfault.test a90b397837209f15e54afa62e8be39b2759a0101fae04e05a08bcc50e243a452
|
||||
@@ -1725,13 +1732,13 @@ F test/with2.test e0030e2f0267a910d6c0e4f46f2dfe941c1cc0d4f659ba69b3597728e7e8f1
|
||||
F test/with3.test b5f1372097690c6ef84db2f13fc7e64a88c7263c3f88493605f90597e8a68d45
|
||||
F test/with4.test 257be66c0c67fee1defbbac0f685c3465e2cad037f21ce65f23f86084f198205
|
||||
F test/withM.test 693b61765f2b387b5e3e24a4536e2e82de15ff64
|
||||
F test/without_rowid1.test f40c2757272ce171b88e4227f14450db2c4d42800d447baa7656a65562d2f8d9
|
||||
F test/without_rowid1.test 0abe18762b74714580c1d4d00a8e540e58966d3e46aae41ddb1a1d2c88c9277d
|
||||
F test/without_rowid2.test af260339f79d13cb220288b67cd287fbcf81ad99
|
||||
F test/without_rowid3.test ea4b59dd1b0d7f5f5e4b7cca978cdb905752a9d7c57dc4344a591dba765a3691
|
||||
F test/without_rowid4.test 4e08bcbaee0399f35d58b5581881e7a6243d458a
|
||||
F test/without_rowid5.test 89b1c587bd92a0590e440da33e7666bf4891572a
|
||||
F test/without_rowid6.test 3c1bbf0eb81c672115933158b62b009e67cf1a7f8c2c612bbce63a7385efa18e
|
||||
F test/without_rowid7.test 0e0d7be00f05f54898e20e07bcc947cd97b42d7106021fa0d2897324bc6d330e
|
||||
F test/without_rowid6.test 8463b20098e9f75a501a9f17dfb42fffc79068eac0b2775fe56ef2281d2df45e
|
||||
F test/without_rowid7.test d7c59a93d726b55812d620f8f284e01904a5b85f9ee9eea8f2f68571a5e8c40e
|
||||
F test/wordcount.c d721a4b6fae93e6e33449700bce1686bc23257c27425bc3ef1599dc912adec66
|
||||
F test/writecrash.test f1da7f7adfe8d7f09ea79b42e5ca6dcc41102f27f8e334ad71539501ddd910cc
|
||||
F test/zeroblob.test 07a5b11ab591d1f26c626945fb7f228f68b993533b2ada77273edf6ee29db174
|
||||
@@ -1759,7 +1766,7 @@ F tool/genfkey.test b6afd7b825d797a1e1274f519ab5695373552ecad5cd373530c63533638a
|
||||
F tool/getlock.c f4c39b651370156cae979501a7b156bdba50e7ce
|
||||
F tool/index_usage.c 9ec344d29cbeb03fdc0fce668eedfb7495792170de933adf95cf8d6904a166ad
|
||||
F tool/kvtest-speed.sh 4761a9c4b3530907562314d7757995787f7aef8f
|
||||
F tool/lemon.c c9848ef9694689d244a5097238ca1f83df85cc52c80ad149a4cf49595a0ee9c2
|
||||
F tool/lemon.c 61d5f0af1eff8f754b75ddca668c9897fd30759e389bfffb42ce9e4d38fd4746
|
||||
F tool/lempar.c eb2841e2a7fd484cf44b1f526b06e7ab0f216d2f41818bf9485e8f38e3d1db19
|
||||
F tool/libvers.c caafc3b689638a1d88d44bc5f526c2278760d9b9
|
||||
F tool/loadfts.c c3c64e4d5e90e8ba41159232c2189dba4be7b862
|
||||
@@ -1798,7 +1805,7 @@ F tool/showstat4.c 0682ebea7abf4d3657f53c4a243f2e7eab48eab344ed36a94bb75dcd19a5c
|
||||
F tool/showwal.c ad9d768f96ca6199ad3a8c9562d679680bd032dd01204ea3e5ea6fb931d81847
|
||||
F tool/soak1.tcl 8d407956e1a45b485a8e072470a3e629a27037fe
|
||||
F tool/spaceanal.tcl 4bfd19aad7eb3ce0372ef0255f58035e0bba4ff5e9acfd763a10c6fb365c8dec
|
||||
F tool/speed-check.sh 27c7fe178d5b2f7c90a04a127907acda0bfe637fa85b13c43e03e5ed39b008b6
|
||||
F tool/speed-check.sh 2b042d703a9472f08c3b13be27afac658426f8e4fc87cd2d575953fda86f08d1
|
||||
F tool/speedtest.tcl 06c76698485ccf597b9e7dbb1ac70706eb873355
|
||||
F tool/speedtest16.c ecb6542862151c3e6509bbc00509b234562ae81e
|
||||
F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff
|
||||
@@ -1840,10 +1847,8 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93
|
||||
F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc
|
||||
F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e
|
||||
F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0
|
||||
P cb3e2be674316e1d39968eb6567f1fe1b72f9d89af49640a9e83f944979c4cf0
|
||||
R 8499ff2bdbcbd0ce456fbfc5655f865d
|
||||
T *branch * tkt-a7debbe0.
|
||||
T *sym-tkt-a7debbe0. *
|
||||
T -sym-trunk *
|
||||
P 4b73e151cdb4b89bdd2f1bab5c0378500234ce6c479cc1d8cd4e006be79d1162
|
||||
Q +087b8b41c6ed76b55c11315e7e95679d67590be20ae21108b593d00bb7d1c57a
|
||||
R f1bc15780a98eb9fb1abdadc164e3b34
|
||||
U dan
|
||||
Z b93432e9313cfc8d7991fd66b06bef63
|
||||
Z 02ec0c40b41079c9dff32d6e22ece993
|
||||
|
||||
+1
-1
@@ -1 +1 @@
|
||||
1863b7bf12521bdd2b51c5b8d3a4634bff3e15d3713e0b5343952df7da02f794
|
||||
56869f54f31186231a4467f10208bcc08d9edae23c6e21831d6d3dff47da51de
|
||||
+2
-1
@@ -2816,7 +2816,8 @@ void sqlite3DropTable(Parse *pParse, SrcList *pName, int isView, int noErr){
|
||||
}
|
||||
#endif
|
||||
if( sqlite3StrNICmp(pTab->zName, "sqlite_", 7)==0
|
||||
&& sqlite3StrNICmp(pTab->zName, "sqlite_stat", 11)!=0 ){
|
||||
&& sqlite3StrNICmp(pTab->zName+7, "stat", 4)!=0
|
||||
&& sqlite3StrNICmp(pTab->zName+7, "parameters", 10)!=0 ){
|
||||
sqlite3ErrorMsg(pParse, "table %s may not be dropped", pTab->zName);
|
||||
goto exit_drop_table;
|
||||
}
|
||||
|
||||
+22
-4
@@ -905,7 +905,7 @@ Expr *sqlite3ExprAnd(Parse *pParse, Expr *pLeft, Expr *pRight){
|
||||
}else if( ExprAlwaysFalse(pLeft) || ExprAlwaysFalse(pRight) ){
|
||||
sqlite3ExprUnmapAndDelete(pParse, pLeft);
|
||||
sqlite3ExprUnmapAndDelete(pParse, pRight);
|
||||
return sqlite3ExprAlloc(db, TK_INTEGER, &sqlite3IntTokens[0], 0);
|
||||
return sqlite3Expr(db, TK_INTEGER, "0");
|
||||
}else{
|
||||
return sqlite3PExpr(pParse, TK_AND, pLeft, pRight);
|
||||
}
|
||||
@@ -2867,6 +2867,7 @@ void sqlite3CodeRhsOfIN(
|
||||
/* Subroutine return */
|
||||
sqlite3VdbeAddOp1(v, OP_Return, pExpr->y.sub.regReturn);
|
||||
sqlite3VdbeChangeP1(v, pExpr->y.sub.iAddr-1, sqlite3VdbeCurrentAddr(v)-1);
|
||||
sqlite3ClearTempRegCache(pParse);
|
||||
}
|
||||
}
|
||||
#endif /* SQLITE_OMIT_SUBQUERY */
|
||||
@@ -2958,11 +2959,21 @@ int sqlite3CodeSubselect(Parse *pParse, Expr *pExpr){
|
||||
sqlite3VdbeAddOp2(v, OP_Integer, 0, dest.iSDParm);
|
||||
VdbeComment((v, "Init EXISTS result"));
|
||||
}
|
||||
pLimit = sqlite3ExprAlloc(pParse->db, TK_INTEGER,&sqlite3IntTokens[1], 0);
|
||||
if( pSel->pLimit ){
|
||||
sqlite3ExprDelete(pParse->db, pSel->pLimit->pLeft);
|
||||
/* The subquery already has a limit. If the pre-existing limit is X
|
||||
** then make the new limit X<>0 so that the new limit is either 1 or 0 */
|
||||
sqlite3 *db = pParse->db;
|
||||
pLimit = sqlite3Expr(db, TK_INTEGER, "0");
|
||||
if( pLimit ){
|
||||
pLimit->affExpr = SQLITE_AFF_NUMERIC;
|
||||
pLimit = sqlite3PExpr(pParse, TK_NE,
|
||||
sqlite3ExprDup(db, pSel->pLimit->pLeft, 0), pLimit);
|
||||
}
|
||||
sqlite3ExprDelete(db, pSel->pLimit->pLeft);
|
||||
pSel->pLimit->pLeft = pLimit;
|
||||
}else{
|
||||
/* If there is no pre-existing limit add a limit of 1 */
|
||||
pLimit = sqlite3Expr(pParse->db, TK_INTEGER, "1");
|
||||
pSel->pLimit = sqlite3PExpr(pParse, TK_LIMIT, pLimit, 0);
|
||||
}
|
||||
pSel->iLimit = 0;
|
||||
@@ -2977,6 +2988,7 @@ int sqlite3CodeSubselect(Parse *pParse, Expr *pExpr){
|
||||
/* Subroutine return */
|
||||
sqlite3VdbeAddOp1(v, OP_Return, pExpr->y.sub.regReturn);
|
||||
sqlite3VdbeChangeP1(v, pExpr->y.sub.iAddr-1, sqlite3VdbeCurrentAddr(v)-1);
|
||||
sqlite3ClearTempRegCache(pParse);
|
||||
}
|
||||
|
||||
return rReg;
|
||||
@@ -4944,7 +4956,8 @@ int sqlite3ExprCompare(Parse *pParse, Expr *pA, Expr *pB, int iTab){
|
||||
){
|
||||
if( pA->iColumn!=pB->iColumn ) return 2;
|
||||
if( pA->op2!=pB->op2 ) return 2;
|
||||
if( pA->iTable!=pB->iTable
|
||||
if( pA->op!=TK_IN
|
||||
&& pA->iTable!=pB->iTable
|
||||
&& (pA->iTable!=iTab || NEVER(pB->iTable>=0)) ) return 2;
|
||||
}
|
||||
}
|
||||
@@ -5608,6 +5621,11 @@ void sqlite3ReleaseTempRange(Parse *pParse, int iReg, int nReg){
|
||||
|
||||
/*
|
||||
** Mark all temporary registers as being unavailable for reuse.
|
||||
**
|
||||
** Always invoke this procedure after coding a subroutine or co-routine
|
||||
** that might be invoked from other parts of the code, to ensure that
|
||||
** the sub/co-routine does not use registers in common with the code that
|
||||
** invokes the sub/co-routine.
|
||||
*/
|
||||
void sqlite3ClearTempRegCache(Parse *pParse){
|
||||
pParse->nTempReg = 0;
|
||||
|
||||
+21
-2
@@ -203,6 +203,8 @@ static void instrFunc(
|
||||
int N = 1;
|
||||
int isText;
|
||||
unsigned char firstChar;
|
||||
sqlite3_value *pC1 = 0;
|
||||
sqlite3_value *pC2 = 0;
|
||||
|
||||
UNUSED_PARAMETER(argc);
|
||||
typeHaystack = sqlite3_value_type(argv[0]);
|
||||
@@ -215,12 +217,22 @@ static void instrFunc(
|
||||
zHaystack = sqlite3_value_blob(argv[0]);
|
||||
zNeedle = sqlite3_value_blob(argv[1]);
|
||||
isText = 0;
|
||||
}else{
|
||||
}else if( typeHaystack!=SQLITE_BLOB && typeNeedle!=SQLITE_BLOB ){
|
||||
zHaystack = sqlite3_value_text(argv[0]);
|
||||
zNeedle = sqlite3_value_text(argv[1]);
|
||||
isText = 1;
|
||||
}else{
|
||||
pC1 = sqlite3_value_dup(argv[0]);
|
||||
zHaystack = sqlite3_value_text(pC1);
|
||||
if( zHaystack==0 ) goto endInstrOOM;
|
||||
nHaystack = sqlite3_value_bytes(pC1);
|
||||
pC2 = sqlite3_value_dup(argv[1]);
|
||||
zNeedle = sqlite3_value_text(pC2);
|
||||
if( zNeedle==0 ) goto endInstrOOM;
|
||||
nNeedle = sqlite3_value_bytes(pC2);
|
||||
isText = 1;
|
||||
}
|
||||
if( zNeedle==0 || (nHaystack && zHaystack==0) ) return;
|
||||
if( zNeedle==0 || (nHaystack && zHaystack==0) ) goto endInstrOOM;
|
||||
firstChar = zNeedle[0];
|
||||
while( nNeedle<=nHaystack
|
||||
&& (zHaystack[0]!=firstChar || memcmp(zHaystack, zNeedle, nNeedle)!=0)
|
||||
@@ -234,6 +246,13 @@ static void instrFunc(
|
||||
if( nNeedle>nHaystack ) N = 0;
|
||||
}
|
||||
sqlite3_result_int(context, N);
|
||||
endInstr:
|
||||
sqlite3_value_free(pC1);
|
||||
sqlite3_value_free(pC2);
|
||||
return;
|
||||
endInstrOOM:
|
||||
sqlite3_result_error_nomem(context);
|
||||
goto endInstr;
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -271,14 +271,6 @@ SQLITE_WSD struct Sqlite3Config sqlite3Config = {
|
||||
*/
|
||||
FuncDefHash sqlite3BuiltinFunctions;
|
||||
|
||||
/*
|
||||
** Constant tokens for values 0 and 1.
|
||||
*/
|
||||
const Token sqlite3IntTokens[] = {
|
||||
{ "0", 1 },
|
||||
{ "1", 1 }
|
||||
};
|
||||
|
||||
#ifdef VDBE_PROFILE
|
||||
/*
|
||||
** The following performance counter can be used in place of
|
||||
|
||||
@@ -463,7 +463,11 @@ static const sqlite3_api_routines sqlite3Apis = {
|
||||
sqlite3_stmt_isexplain,
|
||||
sqlite3_value_frombind,
|
||||
/* Version 3.30.0 and later */
|
||||
#ifndef SQLITE_OMIT_VIRTUALTABLE
|
||||
sqlite3_drop_modules,
|
||||
#else
|
||||
0,
|
||||
#endif
|
||||
};
|
||||
|
||||
/*
|
||||
|
||||
+1
-1
@@ -1719,7 +1719,7 @@ int sqlite3CreateFunc(
|
||||
|
||||
assert( SQLITE_FUNC_CONSTANT==SQLITE_DETERMINISTIC );
|
||||
assert( SQLITE_FUNC_DIRECT==SQLITE_DIRECTONLY );
|
||||
extraFlags = enc & (SQLITE_DETERMINISTIC|SQLITE_DIRECTONLY);
|
||||
extraFlags = enc & (SQLITE_DETERMINISTIC|SQLITE_DIRECTONLY|SQLITE_SUBTYPE);
|
||||
enc &= (SQLITE_FUNC_ENCMASK|SQLITE_ANY);
|
||||
|
||||
#ifndef SQLITE_OMIT_UTF16
|
||||
|
||||
@@ -67,4 +67,5 @@
|
||||
#define MUTEX_LOGIC(X)
|
||||
#else
|
||||
#define MUTEX_LOGIC(X) X
|
||||
int sqlite3_mutex_held(sqlite3_mutex*);
|
||||
#endif /* defined(SQLITE_MUTEX_OMIT) */
|
||||
|
||||
+38
-14
@@ -105,13 +105,29 @@
|
||||
# include <sys/param.h>
|
||||
#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."
|
||||
/*
|
||||
** Try to determine if gethostuuid() is available based on standard
|
||||
** macros. This might sometimes compute the wrong value for some
|
||||
** obscure platforms. For those cases, simply compile with one of
|
||||
** the following:
|
||||
**
|
||||
** -DHAVE_GETHOSTUUID=0
|
||||
** -DHAVE_GETHOSTUUID=1
|
||||
**
|
||||
** None if this matters except when building on Apple products with
|
||||
** -DSQLITE_ENABLE_LOCKING_STYLE.
|
||||
*/
|
||||
#ifndef HAVE_GETHOSTUUID
|
||||
# define HAVE_GETHOSTUUID 0
|
||||
# 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))
|
||||
# undef HAVE_GETHOSTUUID
|
||||
# define HAVE_GETHOSTUUID 1
|
||||
# else
|
||||
# warning "gethostuuid() is disabled."
|
||||
# endif
|
||||
# endif
|
||||
#endif
|
||||
|
||||
@@ -5824,7 +5840,7 @@ static int getFileMode(
|
||||
** If the SQLITE_ENABLE_8_3_NAMES option is enabled, then the
|
||||
** original filename is unavailable. But 8_3_NAMES is only used for
|
||||
** FAT filesystems and permissions do not matter there, so just use
|
||||
** the default permissions.
|
||||
** the default permissions. In 8_3_NAMES mode, leave *pMode set to zero.
|
||||
*/
|
||||
static int findCreateFileMode(
|
||||
const char *zPath, /* Path of file (possibly) being created */
|
||||
@@ -6059,11 +6075,19 @@ static int unixOpen(
|
||||
goto open_finished;
|
||||
}
|
||||
|
||||
/* If this process is running as root and if creating a new rollback
|
||||
** journal or WAL file, set the ownership of the journal or WAL to be
|
||||
** the same as the original database.
|
||||
/* The owner of the rollback journal or WAL file should always be the
|
||||
** same as the owner of the database file. Try to ensure that this is
|
||||
** the case. The chown() system call will be a no-op if the current
|
||||
** process lacks root privileges, be we should at least try. Without
|
||||
** this step, if a root process opens a database file, it can leave
|
||||
** behinds a journal/WAL that is owned by root and hence make the
|
||||
** database inaccessible to unprivileged processes.
|
||||
**
|
||||
** If openMode==0, then that means uid and gid are not set correctly
|
||||
** (probably because SQLite is configured to use 8+3 filename mode) and
|
||||
** in that case we do not want to attempt the chown().
|
||||
*/
|
||||
if( flags & (SQLITE_OPEN_WAL|SQLITE_OPEN_MAIN_JOURNAL) ){
|
||||
if( openMode && (flags & (SQLITE_OPEN_WAL|SQLITE_OPEN_MAIN_JOURNAL))!=0 ){
|
||||
robustFchown(fd, uid, gid);
|
||||
}
|
||||
}
|
||||
@@ -6921,7 +6945,7 @@ int sqlite3_hostid_num = 0;
|
||||
|
||||
#define PROXY_HOSTIDLEN 16 /* conch file host id length */
|
||||
|
||||
#ifdef HAVE_GETHOSTUUID
|
||||
#if HAVE_GETHOSTUUID
|
||||
/* Not always defined in the headers as it ought to be */
|
||||
extern int gethostuuid(uuid_t id, const struct timespec *wait);
|
||||
#endif
|
||||
@@ -6932,7 +6956,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);
|
||||
#ifdef HAVE_GETHOSTUUID
|
||||
#if HAVE_GETHOSTUUID
|
||||
{
|
||||
struct timespec timeout = {1, 0}; /* 1 sec timeout */
|
||||
if( gethostuuid(pHostID, &timeout) ){
|
||||
|
||||
+1
-1
@@ -1181,7 +1181,7 @@ expr(A) ::= expr(A) between_op(N) expr(X) AND expr(Y). [BETWEEN] {
|
||||
** regardless of the value of expr1.
|
||||
*/
|
||||
sqlite3ExprUnmapAndDelete(pParse, A);
|
||||
A = sqlite3ExprAlloc(pParse->db, TK_INTEGER,&sqlite3IntTokens[N],1);
|
||||
A = sqlite3Expr(pParse->db, TK_INTEGER, N ? "1" : "0");
|
||||
}else{
|
||||
A = sqlite3PExpr(pParse, TK_IN, A, 0);
|
||||
if( A ){
|
||||
|
||||
@@ -96,6 +96,13 @@ static void resolveAlias(
|
||||
pExpr->u.zToken = sqlite3DbStrDup(db, pExpr->u.zToken);
|
||||
pExpr->flags |= EP_MemToken;
|
||||
}
|
||||
if( ExprHasProperty(pExpr, EP_WinFunc) ){
|
||||
if( pExpr->y.pWin!=0 ){
|
||||
pExpr->y.pWin->pOwner = pExpr;
|
||||
}else{
|
||||
assert( db->mallocFailed );
|
||||
}
|
||||
}
|
||||
sqlite3DbFree(db, pDup);
|
||||
}
|
||||
ExprSetProperty(pExpr, EP_Alias);
|
||||
|
||||
+52
-24
@@ -3418,7 +3418,6 @@ typedef struct SubstContext {
|
||||
int iNewTable; /* New table number */
|
||||
int isLeftJoin; /* Add TK_IF_NULL_ROW opcodes on each replacement */
|
||||
ExprList *pEList; /* Replacement expressions */
|
||||
int bFlattener; /* True for query-flattener, false otherwise */
|
||||
} SubstContext;
|
||||
|
||||
/* Forward Declarations */
|
||||
@@ -3480,9 +3479,9 @@ static Expr *substExpr(
|
||||
sqlite3ExprDelete(db, pExpr);
|
||||
pExpr = pNew;
|
||||
|
||||
/* If this call is part of query-flattening, ensure that the
|
||||
** new expression has an implicit collation sequence. */
|
||||
if( pSubst->bFlattener && pExpr ){
|
||||
/* Ensure that the expression now has an implicit collation sequence,
|
||||
** just as it did when it was a column of a view or sub-query. */
|
||||
if( pExpr ){
|
||||
if( pExpr->op!=TK_COLUMN && pExpr->op!=TK_COLLATE ){
|
||||
CollSeq *pColl = sqlite3ExprCollSeq(pSubst->pParse, pExpr);
|
||||
pExpr = sqlite3ExprAddCollateString(pSubst->pParse, pExpr,
|
||||
@@ -4056,7 +4055,6 @@ static int flattenSubquery(
|
||||
x.iNewTable = iNewParent;
|
||||
x.isLeftJoin = isLeftJoin;
|
||||
x.pEList = pSub->pEList;
|
||||
x.bFlattener = 1;
|
||||
substSelect(&x, pParent, 0);
|
||||
}
|
||||
|
||||
@@ -4382,7 +4380,6 @@ static int pushDownWhereTerms(
|
||||
x.iNewTable = iCursor;
|
||||
x.isLeftJoin = 0;
|
||||
x.pEList = pSubq->pEList;
|
||||
x.bFlattener = 0;
|
||||
pNew = substExpr(&x, pNew);
|
||||
if( pSubq->selFlags & SF_Aggregate ){
|
||||
pSubq->pHaving = sqlite3ExprAnd(pParse, pSubq->pHaving, pNew);
|
||||
@@ -5359,6 +5356,19 @@ static void updateAccumulator(Parse *pParse, int regAcc, AggInfo *pAggInfo){
|
||||
assert( !IsWindowFunc(pF->pExpr) );
|
||||
if( ExprHasProperty(pF->pExpr, EP_WinFunc) ){
|
||||
Expr *pFilter = pF->pExpr->y.pWin->pFilter;
|
||||
if( pAggInfo->nAccumulator
|
||||
&& (pF->pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL)
|
||||
){
|
||||
if( regHit==0 ) regHit = ++pParse->nMem;
|
||||
/* If this is the first row of the group (regAcc==0), clear the
|
||||
** "magnet" register regHit so that the accumulator registers
|
||||
** are populated if the FILTER clause jumps over the the
|
||||
** invocation of min() or max() altogether. Or, if this is not
|
||||
** the first row (regAcc==1), set the magnet register so that the
|
||||
** accumulators are not populated unless the min()/max() is invoked and
|
||||
** indicates that they should be. */
|
||||
sqlite3VdbeAddOp2(v, OP_Copy, regAcc, regHit);
|
||||
}
|
||||
addrNext = sqlite3VdbeMakeLabel(pParse);
|
||||
sqlite3ExprIfFalse(pParse, pFilter, addrNext, SQLITE_JUMPIFNULL);
|
||||
}
|
||||
@@ -5409,6 +5419,7 @@ static void updateAccumulator(Parse *pParse, int regAcc, AggInfo *pAggInfo){
|
||||
for(i=0, pC=pAggInfo->aCol; i<pAggInfo->nAccumulator; i++, pC++){
|
||||
sqlite3ExprCode(pParse, pC->pExpr, pC->iMem);
|
||||
}
|
||||
|
||||
pAggInfo->directMode = 0;
|
||||
if( addrHitTest ){
|
||||
sqlite3VdbeJumpHere(v, addrHitTest);
|
||||
@@ -5454,7 +5465,7 @@ static int havingToWhereExprCb(Walker *pWalker, Expr *pExpr){
|
||||
Select *pS = pWalker->u.pSelect;
|
||||
if( sqlite3ExprIsConstantOrGroupBy(pWalker->pParse, pExpr, pS->pGroupBy) ){
|
||||
sqlite3 *db = pWalker->pParse->db;
|
||||
Expr *pNew = sqlite3ExprAlloc(db, TK_INTEGER, &sqlite3IntTokens[1], 0);
|
||||
Expr *pNew = sqlite3Expr(db, TK_INTEGER, "1");
|
||||
if( pNew ){
|
||||
Expr *pWhere = pS->pWhere;
|
||||
SWAP(Expr, *pNew, *pExpr);
|
||||
@@ -6212,23 +6223,35 @@ int sqlite3Select(
|
||||
}
|
||||
assert( 66==sqlite3LogEst(100) );
|
||||
if( p->nSelectRow>66 ) p->nSelectRow = 66;
|
||||
|
||||
/* If there is both a GROUP BY and an ORDER BY clause and they are
|
||||
** identical, then it may be possible to disable the ORDER BY clause
|
||||
** on the grounds that the GROUP BY will cause elements to come out
|
||||
** in the correct order. It also may not - the GROUP BY might use a
|
||||
** database index that causes rows to be grouped together as required
|
||||
** but not actually sorted. Either way, record the fact that the
|
||||
** ORDER BY and GROUP BY clauses are the same by setting the orderByGrp
|
||||
** variable. */
|
||||
if( sSort.pOrderBy && pGroupBy->nExpr==sSort.pOrderBy->nExpr ){
|
||||
int ii;
|
||||
/* The GROUP BY processing doesn't care whether rows are delivered in
|
||||
** ASC or DESC order - only that each group is returned contiguously.
|
||||
** So set the ASC/DESC flags in the GROUP BY to match those in the
|
||||
** ORDER BY to maximize the chances of rows being delivered in an
|
||||
** order that makes the ORDER BY redundant. */
|
||||
for(ii=0; ii<pGroupBy->nExpr; ii++){
|
||||
u8 sortFlags = sSort.pOrderBy->a[ii].sortFlags & KEYINFO_ORDER_DESC;
|
||||
pGroupBy->a[ii].sortFlags = sortFlags;
|
||||
}
|
||||
if( sqlite3ExprListCompare(pGroupBy, sSort.pOrderBy, -1)==0 ){
|
||||
orderByGrp = 1;
|
||||
}
|
||||
}
|
||||
}else{
|
||||
assert( 0==sqlite3LogEst(1) );
|
||||
p->nSelectRow = 0;
|
||||
}
|
||||
|
||||
/* If there is both a GROUP BY and an ORDER BY clause and they are
|
||||
** identical, then it may be possible to disable the ORDER BY clause
|
||||
** on the grounds that the GROUP BY will cause elements to come out
|
||||
** in the correct order. It also may not - the GROUP BY might use a
|
||||
** database index that causes rows to be grouped together as required
|
||||
** but not actually sorted. Either way, record the fact that the
|
||||
** ORDER BY and GROUP BY clauses are the same by setting the orderByGrp
|
||||
** variable. */
|
||||
if( sqlite3ExprListCompare(pGroupBy, sSort.pOrderBy, -1)==0 ){
|
||||
orderByGrp = 1;
|
||||
}
|
||||
|
||||
/* Create a label to jump to when we want to abort the query */
|
||||
addrEnd = sqlite3VdbeMakeLabel(pParse);
|
||||
|
||||
@@ -6584,13 +6607,18 @@ int sqlite3Select(
|
||||
{
|
||||
int regAcc = 0; /* "populate accumulators" flag */
|
||||
|
||||
/* If there are accumulator registers but no min() or max() functions,
|
||||
** allocate register regAcc. Register regAcc will contain 0 the first
|
||||
** time the inner loop runs, and 1 thereafter. The code generated
|
||||
** by updateAccumulator() only updates the accumulator registers if
|
||||
** regAcc contains 0. */
|
||||
/* If there are accumulator registers but no min() or max() functions
|
||||
** without FILTER clauses, allocate register regAcc. Register regAcc
|
||||
** will contain 0 the first time the inner loop runs, and 1 thereafter.
|
||||
** The code generated by updateAccumulator() uses this to ensure
|
||||
** that the accumulator registers are (a) updated only once if
|
||||
** there are no min() or max functions or (b) always updated for the
|
||||
** first row visited by the aggregate, so that they are updated at
|
||||
** least once even if the FILTER clause means the min() or max()
|
||||
** function visits zero rows. */
|
||||
if( sAggInfo.nAccumulator ){
|
||||
for(i=0; i<sAggInfo.nFunc; i++){
|
||||
if( ExprHasProperty(sAggInfo.aFunc[i].pExpr, EP_WinFunc) ) continue;
|
||||
if( sAggInfo.aFunc[i].pFunc->funcFlags&SQLITE_FUNC_NEEDCOLL ) break;
|
||||
}
|
||||
if( i==sAggInfo.nFunc ){
|
||||
|
||||
+18
-8
@@ -3588,6 +3588,8 @@ static const char *(azHelp[]) = {
|
||||
" --freelist-corrupt Assume the freelist is corrupt",
|
||||
" --recovery-db NAME Store recovery metadata in database file NAME",
|
||||
" --lost-and-found TABLE Alternative name for the lost-and-found table",
|
||||
" --no-rowids Do not attempt to recover rowid values",
|
||||
" that are not also INTEGER PRIMARY KEYs",
|
||||
#endif
|
||||
".restore ?DB? FILE Restore content of DB (default \"main\") from FILE",
|
||||
".save FILE Write in-memory database into FILE",
|
||||
@@ -6592,6 +6594,7 @@ static int recoverDatabaseCmd(ShellState *pState, int nArg, char **azArg){
|
||||
RecoverTable *pOrphan = 0;
|
||||
|
||||
int bFreelist = 1; /* 0 if --freelist-corrupt is specified */
|
||||
int bRowids = 1; /* 0 if --no-rowids */
|
||||
for(i=1; i<nArg; i++){
|
||||
char *z = azArg[i];
|
||||
int n;
|
||||
@@ -6607,6 +6610,9 @@ static int recoverDatabaseCmd(ShellState *pState, int nArg, char **azArg){
|
||||
if( n<=15 && memcmp("-lost-and-found", z, n)==0 && i<(nArg-1) ){
|
||||
i++;
|
||||
zLostAndFound = azArg[i];
|
||||
}else
|
||||
if( n<=10 && memcmp("-no-rowids", z, n)==0 ){
|
||||
bRowids = 0;
|
||||
}
|
||||
else{
|
||||
utf8_printf(stderr, "unexpected option: %s\n", azArg[i]);
|
||||
@@ -6772,8 +6778,11 @@ static int recoverDatabaseCmd(ShellState *pState, int nArg, char **azArg){
|
||||
shellPrepare(pState->db, &rc,
|
||||
"SELECT pgno FROM recovery.map WHERE root=?", &pPages
|
||||
);
|
||||
|
||||
shellPrepare(pState->db, &rc,
|
||||
"SELECT max(field), group_concat(shell_escape_crnl(quote(value)), ', ')"
|
||||
"SELECT max(field), group_concat(shell_escape_crnl(quote"
|
||||
"(case when (? AND field<0) then NULL else value end)"
|
||||
"), ', ')"
|
||||
", min(field) "
|
||||
"FROM sqlite_dbdata WHERE pgno = ? AND field != ?"
|
||||
"GROUP BY cell", &pCells
|
||||
@@ -6808,11 +6817,16 @@ static int recoverDatabaseCmd(ShellState *pState, int nArg, char **azArg){
|
||||
raw_printf(pState->out, "DELETE FROM sqlite_sequence;\n");
|
||||
}
|
||||
sqlite3_bind_int(pPages, 1, iRoot);
|
||||
sqlite3_bind_int(pCells, 2, pTab->iPk);
|
||||
if( bRowids==0 && pTab->iPk<0 ){
|
||||
sqlite3_bind_int(pCells, 1, 1);
|
||||
}else{
|
||||
sqlite3_bind_int(pCells, 1, 0);
|
||||
}
|
||||
sqlite3_bind_int(pCells, 3, pTab->iPk);
|
||||
|
||||
while( rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pPages) ){
|
||||
int iPgno = sqlite3_column_int(pPages, 0);
|
||||
sqlite3_bind_int(pCells, 1, iPgno);
|
||||
sqlite3_bind_int(pCells, 2, iPgno);
|
||||
while( rc==SQLITE_OK && SQLITE_ROW==sqlite3_step(pCells) ){
|
||||
int nField = sqlite3_column_int(pCells, 0);
|
||||
int iMin = sqlite3_column_int(pCells, 2);
|
||||
@@ -8134,12 +8148,8 @@ static int do_meta_command(char *zLine, ShellState *p){
|
||||
** Clear all bind parameters by dropping the TEMP table that holds them.
|
||||
*/
|
||||
if( nArg==2 && strcmp(azArg[1],"clear")==0 ){
|
||||
int wrSchema = 0;
|
||||
sqlite3_db_config(p->db, SQLITE_DBCONFIG_WRITABLE_SCHEMA, -1, &wrSchema);
|
||||
sqlite3_db_config(p->db, SQLITE_DBCONFIG_WRITABLE_SCHEMA, 1, 0);
|
||||
sqlite3_exec(p->db, "DROP TABLE IF EXISTS temp.sqlite_parameters;",
|
||||
0, 0, 0);
|
||||
sqlite3_db_config(p->db, SQLITE_DBCONFIG_WRITABLE_SCHEMA, wrSchema, 0);
|
||||
}else
|
||||
|
||||
/* .parameter list
|
||||
@@ -9409,7 +9419,7 @@ static int do_meta_command(char *zLine, ShellState *p){
|
||||
}else
|
||||
#endif /* !defined(SQLITE_OMIT_TRACE) */
|
||||
|
||||
#ifdef SQLITE_DEBUG
|
||||
#if defined(SQLITE_DEBUG) && !defined(SQLITE_OMIT_VIRTUALTABLE)
|
||||
if( c=='u' && strncmp(azArg[0], "unmodule", n)==0 ){
|
||||
int ii;
|
||||
int lenOpt;
|
||||
|
||||
+19
-2
@@ -4860,9 +4860,12 @@ int sqlite3_reset(sqlite3_stmt *pStmt);
|
||||
** function that is not deterministic. The SQLite query planner is able to
|
||||
** perform additional optimizations on deterministic functions, so use
|
||||
** of the [SQLITE_DETERMINISTIC] flag is recommended where possible.
|
||||
**
|
||||
** ^The fourth parameter may also optionally include the [SQLITE_DIRECTONLY]
|
||||
** flag, which if present prevents the function from being invoked from
|
||||
** within VIEWs or TRIGGERs.
|
||||
** within VIEWs or TRIGGERs. For security reasons, the [SQLITE_DIRECTONLY]
|
||||
** flag is recommended for any application-defined SQL function that has
|
||||
** side-effects.
|
||||
**
|
||||
** ^(The fifth parameter is an arbitrary pointer. The implementation of the
|
||||
** function can gain access to this pointer using [sqlite3_user_data()].)^
|
||||
@@ -4986,10 +4989,24 @@ int sqlite3_create_window_function(
|
||||
** deterministic, for example, but randomblob() is not.
|
||||
**
|
||||
** The SQLITE_DIRECTONLY flag means that the function may only be invoked
|
||||
** from top-level SQL, and cannot be used in VIEWs or TRIGGERs.
|
||||
** from top-level SQL, and cannot be used in VIEWs or TRIGGERs. This is
|
||||
** a security feature which is recommended for all
|
||||
** [application-defined SQL functions] that have side-effects. This flag
|
||||
** prevents an attacker from adding triggers and views to a schema then
|
||||
** tricking a high-privilege application into causing unintended side-effects
|
||||
** while performing ordinary queries.
|
||||
**
|
||||
** The SQLITE_SUBTYPE flag indicates to SQLite that a function may call
|
||||
** [sqlite3_value_subtype()] to inspect the sub-types of its arguments.
|
||||
** Specifying this flag makes no difference for scalar or aggregate user
|
||||
** functions. However, if it is not specified for a user-defined window
|
||||
** function, then any sub-types belonging to arguments passed to the window
|
||||
** function may be discarded before the window function is called (i.e.
|
||||
** sqlite3_value_subtype() will always return 0).
|
||||
*/
|
||||
#define SQLITE_DETERMINISTIC 0x000000800
|
||||
#define SQLITE_DIRECTONLY 0x000080000
|
||||
#define SQLITE_SUBTYPE 0x000100000
|
||||
|
||||
/*
|
||||
** CAPI3REF: Deprecated Functions
|
||||
|
||||
+11
-5
@@ -1686,6 +1686,7 @@ struct FuncDestructor {
|
||||
#define SQLITE_FUNC_WINDOW 0x00010000 /* Built-in window-only function */
|
||||
#define SQLITE_FUNC_INTERNAL 0x00040000 /* For use by NestedParse() only */
|
||||
#define SQLITE_FUNC_DIRECT 0x00080000 /* Not for use in TRIGGERs or VIEWs */
|
||||
#define SQLITE_FUNC_SUBTYPE 0x00100000 /* Result likely to have sub-type */
|
||||
|
||||
/*
|
||||
** The following three macros, FUNCTION(), LIKEFUNC() and AGGREGATE() are
|
||||
@@ -2142,8 +2143,11 @@ struct KeyInfo {
|
||||
CollSeq *aColl[1]; /* Collating sequence for each term of the key */
|
||||
};
|
||||
|
||||
#define KEYINFO_ORDER_DESC 0x01
|
||||
#define KEYINFO_ORDER_BIGNULL 0x02
|
||||
/*
|
||||
** Allowed bit values for entries in the KeyInfo.aSortFlags[] array.
|
||||
*/
|
||||
#define KEYINFO_ORDER_DESC 0x01 /* DESC sort order */
|
||||
#define KEYINFO_ORDER_BIGNULL 0x02 /* NULL is larger than any other value */
|
||||
|
||||
/*
|
||||
** This object holds a record which has been parsed out into individual
|
||||
@@ -2473,6 +2477,7 @@ struct Expr {
|
||||
** TK_REGISTER: register number
|
||||
** TK_TRIGGER: 1 -> new, 0 -> old
|
||||
** EP_Unlikely: 134217728 times likelihood
|
||||
** TK_IN: ephemerial table holding RHS
|
||||
** TK_SELECT_COLUMN: Number of columns on the LHS
|
||||
** TK_SELECT: 1st register of result vector */
|
||||
ynVar iColumn; /* TK_COLUMN: column index. -1 for rowid.
|
||||
@@ -3600,8 +3605,8 @@ struct Window {
|
||||
Expr *pFilter; /* The FILTER expression */
|
||||
FuncDef *pFunc; /* The function */
|
||||
int iEphCsr; /* Partition buffer or Peer buffer */
|
||||
int regAccum;
|
||||
int regResult;
|
||||
int regAccum; /* Accumulator */
|
||||
int regResult; /* Interim result */
|
||||
int csrApp; /* Function cursor (used by min/max) */
|
||||
int regApp; /* Function register (also used by min/max) */
|
||||
int regPart; /* Array of registers for PARTITION BY values */
|
||||
@@ -3611,6 +3616,8 @@ struct Window {
|
||||
int regOne; /* Register containing constant value 1 */
|
||||
int regStartRowid;
|
||||
int regEndRowid;
|
||||
u8 bExprArgs; /* Defer evaluation of window function arguments
|
||||
** due to the SQLITE_SUBTYPE flag */
|
||||
};
|
||||
|
||||
#ifndef SQLITE_OMIT_WINDOWFUNC
|
||||
@@ -4315,7 +4322,6 @@ extern const unsigned char sqlite3OpcodeProperty[];
|
||||
extern const char sqlite3StrBINARY[];
|
||||
extern const unsigned char sqlite3UpperToLower[];
|
||||
extern const unsigned char sqlite3CtypeMap[];
|
||||
extern const Token sqlite3IntTokens[];
|
||||
extern SQLITE_WSD struct Sqlite3Config sqlite3Config;
|
||||
extern FuncDefHash sqlite3BuiltinFunctions;
|
||||
#ifndef SQLITE_OMIT_WSD
|
||||
|
||||
@@ -1131,7 +1131,9 @@ static int SQLITE_TCLAPI test_drop_modules(
|
||||
return TCL_ERROR;
|
||||
}
|
||||
if( getDbPointer(interp, argv[1], &db) ) return TCL_ERROR;
|
||||
#ifndef SQLITE_OMIT_VIRTUALTABLE
|
||||
sqlite3_drop_modules(db, argc>2 ? (const char**)(argv+2) : 0);
|
||||
#endif
|
||||
return TCL_OK;
|
||||
}
|
||||
|
||||
@@ -7200,6 +7202,7 @@ static int SQLITE_TCLAPI optimization_control(
|
||||
{ "omit-noop-join", SQLITE_OmitNoopJoin },
|
||||
{ "stat4", SQLITE_Stat4 },
|
||||
{ "skip-scan", SQLITE_SkipScan },
|
||||
{ "push-down", SQLITE_PushDown },
|
||||
};
|
||||
|
||||
if( objc!=4 ){
|
||||
|
||||
@@ -337,6 +337,17 @@ static int getFts3Varint(const char *p, sqlite_int64 *v){
|
||||
return (int) (q - (unsigned char *)p);
|
||||
}
|
||||
|
||||
static int putFts3Varint(char *p, sqlite_int64 v){
|
||||
unsigned char *q = (unsigned char *) p;
|
||||
sqlite_uint64 vu = v;
|
||||
do{
|
||||
*q++ = (unsigned char) ((vu & 0x7f) | 0x80);
|
||||
vu >>= 7;
|
||||
}while( vu!=0 );
|
||||
q[-1] &= 0x7f; /* turn off high bit in final byte */
|
||||
assert( q - (unsigned char *)p <= 10 );
|
||||
return (int) (q - (unsigned char *)p);
|
||||
}
|
||||
|
||||
/*
|
||||
** USAGE: read_fts3varint BLOB VARNAME
|
||||
@@ -367,6 +378,67 @@ static int SQLITE_TCLAPI read_fts3varint(
|
||||
return TCL_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
** USAGE: make_fts3record ARGLIST
|
||||
*/
|
||||
static int SQLITE_TCLAPI make_fts3record(
|
||||
void * clientData,
|
||||
Tcl_Interp *interp,
|
||||
int objc,
|
||||
Tcl_Obj *CONST objv[]
|
||||
){
|
||||
Tcl_Obj **aArg = 0;
|
||||
int nArg = 0;
|
||||
unsigned char *aOut = 0;
|
||||
int nOut = 0;
|
||||
int nAlloc = 0;
|
||||
int i;
|
||||
|
||||
if( objc!=2 ){
|
||||
Tcl_WrongNumArgs(interp, 1, objv, "LIST");
|
||||
return TCL_ERROR;
|
||||
}
|
||||
if( Tcl_ListObjGetElements(interp, objv[1], &nArg, &aArg) ){
|
||||
return TCL_ERROR;
|
||||
}
|
||||
|
||||
for(i=0; i<nArg; i++){
|
||||
sqlite3_int64 iVal;
|
||||
if( TCL_OK==Tcl_GetWideIntFromObj(0, aArg[i], &iVal) ){
|
||||
if( nOut+10>nAlloc ){
|
||||
int nNew = nAlloc?nAlloc*2:128;
|
||||
unsigned char *aNew = sqlite3_realloc(aOut, nNew);
|
||||
if( aNew==0 ){
|
||||
sqlite3_free(aOut);
|
||||
return TCL_ERROR;
|
||||
}
|
||||
aOut = aNew;
|
||||
nAlloc = nNew;
|
||||
}
|
||||
nOut += putFts3Varint((char*)&aOut[nOut], iVal);
|
||||
}else{
|
||||
int nVal = 0;
|
||||
char *zVal = Tcl_GetStringFromObj(aArg[i], &nVal);
|
||||
while( (nOut + nVal)>nAlloc ){
|
||||
int nNew = nAlloc?nAlloc*2:128;
|
||||
unsigned char *aNew = sqlite3_realloc(aOut, nNew);
|
||||
if( aNew==0 ){
|
||||
sqlite3_free(aOut);
|
||||
return TCL_ERROR;
|
||||
}
|
||||
aOut = aNew;
|
||||
nAlloc = nNew;
|
||||
}
|
||||
memcpy(&aOut[nOut], zVal, nVal);
|
||||
nOut += nVal;
|
||||
}
|
||||
}
|
||||
|
||||
Tcl_SetObjResult(interp, Tcl_NewByteArrayObj(aOut, nOut));
|
||||
sqlite3_free(aOut);
|
||||
return TCL_OK;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
** Register commands with the TCL interpreter.
|
||||
@@ -383,6 +455,7 @@ int Sqlitetest_hexio_Init(Tcl_Interp *interp){
|
||||
{ "hexio_render_int32", hexio_render_int32 },
|
||||
{ "utf8_to_utf8", utf8_to_utf8 },
|
||||
{ "read_fts3varint", read_fts3varint },
|
||||
{ "make_fts3record", make_fts3record },
|
||||
};
|
||||
int i;
|
||||
for(i=0; i<sizeof(aObjCmd)/sizeof(aObjCmd[0]); i++){
|
||||
|
||||
+8
-1
@@ -536,7 +536,14 @@ void sqlite3TreeViewExpr(TreeView *pView, const Expr *pExpr, u8 moreToFollow){
|
||||
}
|
||||
|
||||
case TK_COLLATE: {
|
||||
sqlite3TreeViewLine(pView, "COLLATE %Q", pExpr->u.zToken);
|
||||
/* COLLATE operators without the EP_Collate flag are intended to
|
||||
** emulate collation associated with a table column. These show
|
||||
** up in the treeview output as "SOFT-COLLATE". Explicit COLLATE
|
||||
** operators that appear in the original SQL always have the
|
||||
** EP_Collate bit set and appear in treeview output as just "COLLATE" */
|
||||
sqlite3TreeViewLine(pView, "%sCOLLATE %Q%s",
|
||||
!ExprHasProperty(pExpr, EP_Collate) ? "SOFT-" : "",
|
||||
pExpr->u.zToken, zFlgs);
|
||||
sqlite3TreeViewExpr(pView, pExpr->pLeft, 0);
|
||||
break;
|
||||
}
|
||||
|
||||
+3
-2
@@ -483,6 +483,7 @@ void sqlite3VdbeMemPrettyPrint(Mem *pMem, char *zBuf){
|
||||
c = 's';
|
||||
}
|
||||
*(zCsr++) = c;
|
||||
*(zCsr++) = 'x';
|
||||
sqlite3_snprintf(100, zCsr, "%d[", pMem->n);
|
||||
zCsr += sqlite3Strlen30(zCsr);
|
||||
for(i=0; i<25 && i<pMem->n; i++){
|
||||
@@ -553,7 +554,7 @@ static void memTracePrint(Mem *p){
|
||||
printf(" i:%lld", p->u.i);
|
||||
#ifndef SQLITE_OMIT_FLOATING_POINT
|
||||
}else if( p->flags & MEM_Real ){
|
||||
printf(" r:%g", p->u.r);
|
||||
printf(" r:%.17g", p->u.r);
|
||||
#endif
|
||||
}else if( sqlite3VdbeMemIsRowSet(p) ){
|
||||
printf(" (rowset)");
|
||||
@@ -1142,7 +1143,6 @@ case OP_Real: { /* same as TK_FLOAT, out2 */
|
||||
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);
|
||||
|
||||
#ifndef SQLITE_OMIT_UTF16
|
||||
@@ -1166,6 +1166,7 @@ case OP_String8: { /* same as TK_STRING, out2 */
|
||||
if( pOp->p1>db->aLimit[SQLITE_LIMIT_LENGTH] ){
|
||||
goto too_big;
|
||||
}
|
||||
pOp->opcode = OP_String;
|
||||
assert( rc==SQLITE_OK );
|
||||
/* Fall through to the next case, OP_String */
|
||||
}
|
||||
|
||||
+7
-1
@@ -232,7 +232,13 @@ SQLITE_NOINLINE int sqlite3VdbeMemGrow(Mem *pMem, int n, int bPreserve){
|
||||
assert( pMem->szMalloc==0
|
||||
|| pMem->szMalloc==sqlite3DbMallocSize(pMem->db, pMem->zMalloc) );
|
||||
if( pMem->szMalloc>0 && bPreserve && pMem->z==pMem->zMalloc ){
|
||||
pMem->z = pMem->zMalloc = sqlite3DbReallocOrFree(pMem->db, pMem->z, n);
|
||||
if( pMem->db ){
|
||||
pMem->z = pMem->zMalloc = sqlite3DbReallocOrFree(pMem->db, pMem->z, n);
|
||||
}else{
|
||||
pMem->zMalloc = sqlite3Realloc(pMem->z, n);
|
||||
if( pMem->zMalloc==0 ) sqlite3_free(pMem->z);
|
||||
pMem->z = pMem->zMalloc;
|
||||
}
|
||||
bPreserve = 0;
|
||||
}else{
|
||||
if( pMem->szMalloc>0 ) sqlite3DbFreeNN(pMem->db, pMem->zMalloc);
|
||||
|
||||
+2
-1
@@ -2268,7 +2268,7 @@ static void whereLoopOutputAdjust(
|
||||
){
|
||||
WhereTerm *pTerm, *pX;
|
||||
Bitmask notAllowed = ~(pLoop->prereq|pLoop->maskSelf);
|
||||
int i, j, k;
|
||||
int i, j;
|
||||
LogEst iReduce = 0; /* pLoop->nOut should not exceed nRow-iReduce */
|
||||
|
||||
assert( (pLoop->wsFlags & WHERE_AUTO_INDEX)==0 );
|
||||
@@ -2294,6 +2294,7 @@ static void whereLoopOutputAdjust(
|
||||
pLoop->nOut--;
|
||||
if( pTerm->eOperator&(WO_EQ|WO_IS) ){
|
||||
Expr *pRight = pTerm->pExpr->pRight;
|
||||
int k = 0;
|
||||
testcase( pTerm->pExpr->op==TK_IS );
|
||||
if( sqlite3ExprIsInteger(pRight, &k) && k>=(-1) && k<=1 ){
|
||||
k = 10;
|
||||
|
||||
+8
-3
@@ -284,6 +284,7 @@ static int isLikeOrGlob(
|
||||
** 2019-05-02 https://sqlite.org/src/info/b043a54c3de54b28
|
||||
** 2019-06-10 https://sqlite.org/src/info/fd76310a5e843e07
|
||||
** 2019-06-14 https://sqlite.org/src/info/ce8717f0885af975
|
||||
** 2019-09-03 https://sqlite.org/src/info/0f0428096f17252a
|
||||
*/
|
||||
if( pLeft->op!=TK_COLUMN
|
||||
|| sqlite3ExprAffinity(pLeft)!=SQLITE_AFF_TEXT
|
||||
@@ -293,9 +294,13 @@ static int isLikeOrGlob(
|
||||
double rDummy;
|
||||
isNum = sqlite3AtoF(zNew, &rDummy, iTo, SQLITE_UTF8);
|
||||
if( isNum<=0 ){
|
||||
zNew[iTo-1]++;
|
||||
isNum = sqlite3AtoF(zNew, &rDummy, iTo, SQLITE_UTF8);
|
||||
zNew[iTo-1]--;
|
||||
if( iTo==1 && zNew[0]=='-' ){
|
||||
isNum = +1;
|
||||
}else{
|
||||
zNew[iTo-1]++;
|
||||
isNum = sqlite3AtoF(zNew, &rDummy, iTo, SQLITE_UTF8);
|
||||
zNew[iTo-1]--;
|
||||
}
|
||||
}
|
||||
if( isNum>0 ){
|
||||
sqlite3ExprDelete(db, pPrefix);
|
||||
|
||||
+171
-120
@@ -965,8 +965,15 @@ int sqlite3WindowRewrite(Parse *pParse, Select *p){
|
||||
** window function - one for the accumulator, another for interim
|
||||
** results. */
|
||||
for(pWin=pMWin; pWin; pWin=pWin->pNextWin){
|
||||
pWin->iArgCol = (pSublist ? pSublist->nExpr : 0);
|
||||
pSublist = exprListAppendList(pParse, pSublist, pWin->pOwner->x.pList, 0);
|
||||
ExprList *pArgs = pWin->pOwner->x.pList;
|
||||
if( pWin->pFunc->funcFlags & SQLITE_FUNC_SUBTYPE ){
|
||||
selectWindowRewriteEList(pParse, pMWin, pSrc, pArgs, pTab, &pSublist);
|
||||
pWin->iArgCol = (pSublist ? pSublist->nExpr : 0);
|
||||
pWin->bExprArgs = 1;
|
||||
}else{
|
||||
pWin->iArgCol = (pSublist ? pSublist->nExpr : 0);
|
||||
pSublist = exprListAppendList(pParse, pSublist, pArgs, 0);
|
||||
}
|
||||
if( pWin->pFilter ){
|
||||
Expr *pFilter = sqlite3ExprDup(db, pWin->pFilter, 0);
|
||||
pSublist = sqlite3ExprListAppend(pParse, pSublist, pFilter);
|
||||
@@ -984,7 +991,7 @@ int sqlite3WindowRewrite(Parse *pParse, Select *p){
|
||||
*/
|
||||
if( pSublist==0 ){
|
||||
pSublist = sqlite3ExprListAppend(pParse, 0,
|
||||
sqlite3ExprAlloc(db, TK_INTEGER, &sqlite3IntTokens[0], 0)
|
||||
sqlite3Expr(db, TK_INTEGER, "0")
|
||||
);
|
||||
}
|
||||
|
||||
@@ -1401,102 +1408,6 @@ static int windowArgCount(Window *pWin){
|
||||
return (pList ? pList->nExpr : 0);
|
||||
}
|
||||
|
||||
/*
|
||||
** Generate VM code to invoke either xStep() (if bInverse is 0) or
|
||||
** xInverse (if bInverse is non-zero) for each window function in the
|
||||
** linked list starting at pMWin. Or, for built-in window functions
|
||||
** that do not use the standard function API, generate the required
|
||||
** inline VM code.
|
||||
**
|
||||
** If argument csr is greater than or equal to 0, then argument reg is
|
||||
** the first register in an array of registers guaranteed to be large
|
||||
** enough to hold the array of arguments for each function. In this case
|
||||
** the arguments are extracted from the current row of csr into the
|
||||
** array of registers before invoking OP_AggStep or OP_AggInverse
|
||||
**
|
||||
** Or, if csr is less than zero, then the array of registers at reg is
|
||||
** already populated with all columns from the current row of the sub-query.
|
||||
**
|
||||
** If argument regPartSize is non-zero, then it is a register containing the
|
||||
** number of rows in the current partition.
|
||||
*/
|
||||
static void windowAggStep(
|
||||
Parse *pParse,
|
||||
Window *pMWin, /* Linked list of window functions */
|
||||
int csr, /* Read arguments from this cursor */
|
||||
int bInverse, /* True to invoke xInverse instead of xStep */
|
||||
int reg /* Array of registers */
|
||||
){
|
||||
Vdbe *v = sqlite3GetVdbe(pParse);
|
||||
Window *pWin;
|
||||
for(pWin=pMWin; pWin; pWin=pWin->pNextWin){
|
||||
FuncDef *pFunc = pWin->pFunc;
|
||||
int regArg;
|
||||
int nArg = windowArgCount(pWin);
|
||||
int i;
|
||||
|
||||
assert( bInverse==0 || pWin->eStart!=TK_UNBOUNDED );
|
||||
|
||||
for(i=0; i<nArg; i++){
|
||||
if( i!=1 || pFunc->zName!=nth_valueName ){
|
||||
sqlite3VdbeAddOp3(v, OP_Column, csr, pWin->iArgCol+i, reg+i);
|
||||
}else{
|
||||
sqlite3VdbeAddOp3(v, OP_Column, pMWin->iEphCsr, pWin->iArgCol+i, reg+i);
|
||||
}
|
||||
}
|
||||
regArg = reg;
|
||||
|
||||
if( pMWin->regStartRowid==0
|
||||
&& (pFunc->funcFlags & SQLITE_FUNC_MINMAX)
|
||||
&& (pWin->eStart!=TK_UNBOUNDED)
|
||||
){
|
||||
int addrIsNull = sqlite3VdbeAddOp1(v, OP_IsNull, regArg);
|
||||
VdbeCoverage(v);
|
||||
if( bInverse==0 ){
|
||||
sqlite3VdbeAddOp2(v, OP_AddImm, pWin->regApp+1, 1);
|
||||
sqlite3VdbeAddOp2(v, OP_SCopy, regArg, pWin->regApp);
|
||||
sqlite3VdbeAddOp3(v, OP_MakeRecord, pWin->regApp, 2, pWin->regApp+2);
|
||||
sqlite3VdbeAddOp2(v, OP_IdxInsert, pWin->csrApp, pWin->regApp+2);
|
||||
}else{
|
||||
sqlite3VdbeAddOp4Int(v, OP_SeekGE, pWin->csrApp, 0, regArg, 1);
|
||||
VdbeCoverageNeverTaken(v);
|
||||
sqlite3VdbeAddOp1(v, OP_Delete, pWin->csrApp);
|
||||
sqlite3VdbeJumpHere(v, sqlite3VdbeCurrentAddr(v)-2);
|
||||
}
|
||||
sqlite3VdbeJumpHere(v, addrIsNull);
|
||||
}else if( pWin->regApp ){
|
||||
assert( pFunc->zName==nth_valueName
|
||||
|| pFunc->zName==first_valueName
|
||||
);
|
||||
assert( bInverse==0 || bInverse==1 );
|
||||
sqlite3VdbeAddOp2(v, OP_AddImm, pWin->regApp+1-bInverse, 1);
|
||||
}else if( pFunc->xSFunc!=noopStepFunc ){
|
||||
int addrIf = 0;
|
||||
if( pWin->pFilter ){
|
||||
int regTmp;
|
||||
assert( nArg==0 || nArg==pWin->pOwner->x.pList->nExpr );
|
||||
assert( nArg || pWin->pOwner->x.pList==0 );
|
||||
regTmp = sqlite3GetTempReg(pParse);
|
||||
sqlite3VdbeAddOp3(v, OP_Column, csr, pWin->iArgCol+nArg,regTmp);
|
||||
addrIf = sqlite3VdbeAddOp3(v, OP_IfNot, regTmp, 0, 1);
|
||||
VdbeCoverage(v);
|
||||
sqlite3ReleaseTempReg(pParse, regTmp);
|
||||
}
|
||||
if( pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL ){
|
||||
CollSeq *pColl;
|
||||
assert( nArg>0 );
|
||||
pColl = sqlite3ExprNNCollSeq(pParse, pWin->pOwner->x.pList->a[0].pExpr);
|
||||
sqlite3VdbeAddOp4(v, OP_CollSeq, 0,0,0, (const char*)pColl, P4_COLLSEQ);
|
||||
}
|
||||
sqlite3VdbeAddOp3(v, bInverse? OP_AggInverse : OP_AggStep,
|
||||
bInverse, regArg, pWin->regAccum);
|
||||
sqlite3VdbeAppendP4(v, pFunc, P4_FUNCDEF);
|
||||
sqlite3VdbeChangeP5(v, (u8)nArg);
|
||||
if( addrIf ) sqlite3VdbeJumpHere(v, addrIf);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
typedef struct WindowCodeArg WindowCodeArg;
|
||||
typedef struct WindowCsrAndReg WindowCsrAndReg;
|
||||
|
||||
@@ -1577,13 +1488,6 @@ struct WindowCodeArg {
|
||||
WindowCsrAndReg end;
|
||||
};
|
||||
|
||||
/*
|
||||
** Values that may be passed as the second argument to windowCodeOp().
|
||||
*/
|
||||
#define WINDOW_RETURN_ROW 1
|
||||
#define WINDOW_AGGINVERSE 2
|
||||
#define WINDOW_AGGSTEP 3
|
||||
|
||||
/*
|
||||
** Generate VM code to read the window frames peer values from cursor csr into
|
||||
** an array of registers starting at reg.
|
||||
@@ -1606,6 +1510,133 @@ static void windowReadPeerValues(
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
** Generate VM code to invoke either xStep() (if bInverse is 0) or
|
||||
** xInverse (if bInverse is non-zero) for each window function in the
|
||||
** linked list starting at pMWin. Or, for built-in window functions
|
||||
** that do not use the standard function API, generate the required
|
||||
** inline VM code.
|
||||
**
|
||||
** If argument csr is greater than or equal to 0, then argument reg is
|
||||
** the first register in an array of registers guaranteed to be large
|
||||
** enough to hold the array of arguments for each function. In this case
|
||||
** the arguments are extracted from the current row of csr into the
|
||||
** array of registers before invoking OP_AggStep or OP_AggInverse
|
||||
**
|
||||
** Or, if csr is less than zero, then the array of registers at reg is
|
||||
** already populated with all columns from the current row of the sub-query.
|
||||
**
|
||||
** If argument regPartSize is non-zero, then it is a register containing the
|
||||
** number of rows in the current partition.
|
||||
*/
|
||||
static void windowAggStep(
|
||||
WindowCodeArg *p,
|
||||
Window *pMWin, /* Linked list of window functions */
|
||||
int csr, /* Read arguments from this cursor */
|
||||
int bInverse, /* True to invoke xInverse instead of xStep */
|
||||
int reg /* Array of registers */
|
||||
){
|
||||
Parse *pParse = p->pParse;
|
||||
Vdbe *v = sqlite3GetVdbe(pParse);
|
||||
Window *pWin;
|
||||
for(pWin=pMWin; pWin; pWin=pWin->pNextWin){
|
||||
FuncDef *pFunc = pWin->pFunc;
|
||||
int regArg;
|
||||
int nArg = pWin->bExprArgs ? 0 : windowArgCount(pWin);
|
||||
int i;
|
||||
|
||||
assert( bInverse==0 || pWin->eStart!=TK_UNBOUNDED );
|
||||
|
||||
/* All OVER clauses in the same window function aggregate step must
|
||||
** be the same. */
|
||||
assert( pWin==pMWin || sqlite3WindowCompare(pParse,pWin,pMWin,0)==0 );
|
||||
|
||||
for(i=0; i<nArg; i++){
|
||||
if( i!=1 || pFunc->zName!=nth_valueName ){
|
||||
sqlite3VdbeAddOp3(v, OP_Column, csr, pWin->iArgCol+i, reg+i);
|
||||
}else{
|
||||
sqlite3VdbeAddOp3(v, OP_Column, pMWin->iEphCsr, pWin->iArgCol+i, reg+i);
|
||||
}
|
||||
}
|
||||
regArg = reg;
|
||||
|
||||
if( pMWin->regStartRowid==0
|
||||
&& (pFunc->funcFlags & SQLITE_FUNC_MINMAX)
|
||||
&& (pWin->eStart!=TK_UNBOUNDED)
|
||||
){
|
||||
int addrIsNull = sqlite3VdbeAddOp1(v, OP_IsNull, regArg);
|
||||
VdbeCoverage(v);
|
||||
if( bInverse==0 ){
|
||||
sqlite3VdbeAddOp2(v, OP_AddImm, pWin->regApp+1, 1);
|
||||
sqlite3VdbeAddOp2(v, OP_SCopy, regArg, pWin->regApp);
|
||||
sqlite3VdbeAddOp3(v, OP_MakeRecord, pWin->regApp, 2, pWin->regApp+2);
|
||||
sqlite3VdbeAddOp2(v, OP_IdxInsert, pWin->csrApp, pWin->regApp+2);
|
||||
}else{
|
||||
sqlite3VdbeAddOp4Int(v, OP_SeekGE, pWin->csrApp, 0, regArg, 1);
|
||||
VdbeCoverageNeverTaken(v);
|
||||
sqlite3VdbeAddOp1(v, OP_Delete, pWin->csrApp);
|
||||
sqlite3VdbeJumpHere(v, sqlite3VdbeCurrentAddr(v)-2);
|
||||
}
|
||||
sqlite3VdbeJumpHere(v, addrIsNull);
|
||||
}else if( pWin->regApp ){
|
||||
assert( pFunc->zName==nth_valueName
|
||||
|| pFunc->zName==first_valueName
|
||||
);
|
||||
assert( bInverse==0 || bInverse==1 );
|
||||
sqlite3VdbeAddOp2(v, OP_AddImm, pWin->regApp+1-bInverse, 1);
|
||||
}else if( pFunc->xSFunc!=noopStepFunc ){
|
||||
int addrIf = 0;
|
||||
if( pWin->pFilter ){
|
||||
int regTmp;
|
||||
assert( pWin->bExprArgs || !nArg ||nArg==pWin->pOwner->x.pList->nExpr );
|
||||
assert( pWin->bExprArgs || nArg ||pWin->pOwner->x.pList==0 );
|
||||
regTmp = sqlite3GetTempReg(pParse);
|
||||
sqlite3VdbeAddOp3(v, OP_Column, csr, pWin->iArgCol+nArg,regTmp);
|
||||
addrIf = sqlite3VdbeAddOp3(v, OP_IfNot, regTmp, 0, 1);
|
||||
VdbeCoverage(v);
|
||||
sqlite3ReleaseTempReg(pParse, regTmp);
|
||||
}
|
||||
|
||||
if( pWin->bExprArgs ){
|
||||
int iStart = sqlite3VdbeCurrentAddr(v);
|
||||
VdbeOp *pOp, *pEnd;
|
||||
|
||||
nArg = pWin->pOwner->x.pList->nExpr;
|
||||
regArg = sqlite3GetTempRange(pParse, nArg);
|
||||
sqlite3ExprCodeExprList(pParse, pWin->pOwner->x.pList, regArg, 0, 0);
|
||||
|
||||
pEnd = sqlite3VdbeGetOp(v, -1);
|
||||
for(pOp=sqlite3VdbeGetOp(v, iStart); pOp<=pEnd; pOp++){
|
||||
if( pOp->opcode==OP_Column && pOp->p1==pWin->iEphCsr ){
|
||||
pOp->p1 = csr;
|
||||
}
|
||||
}
|
||||
}
|
||||
if( pFunc->funcFlags & SQLITE_FUNC_NEEDCOLL ){
|
||||
CollSeq *pColl;
|
||||
assert( nArg>0 );
|
||||
pColl = sqlite3ExprNNCollSeq(pParse, pWin->pOwner->x.pList->a[0].pExpr);
|
||||
sqlite3VdbeAddOp4(v, OP_CollSeq, 0,0,0, (const char*)pColl, P4_COLLSEQ);
|
||||
}
|
||||
sqlite3VdbeAddOp3(v, bInverse? OP_AggInverse : OP_AggStep,
|
||||
bInverse, regArg, pWin->regAccum);
|
||||
sqlite3VdbeAppendP4(v, pFunc, P4_FUNCDEF);
|
||||
sqlite3VdbeChangeP5(v, (u8)nArg);
|
||||
if( pWin->bExprArgs ){
|
||||
sqlite3ReleaseTempRange(pParse, regArg, nArg);
|
||||
}
|
||||
if( addrIf ) sqlite3VdbeJumpHere(v, addrIf);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
** Values that may be passed as the second argument to windowCodeOp().
|
||||
*/
|
||||
#define WINDOW_RETURN_ROW 1
|
||||
#define WINDOW_AGGINVERSE 2
|
||||
#define WINDOW_AGGSTEP 3
|
||||
|
||||
/*
|
||||
** Generate VM code to invoke either xValue() (bFin==0) or xFinalize()
|
||||
** (bFin==1) for each window function in the linked list starting at
|
||||
@@ -1668,6 +1699,8 @@ static void windowFullScan(WindowCodeArg *p){
|
||||
int addrNext;
|
||||
int csr;
|
||||
|
||||
VdbeModuleComment((v, "windowFullScan begin"));
|
||||
|
||||
assert( pMWin!=0 );
|
||||
csr = pMWin->csrApp;
|
||||
nPeer = (pMWin->pOrderBy ? pMWin->pOrderBy->nExpr : 0);
|
||||
@@ -1724,7 +1757,7 @@ static void windowFullScan(WindowCodeArg *p){
|
||||
if( addrEq ) sqlite3VdbeJumpHere(v, addrEq);
|
||||
}
|
||||
|
||||
windowAggStep(pParse, pMWin, csr, 0, p->regArg);
|
||||
windowAggStep(p, pMWin, csr, 0, p->regArg);
|
||||
|
||||
sqlite3VdbeResolveLabel(v, lblNext);
|
||||
sqlite3VdbeAddOp2(v, OP_Next, csr, addrNext);
|
||||
@@ -1739,6 +1772,7 @@ static void windowFullScan(WindowCodeArg *p){
|
||||
}
|
||||
|
||||
windowAggFinal(p, 1);
|
||||
VdbeModuleComment((v, "windowFullScan end"));
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -2069,9 +2103,7 @@ static int windowCodeOp(
|
||||
Window *pMWin = p->pMWin;
|
||||
int ret = 0;
|
||||
Vdbe *v = p->pVdbe;
|
||||
int addrIf = 0;
|
||||
int addrContinue = 0;
|
||||
int addrGoto = 0;
|
||||
int bPeer = (pMWin->eFrmType!=TK_ROWS);
|
||||
|
||||
int lblDone = sqlite3VdbeMakeLabel(pParse);
|
||||
@@ -2104,7 +2136,7 @@ static int windowCodeOp(
|
||||
);
|
||||
}
|
||||
}else{
|
||||
addrIf = sqlite3VdbeAddOp3(v, OP_IfPos, regCountdown, 0, 1);
|
||||
sqlite3VdbeAddOp3(v, OP_IfPos, regCountdown, lblDone, 1);
|
||||
VdbeCoverage(v);
|
||||
}
|
||||
}
|
||||
@@ -2113,6 +2145,25 @@ static int windowCodeOp(
|
||||
windowAggFinal(p, 0);
|
||||
}
|
||||
addrContinue = sqlite3VdbeCurrentAddr(v);
|
||||
|
||||
/* If this is a (RANGE BETWEEN a FOLLOWING AND b FOLLOWING) or
|
||||
** (RANGE BETWEEN b PRECEDING AND a PRECEDING) frame, ensure the
|
||||
** start cursor does not advance past the end cursor within the
|
||||
** temporary table. It otherwise might, if (a>b). */
|
||||
if( pMWin->eStart==pMWin->eEnd && regCountdown
|
||||
&& pMWin->eFrmType==TK_RANGE && op==WINDOW_AGGINVERSE
|
||||
){
|
||||
int regRowid1 = sqlite3GetTempReg(pParse);
|
||||
int regRowid2 = sqlite3GetTempReg(pParse);
|
||||
sqlite3VdbeAddOp2(v, OP_Rowid, p->start.csr, regRowid1);
|
||||
sqlite3VdbeAddOp2(v, OP_Rowid, p->end.csr, regRowid2);
|
||||
sqlite3VdbeAddOp3(v, OP_Ge, regRowid2, lblDone, regRowid1);
|
||||
VdbeCoverage(v);
|
||||
sqlite3ReleaseTempReg(pParse, regRowid1);
|
||||
sqlite3ReleaseTempReg(pParse, regRowid2);
|
||||
assert( pMWin->eStart==TK_PRECEDING || pMWin->eStart==TK_FOLLOWING );
|
||||
}
|
||||
|
||||
switch( op ){
|
||||
case WINDOW_RETURN_ROW:
|
||||
csr = p->current.csr;
|
||||
@@ -2127,7 +2178,7 @@ static int windowCodeOp(
|
||||
assert( pMWin->regEndRowid );
|
||||
sqlite3VdbeAddOp2(v, OP_AddImm, pMWin->regStartRowid, 1);
|
||||
}else{
|
||||
windowAggStep(pParse, pMWin, csr, 1, p->regArg);
|
||||
windowAggStep(p, pMWin, csr, 1, p->regArg);
|
||||
}
|
||||
break;
|
||||
|
||||
@@ -2139,7 +2190,7 @@ static int windowCodeOp(
|
||||
assert( pMWin->regEndRowid );
|
||||
sqlite3VdbeAddOp2(v, OP_AddImm, pMWin->regEndRowid, 1);
|
||||
}else{
|
||||
windowAggStep(pParse, pMWin, csr, 0, p->regArg);
|
||||
windowAggStep(p, pMWin, csr, 0, p->regArg);
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -2157,7 +2208,7 @@ static int windowCodeOp(
|
||||
sqlite3VdbeAddOp2(v, OP_Next, csr, sqlite3VdbeCurrentAddr(v)+1+bPeer);
|
||||
VdbeCoverage(v);
|
||||
if( bPeer ){
|
||||
addrGoto = sqlite3VdbeAddOp0(v, OP_Goto);
|
||||
sqlite3VdbeAddOp2(v, OP_Goto, 0, lblDone);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2173,8 +2224,6 @@ static int windowCodeOp(
|
||||
sqlite3VdbeAddOp2(v, OP_Goto, 0, addrNextRange);
|
||||
}
|
||||
sqlite3VdbeResolveLabel(v, lblDone);
|
||||
if( addrGoto ) sqlite3VdbeJumpHere(v, addrGoto);
|
||||
if( addrIf ) sqlite3VdbeJumpHere(v, addrIf);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -2190,6 +2239,7 @@ Window *sqlite3WindowDup(sqlite3 *db, Expr *pOwner, Window *p){
|
||||
pNew = sqlite3DbMallocZero(db, sizeof(Window));
|
||||
if( pNew ){
|
||||
pNew->zName = sqlite3DbStrDup(db, p->zName);
|
||||
pNew->zBase = sqlite3DbStrDup(db, p->zBase);
|
||||
pNew->pFilter = sqlite3ExprDup(db, p->pFilter, 0);
|
||||
pNew->pFunc = p->pFunc;
|
||||
pNew->pPartition = sqlite3ExprListDup(db, p->pPartition, 0);
|
||||
@@ -2202,6 +2252,7 @@ Window *sqlite3WindowDup(sqlite3 *db, Expr *pOwner, Window *p){
|
||||
pNew->pStart = sqlite3ExprDup(db, p->pStart, 0);
|
||||
pNew->pEnd = sqlite3ExprDup(db, p->pEnd, 0);
|
||||
pNew->pOwner = pOwner;
|
||||
pNew->bImplicitFrame = p->bImplicitFrame;
|
||||
}
|
||||
}
|
||||
return pNew;
|
||||
@@ -2525,7 +2576,7 @@ static int windowExprGtZero(Parse *pParse, Expr *pExpr){
|
||||
** regEnd = <expr2>
|
||||
** regStart = <expr1>
|
||||
** }else{
|
||||
** if( (csrEnd.key + regEnd) <= csrCurrent.key ){
|
||||
** while( (csrEnd.key + regEnd) <= csrCurrent.key ){
|
||||
** AGGSTEP
|
||||
** }
|
||||
** while( (csrStart.key + regStart) < csrCurrent.key ){
|
||||
@@ -2598,8 +2649,6 @@ void sqlite3WindowCodeStep(
|
||||
int addrGosubFlush = 0; /* Address of OP_Gosub to flush: */
|
||||
int addrInteger = 0; /* Address of OP_Integer */
|
||||
int addrEmpty; /* Address of OP_Rewind in flush: */
|
||||
int regStart = 0; /* Value of <expr> PRECEDING */
|
||||
int regEnd = 0; /* Value of <expr> FOLLOWING */
|
||||
int regNew; /* Array of registers holding new input row */
|
||||
int regRecord; /* regNew array in record form */
|
||||
int regRowid; /* Rowid for regRecord in eph table */
|
||||
@@ -2608,6 +2657,8 @@ void sqlite3WindowCodeStep(
|
||||
int regFlushPart = 0; /* Register for "Gosub flush_partition" */
|
||||
WindowCodeArg s; /* Context object for sub-routines */
|
||||
int lblWhereEnd; /* Label just before sqlite3WhereEnd() code */
|
||||
int regStart = 0; /* Value of <expr> PRECEDING */
|
||||
int regEnd = 0; /* Value of <expr> FOLLOWING */
|
||||
|
||||
assert( pMWin->eStart==TK_PRECEDING || pMWin->eStart==TK_CURRENT
|
||||
|| pMWin->eStart==TK_FOLLOWING || pMWin->eStart==TK_UNBOUNDED
|
||||
@@ -2738,11 +2789,11 @@ void sqlite3WindowCodeStep(
|
||||
|
||||
if( regStart ){
|
||||
sqlite3ExprCode(pParse, pMWin->pStart, regStart);
|
||||
windowCheckValue(pParse, regStart, 0 + (pMWin->eFrmType==TK_RANGE ? 3 : 0));
|
||||
windowCheckValue(pParse, regStart, 0 + (pMWin->eFrmType==TK_RANGE?3:0));
|
||||
}
|
||||
if( regEnd ){
|
||||
sqlite3ExprCode(pParse, pMWin->pEnd, regEnd);
|
||||
windowCheckValue(pParse, regEnd, 1 + (pMWin->eFrmType==TK_RANGE ? 3 : 0));
|
||||
windowCheckValue(pParse, regEnd, 1 + (pMWin->eFrmType==TK_RANGE?3:0));
|
||||
}
|
||||
|
||||
if( pMWin->eFrmType!=TK_RANGE && pMWin->eStart==pMWin->eEnd && regStart ){
|
||||
|
||||
+14
-9
@@ -118,14 +118,19 @@ do_execsql_test 507 {
|
||||
|
||||
# 2019-08-30 ticket https://www.sqlite.org/src/info/40812aea1fde9594
|
||||
#
|
||||
do_execsql_test 600 {
|
||||
DROP TABLE IF EXISTS t0;
|
||||
CREATE TABLE t0(c0 REAL UNIQUE);
|
||||
INSERT INTO t0(c0) VALUES (3175546974276630385);
|
||||
SELECT 3175546974276630385 < c0 FROM t0;
|
||||
} {1}
|
||||
do_execsql_test 601 {
|
||||
SELECT 1 FROM t0 WHERE 3175546974276630385 < c0;
|
||||
} {1}
|
||||
# Due to some differences in floating point computations, these tests do not
|
||||
# work under valgrind.
|
||||
#
|
||||
if {![info exists ::G(valgrind)]} {
|
||||
do_execsql_test 600 {
|
||||
DROP TABLE IF EXISTS t0;
|
||||
CREATE TABLE t0(c0 REAL UNIQUE);
|
||||
INSERT INTO t0(c0) VALUES (3175546974276630385);
|
||||
SELECT 3175546974276630385 < c0 FROM t0;
|
||||
} {1}
|
||||
do_execsql_test 601 {
|
||||
SELECT 1 FROM t0 WHERE 3175546974276630385 < c0;
|
||||
} {1}
|
||||
}
|
||||
|
||||
finish_test
|
||||
|
||||
+10
-4
@@ -377,11 +377,14 @@ do_test 4.0 {
|
||||
| end crash-6b48ba69806134.db
|
||||
}]} {}
|
||||
|
||||
set res {1 {database disk image is malformed}}
|
||||
ifcapable oversize_cell_check {
|
||||
set res {1 {no such table: t3}}
|
||||
}
|
||||
do_catchsql_test 4.1 {
|
||||
PRAGMA writable_schema=ON; -- bypass improved sqlite_master consistency checking
|
||||
INSERT INTO t3 SELECT * FROM t2;
|
||||
} {1 {database disk image is malformed}}
|
||||
|
||||
} $res
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
@@ -835,11 +838,14 @@ do_test 8.0 {
|
||||
| end a.db
|
||||
}]} {}
|
||||
|
||||
|
||||
set res {1 {database disk image is malformed}}
|
||||
ifcapable oversize_cell_check {
|
||||
set res {1 {no such table: t3}}
|
||||
}
|
||||
do_catchsql_test 8.1 {
|
||||
PRAGMA writable_schema=ON; -- bypass improved sqlite_master consistency checking
|
||||
INSERT INTO t3 SELECT * FROM t2;
|
||||
} {1 {database disk image is malformed}}
|
||||
} $res
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
|
||||
+36
-52
@@ -22,6 +22,16 @@ set testprefix corruptM
|
||||
#
|
||||
database_may_be_corrupt
|
||||
|
||||
proc open_db2_and_catchsql {sql} {
|
||||
set rc [catch { sqlite3 db2 test.db } msg]
|
||||
if {$rc} {
|
||||
return [list $rc $msg]
|
||||
}
|
||||
set res [catchsql $sql db2]
|
||||
db2 close
|
||||
set res
|
||||
}
|
||||
|
||||
db close
|
||||
forcedelete test.db
|
||||
sqlite3 db test.db
|
||||
@@ -38,165 +48,139 @@ do_execsql_test corruptM-101 {
|
||||
UPDATE sqlite_master SET tbl_name=NULL WHERE name='t1';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {table t1 {} | index i1 t1 | view v2 v2 | trigger r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-102 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (t1)}}
|
||||
db2 close
|
||||
|
||||
do_execsql_test corruptM-110 {
|
||||
UPDATE sqlite_master SET tbl_name='tx' WHERE name='t1';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {table t1 tx | index i1 t1 | view v2 v2 | trigger r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-111 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (t1)}}
|
||||
db2 close
|
||||
do_execsql_test corruptM-112 {
|
||||
UPDATE sqlite_master SET tbl_name='t1', type='tabl' WHERE name='t1';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {tabl t1 t1 | index i1 t1 | view v2 v2 | trigger r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-113 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (t1)}}
|
||||
db2 close
|
||||
do_execsql_test corruptM-114 {
|
||||
UPDATE sqlite_master SET tbl_name='t9',type='table',name='t9'WHERE name='t1';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {table t9 t9 | index i1 t1 | view v2 v2 | trigger r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-114 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (t9)}}
|
||||
db2 close
|
||||
|
||||
do_execsql_test corruptM-120 {
|
||||
UPDATE sqlite_master SET name='t1',tbl_name='T1' WHERE name='t9';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {table t1 T1 | index i1 t1 | view v2 v2 | trigger r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-121 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
SELECT * FROM t1, v2;
|
||||
} db2
|
||||
}
|
||||
} {0 {ok 111 222 333 15 22}}
|
||||
db2 close
|
||||
|
||||
do_execsql_test corruptM-130 {
|
||||
UPDATE sqlite_master SET type='view' WHERE name='t1';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {view t1 T1 | index i1 t1 | view v2 v2 | trigger r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-131 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
SELECT * FROM t1, v2;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (t1)}}
|
||||
db2 close
|
||||
|
||||
do_execsql_test corruptM-140 {
|
||||
UPDATE sqlite_master SET type='table', tbl_name='t1' WHERE name='t1';
|
||||
UPDATE sqlite_master SET tbl_name='tx' WHERE name='i1';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {table t1 t1 | index i1 tx | view v2 v2 | trigger r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-141 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
SELECT * FROM t1, v2;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (i1)}}
|
||||
db2 close
|
||||
|
||||
do_execsql_test corruptM-150 {
|
||||
UPDATE sqlite_master SET type='table', tbl_name='t1' WHERE name='i1';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {table t1 t1 | table i1 t1 | view v2 v2 | trigger r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-151 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
SELECT * FROM t1, v2;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (i1)}}
|
||||
db2 close
|
||||
|
||||
do_execsql_test corruptM-160 {
|
||||
UPDATE sqlite_master SET type='view', tbl_name='t1' WHERE name='i1';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {table t1 t1 | view i1 t1 | view v2 v2 | trigger r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-161 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
SELECT * FROM t1, v2;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (i1)}}
|
||||
db2 close
|
||||
|
||||
do_execsql_test corruptM-170 {
|
||||
UPDATE sqlite_master SET type='index', tbl_name='t1' WHERE name='i1';
|
||||
UPDATE sqlite_master SET type='table', tbl_name='v2' WHERE name='v2';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {table t1 t1 | index i1 t1 | table v2 v2 | trigger r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-171 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
SELECT * FROM t1, v2;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (v2)}}
|
||||
db2 close
|
||||
|
||||
do_execsql_test corruptM-180 {
|
||||
UPDATE sqlite_master SET type='view',name='v3',tbl_name='v3' WHERE name='v2';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {table t1 t1 | index i1 t1 | view v3 v3 | trigger r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-181 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
SELECT * FROM t1, v2;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (v3)}}
|
||||
db2 close
|
||||
|
||||
do_execsql_test corruptM-190 {
|
||||
UPDATE sqlite_master SET type='view',name='v2',tbl_name='v2' WHERE name='v3';
|
||||
UPDATE sqlite_master SET type='view' WHERE name='r1';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {table t1 t1 | index i1 t1 | view v2 v2 | view r1 t1 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-191 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
SELECT * FROM t1, v2;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (r1)}}
|
||||
db2 close
|
||||
do_execsql_test corruptM-192 {
|
||||
UPDATE sqlite_master SET type='trigger',tbl_name='v2' WHERE name='r1';
|
||||
SELECT type, name, tbl_name, '|' FROM sqlite_master;
|
||||
} {table t1 t1 | index i1 t1 | view v2 v2 | trigger r1 v2 |}
|
||||
sqlite3 db2 test.db
|
||||
do_test corruptM-193 {
|
||||
catchsql {
|
||||
open_db2_and_catchsql {
|
||||
PRAGMA quick_check;
|
||||
SELECT * FROM t1, v2;
|
||||
} db2
|
||||
}
|
||||
} {1 {malformed database schema (r1)}}
|
||||
db2 close
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -101,4 +101,68 @@ do_catchsql_test 2.3 {
|
||||
SELECT sum(a) FILTER (WHERE 1 - count(a)) FROM t1
|
||||
} {1 {misuse of aggregate function count()}}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
do_execsql_test 3.0 {
|
||||
CREATE TABLE t1(a,b);
|
||||
INSERT INTO t1 VALUES(1, 1);
|
||||
}
|
||||
do_execsql_test 3.1 {
|
||||
SELECT b, max(a) FILTER (WHERE b='x') FROM t1;
|
||||
} {1 {}}
|
||||
|
||||
do_execsql_test 3.2 {
|
||||
CREATE TABLE t2(a, b, c);
|
||||
INSERT INTO t2 VALUES(1, 2, 3);
|
||||
INSERT INTO t2 VALUES(1, 3, 4);
|
||||
INSERT INTO t2 VALUES(2, 5, 6);
|
||||
INSERT INTO t2 VALUES(2, 7, 8);
|
||||
}
|
||||
do_execsql_test 3.3 {
|
||||
SELECT a, c, max(b) FILTER (WHERE c='x') FROM t2 GROUP BY a;
|
||||
} {1 3 {} 2 6 {}}
|
||||
|
||||
do_execsql_test 3.4 {
|
||||
DELETE FROM t2;
|
||||
INSERT INTO t2 VALUES(1, 5, 'x');
|
||||
INSERT INTO t2 VALUES(1, 2, 3);
|
||||
INSERT INTO t2 VALUES(1, 4, 'x');
|
||||
INSERT INTO t2 VALUES(2, 5, 6);
|
||||
INSERT INTO t2 VALUES(2, 7, 8);
|
||||
}
|
||||
do_execsql_test 3.5 {
|
||||
SELECT a, c, max(b) FILTER (WHERE c='x') FROM t2 GROUP BY a;
|
||||
} {1 x 5 2 6 {}}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
do_execsql_test 4.0 {
|
||||
CREATE TABLE t1(a, b, c);
|
||||
INSERT INTO t1 VALUES('a', 0, 5);
|
||||
INSERT INTO t1 VALUES('a', 1, 10);
|
||||
INSERT INTO t1 VALUES('a', 0, 15);
|
||||
|
||||
INSERT INTO t1 VALUES('b', 0, 5);
|
||||
INSERT INTO t1 VALUES('b', 1, 1000);
|
||||
INSERT INTO t1 VALUES('b', 0, 5);
|
||||
|
||||
INSERT INTO t1 VALUES('c', 0, 1);
|
||||
INSERT INTO t1 VALUES('c', 1, 2);
|
||||
INSERT INTO t1 VALUES('c', 0, 3);
|
||||
}
|
||||
|
||||
do_execsql_test 4.1 {
|
||||
SELECT avg(c) FILTER (WHERE b!=1) AS h FROM t1 GROUP BY a ORDER BY h;
|
||||
} {2.0 5.0 10.0}
|
||||
do_execsql_test 4.2 {
|
||||
SELECT avg(c) FILTER (WHERE b!=1) AS h FROM t1 GROUP BY a ORDER BY (h+1.0);
|
||||
} {2.0 5.0 10.0}
|
||||
do_execsql_test 4.3 {
|
||||
SELECT a, avg(c) FILTER (WHERE b!=1) AS h FROM t1 GROUP BY a ORDER BY avg(c);
|
||||
} {c 2.0 a 10.0 b 5.0}
|
||||
do_execsql_test 4.4 {
|
||||
SELECT a, avg(c) FILTER (WHERE b!=1) FROM t1 GROUP BY a ORDER BY 2
|
||||
} {c 2.0 b 5.0 a 10.0}
|
||||
|
||||
finish_test
|
||||
|
||||
|
||||
@@ -5329,4 +5329,221 @@ do_catchsql_test 29.1 {
|
||||
INSERT INTO t1(t1) SELECT x FROM t2;
|
||||
} {1 {database disk image is malformed}}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
#
|
||||
reset_db
|
||||
do_test 30.0 {
|
||||
sqlite3 db {}
|
||||
db deserialize [decode_hexdb {
|
||||
| size 28672 pagesize 4096 filename crash-e6e3857edf9b26.db
|
||||
| page 1 offset 0
|
||||
| 0: 53 51 4c 69 74 65 20 66 6f 72 6d 61 74 20 33 00 SQLite format 3.
|
||||
| 16: 10 00 01 01 00 40 20 20 00 00 00 00 00 00 00 00 .....@ ........
|
||||
| 96: 00 00 00 00 0d 0e b1 00 06 0d a4 00 0f 8d 0f 21 ...............!
|
||||
| 112: 0e b9 0d c8 0e 7e 0d a4 00 00 00 00 00 00 00 00 .....~..........
|
||||
| 3488: 00 00 00 00 22 07 06 17 11 11 01 31 74 61 62 6c ...........1tabl
|
||||
| 3504: 65 74 32 74 32 07 43 52 45 41 54 45 20 54 41 42 et2t2.CREATE TAB
|
||||
| 3520: 4c 45 20 74 32 28 78 29 81 33 05 07 17 1f 1f 01 LE t2(x).3......
|
||||
| 3536: 82 35 74 61 62 6c 65 74 31 5f 73 65 67 64 69 72 .5tablet1_segdir
|
||||
| 3552: 74 31 5f 73 65 67 64 69 72 05 43 52 45 41 54 45 t1_segdir.CREATE
|
||||
| 3568: 20 54 41 42 4c 45 20 27 74 31 5f 73 65 67 64 69 TABLE 't1_segdi
|
||||
| 3584: 72 27 28 6c 65 76 65 6c 20 49 4e 54 45 47 45 52 r'(level INTEGER
|
||||
| 3600: 2c 69 64 78 20 49 4e 54 45 47 45 52 2c 73 74 61 ,idx INTEGER,sta
|
||||
| 3616: 72 74 5f 62 6c 6f 63 6b 20 49 4e 54 45 47 45 52 rt_block INTEGER
|
||||
| 3632: 2c 6c 65 61 76 65 73 5f 65 6e 64 5f 62 6c 6f 63 ,leaves_end_bloc
|
||||
| 3648: 6b 20 49 4e 54 45 47 45 52 2c 65 6e 64 5f 62 6c k INTEGER,end_bl
|
||||
| 3664: 6f 63 6b 20 49 4e 54 45 47 45 62 2c 72 6f 6f 74 ock INTEGEb,root
|
||||
| 3680: 20 42 4c 4f 42 2c 50 52 49 4d 41 52 59 20 4b 45 BLOB,PRIMARY KE
|
||||
| 3696: 59 28 6c 65 76 65 6c 2c 20 69 64 78 29 29 31 06 Y(level, idx))1.
|
||||
| 3712: 06 17 45 1f 01 00 69 6e 64 65 78 73 71 6c 69 74 ..E...indexsqlit
|
||||
| 3728: 65 5f 61 75 74 6f 69 6e 64 65 78 5f 74 31 5f 73 e_autoindex_t1_s
|
||||
| 3744: 65 67 64 69 72 5f 31 74 31 5f 73 65 67 64 69 72 egdir_1t1_segdir
|
||||
| 3760: 06 0f c7 00 08 00 00 00 00 66 04 07 17 23 23 01 .........f...##.
|
||||
| 3776: 81 13 74 61 62 6c 65 74 31 5f 73 65 67 6d 65 6e ..tablet1_segmen
|
||||
| 3792: 74 73 74 31 5f 73 65 67 6d 65 6e 74 73 04 43 52 tst1_segments.CR
|
||||
| 3808: 45 41 54 45 20 54 41 42 4c 45 20 27 74 31 5f 73 EATE TABLE 't1_s
|
||||
| 3824: 65 67 6d 65 6e 74 73 27 28 62 6c 6f 63 6b 69 64 egments'(blockid
|
||||
| 3840: 20 49 4e 54 45 47 45 52 20 50 52 49 4d 41 52 59 INTEGER PRIMARY
|
||||
| 3856: 20 4b 45 59 2c 20 62 6c 6f 63 6b 20 42 4c 4f 42 KEY, block BLOB
|
||||
| 3872: 29 6a 03 07 17 21 21 01 81 1f 74 61 62 6c 65 74 )j...!!...tablet
|
||||
| 3888: 31 5f 63 6f 6e 74 65 6e 74 74 31 5f 63 6f 6e 74 1_contentt1_cont
|
||||
| 3904: 65 6e 74 03 43 52 45 41 54 45 20 54 41 42 4c 45 ent.CREATE TABLE
|
||||
| 3920: 20 27 74 31 5f 63 6f 6e 74 65 6e 74 27 28 64 6f 't1_content'(do
|
||||
| 3936: 63 69 64 20 49 4e 54 45 47 45 52 20 50 52 49 4d cid INTEGER PRIM
|
||||
| 3952: 41 52 59 20 4b 45 59 2c 20 27 63 30 61 27 2c 20 ARY KEY, 'c0a',
|
||||
| 3968: 27 63 31 62 27 2c 20 27 63 32 63 27 29 38 02 06 'c1b', 'c2c')8..
|
||||
| 3984: 17 11 11 08 5f 74 61 62 6c 65 74 31 74 31 43 52 ...._tablet1t1CR
|
||||
| 4000: 45 41 54 45 20 56 49 52 54 55 41 4c 20 54 41 42 EATE VIRTUAL TAB
|
||||
| 4016: 4c 45 20 74 31 20 55 53 49 4e 47 20 66 74 73 33 LE t1 USING fts3
|
||||
| 4032: 28 61 2c 62 2c 63 29 00 00 00 00 00 00 00 00 00 (a,b,c).........
|
||||
| page 3 offset 8192
|
||||
| 0: 0d 00 00 00 25 0b 48 00 0f d8 0f af 0f 86 0f 74 ....%.H........t
|
||||
| 16: 0f 61 0f 4e 0f 2f 0f 0f 0e ef 0e d7 0e be 0e a5 .a.N./..........
|
||||
| 32: 0e 8d 0e 74 0e 5b 0e 40 0e 24 0e 08 0d ef 00 00 ...t.[.@.$......
|
||||
| 2880: 00 00 00 00 00 00 00 00 81 3f 25 06 00 82 7e f0 .........?%...~.
|
||||
| 2896: 00 43 4f 4d 50 49 4c 45 52 3d 67 63 63 2d 35 2e .COMPILER=gcc-5.
|
||||
| 2912: 34 23 00 20 32 30 31 36 30 36 30 39 20 44 45 42 4#. 20160609 DEB
|
||||
| 2928: 55 47 20 45 4e 41 42 4c 45 20 44 42 53 54 41 54 UG ENABLE DBSTAT
|
||||
| 2944: 20 56 54 41 42 20 45 4e 42 92 4c 45 20 46 54 53 VTAB ENB.LE FTS
|
||||
| 2960: 34 20 45 4e 41 42 4c 45 20 46 54 53 35 20 45 4e 4 ENABLE FTS5 EN
|
||||
| 2976: 41 42 4c 45 20 47 45 4f 50 4f 4c 59 20 45 4e 41 ABLE GEOPOLY ENA
|
||||
| 2992: 42 4c 45 1f 4a 53 4f 4e 31 20 45 4e 41 42 4c 49 BLE.JSON1 ENABLI
|
||||
| 3008: 00 4d 45 4d 53 59 53 35 20 45 4e 41 42 4c 45 20 .MEMSYS5 ENABLE
|
||||
| 3024: 52 54 52 45 45 20 4d 41 58 20 4d 45 4d 4f 52 59 RTREE MAX MEMORY
|
||||
| 3040: 3d 35 30 30 30 30 30 30 30 20 4f 4d 49 54 20 4c =50000000 OMIT L
|
||||
| 3056: 4f 41 44 20 45 58 54 45 4e 53 49 4f 4e 20 54 48 OAD EXTENSION TH
|
||||
| 3072: 52 45 41 44 53 41 46 45 3d 30 18 24 05 00 25 0f READSAFE=0.$..%.
|
||||
| 3088: 19 54 48 52 45 41 44 53 41 46 45 3d 30 58 42 49 .THREADSAFE=0XBI
|
||||
| 3104: 4e 41 52 59 18 23 05 00 25 0f 19 54 48 52 45 41 NARY.#..%..THREA
|
||||
| 3120: 44 53 41 46 45 3d 30 88 4e 4f 43 41 53 45 17 22 DSAFE=0.NOCASE..
|
||||
| 3136: 05 00 25 0f 17 54 48 52 45 41 44 53 41 46 45 3d ..%..THREADSAFE=
|
||||
| 3152: 30 58 52 54 52 49 4d 1f 21 05 00 33 0f 19 4f 4d 0XRTRIM.!..3..OM
|
||||
| 3168: 49 54 20 4c 4f 41 44 20 45 58 54 45 4e 53 49 4f IT LOAD EXTENSIO
|
||||
| 3184: 4e 58 42 49 4e 41 52 59 1f 20 05 00 33 0f 19 4f NXBINARY. ..3..O
|
||||
| 3200: 4d 49 54 20 4c 4f 41 44 20 45 58 54 45 4e 53 49 MIT LOAD EXTENSI
|
||||
| 3216: 4f 4e 58 4e 4f 43 41 53 45 1e 20 05 00 33 0f 17 ONXNOCASE. ..3..
|
||||
| 3232: 4f 4d 49 54 20 4c 4f 41 54 20 45 58 54 45 4e 53 OMIT LOAT EXTENS
|
||||
| 3248: 49 4f 4e 58 52 54 52 49 4d 1f 1e 04 00 33 0f 19 IONXRTRIM....3..
|
||||
| 3264: 82 41 58 20 4d 45 4d 4f 52 59 3d 35 30 30 30 30 .AX MEMORY=50000
|
||||
| 3280: 30 30 30 58 42 49 4e 41 52 59 1f 1d 05 00 33 0f 000XBINARY....3.
|
||||
| 3296: 19 4d 41 58 20 4d 45 4d 4f 52 59 3d 35 30 30 30 .MAX MEMORY=5000
|
||||
| 3312: 30 30 30 30 58 4e 4f 43 41 53 45 1e 1c 05 00 33 0000XNOCASE....3
|
||||
| 3328: 0f 17 4d 41 58 20 4d 45 4d fa 52 59 3d 35 30 20 ..MAX MEM.RY=50
|
||||
| 3344: 30 30 30 30 30 58 52 54 52 49 4d 18 1b 05 00 25 00000XRTRIM....%
|
||||
| 3360: 0f 19 45 4e 41 42 4c 45 20 52 53 52 45 45 58 42 ..ENABLE RSREEXB
|
||||
| 3376: 49 4e 41 52 59 18 1a 05 00 25 0f 19 45 4e 41 42 INARY....%..ENAB
|
||||
| 3392: 4c 45 20 52 54 52 45 45 58 4e 4f 53 41 53 45 17 LE RTREEXNOSASE.
|
||||
| 3408: 19 05 00 25 0f 17 45 4e 42 42 4c 45 20 52 54 52 ...%..ENBBLE RTR
|
||||
| 3424: 45 45 58 52 54 52 49 4d 1a 18 05 00 29 0f 19 45 EEXRTRIM....)..E
|
||||
| 3440: 4e 41 42 4c 45 20 4d 45 4d 53 5a 53 35 58 42 49 NABLE MEMSZS5XBI
|
||||
| 3456: 4e 41 52 59 1a 17 05 00 29 0f 19 45 4e 41 42 3c NARY....)..ENAB<
|
||||
| 3472: 45 20 4d 45 4d 53 59 53 35 58 4e 4f 43 41 53 45 E MEMSYS5XNOCASE
|
||||
| 3488: 19 16 05 00 29 0f 17 45 4e 41 42 4c 45 20 4d 45 ....)..ENABLE ME
|
||||
| 3504: 4d 53 59 53 35 58 52 54 52 49 4d 18 15 05 00 25 MSYS5XRTRIM....%
|
||||
| 3520: 0f 19 45 4e 41 42 4c 45 20 4a 53 4f 4e 31 58 42 ..ENABLE JSON1XB
|
||||
| 3536: 49 4e 41 52 59 18 14 05 00 25 0f 19 45 4e 41 42 INARY....%..ENAB
|
||||
| 3552: 4c 45 20 4a 53 4f 4e 31 58 4e 4f 43 41 53 45 17 LE JSON1XNOCASE.
|
||||
| 3568: 13 05 00 25 0f 17 45 4e 41 42 4c 45 20 4a 53 4f ...%..ENABLE JSO
|
||||
| 3584: 4e 31 58 52 54 52 49 4d 1a 12 05 00 29 0f 19 45 N1XRTRIM....)..E
|
||||
| 3600: 4e 31 42 4c 45 20 47 45 4e 50 4f 4c 59 58 42 49 N1BLE GENPOLYXBI
|
||||
| 3616: 4e 41 52 59 1a 11 05 00 29 0f 19 45 4e f2 1e 4c NARY....)..EN..L
|
||||
| 3632: 45 20 47 45 4f 50 4f 4c 59 58 4e 4f 43 41 53 45 E GEOPOLYXNOCASE
|
||||
| 3648: 19 10 05 00 29 0f 17 45 4e 41 42 4c 45 20 47 45 ....)..ENABLE GE
|
||||
| 3664: 4f 50 4f 4c 59 58 52 54 52 49 4d 17 0f 05 00 23 OPOLYXRTRIM....#
|
||||
| 3680: 0f 19 45 4e 41 42 4c 45 20 46 54 53 35 58 42 49 ..ENABLE FTS5XBI
|
||||
| 3696: 4e 41 52 59 17 0e 05 00 23 0f 19 45 4e 41 42 3c NARY....#..ENAB<
|
||||
| 3712: 45 20 46 54 53 35 58 4e 4f 43 41 53 45 16 0d 05 E FTS5XNOCASE...
|
||||
| 3728: 00 23 0f 17 45 4e 41 42 4c 45 20 46 54 53 35 58 .#..ENABLE FTS5X
|
||||
| 3744: 52 54 52 49 4d 17 0c 05 00 23 0f 19 45 4e 41 42 RTRIM....#..ENAB
|
||||
| 3760: 4c 45 20 46 54 53 34 58 42 49 4e 41 52 59 17 0b LE FTS4XBINARY..
|
||||
| 3776: 05 00 23 0f 19 45 4e 41 43 4c 45 20 46 54 53 35 ..#..ENACLE FTS5
|
||||
| 3792: 58 4e 4f 43 40 53 45 16 0a 05 00 23 0f 17 45 4e XNOC@SE....#..EN
|
||||
| 3808: 41 42 4c 45 20 46 54 53 34 58 52 54 52 49 4d 1e ABLE FTS4XRTRIM.
|
||||
| 3824: 09 05 00 31 0f 19 45 4e 41 42 4c 45 20 44 42 53 ...1..ENABLE DBS
|
||||
| 3840: 54 41 55 20 56 54 41 42 58 42 49 4e 41 52 59 1e TAU VTABXBINARY.
|
||||
| 3856: 08 05 00 31 0f 19 45 4e 41 42 4c 45 20 44 42 53 ...1..ENABLE DBS
|
||||
| 3872: 54 41 54 20 56 54 41 42 58 4e 4f 43 41 53 45 1d TAT VTABXNOCASE.
|
||||
| 3888: 07 05 00 31 0f 17 45 4e 41 42 4c 45 20 44 42 53 ...1..ENABLE DBS
|
||||
| 3904: 54 41 54 20 56 54 41 42 58 52 54 62 49 4d 11 06 TAT VTABXRTbIM..
|
||||
| 3920: 05 00 17 0f 19 44 45 42 54 47 58 42 49 4e 41 52 .....DEBTGXBINAR
|
||||
| 3936: 59 11 05 05 00 17 0f 19 54 45 42 55 47 58 4e 4f Y.......TEBUGXNO
|
||||
| 3952: 43 41 53 45 10 04 05 00 17 0f 17 44 45 42 55 47 CASE.......DEBUG
|
||||
| 3968: 68 52 54 52 49 4d 27 03 05 00 43 0f 19 43 4f 4d hRTRIM'...C..COM
|
||||
| 3984: 50 49 4c 45 52 3d 67 63 63 2d 35 2e 34 2e 30 20 PILER=gcc-5.4.0
|
||||
| 4000: 32 30 31 36 30 36 30 39 58 42 49 4e 41 52 59 27 20160609XBINARY'
|
||||
| 4016: 02 05 00 43 0f 19 43 4f 4d 50 49 4c 45 52 3d 67 ...C..COMPILER=g
|
||||
| 4032: 63 63 2d 35 2e 34 2e 30 20 32 30 31 36 30 36 30 cc-5.4.0 2016060
|
||||
| 4048: 39 58 4f 4f 43 41 53 45 26 01 05 00 43 0f 17 43 9XOOCASE&...C..C
|
||||
| 4064: 4f 4d 50 49 4c 45 52 3d 67 63 63 2d 35 2e 34 2e OMPILER=gcc-5.4.
|
||||
| 4080: 30 20 32 30 31 36 30 36 30 39 58 52 54 52 49 4d 0 20160609XRTRIM
|
||||
| page 4 offset 12288
|
||||
| 0: 0d 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
|
||||
| page 5 offset 16384
|
||||
| 0: 0d 00 00 00 02 0b a0 00 0c ad 0b a0 00 00 00 00 ................
|
||||
| 2976: 82 0a 02 08 08 09 08 08 17 84 06 30 20 32 35 33 ...........0 253
|
||||
| 2992: 00 01 30 04 25 06 1b 00 00 08 32 30 31 36 30 36 ..0.%.....201606
|
||||
| 3008: 30 39 03 25 07 00 00 01 34 03 25 05 00 00 01 35 09.%....4.%....5
|
||||
| 3024: 03 25 04 00 01 07 30 30 30 30 30 30 30 03 25 1a .%....0000000.%.
|
||||
| 3040: 00 00 08 63 6f 6d 70 69 6c 65 72 03 25 02 00 00 ...compiler.%...
|
||||
| 3056: 06 64 62 73 74 61 74 03 25 0a 00 01 04 65 62 75 .dbstat.%....ebu
|
||||
| 3072: 67 03 25 08 00 00 06 65 6e 61 62 6c 65 09 25 09 g.%....enable.%.
|
||||
| 3088: 05 04 04 04 04 04 00 01 08 78 74 65 6e 73 69 6f .........xtensio
|
||||
| 3104: 6e 03 25 1d 00 00 04 66 74 73 34 03 25 0d 00 03 n.%....fts4.%...
|
||||
| 3120: 01 35 03 25 0f 00 00 03 67 63 63 03 25 03 00 01 .5.%....gcc.%...
|
||||
| 3136: 06 65 6f 70 6f 6c 79 03 25 11 00 00 05 6a 73 6f .eopoly.%....jso
|
||||
| 3152: 6e 31 03 25 14 00 e8 04 6c 6f 61 64 03 25 1c 00 n1.%....load.%..
|
||||
| 3168: 00 03 6d 61 78 03 25 18 00 01 05 65 6d 6f 72 79 ..max.%....emory
|
||||
| 3184: 03 25 19 00 03 04 73 79 73 35 03 25 15 00 00 04 .%....sys5.%....
|
||||
| 3200: 6f 6d 69 74 03 25 1b 00 00 05 72 74 72 65 65 03 omit.%....rtree.
|
||||
| 3216: 25 17 00 00 0a 74 68 72 65 61 64 73 61 66 65 03 %....threadsafe.
|
||||
| 3232: 25 1e 00 00 04 76 74 61 62 03 25 0b 00 86 50 01 %....vtab.%...P.
|
||||
| 3248: 08 08 08 08 08 17 8d 12 30 20 38 33 35 00 01 30 ........0 835..0
|
||||
| 3264: 12 01 06 00 01 06 00 01 06 00 1f 03 00 01 03 00 ................
|
||||
| 3280: 01 03 00 00 08 32 30 31 36 30 36 30 39 09 01 07 .....20160609...
|
||||
| 3296: 00 01 07 00 01 07 00 00 01 34 09 01 05 00 01 05 .........4......
|
||||
| 3312: 00 01 05 00 00 01 35 09 01 04 00 01 04 00 01 04 ......5.........
|
||||
| 3328: 00 01 07 30 30 30 30 30 30 30 09 1c 04 00 01 04 ...0000000......
|
||||
| 3344: 00 01 04 00 00 06 62 69 6e 61 72 79 3c 03 01 02 ......binary<...
|
||||
| 3360: 02 00 03 01 02 02 00 03 01 02 02 00 03 01 02 02 ................
|
||||
| 3376: 00 03 01 02 f2 00 03 01 02 02 00 03 01 02 02 00 ................
|
||||
| 3392: 03 01 02 02 00 03 01 02 02 00 03 01 02 02 00 03 ................
|
||||
| 3408: 01 02 02 00 03 01 02 02 00 00 08 63 6f 6d 70 69 ...........compi
|
||||
| 3424: 6c 65 72 09 01 02 00 01 02 00 01 02 00 00 06 64 ler............d
|
||||
| 3440: 62 73 74 61 74 09 07 03 00 01 03 00 01 03 00 01 bstat...........
|
||||
| 3456: 04 65 62 75 67 09 04 02 00 01 02 00 01 02 00 00 .ebug...........
|
||||
| 3472: 06 65 6e 60 62 6c 65 3f 07 02 00 01 02 00 01 01 .en`ble?........
|
||||
| 3488: ff f1 b1 00 00 02 3f 01 01 f0 f1 02 00 57 02 00 ......?......W..
|
||||
| 3504: 01 02 00 01 02 00 01 02 00 01 02 00 01 02 10 01 ................
|
||||
| 3520: 02 00 01 02 00 01 02 00 01 02 01 01 02 00 01 02 ................
|
||||
| 3536: 00 01 02 00 00 f2 00 01 08 78 74 65 6e 73 69 6f .........xtensio
|
||||
| 3552: 6e 09 1f 04 00 01 04 00 01 04 00 00 04 66 74 73 n............fts
|
||||
| 3568: 34 09 0a 03 00 01 03 00 01 03 00 03 01 35 09 0d 4............5..
|
||||
| 3584: 03 00 01 03 00 01 03 00 00 03 67 63 63 09 01 03 ..........gcc...
|
||||
| 3600: 00 01 03 00 01 03 00 01 06 65 6f 70 6f 6c 79 09 .........eopoly.
|
||||
| 3616: 10 03 00 01 03 00 01 03 00 00 b3 6a 73 6f 6e 31 ...........json1
|
||||
| 3632: 09 13 03 00 01 03 00 01 03 00 00 04 6c 6f 61 64 ............load
|
||||
| 3648: 09 1f 03 00 01 03 00 01 03 00 00 03 6d 61 78 09 ............max.
|
||||
| 3664: 1c 02 00 01 02 00 01 02 00 01 05 65 6d 6f 72 79 ...........emory
|
||||
| 3680: 09 1c 03 00 01 03 00 01 03 00 03 04 73 79 73 35 ............sys5
|
||||
| 3696: 09 16 03 00 01 03 00 01 03 cc 00 06 6e 6f 63 61 ............noca
|
||||
| 3712: 73 65 3c 02 01 02 02 00 03 01 02 02 00 03 01 02 se<.............
|
||||
| 3728: 02 00 03 01 02 02 00 03 01 02 02 00 03 01 02 02 ................
|
||||
| 3744: 00 03 01 02 02 00 03 01 02 02 00 03 01 02 02 00 ................
|
||||
| 3760: 03 01 02 02 00 03 01 02 02 00 03 01 02 02 00 00 ................
|
||||
| 3776: 04 6f 6d 69 74 09 1f 02 00 01 02 00 01 02 00 00 .omit...........
|
||||
| 3792: 05 72 74 62 65 65 09 19 03 00 01 03 00 01 03 00 .rtbee..........
|
||||
| 3808: 03 02 69 6d 3c 01 01 02 02 00 03 01 02 02 00 03 ..im<...........
|
||||
| 3824: 01 02 02 00 03 01 02 02 00 03 01 02 02 00 03 01 ................
|
||||
| 3840: 02 02 00 03 01 02 02 00 03 01 02 02 00 03 01 02 ................
|
||||
| 3856: 02 00 03 01 02 02 00 03 01 02 01 00 03 01 02 02 ................
|
||||
| 3872: 00 00 0a 74 68 72 65 61 64 73 61 66 65 09 22 02 ...threadsafe...
|
||||
| 3888: 00 01 02 00 02 02 00 00 04 76 74 61 62 09 07 04 .........vtab...
|
||||
| 3904: 00 01 03 00 01 04 00 00 01 78 b4 01 01 01 01 02 .........x......
|
||||
| 3920: 00 01 01 01 02 00 01 01 01 02 00 01 01 01 02 00 ................
|
||||
| 3936: 01 01 01 02 00 01 01 01 02 00 01 01 01 02 00 01 ................
|
||||
| 3952: 01 01 02 00 01 01 01 02 00 01 01 01 02 00 01 01 ................
|
||||
| 3968: 01 02 00 01 01 01 02 00 01 01 01 02 00 01 01 01 ................
|
||||
| 3984: 02 01 01 01 01 02 00 01 01 01 02 00 01 01 01 02 ................
|
||||
| 4000: 00 01 01 01 02 00 01 01 01 02 00 01 01 01 02 00 ................
|
||||
| 4016: 01 01 01 02 00 01 01 01 02 00 01 01 01 02 00 01 ................
|
||||
| 4032: 01 01 02 00 01 01 01 da 00 01 01 01 02 00 01 01 ................
|
||||
| 4048: 01 02 00 01 01 01 01 ff ff 01 01 02 00 01 01 01 ................
|
||||
| 4064: 02 00 01 01 01 02 00 01 01 01 02 00 01 01 01 02 ................
|
||||
| 4080: 00 01 01 01 02 00 01 01 01 02 00 01 01 01 02 00 ................
|
||||
| page 6 offset 20480
|
||||
| 0: 0a 00 00 00 02 0f f5 00 0f fb 0f f5 01 00 00 00 ................
|
||||
| 4080: 00 00 00 00 00 05 04 08 09 01 02 04 04 08 08 09 ................
|
||||
| page 7 offset 24576
|
||||
| 0: 01 6f 00 00 00 00 00 00 00 00 00 00 00 00 00 00 .o..............
|
||||
| end crash-e6e3857edf9b26.db
|
||||
}]} {}
|
||||
|
||||
do_execsql_test 30.1 {
|
||||
UPDATE t1 SET b=a;
|
||||
}
|
||||
|
||||
do_catchsql_test 30.2 {
|
||||
SELECT (matchinfo(null)) FROM t1 WHERE t1 MATCH 'ee*e*e*e*e*e*e*Re*e*e*e**'
|
||||
} {1 {database disk image is malformed}}
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -0,0 +1,58 @@
|
||||
# 2019 October 02
|
||||
#
|
||||
# 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 file implements regression tests for SQLite library. The
|
||||
# focus of this script is testing the FTS4 module.
|
||||
#
|
||||
|
||||
set testdir [file dirname $argv0]
|
||||
source $testdir/tester.tcl
|
||||
set testprefix fts4merge5
|
||||
|
||||
# If SQLITE_ENABLE_FTS3 is defined, omit this file.
|
||||
ifcapable !fts3 {
|
||||
finish_test
|
||||
return
|
||||
}
|
||||
|
||||
source $testdir/genesis.tcl
|
||||
|
||||
do_execsql_test 1.1 {
|
||||
CREATE TABLE t1(docid, words);
|
||||
}
|
||||
fts_kjv_genesis
|
||||
|
||||
do_execsql_test 1.2 {
|
||||
CREATE VIRTUAL TABLE x1 USING fts3;
|
||||
INSERT INTO x1(x1) VALUES('nodesize=64');
|
||||
INSERT INTO x1(x1) VALUES('maxpending=64');
|
||||
}
|
||||
|
||||
do_execsql_test 1.3 {
|
||||
INSERT INTO x1(docid, content) SELECT * FROM t1;
|
||||
}
|
||||
|
||||
for {set tn 1} {1} {incr tn} {
|
||||
set tc1 [db total_changes]
|
||||
do_execsql_test 1.4.$tn.1 {
|
||||
INSERT INTO x1(x1) VALUES('merge=1,2');
|
||||
}
|
||||
set tc2 [db total_changes]
|
||||
|
||||
if {($tc2 - $tc1)<2} break
|
||||
|
||||
do_execsql_test 1.4.$tn.1 {
|
||||
INSERT INTO x1(x1) VALUES('integrity-check');
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
finish_test
|
||||
@@ -0,0 +1,120 @@
|
||||
# 2019 September 18
|
||||
#
|
||||
# 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 file implements regression tests for SQLite library. The
|
||||
# focus of this script is testing the FTS4 module.
|
||||
#
|
||||
#
|
||||
|
||||
set testdir [file dirname $argv0]
|
||||
source $testdir/tester.tcl
|
||||
source $testdir/fts3_common.tcl
|
||||
set testprefix fts4record
|
||||
|
||||
# If SQLITE_ENABLE_FTS3 is defined, omit this file.
|
||||
ifcapable !fts3 {
|
||||
finish_test
|
||||
return
|
||||
}
|
||||
|
||||
sqlite3_fts3_may_be_corrupt 1
|
||||
|
||||
do_execsql_test 1.0 {
|
||||
CREATE VIRTUAL TABLE t1 USING fts4(x);
|
||||
INSERT INTO t1 VALUES('terma terma terma termb');
|
||||
}
|
||||
|
||||
do_execsql_test 1.1 {
|
||||
SELECT quote(root) FROM t1_segdir
|
||||
} {
|
||||
X'00057465726D6105010203030004016203010500'
|
||||
}
|
||||
|
||||
proc make_record_wrapper {args} { make_fts3record $args }
|
||||
db func record make_record_wrapper
|
||||
|
||||
do_execsql_test 1.2 {
|
||||
select quote(
|
||||
record(0, 5, 'terma', 5, 1, 2, 3, 3, 0,
|
||||
4, 1, 'b' , 3, 1, 5, 0
|
||||
) );
|
||||
} {
|
||||
X'00057465726D6105010203030004016203010500'
|
||||
}
|
||||
|
||||
do_execsql_test 1.3.1 {
|
||||
UPDATE t1_segdir SET root =
|
||||
record(0, 5, 'terma', 5, 1, 2, 3, 3, 0,
|
||||
4, 1, 'b' , 3, 1, 5,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0
|
||||
);
|
||||
}
|
||||
|
||||
do_catchsql_test 1.3.2 {
|
||||
SELECT snippet(t1) FROM t1 WHERE t1 MATCH 'term*'
|
||||
} {1 {database disk image is malformed}}
|
||||
|
||||
do_execsql_test 1.4.1 {
|
||||
UPDATE t1_segdir SET root =
|
||||
record(0, 5, 'terma', 5, 1, 2, 3, 3, 0,
|
||||
4, 1, 'b' , 4, 1, 5,
|
||||
256, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0
|
||||
);
|
||||
}
|
||||
|
||||
do_catchsql_test 1.4.2 {
|
||||
SELECT snippet(t1) FROM t1 WHERE t1 MATCH 'term*'
|
||||
} {1 {database disk image is malformed}}
|
||||
|
||||
do_execsql_test 1.4.3 {
|
||||
SELECT quote(root) FROM t1_segdir
|
||||
} {
|
||||
X'00057465726D610501020303000401620401058002010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010100'
|
||||
}
|
||||
|
||||
do_execsql_test 1.5.1 {
|
||||
UPDATE t1_segdir SET root =
|
||||
record(0, 5, 'terma', 5, 1, 2, 3, 3, 0,
|
||||
4, 1, 'b' , 4, 1, 5,
|
||||
256, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0
|
||||
);
|
||||
}
|
||||
|
||||
do_catchsql_test 1.4.2 {
|
||||
SELECT snippet(t1) FROM t1 WHERE t1 MATCH 'term*'
|
||||
} {1 {database disk image is malformed}}
|
||||
|
||||
do_execsql_test 1.4.3 {
|
||||
SELECT quote(root) FROM t1_segdir
|
||||
} {
|
||||
X'00057465726D610501020303000401620401058002010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010100'
|
||||
}
|
||||
|
||||
|
||||
do_execsql_test 1.5.1 {
|
||||
UPDATE t1_segdir SET root =
|
||||
X'00057465726D61050102030300040162040105FF00010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010101010100'
|
||||
}
|
||||
|
||||
do_catchsql_test 1.5.2 {
|
||||
SELECT snippet(t1) FROM t1 WHERE t1 MATCH 'term*'
|
||||
} {1 {database disk image is malformed}}
|
||||
|
||||
do_catchsql_test 1.5.3 {
|
||||
INSERT INTO t1(t1) VALUES('integrity-check');
|
||||
} {1 {database disk image is malformed}}
|
||||
|
||||
finish_test
|
||||
Binary file not shown.
+19
-17
@@ -463,22 +463,24 @@ do_execsql_test indexexpr-1700 {
|
||||
# value, be sure to use the REAL value and not the INT value when
|
||||
# computing the expression.
|
||||
#
|
||||
do_execsql_test indexexpr-1800 {
|
||||
DROP TABLE IF EXISTS t0;
|
||||
CREATE TABLE t0(c0 REAL, c1 TEXT);
|
||||
CREATE INDEX i0 ON t0(+c0, c0);
|
||||
INSERT INTO t0(c0) VALUES(0);
|
||||
SELECT CAST(+ t0.c0 AS BLOB) LIKE 0 FROM t0;
|
||||
} {0}
|
||||
do_execsql_test indexexpr-1810 {
|
||||
SELECT CAST(+ t0.c0 AS BLOB) LIKE '0.0' FROM t0;
|
||||
} {1}
|
||||
do_execsql_test indexexpr-1820 {
|
||||
DROP TABLE IF EXISTS t1;
|
||||
CREATE TABLE t1(x REAL);
|
||||
CREATE INDEX t1x ON t1(x, +x);
|
||||
INSERT INTO t1(x) VALUES(2);
|
||||
SELECT +x FROM t1 WHERE x=2;
|
||||
} {2.0}
|
||||
ifcapable like_match_blobs {
|
||||
do_execsql_test indexexpr-1800 {
|
||||
DROP TABLE IF EXISTS t0;
|
||||
CREATE TABLE t0(c0 REAL, c1 TEXT);
|
||||
CREATE INDEX i0 ON t0(+c0, c0);
|
||||
INSERT INTO t0(c0) VALUES(0);
|
||||
SELECT CAST(+ t0.c0 AS BLOB) LIKE 0 FROM t0;
|
||||
} {0}
|
||||
do_execsql_test indexexpr-1810 {
|
||||
SELECT CAST(+ t0.c0 AS BLOB) LIKE '0.0' FROM t0;
|
||||
} {1}
|
||||
do_execsql_test indexexpr-1820 {
|
||||
DROP TABLE IF EXISTS t1;
|
||||
CREATE TABLE t1(x REAL);
|
||||
CREATE INDEX t1x ON t1(x, +x);
|
||||
INSERT INTO t1(x) VALUES(2);
|
||||
SELECT +x FROM t1 WHERE x=2;
|
||||
} {2.0}
|
||||
}
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -257,4 +257,25 @@ do_execsql_test instr-1.64 {
|
||||
SELECT instr(a, b) FROM x1;
|
||||
} 0
|
||||
|
||||
# 2019-09-16 ticket https://www.sqlite.org/src/info/587791f92620090e
|
||||
#
|
||||
do_execsql_test instr-2.0 {
|
||||
DROP TABLE IF EXISTS t0;
|
||||
CREATE TABLE t0(c0 PRIMARY KEY, c1);
|
||||
INSERT INTO t0(c0) VALUES (x'bb'), (0);
|
||||
SELECT COUNT(*) FROM t0 WHERE INSTR(x'aabb', t0.c0) ORDER BY t0.c0, t0.c1;
|
||||
} {1}
|
||||
do_execsql_test instr-2.1 {
|
||||
SELECT quote(c0) FROM t0 WHERE INSTR(x'aabb', t0.c0) ORDER BY t0.c0, t0.c1;
|
||||
} {X'BB'}
|
||||
do_execsql_test instr-2.2 {
|
||||
DROP TABLE IF EXISTS t1;
|
||||
CREATE TABLE t1(x);
|
||||
INSERT INTO t1(x) VALUES('text'),(x'bb');
|
||||
SELECT quote(x) FROM t1 WHERE instr(x'aabb',x);
|
||||
} {X'BB'}
|
||||
do_execsql_test instr-2.3 {
|
||||
SELECT quote(x) FROM t1 WHERE x>'zzz' AND instr(x'aabb',x);
|
||||
} {X'BB'}
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -207,6 +207,19 @@ do_execsql_test like3-5.410 {
|
||||
SELECT * FROM t0 WHERE t0.c0 LIKE '.1%';
|
||||
} {.1%}
|
||||
|
||||
# 2019-09-03
|
||||
# Ticket https://www.sqlite.org/src/info/0f0428096f
|
||||
do_execsql_test like3-5.420 {
|
||||
DROP TABLE IF EXISTS t0;
|
||||
CREATE TABLE t0(c0 UNIQUE);
|
||||
INSERT INTO t0(c0) VALUES(-1);
|
||||
SELECT * FROM t0 WHERE t0.c0 GLOB '-*';
|
||||
} {-1}
|
||||
do_execsql_test like3-5.421 {
|
||||
SELECT t0.c0 GLOB '-*' FROM t0;
|
||||
} {1}
|
||||
|
||||
|
||||
|
||||
# 2019-02-27
|
||||
# Verify that the LIKE optimization works with an ESCAPE clause when
|
||||
|
||||
@@ -0,0 +1,147 @@
|
||||
# 2019-09-21
|
||||
#
|
||||
# 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 file implements regression tests for SQLite library.
|
||||
#
|
||||
# Specifically, it tests cases where the expressions in a GROUP BY
|
||||
# clause are the same as those in the ORDER BY clause.
|
||||
#
|
||||
|
||||
set testdir [file dirname $argv0]
|
||||
source $testdir/tester.tcl
|
||||
set ::testprefix orderbyA
|
||||
|
||||
proc do_sortcount_test {tn sql cnt res} {
|
||||
set eqp [execsql "EXPLAIN QUERY PLAN $sql"]
|
||||
set rcnt [regexp -all {USE TEMP} $eqp]
|
||||
uplevel [list do_test $tn.1 [list set {} $rcnt] $cnt]
|
||||
uplevel [list do_execsql_test $tn.2 $sql $res]
|
||||
}
|
||||
|
||||
do_execsql_test 1.0 {
|
||||
CREATE TABLE t1(a, b, c);
|
||||
INSERT INTO t1 VALUES('one', 1, 11);
|
||||
INSERT INTO t1 VALUES('three', 7, 11);
|
||||
INSERT INTO t1 VALUES('one', 2, 11);
|
||||
INSERT INTO t1 VALUES('one', 3, 11);
|
||||
INSERT INTO t1 VALUES('two', 4, 11);
|
||||
INSERT INTO t1 VALUES('two', 6, 11);
|
||||
INSERT INTO t1 VALUES('three', 8, 11);
|
||||
INSERT INTO t1 VALUES('two', 5, 11);
|
||||
INSERT INTO t1 VALUES('three', 9, 11);
|
||||
}
|
||||
|
||||
foreach {tn idx} {
|
||||
1 {}
|
||||
2 {CREATE INDEX i1 ON t1(a)}
|
||||
3 {CREATE INDEX i1 ON t1(a DESC)}
|
||||
} {
|
||||
execsql { DROP INDEX IF EXISTS i1 }
|
||||
execsql $idx
|
||||
|
||||
# $match is the number of temp-table sorts we expect if the GROUP BY
|
||||
# can use the same sort order as the ORDER BY. $nomatch is the number
|
||||
# of expected sorts if the GROUP BY and ORDER BY are not compatible.
|
||||
set match 1
|
||||
set nomatch 2
|
||||
if {$tn>=2} {
|
||||
set match 0
|
||||
set nomatch 1
|
||||
}
|
||||
|
||||
do_sortcount_test 1.$tn.1.1 {
|
||||
SELECT a, sum(b) FROM t1 GROUP BY a ORDER BY a
|
||||
} $match {one 6 three 24 two 15}
|
||||
do_sortcount_test 1.$tn.1.2 {
|
||||
SELECT a, sum(b) FROM t1 GROUP BY a ORDER BY a DESC
|
||||
} $match {two 15 three 24 one 6}
|
||||
|
||||
do_sortcount_test 1.$tn.2.1 {
|
||||
SELECT a, sum(b) FROM t1 GROUP BY a ORDER BY a||''
|
||||
} $nomatch {one 6 three 24 two 15}
|
||||
do_sortcount_test 1.$tn.2.2 {
|
||||
SELECT a, sum(b) FROM t1 GROUP BY a ORDER BY a||'' DESC
|
||||
} $nomatch {two 15 three 24 one 6}
|
||||
|
||||
do_sortcount_test 1.$tn.3.1 {
|
||||
SELECT a, sum(b) FROM t1 GROUP BY a ORDER BY a NULLS LAST
|
||||
} $nomatch {one 6 three 24 two 15}
|
||||
do_sortcount_test 1.$tn.3.2 {
|
||||
SELECT a, sum(b) FROM t1 GROUP BY a ORDER BY a DESC NULLS FIRST
|
||||
} $nomatch {two 15 three 24 one 6}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
do_execsql_test 2.0 {
|
||||
CREATE TABLE t2(a, b, c);
|
||||
INSERT INTO t2 VALUES(1, 'one', 1);
|
||||
INSERT INTO t2 VALUES(1, 'two', 2);
|
||||
INSERT INTO t2 VALUES(1, 'one', 3);
|
||||
INSERT INTO t2 VALUES(1, 'two', 4);
|
||||
INSERT INTO t2 VALUES(1, 'one', 5);
|
||||
INSERT INTO t2 VALUES(1, 'two', 6);
|
||||
|
||||
INSERT INTO t2 VALUES(2, 'one', 7);
|
||||
INSERT INTO t2 VALUES(2, 'two', 8);
|
||||
INSERT INTO t2 VALUES(2, 'one', 9);
|
||||
INSERT INTO t2 VALUES(2, 'two', 10);
|
||||
INSERT INTO t2 VALUES(2, 'one', 11);
|
||||
INSERT INTO t2 VALUES(2, 'two', 12);
|
||||
|
||||
INSERT INTO t2 VALUES(NULL, 'one', 13);
|
||||
INSERT INTO t2 VALUES(NULL, 'two', 14);
|
||||
INSERT INTO t2 VALUES(NULL, 'one', 15);
|
||||
INSERT INTO t2 VALUES(NULL, 'two', 16);
|
||||
INSERT INTO t2 VALUES(NULL, 'one', 17);
|
||||
INSERT INTO t2 VALUES(NULL, 'two', 18);
|
||||
}
|
||||
|
||||
foreach {tn idx} {
|
||||
1 {}
|
||||
|
||||
2 { CREATE INDEX i2 ON t2(a, b) }
|
||||
3 { CREATE INDEX i2 ON t2(a DESC, b DESC) }
|
||||
|
||||
4 { CREATE INDEX i2 ON t2(a, b DESC) }
|
||||
5 { CREATE INDEX i2 ON t2(a DESC, b) }
|
||||
} {
|
||||
execsql { DROP INDEX IF EXISTS i2 }
|
||||
execsql $idx
|
||||
|
||||
|
||||
set nSort [expr ($tn==2 || $tn==3) ? 0 : 1]
|
||||
do_sortcount_test 2.$tn.1.1 {
|
||||
SELECT a, b, sum(c) FROM t2 GROUP BY a, b ORDER BY a, b;
|
||||
} $nSort {{} one 45 {} two 48 1 one 9 1 two 12 2 one 27 2 two 30}
|
||||
do_sortcount_test 2.$tn.1.2 {
|
||||
SELECT a, b, sum(c) FROM t2 GROUP BY a, b ORDER BY a DESC, b DESC;
|
||||
} $nSort {2 two 30 2 one 27 1 two 12 1 one 9 {} two 48 {} one 45}
|
||||
|
||||
set nSort [expr ($tn==4 || $tn==5) ? 0 : 1]
|
||||
do_sortcount_test 2.$tn.2.1 {
|
||||
SELECT a, b, sum(c) FROM t2 GROUP BY a, b ORDER BY a, b DESC;
|
||||
} $nSort { {} two 48 {} one 45 1 two 12 1 one 9 2 two 30 2 one 27 }
|
||||
do_sortcount_test 2.$tn.2.2 {
|
||||
SELECT a, b, sum(c) FROM t2 GROUP BY a, b ORDER BY a DESC, b;
|
||||
} $nSort { 2 one 27 2 two 30 1 one 9 1 two 12 {} one 45 {} two 48 }
|
||||
|
||||
# ORDER BY can never piggyback on the GROUP BY sort if it uses
|
||||
# non-standard NULLS behaviour.
|
||||
set nSort [expr $tn==1 ? 2 : 1]
|
||||
do_sortcount_test 2.$tn.3.1 {
|
||||
SELECT a, b, sum(c) FROM t2 GROUP BY a, b ORDER BY a, b DESC NULLS FIRST;
|
||||
} $nSort { {} two 48 {} one 45 1 two 12 1 one 9 2 two 30 2 one 27 }
|
||||
do_sortcount_test 2.$tn.3.2 {
|
||||
SELECT a, b, sum(c) FROM t2 GROUP BY a, b ORDER BY a DESC, b NULLS LAST;
|
||||
} $nSort { 2 one 27 2 two 30 1 one 9 1 two 12 {} one 45 {} two 48 }
|
||||
}
|
||||
|
||||
|
||||
finish_test
|
||||
@@ -126,6 +126,7 @@ set allquicktests [test_set $alltests -exclude {
|
||||
walcrash2.test e_fkey.test backup.test
|
||||
|
||||
fts4merge.test fts4merge2.test fts4merge4.test fts4check.test
|
||||
fts4merge5.test
|
||||
fts3cov.test fts3snippet.test fts3corrupt2.test fts3an.test
|
||||
fts3defer.test fts4langid.test fts3sort.test fts5unicode.test
|
||||
|
||||
@@ -455,8 +456,8 @@ test_suite "coverage-analyze" -description {
|
||||
Coverage tests for file analyze.c.
|
||||
} -files {
|
||||
analyze3.test analyze4.test analyze5.test analyze6.test
|
||||
analyze7.test analyze8.test analyze9.test analyzeA.test
|
||||
analyze.test analyzeB.test mallocA.test
|
||||
analyze7.test analyze8.test analyze9.test
|
||||
analyze.test mallocA.test
|
||||
}
|
||||
|
||||
test_suite "coverage-sorter" -description {
|
||||
@@ -624,7 +625,7 @@ test_suite "utf16" -description {
|
||||
} -files {
|
||||
alter.test alter3.test
|
||||
analyze.test analyze3.test analyze4.test analyze5.test analyze6.test
|
||||
analyze7.test analyze8.test analyze9.test analyzeA.test analyzeB.test
|
||||
analyze7.test analyze8.test analyze9.test
|
||||
auth.test bind.test blob.test capi2.test capi3.test collate1.test
|
||||
collate2.test collate3.test collate4.test collate5.test collate6.test
|
||||
conflict.test date.test delete.test expr.test fkey1.test func.test
|
||||
|
||||
+11
-5
@@ -1859,10 +1859,11 @@ do_test 23.1 {
|
||||
CREATE INDEX i1 ON t1(b,c);
|
||||
CREATE INDEX i2 ON t1(c,d);
|
||||
CREATE INDEX i2x ON t1(d COLLATE nocase, c DESC);
|
||||
CREATE INDEX i3 ON t1(d,b+c,c);
|
||||
CREATE TABLE t2(x INTEGER REFERENCES t1);
|
||||
}
|
||||
db2 eval {SELECT name FROM sqlite_master}
|
||||
} {t1 i1 i2 i2x t2}
|
||||
} {t1 i1 i2 i2x i3 t2}
|
||||
do_test 23.2a {
|
||||
db eval {
|
||||
DROP INDEX i2;
|
||||
@@ -1889,13 +1890,14 @@ do_test 23.2b {
|
||||
# means left-most. Key columns come before auxiliary columns.)
|
||||
#
|
||||
# (The second column of output from PRAGMA index_xinfo is...)
|
||||
# EVIDENCE-OF: R-40889-06838 The rank of the column within the table
|
||||
# EVIDENCE-OF: R-06603-49335 The rank of the column within the table
|
||||
# being indexed, or -1 if the index-column is the rowid of the table
|
||||
# being indexed.
|
||||
# being indexed and -2 if the index is on an expression.
|
||||
#
|
||||
# (The third column of output from PRAGMA index_xinfo is...)
|
||||
# EVIDENCE-OF: R-22751-28901 The name of the column being indexed, or
|
||||
# NULL if the index-column is the rowid of the table being indexed.
|
||||
# EVIDENCE-OF: R-40641-22898 The name of the column being indexed, or
|
||||
# NULL if the index-column is the rowid of the table being indexed or an
|
||||
# expression.
|
||||
#
|
||||
# (The fourth column of output from PRAGMA index_xinfo is...)
|
||||
# EVIDENCE-OF: R-11847-09179 1 if the index-column is sorted in reverse
|
||||
@@ -1915,6 +1917,9 @@ do_test 23.2c {
|
||||
do_test 23.2d {
|
||||
db2 eval {PRAGMA index_xinfo(i2x)}
|
||||
} {0 3 d 0 nocase 1 1 2 c 1 BINARY 1 2 -1 {} 0 BINARY 0}
|
||||
do_test 23.2e {
|
||||
db2 eval {PRAGMA index_xinfo(i3)}
|
||||
} {0 3 d 0 BINARY 1 1 -2 {} 0 BINARY 1 2 2 c 0 BINARY 1 3 -1 {} 0 BINARY 0}
|
||||
|
||||
# EVIDENCE-OF: R-64103-17776 PRAGMA schema.index_list(table-name); This
|
||||
# pragma returns one row for each index associated with the given table.
|
||||
@@ -1936,6 +1941,7 @@ do_test 23.2d {
|
||||
#
|
||||
do_test 23.3 {
|
||||
db eval {
|
||||
DROP INDEX IF EXISTS i3;
|
||||
CREATE INDEX i3 ON t1(d,b,c);
|
||||
}
|
||||
capture_pragma db2 out {PRAGMA index_list(t1)}
|
||||
|
||||
@@ -412,6 +412,8 @@ proc count_tests_and_errors {logfile rcVar errmsgVar} {
|
||||
# skip over "value is outside range" errors
|
||||
if {[regexp {value .* is outside the range of representable} $line]} {
|
||||
# noop
|
||||
} elseif {[regexp {overflow: .* cannot be represented} $line]} {
|
||||
# noop
|
||||
} else {
|
||||
incr ::NERRCASE
|
||||
if {$rc==0} {
|
||||
|
||||
@@ -578,10 +578,14 @@ proc main_tests {args} {
|
||||
puts "$config \"$target\""
|
||||
if {$bNodebug==0 && $bNosynthetic==0} {
|
||||
set iHas [string first SQLITE_DEBUG $::Configs($config)]
|
||||
set dtarget test
|
||||
if {$target=="tcltest"} {
|
||||
set dtarget tcltest
|
||||
}
|
||||
if {$iHas>=0} {
|
||||
puts "$config-ndebug \"test\""
|
||||
puts "$config-ndebug \"$dtarget\""
|
||||
} else {
|
||||
puts "$config-debug \"test\""
|
||||
puts "$config-debug \"$dtarget\""
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,53 @@
|
||||
# 2019 September 10
|
||||
#
|
||||
# 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 file implements regression tests for SQLite library. In particular,
|
||||
# that problems related to ticket [18458b1a] have been fixed.
|
||||
#
|
||||
|
||||
set testdir [file dirname $argv0]
|
||||
source $testdir/tester.tcl
|
||||
set testprefix tkt-18458b1a
|
||||
|
||||
foreach tn {1 2} {
|
||||
reset_db
|
||||
if {$tn==1} {
|
||||
# Disable the flattener and push-down optimizations
|
||||
optimization_control db query-flattener 0
|
||||
optimization_control db push-down 0
|
||||
} else {
|
||||
# Enable them
|
||||
optimization_control db query-flattener 1
|
||||
optimization_control db push-down 1
|
||||
}
|
||||
|
||||
db cache size 0
|
||||
|
||||
do_execsql_test $tn.1.1 {
|
||||
CREATE TABLE t0(c0 COLLATE NOCASE);
|
||||
INSERT INTO t0(c0) VALUES ('B');
|
||||
CREATE VIEW v0(c0, c1) AS SELECT DISTINCT t0.c0, 'a' FROM t0;
|
||||
}
|
||||
|
||||
do_execsql_test $tn.1.2 {
|
||||
SELECT count(*) FROM v0 WHERE c1 >= c0;
|
||||
} 1
|
||||
|
||||
do_execsql_test $tn.1.3 {
|
||||
SELECT count(*) FROM v0 WHERE NOT NOT (c1 >= c0);
|
||||
} 1
|
||||
|
||||
do_execsql_test $tn.1.4 {
|
||||
SELECT count(*) FROM v0 WHERE ((c1 >= c0) OR 0+0);
|
||||
} 1
|
||||
}
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
# 2011 December 06
|
||||
# 2011-12-06
|
||||
#
|
||||
# The author disclaims copyright to this source code. In place of
|
||||
# a legal notice, here is a blessing:
|
||||
@@ -68,5 +68,19 @@ do_execsql_test 2.2 {
|
||||
)
|
||||
} {FACTORING FACTOR SWIMMING SWIMM}
|
||||
|
||||
# Similar problem discovered by dbsqlfuzz on 2019-09-18
|
||||
#
|
||||
do_execsql_test 3.0 {
|
||||
DROP TABLE IF EXISTS t1;
|
||||
CREATE TABLE t1(i INT PRIMARY KEY, a, b);
|
||||
INSERT INTO t1 VALUES(NULL,'one','i');
|
||||
CREATE INDEX i1a ON t1(a);
|
||||
CREATE INDEX i1b ON t1(b);
|
||||
SELECT (SELECT 1
|
||||
FROM (SELECT 1 FROM t1 WHERE a=1 OR b='i')
|
||||
WHERE a='o'
|
||||
OR b IN (SELECT a=('b' IN (SELECT 'a'))))
|
||||
FROM t1;
|
||||
} {{}}
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -59,27 +59,27 @@ foreach tn {1 2} {
|
||||
do_execsql_test $tn.1.2.6 { SELECT a < B FROM v5 } 0
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
do_execsql_test 2.0 {
|
||||
do_execsql_test $tn.2.0 {
|
||||
CREATE TABLE t5(a, b COLLATE NOCASE);
|
||||
INSERT INTO t5 VALUES(1, 'XYZ');
|
||||
}
|
||||
|
||||
# Result should be 0, as column "xyz" from the sub-query has implicit
|
||||
# collation sequence BINARY.
|
||||
do_execsql_test 2.1 {
|
||||
do_execsql_test $tn.2.1 {
|
||||
SELECT xyz==b FROM ( SELECT a, 'xyz' AS xyz FROM t5 ), t5;
|
||||
} {0}
|
||||
|
||||
# Result should be 1, as literal 'xyz' has no collation sequence, so
|
||||
# the comparison uses the implicit collation sequence of the RHS - NOCASE.
|
||||
do_execsql_test 2.2 {
|
||||
do_execsql_test $tn.2.2 {
|
||||
SELECT 'xyz'==b FROM ( SELECT a, 'xyz' AS xyz FROM t5 ), t5;
|
||||
} {1}
|
||||
|
||||
#-----------------------------------------------------------------------
|
||||
# The test case submitted with the ticket.
|
||||
#
|
||||
do_execsql_test 3.0 {
|
||||
do_execsql_test $tn.3.0 {
|
||||
DROP TABLE t0;
|
||||
DROP VIEW v2;
|
||||
|
||||
@@ -94,7 +94,7 @@ foreach tn {1 2} {
|
||||
|
||||
# The result is 1, as the collation used is the implicit collation sequence
|
||||
# of v2.c1 - BINARY.
|
||||
do_execsql_test 3.1 {
|
||||
do_execsql_test $tn.3.1 {
|
||||
SELECT v2.c1 BETWEEN v2.c0 AND v2.c1 as count FROM v2;
|
||||
} 1
|
||||
}
|
||||
|
||||
@@ -60,7 +60,7 @@ foreach {tn q res eqp} [subst -nocommands {
|
||||
{1 3 2 2 3 1} {$idxscan*$sort}
|
||||
|
||||
8 "SELECT * FROM t1 GROUP BY x, y ORDER BY x DESC, y DESC"
|
||||
{3 1 2 2 1 3} {$idxscan*$sort}
|
||||
{3 1 2 2 1 3} {$idxscan}
|
||||
|
||||
9 "SELECT * FROM t1 GROUP BY x, y ORDER BY x ASC, y ASC"
|
||||
{1 3 2 2 3 1} {$idxscan}
|
||||
|
||||
+6
-2
@@ -825,8 +825,13 @@ for {set i 0} {$i < [llength $argv]} {incr i} {
|
||||
}
|
||||
}
|
||||
|
||||
wapptest_init
|
||||
for {set i 0} {$i < [llength $lTestArg]} {incr i} {
|
||||
switch -- [lindex $lTestArg $i] {
|
||||
set opt [lindex $lTestArg $i]
|
||||
if {[string range $opt 0 1]=="--"} {
|
||||
set opt [string range $opt 1 end]
|
||||
}
|
||||
switch -- $opt {
|
||||
-platform {
|
||||
if {$i==[llength $lTestArg]-1} { wapptest_usage }
|
||||
incr i
|
||||
@@ -882,7 +887,6 @@ for {set i 0} {$i < [llength $lTestArg]} {incr i} {
|
||||
}
|
||||
}
|
||||
|
||||
wapptest_init
|
||||
if {$G(noui)==0} {
|
||||
wapp-start $lWappArg
|
||||
} else {
|
||||
|
||||
@@ -432,6 +432,21 @@ execsql_test 4.11 {
|
||||
SELECT count(distinct a) FILTER (WHERE b='odd') FROM t1
|
||||
}
|
||||
|
||||
==========
|
||||
|
||||
execsql_test 5.0 {
|
||||
DROP TABLE IF EXISTS t1;
|
||||
CREATE TABLE t1(x INTEGER, y INTEGER);
|
||||
INSERT INTO t1 VALUES(10, 1);
|
||||
INSERT INTO t1 VALUES(20, 2);
|
||||
INSERT INTO t1 VALUES(3, 3);
|
||||
INSERT INTO t1 VALUES(2, 4);
|
||||
INSERT INTO t1 VALUES(1, 5);
|
||||
}
|
||||
|
||||
execsql_float_test 5.1 {
|
||||
SELECT avg(x) OVER (ORDER BY y) AS z FROM t1 ORDER BY z;
|
||||
}
|
||||
|
||||
finish_test
|
||||
|
||||
|
||||
@@ -901,4 +901,33 @@ do_execsql_test 4.11 {
|
||||
SELECT count(distinct a) FILTER (WHERE b='odd') FROM t1
|
||||
} {3}
|
||||
|
||||
#==========================================================================
|
||||
|
||||
do_execsql_test 5.0 {
|
||||
DROP TABLE IF EXISTS t1;
|
||||
CREATE TABLE t1(x INTEGER, y INTEGER);
|
||||
INSERT INTO t1 VALUES(10, 1);
|
||||
INSERT INTO t1 VALUES(20, 2);
|
||||
INSERT INTO t1 VALUES(3, 3);
|
||||
INSERT INTO t1 VALUES(2, 4);
|
||||
INSERT INTO t1 VALUES(1, 5);
|
||||
} {}
|
||||
|
||||
|
||||
do_test 5.1 {
|
||||
set myres {}
|
||||
foreach r [db eval {SELECT avg(x) OVER (ORDER BY y) AS z FROM t1 ORDER BY z;}] {
|
||||
lappend myres [format %.4f [set r]]
|
||||
}
|
||||
set res2 {7.2000 8.7500 10.0000 11.0000 15.0000}
|
||||
set i 0
|
||||
foreach r [set myres] r2 [set res2] {
|
||||
if {[set r]<([set r2]-0.0001) || [set r]>([set r2]+0.0001)} {
|
||||
error "list element [set i] does not match: got=[set r] expected=[set r2]"
|
||||
}
|
||||
incr i
|
||||
}
|
||||
set {} {}
|
||||
} {}
|
||||
|
||||
finish_test
|
||||
|
||||
@@ -195,5 +195,42 @@ do_execsql_test 6.2 {
|
||||
BETWEEN 1 AND 1;
|
||||
} {0}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
do_execsql_test 7.0 {
|
||||
DROP TABLE IF EXISTS t1;
|
||||
CREATE TABLE t1(x, y);
|
||||
INSERT INTO t1 VALUES(10, 1);
|
||||
INSERT INTO t1 VALUES(20, 2);
|
||||
INSERT INTO t1 VALUES(3, 3);
|
||||
INSERT INTO t1 VALUES(2, 4);
|
||||
INSERT INTO t1 VALUES(1, 5);
|
||||
} {}
|
||||
|
||||
|
||||
do_execsql_test 7.1 {
|
||||
SELECT avg(x) OVER (ORDER BY y) AS z FROM t1 ORDER BY z
|
||||
} {
|
||||
7.2 8.75 10.0 11.0 15.0
|
||||
}
|
||||
|
||||
do_execsql_test 7.2 {
|
||||
SELECT avg(x) OVER (ORDER BY y) z FROM t1 ORDER BY (z IS y);
|
||||
} {
|
||||
10.0 15.0 11.0 8.75 7.2
|
||||
}
|
||||
|
||||
do_execsql_test 7.3 {
|
||||
SELECT avg(x) OVER (ORDER BY y) z FROM t1 ORDER BY (y IS z);
|
||||
} {
|
||||
10.0 15.0 11.0 8.75 7.2
|
||||
}
|
||||
|
||||
do_execsql_test 7.4 {
|
||||
SELECT avg(x) OVER (ORDER BY y) z FROM t1 ORDER BY z + 0.0;
|
||||
} {
|
||||
7.2 8.75 10.0 11.0 15.0
|
||||
}
|
||||
|
||||
finish_test
|
||||
|
||||
|
||||
@@ -0,0 +1,339 @@
|
||||
# 2019-08-30
|
||||
#
|
||||
# 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.
|
||||
#
|
||||
#***********************************************************************
|
||||
# Test cases for RANGE BETWEEN and especially with NULLS LAST
|
||||
#
|
||||
|
||||
set testdir [file dirname $argv0]
|
||||
source $testdir/tester.tcl
|
||||
set testprefix windowB
|
||||
|
||||
ifcapable !windowfunc {
|
||||
finish_test
|
||||
return
|
||||
}
|
||||
|
||||
do_execsql_test 1.0 {
|
||||
CREATE TABLE t1(a, b);
|
||||
INSERT INTO t1 VALUES(NULL, 1);
|
||||
INSERT INTO t1 VALUES(NULL, 2);
|
||||
INSERT INTO t1 VALUES(NULL, 3);
|
||||
} {}
|
||||
|
||||
foreach {tn win} {
|
||||
1 { ORDER BY a RANGE BETWEEN 1 PRECEDING AND 1 FOLLOWING }
|
||||
2 { ORDER BY a NULLS LAST RANGE BETWEEN 1 PRECEDING AND 1 FOLLOWING }
|
||||
3 { ORDER BY a DESC RANGE BETWEEN 1 PRECEDING AND 1 FOLLOWING }
|
||||
4 { ORDER BY a DESC NULLS FIRST RANGE BETWEEN 1 PRECEDING AND 1 FOLLOWING }
|
||||
|
||||
5 { ORDER BY a NULLS LAST RANGE BETWEEN 1 FOLLOWING AND 2 FOLLOWING }
|
||||
6 { ORDER BY a DESC NULLS FIRST RANGE BETWEEN 1 FOLLOWING AND 2 FOLLOWING }
|
||||
|
||||
7 { ORDER BY a NULLS LAST RANGE BETWEEN 2 PRECEDING AND 1 PRECEDING }
|
||||
8 { ORDER BY a DESC NULLS FIRST RANGE BETWEEN 2 PRECEDING AND 1 PRECEDING }
|
||||
} {
|
||||
do_execsql_test 1.$tn "
|
||||
SELECT sum(b) OVER win FROM t1
|
||||
WINDOW win AS ( $win )
|
||||
" {6 6 6}
|
||||
}
|
||||
|
||||
do_execsql_test 1.2 {
|
||||
SELECT sum(b) OVER win FROM t1
|
||||
WINDOW win AS (
|
||||
ORDER BY a DESC NULLS FIRST RANGE BETWEEN 1 PRECEDING AND 1 FOLLOWING
|
||||
)
|
||||
} {6 6 6}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
do_execsql_test 2.0 {
|
||||
CREATE TABLE t1(a, b);
|
||||
INSERT INTO t1 VALUES(1, NULL);
|
||||
INSERT INTO t1 VALUES(2, 45);
|
||||
INSERT INTO t1 VALUES(3, 66.2);
|
||||
INSERT INTO t1 VALUES(4, 'hello world');
|
||||
INSERT INTO t1 VALUES(5, 'hello world');
|
||||
INSERT INTO t1 VALUES(6, X'1234');
|
||||
INSERT INTO t1 VALUES(7, X'1234');
|
||||
INSERT INTO t1 VALUES(8, NULL);
|
||||
}
|
||||
|
||||
foreach {tn win} {
|
||||
1 "ORDER BY b RANGE BETWEEN 1 PRECEDING AND 2 PRECEDING"
|
||||
2 "ORDER BY b RANGE BETWEEN 2 FOLLOWING AND 2 FOLLOWING"
|
||||
3 "ORDER BY b NULLS LAST RANGE BETWEEN 1 PRECEDING AND 2 PRECEDING"
|
||||
4 "ORDER BY b NULLS LAST RANGE BETWEEN 2 FOLLOWING AND 2 FOLLOWING"
|
||||
} {
|
||||
do_execsql_test 2.1.$tn "
|
||||
SELECT a, sum(a) OVER win FROM t1
|
||||
WINDOW win AS ( $win )
|
||||
ORDER BY 1
|
||||
" {1 9 2 {} 3 {} 4 9 5 9 6 13 7 13 8 9}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
ifcapable json1 {
|
||||
reset_db
|
||||
do_execsql_test 3.0 {
|
||||
CREATE TABLE testjson(id INTEGER PRIMARY KEY, j TEXT, x TEXT);
|
||||
INSERT INTO testjson VALUES(1, '{"a":1}', 'a');
|
||||
INSERT INTO testjson VALUES(2, '{"b":2}', 'b');
|
||||
INSERT INTO testjson VALUES(3, '{"c":3}', 'c');
|
||||
INSERT INTO testjson VALUES(4, '{"d":4}', 'd');
|
||||
}
|
||||
|
||||
do_execsql_test 3.1 {
|
||||
SELECT json_group_array(json(j)) FROM testjson;
|
||||
} {
|
||||
{[{"a":1},{"b":2},{"c":3},{"d":4}]}
|
||||
}
|
||||
|
||||
do_execsql_test 3.2 {
|
||||
SELECT json_group_array(json(j)) OVER (ORDER BY id) FROM testjson;
|
||||
} {
|
||||
{[{"a":1}]}
|
||||
{[{"a":1},{"b":2}]}
|
||||
{[{"a":1},{"b":2},{"c":3}]}
|
||||
{[{"a":1},{"b":2},{"c":3},{"d":4}]}
|
||||
}
|
||||
|
||||
do_execsql_test 3.3 {
|
||||
SELECT json_group_array(json(j)) OVER (
|
||||
ORDER BY id RANGE BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW
|
||||
EXCLUDE TIES
|
||||
) FROM testjson;
|
||||
} {
|
||||
{[{"a":1}]}
|
||||
{[{"a":1},{"b":2}]}
|
||||
{[{"a":1},{"b":2},{"c":3}]}
|
||||
{[{"a":1},{"b":2},{"c":3},{"d":4}]}
|
||||
}
|
||||
|
||||
do_execsql_test 3.4 {
|
||||
SELECT json_group_array(json(j)) OVER (
|
||||
ORDER BY id ROWS BETWEEN 1 PRECEDING AND 1 FOLLOWING
|
||||
) FROM testjson;
|
||||
} {
|
||||
{[{"a":1},{"b":2}]}
|
||||
{[{"a":1},{"b":2},{"c":3}]}
|
||||
{[{"b":2},{"c":3},{"d":4}]}
|
||||
{[{"c":3},{"d":4}]}
|
||||
}
|
||||
|
||||
do_execsql_test 3.5 {
|
||||
SELECT json_group_array(json(j)) OVER (
|
||||
ORDER BY id ROWS BETWEEN 2 PRECEDING AND 1 PRECEDING
|
||||
) FROM testjson;
|
||||
} {
|
||||
{[]}
|
||||
{[{"a":1}]}
|
||||
{[{"a":1},{"b":2}]}
|
||||
{[{"b":2},{"c":3}]}
|
||||
}
|
||||
|
||||
do_execsql_test 3.5a {
|
||||
UPDATE testjson SET j = replace(j,char(125),',"e":9'||char(125));
|
||||
SELECT j FROM testjson;
|
||||
} {
|
||||
{{"a":1,"e":9}}
|
||||
{{"b":2,"e":9}}
|
||||
{{"c":3,"e":9}}
|
||||
{{"d":4,"e":9}}
|
||||
}
|
||||
do_execsql_test 3.5b {
|
||||
SELECT group_concat(x,'') OVER (
|
||||
ORDER BY id ROWS BETWEEN 1 FOLLOWING AND 2 FOLLOWING
|
||||
) FROM testjson ORDER BY id;
|
||||
} {bc cd d {}}
|
||||
do_execsql_test 3.5c {
|
||||
SELECT json_group_array(json(j)) OVER (
|
||||
ORDER BY id ROWS BETWEEN 1 FOLLOWING AND 2 FOLLOWING
|
||||
) FROM testjson;
|
||||
} {
|
||||
{[{"b":2,"e":9},{"c":3,"e":9}]}
|
||||
{[{"c":3,"e":9},{"d":4,"e":9}]}
|
||||
{[{"d":4,"e":9}]}
|
||||
{[]}
|
||||
}
|
||||
do_execsql_test 3.5d {
|
||||
SELECT json_group_object(x,json(j)) OVER (
|
||||
ORDER BY id ROWS BETWEEN 1 FOLLOWING AND 2 FOLLOWING
|
||||
) FROM testjson;
|
||||
} {
|
||||
{{"b":{"b":2,"e":9},"c":{"c":3,"e":9}}}
|
||||
{{"c":{"c":3,"e":9},"d":{"d":4,"e":9}}}
|
||||
{{"d":{"d":4,"e":9}}}
|
||||
{{}}
|
||||
}
|
||||
|
||||
do_execsql_test 3.7b {
|
||||
SELECT group_concat(x,'') FILTER (WHERE id!=2) OVER (
|
||||
ORDER BY id ROWS BETWEEN 2 PRECEDING AND 1 PRECEDING
|
||||
) FROM testjson;
|
||||
} {{} a a c}
|
||||
|
||||
do_execsql_test 3.7c {
|
||||
SELECT json_group_array(json(j)) FILTER (WHERE id!=2) OVER (
|
||||
ORDER BY id ROWS BETWEEN 2 PRECEDING AND 1 PRECEDING
|
||||
) FROM testjson
|
||||
} {
|
||||
{[]}
|
||||
{[{"a":1,"e":9}]}
|
||||
{[{"a":1,"e":9}]}
|
||||
{[{"c":3,"e":9}]}
|
||||
}
|
||||
do_execsql_test 3.7d {
|
||||
SELECT json_group_object(x,json(j)) FILTER (WHERE id!=2) OVER (
|
||||
ORDER BY id ROWS BETWEEN 2 PRECEDING AND 1 PRECEDING
|
||||
) FROM testjson
|
||||
} {
|
||||
{{}}
|
||||
{{"a":{"a":1,"e":9}}}
|
||||
{{"a":{"a":1,"e":9}}}
|
||||
{{"c":{"c":3,"e":9}}}
|
||||
}
|
||||
}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
do_execsql_test 4.0 {
|
||||
CREATE TABLE x(a);
|
||||
INSERT INTO x VALUES(1);
|
||||
INSERT INTO x VALUES(2);
|
||||
}
|
||||
|
||||
do_execsql_test 4.1 {
|
||||
WITH y AS (
|
||||
SELECT Row_Number() OVER (win) FROM x WINDOW win AS (PARTITION BY a)
|
||||
)
|
||||
SELECT * FROM y;
|
||||
} {
|
||||
1 1
|
||||
}
|
||||
|
||||
do_catchsql_test 4.2 {
|
||||
WITH y AS (
|
||||
SELECT Row_Number() OVER (win) FROM x WINDOW win AS (PARTITION
|
||||
BY fake_column))
|
||||
SELECT * FROM y;
|
||||
} {1 {no such column: fake_column}}
|
||||
|
||||
do_catchsql_test 4.3 {
|
||||
SELECT 1 WINDOW win AS (PARTITION BY fake_column);
|
||||
} {0 1}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
do_execsql_test 5.0 {
|
||||
CREATE TABLE t1(a, c);
|
||||
CREATE INDEX i1 ON t1(a);
|
||||
|
||||
INSERT INTO t1 VALUES(0, 421);
|
||||
INSERT INTO t1 VALUES(1, 844);
|
||||
INSERT INTO t1 VALUES(2, 1001);
|
||||
}
|
||||
|
||||
do_execsql_test 5.1 {
|
||||
SELECT a, sum(c) OVER (
|
||||
ORDER BY a RANGE BETWEEN 0 PRECEDING AND 3 PRECEDING
|
||||
) FROM t1;
|
||||
} {0 {} 1 {} 2 {}}
|
||||
|
||||
do_execsql_test 5.2 {
|
||||
INSERT INTO t1 VALUES(NULL, 123);
|
||||
INSERT INTO t1 VALUES(NULL, 111);
|
||||
INSERT INTO t1 VALUES('xyz', 222);
|
||||
INSERT INTO t1 VALUES('xyz', 333);
|
||||
|
||||
SELECT a, sum(c) OVER (
|
||||
ORDER BY a RANGE BETWEEN 0 PRECEDING AND 3 PRECEDING
|
||||
) FROM t1;
|
||||
} {{} 234 {} 234 0 {} 1 {} 2 {} xyz 555 xyz 555}
|
||||
|
||||
do_execsql_test 5.3 {
|
||||
SELECT a, sum(c) OVER (
|
||||
ORDER BY a RANGE BETWEEN 2 FOLLOWING AND 0 FOLLOWING
|
||||
) FROM t1;
|
||||
} {{} 234 {} 234 0 {} 1 {} 2 {} xyz 555 xyz 555}
|
||||
|
||||
do_execsql_test 5.4 {
|
||||
SELECT a, sum(c) OVER (
|
||||
ORDER BY a RANGE BETWEEN 0 PRECEDING AND 3 PRECEDING EXCLUDE NO OTHERS
|
||||
) FROM t1;
|
||||
} {{} 234 {} 234 0 {} 1 {} 2 {} xyz 555 xyz 555}
|
||||
|
||||
do_execsql_test 5.5 {
|
||||
SELECT a, sum(c) OVER (
|
||||
ORDER BY a RANGE BETWEEN 2 FOLLOWING AND 0 FOLLOWING EXCLUDE NO OTHERS
|
||||
) FROM t1;
|
||||
} {{} 234 {} 234 0 {} 1 {} 2 {} xyz 555 xyz 555}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
do_execsql_test 6.0 {
|
||||
CREATE TABLE t1(a, c);
|
||||
CREATE INDEX i1 ON t1(a);
|
||||
|
||||
INSERT INTO t1 VALUES(7, 997);
|
||||
INSERT INTO t1 VALUES(8, 997);
|
||||
INSERT INTO t1 VALUES('abc', 1001);
|
||||
}
|
||||
do_execsql_test 6.1 {
|
||||
SELECT a, sum(c) OVER (
|
||||
ORDER BY a RANGE BETWEEN 2 FOLLOWING AND 0 FOLLOWING
|
||||
) FROM t1;
|
||||
} {7 {} 8 {} abc 1001}
|
||||
do_execsql_test 6.2 {
|
||||
SELECT a, sum(c) OVER (
|
||||
ORDER BY a RANGE BETWEEN 2 FOLLOWING AND 0 FOLLOWING EXCLUDE NO OTHERS
|
||||
) FROM t1;
|
||||
} {7 {} 8 {} abc 1001}
|
||||
|
||||
#-------------------------------------------------------------------------
|
||||
reset_db
|
||||
do_execsql_test 7.0 {
|
||||
CREATE TABLE t1(a, c);
|
||||
CREATE INDEX i1 ON t1(a);
|
||||
|
||||
INSERT INTO t1 VALUES(NULL, 46);
|
||||
INSERT INTO t1 VALUES(NULL, 45);
|
||||
INSERT INTO t1 VALUES(7, 997);
|
||||
INSERT INTO t1 VALUES(7, 1000);
|
||||
INSERT INTO t1 VALUES(8, 997);
|
||||
INSERT INTO t1 VALUES(8, 1000);
|
||||
INSERT INTO t1 VALUES('abc', 1001);
|
||||
INSERT INTO t1 VALUES('abc', 1004);
|
||||
INSERT INTO t1 VALUES('xyz', 3333);
|
||||
}
|
||||
|
||||
do_execsql_test 7.1 {
|
||||
SELECT a, max(c) OVER (
|
||||
ORDER BY a RANGE BETWEEN 2 FOLLOWING AND 0 FOLLOWING
|
||||
) FROM t1;
|
||||
} {{} 46 {} 46 7 {} 7 {} 8 {} 8 {} abc 1004 abc 1004 xyz 3333}
|
||||
do_execsql_test 7.2 {
|
||||
SELECT a, min(c) OVER (
|
||||
ORDER BY a RANGE BETWEEN 2 FOLLOWING AND 0 FOLLOWING
|
||||
) FROM t1;
|
||||
} {{} 45 {} 45 7 {} 7 {} 8 {} 8 {} abc 1001 abc 1001 xyz 3333}
|
||||
|
||||
do_execsql_test 7.3 {
|
||||
SELECT a, max(c) OVER (
|
||||
ORDER BY a RANGE BETWEEN 0 PRECEDING AND 2 PRECEDING
|
||||
) FROM t1;
|
||||
} {{} 46 {} 46 7 {} 7 {} 8 {} 8 {} abc 1004 abc 1004 xyz 3333}
|
||||
do_execsql_test 7.4 {
|
||||
SELECT a, min(c) OVER (
|
||||
ORDER BY a RANGE BETWEEN 0 PRECEDING AND 2 PRECEDING
|
||||
) FROM t1;
|
||||
} {{} 45 {} 45 7 {} 7 {} 8 {} 8 {} abc 1001 abc 1001 xyz 3333}
|
||||
|
||||
finish_test
|
||||
@@ -17,6 +17,10 @@ set testdir [file dirname $argv0]
|
||||
source $testdir/tester.tcl
|
||||
set testprefix without_rowid1
|
||||
|
||||
proc do_execsql_test_if_vtab {tn sql {res {}}} {
|
||||
ifcapable vtab { uplevel [list do_execsql_test $tn $sql $res] }
|
||||
}
|
||||
|
||||
# Create and query a WITHOUT ROWID table.
|
||||
#
|
||||
do_execsql_test without_rowid1-1.0 {
|
||||
@@ -31,7 +35,7 @@ do_execsql_test without_rowid1-1.0 {
|
||||
|
||||
integrity_check without_rowid1-1.0ic
|
||||
|
||||
do_execsql_test without_rowid1-1.0ixi {
|
||||
do_execsql_test_if_vtab without_rowid1-1.0ixi {
|
||||
SELECT name, key FROM pragma_index_xinfo('t1');
|
||||
} {c 1 a 1 b 0 d 0}
|
||||
|
||||
@@ -119,7 +123,7 @@ do_execsql_test 2.1.2 {
|
||||
UPDATE t4 SET a = 'ABC';
|
||||
SELECT * FROM t4;
|
||||
} {ABC def}
|
||||
do_execsql_test 2.1.3 {
|
||||
do_execsql_test_if_vtab 2.1.3 {
|
||||
SELECT name, coll, key FROM pragma_index_xinfo('t4');
|
||||
} {a nocase 1 b BINARY 0}
|
||||
|
||||
@@ -135,7 +139,7 @@ do_execsql_test 2.2.2 {
|
||||
SELECT * FROM t4;
|
||||
} {xyz ABC}
|
||||
|
||||
do_execsql_test 2.2.3 {
|
||||
do_execsql_test_if_vtab 2.2.3 {
|
||||
SELECT name, coll, key FROM pragma_index_xinfo('t4');
|
||||
} {a nocase 1 b BINARY 0}
|
||||
|
||||
@@ -146,7 +150,7 @@ do_execsql_test 2.3.1 {
|
||||
UPDATE t5 SET a='abc', b='def';
|
||||
} {}
|
||||
|
||||
do_execsql_test 2.3.2 {
|
||||
do_execsql_test_if_vtab 2.3.2 {
|
||||
SELECT name, coll, key FROM pragma_index_xinfo('t5');
|
||||
} {b BINARY 1 a BINARY 1}
|
||||
|
||||
@@ -165,7 +169,7 @@ do_execsql_test 2.4.2 {
|
||||
SELECT * FROM t6 ORDER BY c;
|
||||
} {ABC def ghi ABC def ghi}
|
||||
|
||||
do_execsql_test 2.4.3 {
|
||||
do_execsql_test_if_vtab 2.4.3 {
|
||||
SELECT name, coll, key FROM pragma_index_xinfo('t6');
|
||||
} {b BINARY 1 a nocase 1 c BINARY 0}
|
||||
|
||||
|
||||
@@ -16,6 +16,10 @@
|
||||
set testdir [file dirname $argv0]
|
||||
source $testdir/tester.tcl
|
||||
|
||||
proc do_execsql_test_if_vtab {tn sql {res {}}} {
|
||||
ifcapable vtab { uplevel [list do_execsql_test $tn $sql $res] }
|
||||
}
|
||||
|
||||
do_execsql_test without_rowid6-100 {
|
||||
CREATE TABLE t1(a,b,c,d,e, PRIMARY KEY(a,b,c,a,b,c,d,a,b,c)) WITHOUT ROWID;
|
||||
CREATE INDEX t1a ON t1(b, b);
|
||||
@@ -24,7 +28,7 @@ do_execsql_test without_rowid6-100 {
|
||||
INSERT INTO t1(a,b,c,d,e) SELECT i, i+1000, printf('x%dy',i), 0, 0 FROM c;
|
||||
ANALYZE;
|
||||
} {}
|
||||
do_execsql_test without_rowid6-101 {
|
||||
do_execsql_test_if_vtab without_rowid6-101 {
|
||||
SELECT name, key FROM pragma_index_xinfo('t1');
|
||||
} {a 1 b 1 c 1 d 1 e 0}
|
||||
do_execsql_test without_rowid6-110 {
|
||||
@@ -54,7 +58,7 @@ do_execsql_test without_rowid6-200 {
|
||||
INSERT INTO t1(a,b,c) VALUES(1,8,3),(4,5,6),(7,2,9);
|
||||
SELECT a FROM t1 WHERE b>3 ORDER BY b;
|
||||
} {4 1}
|
||||
do_execsql_test without_rowid6-201 {
|
||||
do_execsql_test_if_vtab without_rowid6-201 {
|
||||
SELECT name, key FROM pragma_index_xinfo('t1');
|
||||
} {b 1 a 0 c 0}
|
||||
do_execsql_test without_rowid6-210 {
|
||||
@@ -111,7 +115,7 @@ do_execsql_test without_rowid6-500 {
|
||||
INSERT INTO t1(a,b,c) VALUES(1,8,3),(4,5,6),(7,2,9);
|
||||
SELECT a FROM t1 WHERE b>3 ORDER BY b;
|
||||
} {4 1}
|
||||
do_execsql_test without_rowid6-501 {
|
||||
do_execsql_test_if_vtab without_rowid6-501 {
|
||||
SELECT name, key FROM pragma_index_xinfo('t1');
|
||||
} {b 1 c 1 a 0}
|
||||
do_execsql_test without_rowid6-510 {
|
||||
|
||||
@@ -15,6 +15,10 @@ set testdir [file dirname $argv0]
|
||||
source $testdir/tester.tcl
|
||||
set testprefix without_rowid7
|
||||
|
||||
proc do_execsql_test_if_vtab {tn sql {res {}}} {
|
||||
ifcapable vtab { uplevel [list do_execsql_test $tn $sql $res] }
|
||||
}
|
||||
|
||||
do_execsql_test 1.0 {
|
||||
CREATE TABLE t1(a, b COLLATE nocase, PRIMARY KEY(a, a, b)) WITHOUT ROWID;
|
||||
}
|
||||
@@ -36,13 +40,13 @@ do_execsql_test 2.1 {
|
||||
do_execsql_test 2.2a {
|
||||
PRAGMA index_info(t2);
|
||||
} {0 0 a 1 0 a}
|
||||
do_execsql_test 2.2b {
|
||||
do_execsql_test_if_vtab 2.2b {
|
||||
SELECT *, '|' FROM pragma_index_info('t2');
|
||||
} {0 0 a | 1 0 a |}
|
||||
do_execsql_test 2.3a {
|
||||
PRAGMA index_xinfo(t2);
|
||||
} {0 0 a 0 nocase 1 1 0 a 0 BINARY 1 2 1 b 0 BINARY 0}
|
||||
do_execsql_test 2.3b {
|
||||
do_execsql_test_if_vtab 2.3b {
|
||||
SELECT *, '|' FROM pragma_index_xinfo('t2');
|
||||
} {0 0 a 0 nocase 1 | 1 0 a 0 BINARY 1 | 2 1 b 0 BINARY 0 |}
|
||||
|
||||
|
||||
+1
-1
@@ -4426,7 +4426,7 @@ void ReportTable(
|
||||
}
|
||||
i++;
|
||||
}
|
||||
if( j>0 ) fprintf(out, "\n"); lineno++;
|
||||
if( j>0 ){ fprintf(out, "\n"); lineno++; }
|
||||
fprintf(out, "};\n"); lineno++;
|
||||
|
||||
/* Output the yy_shift_ofst[] table */
|
||||
|
||||
@@ -65,6 +65,15 @@ while test "$1" != ""; do
|
||||
--nomemstat)
|
||||
SPEEDTEST_OPTS="$SPEEDTEST_OPTS $1"
|
||||
;;
|
||||
--multithread)
|
||||
SPEEDTEST_OPTS="$SPEEDTEST_OPTS $1"
|
||||
;;
|
||||
--singlethread)
|
||||
SPEEDTEST_OPTS="$SPEEDTEST_OPTS $1"
|
||||
;;
|
||||
--serialized)
|
||||
SPEEDTEST_OPTS="$SPEEDTEST_OPTS $1"
|
||||
;;
|
||||
--temp)
|
||||
SPEEDTEST_OPTS="$SPEEDTEST_OPTS --temp 6"
|
||||
;;
|
||||
|
||||
Reference in New Issue
Block a user