-C Bring\smakefiles\sand\sbuild\sscripts\sinto\salignment\swith\sthe\ssessions\sbranch.\nNo\schanges\sto\scode.
-D 2013-03-19T16:12:40.639
+C Fix\stext-to-numeric\stype\scasting\sso\sthat\sit\sworks\scorrectly\son\sUTF16\nstrings\sthat\scontain\scharacters\swhere\sthe\sLSB\sis\snumeric\sbut\sthe\sMSB\nis\snon-zero.\s\sTicket\s[689137afb6da41]
+D 2013-03-20T12:04:29.291
F Makefile.arm-wince-mingw32ce-gcc d6df77f1f48d690bd73162294bbba7f59507c72f
F Makefile.in df3e48659d80e1b7765785d8d66c86b320f72cc7
F Makefile.linux-gcc 91d710bdc4998cb015f39edf3cb314ec4f4d7e23
F src/trigger.c cd95ac64efa60e39faf9b5597443192ff27a22fa
F src/update.c 28d2d098b43a2c70dae399896ea8a02f622410ef
F src/utf.c 8d819e2e5104a430fc2005f018db14347c95a38f
-F src/util.c 0af2e515dc0dabacec931bca39525f6c3f1c5455
+F src/util.c 550f2b6a5c0085153a4d00462719fb17ee242792
F src/vacuum.c 2727bdd08847fcb6b2d2da6d14f018910e8645d3
F src/vdbe.c 292f8f7ced59c29c63fe17830cbe5f5a0230cdf0
F src/vdbe.h b52887278cb173e66188da84dfab216bea61119d
F test/notify3.test a86259abbfb923aa27d30f0fc038c88e5251488a
F test/notnull.test 2afad748d18fd66d01f66463de73b3e2501fb226
F test/null.test a8b09b8ed87852742343b33441a9240022108993
+F test/numcast.test 5d126f7f581432e86a90d1e35cac625164aec4a1
F test/openv2.test 0d3040974bf402e19b7df4b783e447289d7ab394
F test/orderby1.test f33968647da5c546528fe4d2bf86c6a6a2e5a7ae
F test/orderby2.test bc11009f7cd99d96b1b11e57b199b00633eb5b04
F tool/warnings-clang.sh f6aa929dc20ef1f856af04a730772f59283631d4
F tool/warnings.sh fbc018d67fd7395f440c28f33ef0f94420226381
F tool/win/sqlite.vsix 97894c2790eda7b5bce3cc79cb2a8ec2fde9b3ac
-P 4fe2db1d866c80fe51f7fddbf9ce6753fb55b5f6
-R 7758dd15e3a5f0387c3f17443ec025d8
+P d1f41089aba075eef45fd696599e5d3a74c84d0c
+R ccf3378e4accef01a0ea31a61ac073d2
U drh
-Z 7c5d1dfbeba3270fc7d5841fae61579f
+Z 400c45055ef48421e523d8328d092a1b
-d1f41089aba075eef45fd696599e5d3a74c84d0c
\ No newline at end of file
+5b22053f918d16f593227a432a5d5b4c195bb0b5
\ No newline at end of file
*/
int sqlite3AtoF(const char *z, double *pResult, int length, u8 enc){
#ifndef SQLITE_OMIT_FLOATING_POINT
- int incr = (enc==SQLITE_UTF8?1:2);
+ int incr;
const char *zEnd = z + length;
/* sign * significand * (10 ^ (esign * exponent)) */
int sign = 1; /* sign of significand */
int eValid = 1; /* True exponent is either not used or is well-formed */
double result;
int nDigits = 0;
+ int nonNum = 0;
+ assert( enc==SQLITE_UTF8 || enc==SQLITE_UTF16LE || enc==SQLITE_UTF16BE );
*pResult = 0.0; /* Default return value, in case of an error */
- if( enc==SQLITE_UTF16BE ) z++;
+ if( enc==SQLITE_UTF8 ){
+ incr = 1;
+ }else{
+ int i;
+ incr = 2;
+ assert( SQLITE_UTF16LE==2 && SQLITE_UTF16BE==3 );
+ for(i=3-enc; i<length && z[i]==0; i+=2){}
+ nonNum = i<length;
+ zEnd = z+i+enc-3;
+ z += (enc&1);
+ }
/* skip leading spaces */
while( z<zEnd && sqlite3Isspace(*z) ) z+=incr;
*pResult = result;
/* return true if number and no extra non-whitespace chracters after */
- return z>=zEnd && nDigits>0 && eValid;
+ return z>=zEnd && nDigits>0 && eValid && nonNum==0;
#else
return !sqlite3Atoi64(z, pResult, length, enc);
#endif /* SQLITE_OMIT_FLOATING_POINT */
** signed 64-bit integer, its negative -9223372036854665808 can be.
**
** If zNum is too big for a 64-bit integer and is not
-** 9223372036854665808 then return 1.
+** 9223372036854665808 or if zNum contains any non-numeric text,
+** then return 1.
**
** length is the number of bytes in the string (bytes, not characters).
** The string is not necessarily zero-terminated. The encoding is
** given by enc.
*/
int sqlite3Atoi64(const char *zNum, i64 *pNum, int length, u8 enc){
- int incr = (enc==SQLITE_UTF8?1:2);
+ int incr;
u64 u = 0;
int neg = 0; /* assume positive */
int i;
int c = 0;
+ int nonNum = 0;
const char *zStart;
const char *zEnd = zNum + length;
- if( enc==SQLITE_UTF16BE ) zNum++;
+ assert( enc==SQLITE_UTF8 || enc==SQLITE_UTF16LE || enc==SQLITE_UTF16BE );
+ if( enc==SQLITE_UTF8 ){
+ incr = 1;
+ }else{
+ incr = 2;
+ assert( SQLITE_UTF16LE==2 && SQLITE_UTF16BE==3 );
+ for(i=3-enc; i<length && zNum[i]==0; i+=2){}
+ nonNum = i<length;
+ zEnd = zNum+i+enc-3;
+ zNum += (enc&1);
+ }
while( zNum<zEnd && sqlite3Isspace(*zNum) ) zNum+=incr;
if( zNum<zEnd ){
if( *zNum=='-' ){
testcase( i==18 );
testcase( i==19 );
testcase( i==20 );
- if( (c!=0 && &zNum[i]<zEnd) || (i==0 && zStart==zNum) || i>19*incr ){
+ if( (c+nonNum!=0 && &zNum[i]<zEnd) || (i==0 && zStart==zNum) || i>19*incr ){
/* zNum is empty or contains non-numeric text or is longer
** than 19 digits (thus guaranteeing that it is too large) */
return 1;
--- /dev/null
+# 2013 March 20
+#
+# The author disclaims copyright to this source code. In place of
+# a legal notice, here is a blessing:
+#
+# May you do good and not evil.
+# May you find forgiveness for yourself and forgive others.
+# May you share freely, never taking more than you give.
+#
+#***********************************************************************
+# This file implements regression tests for SQLite library.
+# This particular file does testing of casting strings into numeric
+# values.
+#
+
+set testdir [file dirname $argv0]
+source $testdir/tester.tcl
+
+foreach enc {utf8 utf16le utf16be} {
+ do_test numcast-$enc.0 {
+ db close
+ sqlite3 db :memory:
+ db eval "PRAGMA encoding='$enc'"
+ set x [db eval {PRAGMA encoding}]
+ string map {- {}} [string tolower $x]
+ } $enc
+ foreach {idx str rval ival} {
+ 1 12345.0 12345.0 12345
+ 2 12345.0e0 12345.0 12345
+ 3 -12345.0e0 -12345.0 -12345
+ 4 -12345.25 -12345.25 -12345
+ 5 { -12345.0} -12345.0 -12345
+ 6 { 876xyz} 876.0 876
+ 7 { 456ķ89} 456.0 456
+ 8 { Ġ 321.5} 0.0 0
+ } {
+ do_test numcast-$enc.$idx.1 {
+ db eval {SELECT CAST($str AS real)}
+ } $rval
+ do_test numcast-$enc.$idx.2 {
+ db eval {SELECT CAST($str AS integer)}
+ } $ival
+ }
+}
+
+finish_test