| Index: third_party/sqlite/src/src/func.c | 
| diff --git a/third_party/sqlite/src/src/func.c b/third_party/sqlite/src/src/func.c | 
| index 6a4f7c09c3d5b315464c61152c861d1f38fba984..cf556e2439d944f85d955f862e6b8c78a7384a2d 100644 | 
| --- a/third_party/sqlite/src/src/func.c | 
| +++ b/third_party/sqlite/src/src/func.c | 
| @@ -9,12 +9,9 @@ | 
| **    May you share freely, never taking more than you give. | 
| ** | 
| ************************************************************************* | 
| -** This file contains the C functions that implement various SQL | 
| -** functions of SQLite. | 
| -** | 
| -** There is only one exported symbol in this file - the function | 
| -** sqliteRegisterBuildinFunctions() found at the bottom of the file. | 
| -** All other code has file scope. | 
| +** This file contains the C-language implementations for many of the SQL | 
| +** functions of SQLite.  (Some function, and in particular the date and | 
| +** time functions, are implemented separately.) | 
| */ | 
| #include "sqliteInt.h" | 
| #include <stdlib.h> | 
| @@ -25,7 +22,18 @@ | 
| ** Return the collating function associated with a function. | 
| */ | 
| static CollSeq *sqlite3GetFuncCollSeq(sqlite3_context *context){ | 
| -  return context->pColl; | 
| +  VdbeOp *pOp = &context->pVdbe->aOp[context->iOp-1]; | 
| +  assert( pOp->opcode==OP_CollSeq ); | 
| +  assert( pOp->p4type==P4_COLLSEQ ); | 
| +  return pOp->p4.pColl; | 
| +} | 
| + | 
| +/* | 
| +** Indicate that the accumulator load should be skipped on this | 
| +** iteration of the aggregate loop. | 
| +*/ | 
| +static void sqlite3SkipAccumulatorLoad(sqlite3_context *context){ | 
| +  context->skipFlag = 1; | 
| } | 
|  | 
| /* | 
| @@ -129,9 +137,9 @@ static void absFunc(sqlite3_context *context, int argc, sqlite3_value **argv){ | 
| case SQLITE_INTEGER: { | 
| i64 iVal = sqlite3_value_int64(argv[0]); | 
| if( iVal<0 ){ | 
| -        if( (iVal<<1)==0 ){ | 
| -          /* IMP: R-35460-15084 If X is the integer -9223372036854775807 then | 
| -          ** abs(X) throws an integer overflow error since there is no | 
| +        if( iVal==SMALLEST_INT64 ){ | 
| +          /* IMP: R-31676-45509 If X is the integer -9223372036854775808 | 
| +          ** then abs(X) throws an integer overflow error since there is no | 
| ** equivalent positive 64-bit two complement value. */ | 
| sqlite3_result_error(context, "integer overflow", -1); | 
| return; | 
| @@ -161,6 +169,82 @@ static void absFunc(sqlite3_context *context, int argc, sqlite3_value **argv){ | 
| } | 
|  | 
| /* | 
| +** Implementation of the instr() function. | 
| +** | 
| +** instr(haystack,needle) finds the first occurrence of needle | 
| +** in haystack and returns the number of previous characters plus 1, | 
| +** or 0 if needle does not occur within haystack. | 
| +** | 
| +** If both haystack and needle are BLOBs, then the result is one more than | 
| +** the number of bytes in haystack prior to the first occurrence of needle, | 
| +** or 0 if needle never occurs in haystack. | 
| +*/ | 
| +static void instrFunc( | 
| +  sqlite3_context *context, | 
| +  int argc, | 
| +  sqlite3_value **argv | 
| +){ | 
| +  const unsigned char *zHaystack; | 
| +  const unsigned char *zNeedle; | 
| +  int nHaystack; | 
| +  int nNeedle; | 
| +  int typeHaystack, typeNeedle; | 
| +  int N = 1; | 
| +  int isText; | 
| + | 
| +  UNUSED_PARAMETER(argc); | 
| +  typeHaystack = sqlite3_value_type(argv[0]); | 
| +  typeNeedle = sqlite3_value_type(argv[1]); | 
| +  if( typeHaystack==SQLITE_NULL || typeNeedle==SQLITE_NULL ) return; | 
| +  nHaystack = sqlite3_value_bytes(argv[0]); | 
| +  nNeedle = sqlite3_value_bytes(argv[1]); | 
| +  if( typeHaystack==SQLITE_BLOB && typeNeedle==SQLITE_BLOB ){ | 
| +    zHaystack = sqlite3_value_blob(argv[0]); | 
| +    zNeedle = sqlite3_value_blob(argv[1]); | 
| +    isText = 0; | 
| +  }else{ | 
| +    zHaystack = sqlite3_value_text(argv[0]); | 
| +    zNeedle = sqlite3_value_text(argv[1]); | 
| +    isText = 1; | 
| +  } | 
| +  while( nNeedle<=nHaystack && memcmp(zHaystack, zNeedle, nNeedle)!=0 ){ | 
| +    N++; | 
| +    do{ | 
| +      nHaystack--; | 
| +      zHaystack++; | 
| +    }while( isText && (zHaystack[0]&0xc0)==0x80 ); | 
| +  } | 
| +  if( nNeedle>nHaystack ) N = 0; | 
| +  sqlite3_result_int(context, N); | 
| +} | 
| + | 
| +/* | 
| +** Implementation of the printf() function. | 
| +*/ | 
| +static void printfFunc( | 
| +  sqlite3_context *context, | 
| +  int argc, | 
| +  sqlite3_value **argv | 
| +){ | 
| +  PrintfArguments x; | 
| +  StrAccum str; | 
| +  const char *zFormat; | 
| +  int n; | 
| + | 
| +  if( argc>=1 && (zFormat = (const char*)sqlite3_value_text(argv[0]))!=0 ){ | 
| +    x.nArg = argc-1; | 
| +    x.nUsed = 0; | 
| +    x.apArg = argv+1; | 
| +    sqlite3StrAccumInit(&str, 0, 0, SQLITE_MAX_LENGTH); | 
| +    str.db = sqlite3_context_db_handle(context); | 
| +    sqlite3XPrintf(&str, SQLITE_PRINTF_SQLFUNC, zFormat, &x); | 
| +    n = str.nChar; | 
| +    sqlite3_result_text(context, sqlite3StrAccumFinish(&str), n, | 
| +                        SQLITE_DYNAMIC); | 
| +  } | 
| +} | 
| + | 
| +/* | 
| ** Implementation of the substr() function. | 
| ** | 
| ** substr(x,p1,p2)  returns p2 characters of x[] beginning with p1. | 
| @@ -170,7 +254,7 @@ static void absFunc(sqlite3_context *context, int argc, sqlite3_value **argv){ | 
| ** | 
| ** If p1 is negative, then we begin abs(p1) from the end of x[]. | 
| ** | 
| -** If p2 is negative, return the p2 characters preceeding p1. | 
| +** If p2 is negative, return the p2 characters preceding p1. | 
| */ | 
| static void substrFunc( | 
| sqlite3_context *context, | 
| @@ -244,13 +328,14 @@ static void substrFunc( | 
| for(z2=z; *z2 && p2; p2--){ | 
| SQLITE_SKIP_UTF8(z2); | 
| } | 
| -    sqlite3_result_text(context, (char*)z, (int)(z2-z), SQLITE_TRANSIENT); | 
| +    sqlite3_result_text64(context, (char*)z, z2-z, SQLITE_TRANSIENT, | 
| +                          SQLITE_UTF8); | 
| }else{ | 
| if( p1+p2>len ){ | 
| p2 = len-p1; | 
| if( p2<0 ) p2 = 0; | 
| } | 
| -    sqlite3_result_blob(context, (char*)&z[p1], (int)p2, SQLITE_TRANSIENT); | 
| +    sqlite3_result_blob64(context, (char*)&z[p1], (u64)p2, SQLITE_TRANSIENT); | 
| } | 
| } | 
|  | 
| @@ -309,7 +394,7 @@ static void *contextMalloc(sqlite3_context *context, i64 nByte){ | 
| sqlite3_result_error_toobig(context); | 
| z = 0; | 
| }else{ | 
| -    z = sqlite3Malloc((int)nByte); | 
| +    z = sqlite3Malloc(nByte); | 
| if( !z ){ | 
| sqlite3_result_error_nomem(context); | 
| } | 
| @@ -332,16 +417,15 @@ static void upperFunc(sqlite3_context *context, int argc, sqlite3_value **argv){ | 
| if( z2 ){ | 
| z1 = contextMalloc(context, ((i64)n)+1); | 
| if( z1 ){ | 
| -      memcpy(z1, z2, n+1); | 
| -      for(i=0; z1[i]; i++){ | 
| -        z1[i] = (char)sqlite3Toupper(z1[i]); | 
| +      for(i=0; i<n; i++){ | 
| +        z1[i] = (char)sqlite3Toupper(z2[i]); | 
| } | 
| -      sqlite3_result_text(context, z1, -1, sqlite3_free); | 
| +      sqlite3_result_text(context, z1, n, sqlite3_free); | 
| } | 
| } | 
| } | 
| static void lowerFunc(sqlite3_context *context, int argc, sqlite3_value **argv){ | 
| -  u8 *z1; | 
| +  char *z1; | 
| const char *z2; | 
| int i, n; | 
| UNUSED_PARAMETER(argc); | 
| @@ -352,43 +436,23 @@ static void lowerFunc(sqlite3_context *context, int argc, sqlite3_value **argv){ | 
| if( z2 ){ | 
| z1 = contextMalloc(context, ((i64)n)+1); | 
| if( z1 ){ | 
| -      memcpy(z1, z2, n+1); | 
| -      for(i=0; z1[i]; i++){ | 
| -        z1[i] = sqlite3Tolower(z1[i]); | 
| +      for(i=0; i<n; i++){ | 
| +        z1[i] = sqlite3Tolower(z2[i]); | 
| } | 
| -      sqlite3_result_text(context, (char *)z1, -1, sqlite3_free); | 
| +      sqlite3_result_text(context, z1, n, sqlite3_free); | 
| } | 
| } | 
| } | 
|  | 
| - | 
| -#if 0  /* This function is never used. */ | 
| -/* | 
| -** The COALESCE() and IFNULL() functions used to be implemented as shown | 
| -** here.  But now they are implemented as VDBE code so that unused arguments | 
| -** do not have to be computed.  This legacy implementation is retained as | 
| -** comment. | 
| -*/ | 
| /* | 
| -** Implementation of the IFNULL(), NVL(), and COALESCE() functions. | 
| -** All three do the same thing.  They return the first non-NULL | 
| -** argument. | 
| +** Some functions like COALESCE() and IFNULL() and UNLIKELY() are implemented | 
| +** as VDBE code so that unused argument values do not have to be computed. | 
| +** However, we still need some kind of function implementation for this | 
| +** routines in the function table.  The noopFunc macro provides this. | 
| +** noopFunc will never be called so it doesn't matter what the implementation | 
| +** is.  We might as well use the "version()" function as a substitute. | 
| */ | 
| -static void ifnullFunc( | 
| -  sqlite3_context *context, | 
| -  int argc, | 
| -  sqlite3_value **argv | 
| -){ | 
| -  int i; | 
| -  for(i=0; i<argc; i++){ | 
| -    if( SQLITE_NULL!=sqlite3_value_type(argv[i]) ){ | 
| -      sqlite3_result_value(context, argv[i]); | 
| -      break; | 
| -    } | 
| -  } | 
| -} | 
| -#endif /* NOT USED */ | 
| -#define ifnullFunc versionFunc   /* Substitute function - never called */ | 
| +#define noopFunc versionFunc   /* Substitute function - never called */ | 
|  | 
| /* | 
| ** Implementation of random().  Return a random integer. | 
| @@ -410,7 +474,7 @@ static void randomFunc( | 
| ** 2s complement of that positive value.  The end result can | 
| ** therefore be no less than -9223372036854775807. | 
| */ | 
| -    r = -(r ^ (((sqlite3_int64)1)<<63)); | 
| +    r = -(r & LARGEST_INT64); | 
| } | 
| sqlite3_result_int64(context, r); | 
| } | 
| @@ -506,10 +570,12 @@ struct compareInfo { | 
| ** whereas only characters less than 0x80 do in ASCII. | 
| */ | 
| #if defined(SQLITE_EBCDIC) | 
| -# define sqlite3Utf8Read(A,C)    (*(A++)) | 
| -# define GlogUpperToLower(A)     A = sqlite3UpperToLower[A] | 
| +# define sqlite3Utf8Read(A)        (*((*A)++)) | 
| +# define GlobUpperToLower(A)       A = sqlite3UpperToLower[A] | 
| +# define GlobUpperToLowerAscii(A)  A = sqlite3UpperToLower[A] | 
| #else | 
| -# define GlogUpperToLower(A)     if( A<0x80 ){ A = sqlite3UpperToLower[A]; } | 
| +# define GlobUpperToLower(A)       if( A<=0x7f ){ A = sqlite3UpperToLower[A]; } | 
| +# define GlobUpperToLowerAscii(A)  A = sqlite3UpperToLower[A] | 
| #endif | 
|  | 
| static const struct compareInfo globInfo = { '*', '?', '[', 0 }; | 
| @@ -522,7 +588,7 @@ static const struct compareInfo likeInfoAlt = { '%', '_',   0, 0 }; | 
|  | 
| /* | 
| ** Compare two UTF-8 strings for equality where the first string can | 
| -** potentially be a "glob" expression.  Return true (1) if they | 
| +** potentially be a "glob" or "like" expression.  Return true (1) if they | 
| ** are the same and false (0) if they are different. | 
| ** | 
| ** Globbing rules: | 
| @@ -542,121 +608,155 @@ static const struct compareInfo likeInfoAlt = { '%', '_',   0, 0 }; | 
| ** "[a-z]" matches any single lower-case letter.  To match a '-', make | 
| ** it the last character in the list. | 
| ** | 
| -** This routine is usually quick, but can be N**2 in the worst case. | 
| +** Like matching rules: | 
| +** | 
| +**      '%'       Matches any sequence of zero or more characters | 
| +** | 
| +***     '_'       Matches any one character | 
| ** | 
| -** Hints: to match '*' or '?', put them in "[]".  Like this: | 
| +**      Ec        Where E is the "esc" character and c is any other | 
| +**                character, including '%', '_', and esc, match exactly c. | 
| ** | 
| -**         abc[*]xyz        Matches "abc*xyz" only | 
| +** The comments through this routine usually assume glob matching. | 
| +** | 
| +** This routine is usually quick, but can be N**2 in the worst case. | 
| */ | 
| static int patternCompare( | 
| const u8 *zPattern,              /* The glob pattern */ | 
| const u8 *zString,               /* The string to compare against the glob */ | 
| const struct compareInfo *pInfo, /* Information about how to do the compare */ | 
| -  const int esc                    /* The escape character */ | 
| +  u32 esc                          /* The escape character */ | 
| ){ | 
| -  int c, c2; | 
| -  int invert; | 
| -  int seen; | 
| -  u8 matchOne = pInfo->matchOne; | 
| -  u8 matchAll = pInfo->matchAll; | 
| -  u8 matchSet = pInfo->matchSet; | 
| -  u8 noCase = pInfo->noCase; | 
| -  int prevEscape = 0;     /* True if the previous character was 'escape' */ | 
| - | 
| -  while( (c = sqlite3Utf8Read(zPattern,&zPattern))!=0 ){ | 
| -    if( !prevEscape && c==matchAll ){ | 
| -      while( (c=sqlite3Utf8Read(zPattern,&zPattern)) == matchAll | 
| +  u32 c, c2;                       /* Next pattern and input string chars */ | 
| +  u32 matchOne = pInfo->matchOne;  /* "?" or "_" */ | 
| +  u32 matchAll = pInfo->matchAll;  /* "*" or "%" */ | 
| +  u32 matchOther;                  /* "[" or the escape character */ | 
| +  u8 noCase = pInfo->noCase;       /* True if uppercase==lowercase */ | 
| +  const u8 *zEscaped = 0;          /* One past the last escaped input char */ | 
| + | 
| +  /* The GLOB operator does not have an ESCAPE clause.  And LIKE does not | 
| +  ** have the matchSet operator.  So we either have to look for one or | 
| +  ** the other, never both.  Hence the single variable matchOther is used | 
| +  ** to store the one we have to look for. | 
| +  */ | 
| +  matchOther = esc ? esc : pInfo->matchSet; | 
| + | 
| +  while( (c = sqlite3Utf8Read(&zPattern))!=0 ){ | 
| +    if( c==matchAll ){  /* Match "*" */ | 
| +      /* Skip over multiple "*" characters in the pattern.  If there | 
| +      ** are also "?" characters, skip those as well, but consume a | 
| +      ** single character of the input string for each "?" skipped */ | 
| +      while( (c=sqlite3Utf8Read(&zPattern)) == matchAll | 
| || c == matchOne ){ | 
| -        if( c==matchOne && sqlite3Utf8Read(zString, &zString)==0 ){ | 
| +        if( c==matchOne && sqlite3Utf8Read(&zString)==0 ){ | 
| return 0; | 
| } | 
| } | 
| if( c==0 ){ | 
| -        return 1; | 
| -      }else if( c==esc ){ | 
| -        c = sqlite3Utf8Read(zPattern, &zPattern); | 
| -        if( c==0 ){ | 
| -          return 0; | 
| -        } | 
| -      }else if( c==matchSet ){ | 
| -        assert( esc==0 );         /* This is GLOB, not LIKE */ | 
| -        assert( matchSet<0x80 );  /* '[' is a single-byte character */ | 
| -        while( *zString && patternCompare(&zPattern[-1],zString,pInfo,esc)==0 ){ | 
| -          SQLITE_SKIP_UTF8(zString); | 
| +        return 1;   /* "*" at the end of the pattern matches */ | 
| +      }else if( c==matchOther ){ | 
| +        if( esc ){ | 
| +          c = sqlite3Utf8Read(&zPattern); | 
| +          if( c==0 ) return 0; | 
| +        }else{ | 
| +          /* "[...]" immediately follows the "*".  We have to do a slow | 
| +          ** recursive search in this case, but it is an unusual case. */ | 
| +          assert( matchOther<0x80 );  /* '[' is a single-byte character */ | 
| +          while( *zString | 
| +                 && patternCompare(&zPattern[-1],zString,pInfo,esc)==0 ){ | 
| +            SQLITE_SKIP_UTF8(zString); | 
| +          } | 
| +          return *zString!=0; | 
| } | 
| -        return *zString!=0; | 
| } | 
| -      while( (c2 = sqlite3Utf8Read(zString,&zString))!=0 ){ | 
| + | 
| +      /* At this point variable c contains the first character of the | 
| +      ** pattern string past the "*".  Search in the input string for the | 
| +      ** first matching character and recursively contine the match from | 
| +      ** that point. | 
| +      ** | 
| +      ** For a case-insensitive search, set variable cx to be the same as | 
| +      ** c but in the other case and search the input string for either | 
| +      ** c or cx. | 
| +      */ | 
| +      if( c<=0x80 ){ | 
| +        u32 cx; | 
| if( noCase ){ | 
| -          GlogUpperToLower(c2); | 
| -          GlogUpperToLower(c); | 
| -          while( c2 != 0 && c2 != c ){ | 
| -            c2 = sqlite3Utf8Read(zString, &zString); | 
| -            GlogUpperToLower(c2); | 
| -          } | 
| +          cx = sqlite3Toupper(c); | 
| +          c = sqlite3Tolower(c); | 
| }else{ | 
| -          while( c2 != 0 && c2 != c ){ | 
| -            c2 = sqlite3Utf8Read(zString, &zString); | 
| -          } | 
| +          cx = c; | 
| +        } | 
| +        while( (c2 = *(zString++))!=0 ){ | 
| +          if( c2!=c && c2!=cx ) continue; | 
| +          if( patternCompare(zPattern,zString,pInfo,esc) ) return 1; | 
| +        } | 
| +      }else{ | 
| +        while( (c2 = sqlite3Utf8Read(&zString))!=0 ){ | 
| +          if( c2!=c ) continue; | 
| +          if( patternCompare(zPattern,zString,pInfo,esc) ) return 1; | 
| } | 
| -        if( c2==0 ) return 0; | 
| -        if( patternCompare(zPattern,zString,pInfo,esc) ) return 1; | 
| } | 
| return 0; | 
| -    }else if( !prevEscape && c==matchOne ){ | 
| -      if( sqlite3Utf8Read(zString, &zString)==0 ){ | 
| -        return 0; | 
| -      } | 
| -    }else if( c==matchSet ){ | 
| -      int prior_c = 0; | 
| -      assert( esc==0 );    /* This only occurs for GLOB, not LIKE */ | 
| -      seen = 0; | 
| -      invert = 0; | 
| -      c = sqlite3Utf8Read(zString, &zString); | 
| -      if( c==0 ) return 0; | 
| -      c2 = sqlite3Utf8Read(zPattern, &zPattern); | 
| -      if( c2=='^' ){ | 
| -        invert = 1; | 
| -        c2 = sqlite3Utf8Read(zPattern, &zPattern); | 
| -      } | 
| -      if( c2==']' ){ | 
| -        if( c==']' ) seen = 1; | 
| -        c2 = sqlite3Utf8Read(zPattern, &zPattern); | 
| -      } | 
| -      while( c2 && c2!=']' ){ | 
| -        if( c2=='-' && zPattern[0]!=']' && zPattern[0]!=0 && prior_c>0 ){ | 
| -          c2 = sqlite3Utf8Read(zPattern, &zPattern); | 
| -          if( c>=prior_c && c<=c2 ) seen = 1; | 
| -          prior_c = 0; | 
| -        }else{ | 
| -          if( c==c2 ){ | 
| -            seen = 1; | 
| +    } | 
| +    if( c==matchOther ){ | 
| +      if( esc ){ | 
| +        c = sqlite3Utf8Read(&zPattern); | 
| +        if( c==0 ) return 0; | 
| +        zEscaped = zPattern; | 
| +      }else{ | 
| +        u32 prior_c = 0; | 
| +        int seen = 0; | 
| +        int invert = 0; | 
| +        c = sqlite3Utf8Read(&zString); | 
| +        if( c==0 ) return 0; | 
| +        c2 = sqlite3Utf8Read(&zPattern); | 
| +        if( c2=='^' ){ | 
| +          invert = 1; | 
| +          c2 = sqlite3Utf8Read(&zPattern); | 
| +        } | 
| +        if( c2==']' ){ | 
| +          if( c==']' ) seen = 1; | 
| +          c2 = sqlite3Utf8Read(&zPattern); | 
| +        } | 
| +        while( c2 && c2!=']' ){ | 
| +          if( c2=='-' && zPattern[0]!=']' && zPattern[0]!=0 && prior_c>0 ){ | 
| +            c2 = sqlite3Utf8Read(&zPattern); | 
| +            if( c>=prior_c && c<=c2 ) seen = 1; | 
| +            prior_c = 0; | 
| +          }else{ | 
| +            if( c==c2 ){ | 
| +              seen = 1; | 
| +            } | 
| +            prior_c = c2; | 
| } | 
| -          prior_c = c2; | 
| +          c2 = sqlite3Utf8Read(&zPattern); | 
| } | 
| -        c2 = sqlite3Utf8Read(zPattern, &zPattern); | 
| -      } | 
| -      if( c2==0 || (seen ^ invert)==0 ){ | 
| -        return 0; | 
| -      } | 
| -    }else if( esc==c && !prevEscape ){ | 
| -      prevEscape = 1; | 
| -    }else{ | 
| -      c2 = sqlite3Utf8Read(zString, &zString); | 
| -      if( noCase ){ | 
| -        GlogUpperToLower(c); | 
| -        GlogUpperToLower(c2); | 
| -      } | 
| -      if( c!=c2 ){ | 
| -        return 0; | 
| +        if( c2==0 || (seen ^ invert)==0 ){ | 
| +          return 0; | 
| +        } | 
| +        continue; | 
| } | 
| -      prevEscape = 0; | 
| } | 
| +    c2 = sqlite3Utf8Read(&zString); | 
| +    if( c==c2 ) continue; | 
| +    if( noCase && c<0x80 && c2<0x80 && sqlite3Tolower(c)==sqlite3Tolower(c2) ){ | 
| +      continue; | 
| +    } | 
| +    if( c==matchOne && zPattern!=zEscaped && c2!=0 ) continue; | 
| +    return 0; | 
| } | 
| return *zString==0; | 
| } | 
|  | 
| /* | 
| +** The sqlite3_strglob() interface. | 
| +*/ | 
| +int sqlite3_strglob(const char *zGlobPattern, const char *zString){ | 
| +  return patternCompare((u8*)zGlobPattern, (u8*)zString, &globInfo, 0)==0; | 
| +} | 
| + | 
| +/* | 
| ** Count the number of times that the LIKE operator (or GLOB which is | 
| ** just a variation of LIKE) gets called.  This is used for testing | 
| ** only. | 
| @@ -684,7 +784,7 @@ static void likeFunc( | 
| sqlite3_value **argv | 
| ){ | 
| const unsigned char *zA, *zB; | 
| -  int escape = 0; | 
| +  u32 escape = 0; | 
| int nPat; | 
| sqlite3 *db = sqlite3_context_db_handle(context); | 
|  | 
| @@ -714,7 +814,7 @@ static void likeFunc( | 
| "ESCAPE expression must be a single character", -1); | 
| return; | 
| } | 
| -    escape = sqlite3Utf8Read(zEsc, &zEsc); | 
| +    escape = sqlite3Utf8Read(&zEsc); | 
| } | 
| if( zA && zB ){ | 
| struct compareInfo *pInfo = sqlite3_user_data(context); | 
| @@ -775,6 +875,21 @@ static void sourceidFunc( | 
| } | 
|  | 
| /* | 
| +** Implementation of the sqlite_log() function.  This is a wrapper around | 
| +** sqlite3_log().  The return value is NULL.  The function exists purely for | 
| +** its side-effects. | 
| +*/ | 
| +static void errlogFunc( | 
| +  sqlite3_context *context, | 
| +  int argc, | 
| +  sqlite3_value **argv | 
| +){ | 
| +  UNUSED_PARAMETER(argc); | 
| +  UNUSED_PARAMETER(context); | 
| +  sqlite3_log(sqlite3_value_int(argv[0]), "%s", sqlite3_value_text(argv[1])); | 
| +} | 
| + | 
| +/* | 
| ** Implementation of the sqlite_compileoption_used() function. | 
| ** The result is an integer that identifies if the compiler option | 
| ** was used to build SQLite. | 
| @@ -828,10 +943,6 @@ static const char hexdigits[] = { | 
| }; | 
|  | 
| /* | 
| -** EXPERIMENTAL - This is not an official function.  The interface may | 
| -** change.  This function may disappear.  Do not write code that depends | 
| -** on this function. | 
| -** | 
| ** Implementation of the QUOTE() function.  This function takes a single | 
| ** argument.  If the argument is numeric, the return value is the same as | 
| ** the argument.  If the argument is NULL, the return value is the string | 
| @@ -842,8 +953,19 @@ static void quoteFunc(sqlite3_context *context, int argc, sqlite3_value **argv){ | 
| assert( argc==1 ); | 
| UNUSED_PARAMETER(argc); | 
| switch( sqlite3_value_type(argv[0]) ){ | 
| -    case SQLITE_INTEGER: | 
| case SQLITE_FLOAT: { | 
| +      double r1, r2; | 
| +      char zBuf[50]; | 
| +      r1 = sqlite3_value_double(argv[0]); | 
| +      sqlite3_snprintf(sizeof(zBuf), zBuf, "%!.15g", r1); | 
| +      sqlite3AtoF(zBuf, &r2, 20, SQLITE_UTF8); | 
| +      if( r1!=r2 ){ | 
| +        sqlite3_snprintf(sizeof(zBuf), zBuf, "%!.20e", r1); | 
| +      } | 
| +      sqlite3_result_text(context, zBuf, -1, SQLITE_TRANSIENT); | 
| +      break; | 
| +    } | 
| +    case SQLITE_INTEGER: { | 
| sqlite3_result_value(context, argv[0]); | 
| break; | 
| } | 
| @@ -900,6 +1022,62 @@ static void quoteFunc(sqlite3_context *context, int argc, sqlite3_value **argv){ | 
| } | 
|  | 
| /* | 
| +** The unicode() function.  Return the integer unicode code-point value | 
| +** for the first character of the input string. | 
| +*/ | 
| +static void unicodeFunc( | 
| +  sqlite3_context *context, | 
| +  int argc, | 
| +  sqlite3_value **argv | 
| +){ | 
| +  const unsigned char *z = sqlite3_value_text(argv[0]); | 
| +  (void)argc; | 
| +  if( z && z[0] ) sqlite3_result_int(context, sqlite3Utf8Read(&z)); | 
| +} | 
| + | 
| +/* | 
| +** The char() function takes zero or more arguments, each of which is | 
| +** an integer.  It constructs a string where each character of the string | 
| +** is the unicode character for the corresponding integer argument. | 
| +*/ | 
| +static void charFunc( | 
| +  sqlite3_context *context, | 
| +  int argc, | 
| +  sqlite3_value **argv | 
| +){ | 
| +  unsigned char *z, *zOut; | 
| +  int i; | 
| +  zOut = z = sqlite3_malloc( argc*4+1 ); | 
| +  if( z==0 ){ | 
| +    sqlite3_result_error_nomem(context); | 
| +    return; | 
| +  } | 
| +  for(i=0; i<argc; i++){ | 
| +    sqlite3_int64 x; | 
| +    unsigned c; | 
| +    x = sqlite3_value_int64(argv[i]); | 
| +    if( x<0 || x>0x10ffff ) x = 0xfffd; | 
| +    c = (unsigned)(x & 0x1fffff); | 
| +    if( c<0x00080 ){ | 
| +      *zOut++ = (u8)(c&0xFF); | 
| +    }else if( c<0x00800 ){ | 
| +      *zOut++ = 0xC0 + (u8)((c>>6)&0x1F); | 
| +      *zOut++ = 0x80 + (u8)(c & 0x3F); | 
| +    }else if( c<0x10000 ){ | 
| +      *zOut++ = 0xE0 + (u8)((c>>12)&0x0F); | 
| +      *zOut++ = 0x80 + (u8)((c>>6) & 0x3F); | 
| +      *zOut++ = 0x80 + (u8)(c & 0x3F); | 
| +    }else{ | 
| +      *zOut++ = 0xF0 + (u8)((c>>18) & 0x07); | 
| +      *zOut++ = 0x80 + (u8)((c>>12) & 0x3F); | 
| +      *zOut++ = 0x80 + (u8)((c>>6) & 0x3F); | 
| +      *zOut++ = 0x80 + (u8)(c & 0x3F); | 
| +    }                                                    \ | 
| +  } | 
| +  sqlite3_result_text64(context, (char*)z, zOut-z, sqlite3_free, SQLITE_UTF8); | 
| +} | 
| + | 
| +/* | 
| ** The hex() function.  Interpret the argument as a blob.  Return | 
| ** a hexadecimal rendering as text. | 
| */ | 
| @@ -953,7 +1131,7 @@ static void zeroblobFunc( | 
| /* | 
| ** The replace() function.  Three arguments are all strings: call | 
| ** them A, B, and C. The result is also a string which is derived | 
| -** from A by replacing every occurance of B with C.  The match | 
| +** from A by replacing every occurrence of B with C.  The match | 
| ** must be exact.  Collating sequences are not used. | 
| */ | 
| static void replaceFunc( | 
| @@ -1321,11 +1499,12 @@ static void minmaxStep( | 
| Mem *pBest; | 
| UNUSED_PARAMETER(NotUsed); | 
|  | 
| -  if( sqlite3_value_type(argv[0])==SQLITE_NULL ) return; | 
| pBest = (Mem *)sqlite3_aggregate_context(context, sizeof(*pBest)); | 
| if( !pBest ) return; | 
|  | 
| -  if( pBest->flags ){ | 
| +  if( sqlite3_value_type(argv[0])==SQLITE_NULL ){ | 
| +    if( pBest->flags ) sqlite3SkipAccumulatorLoad(context); | 
| +  }else if( pBest->flags ){ | 
| int max; | 
| int cmp; | 
| CollSeq *pColl = sqlite3GetFuncCollSeq(context); | 
| @@ -1341,8 +1520,11 @@ static void minmaxStep( | 
| cmp = sqlite3MemCompare(pBest, pArg, pColl); | 
| if( (max && cmp<0) || (!max && cmp>0) ){ | 
| sqlite3VdbeMemCopy(pBest, pArg); | 
| +    }else{ | 
| +      sqlite3SkipAccumulatorLoad(context); | 
| } | 
| }else{ | 
| +    pBest->db = sqlite3_context_db_handle(context); | 
| sqlite3VdbeMemCopy(pBest, pArg); | 
| } | 
| } | 
| @@ -1350,7 +1532,7 @@ static void minMaxFinalize(sqlite3_context *context){ | 
| sqlite3_value *pRes; | 
| pRes = (sqlite3_value *)sqlite3_aggregate_context(context, 0); | 
| if( pRes ){ | 
| -    if( ALWAYS(pRes->flags) ){ | 
| +    if( pRes->flags ){ | 
| sqlite3_result_value(context, pRes); | 
| } | 
| sqlite3VdbeMemRelease(pRes); | 
| @@ -1386,20 +1568,20 @@ static void groupConcatStep( | 
| zSep = ","; | 
| nSep = 1; | 
| } | 
| -      sqlite3StrAccumAppend(pAccum, zSep, nSep); | 
| +      if( nSep ) sqlite3StrAccumAppend(pAccum, zSep, nSep); | 
| } | 
| zVal = (char*)sqlite3_value_text(argv[0]); | 
| nVal = sqlite3_value_bytes(argv[0]); | 
| -    sqlite3StrAccumAppend(pAccum, zVal, nVal); | 
| +    if( zVal ) sqlite3StrAccumAppend(pAccum, zVal, nVal); | 
| } | 
| } | 
| static void groupConcatFinalize(sqlite3_context *context){ | 
| StrAccum *pAccum; | 
| pAccum = sqlite3_aggregate_context(context, 0); | 
| if( pAccum ){ | 
| -    if( pAccum->tooBig ){ | 
| +    if( pAccum->accError==STRACCUM_TOOBIG ){ | 
| sqlite3_result_error_toobig(context); | 
| -    }else if( pAccum->mallocFailed ){ | 
| +    }else if( pAccum->accError==STRACCUM_NOMEM ){ | 
| sqlite3_result_error_nomem(context); | 
| }else{ | 
| sqlite3_result_text(context, sqlite3StrAccumFinish(pAccum), -1, | 
| @@ -1429,7 +1611,7 @@ static void setLikeOptFlag(sqlite3 *db, const char *zName, u8 flagVal){ | 
| pDef = sqlite3FindFunction(db, zName, sqlite3Strlen30(zName), | 
| 2, SQLITE_UTF8, 0); | 
| if( ALWAYS(pDef) ){ | 
| -    pDef->flags = flagVal; | 
| +    pDef->funcFlags |= flagVal; | 
| } | 
| } | 
|  | 
| @@ -1473,7 +1655,7 @@ int sqlite3IsLikeFunction(sqlite3 *db, Expr *pExpr, int *pIsNocase, char *aWc){ | 
| pDef = sqlite3FindFunction(db, pExpr->u.zToken, | 
| sqlite3Strlen30(pExpr->u.zToken), | 
| 2, SQLITE_UTF8, 0); | 
| -  if( NEVER(pDef==0) || (pDef->flags & SQLITE_FUNC_LIKE)==0 ){ | 
| +  if( NEVER(pDef==0) || (pDef->funcFlags & SQLITE_FUNC_LIKE)==0 ){ | 
| return 0; | 
| } | 
|  | 
| @@ -1485,12 +1667,12 @@ int sqlite3IsLikeFunction(sqlite3 *db, Expr *pExpr, int *pIsNocase, char *aWc){ | 
| assert( (char*)&likeInfoAlt == (char*)&likeInfoAlt.matchAll ); | 
| assert( &((char*)&likeInfoAlt)[1] == (char*)&likeInfoAlt.matchOne ); | 
| assert( &((char*)&likeInfoAlt)[2] == (char*)&likeInfoAlt.matchSet ); | 
| -  *pIsNocase = (pDef->flags & SQLITE_FUNC_CASE)==0; | 
| +  *pIsNocase = (pDef->funcFlags & SQLITE_FUNC_CASE)==0; | 
| return 1; | 
| } | 
|  | 
| /* | 
| -** All all of the FuncDef structures in the aBuiltinFunc[] array above | 
| +** All of the FuncDef structures in the aBuiltinFunc[] array above | 
| ** to the global function hash table.  This occurs at start-time (as | 
| ** a consequence of calling sqlite3_initialize()). | 
| ** | 
| @@ -1514,14 +1696,20 @@ void sqlite3RegisterGlobalFunctions(void){ | 
| FUNCTION(trim,               2, 3, 0, trimFunc         ), | 
| FUNCTION(min,               -1, 0, 1, minmaxFunc       ), | 
| FUNCTION(min,                0, 0, 1, 0                ), | 
| -    AGGREGATE(min,               1, 0, 1, minmaxStep,      minMaxFinalize ), | 
| +    AGGREGATE2(min,              1, 0, 1, minmaxStep,      minMaxFinalize, | 
| +                                          SQLITE_FUNC_MINMAX ), | 
| FUNCTION(max,               -1, 1, 1, minmaxFunc       ), | 
| FUNCTION(max,                0, 1, 1, 0                ), | 
| -    AGGREGATE(max,               1, 1, 1, minmaxStep,      minMaxFinalize ), | 
| -    FUNCTION(typeof,             1, 0, 0, typeofFunc       ), | 
| -    FUNCTION(length,             1, 0, 0, lengthFunc       ), | 
| +    AGGREGATE2(max,              1, 1, 1, minmaxStep,      minMaxFinalize, | 
| +                                          SQLITE_FUNC_MINMAX ), | 
| +    FUNCTION2(typeof,            1, 0, 0, typeofFunc,  SQLITE_FUNC_TYPEOF), | 
| +    FUNCTION2(length,            1, 0, 0, lengthFunc,  SQLITE_FUNC_LENGTH), | 
| +    FUNCTION(instr,              2, 0, 0, instrFunc        ), | 
| FUNCTION(substr,             2, 0, 0, substrFunc       ), | 
| FUNCTION(substr,             3, 0, 0, substrFunc       ), | 
| +    FUNCTION(printf,            -1, 0, 0, printfFunc       ), | 
| +    FUNCTION(unicode,            1, 0, 0, unicodeFunc      ), | 
| +    FUNCTION(char,              -1, 0, 0, charFunc         ), | 
| FUNCTION(abs,                1, 0, 0, absFunc          ), | 
| #ifndef SQLITE_OMIT_FLOATING_POINT | 
| FUNCTION(round,              1, 0, 0, roundFunc        ), | 
| @@ -1531,24 +1719,29 @@ void sqlite3RegisterGlobalFunctions(void){ | 
| FUNCTION(lower,              1, 0, 0, lowerFunc        ), | 
| FUNCTION(coalesce,           1, 0, 0, 0                ), | 
| FUNCTION(coalesce,           0, 0, 0, 0                ), | 
| -/*  FUNCTION(coalesce,          -1, 0, 0, ifnullFunc       ), */ | 
| -    {-1,SQLITE_UTF8,SQLITE_FUNC_COALESCE,0,0,ifnullFunc,0,0,"coalesce",0,0}, | 
| +    FUNCTION2(coalesce,         -1, 0, 0, noopFunc,  SQLITE_FUNC_COALESCE), | 
| FUNCTION(hex,                1, 0, 0, hexFunc          ), | 
| -/*  FUNCTION(ifnull,             2, 0, 0, ifnullFunc       ), */ | 
| -    {2,SQLITE_UTF8,SQLITE_FUNC_COALESCE,0,0,ifnullFunc,0,0,"ifnull",0,0}, | 
| -    FUNCTION(random,             0, 0, 0, randomFunc       ), | 
| -    FUNCTION(randomblob,         1, 0, 0, randomBlob       ), | 
| +    FUNCTION2(ifnull,            2, 0, 0, noopFunc,  SQLITE_FUNC_COALESCE), | 
| +    FUNCTION2(unlikely,          1, 0, 0, noopFunc,  SQLITE_FUNC_UNLIKELY), | 
| +    FUNCTION2(likelihood,        2, 0, 0, noopFunc,  SQLITE_FUNC_UNLIKELY), | 
| +    FUNCTION2(likely,            1, 0, 0, noopFunc,  SQLITE_FUNC_UNLIKELY), | 
| +    VFUNCTION(random,            0, 0, 0, randomFunc       ), | 
| +    VFUNCTION(randomblob,        1, 0, 0, randomBlob       ), | 
| FUNCTION(nullif,             2, 0, 1, nullifFunc       ), | 
| FUNCTION(sqlite_version,     0, 0, 0, versionFunc      ), | 
| FUNCTION(sqlite_source_id,   0, 0, 0, sourceidFunc     ), | 
| +    FUNCTION(sqlite_log,         2, 0, 0, errlogFunc       ), | 
| +#if SQLITE_USER_AUTHENTICATION | 
| +    FUNCTION(sqlite_crypt,       2, 0, 0, sqlite3CryptFunc ), | 
| +#endif | 
| #ifndef SQLITE_OMIT_COMPILEOPTION_DIAGS | 
| FUNCTION(sqlite_compileoption_used,1, 0, 0, compileoptionusedFunc  ), | 
| FUNCTION(sqlite_compileoption_get, 1, 0, 0, compileoptiongetFunc  ), | 
| #endif /* SQLITE_OMIT_COMPILEOPTION_DIAGS */ | 
| FUNCTION(quote,              1, 0, 0, quoteFunc        ), | 
| -    FUNCTION(last_insert_rowid,  0, 0, 0, last_insert_rowid), | 
| -    FUNCTION(changes,            0, 0, 0, changes          ), | 
| -    FUNCTION(total_changes,      0, 0, 0, total_changes    ), | 
| +    VFUNCTION(last_insert_rowid, 0, 0, 0, last_insert_rowid), | 
| +    VFUNCTION(changes,           0, 0, 0, changes          ), | 
| +    VFUNCTION(total_changes,     0, 0, 0, total_changes    ), | 
| FUNCTION(replace,            3, 0, 0, replaceFunc      ), | 
| FUNCTION(zeroblob,           1, 0, 0, zeroblobFunc     ), | 
| #ifdef SQLITE_SOUNDEX | 
| @@ -1561,8 +1754,8 @@ void sqlite3RegisterGlobalFunctions(void){ | 
| AGGREGATE(sum,               1, 0, 0, sumStep,         sumFinalize    ), | 
| AGGREGATE(total,             1, 0, 0, sumStep,         totalFinalize    ), | 
| AGGREGATE(avg,               1, 0, 0, sumStep,         avgFinalize    ), | 
| - /* AGGREGATE(count,             0, 0, 0, countStep,       countFinalize  ), */ | 
| -    {0,SQLITE_UTF8,SQLITE_FUNC_COUNT,0,0,0,countStep,countFinalize,"count",0,0}, | 
| +    AGGREGATE2(count,            0, 0, 0, countStep,       countFinalize, | 
| +               SQLITE_FUNC_COUNT  ), | 
| AGGREGATE(count,             1, 0, 0, countStep,       countFinalize  ), | 
| AGGREGATE(group_concat,      1, 0, 0, groupConcatStep, groupConcatFinalize), | 
| AGGREGATE(group_concat,      2, 0, 0, groupConcatStep, groupConcatFinalize), | 
| @@ -1588,4 +1781,7 @@ void sqlite3RegisterGlobalFunctions(void){ | 
| #ifndef SQLITE_OMIT_ALTERTABLE | 
| sqlite3AlterFunctions(); | 
| #endif | 
| +#if defined(SQLITE_ENABLE_STAT3) || defined(SQLITE_ENABLE_STAT4) | 
| +  sqlite3AnalyzeFunctions(); | 
| +#endif | 
| } | 
|  |