1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/os/persistentdata/persistentstorage/sqlite3api/TEST/TclScript/enc2.test Fri Jun 15 03:10:57 2012 +0200
1.3 @@ -0,0 +1,555 @@
1.4 +# 2002 May 24
1.5 +#
1.6 +# The author disclaims copyright to this source code. In place of
1.7 +# a legal notice, here is a blessing:
1.8 +#
1.9 +# May you do good and not evil.
1.10 +# May you find forgiveness for yourself and forgive others.
1.11 +# May you share freely, never taking more than you give.
1.12 +#
1.13 +#***********************************************************************
1.14 +# This file implements regression tests for SQLite library. The focus of
1.15 +# this file is testing the SQLite routines used for converting between the
1.16 +# various suported unicode encodings (UTF-8, UTF-16, UTF-16le and
1.17 +# UTF-16be).
1.18 +#
1.19 +# $Id: enc2.test,v 1.29 2007/10/09 08:29:32 danielk1977 Exp $
1.20 +
1.21 +set testdir [file dirname $argv0]
1.22 +source $testdir/tester.tcl
1.23 +
1.24 +# If UTF16 support is disabled, ignore the tests in this file
1.25 +#
1.26 +ifcapable {!utf16} {
1.27 + finish_test
1.28 + return
1.29 +}
1.30 +
1.31 +# The rough organisation of tests in this file is:
1.32 +#
1.33 +# enc2.1.*: Simple tests with a UTF-8 db.
1.34 +# enc2.2.*: Simple tests with a UTF-16LE db.
1.35 +# enc2.3.*: Simple tests with a UTF-16BE db.
1.36 +# enc2.4.*: Test that attached databases must have the same text encoding
1.37 +# as the main database.
1.38 +# enc2.5.*: Test the behaviour of the library when a collation sequence is
1.39 +# not available for the most desirable text encoding.
1.40 +# enc2.6.*: Similar test for user functions.
1.41 +# enc2.7.*: Test that the VerifyCookie opcode protects against assuming the
1.42 +# wrong text encoding for the database.
1.43 +# enc2.8.*: Test sqlite3_complete16()
1.44 +#
1.45 +
1.46 +db close
1.47 +
1.48 +# Return the UTF-8 representation of the supplied UTF-16 string $str.
1.49 +proc utf8 {str} {
1.50 + # If $str ends in two 0x00 0x00 bytes, knock these off before
1.51 + # converting to UTF-8 using TCL.
1.52 + binary scan $str \c* vals
1.53 + if {[lindex $vals end]==0 && [lindex $vals end-1]==0} {
1.54 + set str [binary format \c* [lrange $vals 0 end-2]]
1.55 + }
1.56 +
1.57 + set r [encoding convertfrom unicode $str]
1.58 + return $r
1.59 +}
1.60 +
1.61 +#
1.62 +# This proc contains all the tests in this file. It is run
1.63 +# three times. Each time the file 'test.db' contains a database
1.64 +# with the following contents:
1.65 +set dbcontents {
1.66 + CREATE TABLE t1(a PRIMARY KEY, b, c);
1.67 + INSERT INTO t1 VALUES('one', 'I', 1);
1.68 +}
1.69 +# This proc tests that we can open and manipulate the test.db
1.70 +# database, and that it is possible to retreive values in
1.71 +# various text encodings.
1.72 +#
1.73 +proc run_test_script {t enc} {
1.74 +
1.75 +# Open the database and pull out a (the) row.
1.76 +do_test $t.1 {
1.77 + sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.78 + execsql {SELECT * FROM t1}
1.79 +} {one I 1}
1.80 +
1.81 +# Insert some data
1.82 +do_test $t.2 {
1.83 + execsql {INSERT INTO t1 VALUES('two', 'II', 2);}
1.84 + execsql {SELECT * FROM t1}
1.85 +} {one I 1 two II 2}
1.86 +
1.87 +# Insert some data
1.88 +do_test $t.3 {
1.89 + execsql {
1.90 + INSERT INTO t1 VALUES('three','III',3);
1.91 + INSERT INTO t1 VALUES('four','IV',4);
1.92 + INSERT INTO t1 VALUES('five','V',5);
1.93 + }
1.94 + execsql {SELECT * FROM t1}
1.95 +} {one I 1 two II 2 three III 3 four IV 4 five V 5}
1.96 +
1.97 +# Use the index
1.98 +do_test $t.4 {
1.99 + execsql {
1.100 + SELECT * FROM t1 WHERE a = 'one';
1.101 + }
1.102 +} {one I 1}
1.103 +do_test $t.5 {
1.104 + execsql {
1.105 + SELECT * FROM t1 WHERE a = 'four';
1.106 + }
1.107 +} {four IV 4}
1.108 +ifcapable subquery {
1.109 + do_test $t.6 {
1.110 + execsql {
1.111 + SELECT * FROM t1 WHERE a IN ('one', 'two');
1.112 + }
1.113 + } {one I 1 two II 2}
1.114 +}
1.115 +
1.116 +# Now check that we can retrieve data in both UTF-16 and UTF-8
1.117 +do_test $t.7 {
1.118 + set STMT [sqlite3_prepare $DB "SELECT a FROM t1 WHERE c>3;" -1 TAIL]
1.119 + sqlite3_step $STMT
1.120 + sqlite3_column_text $STMT 0
1.121 +} {four}
1.122 +
1.123 +do_test $t.8 {
1.124 + sqlite3_step $STMT
1.125 + utf8 [sqlite3_column_text16 $STMT 0]
1.126 +} {five}
1.127 +
1.128 +do_test $t.9 {
1.129 + sqlite3_finalize $STMT
1.130 +} SQLITE_OK
1.131 +
1.132 +ifcapable vacuum {
1.133 + execsql VACUUM
1.134 +}
1.135 +
1.136 +do_test $t.10 {
1.137 + db eval {PRAGMA encoding}
1.138 +} $enc
1.139 +
1.140 +}
1.141 +
1.142 +# The three unicode encodings understood by SQLite.
1.143 +set encodings [list UTF-8 UTF-16le UTF-16be]
1.144 +
1.145 +set sqlite_os_trace 0
1.146 +set i 1
1.147 +foreach enc $encodings {
1.148 + file delete -force test.db
1.149 + sqlite3 db test.db
1.150 + db eval "PRAGMA encoding = \"$enc\""
1.151 + execsql $dbcontents
1.152 + do_test enc2-$i.0.1 {
1.153 + db eval {PRAGMA encoding}
1.154 + } $enc
1.155 + do_test enc2-$i.0.2 {
1.156 + db eval {PRAGMA encoding=UTF8}
1.157 + db eval {PRAGMA encoding}
1.158 + } $enc
1.159 + do_test enc2-$i.0.3 {
1.160 + db eval {PRAGMA encoding=UTF16le}
1.161 + db eval {PRAGMA encoding}
1.162 + } $enc
1.163 + do_test enc2-$i.0.4 {
1.164 + db eval {PRAGMA encoding=UTF16be}
1.165 + db eval {PRAGMA encoding}
1.166 + } $enc
1.167 +
1.168 + db close
1.169 + run_test_script enc2-$i $enc
1.170 + db close
1.171 + incr i
1.172 +}
1.173 +
1.174 +# Test that it is an error to try to attach a database with a different
1.175 +# encoding to the main database.
1.176 +ifcapable attach {
1.177 + do_test enc2-4.1 {
1.178 + file delete -force test.db
1.179 + sqlite3 db test.db
1.180 + db eval "PRAGMA encoding = 'UTF-8'"
1.181 + db eval "CREATE TABLE abc(a, b, c);"
1.182 + } {}
1.183 + do_test enc2-4.2 {
1.184 + file delete -force test2.db
1.185 + sqlite3 db2 test2.db
1.186 + db2 eval "PRAGMA encoding = 'UTF-16'"
1.187 + db2 eval "CREATE TABLE abc(a, b, c);"
1.188 + } {}
1.189 + do_test enc2-4.3 {
1.190 + catchsql {
1.191 + ATTACH 'test2.db' as aux;
1.192 + }
1.193 + } {1 {attached databases must use the same text encoding as main database}}
1.194 + db2 close
1.195 + db close
1.196 +}
1.197 +
1.198 +# The following tests - enc2-5.* - test that SQLite selects the correct
1.199 +# collation sequence when more than one is available.
1.200 +
1.201 +set ::values [list one two three four five]
1.202 +set ::test_collate_enc INVALID
1.203 +proc test_collate {enc lhs rhs} {
1.204 + set ::test_collate_enc $enc
1.205 + set l [lsearch -exact $::values $lhs]
1.206 + set r [lsearch -exact $::values $rhs]
1.207 + set res [expr $l - $r]
1.208 + # puts "enc=$enc lhs=$lhs/$l rhs=$rhs/$r res=$res"
1.209 + return $res
1.210 +}
1.211 +
1.212 +file delete -force test.db
1.213 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.214 +do_test enc2-5.0 {
1.215 + execsql {
1.216 + CREATE TABLE t5(a);
1.217 + INSERT INTO t5 VALUES('one');
1.218 + INSERT INTO t5 VALUES('two');
1.219 + INSERT INTO t5 VALUES('five');
1.220 + INSERT INTO t5 VALUES('three');
1.221 + INSERT INTO t5 VALUES('four');
1.222 + }
1.223 +} {}
1.224 +do_test enc2-5.1 {
1.225 + add_test_collate $DB 1 1 1
1.226 + set res [execsql {SELECT * FROM t5 ORDER BY 1 COLLATE test_collate;}]
1.227 + lappend res $::test_collate_enc
1.228 +} {one two three four five UTF-8}
1.229 +do_test enc2-5.2 {
1.230 + add_test_collate $DB 0 1 0
1.231 + set res [execsql {SELECT * FROM t5 ORDER BY 1 COLLATE test_collate}]
1.232 + lappend res $::test_collate_enc
1.233 +} {one two three four five UTF-16LE}
1.234 +do_test enc2-5.3 {
1.235 + add_test_collate $DB 0 0 1
1.236 + set res [execsql {SELECT * FROM t5 ORDER BY 1 COLLATE test_collate}]
1.237 + lappend res $::test_collate_enc
1.238 +} {one two three four five UTF-16BE}
1.239 +
1.240 +db close
1.241 +file delete -force test.db
1.242 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.243 +execsql {pragma encoding = 'UTF-16LE'}
1.244 +do_test enc2-5.4 {
1.245 + execsql {
1.246 + CREATE TABLE t5(a);
1.247 + INSERT INTO t5 VALUES('one');
1.248 + INSERT INTO t5 VALUES('two');
1.249 + INSERT INTO t5 VALUES('five');
1.250 + INSERT INTO t5 VALUES('three');
1.251 + INSERT INTO t5 VALUES('four');
1.252 + }
1.253 +} {}
1.254 +do_test enc2-5.5 {
1.255 + add_test_collate $DB 1 1 1
1.256 + set res [execsql {SELECT * FROM t5 ORDER BY 1 COLLATE test_collate}]
1.257 + lappend res $::test_collate_enc
1.258 +} {one two three four five UTF-16LE}
1.259 +do_test enc2-5.6 {
1.260 + add_test_collate $DB 1 0 1
1.261 + set res [execsql {SELECT * FROM t5 ORDER BY 1 COLLATE test_collate}]
1.262 + lappend res $::test_collate_enc
1.263 +} {one two three four five UTF-16BE}
1.264 +do_test enc2-5.7 {
1.265 + add_test_collate $DB 1 0 0
1.266 + set res [execsql {SELECT * FROM t5 ORDER BY 1 COLLATE test_collate}]
1.267 + lappend res $::test_collate_enc
1.268 +} {one two three four five UTF-8}
1.269 +
1.270 +db close
1.271 +file delete -force test.db
1.272 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.273 +execsql {pragma encoding = 'UTF-16BE'}
1.274 +do_test enc2-5.8 {
1.275 + execsql {
1.276 + CREATE TABLE t5(a);
1.277 + INSERT INTO t5 VALUES('one');
1.278 + INSERT INTO t5 VALUES('two');
1.279 + INSERT INTO t5 VALUES('five');
1.280 + INSERT INTO t5 VALUES('three');
1.281 + INSERT INTO t5 VALUES('four');
1.282 + }
1.283 +} {}
1.284 +do_test enc2-5.9 {
1.285 + add_test_collate $DB 1 1 1
1.286 + set res [execsql {SELECT * FROM t5 ORDER BY 1 COLLATE test_collate}]
1.287 + lappend res $::test_collate_enc
1.288 +} {one two three four five UTF-16BE}
1.289 +do_test enc2-5.10 {
1.290 + add_test_collate $DB 1 1 0
1.291 + set res [execsql {SELECT * FROM t5 ORDER BY 1 COLLATE test_collate}]
1.292 + lappend res $::test_collate_enc
1.293 +} {one two three four five UTF-16LE}
1.294 +do_test enc2-5.11 {
1.295 + add_test_collate $DB 1 0 0
1.296 + set res [execsql {SELECT * FROM t5 ORDER BY 1 COLLATE test_collate}]
1.297 + lappend res $::test_collate_enc
1.298 +} {one two three four five UTF-8}
1.299 +
1.300 +# Also test that a UTF-16 collation factory works.
1.301 +do_test enc2-5-12 {
1.302 + add_test_collate $DB 0 0 0
1.303 + catchsql {
1.304 + SELECT * FROM t5 ORDER BY 1 COLLATE test_collate
1.305 + }
1.306 +} {1 {no such collation sequence: test_collate}}
1.307 +do_test enc2-5.13 {
1.308 + add_test_collate_needed $DB
1.309 + set res [execsql {SELECT * FROM t5 ORDER BY 1 COLLATE test_collate; }]
1.310 + lappend res $::test_collate_enc
1.311 +} {one two three four five UTF-16BE}
1.312 +do_test enc2-5.14 {
1.313 + set ::sqlite_last_needed_collation
1.314 +} test_collate
1.315 +
1.316 +db close
1.317 +file delete -force test.db
1.318 +
1.319 +do_test enc2-5.15 {
1.320 + sqlite3 db test.db; set ::DB [sqlite3_connection_pointer db]
1.321 + add_test_collate_needed $::DB
1.322 + set ::sqlite_last_needed_collation
1.323 +} {}
1.324 +do_test enc2-5.16 {
1.325 + execsql {CREATE TABLE t1(a varchar collate test_collate);}
1.326 +} {}
1.327 +do_test enc2-5.17 {
1.328 + set ::sqlite_last_needed_collation
1.329 +} {test_collate}
1.330 +
1.331 +# The following tests - enc2-6.* - test that SQLite selects the correct
1.332 +# user function when more than one is available.
1.333 +
1.334 +proc test_function {enc arg} {
1.335 + return "$enc $arg"
1.336 +}
1.337 +
1.338 +db close
1.339 +file delete -force test.db
1.340 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.341 +execsql {pragma encoding = 'UTF-8'}
1.342 +do_test enc2-6.0 {
1.343 + execsql {
1.344 + CREATE TABLE t5(a);
1.345 + INSERT INTO t5 VALUES('one');
1.346 + }
1.347 +} {}
1.348 +do_test enc2-6.1 {
1.349 + add_test_function $DB 1 1 1
1.350 + execsql {
1.351 + SELECT test_function('sqlite')
1.352 + }
1.353 +} {{UTF-8 sqlite}}
1.354 +db close
1.355 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.356 +do_test enc2-6.2 {
1.357 + add_test_function $DB 0 1 0
1.358 + execsql {
1.359 + SELECT test_function('sqlite')
1.360 + }
1.361 +} {{UTF-16LE sqlite}}
1.362 +db close
1.363 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.364 +do_test enc2-6.3 {
1.365 + add_test_function $DB 0 0 1
1.366 + execsql {
1.367 + SELECT test_function('sqlite')
1.368 + }
1.369 +} {{UTF-16BE sqlite}}
1.370 +
1.371 +db close
1.372 +file delete -force test.db
1.373 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.374 +execsql {pragma encoding = 'UTF-16LE'}
1.375 +do_test enc2-6.3 {
1.376 + execsql {
1.377 + CREATE TABLE t5(a);
1.378 + INSERT INTO t5 VALUES('sqlite');
1.379 + }
1.380 +} {}
1.381 +do_test enc2-6.4 {
1.382 + add_test_function $DB 1 1 1
1.383 + execsql {
1.384 + SELECT test_function('sqlite')
1.385 + }
1.386 +} {{UTF-16LE sqlite}}
1.387 +db close
1.388 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.389 +do_test enc2-6.5 {
1.390 + add_test_function $DB 0 1 0
1.391 + execsql {
1.392 + SELECT test_function('sqlite')
1.393 + }
1.394 +} {{UTF-16LE sqlite}}
1.395 +db close
1.396 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.397 +do_test enc2-6.6 {
1.398 + add_test_function $DB 0 0 1
1.399 + execsql {
1.400 + SELECT test_function('sqlite')
1.401 + }
1.402 +} {{UTF-16BE sqlite}}
1.403 +
1.404 +db close
1.405 +file delete -force test.db
1.406 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.407 +execsql {pragma encoding = 'UTF-16BE'}
1.408 +do_test enc2-6.7 {
1.409 + execsql {
1.410 + CREATE TABLE t5(a);
1.411 + INSERT INTO t5 VALUES('sqlite');
1.412 + }
1.413 +} {}
1.414 +do_test enc2-6.8 {
1.415 + add_test_function $DB 1 1 1
1.416 + execsql {
1.417 + SELECT test_function('sqlite')
1.418 + }
1.419 +} {{UTF-16BE sqlite}}
1.420 +db close
1.421 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.422 +do_test enc2-6.9 {
1.423 + add_test_function $DB 0 1 0
1.424 + execsql {
1.425 + SELECT test_function('sqlite')
1.426 + }
1.427 +} {{UTF-16LE sqlite}}
1.428 +db close
1.429 +sqlite3 db test.db; set DB [sqlite3_connection_pointer db]
1.430 +do_test enc2-6.10 {
1.431 + add_test_function $DB 0 0 1
1.432 + execsql {
1.433 + SELECT test_function('sqlite')
1.434 + }
1.435 +} {{UTF-16BE sqlite}}
1.436 +
1.437 +
1.438 +db close
1.439 +file delete -force test.db
1.440 +
1.441 +# The following tests - enc2-7.* - function as follows:
1.442 +#
1.443 +# 1: Open an empty database file assuming UTF-16 encoding.
1.444 +# 2: Open the same database with a different handle assuming UTF-8. Create
1.445 +# a table using this handle.
1.446 +# 3: Read the sqlite_master table from the first handle.
1.447 +# 4: Ensure the first handle recognises the database encoding is UTF-8.
1.448 +#
1.449 +do_test enc2-7.1 {
1.450 + sqlite3 db test.db
1.451 + execsql {
1.452 + PRAGMA encoding = 'UTF-16';
1.453 + SELECT * FROM sqlite_master;
1.454 + }
1.455 +} {}
1.456 +do_test enc2-7.2 {
1.457 + set enc [execsql {
1.458 + PRAGMA encoding;
1.459 + }]
1.460 + string range $enc 0 end-2 ;# Chop off the "le" or "be"
1.461 +} {UTF-16}
1.462 +do_test enc2-7.3 {
1.463 + sqlite3 db2 test.db
1.464 + execsql {
1.465 + PRAGMA encoding = 'UTF-8';
1.466 + CREATE TABLE abc(a, b, c);
1.467 + } db2
1.468 +} {}
1.469 +do_test enc2-7.4 {
1.470 + execsql {
1.471 + SELECT * FROM sqlite_master;
1.472 + }
1.473 +} "table abc abc [expr $AUTOVACUUM?3:2] {CREATE TABLE abc(a, b, c)}"
1.474 +do_test enc2-7.5 {
1.475 + execsql {
1.476 + PRAGMA encoding;
1.477 + }
1.478 +} {UTF-8}
1.479 +
1.480 +db close
1.481 +db2 close
1.482 +
1.483 +proc utf16 {utf8} {
1.484 + set utf16 [encoding convertto unicode $utf8]
1.485 + append utf16 "\x00\x00"
1.486 + return $utf16
1.487 +}
1.488 +ifcapable {complete} {
1.489 + do_test enc2-8.1 {
1.490 + sqlite3_complete16 [utf16 "SELECT * FROM t1;"]
1.491 + } {1}
1.492 + do_test enc2-8.2 {
1.493 + sqlite3_complete16 [utf16 "SELECT * FROM"]
1.494 + } {0}
1.495 +}
1.496 +
1.497 +# Test that the encoding of an empty database may still be set after the
1.498 +# (empty) schema has been initialized.
1.499 +file delete -force test.db
1.500 +do_test enc2-9.1 {
1.501 + sqlite3 db test.db
1.502 + execsql {
1.503 + PRAGMA encoding = 'UTF-8';
1.504 + PRAGMA encoding;
1.505 + }
1.506 +} {UTF-8}
1.507 +do_test enc2-9.2 {
1.508 + sqlite3 db test.db
1.509 + execsql {
1.510 + PRAGMA encoding = 'UTF-16le';
1.511 + PRAGMA encoding;
1.512 + }
1.513 +} {UTF-16le}
1.514 +do_test enc2-9.3 {
1.515 + sqlite3 db test.db
1.516 + execsql {
1.517 + SELECT * FROM sqlite_master;
1.518 + PRAGMA encoding = 'UTF-8';
1.519 + PRAGMA encoding;
1.520 + }
1.521 +} {UTF-8}
1.522 +do_test enc2-9.4 {
1.523 + sqlite3 db test.db
1.524 + execsql {
1.525 + PRAGMA encoding = 'UTF-16le';
1.526 + CREATE TABLE abc(a, b, c);
1.527 + PRAGMA encoding;
1.528 + }
1.529 +} {UTF-16le}
1.530 +do_test enc2-9.5 {
1.531 + sqlite3 db test.db
1.532 + execsql {
1.533 + PRAGMA encoding = 'UTF-8';
1.534 + PRAGMA encoding;
1.535 + }
1.536 +} {UTF-16le}
1.537 +
1.538 +# Ticket #1987.
1.539 +# Disallow encoding changes once the encoding has been set.
1.540 +#
1.541 +do_test enc2-10.1 {
1.542 + db close
1.543 + file delete -force test.db test.db-journal
1.544 + sqlite3 db test.db
1.545 + db eval {
1.546 + PRAGMA encoding=UTF16;
1.547 + CREATE TABLE t1(a);
1.548 + PRAGMA encoding=UTF8;
1.549 + CREATE TABLE t2(b);
1.550 + }
1.551 + db close
1.552 + sqlite3 db test.db
1.553 + db eval {
1.554 + SELECT name FROM sqlite_master
1.555 + }
1.556 +} {t1 t2}
1.557 +
1.558 +finish_test