downgrade memory unlock failures to info level and fix function name in log output
[sqlcipher.git] / test / func.test
bloba3ecd4e30bbbd9f2b9e2b4a519e4a1c50787396c
1 # 2001 September 15
3 # The author disclaims copyright to this source code.  In place of
4 # a legal notice, here is a blessing:
6 #    May you do good and not evil.
7 #    May you find forgiveness for yourself and forgive others.
8 #    May you share freely, never taking more than you give.
10 #***********************************************************************
11 # This file implements regression tests for SQLite library.  The
12 # focus of this file is testing built-in functions.
15 set testdir [file dirname $argv0]
16 source $testdir/tester.tcl
17 set testprefix func
19 # Create a table to work with.
21 do_test func-0.0 {
22   execsql {CREATE TABLE tbl1(t1 text)}
23   foreach word {this program is free software} {
24     execsql "INSERT INTO tbl1 VALUES('$word')"
25   }
26   execsql {SELECT t1 FROM tbl1 ORDER BY t1}
27 } {free is program software this}
28 do_test func-0.1 {
29   execsql {
30      CREATE TABLE t2(a);
31      INSERT INTO t2 VALUES(1);
32      INSERT INTO t2 VALUES(NULL);
33      INSERT INTO t2 VALUES(345);
34      INSERT INTO t2 VALUES(NULL);
35      INSERT INTO t2 VALUES(67890);
36      SELECT * FROM t2;
37   }
38 } {1 {} 345 {} 67890}
40 # Check out the length() function
42 do_test func-1.0 {
43   execsql {SELECT length(t1) FROM tbl1 ORDER BY t1}
44 } {4 2 7 8 4}
45 set isutf16 [regexp 16 [db one {PRAGMA encoding}]]
46 do_execsql_test func-1.0b {
47   SELECT octet_length(t1) FROM tbl1 ORDER BY t1;
48 } [expr {$isutf16?"8 4 14 16 8":"4 2 7 8 4"}]
49 do_test func-1.1 {
50   set r [catch {execsql {SELECT length(*) FROM tbl1 ORDER BY t1}} msg]
51   lappend r $msg
52 } {1 {wrong number of arguments to function length()}}
53 do_test func-1.2 {
54   set r [catch {execsql {SELECT length(t1,5) FROM tbl1 ORDER BY t1}} msg]
55   lappend r $msg
56 } {1 {wrong number of arguments to function length()}}
57 do_test func-1.3 {
58   execsql {SELECT length(t1), count(*) FROM tbl1 GROUP BY length(t1)
59            ORDER BY length(t1)}
60 } {2 1 4 2 7 1 8 1}
61 do_test func-1.4 {
62   execsql {SELECT coalesce(length(a),-1) FROM t2}
63 } {1 -1 3 -1 5}
64 do_execsql_test func-1.5 {
65   SELECT octet_length(12345);
66 } [expr {(1+($isutf16!=0))*5}]
67 db null NULL
68 do_execsql_test func-1.6 {
69   SELECT octet_length(NULL);
70 } {NULL}
71 do_execsql_test func-1.7 {
72   SELECT octet_length(7.5);
73 } [expr {(1+($isutf16!=0))*3}]
74 do_execsql_test func-1.8 {
75   SELECT octet_length(x'30313233');
76 } {4}
77 do_execsql_test func-1.9 {
78   WITH c(x) AS (VALUES(char(350,351,352,353,354)))
79   SELECT length(x), octet_length(x) FROM c;
80 } {5 10}
84 # Check out the substr() function
86 db null {}
87 do_test func-2.0 {
88   execsql {SELECT substr(t1,1,2) FROM tbl1 ORDER BY t1}
89 } {fr is pr so th}
90 do_test func-2.1 {
91   execsql {SELECT substr(t1,2,1) FROM tbl1 ORDER BY t1}
92 } {r s r o h}
93 do_test func-2.2 {
94   execsql {SELECT substr(t1,3,3) FROM tbl1 ORDER BY t1}
95 } {ee {} ogr ftw is}
96 do_test func-2.3 {
97   execsql {SELECT substr(t1,-1,1) FROM tbl1 ORDER BY t1}
98 } {e s m e s}
99 do_test func-2.4 {
100   execsql {SELECT substr(t1,-1,2) FROM tbl1 ORDER BY t1}
101 } {e s m e s}
102 do_test func-2.5 {
103   execsql {SELECT substr(t1,-2,1) FROM tbl1 ORDER BY t1}
104 } {e i a r i}
105 do_test func-2.6 {
106   execsql {SELECT substr(t1,-2,2) FROM tbl1 ORDER BY t1}
107 } {ee is am re is}
108 do_test func-2.7 {
109   execsql {SELECT substr(t1,-4,2) FROM tbl1 ORDER BY t1}
110 } {fr {} gr wa th}
111 do_test func-2.8 {
112   execsql {SELECT t1 FROM tbl1 ORDER BY substr(t1,2,20)}
113 } {this software free program is}
114 do_test func-2.9 {
115   execsql {SELECT substr(a,1,1) FROM t2}
116 } {1 {} 3 {} 6}
117 do_test func-2.10 {
118   execsql {SELECT substr(a,2,2) FROM t2}
119 } {{} {} 45 {} 78}
121 # Only do the following tests if TCL has UTF-8 capabilities
123 if {"\u1234"!="u1234"} {
125 # Put some UTF-8 characters in the database
127 do_test func-3.0 {
128   execsql {DELETE FROM tbl1}
129   foreach word "contains UTF-8 characters hi\u1234ho" {
130     execsql "INSERT INTO tbl1 VALUES('$word')"
131   }
132   execsql {SELECT t1 FROM tbl1 ORDER BY t1}
133 } "UTF-8 characters contains hi\u1234ho"
134 do_test func-3.1 {
135   execsql {SELECT length(t1) FROM tbl1 ORDER BY t1}
136 } {5 10 8 5}
137 do_test func-3.2 {
138   execsql {SELECT substr(t1,1,2) FROM tbl1 ORDER BY t1}
139 } {UT ch co hi}
140 do_test func-3.3 {
141   execsql {SELECT substr(t1,1,3) FROM tbl1 ORDER BY t1}
142 } "UTF cha con hi\u1234"
143 do_test func-3.4 {
144   execsql {SELECT substr(t1,2,2) FROM tbl1 ORDER BY t1}
145 } "TF ha on i\u1234"
146 do_test func-3.5 {
147   execsql {SELECT substr(t1,2,3) FROM tbl1 ORDER BY t1}
148 } "TF- har ont i\u1234h"
149 do_test func-3.6 {
150   execsql {SELECT substr(t1,3,2) FROM tbl1 ORDER BY t1}
151 } "F- ar nt \u1234h"
152 do_test func-3.7 {
153   execsql {SELECT substr(t1,4,2) FROM tbl1 ORDER BY t1}
154 } "-8 ra ta ho"
155 do_test func-3.8 {
156   execsql {SELECT substr(t1,-1,1) FROM tbl1 ORDER BY t1}
157 } "8 s s o"
158 do_test func-3.9 {
159   execsql {SELECT substr(t1,-3,2) FROM tbl1 ORDER BY t1}
160 } "F- er in \u1234h"
161 do_test func-3.10 {
162   execsql {SELECT substr(t1,-4,3) FROM tbl1 ORDER BY t1}
163 } "TF- ter ain i\u1234h"
164 do_test func-3.99 {
165   execsql {DELETE FROM tbl1}
166   foreach word {this program is free software} {
167     execsql "INSERT INTO tbl1 VALUES('$word')"
168   }
169   execsql {SELECT t1 FROM tbl1}
170 } {this program is free software}
172 } ;# End \u1234!=u1234
174 # Test the abs() and round() functions.
176 ifcapable !floatingpoint {
177   do_test func-4.1 {
178     execsql {
179       CREATE TABLE t1(a,b,c);
180       INSERT INTO t1 VALUES(1,2,3);
181       INSERT INTO t1 VALUES(2,12345678901234,-1234567890);
182       INSERT INTO t1 VALUES(3,-2,-5);
183     }
184     catchsql {SELECT abs(a,b) FROM t1}
185   } {1 {wrong number of arguments to function abs()}}
187 ifcapable floatingpoint {
188   do_test func-4.1 {
189     execsql {
190       CREATE TABLE t1(a,b,c);
191       INSERT INTO t1 VALUES(1,2,3);
192       INSERT INTO t1 VALUES(2,1.2345678901234,-12345.67890);
193       INSERT INTO t1 VALUES(3,-2,-5);
194     }
195     catchsql {SELECT abs(a,b) FROM t1}
196   } {1 {wrong number of arguments to function abs()}}
198 do_test func-4.2 {
199   catchsql {SELECT abs() FROM t1}
200 } {1 {wrong number of arguments to function abs()}}
201 ifcapable floatingpoint {
202   do_test func-4.3 {
203     catchsql {SELECT abs(b) FROM t1 ORDER BY a}
204   } {0 {2 1.2345678901234 2}}
205   do_test func-4.4 {
206     catchsql {SELECT abs(c) FROM t1 ORDER BY a}
207   } {0 {3 12345.6789 5}}
209 ifcapable !floatingpoint {
210   if {[working_64bit_int]} {
211     do_test func-4.3 {
212       catchsql {SELECT abs(b) FROM t1 ORDER BY a}
213     } {0 {2 12345678901234 2}}
214   }
215   do_test func-4.4 {
216     catchsql {SELECT abs(c) FROM t1 ORDER BY a}
217   } {0 {3 1234567890 5}}
219 do_test func-4.4.1 {
220   execsql {SELECT abs(a) FROM t2}
221 } {1 {} 345 {} 67890}
222 do_test func-4.4.2 {
223   execsql {SELECT abs(t1) FROM tbl1}
224 } {0.0 0.0 0.0 0.0 0.0}
226 ifcapable floatingpoint {
227   do_test func-4.5 {
228     catchsql {SELECT round(a,b,c) FROM t1}
229   } {1 {wrong number of arguments to function round()}}
230   do_test func-4.6 {
231     catchsql {SELECT round(b,2) FROM t1 ORDER BY b}
232   } {0 {-2.0 1.23 2.0}}
233   do_test func-4.7 {
234     catchsql {SELECT round(b,0) FROM t1 ORDER BY a}
235   } {0 {2.0 1.0 -2.0}}
236   do_test func-4.8 {
237     catchsql {SELECT round(c) FROM t1 ORDER BY a}
238   } {0 {3.0 -12346.0 -5.0}}
239   do_test func-4.9 {
240     catchsql {SELECT round(c,a) FROM t1 ORDER BY a}
241   } {0 {3.0 -12345.68 -5.0}}
242   do_test func-4.10 {
243     catchsql {SELECT 'x' || round(c,a) || 'y' FROM t1 ORDER BY a}
244   } {0 {x3.0y x-12345.68y x-5.0y}}
245   do_test func-4.11 {
246     catchsql {SELECT round() FROM t1 ORDER BY a}
247   } {1 {wrong number of arguments to function round()}}
248   do_test func-4.12 {
249     execsql {SELECT coalesce(round(a,2),'nil') FROM t2}
250   } {1.0 nil 345.0 nil 67890.0}
251   do_test func-4.13 {
252     execsql {SELECT round(t1,2) FROM tbl1}
253   } {0.0 0.0 0.0 0.0 0.0}
254   do_test func-4.14 {
255     execsql {SELECT typeof(round(5.1,1));}
256   } {real}
257   do_test func-4.15 {
258     execsql {SELECT typeof(round(5.1));}
259   } {real}
260   do_test func-4.16 {
261     catchsql {SELECT round(b,2.0) FROM t1 ORDER BY b}
262   } {0 {-2.0 1.23 2.0}}
263   # Verify some values reported on the mailing list.
264   # Some of these fail on MSVC builds with 64-bit
265   # long doubles, but not on GCC builds with 80-bit
266   # long doubles.
267   for {set i 1} {$i<999} {incr i} {
268     set x1 [expr 40222.5 + $i]
269     set x2 [expr 40223.0 + $i]
270     do_test func-4.17.$i {
271       execsql {SELECT round($x1);}
272     } $x2
273   }
274   for {set i 1} {$i<999} {incr i} {
275     set x1 [expr 40222.05 + $i]
276     set x2 [expr 40222.10 + $i]
277     do_test func-4.18.$i {
278       execsql {SELECT round($x1,1);}
279     } $x2
280   }
281   do_test func-4.20 {
282     execsql {SELECT round(40223.4999999999);}
283   } {40223.0}
284   do_test func-4.21 {
285     execsql {SELECT round(40224.4999999999);}
286   } {40224.0}
287   do_test func-4.22 {
288     execsql {SELECT round(40225.4999999999);}
289   } {40225.0}
290   for {set i 1} {$i<10} {incr i} {
291     do_test func-4.23.$i {
292       execsql {SELECT round(40223.4999999999,$i);}
293     } {40223.5}
294     do_test func-4.24.$i {
295       execsql {SELECT round(40224.4999999999,$i);}
296     } {40224.5}
297     do_test func-4.25.$i {
298       execsql {SELECT round(40225.4999999999,$i);}
299     } {40225.5}
300   }
301   for {set i 10} {$i<32} {incr i} {
302     do_test func-4.26.$i {
303       execsql {SELECT round(40223.4999999999,$i);}
304     } {40223.4999999999}
305     do_test func-4.27.$i {
306       execsql {SELECT round(40224.4999999999,$i);}
307     } {40224.4999999999}
308     do_test func-4.28.$i {
309       execsql {SELECT round(40225.4999999999,$i);}
310     } {40225.4999999999}
311   }
312   do_test func-4.29 {
313     execsql {SELECT round(1234567890.5);}
314   } {1234567891.0}
315   do_test func-4.30 {
316     execsql {SELECT round(12345678901.5);}
317   } {12345678902.0}
318   do_test func-4.31 {
319     execsql {SELECT round(123456789012.5);}
320   } {123456789013.0}
321   do_test func-4.32 {
322     execsql {SELECT round(1234567890123.5);}
323   } {1234567890124.0}
324   do_test func-4.33 {
325     execsql {SELECT round(12345678901234.5);}
326   } {12345678901235.0}
327   do_test func-4.34 {
328     execsql {SELECT round(1234567890123.35,1);}
329   } {1234567890123.4}
330   do_test func-4.35 {
331     execsql {SELECT round(1234567890123.445,2);}
332   } {1234567890123.45}
333   do_test func-4.36 {
334     execsql {SELECT round(99999999999994.5);}
335   } {99999999999995.0}
336   do_test func-4.37 {
337     execsql {SELECT round(9999999999999.55,1);}
338   } {9999999999999.6}
339   do_test func-4.38 {
340     execsql {SELECT round(9999999999999.556,2);}
341   } {9999999999999.56}
342   do_test func-4.39 {
343     string tolower [db eval {SELECT round(1e500), round(-1e500);}]
344   } {inf -inf}
347 # Test the upper() and lower() functions
349 do_test func-5.1 {
350   execsql {SELECT upper(t1) FROM tbl1}
351 } {THIS PROGRAM IS FREE SOFTWARE}
352 do_test func-5.2 {
353   execsql {SELECT lower(upper(t1)) FROM tbl1}
354 } {this program is free software}
355 do_test func-5.3 {
356   execsql {SELECT upper(a), lower(a) FROM t2}
357 } {1 1 {} {} 345 345 {} {} 67890 67890}
358 ifcapable !icu {
359   do_test func-5.4 {
360     catchsql {SELECT upper(a,5) FROM t2}
361   } {1 {wrong number of arguments to function upper()}}
363 do_test func-5.5 {
364   catchsql {SELECT upper(*) FROM t2}
365 } {1 {wrong number of arguments to function upper()}}
367 # Test the coalesce() and nullif() functions
369 do_test func-6.1 {
370   execsql {SELECT coalesce(a,'xyz') FROM t2}
371 } {1 xyz 345 xyz 67890}
372 do_test func-6.2 {
373   execsql {SELECT coalesce(upper(a),'nil') FROM t2}
374 } {1 nil 345 nil 67890}
375 do_test func-6.3 {
376   execsql {SELECT coalesce(nullif(1,1),'nil')}
377 } {nil}
378 do_test func-6.4 {
379   execsql {SELECT coalesce(nullif(1,2),'nil')}
380 } {1}
381 do_test func-6.5 {
382   execsql {SELECT coalesce(nullif(1,NULL),'nil')}
383 } {1}
386 # Test the last_insert_rowid() function
388 do_test func-7.1 {
389   execsql {SELECT last_insert_rowid()}
390 } [db last_insert_rowid]
392 # Tests for aggregate functions and how they handle NULLs.
394 ifcapable floatingpoint {
395   do_test func-8.1 {
396     ifcapable explain {
397       execsql {EXPLAIN SELECT sum(a) FROM t2;}
398     }
399     execsql {
400       SELECT sum(a), count(a), round(avg(a),2), min(a), max(a), count(*) FROM t2;
401     }
402   } {68236 3 22745.33 1 67890 5}
404 ifcapable !floatingpoint {
405   do_test func-8.1 {
406     ifcapable explain {
407       execsql {EXPLAIN SELECT sum(a) FROM t2;}
408     }
409     execsql {
410       SELECT sum(a), count(a), avg(a), min(a), max(a), count(*) FROM t2;
411     }
412   } {68236 3 22745.0 1 67890 5}
414 do_test func-8.2 {
415   execsql {
416     SELECT max('z+'||a||'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOP') FROM t2;
417   }
418 } {z+67890abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOP}
420 ifcapable tempdb {
421   do_test func-8.3 {
422     execsql {
423       CREATE TEMP TABLE t3 AS SELECT a FROM t2 ORDER BY a DESC;
424       SELECT min('z+'||a||'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOP') FROM t3;
425     }
426   } {z+1abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOP}
427 } else {
428   do_test func-8.3 {
429     execsql {
430       CREATE TABLE t3 AS SELECT a FROM t2 ORDER BY a DESC;
431       SELECT min('z+'||a||'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOP') FROM t3;
432     }
433   } {z+1abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOP}
435 do_test func-8.4 {
436   execsql {
437     SELECT max('z+'||a||'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOP') FROM t3;
438   }
439 } {z+67890abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOP}
440 ifcapable compound {
441   do_test func-8.5 {
442     execsql {
443       SELECT sum(x) FROM (SELECT '9223372036' || '854775807' AS x
444                           UNION ALL SELECT -9223372036854775807)
445     }
446   } {0}
447   do_test func-8.6 {
448     execsql {
449       SELECT typeof(sum(x)) FROM (SELECT '9223372036' || '854775807' AS x
450                           UNION ALL SELECT -9223372036854775807)
451     }
452   } {integer}
453   do_test func-8.7 {
454     execsql {
455       SELECT typeof(sum(x)) FROM (SELECT '9223372036' || '854775808' AS x
456                           UNION ALL SELECT -9223372036854775807)
457     }
458   } {real}
459 ifcapable floatingpoint {
460   do_test func-8.8 {
461     execsql {
462       SELECT sum(x)>0.0 FROM (SELECT '9223372036' || '854775808' AS x
463                           UNION ALL SELECT -9223372036850000000)
464     }
465   } {1}
467 ifcapable !floatingpoint {
468   do_test func-8.8 {
469     execsql {
470       SELECT sum(x)>0 FROM (SELECT '9223372036' || '854775808' AS x
471                           UNION ALL SELECT -9223372036850000000)
472     }
473   } {1}
477 # How do you test the random() function in a meaningful, deterministic way?
479 do_test func-9.1 {
480   execsql {
481     SELECT random() is not null;
482   }
483 } {1}
484 do_test func-9.2 {
485   execsql {
486     SELECT typeof(random());
487   }
488 } {integer}
489 do_test func-9.3 {
490   execsql {
491     SELECT randomblob(32) is not null;
492   }
493 } {1}
494 do_test func-9.4 {
495   execsql {
496     SELECT typeof(randomblob(32));
497   }
498 } {blob}
499 do_test func-9.5 {
500   execsql {
501     SELECT length(randomblob(32)), length(randomblob(-5)),
502            length(randomblob(2000))
503   }
504 } {32 1 2000}
506 # The "hex()" function was added in order to be able to render blobs
507 # generated by randomblob().  So this seems like a good place to test
508 # hex().
510 ifcapable bloblit {
511   do_test func-9.10 {
512     execsql {SELECT hex(x'00112233445566778899aAbBcCdDeEfF')}
513   } {00112233445566778899AABBCCDDEEFF}
515 set encoding [db one {PRAGMA encoding}]
516 if {$encoding=="UTF-16le"} {
517   do_test func-9.11-utf16le {
518     execsql {SELECT hex(replace('abcdefg','ef','12'))}
519   } {6100620063006400310032006700}
520   do_test func-9.12-utf16le {
521     execsql {SELECT hex(replace('abcdefg','','12'))}
522   } {6100620063006400650066006700}
523   do_test func-9.13-utf16le {
524     execsql {SELECT hex(replace('aabcdefg','a','aaa'))}
525   } {610061006100610061006100620063006400650066006700}
526 } elseif {$encoding=="UTF-8"} {
527   do_test func-9.11-utf8 {
528     execsql {SELECT hex(replace('abcdefg','ef','12'))}
529   } {61626364313267}
530   do_test func-9.12-utf8 {
531     execsql {SELECT hex(replace('abcdefg','','12'))}
532   } {61626364656667}
533   do_test func-9.13-utf8 {
534     execsql {SELECT hex(replace('aabcdefg','a','aaa'))}
535   } {616161616161626364656667}
537 do_execsql_test func-9.14 {
538   WITH RECURSIVE c(x) AS (
539      VALUES(1)
540      UNION ALL
541      SELECT x+1 FROM c WHERE x<1040
542   )
543   SELECT 
544     count(*),
545     sum(length(replace(printf('abc%.*cxyz',x,'m'),'m','nnnn'))-(6+x*4))
546   FROM c;
547 } {1040 0}
548   
549 # Use the "sqlite_register_test_function" TCL command which is part of
550 # the text fixture in order to verify correct operation of some of
551 # the user-defined SQL function APIs that are not used by the built-in
552 # functions.
554 set ::DB [sqlite3_connection_pointer db]
555 sqlite_register_test_function $::DB testfunc
556 do_test func-10.1 {
557   catchsql {
558     SELECT testfunc(NULL,NULL);
559   }
560 } {1 {first argument should be one of: int int64 string double null value}}
561 do_test func-10.2 {
562   execsql {
563     SELECT testfunc(
564      'string', 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ',
565      'int', 1234
566     );
567   }
568 } {1234}
569 do_test func-10.3 {
570   execsql {
571     SELECT testfunc(
572      'string', 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ',
573      'string', NULL
574     );
575   }
576 } {{}}
578 ifcapable floatingpoint {
579   do_test func-10.4 {
580     execsql {
581       SELECT testfunc(
582        'string', 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ',
583        'double', 1.234
584       );
585     }
586   } {1.234}
587   do_test func-10.5 {
588     execsql {
589       SELECT testfunc(
590        'string', 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ',
591        'int', 1234,
592        'string', 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ',
593        'string', NULL,
594        'string', 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ',
595        'double', 1.234,
596        'string', 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ',
597        'int', 1234,
598        'string', 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ',
599        'string', NULL,
600        'string', 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ',
601        'double', 1.234
602       );
603     }
604   } {1.234}
607 # Test the built-in sqlite_version(*) SQL function.
609 do_test func-11.1 {
610   execsql {
611     SELECT sqlite_version(*);
612   }
613 } [sqlite3 -version]
615 # Test that destructors passed to sqlite3 by calls to sqlite3_result_text()
616 # etc. are called. These tests use two special user-defined functions
617 # (implemented in func.c) only available in test builds. 
619 # Function test_destructor() takes one argument and returns a copy of the
620 # text form of that argument. A destructor is associated with the return
621 # value. Function test_destructor_count() returns the number of outstanding
622 # destructor calls for values returned by test_destructor().
624 if {[db eval {PRAGMA encoding}]=="UTF-8"} {
625   do_test func-12.1-utf8 {
626     execsql {
627       SELECT test_destructor('hello world'), test_destructor_count();
628     }
629   } {{hello world} 1}
630 } else {
631     ifcapable {utf16} {
632       do_test func-12.1-utf16 {
633         execsql {
634           SELECT test_destructor16('hello world'), test_destructor_count();
635         }
636       } {{hello world} 1}
637     }
639 do_test func-12.2 {
640   execsql {
641     SELECT test_destructor_count();
642   }
643 } {0}
644 do_test func-12.3 {
645   execsql {
646     SELECT test_destructor('hello')||' world'
647   }
648 } {{hello world}}
649 do_test func-12.4 {
650   execsql {
651     SELECT test_destructor_count();
652   }
653 } {0}
654 do_test func-12.5 {
655   execsql {
656     CREATE TABLE t4(x);
657     INSERT INTO t4 VALUES(test_destructor('hello'));
658     INSERT INTO t4 VALUES(test_destructor('world'));
659     SELECT min(test_destructor(x)), max(test_destructor(x)) FROM t4;
660   }
661 } {hello world}
662 do_test func-12.6 {
663   execsql {
664     SELECT test_destructor_count();
665   }
666 } {0}
667 do_test func-12.7 {
668   execsql {
669     DROP TABLE t4;
670   }
671 } {}
674 # Test that the auxdata API for scalar functions works. This test uses
675 # a special user-defined function only available in test builds,
676 # test_auxdata(). Function test_auxdata() takes any number of arguments.
677 do_test func-13.1 {
678   execsql {
679     SELECT test_auxdata('hello world');
680   }
681 } {0}
683 do_test func-13.2 {
684   execsql {
685     CREATE TABLE t4(a, b);
686     INSERT INTO t4 VALUES('abc', 'def');
687     INSERT INTO t4 VALUES('ghi', 'jkl');
688   }
689 } {}
690 do_test func-13.3 {
691   execsql {
692     SELECT test_auxdata('hello world') FROM t4;
693   }
694 } {0 1}
695 do_test func-13.4 {
696   execsql {
697     SELECT test_auxdata('hello world', 123) FROM t4;
698   }
699 } {{0 0} {1 1}}
700 do_test func-13.5 {
701   execsql {
702     SELECT test_auxdata('hello world', a) FROM t4;
703   }
704 } {{0 0} {1 0}}
705 do_test func-13.6 {
706   execsql {
707     SELECT test_auxdata('hello'||'world', a) FROM t4;
708   }
709 } {{0 0} {1 0}}
711 # Test that auxilary data is preserved between calls for SQL variables.
712 do_test func-13.7 {
713   set DB [sqlite3_connection_pointer db]
714   set sql "SELECT test_auxdata( ? , a ) FROM t4;"
715   set STMT [sqlite3_prepare $DB $sql -1 TAIL]
716   sqlite3_bind_text $STMT 1 hello\000 -1
717   set res [list]
718   while { "SQLITE_ROW"==[sqlite3_step $STMT] } {
719     lappend res [sqlite3_column_text $STMT 0]
720   }
721   lappend res [sqlite3_finalize $STMT]
722 } {{0 0} {1 0} SQLITE_OK}
724 # Test that auxiliary data is discarded when a statement is reset.
725 do_execsql_test 13.8.1 {
726   SELECT test_auxdata('constant') FROM t4;
727 } {0 1}
728 do_execsql_test 13.8.2 {
729   SELECT test_auxdata('constant') FROM t4;
730 } {0 1}
731 db cache flush
732 do_execsql_test 13.8.3 {
733   SELECT test_auxdata('constant') FROM t4;
734 } {0 1}
735 set V "one"
736 do_execsql_test 13.8.4 {
737   SELECT test_auxdata($V), $V FROM t4;
738 } {0 one 1 one}
739 set V "two"
740 do_execsql_test 13.8.5 {
741   SELECT test_auxdata($V), $V FROM t4;
742 } {0 two 1 two}
743 db cache flush
744 set V "three"
745 do_execsql_test 13.8.6 {
746   SELECT test_auxdata($V), $V FROM t4;
747 } {0 three 1 three}
750 # Make sure that a function with a very long name is rejected
751 do_test func-14.1 {
752   catch {
753     db function [string repeat X 254] {return "hello"}
754   } 
755 } {0}
756 do_test func-14.2 {
757   catch {
758     db function [string repeat X 256] {return "hello"}
759   }
760 } {1}
762 do_test func-15.1 {
763   catchsql {select test_error(NULL)}
764 } {1 {}}
765 do_test func-15.2 {
766   catchsql {select test_error('this is the error message')}
767 } {1 {this is the error message}}
768 do_test func-15.3 {
769   catchsql {select test_error('this is the error message',12)}
770 } {1 {this is the error message}}
771 do_test func-15.4 {
772   db errorcode
773 } {12}
775 # Test the quote function for BLOB and NULL values.
776 do_test func-16.1 {
777   execsql {
778     CREATE TABLE tbl2(a, b);
779   }
780   set STMT [sqlite3_prepare $::DB "INSERT INTO tbl2 VALUES(?, ?)" -1 TAIL]
781   sqlite3_bind_blob $::STMT 1 abc 3
782   sqlite3_step $::STMT
783   sqlite3_finalize $::STMT
784   execsql {
785     SELECT quote(a), quote(b) FROM tbl2;
786   }
787 } {X'616263' NULL}
789 # Test the quote function for +Inf and -Inf
790 do_execsql_test func-16.2 {
791   SELECT quote(4.2e+859), quote(-7.8e+904);
792 } {9.0e+999 -9.0e+999}
794 # Correctly handle function error messages that include %.  Ticket #1354
796 do_test func-17.1 {
797   proc testfunc1 args {error "Error %d with %s percents %p"}
798   db function testfunc1 ::testfunc1
799   catchsql {
800     SELECT testfunc1(1,2,3);
801   }
802 } {1 {Error %d with %s percents %p}}
804 # The SUM function should return integer results when all inputs are integer.
806 do_test func-18.1 {
807   execsql {
808     CREATE TABLE t5(x);
809     INSERT INTO t5 VALUES(1);
810     INSERT INTO t5 VALUES(-99);
811     INSERT INTO t5 VALUES(10000);
812     SELECT sum(x) FROM t5;
813   }
814 } {9902}
815 ifcapable floatingpoint {
816   do_test func-18.2 {
817     execsql {
818       INSERT INTO t5 VALUES(0.0);
819       SELECT sum(x) FROM t5;
820     }
821   } {9902.0}
824 # The sum of nothing is NULL.  But the sum of all NULLs is NULL.
826 # The TOTAL of nothing is 0.0.
828 do_test func-18.3 {
829   execsql {
830     DELETE FROM t5;
831     SELECT sum(x), total(x) FROM t5;
832   }
833 } {{} 0.0}
834 do_test func-18.4 {
835   execsql {
836     INSERT INTO t5 VALUES(NULL);
837     SELECT sum(x), total(x) FROM t5
838   }
839 } {{} 0.0}
840 do_test func-18.5 {
841   execsql {
842     INSERT INTO t5 VALUES(NULL);
843     SELECT sum(x), total(x) FROM t5
844   }
845 } {{} 0.0}
846 do_test func-18.6 {
847   execsql {
848     INSERT INTO t5 VALUES(123);
849     SELECT sum(x), total(x) FROM t5
850   }
851 } {123 123.0}
853 # Ticket #1664, #1669, #1670, #1674: An integer overflow on SUM causes
854 # an error. The non-standard TOTAL() function continues to give a helpful
855 # result.
857 do_test func-18.10 {
858   execsql {
859     CREATE TABLE t6(x INTEGER);
860     INSERT INTO t6 VALUES(1);
861     INSERT INTO t6 VALUES(1<<62);
862     SELECT sum(x) - ((1<<62)+1) from t6;
863   }
864 } 0
865 do_test func-18.11 {
866   execsql {
867     SELECT typeof(sum(x)) FROM t6
868   }
869 } integer
870 ifcapable floatingpoint {
871   do_catchsql_test func-18.12 {
872     INSERT INTO t6 VALUES(1<<62);
873     SELECT sum(x) - ((1<<62)*2.0+1) from t6;
874   } {1 {integer overflow}}
875   do_catchsql_test func-18.13 {
876     SELECT total(x) - ((1<<62)*2.0+1) FROM t6
877   } {0 0.0}
879 if {[working_64bit_int]} {
880   do_test func-18.14 {
881     execsql {
882       SELECT sum(-9223372036854775805);
883     }
884   } -9223372036854775805
886 ifcapable compound&&subquery {
888 do_test func-18.15 {
889   catchsql {
890     SELECT sum(x) FROM 
891        (SELECT 9223372036854775807 AS x UNION ALL
892         SELECT 10 AS x);
893   }
894 } {1 {integer overflow}}
895 if {[working_64bit_int]} {
896   do_test func-18.16 {
897     catchsql {
898       SELECT sum(x) FROM 
899          (SELECT 9223372036854775807 AS x UNION ALL
900           SELECT -10 AS x);
901     }
902   } {0 9223372036854775797}
903   do_test func-18.17 {
904     catchsql {
905       SELECT sum(x) FROM 
906          (SELECT -9223372036854775807 AS x UNION ALL
907           SELECT 10 AS x);
908     }
909   } {0 -9223372036854775797}
911 do_test func-18.18 {
912   catchsql {
913     SELECT sum(x) FROM 
914        (SELECT -9223372036854775807 AS x UNION ALL
915         SELECT -10 AS x);
916   }
917 } {1 {integer overflow}}
918 do_test func-18.19 {
919   catchsql {
920     SELECT sum(x) FROM (SELECT 9 AS x UNION ALL SELECT -10 AS x);
921   }
922 } {0 -1}
923 do_test func-18.20 {
924   catchsql {
925     SELECT sum(x) FROM (SELECT -9 AS x UNION ALL SELECT 10 AS x);
926   }
927 } {0 1}
928 do_test func-18.21 {
929   catchsql {
930     SELECT sum(x) FROM (SELECT -10 AS x UNION ALL SELECT 9 AS x);
931   }
932 } {0 -1}
933 do_test func-18.22 {
934   catchsql {
935     SELECT sum(x) FROM (SELECT 10 AS x UNION ALL SELECT -9 AS x);
936   }
937 } {0 1}
939 } ;# ifcapable compound&&subquery
941 # Integer overflow on abs()
943 if {[working_64bit_int]} {
944   do_test func-18.31 {
945     catchsql {
946       SELECT abs(-9223372036854775807);
947     }
948   } {0 9223372036854775807}
950 do_test func-18.32 {
951   catchsql {
952     SELECT abs(-9223372036854775807-1);
953   }
954 } {1 {integer overflow}}
956 # The MATCH function exists but is only a stub and always throws an error.
958 do_test func-19.1 {
959   execsql {
960     SELECT match(a,b) FROM t1 WHERE 0;
961   }
962 } {}
963 do_test func-19.2 {
964   catchsql {
965     SELECT 'abc' MATCH 'xyz';
966   }
967 } {1 {unable to use function MATCH in the requested context}}
968 do_test func-19.3 {
969   catchsql {
970     SELECT 'abc' NOT MATCH 'xyz';
971   }
972 } {1 {unable to use function MATCH in the requested context}}
973 do_test func-19.4 {
974   catchsql {
975     SELECT match(1,2,3);
976   }
977 } {1 {wrong number of arguments to function match()}}
979 # Soundex tests.
981 if {![catch {db eval {SELECT soundex('hello')}}]} {
982   set i 0
983   foreach {name sdx} {
984     euler        E460
985     EULER        E460
986     Euler        E460
987     ellery       E460
988     gauss        G200
989     ghosh        G200
990     hilbert      H416
991     Heilbronn    H416
992     knuth        K530
993     kant         K530
994     Lloyd        L300
995     LADD         L300
996     Lukasiewicz  L222
997     Lissajous    L222
998     A            A000
999     12345        ?000
1000   } {
1001     incr i
1002     do_test func-20.$i {
1003       execsql {SELECT soundex($name)}
1004     } $sdx
1005   }
1008 # Tests of the REPLACE function.
1010 do_test func-21.1 {
1011   catchsql {
1012     SELECT replace(1,2);
1013   }
1014 } {1 {wrong number of arguments to function replace()}}
1015 do_test func-21.2 {
1016   catchsql {
1017     SELECT replace(1,2,3,4);
1018   }
1019 } {1 {wrong number of arguments to function replace()}}
1020 do_test func-21.3 {
1021   execsql {
1022     SELECT typeof(replace('This is the main test string', NULL, 'ALT'));
1023   }
1024 } {null}
1025 do_test func-21.4 {
1026   execsql {
1027     SELECT typeof(replace(NULL, 'main', 'ALT'));
1028   }
1029 } {null}
1030 do_test func-21.5 {
1031   execsql {
1032     SELECT typeof(replace('This is the main test string', 'main', NULL));
1033   }
1034 } {null}
1035 do_test func-21.6 {
1036   execsql {
1037     SELECT replace('This is the main test string', 'main', 'ALT');
1038   }
1039 } {{This is the ALT test string}}
1040 do_test func-21.7 {
1041   execsql {
1042     SELECT replace('This is the main test string', 'main', 'larger-main');
1043   }
1044 } {{This is the larger-main test string}}
1045 do_test func-21.8 {
1046   execsql {
1047     SELECT replace('aaaaaaa', 'a', '0123456789');
1048   }
1049 } {0123456789012345678901234567890123456789012345678901234567890123456789}
1050 do_execsql_test func-21.9 {
1051   SELECT typeof(replace(1,'',0));
1052 } {text}
1054 ifcapable tclvar {
1055   do_test func-21.9 {
1056     # Attempt to exploit a buffer-overflow that at one time existed 
1057     # in the REPLACE function. 
1058     set ::str "[string repeat A 29998]CC[string repeat A 35537]"
1059     set ::rep [string repeat B 65536]
1060     execsql {
1061       SELECT LENGTH(REPLACE($::str, 'C', $::rep));
1062     }
1063   } [expr 29998 + 2*65536 + 35537]
1066 # Tests for the TRIM, LTRIM and RTRIM functions.
1068 do_test func-22.1 {
1069   catchsql {SELECT trim(1,2,3)}
1070 } {1 {wrong number of arguments to function trim()}}
1071 do_test func-22.2 {
1072   catchsql {SELECT ltrim(1,2,3)}
1073 } {1 {wrong number of arguments to function ltrim()}}
1074 do_test func-22.3 {
1075   catchsql {SELECT rtrim(1,2,3)}
1076 } {1 {wrong number of arguments to function rtrim()}}
1077 do_test func-22.4 {
1078   execsql {SELECT trim('  hi  ');}
1079 } {hi}
1080 do_test func-22.5 {
1081   execsql {SELECT ltrim('  hi  ');}
1082 } {{hi  }}
1083 do_test func-22.6 {
1084   execsql {SELECT rtrim('  hi  ');}
1085 } {{  hi}}
1086 do_test func-22.7 {
1087   execsql {SELECT trim('  hi  ','xyz');}
1088 } {{  hi  }}
1089 do_test func-22.8 {
1090   execsql {SELECT ltrim('  hi  ','xyz');}
1091 } {{  hi  }}
1092 do_test func-22.9 {
1093   execsql {SELECT rtrim('  hi  ','xyz');}
1094 } {{  hi  }}
1095 do_test func-22.10 {
1096   execsql {SELECT trim('xyxzy  hi  zzzy','xyz');}
1097 } {{  hi  }}
1098 do_test func-22.11 {
1099   execsql {SELECT ltrim('xyxzy  hi  zzzy','xyz');}
1100 } {{  hi  zzzy}}
1101 do_test func-22.12 {
1102   execsql {SELECT rtrim('xyxzy  hi  zzzy','xyz');}
1103 } {{xyxzy  hi  }}
1104 do_test func-22.13 {
1105   execsql {SELECT trim('  hi  ','');}
1106 } {{  hi  }}
1107 if {[db one {PRAGMA encoding}]=="UTF-8"} {
1108   do_test func-22.14 {
1109     execsql {SELECT hex(trim(x'c280e1bfbff48fbfbf6869',x'6162e1bfbfc280'))}
1110   } {F48FBFBF6869}
1111   do_test func-22.15 {
1112     execsql {SELECT hex(trim(x'6869c280e1bfbff48fbfbf61',
1113                              x'6162e1bfbfc280f48fbfbf'))}
1114   } {6869}
1115   do_test func-22.16 {
1116     execsql {SELECT hex(trim(x'ceb1ceb2ceb3',x'ceb1'));}
1117   } {CEB2CEB3}
1119 do_test func-22.20 {
1120   execsql {SELECT typeof(trim(NULL));}
1121 } {null}
1122 do_test func-22.21 {
1123   execsql {SELECT typeof(trim(NULL,'xyz'));}
1124 } {null}
1125 do_test func-22.22 {
1126   execsql {SELECT typeof(trim('hello',NULL));}
1127 } {null}
1129 # 2021-06-15 - infinite loop due to unsigned character counter
1130 # overflow, reported by Zimuzo Ezeozue
1132 do_execsql_test func-22.23 {
1133   SELECT trim('xyzzy',x'c0808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080808080');
1134 } {xyzzy}
1136 # This is to test the deprecated sqlite3_aggregate_count() API.
1138 ifcapable deprecated {
1139   do_test func-23.1 {
1140     sqlite3_create_aggregate db
1141     execsql {
1142       SELECT legacy_count() FROM t6;
1143     }
1144   } {3}
1147 # The group_concat() and string_agg() functions.
1149 do_test func-24.1 {
1150   execsql {
1151     SELECT group_concat(t1), string_agg(t1,',') FROM tbl1
1152   }
1153 } {this,program,is,free,software this,program,is,free,software}
1154 do_test func-24.2 {
1155   execsql {
1156     SELECT group_concat(t1,' '), string_agg(t1,' ') FROM tbl1
1157   }
1158 } {{this program is free software} {this program is free software}}
1159 do_test func-24.3 {
1160   execsql {
1161     SELECT group_concat(t1,' ' || rowid || ' ') FROM tbl1
1162   }
1163 } {{this 2 program 3 is 4 free 5 software}}
1164 do_test func-24.4 {
1165   execsql {
1166     SELECT group_concat(NULL,t1) FROM tbl1
1167   }
1168 } {{}}
1169 do_test func-24.5 {
1170   execsql {
1171     SELECT group_concat(t1,NULL), string_agg(t1,NULL) FROM tbl1
1172   }
1173 } {thisprogramisfreesoftware thisprogramisfreesoftware}
1174 do_test func-24.6 {
1175   execsql {
1176     SELECT 'BEGIN-'||group_concat(t1) FROM tbl1
1177   }
1178 } {BEGIN-this,program,is,free,software}
1180 # Ticket #3179:  Make sure aggregate functions can take many arguments.
1181 # None of the built-in aggregates do this, so use the md5sum() from the
1182 # test extensions.
1184 unset -nocomplain midargs
1185 set midargs {}
1186 unset -nocomplain midres
1187 set midres {}
1188 unset -nocomplain result
1189 for {set i 1} {$i<[sqlite3_limit db SQLITE_LIMIT_FUNCTION_ARG -1]} {incr i} {
1190   append midargs ,'/$i'
1191   append midres /$i
1192   set result [md5 \
1193      "this${midres}program${midres}is${midres}free${midres}software${midres}"]
1194   set sql "SELECT md5sum(t1$midargs) FROM tbl1"
1195   do_test func-24.7.$i {
1196      db eval $::sql
1197   } $result
1200 # Ticket #3806.  If the initial string in a group_concat is an empty
1201 # string, the separator that follows should still be present.
1203 do_test func-24.8 {
1204   execsql {
1205     SELECT group_concat(CASE t1 WHEN 'this' THEN '' ELSE t1 END) FROM tbl1
1206   }
1207 } {,program,is,free,software}
1208 do_test func-24.9 {
1209   execsql {
1210     SELECT group_concat(CASE WHEN t1!='software' THEN '' ELSE t1 END) FROM tbl1
1211   }
1212 } {,,,,software}
1214 # Ticket #3923.  Initial empty strings have a separator.  But initial
1215 # NULLs do not.
1217 do_test func-24.10 {
1218   execsql {
1219     SELECT group_concat(CASE t1 WHEN 'this' THEN null ELSE t1 END) FROM tbl1
1220   }
1221 } {program,is,free,software}
1222 do_test func-24.11 {
1223   execsql {
1224    SELECT group_concat(CASE WHEN t1!='software' THEN null ELSE t1 END) FROM tbl1
1225   }
1226 } {software}
1227 do_test func-24.12 {
1228   execsql {
1229     SELECT group_concat(CASE t1 WHEN 'this' THEN ''
1230                           WHEN 'program' THEN null ELSE t1 END) FROM tbl1
1231   }
1232 } {,is,free,software}
1233 # Tests to verify ticket http://www.sqlite.org/src/tktview/55746f9e65f8587c0
1234 do_test func-24.13 {
1235   execsql {
1236     SELECT typeof(group_concat(x)) FROM (SELECT '' AS x);
1237   }
1238 } {text}
1239 do_test func-24.14 {
1240   execsql {
1241     SELECT typeof(group_concat(x,''))
1242       FROM (SELECT '' AS x UNION ALL SELECT '');
1243   }
1244 } {text}
1247 # Use the test_isolation function to make sure that type conversions
1248 # on function arguments do not effect subsequent arguments.
1250 do_test func-25.1 {
1251   execsql {SELECT test_isolation(t1,t1) FROM tbl1}
1252 } {this program is free software}
1254 # Try to misuse the sqlite3_create_function() interface.  Verify that
1255 # errors are returned.
1257 do_test func-26.1 {
1258   abuse_create_function db
1259 } {}
1261 # The previous test (func-26.1) registered a function with a very long
1262 # function name that takes many arguments and always returns NULL.  Verify
1263 # that this function works correctly.
1265 do_test func-26.2 {
1266   set a {}
1267   for {set i 1} {$i<=$::SQLITE_MAX_FUNCTION_ARG} {incr i} {
1268     lappend a $i
1269   }
1270   db eval "
1271      SELECT nullx_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789([join $a ,]);
1272   "
1273 } {{}}
1274 do_test func-26.3 {
1275   set a {}
1276   for {set i 1} {$i<=$::SQLITE_MAX_FUNCTION_ARG+1} {incr i} {
1277     lappend a $i
1278   }
1279   catchsql "
1280      SELECT nullx_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789([join $a ,]);
1281   "
1282 } {1 {too many arguments on function nullx_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789}}
1283 do_test func-26.4 {
1284   set a {}
1285   for {set i 1} {$i<=$::SQLITE_MAX_FUNCTION_ARG-1} {incr i} {
1286     lappend a $i
1287   }
1288   catchsql "
1289      SELECT nullx_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789([join $a ,]);
1290   "
1291 } {1 {wrong number of arguments to function nullx_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789()}}
1292 do_test func-26.5 {
1293   catchsql "
1294      SELECT nullx_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_12345678a(0);
1295   "
1296 } {1 {no such function: nullx_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_12345678a}}
1297 do_test func-26.6 {
1298   catchsql "
1299      SELECT nullx_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789a(0);
1300   "
1301 } {1 {no such function: nullx_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789_123456789a}}
1303 do_test func-27.1 {
1304   catchsql {SELECT coalesce()}
1305 } {1 {wrong number of arguments to function coalesce()}}
1306 do_test func-27.2 {
1307   catchsql {SELECT coalesce(1)}
1308 } {1 {wrong number of arguments to function coalesce()}}
1309 do_test func-27.3 {
1310   catchsql {SELECT coalesce(1,2)}
1311 } {0 1}
1313 # Ticket 2d401a94287b5
1314 # Unknown function in a DEFAULT expression causes a segfault.
1316 do_test func-28.1 {
1317   db eval {
1318     CREATE TABLE t28(x, y DEFAULT(nosuchfunc(1)));
1319   }
1320   catchsql {
1321     INSERT INTO t28(x) VALUES(1);
1322   }
1323 } {1 {unknown function: nosuchfunc()}}
1325 # Verify that the length() and typeof() functions do not actually load
1326 # the content of their argument.
1328 do_test func-29.1 {
1329   db eval {
1330     CREATE TABLE t29(id INTEGER PRIMARY KEY, x, y);
1331     INSERT INTO t29 VALUES(1, 2, 3), (2, NULL, 4), (3, 4.5, 5);
1332     INSERT INTO t29 VALUES(4, randomblob(1000000), 6);
1333     INSERT INTO t29 VALUES(5, 'hello', 7);
1334   }
1335   db close
1336   sqlite3 db test.db
1337   sqlite3_db_status db CACHE_MISS 1
1338   db eval {SELECT typeof(x), length(x), typeof(y) FROM t29 ORDER BY id}
1339 } {integer 1 integer null {} integer real 3 integer blob 1000000 integer text 5 integer}
1340 do_test func-29.2 {
1341   set x [lindex [sqlite3_db_status db CACHE_MISS 1] 1]
1342   if {$x<5} {set x 1}
1343   set x
1344 } {1}
1345 do_test func-29.3 {
1346   db close
1347   sqlite3 db test.db
1348   sqlite3_db_status db CACHE_MISS 1
1349   db eval {SELECT typeof(+x) FROM t29 ORDER BY id}
1350 } {integer null real blob text}
1351 if {[permutation] != "mmap"} {
1352   ifcapable !direct_read {
1353     do_test func-29.4 {
1354       set x [lindex [sqlite3_db_status db CACHE_MISS 1] 1]
1355       if {$x>100} {set x many}
1356       set x
1357     } {many}
1358   }
1360 do_test func-29.5 {
1361   db close
1362   sqlite3 db test.db
1363   sqlite3_db_status db CACHE_MISS 1
1364   db eval {SELECT sum(length(x)) FROM t29}
1365 } {1000009}
1366 do_test func-29.6 {
1367   set x [lindex [sqlite3_db_status db CACHE_MISS 1] 1]
1368   if {$x<5} {set x 1}
1369   set x
1370 } {1}
1372 # The OP_Column opcode has an optimization that avoids loading content
1373 # for fields with content-length=0 when the content offset is on an overflow
1374 # page.  Make sure the optimization works.
1376 do_execsql_test func-29.10 {
1377   CREATE TABLE t29b(a,b,c,d,e,f,g,h,i);
1378   INSERT INTO t29b 
1379    VALUES(1, hex(randomblob(2000)), null, 0, 1, '', zeroblob(0),'x',x'01');
1380   SELECT typeof(c), typeof(d), typeof(e), typeof(f),
1381          typeof(g), typeof(h), typeof(i) FROM t29b;
1382 } {null integer integer text blob text blob}
1383 do_execsql_test func-29.11 {
1384   SELECT length(f), length(g), length(h), length(i) FROM t29b;
1385 } {0 0 1 1}
1386 do_execsql_test func-29.12 {
1387   SELECT quote(f), quote(g), quote(h), quote(i) FROM t29b;
1388 } {'' X'' 'x' X'01'}
1390 # EVIDENCE-OF: R-29701-50711 The unicode(X) function returns the numeric
1391 # unicode code point corresponding to the first character of the string
1392 # X.
1394 # EVIDENCE-OF: R-55469-62130 The char(X1,X2,...,XN) function returns a
1395 # string composed of characters having the unicode code point values of
1396 # integers X1 through XN, respectively.
1398 do_execsql_test func-30.1 {SELECT unicode('$');} 36
1399 do_execsql_test func-30.2 [subst {SELECT unicode('\u00A2');}] 162
1400 do_execsql_test func-30.3 [subst {SELECT unicode('\u20AC');}] 8364
1401 do_execsql_test func-30.4 {SELECT char(36,162,8364);} [subst {$\u00A2\u20AC}]
1403 for {set i 1} {$i<0xd800} {incr i 13} {
1404   do_execsql_test func-30.5.$i {SELECT unicode(char($i))} $i
1406 for {set i 57344} {$i<=0xfffd} {incr i 17} {
1407   if {$i==0xfeff} continue
1408   do_execsql_test func-30.5.$i {SELECT unicode(char($i))} $i
1410 for {set i 65536} {$i<=0x10ffff} {incr i 139} {
1411   do_execsql_test func-30.5.$i {SELECT unicode(char($i))} $i
1414 # Test char().
1416 do_execsql_test func-31.1 { 
1417   SELECT char(), length(char()), typeof(char()) 
1418 } {{} 0 text}
1420 # sqlite3_value_frombind()
1422 do_execsql_test func-32.100 {
1423   SELECT test_frombind(1,2,3,4);
1424 } {0}
1425 do_execsql_test func-32.110 {
1426   SELECT test_frombind(1,2,?,4);
1427 } {4}
1428 do_execsql_test func-32.120 {
1429   SELECT test_frombind(1,(?),4,?+7);
1430 } {2}
1431 do_execsql_test func-32.130 {
1432   DROP TABLE IF EXISTS t1;
1433   CREATE TABLE t1(a,b,c,e,f);
1434   INSERT INTO t1 VALUES(1,2.5,'xyz',x'e0c1b2a3',null);
1435   SELECT test_frombind(a,b,c,e,f,$xyz) FROM t1;
1436 } {32}
1437 do_execsql_test func-32.140 {
1438   SELECT test_frombind(a,b,c,e,f,$xyz+f) FROM t1;
1439 } {0}
1440 do_execsql_test func-32.150 {
1441   SELECT test_frombind(x.a,y.b,x.c,:123,y.e,x.f,$xyz+y.f) FROM t1 x, t1 y;
1442 } {8}
1444 # 2019-08-15
1445 # Direct-only functions.
1447 proc testdirectonly {x} {return [expr {$x*2}]}
1448 do_test func-33.1 {
1449   db func testdirectonly -directonly testdirectonly
1450   db eval {SELECT testdirectonly(15)}
1451 } {30}
1452 do_catchsql_test func-33.2 {
1453   CREATE VIEW v33(y) AS SELECT testdirectonly(15);
1454   SELECT * FROM v33;
1455 } {1 {unsafe use of testdirectonly()}}
1456 do_execsql_test func-33.3 {
1457   SELECT * FROM (SELECT testdirectonly(15)) AS v33;
1458 } {30}
1459 do_execsql_test func-33.4 {
1460   WITH c(x) AS (SELECT testdirectonly(15))
1461   SELECT * FROM c;
1462 } {30}
1463 do_catchsql_test func-33.5 {
1464   WITH c(x) AS (SELECT * FROM v33)
1465   SELECT * FROM c;
1466 } {1 {unsafe use of testdirectonly()}}
1467 do_execsql_test func-33.10 {
1468   CREATE TABLE t33a(a,b);
1469   CREATE TABLE t33b(x,y);
1470   CREATE TRIGGER r1 AFTER INSERT ON t33a BEGIN
1471     INSERT INTO t33b(x,y) VALUES(testdirectonly(new.a),new.b);
1472   END;
1473 } {}
1474 do_catchsql_test func-33.11 {
1475   INSERT INTO t33a VALUES(1,2);
1476 } {1 {unsafe use of testdirectonly()}}
1478 ifcapable altertable {
1479 do_execsql_test func-33.20 {
1480   ALTER TABLE t33a RENAME COLUMN a TO aaa;
1481   SELECT sql FROM sqlite_master WHERE name='r1';
1482 } {{CREATE TRIGGER r1 AFTER INSERT ON t33a BEGIN
1483     INSERT INTO t33b(x,y) VALUES(testdirectonly(new.aaa),new.b);
1484   END}}
1487 # 2020-01-09 Yongheng fuzzer find
1488 # The bug is in the register-validity debug logic, not in the SQLite core
1489 # and as such it only impacts debug builds.  Release builds work fine.
1491 reset_db
1492 do_execsql_test func-34.10 {
1493   CREATE TABLE t1(a INT CHECK(
1494      datetime( 0, 1, 2, 3, 4, 5, 6, 7, 8, 9,
1495               10,11,12,13,14,15,16,17,18,19,
1496               20,21,22,23,24,25,26,27,28,29,
1497               30,31,32,33,34,35,36,37,38,39,
1498               40,41,42,43,44,45,46,47,48,a)
1499    )
1500   );
1501   INSERT INTO t1(a) VALUES(1),(2);
1502   SELECT * FROM t1;
1503 } {1 2}
1505 # 2020-03-11 COALESCE() should short-circuit
1506 # See also ticket 3c9eadd2a6ba0aa5
1507 # Both issues stem from the fact that functions that could
1508 # throw exceptions were being factored out into initialization
1509 # code.  The fix was to put those function calls inside of
1510 # OP_Once instead.
1512 reset_db
1513 do_execsql_test func-35.100 {
1514   CREATE TABLE t1(x);
1515   SELECT coalesce(x, abs(-9223372036854775808)) FROM t1;
1516 } {}
1517 do_execsql_test func-35.110 {
1518   SELECT coalesce(x, 'xyz' LIKE printf('%.1000000c','y')) FROM t1;
1519 } {}
1520 do_execsql_test func-35.200 {
1521   CREATE TABLE t0(c0 CHECK(ABS(-9223372036854775808)));
1522   PRAGMA integrity_check;
1523 } {ok}
1525 # 2021-01-07:  The -> and ->> operators.
1527 proc ptr1 {a b} { return "$a->$b" }
1528 db func -> ptr1
1529 proc ptr2 {a b} { return "$a->>$b" }
1530 db func ->> ptr2
1531 do_execsql_test func-36.100 {
1532   SELECT 123 -> 456
1533 } {123->456}
1534 do_execsql_test func-36.110 {
1535   SELECT 123 ->> 456
1536 } {123->>456}
1538 # 2023-06-26
1539 # Enhanced precision of SUM().
1541 reset_db
1542 do_catchsql_test func-37.100 {
1543   WITH c(x) AS (VALUES(9223372036854775807),(9223372036854775807),
1544                       (123),(-9223372036854775807),(-9223372036854775807))
1545   SELECT sum(x) FROM c;
1546 } {1 {integer overflow}}
1547 do_catchsql_test func-37.110 {
1548   WITH c(x) AS (VALUES(9223372036854775807),(1))
1549   SELECT sum(x) FROM c;
1550 } {1 {integer overflow}}
1551 do_catchsql_test func-37.120 {
1552   WITH c(x) AS (VALUES(9223372036854775807),(10000),(-10010))
1553   SELECT sum(x) FROM c;
1554 } {1 {integer overflow}}
1556 # 2023-08-28 forum post https://sqlite.org/forum/forumpost/1c06ddcacc86032a
1557 # Incorrect handling of infinity by SUM().
1559 do_execsql_test func-38.100 {
1560   WITH t1(x) AS (VALUES(9e+999)) SELECT sum(x), avg(x), total(x) FROM t1;
1561   WITH t1(x) AS (VALUES(-9e+999)) SELECT sum(x), avg(x), total(x) FROM t1;
1562 } {Inf Inf Inf -Inf -Inf -Inf}
1564 # 2024-03-21 https://sqlite.org/forum/forumpost/23b8688ef4
1565 # Another problem with Kahan-Babushka-Neumaier summation and
1566 # infinities.
1568 do_execsql_test func-39.101 {
1569   WITH RECURSIVE c(n) AS (VALUES(1) UNION ALL SELECT n+1 FROM c WHERE n<1)
1570   SELECT sum(1.7976931348623157e308),
1571          avg(1.7976931348623157e308),
1572          total(1.7976931348623157e308)
1573     FROM c;
1574 } {1.79769313486232e+308 1.79769313486232e+308 1.79769313486232e+308}
1575 for {set i 2} {$i<10} {incr i} {
1576   do_execsql_test func-39.[expr {10*$i+100}] {
1577     WITH RECURSIVE c(n) AS (VALUES(1) UNION ALL SELECT n+1 FROM c WHERE n<$i)
1578     SELECT sum(1.7976931348623157e308),
1579            avg(1.7976931348623157e308),
1580            total(1.7976931348623157e308)
1581       FROM c;
1582   } {Inf Inf Inf}
1585 finish_test