Further improvements to test coverage of fts5 code.

FossilOrigin-Name: d4331943dff259380c4025bb740d8aba6972d351
This commit is contained in:
dan
2015-05-01 20:38:57 +00:00
parent 557085a5a1
commit 0501b2492a
5 changed files with 116 additions and 63 deletions
+40 -41
View File
@@ -104,13 +104,13 @@ struct Fts5Parse {
};
void sqlite3Fts5ParseError(Fts5Parse *pParse, const char *zFmt, ...){
va_list ap;
va_start(ap, zFmt);
if( pParse->rc==SQLITE_OK ){
va_list ap;
va_start(ap, zFmt);
pParse->zErr = sqlite3_vmprintf(zFmt, ap);
va_end(ap);
pParse->rc = SQLITE_ERROR;
}
va_end(ap);
}
static int fts5ExprIsspace(char t){
@@ -269,52 +269,51 @@ int sqlite3Fts5ExprPhraseExpr(
Fts5Expr **ppNew
){
int rc = SQLITE_OK; /* Return code */
Fts5ExprPhrase *pOrig = 0; /* The phrase extracted from pExpr */
int i; /* Used to iterate through phrase terms */
/* Components of the new expression object */
Fts5Expr *pNew;
Fts5ExprPhrase **apPhrase;
Fts5ExprNode *pNode;
Fts5ExprNearset *pNear;
Fts5ExprPhrase *pCopy;
Fts5ExprPhrase *pOrig; /* The phrase extracted from pExpr */
Fts5ExprPhrase *pCopy; /* Copy of pOrig */
Fts5Expr *pNew = 0; /* Expression to return via *ppNew */
pOrig = pExpr->apExprPhrase[iPhrase];
pCopy = (Fts5ExprPhrase*)fts5ExprMalloc(&rc,
sizeof(Fts5ExprPhrase) + sizeof(Fts5ExprTerm) * pOrig->nTerm
);
pNew = (Fts5Expr*)fts5ExprMalloc(&rc, sizeof(Fts5Expr));
apPhrase = (Fts5ExprPhrase**)fts5ExprMalloc(&rc, sizeof(Fts5ExprPhrase*));
pNode = (Fts5ExprNode*)fts5ExprMalloc(&rc, sizeof(Fts5ExprNode));
pNear = (Fts5ExprNearset*)fts5ExprMalloc(&rc,
sizeof(Fts5ExprNearset) + sizeof(Fts5ExprPhrase*)
);
if( pCopy ){
int i; /* Used to iterate through phrase terms */
Fts5ExprPhrase **apPhrase;
Fts5ExprNode *pNode;
Fts5ExprNearset *pNear;
for(i=0; rc==SQLITE_OK && i<pOrig->nTerm; i++){
pCopy->aTerm[i].zTerm = fts5ExprStrdup(&rc, pOrig->aTerm[i].zTerm);
pCopy->aTerm[i].bPrefix = pOrig->aTerm[i].bPrefix;
}
pNew = (Fts5Expr*)fts5ExprMalloc(&rc, sizeof(Fts5Expr));
apPhrase = (Fts5ExprPhrase**)fts5ExprMalloc(&rc, sizeof(Fts5ExprPhrase*));
pNode = (Fts5ExprNode*)fts5ExprMalloc(&rc, sizeof(Fts5ExprNode));
pNear = (Fts5ExprNearset*)fts5ExprMalloc(&rc,
sizeof(Fts5ExprNearset) + sizeof(Fts5ExprPhrase*)
);
if( rc==SQLITE_OK ){
/* All the allocations succeeded. Put the expression object together. */
pNew->pIndex = pExpr->pIndex;
pNew->pRoot = pNode;
pNew->nPhrase = 1;
pNew->apExprPhrase = apPhrase;
pNew->apExprPhrase[0] = pCopy;
for(i=0; i<pOrig->nTerm; i++){
pCopy->aTerm[i].zTerm = fts5ExprStrdup(&rc, pOrig->aTerm[i].zTerm);
pCopy->aTerm[i].bPrefix = pOrig->aTerm[i].bPrefix;
}
pNode->eType = FTS5_STRING;
pNode->pNear = pNear;
if( rc==SQLITE_OK ){
/* All the allocations succeeded. Put the expression object together. */
pNew->pIndex = pExpr->pIndex;
pNew->pRoot = pNode;
pNew->nPhrase = 1;
pNew->apExprPhrase = apPhrase;
pNew->apExprPhrase[0] = pCopy;
pNear->iCol = -1;
pNear->nPhrase = 1;
pNear->apPhrase[0] = pCopy;
pNode->eType = FTS5_STRING;
pNode->pNear = pNear;
pCopy->nTerm = pOrig->nTerm;
pCopy->pNode = pNode;
}else{
/* At least one allocation failed. Free them all. */
if( pCopy ){
pNear->iCol = -1;
pNear->nPhrase = 1;
pNear->apPhrase[0] = pCopy;
pCopy->nTerm = pOrig->nTerm;
pCopy->pNode = pNode;
}else{
/* At least one allocation failed. Free them all. */
for(i=0; i<pOrig->nTerm; i++){
sqlite3_free(pCopy->aTerm[i].zTerm);
}
@@ -504,7 +503,7 @@ static int fts5ExprNearIsMatch(Fts5ExprNearset *pNear, int *pbMatch){
/* If the aStatic[] array is not large enough, allocate a large array
** using sqlite3_malloc(). This approach could be improved upon. */
if( pNear->nPhrase>(sizeof(aStatic) / sizeof(aStatic[0])) ){
int nByte = sizeof(Fts5LookaheadReader) * pNear->nPhrase;
int nByte = sizeof(Fts5NearTrimmer) * pNear->nPhrase;
a = (Fts5NearTrimmer*)sqlite3_malloc(nByte);
if( !a ) return SQLITE_NOMEM;
memset(a, 0, nByte);
@@ -719,7 +718,7 @@ static int fts5ExprNearNextMatch(
/* Advance the iterators until they all point to the same rowid */
rc = fts5ExprNearNextRowidMatch(pExpr, pNode, bFromValid, iFrom);
if( pNode->bEof || rc!=SQLITE_OK ) break;
if( rc!=SQLITE_OK || pNode->bEof ) break;
/* Check that each phrase in the nearset matches the current row.
** Populate the pPhrase->poslist buffers at the same time. If any
+9 -11
View File
@@ -9,6 +9,9 @@
#
#*************************************************************************
#
# Test the fts5 expression parser directly using the fts5_expr() SQL
# test function.
#
source [file join [file dirname [info script]] fts5_common.tcl]
set testprefix fts5ea
@@ -40,6 +43,10 @@ foreach {tn expr res} {
8 {one OR two AND three} {"one" OR ("two" AND "three")}
9 {NEAR(one two)} {NEAR("one" "two", 10)}
10 {NEAR("one three"* two, 5)} {NEAR("one" + "three" * "two", 5)}
11 {a OR b NOT c} {"a" OR ("b" NOT "c")}
12 "\x20one\x20two\x20three" {("one" AND "two") AND "three"}
13 "\x09one\x0Atwo\x0Dthree" {("one" AND "two") AND "three"}
14 {"abc""def"} {"abc" + "def"}
} {
do_execsql_test 1.$tn {SELECT fts5_expr($expr)} [list $res]
}
@@ -53,7 +60,6 @@ foreach {tn expr res} {
do_execsql_test 2.$tn {SELECT fts5_expr($expr, 'c1', 'c2')} [list $res]
}
breakpoint
foreach {tn expr err} {
1 {AND} {fts5: syntax error near "AND"}
2 {abc def AND} {fts5: syntax error near ""}
@@ -63,21 +69,13 @@ foreach {tn expr err} {
6 {(a OR b) NOT c)} {fts5: syntax error near ")"}
7 {nosuch: a nosuch2: b} {no such column: nosuch}
8 {addr: a nosuch2: b} {no such column: nosuch2}
9 {NOT} {fts5: syntax error near "NOT"}
10 {a AND "abc} {unterminated string}
} {
do_catchsql_test 3.$tn {SELECT fts5_expr($expr, 'name', 'addr')} [list 1 $err]
}
# do_syntax_error_test 1.0 {NOT} {syntax error near "NOT"}
# do_catchsql_test 1.1 {
# SELECT fts5_expr('a OR b NOT c')
#} {0 {"a" OR "b" NOT "c"}}
#do_execsql_test 1.0 { SELECT fts5_expr('a') } {{"a"}}
finish_test
+58 -2
View File
@@ -158,8 +158,6 @@ do_faultsim_test 5.2 -faults oom-* -body {
faultsim_test_result "0 {10-$::str {a b c}}"
}
}
#-------------------------------------------------------------------------
# OOM errors within auxiliary functions.
@@ -203,6 +201,64 @@ do_faultsim_test 6.2 -faults oom-t* -body {
faultsim_test_result {0 {0 2 7}} {1 SQLITE_NOMEM}
}
#-------------------------------------------------------------------------
# OOM error when querying for a phrase with many tokens.
#
reset_db
do_execsql_test 7.0 {
CREATE VIRTUAL TABLE tt USING fts5(x, y);
INSERT INTO tt VALUES('f b g b c b', 'f a d c c b'); -- 1
INSERT INTO tt VALUES('d a e f e d', 'f b b d e e'); -- 2
INSERT INTO tt VALUES('f b g a d c', 'e f c f a d'); -- 3
INSERT INTO tt VALUES('f f c d g f', 'f a e b g b'); -- 4
INSERT INTO tt VALUES('a g b d a g', 'e g a e a c'); -- 5
INSERT INTO tt VALUES('c d b d e f', 'f g e g e e'); -- 6
INSERT INTO tt VALUES('e g f f b c', 'f c e f g f'); -- 7
INSERT INTO tt VALUES('e g c f c e', 'f e e a f g'); -- 8
INSERT INTO tt VALUES('e a e b e e', 'd c c f f f'); -- 9
INSERT INTO tt VALUES('f a g g c c', 'e g d g c e'); -- 10
INSERT INTO tt VALUES('c d b a e f', 'f g e h e e'); -- 11
}
do_faultsim_test 7.2 -faults oom-* -body {
db eval { SELECT rowid FROM tt WHERE tt MATCH 'f+g+e+g+e+e' }
} -test {
faultsim_test_result {0 6} {1 SQLITE_NOMEM}
}
do_faultsim_test 7.3 -faults oom-* -body {
db eval { SELECT rowid FROM tt WHERE tt MATCH 'NEAR(a b c d e f)' }
} -test {
faultsim_test_result {0 11} {1 SQLITE_NOMEM}
}
}
#-------------------------------------------------------------------------
#
reset_db
do_execsql_test 8.0 {
CREATE VIRTUAL TABLE tt USING fts5(x);
INSERT INTO tt(tt, rank) VALUES('pgsz', 32);
BEGIN;
INSERT INTO tt(rowid, x) VALUES(1, 'a b c d x x');
WITH ii(i) AS (SELECT 2 UNION ALL SELECT i+1 FROM ii WHERE i<99)
INSERT INTO tt(rowid, x) SELECT i, 'a b c x x d' FROM ii;
INSERT INTO tt(rowid, x) VALUES(100, 'a b c d x x');
COMMIT;
}
do_faultsim_test 8.1 -faults oom-t* -body {
db eval { SELECT rowid FROM tt WHERE tt MATCH 'NEAR(a b c d, 2)' }
} -test {
faultsim_test_result {0 {1 100}} {1 SQLITE_NOMEM}
}
do_faultsim_test 8.2 -faults oom-t* -body {
db eval { SELECT count(*) FROM tt WHERE tt MATCH 'a OR d' }
} -test {
faultsim_test_result {0 100} {1 SQLITE_NOMEM}
}
+8 -8
View File
@@ -1,5 +1,5 @@
C Improve\stest\scoverage\sof\sfts5.c.
D 2015-05-01T12:14:23.640
C Further\simprovements\sto\stest\scoverage\sof\sfts5\scode.
D 2015-05-01T20:38:57.153
F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f
F Makefile.in 31b38b9da2e4b36f54a013bd71a5c3f6e45ca78f
F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23
@@ -110,7 +110,7 @@ F ext/fts5/fts5Int.h 2e0a1a6b77e1e014b7e9b1479ca686ff79930457
F ext/fts5/fts5_aux.c d53f00f31ad615ca4f139dd8751f9041afa00971
F ext/fts5/fts5_buffer.c 8c8cfe7f09ca2767ab53ea883f9a0af0edb6bbae
F ext/fts5/fts5_config.c ecbbd5163758a958106867051892e0dfecf68b5c
F ext/fts5/fts5_expr.c 663c75dfdb1bfd8809d696357d7b55f507815098
F ext/fts5/fts5_expr.c e2005ba7823f4ac51d46a8e5aaa1ff66c701b32e
F ext/fts5/fts5_hash.c 29d8b0668727863cc1f1efa65efe4dd78635b016
F ext/fts5/fts5_index.c de588982b0237b1605d6c37afd115b34c95c3da1
F ext/fts5/fts5_storage.c ef60fc9dcc4e274f9589165e26833173c273ae18
@@ -140,12 +140,12 @@ F ext/fts5/test/fts5corrupt.test 138aecc75c36c3dac9259c7f57c5bc3d009255f8
F ext/fts5/test/fts5corrupt2.test 494111fd4f2dab36499cf97718eaba1f7c11e9d0
F ext/fts5/test/fts5dlidx.test 748a84ceb74a4154725096a26dfa854260b0182f
F ext/fts5/test/fts5doclist.test 635b80ac785627841a59c583bac702b55d49fdc5
F ext/fts5/test/fts5ea.test 04695560a444fcc00c3c4f27783bdcfbf71f030c
F ext/fts5/test/fts5ea.test 7cc498993c16849bb866dbdfb008d91a29f9870b
F ext/fts5/test/fts5eb.test 728a1f23f263548f5c29b29dfb851b5f2dbe723e
F ext/fts5/test/fts5fault1.test ed71717a479bef32d05f02d9c48691011d160d4d
F ext/fts5/test/fts5fault2.test 26c3d70648f691e2cc9391e14bbc11a973656383
F ext/fts5/test/fts5fault3.test d6e9577d4312e331a913c72931bf131704efc8f3
F ext/fts5/test/fts5fault4.test 087066bae36f41227eb85968a2436c8a9c960501
F ext/fts5/test/fts5fault4.test 4090af395d8d3342c0a0b27349dd71eb7cc6262d
F ext/fts5/test/fts5full.test 0924bdca5416a242103239ace79c6f5aa34bab8d
F ext/fts5/test/fts5hash.test adb7b0442cc1c77c507f07e16d11490486e75dfa
F ext/fts5/test/fts5merge.test 453a0717881aa7784885217b2040f3f275caff03
@@ -1315,7 +1315,7 @@ F tool/vdbe_profile.tcl 67746953071a9f8f2f668b73fe899074e2c6d8c1
F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4
F tool/warnings.sh 0abfd78ceb09b7f7c27c688c8e3fe93268a13b32
F tool/win/sqlite.vsix deb315d026cc8400325c5863eef847784a219a2f
P c1f07a3aa98eac87e2747527d15e5e5562221ceb
R 67c24377157269f998af5007c163ea4c
P add4f4681c648dcbecaa68d08f7b2f4e6d63003c
R 58de859125935eeaf7ecede3ffbb5a07
U dan
Z 082bd0388383a4ef8c727daa5b60df05
Z fc00d731e9356a3f17b66c35cad599ad
+1 -1
View File
@@ -1 +1 @@
add4f4681c648dcbecaa68d08f7b2f4e6d63003c
d4331943dff259380c4025bb740d8aba6972d351