aboutsummaryrefslogtreecommitdiff
path: root/test/sort.test
diff options
context:
space:
mode:
authordrh <drh@noemail.net>2014-09-02 15:49:47 +0000
committerdrh <drh@noemail.net>2014-09-02 15:49:47 +0000
commitbf9ed6f9af8db145efb7294b1bb05b35fc70e7fc (patch)
tree870d850426bb945aee018a2dc2612f52f3248619 /test/sort.test
parente1ed0b0e1787b0e5c6b2b59de4e2f161a82bec22 (diff)
parentf8ede57a6165889316f8a9df8ac1166c7a568100 (diff)
downloadsqlite-bf9ed6f9af8db145efb7294b1bb05b35fc70e7fc.tar.gz
sqlite-bf9ed6f9af8db145efb7294b1bb05b35fc70e7fc.zip
Merge the latest trunk changes, including the multi-threaded sorter, into
the sessions branch. FossilOrigin-Name: d4cce2c71e64ab7b6a65a81b88b69445ed859351
Diffstat (limited to 'test/sort.test')
-rw-r--r--test/sort.test175
1 files changed, 173 insertions, 2 deletions
diff --git a/test/sort.test b/test/sort.test
index 08d496b25..1c89552bb 100644
--- a/test/sort.test
+++ b/test/sort.test
@@ -8,10 +8,10 @@
# May you share freely, never taking more than you give.
#
#***********************************************************************
+#
# This file implements regression tests for SQLite library. The
-# focus of this file is testing the CREATE TABLE statement.
+# focus of this file is testing the sorter (code in vdbesort.c).
#
-# $Id: sort.test,v 1.25 2005/11/14 22:29:06 drh Exp $
set testdir [file dirname $argv0]
source $testdir/tester.tcl
@@ -464,4 +464,175 @@ do_test sort-12.1 {
}
} {1 2 xxx 1 3 yyy 1 1 zzz}
+#-------------------------------------------------------------------------
+# Check that the sorter in vdbesort.c sorts in a stable fashion.
+#
+do_execsql_test sort-13.0 {
+ CREATE TABLE t10(a, b);
+}
+do_test sort-13.1 {
+ db transaction {
+ for {set i 0} {$i < 100000} {incr i} {
+ execsql { INSERT INTO t10 VALUES( $i/10, $i%10 ) }
+ }
+ }
+} {}
+do_execsql_test sort-13.2 {
+ SELECT a, b FROM t10 ORDER BY a;
+} [db eval {SELECT a, b FROM t10 ORDER BY a, b}]
+do_execsql_test sort-13.3 {
+ PRAGMA cache_size = 5;
+ SELECT a, b FROM t10 ORDER BY a;
+} [db eval {SELECT a, b FROM t10 ORDER BY a, b}]
+
+#-------------------------------------------------------------------------
+# Sort some large ( > 4KiB) records.
+#
+proc cksum {x} {
+ set i1 1
+ set i2 2
+ binary scan $x c* L
+ foreach {a b} $L {
+ set i1 [expr (($i2<<3) + $a) & 0x7FFFFFFF]
+ set i2 [expr (($i1<<3) + $b) & 0x7FFFFFFF]
+ }
+ list $i1 $i2
+}
+db func cksum cksum
+
+do_execsql_test sort-14.0 {
+ PRAGMA cache_size = 5;
+ CREATE TABLE t11(a, b);
+ INSERT INTO t11 VALUES(randomblob(5000), NULL);
+ INSERT INTO t11 SELECT randomblob(5000), NULL FROM t11; --2
+ INSERT INTO t11 SELECT randomblob(5000), NULL FROM t11; --3
+ INSERT INTO t11 SELECT randomblob(5000), NULL FROM t11; --4
+ INSERT INTO t11 SELECT randomblob(5000), NULL FROM t11; --5
+ INSERT INTO t11 SELECT randomblob(5000), NULL FROM t11; --6
+ INSERT INTO t11 SELECT randomblob(5000), NULL FROM t11; --7
+ INSERT INTO t11 SELECT randomblob(5000), NULL FROM t11; --8
+ INSERT INTO t11 SELECT randomblob(5000), NULL FROM t11; --9
+ UPDATE t11 SET b = cksum(a);
+}
+
+foreach {tn mmap_limit} {
+ 1 0
+ 2 1000000
+} {
+ do_test sort-14.$tn {
+ sqlite3_test_control SQLITE_TESTCTRL_SORTER_MMAP db $mmap_limit
+ set prev ""
+ db eval { SELECT * FROM t11 ORDER BY b } {
+ if {$b != [cksum $a]} {error "checksum failed"}
+ if {[string compare $b $prev] < 0} {error "sort failed"}
+ set prev $b
+ }
+ set {} {}
+ } {}
+}
+
+#-------------------------------------------------------------------------
+#
+foreach {tn mmap_limit nWorker tmpstore coremutex fakeheap softheaplimit} {
+ 1 0 3 file true false 0
+ 2 0 3 file true true 0
+ 3 0 0 file true false 0
+ 4 1000000 3 file true false 0
+ 5 0 0 memory false true 0
+ 6 0 0 file false true 1000000
+ 7 0 0 file false true 10000
+} {
+ db close
+ sqlite3_shutdown
+ if {$coremutex} {
+ sqlite3_config multithread
+ } else {
+ sqlite3_config singlethread
+ }
+ sqlite3_initialize
+ sorter_test_fakeheap $fakeheap
+ sqlite3_soft_heap_limit $softheaplimit
+
+ reset_db
+ sqlite3_test_control SQLITE_TESTCTRL_SORTER_MMAP db $mmap_limit
+ execsql "PRAGMA temp_store = $tmpstore; PRAGMA threads = $nWorker"
+
+
+ set ten [string repeat X 10300]
+ set one [string repeat y 200]
+
+ if {$softheaplimit} {
+ execsql { PRAGMA cache_size = 20 };
+ } else {
+ execsql { PRAGMA cache_size = 5 };
+ }
+
+ do_execsql_test 15.$tn.1 {
+ WITH rr AS (
+ SELECT 4, $ten UNION ALL
+ SELECT 2, $one UNION ALL
+ SELECT 1, $ten UNION ALL
+ SELECT 3, $one
+ )
+ SELECT * FROM rr ORDER BY 1;
+ } [list 1 $ten 2 $one 3 $one 4 $ten]
+
+ do_execsql_test 15.$tn.2 {
+ CREATE TABLE t1(a);
+ INSERT INTO t1 VALUES(4);
+ INSERT INTO t1 VALUES(5);
+ INSERT INTO t1 VALUES(3);
+ INSERT INTO t1 VALUES(2);
+ INSERT INTO t1 VALUES(6);
+ INSERT INTO t1 VALUES(1);
+ CREATE INDEX i1 ON t1(a);
+ SELECT * FROM t1 ORDER BY a;
+ } {1 2 3 4 5 6}
+
+ do_execsql_test 15.$tn.3 {
+ WITH rr AS (
+ SELECT 4, $ten UNION ALL
+ SELECT 2, $one
+ )
+ SELECT * FROM rr ORDER BY 1;
+ } [list 2 $one 4 $ten]
+
+ sorter_test_fakeheap 0
+}
+
+db close
+sqlite3_shutdown
+set t(0) singlethread
+set t(1) multithread
+set t(2) serialized
+sqlite3_config $t($sqlite_options(threadsafe))
+sqlite3_initialize
+sqlite3_soft_heap_limit 0
+
+reset_db
+do_catchsql_test 16.1 {
+ CREATE TABLE t1(a, b, c);
+ INSERT INTO t1 VALUES(1, 2, 3);
+ INSERT INTO t1 VALUES(1, NULL, 3);
+ INSERT INTO t1 VALUES(NULL, 2, 3);
+ INSERT INTO t1 VALUES(1, 2, NULL);
+ INSERT INTO t1 VALUES(4, 5, 6);
+ CREATE UNIQUE INDEX i1 ON t1(b, a, c);
+} {0 {}}
+reset_db
+do_catchsql_test 16.2 {
+ CREATE TABLE t1(a, b, c);
+ INSERT INTO t1 VALUES(1, 2, 3);
+ INSERT INTO t1 VALUES(1, NULL, 3);
+ INSERT INTO t1 VALUES(1, 2, 3);
+ INSERT INTO t1 VALUES(1, 2, NULL);
+ INSERT INTO t1 VALUES(4, 5, 6);
+ CREATE UNIQUE INDEX i1 ON t1(b, a, c);
+} {1 {UNIQUE constraint failed: t1.b, t1.a, t1.c}}
+
+reset_db
+do_execsql_test 17.1 {
+ SELECT * FROM sqlite_master ORDER BY sql;
+} {}
+
finish_test