diff --git a/manifest b/manifest index 40819ec71f..43b03d9330 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Also\supgrade\sscript\sconfig.sub\sto\sthe\slatest\sversion.\sThis\sshould\shave\sbeen\spart\sof\sthe\sprevious\scommit. -D 2019-06-07T18:56:03.782 +C When\scasting\sstring\svalues\sinto\snumeric\sand\sthe\sstring\shas\sa\sprefix\sthat\slooks\nlike\sa\snumber\sbut\stotal\sstring\sis\snot\sa\swell-formed\snumber,\sthen\stake\sextra\ncare\sthat\sthe\sresult\sis\seither\sinteger\sor\sreal\sdepending\son\swhat\sthe\sprefix\nlooks\slike.\s\sFix\sfor\stickets\s[e8bedb2a184001]\sand\s[4c2d7639f076aa]. +D 2019-06-07T22:26:08.019 F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1 F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea F LICENSE.md df5091916dbb40e6e9686186587125e1b2ff51f022cc334e886c19a0e9982724 @@ -470,14 +470,14 @@ F src/build.c c5b97d3518c13081169027f291ff84b12661d526deb605031d413223ff2e0f03 F src/callback.c 25dda5e1c2334a367b94a64077b1d06b2553369f616261ca6783c48bcb6bda73 F src/complete.c a3634ab1e687055cd002e11b8f43eb75c17da23e F src/ctime.c 109e58d00f62e8e71ee1eb5944ac18b90171c928ab2e082e058056e1137cc20b -F src/date.c ebe1dc7c8a347117bb02570f1a931c62dd78f4a2b1b516f4837d45b7d6426957 +F src/date.c e1d8ac7102f3f283e63e13867acb0efa33861cf34f0faf4cdbaf9fa7a1eb7041 F src/dbpage.c 135eb3b5e74f9ef74bde5cec2571192c90c86984fa534c88bf4a055076fa19b7 F src/dbstat.c c12833de69cb655751487d2c5a59607e36be1c58ba1f4bd536609909ad47b319 F src/delete.c d08c9e01a2664afd12edcfa3a9c6578517e8ff8735f35509582693adbe0edeaf F src/expr.c 6b18f022871816c80b772abc3657276562630004b48f588085b404f104fd4430 F src/fault.c 460f3e55994363812d9d60844b2a6de88826e007 F src/fkey.c 0e14d4bef8eac2d87bbd517e492d9084c65008d117823f8922c5e7b2b599bd33 -F src/func.c ad7a7752872eb0bf148e0e56fc6a5e70de95bc6f589497fbe2fa81e2a514e807 +F src/func.c f1ee70d50c75a00620f0b1721438de56fa12b7798b38fb469896582f599fe3c0 F src/global.c 0dea3065ea72a65ae941559b6686aad6516d4913e76fa4f79a95ff7787f624ec F src/hash.c 8d7dda241d0ebdafb6ffdeda3149a412d7df75102cecfc1021c98d6219823b19 F src/hash.h 9d56a9079d523b648774c1784b74b89bd93fac7b365210157482e4319a468f38 @@ -592,15 +592,15 @@ F src/trigger.c bb034c08eca111e66a19cda045903a12547c1be2294b5570d794b869d9c44a73 F src/update.c 3cb9150d2cf661d938e2f1b1749945f3faa767f88febdb739ab1793bbf895ff2 F src/upsert.c 0dd81b40206841814d46942a7337786932475f085716042d0cb2fc7791bf8ca4 F src/utf.c 2f0fac345c7660d5c5bd3df9e9d8d33d4c27f366bcfb09e07443064d751a0507 -F src/util.c bdbb67d3709a0a4b4ba30221e05e0fec184030982a8c94a175ce634ccf547501 +F src/util.c 11e0e5e43850e29571301a3f3b87f43ad69a8ebaef99c69f8ac23793230ab7f9 F src/vacuum.c 82dcec9e7b1afa980288718ad11bc499651c722d7b9f32933c4d694d91cb6ebf -F src/vdbe.c e6fb674eda4aa32c50d53eb09210c9ed802866cb4d1dc0d6187301b55e4a82b7 +F src/vdbe.c 51989be8322328fabc04a257dc207427646a6c165c51c6fe2260e783b72a9f9c F src/vdbe.h 712bca562eaed1c25506b9faf9680bdc75fc42e2f4a1cd518d883fa79c7a4237 F src/vdbeInt.h 3ba14553508d66f58753952d6dd287dce4ec735de02c6440858b4891aed51c17 F src/vdbeapi.c f9161e5c77f512fbb80091ce8af621d19c9556bda5e734cffaac1198407400da F src/vdbeaux.c 3a803d75875031309204df90977059b12ffb706d16b4baa5e2d99f4353962582 F src/vdbeblob.c f5c70f973ea3a9e915d1693278a5f890dc78594300cf4d54e64f2b0917c94191 -F src/vdbemem.c 5ecfa992b496c8e46227f1ff2ebae30c7b7a6bc098229c89a8ff49cf27249d69 +F src/vdbemem.c be520020f89c02de6e0a0df6767e37a4a2eeef3ec7bf9ae64ad6ba32005c19fb F src/vdbesort.c 66592d478dbb46f19aed0b42222325eadb84deb40a90eebe25c6e7c1d8468f47 F src/vdbetrace.c fa3bf238002f0bbbdfb66cc8afb0cea284ff9f148d6439bc1f6f2b4c3b7143f0 F src/vtab.c 1fa256c6ddad7a81e2a4dc080d015d4b0a7135767717d311298e47f6fca64bb3 @@ -723,7 +723,7 @@ F test/capi3b.test efb2b9cfd127efa84433cd7a2d72ce0454ae0dc4 F test/capi3c.test 54e2dc0c8fd7c34ad1590d1be6864397da2438c95a9f5aee2f8fbc60c112e44b F test/capi3d.test aba917805573a03deed961a21f07a5a84505ad0a616f7e3fc1508844a15bccc4 F test/capi3e.test 3d49c01ef2a1a55f41d73cba2b23b5059ec460fe -F test/cast.test 5ceb920718d280b61163500a7d29e0e0a86458b1cbd92d96f962c9d970aa3857 +F test/cast.test 6505b8aecc0e17079536103328add23fe63418530d1f827e46c32e4151a29daf F test/cffault.test 9d6b20606afe712374952eec4f8fd74b1a8097ef F test/check.test dcc952a127c394ce0de2aa634d26c78207e855327cc63a24d3638ca8fbfa641e F test/chunksize.test 427d87791743486cbf0c3b8c625002f3255cb3a89c6eba655a98923b1387b760 @@ -821,7 +821,7 @@ F test/e_createtable.test 1c602347e73ab80b11b9fa083f47155861aaafcff8054aac9e0b76 F test/e_delete.test ab39084f26ae1f033c940b70ebdbbd523dc4962e F test/e_droptrigger.test 3cd080807622c13e5bbb61fc9a57bd7754da2412 F test/e_dropview.test 21ce09c361227ddbc9819a5608ee2700c276bdd5 -F test/e_expr.test 698c8c6e9b4b737f494c39b2210a3eb7af0efd8167137844483b7add5c76a951 +F test/e_expr.test 8cd7d85270cc7b1bca4cad6dc1c65f2d414b8851d0a13eb4eed0aa27a3516b9a F test/e_fkey.test 2febb2084aef9b0186782421c07bc9d377abf067c9cb4efd49d9647ae31f5afe F test/e_fts3.test 17ba7c373aba4d4f5696ba147ee23fd1a1ef70782af050e03e262ca187c5ee07 F test/e_insert.test f02f7f17852b2163732c6611d193f84fc67bc641fb4882c77a464076e5eba80e @@ -1441,7 +1441,7 @@ F test/tkt-9a8b09f8e6.test b2ef151d0984b2ebf237760dbeaa50724e5a0667 F test/tkt-9d68c883.test 16f7cb96781ba579bc2e19bb14b4ad609d9774b6 F test/tkt-9f2eb3abac.test cb6123ac695a08b4454c3792fbe85108f67fabf8 F test/tkt-a7b7803e.test 159ef554234fa1f9fb318c751b284bd1cf858da4 -F test/tkt-a8a0d2996a.test 76662ff0622c90e7ce7bbcb4d9e1129acddf877d17c3489f2da7f17ddfaad1f4 +F test/tkt-a8a0d2996a.test 002e1cde8fc30c39611b52cf981c88200b858765748556822da72e0d32fac73e F test/tkt-b1d3a2e531.test 8f7576e41ca179289ee1a8fee28386fd8e4b0550 F test/tkt-b351d95f9.test d14a503c414c5c58fdde3e80f9a3cfef986498c0 F test/tkt-b72787b1.test a95e8cdad0b98af1853ac7f0afd4ab27b77bf5f3 @@ -1830,7 +1830,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 be8438133f6cd87e5d51f15cfd1eed83176b3239334875eb0c3dec502cfe39d3 -R 00ceb0bb88b1df0dc7ae96766c6b0ad8 -U dan -Z 21b18707f1c3d774dec053a2348d0058 +P efbf31b82e6e16fda88d8cea54202a8593ff52f2267a44dba828704818162e66 +R 30eb5049d622e77cde7b765c01527b8b +U drh +Z 8a6d08c3a530b4e77d8a6a19f29cc9fd diff --git a/manifest.uuid b/manifest.uuid index 662786c7de..9698419a40 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -efbf31b82e6e16fda88d8cea54202a8593ff52f2267a44dba828704818162e66 \ No newline at end of file +67a68af5578f08d2be2e48cf4fd12a6cf35a09c47d259deda81950f7ee1f02f7 \ No newline at end of file diff --git a/src/date.c b/src/date.c index 313c7f9137..e271210679 100644 --- a/src/date.c +++ b/src/date.c @@ -388,7 +388,7 @@ static int parseDateOrTime( return 0; }else if( sqlite3StrICmp(zDate,"now")==0 && sqlite3NotPureFunc(context) ){ return setDateTimeToCurrent(context, p); - }else if( sqlite3AtoF(zDate, &r, sqlite3Strlen30(zDate), SQLITE_UTF8) ){ + }else if( sqlite3AtoF(zDate, &r, sqlite3Strlen30(zDate), SQLITE_UTF8)>0 ){ setRawDateNumber(p, r); return 0; } @@ -722,7 +722,7 @@ static int parseModifier( ** date is already on the appropriate weekday, this is a no-op. */ if( sqlite3_strnicmp(z, "weekday ", 8)==0 - && sqlite3AtoF(&z[8], &r, sqlite3Strlen30(&z[8]), SQLITE_UTF8) + && sqlite3AtoF(&z[8], &r, sqlite3Strlen30(&z[8]), SQLITE_UTF8)>0 && (n=(int)r)==r && n>=0 && r<7 ){ sqlite3_int64 Z; computeYMD_HMS(p); @@ -781,7 +781,7 @@ static int parseModifier( double rRounder; int i; for(n=1; z[n] && z[n]!=':' && !sqlite3Isspace(z[n]); n++){} - if( !sqlite3AtoF(z, &r, n, SQLITE_UTF8) ){ + if( sqlite3AtoF(z, &r, n, SQLITE_UTF8)<=0 ){ rc = 1; break; } diff --git a/src/func.c b/src/func.c index 80c595a559..869d4bd16f 100644 --- a/src/func.c +++ b/src/func.c @@ -397,7 +397,7 @@ static void roundFunc(sqlite3_context *context, int argc, sqlite3_value **argv){ sqlite3_result_error_nomem(context); return; } - if( !sqlite3AtoF(zBuf, &r, sqlite3Strlen30(zBuf), SQLITE_UTF8) ){ + if( sqlite3AtoF(zBuf, &r, sqlite3Strlen30(zBuf), SQLITE_UTF8)<=0 ){ assert( sqlite3_strglob("*Inf", zBuf)==0 ); r = zBuf[0]=='-' ? -HUGE_VAL : +HUGE_VAL; } diff --git a/src/util.c b/src/util.c index e67f22e771..735d6bed6a 100644 --- a/src/util.c +++ b/src/util.c @@ -365,7 +365,9 @@ static LONGDOUBLE_TYPE sqlite3Pow10(int E){ ** return ** 1 => The input string is a pure integer ** 2 or more => The input has a decimal point or eNNN clause -** 0 => The input string is not a valid number +** 0 or less => The input string is not a valid number +** -1 => Not a valid number, but has a valid prefix which +** includes a decimal point and/or an eNNN clause ** ** Valid numbers are in one of these formats: ** @@ -556,7 +558,13 @@ do_atof_calc: *pResult = result; /* return true if number and no extra non-whitespace chracters after */ - return z==zEnd && nDigit>0 && eValid && eType>0 ? eType : 0; + if( z==zEnd && nDigit>0 && eValid && eType>0 ){ + return eType; + }else if( eType>=2 && (eType==3 || eValid) ){ + return -1; + }else{ + return 0; + } #else return !sqlite3Atoi64(z, pResult, length, enc); #endif /* SQLITE_OMIT_FLOATING_POINT */ @@ -599,6 +607,7 @@ static int compare2pow63(const char *zNum, int incr){ ** ** Returns: ** +** -1 Not even a prefix of the input text looks like an integer ** 0 Successful transformation. Fits in a 64-bit signed integer. ** 1 Excess non-space text after the integer value ** 2 Integer too large for a 64-bit signed integer or is malformed @@ -658,9 +667,9 @@ int sqlite3Atoi64(const char *zNum, i64 *pNum, int length, u8 enc){ *pNum = (i64)u; } rc = 0; - if( (i==0 && zStart==zNum) /* No digits */ - || nonNum /* UTF16 with high-order bytes non-zero */ - ){ + if( i==0 && zStart==zNum ){ /* No digits */ + rc = -1; + }else if( nonNum ){ /* UTF16 with high-order bytes non-zero */ rc = 1; }else if( &zNum[i]flags & (MEM_Str|MEM_Int|MEM_Real|MEM_IntReal))==MEM_Str ); rc = sqlite3AtoF(pRec->z, &rValue, pRec->n, enc); - if( rc==0 ) return; + if( rc<=0 ) return; if( rc==1 && alsoAnInt(pRec, rValue, &pRec->u.i) ){ pRec->flags |= MEM_Int; }else{ @@ -422,13 +422,21 @@ void sqlite3ValueApplyAffinity( ** accordingly. */ static u16 SQLITE_NOINLINE computeNumericType(Mem *pMem){ + int rc; + sqlite3_int64 ix; assert( (pMem->flags & (MEM_Int|MEM_Real|MEM_IntReal))==0 ); assert( (pMem->flags & (MEM_Str|MEM_Blob))!=0 ); ExpandBlob(pMem); - if( sqlite3AtoF(pMem->z, &pMem->u.r, pMem->n, pMem->enc)==0 ){ - return 0; - } - if( sqlite3Atoi64(pMem->z, &pMem->u.i, pMem->n, pMem->enc)==0 ){ + rc = sqlite3AtoF(pMem->z, &pMem->u.r, pMem->n, pMem->enc); + if( rc<=0 ){ + if( rc==0 && sqlite3Atoi64(pMem->z, &ix, pMem->n, pMem->enc)<=1 ){ + pMem->u.i = ix; + return MEM_Int; + }else{ + return MEM_Real; + } + }else if( rc==1 && sqlite3Atoi64(pMem->z, &ix, pMem->n, pMem->enc)==0 ){ + pMem->u.i = ix; return MEM_Int; } return MEM_Real; @@ -1590,7 +1598,6 @@ case OP_Subtract: /* same as TK_MINUS, in1, in2, out3 */ case OP_Multiply: /* same as TK_STAR, in1, in2, out3 */ case OP_Divide: /* same as TK_SLASH, in1, in2, out3 */ case OP_Remainder: { /* same as TK_REM, in1, in2, out3 */ - char bIntint; /* Started out as two integer operands */ u16 flags; /* Combined MEM_* flags from both inputs */ u16 type1; /* Numeric type of left operand */ u16 type2; /* Numeric type of right operand */ @@ -1608,7 +1615,6 @@ case OP_Remainder: { /* same as TK_REM, in1, in2, out3 */ if( (type1 & type2 & MEM_Int)!=0 ){ iA = pIn1->u.i; iB = pIn2->u.i; - bIntint = 1; switch( pOp->opcode ){ case OP_Add: if( sqlite3AddInt64(&iB,iA) ) goto fp_math; break; case OP_Subtract: if( sqlite3SubInt64(&iB,iA) ) goto fp_math; break; @@ -1631,7 +1637,6 @@ case OP_Remainder: { /* same as TK_REM, in1, in2, out3 */ }else if( (flags & MEM_Null)!=0 ){ goto arithmetic_result_is_null; }else{ - bIntint = 0; fp_math: rA = sqlite3VdbeRealValue(pIn1); rB = sqlite3VdbeRealValue(pIn2); @@ -1663,9 +1668,6 @@ fp_math: } pOut->u.r = rB; MemSetTypeFlag(pOut, MEM_Real); - if( ((type1|type2)&(MEM_Real|MEM_IntReal))==0 && !bIntint ){ - sqlite3VdbeIntegerAffinity(pOut); - } #endif } break; diff --git a/src/vdbemem.c b/src/vdbemem.c index e8e85dc9e6..a139714a18 100644 --- a/src/vdbemem.c +++ b/src/vdbemem.c @@ -717,20 +717,22 @@ int sqlite3VdbeMemNumerify(Mem *pMem){ testcase( pMem->flags & MEM_Null ); if( (pMem->flags & (MEM_Int|MEM_Real|MEM_IntReal|MEM_Null))==0 ){ int rc; + sqlite3_int64 ix; assert( (pMem->flags & (MEM_Blob|MEM_Str))!=0 ); assert( pMem->db==0 || sqlite3_mutex_held(pMem->db->mutex) ); - rc = sqlite3Atoi64(pMem->z, &pMem->u.i, pMem->n, pMem->enc); - if( rc==0 ){ - MemSetTypeFlag(pMem, MEM_Int); - }else{ - i64 i = pMem->u.i; - sqlite3AtoF(pMem->z, &pMem->u.r, pMem->n, pMem->enc); - if( rc==1 && sqlite3RealSameAsInt(pMem->u.r, i) ){ - pMem->u.i = i; + rc = sqlite3AtoF(pMem->z, &pMem->u.r, pMem->n, pMem->enc); + if( rc<=0 ){ + if( rc==0 && sqlite3Atoi64(pMem->z, &ix, pMem->n, pMem->enc)<=1 ){ + pMem->u.i = ix; MemSetTypeFlag(pMem, MEM_Int); }else{ MemSetTypeFlag(pMem, MEM_Real); } + }else if( rc==1 && sqlite3Atoi64(pMem->z, &ix, pMem->n, pMem->enc)==0 ){ + pMem->u.i = ix; + MemSetTypeFlag(pMem, MEM_Int); + }else{ + MemSetTypeFlag(pMem, MEM_Real); } } assert( (pMem->flags & (MEM_Int|MEM_Real|MEM_IntReal|MEM_Null))!=0 ); diff --git a/test/cast.test b/test/cast.test index f43aa48560..8247636867 100644 --- a/test/cast.test +++ b/test/cast.test @@ -388,4 +388,31 @@ do_execsql_test case-6.1 { SELECT * FROM t1; } {9000000000000000001 9000000000000000001 9000000000000000001 9000000000000000001} +# 2019-06-07 +# https://www.sqlite.org/src/info/4c2d7639f076aa7c +do_execsql_test case-7.1 { + SELECT CAST('-' AS NUMERIC); +} {0} +do_execsql_test case-7.2 { + SELECT CAST('-0' AS NUMERIC); +} {0} +do_execsql_test case-7.3 { + SELECT CAST('+' AS NUMERIC); +} {0} +do_execsql_test case-7.4 { + SELECT CAST('/' AS NUMERIC); +} {0} + +# 2019-06-07 +# https://www.sqlite.org/src/info/e8bedb2a184001bb +do_execsql_test case-7.10 { + SELECT '' - 2851427734582196970; +} {-2851427734582196970} +do_execsql_test case-7.11 { + SELECT 0 - 2851427734582196970; +} {-2851427734582196970} +do_execsql_test case-7.12 { + SELECT '' - 1; +} {-1} + finish_test diff --git a/test/e_expr.test b/test/e_expr.test index 6e3a8d9608..75618a6e06 100644 --- a/test/e_expr.test +++ b/test/e_expr.test @@ -1650,7 +1650,7 @@ do_expr_test e_expr-31.2.4 { # is lossless and reversible. # do_expr_test e_expr-32.1.1 { CAST('45' AS NUMERIC) } integer 45 -do_expr_test e_expr-32.1.2 { CAST('45.0' AS NUMERIC) } integer 45 +do_expr_test e_expr-32.1.2 { CAST('45.0' AS NUMERIC) } real 45.0 do_expr_test e_expr-32.1.3 { CAST('45.2' AS NUMERIC) } real 45.2 do_expr_test e_expr-32.1.4 { CAST('11abc' AS NUMERIC) } integer 11 do_expr_test e_expr-32.1.5 { CAST('11.1abc' AS NUMERIC) } real 11.1 @@ -1701,16 +1701,16 @@ do_execsql_test e_expr-32.2.8 { integer 9000000000000000001 \ integer 9000000000000000001 \ integer 9000000000000000001 \ - integer 9000000000000000001 \ + real 9.0e+18 \ integer 9223372036854775807 \ integer 9223372036854775807 \ integer 9223372036854775807 \ real 9.22337203685478e+18 \ real 9.22337203685478e+18 \ - integer 9223372036854775807 \ - integer 9223372036854775807 \ - integer -5 \ - integer -5 \ + real 9.22337203685478e+18 \ + real 9.22337203685478e+18 \ + real -5.0 \ + real -5.0 \ ] # EVIDENCE-OF: R-64550-29191 Note that the result from casting any diff --git a/test/tkt-a8a0d2996a.test b/test/tkt-a8a0d2996a.test index 03c2ee9448..2644937029 100644 --- a/test/tkt-a8a0d2996a.test +++ b/test/tkt-a8a0d2996a.test @@ -84,12 +84,12 @@ do_execsql_test 4.3 { } {104.5} do_execsql_test 4.4 { SELECT '-9223372036854775807x'-'1x'; -} {-9.22337203685478e+18} +} {-9223372036854775808} do_execsql_test 4.5 { SELECT '9223372036854775806x'+'1x'; -} {9.22337203685478e+18} +} {9223372036854775807} do_execsql_test 4.6 { - SELECT '1234x'/'10y'; -} {123.4} + SELECT '1234x'/'10y', '1234x'/'10.y', '1234x'/'1e1y'; +} {123 123.4 123.4} finish_test