Index: VERSION ================================================================== --- VERSION +++ VERSION @@ -1,1 +1,1 @@ -3.26.0 +3.27.0 Index: configure ================================================================== --- configure +++ configure @@ -1,8 +1,8 @@ #! /bin/sh # Guess values for system-dependent variables and create Makefiles. -# Generated by GNU Autoconf 2.69 for sqlite 3.26.0. +# Generated by GNU Autoconf 2.69 for sqlite 3.27.0. # # # Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc. # # @@ -724,12 +724,12 @@ MAKEFLAGS= # Identity of this package. PACKAGE_NAME='sqlite' PACKAGE_TARNAME='sqlite' -PACKAGE_VERSION='3.26.0' -PACKAGE_STRING='sqlite 3.26.0' +PACKAGE_VERSION='3.27.0' +PACKAGE_STRING='sqlite 3.27.0' PACKAGE_BUGREPORT='' PACKAGE_URL='' # Factoring default headers for most tests. ac_includes_default="\ @@ -1464,11 +1464,11 @@ # if test "$ac_init_help" = "long"; then # Omit some internal or obsolete options to make the list less imposing. # This message is too long to be a string in the A/UX 3.1 sh. cat <<_ACEOF -\`configure' configures sqlite 3.26.0 to adapt to many kinds of systems. +\`configure' configures sqlite 3.27.0 to adapt to many kinds of systems. Usage: $0 [OPTION]... [VAR=VALUE]... To assign environment variables (e.g., CC, CFLAGS...), specify them as VAR=VALUE. See below for descriptions of some of the useful variables. @@ -1529,11 +1529,11 @@ _ACEOF fi if test -n "$ac_init_help"; then case $ac_init_help in - short | recursive ) echo "Configuration of sqlite 3.26.0:";; + short | recursive ) echo "Configuration of sqlite 3.27.0:";; esac cat <<\_ACEOF Optional Features: --disable-option-checking ignore unrecognized --enable/--with options @@ -1655,11 +1655,11 @@ fi test -n "$ac_init_help" && exit $ac_status if $ac_init_version; then cat <<\_ACEOF -sqlite configure 3.26.0 +sqlite configure 3.27.0 generated by GNU Autoconf 2.69 Copyright (C) 2012 Free Software Foundation, Inc. This configure script is free software; the Free Software Foundation gives unlimited permission to copy, distribute and modify it. @@ -2074,11 +2074,11 @@ } # ac_fn_c_check_header_mongrel cat >config.log <<_ACEOF This file contains any messages produced by compilers while running configure, to aid debugging if configure makes a mistake. -It was created by sqlite $as_me 3.26.0, which was +It was created by sqlite $as_me 3.27.0, which was generated by GNU Autoconf 2.69. Invocation command line was $ $0 $@ _ACEOF @@ -12230,11 +12230,11 @@ cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # Save the log message, to keep $0 and so on meaningful, and to # report actual input values of CONFIG_FILES etc. instead of their # values after options handling. ac_log=" -This file was extended by sqlite $as_me 3.26.0, which was +This file was extended by sqlite $as_me 3.27.0, which was generated by GNU Autoconf 2.69. Invocation command line was CONFIG_FILES = $CONFIG_FILES CONFIG_HEADERS = $CONFIG_HEADERS CONFIG_LINKS = $CONFIG_LINKS @@ -12296,11 +12296,11 @@ _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`" ac_cs_version="\\ -sqlite config.status 3.26.0 +sqlite config.status 3.27.0 configured by $0, generated by GNU Autoconf 2.69, with options \\"\$ac_cs_config\\" Copyright (C) 2012 Free Software Foundation, Inc. This config.status script is free software; the Free Software Foundation Index: src/alter.c ================================================================== --- src/alter.c +++ src/alter.c @@ -777,19 +777,36 @@ pCtx->nList++; break; } } } + +/* +** Iterate through the Select objects that are part of WITH clauses attached +** to select statement pSelect. +*/ +static void renameWalkWith(Walker *pWalker, Select *pSelect){ + if( pSelect->pWith ){ + int i; + for(i=0; ipWith->nCte; i++){ + Select *p = pSelect->pWith->a[i].pSelect; + NameContext sNC; + memset(&sNC, 0, sizeof(sNC)); + sNC.pParse = pWalker->pParse; + sqlite3SelectPrep(sNC.pParse, p, &sNC); + sqlite3WalkSelect(pWalker, p); + } + } +} /* ** This is a Walker select callback. It does nothing. It is only required ** because without a dummy callback, sqlite3WalkExpr() and similar do not ** descend into sub-select statements. */ static int renameColumnSelectCb(Walker *pWalker, Select *p){ - UNUSED_PARAMETER(pWalker); - UNUSED_PARAMETER(p); + renameWalkWith(pWalker, p); return WRC_Continue; } /* ** This is a Walker expression callback. @@ -1362,10 +1379,11 @@ struct SrcList_item *pItem = &pSrc->a[i]; if( pItem->pTab==p->pTab ){ renameTokenFind(pWalker->pParse, p, pItem->zName); } } + renameWalkWith(pWalker, pSelect); return WRC_Continue; } Index: src/callback.c ================================================================== --- src/callback.c +++ src/callback.c @@ -281,11 +281,11 @@ /* ** Search a FuncDefHash for a function with the given name. Return ** a pointer to the matching FuncDef if found, or 0 if there is no match. */ -static FuncDef *functionSearch( +FuncDef *sqlite3FunctionSearch( int h, /* Hash of the name */ const char *zFunc /* Name of function */ ){ FuncDef *p; for(p=sqlite3BuiltinFunctions.a[h]; p; p=p->u.pHash){ @@ -293,25 +293,10 @@ return p; } } return 0; } -#ifdef SQLITE_ENABLE_NORMALIZE -FuncDef *sqlite3FunctionSearchN( - int h, /* Hash of the name */ - const char *zFunc, /* Name of function */ - int nFunc /* Length of the name */ -){ - FuncDef *p; - for(p=sqlite3BuiltinFunctions.a[h]; p; p=p->u.pHash){ - if( sqlite3StrNICmp(p->zName, zFunc, nFunc)==0 ){ - return p; - } - } - return 0; -} -#endif /* SQLITE_ENABLE_NORMALIZE */ /* ** Insert a new FuncDef into a FuncDefHash hash table. */ void sqlite3InsertBuiltinFuncs( @@ -323,11 +308,11 @@ FuncDef *pOther; const char *zName = aDef[i].zName; int nName = sqlite3Strlen30(zName); int h = SQLITE_FUNC_HASH(zName[0], nName); assert( zName[0]>='a' && zName[0]<='z' ); - pOther = functionSearch(h, zName); + pOther = sqlite3FunctionSearch(h, zName); if( pOther ){ assert( pOther!=&aDef[i] && pOther->pNext!=&aDef[i] ); aDef[i].pNext = pOther->pNext; pOther->pNext = &aDef[i]; }else{ @@ -401,11 +386,11 @@ ** So we must not search for built-ins when creating a new function. */ if( !createFlag && (pBest==0 || (db->mDbFlags & DBFLAG_PreferBuiltin)!=0) ){ bestScore = 0; h = SQLITE_FUNC_HASH(sqlite3UpperToLower[(u8)zName[0]], nName); - p = functionSearch(h, zName); + p = sqlite3FunctionSearch(h, zName); while( p ){ int score = matchQuality(p, nArg, enc); if( score>bestScore ){ pBest = p; bestScore = score; Index: src/expr.c ================================================================== --- src/expr.c +++ src/expr.c @@ -2147,18 +2147,10 @@ if( sqlite3StrICmp(z, "_ROWID_")==0 ) return 1; if( sqlite3StrICmp(z, "ROWID")==0 ) return 1; if( sqlite3StrICmp(z, "OID")==0 ) return 1; return 0; } -#ifdef SQLITE_ENABLE_NORMALIZE -int sqlite3IsRowidN(const char *z, int n){ - if( sqlite3StrNICmp(z, "_ROWID_", n)==0 ) return 1; - if( sqlite3StrNICmp(z, "ROWID", n)==0 ) return 1; - if( sqlite3StrNICmp(z, "OID", n)==0 ) return 1; - return 0; -} -#endif /* ** pX is the RHS of an IN operator. If pX is a SELECT statement ** that can be simplified to a direct table access, then return ** a pointer to the SELECT statement. If pX is not a SELECT statement, Index: src/hash.c ================================================================== --- src/hash.c +++ src/hash.c @@ -62,24 +62,10 @@ h += sqlite3UpperToLower[c]; h *= 0x9e3779b1; } return h; } -#ifdef SQLITE_ENABLE_NORMALIZE -static unsigned int strHashN(const char *z, int n){ - unsigned int h = 0; - int i; - for(i=0; inext; } return &nullElement; } -#ifdef SQLITE_ENABLE_NORMALIZE -static HashElem *findElementWithHashN( - const Hash *pH, /* The pH to be searched */ - const char *pKey, /* The key we are searching for */ - int nKey, /* Number of key bytes to use */ - unsigned int *pHash /* Write the hash value here */ -){ - HashElem *elem; /* Used to loop thru the element list */ - int count; /* Number of elements left to test */ - unsigned int h; /* The computed hash */ - static HashElem nullElement = { 0, 0, 0, 0 }; - - if( pH->ht ){ /*OPTIMIZATION-IF-TRUE*/ - struct _ht *pEntry; - h = strHashN(pKey, nKey) % pH->htsize; - pEntry = &pH->ht[h]; - elem = pEntry->chain; - count = pEntry->count; - }else{ - h = 0; - elem = pH->first; - count = pH->count; - } - if( pHash ) *pHash = h; - while( count-- ){ - assert( elem!=0 ); - if( sqlite3StrNICmp(elem->pKey,pKey,nKey)==0 ){ - return elem; - } - elem = elem->next; - } - return &nullElement; -} -#endif /* SQLITE_ENABLE_NORMALIZE */ /* Remove a single entry from the hash table given a pointer to that ** element and a hash on the element's key. */ static void removeElementGivenHash( @@ -265,18 +217,10 @@ void *sqlite3HashFind(const Hash *pH, const char *pKey){ assert( pH!=0 ); assert( pKey!=0 ); return findElementWithHash(pH, pKey, 0)->data; } -#ifdef SQLITE_ENABLE_NORMALIZE -void *sqlite3HashFindN(const Hash *pH, const char *pKey, int nKey){ - assert( pH!=0 ); - assert( pKey!=0 ); - assert( nKey>=0 ); - return findElementWithHashN(pH, pKey, nKey, 0)->data; -} -#endif /* SQLITE_ENABLE_NORMALIZE */ /* Insert an element into the hash table pH. The key is pKey ** and the data is "data". ** ** If no element exists with a matching key, then a new Index: src/hash.h ================================================================== --- src/hash.h +++ src/hash.h @@ -66,13 +66,10 @@ ** Access routines. To delete, insert a NULL pointer. */ void sqlite3HashInit(Hash*); void *sqlite3HashInsert(Hash*, const char *pKey, void *pData); void *sqlite3HashFind(const Hash*, const char *pKey); -#ifdef SQLITE_ENABLE_NORMALIZE -void *sqlite3HashFindN(const Hash *pH, const char *pKey, int nKey); -#endif void sqlite3HashClear(Hash*); /* ** Macros for looping over all elements of a hash table. The idiom is ** like this: Index: src/prepare.c ================================================================== --- src/prepare.c +++ src/prepare.c @@ -708,81 +708,10 @@ sqlite3_mutex_leave(db->mutex); return rc; } #ifdef SQLITE_ENABLE_NORMALIZE -/* -** Checks if the specified token is a table, column, or function name, -** based on the databases associated with the statement being prepared. -** If the function fails, zero is returned and pRc is filled with the -** error code. -*/ -static int shouldTreatAsIdentifier( - sqlite3 *db, /* Database handle. */ - const char *zToken, /* Pointer to start of token to be checked */ - int nToken, /* Length of token to be checked */ - int *pRc /* Pointer to error code upon failure */ -){ - int bFound = 0; /* Non-zero if token is an identifier name. */ - int i, j; /* Database and column loop indexes. */ - Schema *pSchema; /* Schema for current database. */ - Hash *pHash; /* Hash table of tables for current database. */ - HashElem *e; /* Hash element for hash table iteration. */ - Table *pTab; /* Database table for columns being checked. */ - - if( sqlite3IsRowidN(zToken, nToken) ){ - return 1; - } - if( nToken>0 ){ - int hash = SQLITE_FUNC_HASH(sqlite3UpperToLower[(u8)zToken[0]], nToken); - if( sqlite3FunctionSearchN(hash, zToken, nToken) ) return 1; - } - assert( db!=0 ); - sqlite3_mutex_enter(db->mutex); - sqlite3BtreeEnterAll(db); - for(i=0; inDb; i++){ - pHash = &db->aFunc; - if( sqlite3HashFindN(pHash, zToken, nToken) ){ - bFound = 1; - break; - } - pSchema = db->aDb[i].pSchema; - if( pSchema==0 ) continue; - pHash = &pSchema->tblHash; - if( sqlite3HashFindN(pHash, zToken, nToken) ){ - bFound = 1; - break; - } - for(e=sqliteHashFirst(pHash); e; e=sqliteHashNext(e)){ - pTab = sqliteHashData(e); - if( pTab==0 ) continue; - pHash = pTab->pColHash; - if( pHash==0 ){ - pTab->pColHash = pHash = sqlite3_malloc(sizeof(Hash)); - if( pHash ){ - sqlite3HashInit(pHash); - for(j=0; jnCol; j++){ - Column *pCol = &pTab->aCol[j]; - sqlite3HashInsert(pHash, pCol->zName, pCol); - } - }else{ - *pRc = SQLITE_NOMEM_BKPT; - bFound = 0; - goto done; - } - } - if( pHash && sqlite3HashFindN(pHash, zToken, nToken) ){ - bFound = 1; - goto done; - } - } - } -done: - sqlite3BtreeLeaveAll(db); - sqlite3_mutex_leave(db->mutex); - return bFound; -} /* ** Attempt to estimate the final output buffer size needed for the fully ** normalized version of the specified SQL string. This should take into ** account any potential expansion that could occur (e.g. via IN clauses @@ -862,19 +791,19 @@ int j; /* Next character to fill in on z[] */ int tokenType = 0; /* Type of the next token */ int prevTokenType = 0; /* Type of the previous token, except spaces */ int n; /* Size of the next token */ int nParen = 0; /* Nesting level of parenthesis */ - Hash inHash; /* Table of parenthesis levels to output index. */ + int iStartIN = 0; /* Start of RHS of IN operator in z[] */ + int nParenAtIN = 0; /* Value of nParent at start of RHS of IN operator */ db = sqlite3VdbeDb(pVdbe); assert( db!=0 ); if( zSql==0 ) return 0; nZ = estimateNormalizedSize(zSql, nSql); z = sqlite3DbMallocRawNN(db, nZ); if( z==0 ) goto normalizeError; - sqlite3HashInit(&inHash); for(i=j=0; i0 ){ - sqlite3HashInsert(&inHash, zSql+nParen, 0); - assert( jj+60 && nParen==nParenAtIN ){ + assert( iStartIN+6=0 ); assert( nZ-1-j=0 ); /* Fall through */ @@ -954,23 +880,13 @@ } if( j>0 && sqlite3IsIdChar(z[j-1]) && sqlite3IsIdChar(zSql[i]) ){ z[j++] = ' '; } if( tokenType==TK_ID ){ - int i2 = i, n2 = n, rc = SQLITE_OK; - if( nParen>0 ){ - assert( nParen0 && z[j-1]==' ' ){ j--; } if( j>0 && z[j-1]!=';' ){ z[j++] = ';'; } z[j] = 0; assert( j