]> git.ipfire.org Git - thirdparty/sqlite.git/commitdiff
Minor optimizations to fts3 code.
authordan <dan@noemail.net>
Fri, 20 Nov 2009 02:24:15 +0000 (02:24 +0000)
committerdan <dan@noemail.net>
Fri, 20 Nov 2009 02:24:15 +0000 (02:24 +0000)
FossilOrigin-Name: b456eacbbb16513d1b27e90015ea58a6dc92cc3b

ext/fts3/fts3.c
ext/fts3/fts3Int.h
ext/fts3/fts3_write.c
manifest
manifest.uuid

index 016735350538bbdf31b003561e53a442842b0fac..c868a75b9d9a7d197c49581f227f6b5cdc4f3a9b 100644 (file)
@@ -498,7 +498,11 @@ static int fts3DisconnectMethod(sqlite3_vtab *pVtab){
   for(i=0; i<SizeofArray(p->aStmt); i++){
     sqlite3_finalize(p->aStmt[i]);
   }
+  for(i=0; i<p->nLeavesStmt; i++){
+    sqlite3_finalize(p->aLeavesStmt[i]);
+  }
   sqlite3_free(p->zSelectLeaves);
+  sqlite3_free(p->aLeavesStmt);
 
   /* Invoke the tokenizer destructor to free the tokenizer. */
   p->pTokenizer->pModule->xDestroy(p->pTokenizer);
@@ -864,32 +868,40 @@ static int fulltextClose(sqlite3_vtab_cursor *pCursor){
   return SQLITE_OK;
 }
 
+static int fts3CursorSeek(Fts3Cursor *pCsr){
+  if( pCsr->isRequireSeek ){
+    pCsr->isRequireSeek = 0;
+    sqlite3_bind_int64(pCsr->pStmt, 1, pCsr->iPrevId);
+    if( SQLITE_ROW==sqlite3_step(pCsr->pStmt) ){
+      return SQLITE_OK;
+    }else{
+      int rc;
+      pCsr->isEof = 1;
+      if( SQLITE_OK==(rc = sqlite3_reset(pCsr->pStmt)) ){
+        rc = SQLITE_ERROR;
+      }
+      return rc;
+    }
+  }else{
+    return SQLITE_OK;
+  }
+}
+
 static int fts3NextMethod(sqlite3_vtab_cursor *pCursor){
-  int rc;                         /* Return code */
+  int rc = SQLITE_OK;             /* Return code */
   Fts3Cursor *pCsr = (Fts3Cursor *)pCursor;
 
   if( pCsr->aDoclist==0 ){
-    if( SQLITE_ROW==sqlite3_step(pCsr->pStmt) ){
-      rc = SQLITE_OK;
-    }else{
+    if( SQLITE_ROW!=sqlite3_step(pCsr->pStmt) ){
       pCsr->isEof = 1;
       rc = sqlite3_reset(pCsr->pStmt);
     }
   }else if( pCsr->pNextId>=&pCsr->aDoclist[pCsr->nDoclist] ){
     pCsr->isEof = 1;
-    rc = SQLITE_OK;
   }else{
     sqlite3_reset(pCsr->pStmt);
     fts3GetDeltaVarint(&pCsr->pNextId, &pCsr->iPrevId);
-    sqlite3_bind_int64(pCsr->pStmt, 1, pCsr->iPrevId);
-    if( SQLITE_ROW==sqlite3_step(pCsr->pStmt) ){
-      rc = SQLITE_OK;
-    }else{
-      pCsr->isEof = 1;
-      if( SQLITE_OK==(rc = sqlite3_reset(pCsr->pStmt)) ){
-        rc = SQLITE_ERROR;
-      }
-    }
+    pCsr->isRequireSeek = 1;
   }
   return rc;
 }
@@ -1524,7 +1536,7 @@ static int fts3TermSelect(
             apSegment, nAlloc*sizeof(Fts3SegReader *)
         );
         if( !pArray ){
-          sqlite3Fts3SegReaderFree(pNew);
+          sqlite3Fts3SegReaderFree(p, pNew);
           rc = SQLITE_NOMEM;
           goto finished;
         }
@@ -1563,7 +1575,7 @@ static int fts3TermSelect(
 finished:
   sqlite3_reset(pStmt);
   for(i=0; i<nSegment; i++){
-    sqlite3Fts3SegReaderFree(apSegment[i]);
+    sqlite3Fts3SegReaderFree(p, apSegment[i]);
   }
   sqlite3_free(apSegment);
   return rc;
@@ -1829,10 +1841,14 @@ static int fts3EofMethod(sqlite3_vtab_cursor *pCursor){
 ** one of the sqlite3_result_*() routines to store the requested
 ** value back in the pContext.
 */
-static int fulltextColumn(sqlite3_vtab_cursor *pCursor,
+static int fts3ColumnMethod(sqlite3_vtab_cursor *pCursor,
                           sqlite3_context *pContext, int idxCol){
   Fts3Cursor *c = (Fts3Cursor *) pCursor;
   Fts3Table *v = cursor_vtab(c);
+  int rc = fts3CursorSeek(c);
+  if( rc!=SQLITE_OK ){
+    return rc;
+  }
 
   if( idxCol<v->nColumn ){
     sqlite3_value *pVal = sqlite3_column_value(c->pStmt, idxCol+1);
@@ -1858,7 +1874,11 @@ static int fulltextColumn(sqlite3_vtab_cursor *pCursor,
 */
 static int fts3RowidMethod(sqlite3_vtab_cursor *pCursor, sqlite_int64 *pRowid){
   Fts3Cursor *pCsr = (Fts3Cursor *) pCursor;
-  *pRowid = sqlite3_column_int64(pCsr->pStmt, 0);
+  if( pCsr->aDoclist ){
+    *pRowid = pCsr->iPrevId;
+  }else{
+    *pRowid = sqlite3_column_int64(pCsr->pStmt, 0);
+  }
   return SQLITE_OK;
 }
 
@@ -2089,7 +2109,7 @@ static const sqlite3_module fts3Module = {
   /* xFilter       */ fts3FilterMethod,
   /* xNext         */ fts3NextMethod,
   /* xEof          */ fts3EofMethod,
-  /* xColumn       */ fulltextColumn,
+  /* xColumn       */ fts3ColumnMethod,
   /* xRowid        */ fts3RowidMethod,
   /* xUpdate       */ fts3UpdateMethod,
   /* xBegin        */ fts3BeginMethod,
index af80792a1b87534e98f33ff37083de402d9f7320..77951746df03586ec232276defdbb8ce5e63bc16 100644 (file)
@@ -68,13 +68,13 @@ typedef struct Fts3SegFilter Fts3SegFilter;
 ** arguments.
 */
 struct Fts3Table {
-  sqlite3_vtab base;               /* Base class used by SQLite core */
-  sqlite3 *db;                     /* The database connection */
-  const char *zDb;                 /* logical database name */
-  const char *zName;               /* virtual table name */
-  int nColumn;                     /* number of columns in virtual table */
-  char **azColumn;                 /* column names.  malloced */
-  sqlite3_tokenizer *pTokenizer;   /* tokenizer for inserts and queries */
+  sqlite3_vtab base;              /* Base class used by SQLite core */
+  sqlite3 *db;                    /* The database connection */
+  const char *zDb;                /* logical database name */
+  const char *zName;              /* virtual table name */
+  int nColumn;                    /* number of columns in virtual table */
+  char **azColumn;                /* column names.  malloced */
+  sqlite3_tokenizer *pTokenizer;  /* tokenizer for inserts and queries */
 
   /* Precompiled statements used by the implementation. Each of these 
   ** statements is run and reset within a single virtual table API call. 
@@ -87,6 +87,10 @@ struct Fts3Table {
   **    ORDER BY blockid"
   */
   char *zSelectLeaves;
+  int nLeavesStmt;                /* Valid statements in aLeavesStmt */
+  int nLeavesTotal;               /* Total number of prepared leaves stmts */
+  int nLeavesAlloc;               /* Allocated size of aLeavesStmt */
+  sqlite3_stmt **aLeavesStmt;     /* Array of prepared zSelectLeaves stmts */
 
   /* The following hash table is used to buffer pending index updates during
   ** transactions. Variable nPendingData estimates the memory size of the 
@@ -110,6 +114,7 @@ struct Fts3Cursor {
   int eType;                      /* Search strategy (see below) */
   sqlite3_stmt *pStmt;            /* Prepared statement in use by the cursor */
   int isEof;                      /* True if at End Of Results */
+  int isRequireSeek;              /* True if must seek pStmt to %_content row */
   Fts3Expr *pExpr;                /* Parsed MATCH query string */
   sqlite3_int64 iPrevId;          /* Previous id read from aDoclist */
   char *pNextId;                  /* Pointer into the body of aDoclist */
@@ -176,7 +181,7 @@ void sqlite3Fts3PendingTermsClear(Fts3Table *);
 int sqlite3Fts3Optimize(Fts3Table *);
 int sqlite3Fts3SegReaderNew(Fts3Table *,int, sqlite3_int64,
   sqlite3_int64, sqlite3_int64, const char *, int, Fts3SegReader**);
-void sqlite3Fts3SegReaderFree(Fts3SegReader *);
+void sqlite3Fts3SegReaderFree(Fts3Table *, Fts3SegReader *);
 int sqlite3Fts3SegReaderIterate(
   Fts3Table *, Fts3SegReader **, int, Fts3SegFilter *,
   int (*)(Fts3Table *, void *, char *, int, char *, int),  void *
index b420f45137fb5b10a49b9e2b975f83041be69f75..ec3d00e5d132e9e02831d75659f8594ef5253b99 100644 (file)
@@ -779,9 +779,13 @@ static void fts3SegReaderNextDocid(
 ** Free all allocations associated with the iterator passed as the first
 ** argument.
 */
-void sqlite3Fts3SegReaderFree(Fts3SegReader *pReader){
+void sqlite3Fts3SegReaderFree(Fts3Table *p, Fts3SegReader *pReader){
   if( pReader ){
-    sqlite3_finalize(pReader->pStmt);
+    if( pReader->pStmt ){
+      assert( p->nLeavesStmt<p->nLeavesTotal );
+      sqlite3_reset(pReader->pStmt);
+      p->aLeavesStmt[p->nLeavesStmt++] = pReader->pStmt;
+    }
     sqlite3_free(pReader->zTerm);
     sqlite3_free(pReader);
   }
@@ -820,6 +824,7 @@ int sqlite3Fts3SegReaderNew(
     pReader->nNode = nRoot;
     memcpy(pReader->aNode, zRoot, nRoot);
   }else{
+    sqlite3_stmt *pStmt;
     if( !p->zSelectLeaves ){
       p->zSelectLeaves = sqlite3_mprintf(
           "SELECT block FROM %Q.'%q_segments' WHERE blockid BETWEEN ? AND ? "
@@ -830,9 +835,26 @@ int sqlite3Fts3SegReaderNew(
         goto finished;
       }
     }
-    rc = sqlite3_prepare_v2(p->db, p->zSelectLeaves, -1, &pReader->pStmt, 0);
-    if( rc!=SQLITE_OK ){
-      goto finished;
+    if( p->nLeavesStmt==0 ){
+      if( p->nLeavesTotal==p->nLeavesAlloc ){
+        int nNew = p->nLeavesAlloc + 16;
+        sqlite3_stmt **aNew = (sqlite3_stmt **)sqlite3_realloc(
+            p->aLeavesStmt, nNew*sizeof(sqlite3_stmt *)
+        );
+        if( !aNew ){
+          rc = SQLITE_NOMEM;
+          goto finished;
+        }
+        p->nLeavesAlloc = nNew;
+        p->aLeavesStmt = aNew;
+      }
+      rc = sqlite3_prepare_v2(p->db, p->zSelectLeaves, -1, &pReader->pStmt, 0);
+      if( rc!=SQLITE_OK ){
+        goto finished;
+      }
+      p->nLeavesTotal++;
+    }else{
+      pReader->pStmt = p->aLeavesStmt[--p->nLeavesStmt];
     }
     sqlite3_bind_int64(pReader->pStmt, 1, iStartLeaf);
     sqlite3_bind_int64(pReader->pStmt, 2, iEndLeaf);
@@ -843,7 +865,7 @@ int sqlite3Fts3SegReaderNew(
   if( rc==SQLITE_OK ){
     *ppReader = pReader;
   }else{
-    sqlite3Fts3SegReaderFree(pReader);
+    sqlite3Fts3SegReaderFree(p, pReader);
   }
   return rc;
 }
@@ -1791,7 +1813,7 @@ static int fts3SegmentMerge(Fts3Table *p, int iLevel){
   fts3SegWriterFree(pWriter);
   if( apSegment ){
     for(i=0; i<nSegment; i++){
-      sqlite3Fts3SegReaderFree(apSegment[i]);
+      sqlite3Fts3SegReaderFree(p, apSegment[i]);
     }
     sqlite3_free(apSegment);
   }
index 648a6feefe4fd12799679b6748180001f16c7ff1..85c48d7902b870281a5bc60a9ab8932b347d4762 100644 (file)
--- a/manifest
+++ b/manifest
@@ -1,5 +1,5 @@
-C Merge\sleaves\s[7cd178a72a]\sand\s[598727e6da].
-D 2009-11-19T18:30:14
+C Minor\soptimizations\sto\sfts3\scode.
+D 2009-11-20T02:24:15
 F Makefile.arm-wince-mingw32ce-gcc fcd5e9cd67fe88836360bb4f9ef4cb7f8e2fb5a0
 F Makefile.in 7f6c6aa7feeeb5e26e01b344161d9aa1b5d64177
 F Makefile.linux-gcc d53183f4aa6a9192d249731c90dbdffbd2c68654
@@ -56,9 +56,9 @@ F ext/fts2/mkfts2amal.tcl 974d5d438cb3f7c4a652639262f82418c1e4cff0
 F ext/fts3/README.syntax a19711dc5458c20734b8e485e75fb1981ec2427a
 F ext/fts3/README.tokenizers 998756696647400de63d5ba60e9655036cb966e9
 F ext/fts3/README.txt 8c18f41574404623b76917b9da66fcb0ab38328d
-F ext/fts3/fts3.c e7383c74407e54e198317a92a0229162d2b0b9a7
+F ext/fts3/fts3.c 4990e02c64ea19515b06b1300340bdf9a6f0eaa6
 F ext/fts3/fts3.h 3a10a0af180d502cecc50df77b1b22df142817fe
-F ext/fts3/fts3Int.h f7488bbc9fd12bd3843f59265227321a92b39ed4
+F ext/fts3/fts3Int.h 74b21db1c4479c220e803ecf45a78de3b5ac9480
 F ext/fts3/fts3_expr.c bdf11f3602f62f36f0e42823680bf22033dae0de
 F ext/fts3/fts3_hash.c 1af1833a4d581ee8d668bb71f5a500f7a0104982
 F ext/fts3/fts3_hash.h 39524725425078bf9e814e9569c74a8e5a21b9fb
@@ -68,7 +68,7 @@ F ext/fts3/fts3_snippet.c 082f2906deaaa2656f19b88834e89d099352af6e
 F ext/fts3/fts3_tokenizer.c 36f78d1a43a29b0feaec1ced6da9e56b9c653d1f
 F ext/fts3/fts3_tokenizer.h 7ff73caa3327589bf6550f60d93ebdd1f6a0fb5c
 F ext/fts3/fts3_tokenizer1.c 0a5bcc579f35de5d24a9345d7908dc25ae403ee7
-F ext/fts3/fts3_write.c 9048d3c1d5dcb43769cde7c00c3b3c8bcac41099
+F ext/fts3/fts3_write.c 3c8a5d912af939232480b3f4064ac49621816250
 F ext/fts3/mkfts3amal.tcl 252ecb7fe6467854f2aa237bf2c390b74e71f100
 F ext/icu/README.txt 3b130aa66e7a681136f6add198b076a2f90d1e33
 F ext/icu/icu.c 12e763d288d23b5a49de37caa30737b971a2f1e2
@@ -772,7 +772,7 @@ F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff
 F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224
 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e
 F tool/vdbe-compress.tcl d70ea6d8a19e3571d7ab8c9b75cba86d1173ff0f
-P 7cd178a72ab99c94fdacffb19aad819ae600e57d 598727e6dae87f133c658fa125684f6ad978be60
-R fa3f77e1031f7ddfc32b18ebcb9c7d5a
+P 4115c0c286052e32cb81f77a644d530c1766206f
+R d93aed1e18b2651263389c52f5a6aa80
 U dan
-Z 98edfed95630a7f71d24a5499ccf87bc
+Z 234100290840447274601364a421931c
index 573dbc00c3f0b0466e692114b28e924da73fa364..92feca51d4c3ea0f053a65a9fd16948a7a4cebb4 100644 (file)
@@ -1 +1 @@
-4115c0c286052e32cb81f77a644d530c1766206f
\ No newline at end of file
+b456eacbbb16513d1b27e90015ea58a6dc92cc3b
\ No newline at end of file