From: drh Date: Fri, 23 Dec 2016 13:52:45 +0000 (+0000) Subject: Add check to prevent a VList from growing after pointers to labels have been X-Git-Tag: version-3.16.0~27^2 X-Git-Url: http://git.ipfire.org/?a=commitdiff_plain;h=ce1bbe51b5c57b6487e92fe83c5c168a84c9e051;p=thirdparty%2Fsqlite.git Add check to prevent a VList from growing after pointers to labels have been taken. FossilOrigin-Name: aa23d7eaf69f5ecbf9500b2353846094cae41e6c --- diff --git a/manifest b/manifest index ed40e8d7f5..6842b9b8b8 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Fix\sthe\sVList\sobject\sso\sthat\sit\sactually\sworks. -D 2016-12-23T13:30:53.667 +C Add\scheck\sto\sprevent\sa\sVList\sfrom\sgrowing\safter\spointers\sto\slabels\shave\sbeen\ntaken. +D 2016-12-23T13:52:45.010 F Makefile.in 41bd4cad981487345c4a84081074bcdb876e4b2e F Makefile.linux-gcc 7bc79876b875010e8c8f9502eb935ca92aa3c434 F Makefile.msc b8ca53350ae545e3562403d5da2a69cec79308da @@ -341,7 +341,7 @@ F src/ctime.c 9f2296a4e5d26ebf0e0d95a0af4628f1ea694e7a F src/date.c b48378aeac68fa20c811404955a9b62108df47d8 F src/dbstat.c 19ee7a4e89979d4df8e44cfac7a8f905ec89b77d F src/delete.c c8bc10d145c9666a34ae906250326fdaa8d58fa5 -F src/expr.c fedcfcd8749f95627dfe0aeb5630b68c5979cb0b +F src/expr.c a90e37bc542abe33890cafccacbf8a7db9cb5401 F src/fault.c 460f3e55994363812d9d60844b2a6de88826e007 F src/fkey.c 2e9aabe1aee76273aff8a84ee92c464e095400ae F src/func.c 43916c1d8e6da5d107d91d2b212577d4f69a876a @@ -453,7 +453,7 @@ F src/treeview.c 4e44ade3bfe59d82005039f72e09333ce2b4162c F src/trigger.c c9f0810043b265724fdb1bdd466894f984dfc182 F src/update.c 1da7c462110bffed442a42884cb0d528c1db46d8 F src/utf.c 699001c79f28e48e9bcdf8a463da029ea660540c -F src/util.c adf5ff9e457b69d3cab2afa45c9c4ce5da83da06 +F src/util.c 1534060bc034cdc51381c040c8bd6252dbcb64c9 F src/vacuum.c 33c174b28886b2faf26e503b5a49a1c01a9b1c16 F src/vdbe.c 54b12d95dbf10533ab2584acbf31ae12b8bfe171 F src/vdbe.h 50ee139f9c68fff91be1d717ed3a6abbd496919c @@ -1539,7 +1539,7 @@ F vsixtest/vsixtest.tcl 6a9a6ab600c25a91a7acc6293828957a386a8a93 F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0 -P 68ecafa1425a41358c88f41efea3262f1b4490f2 -R e3b464298f4645ba05beea0d35779569 +P 9dcd85698af46fd5ba34004ca690d368c4ae3078 +R 2f816100f2d74d42d3a1978c26f09af2 U drh -Z e1b50397ad009309edd4038594b0291c +Z 3cd0270ead5747022cdd1e84b75d8956 diff --git a/manifest.uuid b/manifest.uuid index d87d18b9ad..63d4ce335d 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -9dcd85698af46fd5ba34004ca690d368c4ae3078 \ No newline at end of file +aa23d7eaf69f5ecbf9500b2353846094cae41e6c \ No newline at end of file diff --git a/src/expr.c b/src/expr.c index 3f8406bc53..ecc6c7928b 100644 --- a/src/expr.c +++ b/src/expr.c @@ -3422,6 +3422,7 @@ int sqlite3ExprCodeTarget(Parse *pParse, Expr *pExpr, int target){ if( pExpr->u.zToken[1]!=0 ){ const char *z = sqlite3VListNumToName(pParse->pVList, pExpr->iColumn); assert( pExpr->u.zToken[0]=='?' || strcmp(pExpr->u.zToken, z)==0 ); + pParse->pVList[0] = 0; /* Indicate VList may no longer be enlarged */ sqlite3VdbeAppendP4(v, (char*)z, P4_STATIC); } return target; diff --git a/src/util.c b/src/util.c index 5ece9226ff..b9684c6c01 100644 --- a/src/util.c +++ b/src/util.c @@ -1457,7 +1457,7 @@ u64 sqlite3LogEstToInt(LogEst x){ /* ** Add a new name/number pair to a VList. This might require that the ** VList object be reallocated, so return the new VList. If an OOM -** error occurs, the original VList freed, NULL is returned, and the +** error occurs, the original VList returned and the ** db->mallocFailed flag is set. ** ** A VList is really just an array of integers. To destroy a VList, @@ -1468,11 +1468,27 @@ u64 sqlite3LogEstToInt(LogEst x){ ** Each name/number pair is encoded by subsequent groups of 3 or more ** integers. ** -** Each name/number pair starts with two integers which are the number +** Each name/number pair starts with two integers which are the numeric ** value for the pair and the size of the name/number pair, respectively. ** The text name overlays one or more following integers. The text name ** is always zero-terminated. -** +** +** Conceptually: +** +** struct VList { +** int nAlloc; // Number of allocated slots +** int nUsed; // Number of used slots +** struct VListEntry { +** int iValue; // Value for this entry +** int nSlot; // Slots used by this entry +** // ... variable name goes here +** } a[0]; +** } +** +** During code generation, pointers to the variable names within the +** VList are taken. When that happens, nAlloc is set to zero as an +** indication that the VList may never again be enlarged, since the +** accompanying realloc() would invalidate the pointers. */ VList *sqlite3VListAdd( sqlite3 *db, /* The database connection used for malloc() */ @@ -1482,18 +1498,16 @@ VList *sqlite3VListAdd( int iVal /* Value to associate with zName */ ){ int nInt; /* number of sizeof(int) objects needed for zName */ - char *z; - int i; + char *z; /* Pointer to where zName will be stored */ + int i; /* Index in pIn[] where zName is stored */ nInt = nName/4 + 3; + assert( pIn==0 || pIn[0]>=3 ); /* Verify ok to add new elements */ if( pIn==0 || pIn[1]+nInt > pIn[0] ){ /* Enlarge the allocation */ int nAlloc = (pIn ? pIn[0]*2 : 10) + nInt; VList *pOut = sqlite3DbRealloc(db, pIn, nAlloc*sizeof(int)); - if( pOut==0 ){ - sqlite3DbFree(db, pIn); - return 0; - } + if( pOut==0 ) return pIn; if( pIn==0 ) pOut[1] = 2; pIn = pOut; pIn[0] = nAlloc;