Fixes default log output to console for macOS
[sqlcipher.git] / ext / misc / totype.c
blob31c497a5675a63b73af256480f90baaac63f2b7f
1 /*
2 ** 2013-10-14
3 **
4 ** The author disclaims copyright to this source code. In place of
5 ** a legal notice, here is a blessing:
6 **
7 ** May you do good and not evil.
8 ** May you find forgiveness for yourself and forgive others.
9 ** May you share freely, never taking more than you give.
11 ******************************************************************************
13 ** This SQLite extension implements functions tointeger(X) and toreal(X).
15 ** If X is an integer, real, or string value that can be
16 ** losslessly represented as an integer, then tointeger(X)
17 ** returns the corresponding integer value.
18 ** If X is an 8-byte BLOB then that blob is interpreted as
19 ** a signed two-compliment little-endian encoding of an integer
20 ** and tointeger(X) returns the corresponding integer value.
21 ** Otherwise tointeger(X) return NULL.
23 ** If X is an integer, real, or string value that can be
24 ** convert into a real number, preserving at least 15 digits
25 ** of precision, then toreal(X) returns the corresponding real value.
26 ** If X is an 8-byte BLOB then that blob is interpreted as
27 ** a 64-bit IEEE754 big-endian floating point value
28 ** and toreal(X) returns the corresponding real value.
29 ** Otherwise toreal(X) return NULL.
31 ** Note that tointeger(X) of an 8-byte BLOB assumes a little-endian
32 ** encoding whereas toreal(X) of an 8-byte BLOB assumes a big-endian
33 ** encoding.
35 #include "sqlite3ext.h"
36 SQLITE_EXTENSION_INIT1
37 #include <assert.h>
38 #include <string.h>
41 ** Determine if this is running on a big-endian or little-endian
42 ** processor
44 #if defined(i386) || defined(__i386__) || defined(_M_IX86)\
45 || defined(__x86_64) || defined(__x86_64__)
46 # define TOTYPE_BIGENDIAN 0
47 # define TOTYPE_LITTLEENDIAN 1
48 #else
49 const int totype_one = 1;
50 # define TOTYPE_BIGENDIAN (*(char *)(&totype_one)==0)
51 # define TOTYPE_LITTLEENDIAN (*(char *)(&totype_one)==1)
52 #endif
55 ** Constants for the largest and smallest possible 64-bit signed integers.
56 ** These macros are designed to work correctly on both 32-bit and 64-bit
57 ** compilers.
59 #ifndef LARGEST_INT64
60 # define LARGEST_INT64 (0xffffffff|(((sqlite3_int64)0x7fffffff)<<32))
61 #endif
63 #ifndef SMALLEST_INT64
64 # define SMALLEST_INT64 (((sqlite3_int64)-1) - LARGEST_INT64)
65 #endif
68 ** Return TRUE if character c is a whitespace character
70 static int totypeIsspace(unsigned char c){
71 return c==' ' || c=='\t' || c=='\n' || c=='\v' || c=='\f' || c=='\r';
75 ** Return TRUE if character c is a digit
77 static int totypeIsdigit(unsigned char c){
78 return c>='0' && c<='9';
82 ** Compare the 19-character string zNum against the text representation
83 ** value 2^63: 9223372036854775808. Return negative, zero, or positive
84 ** if zNum is less than, equal to, or greater than the string.
85 ** Note that zNum must contain exactly 19 characters.
87 ** Unlike memcmp() this routine is guaranteed to return the difference
88 ** in the values of the last digit if the only difference is in the
89 ** last digit. So, for example,
91 ** totypeCompare2pow63("9223372036854775800")
93 ** will return -8.
95 static int totypeCompare2pow63(const char *zNum){
96 int c = 0;
97 int i;
98 /* 012345678901234567 */
99 const char *pow63 = "922337203685477580";
100 for(i=0; c==0 && i<18; i++){
101 c = (zNum[i]-pow63[i])*10;
103 if( c==0 ){
104 c = zNum[18] - '8';
106 return c;
110 ** Convert zNum to a 64-bit signed integer.
112 ** If the zNum value is representable as a 64-bit twos-complement
113 ** integer, then write that value into *pNum and return 0.
115 ** If zNum is exactly 9223372036854665808, return 2. This special
116 ** case is broken out because while 9223372036854665808 cannot be a
117 ** signed 64-bit integer, its negative -9223372036854665808 can be.
119 ** If zNum is too big for a 64-bit integer and is not
120 ** 9223372036854665808 or if zNum contains any non-numeric text,
121 ** then return 1.
123 ** The string is not necessarily zero-terminated.
125 static int totypeAtoi64(const char *zNum, sqlite3_int64 *pNum, int length){
126 sqlite3_uint64 u = 0;
127 int neg = 0; /* assume positive */
128 int i;
129 int c = 0;
130 int nonNum = 0;
131 const char *zStart;
132 const char *zEnd = zNum + length;
134 while( zNum<zEnd && totypeIsspace(*zNum) ) zNum++;
135 if( zNum<zEnd ){
136 if( *zNum=='-' ){
137 neg = 1;
138 zNum++;
139 }else if( *zNum=='+' ){
140 zNum++;
143 zStart = zNum;
144 while( zNum<zEnd && zNum[0]=='0' ){ zNum++; } /* Skip leading zeros. */
145 for(i=0; &zNum[i]<zEnd && (c=zNum[i])>='0' && c<='9'; i++){
146 u = u*10 + c - '0';
148 if( u>LARGEST_INT64 ){
149 *pNum = SMALLEST_INT64;
150 }else if( neg ){
151 *pNum = -(sqlite3_int64)u;
152 }else{
153 *pNum = (sqlite3_int64)u;
155 if( (c!=0 && &zNum[i]<zEnd) || (i==0 && zStart==zNum) || i>19 || nonNum ){
156 /* zNum is empty or contains non-numeric text or is longer
157 ** than 19 digits (thus guaranteeing that it is too large) */
158 return 1;
159 }else if( i<19 ){
160 /* Less than 19 digits, so we know that it fits in 64 bits */
161 assert( u<=LARGEST_INT64 );
162 return 0;
163 }else{
164 /* zNum is a 19-digit numbers. Compare it against 9223372036854775808. */
165 c = totypeCompare2pow63(zNum);
166 if( c<0 ){
167 /* zNum is less than 9223372036854775808 so it fits */
168 assert( u<=LARGEST_INT64 );
169 return 0;
170 }else if( c>0 ){
171 /* zNum is greater than 9223372036854775808 so it overflows */
172 return 1;
173 }else{
174 /* zNum is exactly 9223372036854775808. Fits if negative. The
175 ** special case 2 overflow if positive */
176 assert( u-1==LARGEST_INT64 );
177 assert( (*pNum)==SMALLEST_INT64 );
178 return neg ? 0 : 2;
184 ** The string z[] is an text representation of a real number.
185 ** Convert this string to a double and write it into *pResult.
187 ** The string is not necessarily zero-terminated.
189 ** Return TRUE if the result is a valid real number (or integer) and FALSE
190 ** if the string is empty or contains extraneous text. Valid numbers
191 ** are in one of these formats:
193 ** [+-]digits[E[+-]digits]
194 ** [+-]digits.[digits][E[+-]digits]
195 ** [+-].digits[E[+-]digits]
197 ** Leading and trailing whitespace is ignored for the purpose of determining
198 ** validity.
200 ** If some prefix of the input string is a valid number, this routine
201 ** returns FALSE but it still converts the prefix and writes the result
202 ** into *pResult.
204 static int totypeAtoF(const char *z, double *pResult, int length){
205 const char *zEnd = z + length;
206 /* sign * significand * (10 ^ (esign * exponent)) */
207 int sign = 1; /* sign of significand */
208 sqlite3_int64 s = 0; /* significand */
209 int d = 0; /* adjust exponent for shifting decimal point */
210 int esign = 1; /* sign of exponent */
211 int e = 0; /* exponent */
212 int eValid = 1; /* True exponent is either not used or is well-formed */
213 double result;
214 int nDigits = 0;
215 int nonNum = 0;
217 *pResult = 0.0; /* Default return value, in case of an error */
219 /* skip leading spaces */
220 while( z<zEnd && totypeIsspace(*z) ) z++;
221 if( z>=zEnd ) return 0;
223 /* get sign of significand */
224 if( *z=='-' ){
225 sign = -1;
226 z++;
227 }else if( *z=='+' ){
228 z++;
231 /* skip leading zeroes */
232 while( z<zEnd && z[0]=='0' ) z++, nDigits++;
234 /* copy max significant digits to significand */
235 while( z<zEnd && totypeIsdigit(*z) && s<((LARGEST_INT64-9)/10) ){
236 s = s*10 + (*z - '0');
237 z++, nDigits++;
240 /* skip non-significant significand digits
241 ** (increase exponent by d to shift decimal left) */
242 while( z<zEnd && totypeIsdigit(*z) ) z++, nDigits++, d++;
243 if( z>=zEnd ) goto totype_atof_calc;
245 /* if decimal point is present */
246 if( *z=='.' ){
247 z++;
248 /* copy digits from after decimal to significand
249 ** (decrease exponent by d to shift decimal right) */
250 while( z<zEnd && totypeIsdigit(*z) && s<((LARGEST_INT64-9)/10) ){
251 s = s*10 + (*z - '0');
252 z++, nDigits++, d--;
254 /* skip non-significant digits */
255 while( z<zEnd && totypeIsdigit(*z) ) z++, nDigits++;
257 if( z>=zEnd ) goto totype_atof_calc;
259 /* if exponent is present */
260 if( *z=='e' || *z=='E' ){
261 z++;
262 eValid = 0;
263 if( z>=zEnd ) goto totype_atof_calc;
264 /* get sign of exponent */
265 if( *z=='-' ){
266 esign = -1;
267 z++;
268 }else if( *z=='+' ){
269 z++;
271 /* copy digits to exponent */
272 while( z<zEnd && totypeIsdigit(*z) ){
273 e = e<10000 ? (e*10 + (*z - '0')) : 10000;
274 z++;
275 eValid = 1;
279 /* skip trailing spaces */
280 if( nDigits && eValid ){
281 while( z<zEnd && totypeIsspace(*z) ) z++;
284 totype_atof_calc:
285 /* adjust exponent by d, and update sign */
286 e = (e*esign) + d;
287 if( e<0 ) {
288 esign = -1;
289 e *= -1;
290 } else {
291 esign = 1;
294 /* if 0 significand */
295 if( !s ) {
296 /* In the IEEE 754 standard, zero is signed.
297 ** Add the sign if we've seen at least one digit */
298 result = (sign<0 && nDigits) ? -(double)0 : (double)0;
299 } else {
300 /* attempt to reduce exponent */
301 if( esign>0 ){
302 while( s<(LARGEST_INT64/10) && e>0 ) e--,s*=10;
303 }else{
304 while( !(s%10) && e>0 ) e--,s/=10;
307 /* adjust the sign of significand */
308 s = sign<0 ? -s : s;
310 /* if exponent, scale significand as appropriate
311 ** and store in result. */
312 if( e ){
313 double scale = 1.0;
314 /* attempt to handle extremely small/large numbers better */
315 if( e>307 && e<342 ){
316 while( e%308 ) { scale *= 1.0e+1; e -= 1; }
317 if( esign<0 ){
318 result = s / scale;
319 result /= 1.0e+308;
320 }else{
321 result = s * scale;
322 result *= 1.0e+308;
324 }else if( e>=342 ){
325 if( esign<0 ){
326 result = 0.0*s;
327 }else{
328 result = 1e308*1e308*s; /* Infinity */
330 }else{
331 /* 1.0e+22 is the largest power of 10 than can be
332 ** represented exactly. */
333 while( e%22 ) { scale *= 1.0e+1; e -= 1; }
334 while( e>0 ) { scale *= 1.0e+22; e -= 22; }
335 if( esign<0 ){
336 result = s / scale;
337 }else{
338 result = s * scale;
341 } else {
342 result = (double)s;
346 /* store the result */
347 *pResult = result;
349 /* return true if number and no extra non-whitespace chracters after */
350 return z>=zEnd && nDigits>0 && eValid && nonNum==0;
354 ** Convert a floating point value to an integer. Or, if this cannot be
355 ** done in a way that avoids 'outside the range of representable values'
356 ** warnings from UBSAN, return 0.
358 ** This function is a modified copy of internal SQLite function
359 ** sqlite3RealToI64().
361 static sqlite3_int64 totypeDoubleToInt(double r){
362 if( r<-9223372036854774784.0 ) return 0;
363 if( r>+9223372036854774784.0 ) return 0;
364 return (sqlite3_int64)r;
368 ** tointeger(X): If X is any value (integer, double, blob, or string) that
369 ** can be losslessly converted into an integer, then make the conversion and
370 ** return the result. Otherwise, return NULL.
372 static void tointegerFunc(
373 sqlite3_context *context,
374 int argc,
375 sqlite3_value **argv
377 assert( argc==1 );
378 (void)argc;
379 switch( sqlite3_value_type(argv[0]) ){
380 case SQLITE_FLOAT: {
381 double rVal = sqlite3_value_double(argv[0]);
382 sqlite3_int64 iVal = totypeDoubleToInt(rVal);
383 if( rVal==(double)iVal ){
384 sqlite3_result_int64(context, iVal);
386 break;
388 case SQLITE_INTEGER: {
389 sqlite3_result_int64(context, sqlite3_value_int64(argv[0]));
390 break;
392 case SQLITE_BLOB: {
393 const unsigned char *zBlob = sqlite3_value_blob(argv[0]);
394 if( zBlob ){
395 int nBlob = sqlite3_value_bytes(argv[0]);
396 if( nBlob==sizeof(sqlite3_int64) ){
397 sqlite3_int64 iVal;
398 if( TOTYPE_BIGENDIAN ){
399 int i;
400 unsigned char zBlobRev[sizeof(sqlite3_int64)];
401 for(i=0; i<sizeof(sqlite3_int64); i++){
402 zBlobRev[i] = zBlob[sizeof(sqlite3_int64)-1-i];
404 memcpy(&iVal, zBlobRev, sizeof(sqlite3_int64));
405 }else{
406 memcpy(&iVal, zBlob, sizeof(sqlite3_int64));
408 sqlite3_result_int64(context, iVal);
411 break;
413 case SQLITE_TEXT: {
414 const unsigned char *zStr = sqlite3_value_text(argv[0]);
415 if( zStr ){
416 int nStr = sqlite3_value_bytes(argv[0]);
417 if( nStr && !totypeIsspace(zStr[0]) ){
418 sqlite3_int64 iVal;
419 if( !totypeAtoi64((const char*)zStr, &iVal, nStr) ){
420 sqlite3_result_int64(context, iVal);
424 break;
426 default: {
427 assert( sqlite3_value_type(argv[0])==SQLITE_NULL );
428 break;
434 ** toreal(X): If X is any value (integer, double, blob, or string) that can
435 ** be losslessly converted into a real number, then do so and return that
436 ** real number. Otherwise return NULL.
438 #if defined(_MSC_VER)
439 #pragma warning(disable: 4748)
440 #pragma optimize("", off)
441 #endif
442 static void torealFunc(
443 sqlite3_context *context,
444 int argc,
445 sqlite3_value **argv
447 assert( argc==1 );
448 (void)argc;
449 switch( sqlite3_value_type(argv[0]) ){
450 case SQLITE_FLOAT: {
451 sqlite3_result_double(context, sqlite3_value_double(argv[0]));
452 break;
454 case SQLITE_INTEGER: {
455 sqlite3_int64 iVal = sqlite3_value_int64(argv[0]);
456 double rVal = (double)iVal;
457 if( iVal==totypeDoubleToInt(rVal) ){
458 sqlite3_result_double(context, rVal);
460 break;
462 case SQLITE_BLOB: {
463 const unsigned char *zBlob = sqlite3_value_blob(argv[0]);
464 if( zBlob ){
465 int nBlob = sqlite3_value_bytes(argv[0]);
466 if( nBlob==sizeof(double) ){
467 double rVal;
468 if( TOTYPE_LITTLEENDIAN ){
469 int i;
470 unsigned char zBlobRev[sizeof(double)];
471 for(i=0; i<sizeof(double); i++){
472 zBlobRev[i] = zBlob[sizeof(double)-1-i];
474 memcpy(&rVal, zBlobRev, sizeof(double));
475 }else{
476 memcpy(&rVal, zBlob, sizeof(double));
478 sqlite3_result_double(context, rVal);
481 break;
483 case SQLITE_TEXT: {
484 const unsigned char *zStr = sqlite3_value_text(argv[0]);
485 if( zStr ){
486 int nStr = sqlite3_value_bytes(argv[0]);
487 if( nStr && !totypeIsspace(zStr[0]) && !totypeIsspace(zStr[nStr-1]) ){
488 double rVal;
489 if( totypeAtoF((const char*)zStr, &rVal, nStr) ){
490 sqlite3_result_double(context, rVal);
491 return;
495 break;
497 default: {
498 assert( sqlite3_value_type(argv[0])==SQLITE_NULL );
499 break;
503 #if defined(_MSC_VER)
504 #pragma optimize("", on)
505 #pragma warning(default: 4748)
506 #endif
508 #ifdef _WIN32
509 __declspec(dllexport)
510 #endif
511 int sqlite3_totype_init(
512 sqlite3 *db,
513 char **pzErrMsg,
514 const sqlite3_api_routines *pApi
516 int rc = SQLITE_OK;
517 SQLITE_EXTENSION_INIT2(pApi);
518 (void)pzErrMsg; /* Unused parameter */
519 rc = sqlite3_create_function(db, "tointeger", 1,
520 SQLITE_UTF8 | SQLITE_DETERMINISTIC | SQLITE_INNOCUOUS, 0,
521 tointegerFunc, 0, 0);
522 if( rc==SQLITE_OK ){
523 rc = sqlite3_create_function(db, "toreal", 1,
524 SQLITE_UTF8 | SQLITE_DETERMINISTIC | SQLITE_INNOCUOUS, 0,
525 torealFunc, 0, 0);
527 return rc;