# 2002 March 6
#
# The author disclaims copyright to this source code.  In place of
# a legal notice, here is a blessing:
#
#    May you do good and not evil.
#    May you find forgiveness for yourself and forgive others.
#    May you share freely, never taking more than you give.
#
#***********************************************************************
# This file implements regression tests for SQLite library.
#
# This file implements tests for the PRAGMA command.
#
# $Id: pragma.test,v 1.51 2007/01/27 14:26:07 drh Exp $

set testdir [file dirname $argv0]
source $testdir/tester.tcl

# Test organization:
#
# pragma-1.*: Test cache_size, default_cache_size and synchronous on main db.
# pragma-2.*: Test synchronous on attached db.
# pragma-3.*: Test detection of table/index inconsistency by integrity_check.
# pragma-4.*: Test cache_size and default_cache_size on attached db.
# pragma-5.*: Test that pragma synchronous may not be used inside of a
#             transaction.
# pragma-6.*: Test schema-query pragmas.
# pragma-7.*: Miscellaneous tests.
# pragma-8.*: Test user_version and schema_version pragmas.
# pragma-9.*: Test temp_store and temp_store_directory.
# pragma-10.*: Test the count_changes pragma in the presence of triggers.
# pragma-11.*: Test the collation_list pragma.
#

ifcapable !pragma {
  finish_test
  return
}

# Delete the preexisting database to avoid the special setup
# that the "all.test" script does.
#
db close
file delete test.db test.db-journal
file delete test3.db test3.db-journal
sqlite3 db test.db; set DB [sqlite3_connection_pointer db]

ifcapable pager_pragmas {
do_test pragma-1.1 {
  execsql {
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {2000 2000 2}
do_test pragma-1.2 {
  execsql {
    PRAGMA synchronous=OFF;
    PRAGMA cache_size=1234;
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {1234 2000 0}
do_test pragma-1.3 {
  db close
  sqlite3 db test.db
  execsql {
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {2000 2000 2}
do_test pragma-1.4 {
  execsql {
    PRAGMA synchronous=OFF;
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {2000 2000 0}
do_test pragma-1.5 {
  execsql {
    PRAGMA cache_size=4321;
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {4321 2000 0}
do_test pragma-1.6 {
  execsql {
    PRAGMA synchronous=ON;
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {4321 2000 1}
do_test pragma-1.7 {
  db close
  sqlite3 db test.db
  execsql {
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {2000 2000 2}
do_test pragma-1.8 {
  execsql {
    PRAGMA default_cache_size=123;
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {123 123 2}
do_test pragma-1.9.1 {
  db close
  sqlite3 db test.db; set ::DB [sqlite3_connection_pointer db]
  execsql {
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {123 123 2}
ifcapable vacuum {
  do_test pragma-1.9.2 {
    execsql {
      VACUUM;
      PRAGMA cache_size;
      PRAGMA default_cache_size;
      PRAGMA synchronous;
    }
  } {123 123 2}
}
do_test pragma-1.10 {
  execsql {
    PRAGMA synchronous=NORMAL;
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {123 123 1}
do_test pragma-1.11 {
  execsql {
    PRAGMA synchronous=FULL;
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {123 123 2}
do_test pragma-1.12 {
  db close
  sqlite3 db test.db; set ::DB [sqlite3_connection_pointer db]
  execsql {
    PRAGMA cache_size;
    PRAGMA default_cache_size;
    PRAGMA synchronous;
  }
} {123 123 2}

# Make sure the pragma handler understands numeric values in addition
# to keywords like "off" and "full".
#
do_test pragma-1.13 {
  execsql {
    PRAGMA synchronous=0;
    PRAGMA synchronous;
  }
} {0}
do_test pragma-1.14 {
  execsql {
    PRAGMA synchronous=2;
    PRAGMA synchronous;
  }
} {2}
} ;# ifcapable pager_pragmas

# Test turning "flag" pragmas on and off.
#
do_test pragma-1.15 {
  execsql {
    PRAGMA vdbe_listing=YES;
    PRAGMA vdbe_listing;
  }
} {1}
do_test pragma-1.16 {
  execsql {
    PRAGMA vdbe_listing=NO;
    PRAGMA vdbe_listing;
  }
} {0}
do_test pragma-1.17 {
  execsql {
    PRAGMA parser_trace=ON;
    PRAGMA parser_trace=OFF;
  }
} {}
do_test pragma-1.18 {
  execsql {
    PRAGMA bogus = -1234;  -- Parsing of negative values
  }
} {}

# Test modifying the safety_level of an attached database.
do_test pragma-2.1 {
  file delete -force test2.db
  file delete -force test2.db-journal
  execsql {
    ATTACH 'test2.db' AS aux;
  } 
} {}
ifcapable pager_pragmas {
do_test pragma-2.2 {
  execsql {
    pragma aux.synchronous;
  } 
} {2}
do_test pragma-2.3 {
  execsql {
    pragma aux.synchronous = OFF;
    pragma aux.synchronous;
    pragma synchronous;
  } 
} {0 2}
do_test pragma-2.4 {
  execsql {
    pragma aux.synchronous = ON;
    pragma synchronous;
    pragma aux.synchronous;
  } 
} {2 1}
} ;# ifcapable pager_pragmas

# Construct a corrupted index and make sure the integrity_check
# pragma finds it.
#
# These tests won't work if the database is encrypted
#
do_test pragma-3.1 {
  execsql {
    BEGIN;
    CREATE TABLE t2(a,b,c);
    CREATE INDEX i2 ON t2(a);
    INSERT INTO t2 VALUES(11,2,3);
    INSERT INTO t2 VALUES(22,3,4);
    COMMIT;
    SELECT rowid, * from t2;
  }
} {1 11 2 3 2 22 3 4}
if {![sqlite3 -has-codec] && $sqlite_options(integrityck)} {
  do_test pragma-3.2 {
    set rootpage [execsql {SELECT rootpage FROM sqlite_master WHERE name='i2'}]
    set db [btree_open test.db 100 0]
    btree_begin_transaction $db
    set c [btree_cursor $db $rootpage 1]
    btree_first $c
    btree_delete $c
    btree_commit $db
    btree_close $db
    execsql {PRAGMA integrity_check}
  } {{rowid 1 missing from index i2} {wrong # of entries in index i2}}
  do_test pragma-3.3 {
    execsql {PRAGMA integrity_check=1}
  } {{rowid 1 missing from index i2}}
  do_test pragma-3.4 {
    execsql {
      ATTACH DATABASE 'test.db' AS t2;
      PRAGMA integrity_check
    }
  } {{rowid 1 missing from index i2} {wrong # of entries in index i2} {rowid 1 missing from index i2} {wrong # of entries in index i2}}
  do_test pragma-3.5 {
    execsql {
      PRAGMA integrity_check=3
    }
  } {{rowid 1 missing from index i2} {wrong # of entries in index i2} {rowid 1 missing from index i2}}
  do_test pragma-3.6 {
    execsql {
      PRAGMA integrity_check=xyz
    }
  } {{rowid 1 missing from index i2} {wrong # of entries in index i2} {rowid 1 missing from index i2} {wrong # of entries in index i2}}
  do_test pragma-3.7 {
    execsql {
      PRAGMA integrity_check=0
    }
  } {{rowid 1 missing from index i2} {wrong # of entries in index i2} {rowid 1 missing from index i2} {wrong # of entries in index i2}}

  # Add additional corruption by appending unused pages to the end of
  # the database file testerr.db
  #
  do_test pragma-3.8 {
    execsql {DETACH t2}
    file delete -force testerr.db testerr.db-journal
    set out [open testerr.db w]
    fconfigure $out -translation binary
    set in [open test.db r]
    fconfigure $in -translation binary
    puts -nonewline $out [read $in]
    seek $in 0
    puts -nonewline $out [read $in]
    close $in
    close $out
    execsql {REINDEX t2}
    execsql {PRAGMA integrity_check}
  } {ok}
  do_test pragma-3.9 {
    execsql {
      ATTACH 'testerr.db' AS t2;
      PRAGMA integrity_check
    }
  } {{*** in database t2 ***
Page 4 is never used
Page 5 is never used
Page 6 is never used} {rowid 1 missing from index i2} {wrong # of entries in index i2}}
  do_test pragma-3.10 {
    execsql {
      PRAGMA integrity_check=1
    }
  } {{*** in database t2 ***
Page 4 is never used}}
  do_test pragma-3.11 {
    execsql {
      PRAGMA integrity_check=5
    }
  } {{*** in database t2 ***
Page 4 is never used
Page 5 is never used
Page 6 is never used} {rowid 1 missing from index i2} {wrong # of entries in index i2}}
  do_test pragma-3.12 {
    execsql {
      PRAGMA integrity_check=4
    }
  } {{*** in database t2 ***
Page 4 is never used
Page 5 is never used
Page 6 is never used} {rowid 1 missing from index i2}}
  do_test pragma-3.13 {
    execsql {
      PRAGMA integrity_check=3
    }
  } {{*** in database t2 ***
Page 4 is never used
Page 5 is never used
Page 6 is never used}}
  do_test pragma-3.14 {
    execsql {
      PRAGMA integrity_check(2)
    }
  } {{*** in database t2 ***
Page 4 is never used
Page 5 is never used}}
  do_test pragma-3.15 {
    execsql {
      ATTACH 'testerr.db' AS t3;
      PRAGMA integrity_check
    }
  } {{*** in database t2 ***
Page 4 is never used
Page 5 is never used
Page 6 is never used} {rowid 1 missing from index i2} {wrong # of entries in index i2} {*** in database t3 ***
Page 4 is never used
Page 5 is never used
Page 6 is never used} {rowid 1 missing from index i2} {wrong # of entries in index i2}}
  do_test pragma-3.16 {
    execsql {
      PRAGMA integrity_check(9)
    }
  } {{*** in database t2 ***
Page 4 is never used
Page 5 is never used
Page 6 is never used} {rowid 1 missing from index i2} {wrong # of entries in index i2} {*** in database t3 ***
Page 4 is never used
Page 5 is never used
Page 6 is never used} {rowid 1 missing from index i2}}
  do_test pragma-3.17 {
    execsql {
      PRAGMA integrity_check=7
    }
  } {{*** in database t2 ***
Page 4 is never used
Page 5 is never used
Page 6 is never used} {rowid 1 missing from index i2} {wrong # of entries in index i2} {*** in database t3 ***
Page 4 is never used
Page 5 is never used}}
  do_test pragma-3.18 {
    execsql {
      PRAGMA integrity_check=4
    }
  } {{*** in database t2 ***
Page 4 is never used
Page 5 is never used
Page 6 is never used} {rowid 1 missing from index i2}}
}
do_test pragma-3.99 {
  catchsql {DETACH t3}
  catchsql {DETACH t2}
  file delete -force testerr.db testerr.db-journal
  catchsql {DROP INDEX i2}
} {0 {}}

# Test modifying the cache_size of an attached database.
ifcapable pager_pragmas {
do_test pragma-4.1 {
  execsql {
    pragma aux.cache_size;
    pragma aux.default_cache_size;
  } 
} {2000 2000}
do_test pragma-4.2 {
  execsql {
    pragma aux.cache_size = 50;
    pragma aux.cache_size;
    pragma aux.default_cache_size;
  } 
} {50 2000}
do_test pragma-4.3 {
  execsql {
    pragma aux.default_cache_size = 456;
    pragma aux.cache_size;
    pragma aux.default_cache_size;
  } 
} {456 456}
do_test pragma-4.4 {
  execsql {
    pragma cache_size;
    pragma default_cache_size;
  } 
} {123 123}
do_test pragma-4.5 {
  execsql {
    DETACH aux;
    ATTACH 'test3.db' AS aux;
    pragma aux.cache_size;
    pragma aux.default_cache_size;
  } 
} {2000 2000}
do_test pragma-4.6 {
  execsql {
    DETACH aux;
    ATTACH 'test2.db' AS aux;
    pragma aux.cache_size;
    pragma aux.default_cache_size;
  } 
} {456 456}
} ;# ifcapable pager_pragmas

# Test that modifying the sync-level in the middle of a transaction is
# disallowed.
ifcapable pager_pragmas {
do_test pragma-5.0 {
  execsql {
    pragma synchronous;
  } 
} {2}
do_test pragma-5.1 {
  catchsql {
    BEGIN;
    pragma synchronous = OFF;
  } 
} {1 {Safety level may not be changed inside a transaction}}
do_test pragma-5.2 {
  execsql {
    pragma synchronous;
  } 
} {2}
catchsql {COMMIT;}
} ;# ifcapable pager_pragmas

# Test schema-query pragmas
#
ifcapable schema_pragmas {
ifcapable tempdb {
  do_test pragma-6.1 {
    set res {}
    execsql {SELECT * FROM sqlite_temp_master}
    foreach {idx name file} [execsql {pragma database_list}] {
      lappend res $idx $name
    }
    set res
  } {0 main 1 temp 2 aux}
}
do_test pragma-6.2 {
  execsql {
    pragma table_info(t2)
  }
} {0 a {} 0 {} 0 1 b {} 0 {} 0 2 c {} 0 {} 0}
db nullvalue <<NULL>>
do_test pragma-6.2.2 {
  execsql {
    CREATE TABLE t5(
      a TEXT DEFAULT CURRENT_TIMESTAMP, 
      b DEFAULT (5+3),
      c TEXT,
      d INTEGER DEFAULT NULL,
      e TEXT DEFAULT ''
    );
    PRAGMA table_info(t5);
  }
} {0 a TEXT 0 CURRENT_TIMESTAMP 0 1 b {} 0 5+3 0 2 c TEXT 0 <<NULL>> 0 3 d INTEGER 0 NULL 0 4 e TEXT 0 '' 0}
db nullvalue {}
ifcapable {foreignkey} {
  do_test pragma-6.3 {
    execsql {
      CREATE TABLE t3(a int references t2(b), b UNIQUE);
      pragma foreign_key_list(t3);
    }
  } {0 0 t2 a b}
  do_test pragma-6.4 {
    execsql {
      pragma index_list(t3);
    }
  } {0 sqlite_autoindex_t3_1 1}
}
ifcapable {!foreignkey} {
  execsql {CREATE TABLE t3(a,b UNIQUE)}
}
do_test pragma-6.5 {
  execsql {
    CREATE INDEX t3i1 ON t3(a,b);
    pragma index_info(t3i1);
  }
} {0 0 a 1 1 b}
} ;# ifcapable schema_pragmas
# Miscellaneous tests
#
ifcapable schema_pragmas {
do_test pragma-7.1 {
  # Make sure a pragma knows to read the schema if it needs to
  db close
  sqlite3 db test.db
  execsql {
    pragma index_list(t3);
  }
} {0 t3i1 0 1 sqlite_autoindex_t3_1 1}
} ;# ifcapable schema_pragmas
ifcapable {utf16} {
  do_test pragma-7.2 {
    db close
    sqlite3 db test.db
    catchsql {
      pragma encoding=bogus;
    }
  } {1 {unsupported encoding: bogus}}
}
ifcapable tempdb {
  do_test pragma-7.3 {
    db close
    sqlite3 db test.db
    execsql {
      pragma lock_status;
    }
  } {main unlocked temp closed}
} else {
  do_test pragma-7.3 {
    db close
    sqlite3 db test.db
    execsql {
      pragma lock_status;
    }
  } {main unlocked}
}


#----------------------------------------------------------------------
# Test cases pragma-8.* test the "PRAGMA schema_version" and "PRAGMA
# user_version" statements.
#
# pragma-8.1: PRAGMA schema_version
# pragma-8.2: PRAGMA user_version
#

ifcapable schema_version {

# First check that we can set the schema version and then retrieve the
# same value.
do_test pragma-8.1.1 {
  execsql {
    PRAGMA schema_version = 105;
  }
} {}
do_test pragma-8.1.2 {
  execsql2 {
    PRAGMA schema_version;
  }
} {schema_version 105}
do_test pragma-8.1.3 {
  execsql {
    PRAGMA schema_version = 106;
  }
} {}
do_test pragma-8.1.4 {
  execsql {
    PRAGMA schema_version;
  }
} 106

# Check that creating a table modifies the schema-version (this is really
# to verify that the value being read is in fact the schema version).
do_test pragma-8.1.5 {
  execsql {
    CREATE TABLE t4(a, b, c);
    INSERT INTO t4 VALUES(1, 2, 3);
    SELECT * FROM t4;
  }
} {1 2 3}
do_test pragma-8.1.6 {
  execsql {
    PRAGMA schema_version;
  }
} 107

# Now open a second connection to the database. Ensure that changing the
# schema-version using the first connection forces the second connection
# to reload the schema. This has to be done using the C-API test functions,
# because the TCL API accounts for SCHEMA_ERROR and retries the query.
do_test pragma-8.1.7 {
  sqlite3 db2 test.db; set ::DB2 [sqlite3_connection_pointer db2]
  execsql {
    SELECT * FROM t4;
  } db2
} {1 2 3}
do_test pragma-8.1.8 {
  execsql {
    PRAGMA schema_version = 108;
  }
} {}
do_test pragma-8.1.9 {
  set ::STMT [sqlite3_prepare $::DB2 "SELECT * FROM t4" -1 DUMMY]
  sqlite3_step $::STMT
} SQLITE_ERROR
do_test pragma-8.1.10 {
  sqlite3_finalize $::STMT
} SQLITE_SCHEMA

# Make sure the schema-version can be manipulated in an attached database.
file delete -force test2.db
file delete -force test2.db-journal
do_test pragma-8.1.11 {
  execsql {
    ATTACH 'test2.db' AS aux;
    CREATE TABLE aux.t1(a, b, c);
    PRAGMA aux.schema_version = 205;
  }
} {}
do_test pragma-8.1.12 {
  execsql {
    PRAGMA aux.schema_version;
  }
} 205
do_test pragma-8.1.13 {
  execsql {
    PRAGMA schema_version;
  }
} 108

# And check that modifying the schema-version in an attached database
# forces the second connection to reload the schema.
do_test pragma-8.1.14 {
  sqlite3 db2 test.db; set ::DB2 [sqlite3_connection_pointer db2]
  execsql {
    ATTACH 'test2.db' AS aux;
    SELECT * FROM aux.t1;
  } db2
} {}
do_test pragma-8.1.15 {
  execsql {
    PRAGMA aux.schema_version = 206;
  }
} {}
do_test pragma-8.1.16 {
  set ::STMT [sqlite3_prepare $::DB2 "SELECT * FROM aux.t1" -1 DUMMY]
  sqlite3_step $::STMT
} SQLITE_ERROR
do_test pragma-8.1.17 {
  sqlite3_finalize $::STMT
} SQLITE_SCHEMA
do_test pragma-8.1.18 {
  db2 close
} {}

# Now test that the user-version can be read and written (and that we aren't
# accidentally manipulating the schema-version instead).
do_test pragma-8.2.1 {
  execsql2 {
    PRAGMA user_version;
  }
} {user_version 0}
do_test pragma-8.2.2 {
  execsql {
    PRAGMA user_version = 2;
  }
} {}
do_test pragma-8.2.3.1 {
  execsql2 {
    PRAGMA user_version;
  }
} {user_version 2}
do_test pragma-8.2.3.2 {
  db close
  sqlite3 db test.db
  execsql {
    PRAGMA user_version;
  }
} {2}
do_test pragma-8.2.4.1 {
  execsql {
    PRAGMA schema_version;
  }
} {108}
ifcapable vacuum {
  do_test pragma-8.2.4.2 {
    execsql {
      VACUUM;
      PRAGMA user_version;
    }
  } {2}
  do_test pragma-8.2.4.3 {
    execsql {
      PRAGMA schema_version;
    }
  } {109}
}
db eval {ATTACH 'test2.db' AS aux}

# Check that the user-version in the auxilary database can be manipulated (
# and that we aren't accidentally manipulating the same in the main db).
do_test pragma-8.2.5 {
  execsql {
    PRAGMA aux.user_version;
  }
} {0}
do_test pragma-8.2.6 {
  execsql {
    PRAGMA aux.user_version = 3;
  }
} {}
do_test pragma-8.2.7 {
  execsql {
    PRAGMA aux.user_version;
  }
} {3}
do_test pragma-8.2.8 {
  execsql {
    PRAGMA main.user_version;
  }
} {2}

# Now check that a ROLLBACK resets the user-version if it has been modified
# within a transaction.
do_test pragma-8.2.9 {
  execsql {
    BEGIN;
    PRAGMA aux.user_version = 10;
    PRAGMA user_version = 11;
  }
} {}
do_test pragma-8.2.10 {
  execsql {
    PRAGMA aux.user_version;
  }
} {10}
do_test pragma-8.2.11 {
  execsql {
    PRAGMA main.user_version;
  }
} {11}
do_test pragma-8.2.12 {
  execsql {
    ROLLBACK;
    PRAGMA aux.user_version;
  }
} {3}
do_test pragma-8.2.13 {
  execsql {
    PRAGMA main.user_version;
  }
} {2}

# Try a negative value for the user-version
do_test pragma-8.2.14 {
  execsql {
    PRAGMA user_version = -450;
  }
} {}
do_test pragma-8.2.15 {
  execsql {
    PRAGMA user_version;
  }
} {-450}
} ; # ifcapable schema_version


# Test temp_store and temp_store_directory pragmas
#
ifcapable pager_pragmas {
do_test pragma-9.1 {
  db close
  sqlite3 db test.db
  execsql {
    PRAGMA temp_store;
  }
} {0}
do_test pragma-9.2 {
  execsql {
    PRAGMA temp_store=file;
    PRAGMA temp_store;
  }
} {1}
do_test pragma-9.3 {
  execsql {
    PRAGMA temp_store=memory;
    PRAGMA temp_store;
  }
} {2}
do_test pragma-9.4 {
  execsql {
    PRAGMA temp_store_directory;
  }
} {}
do_test pragma-9.5 {
  set pwd [string map {' ''} [pwd]]
  execsql "
    PRAGMA temp_store_directory='$pwd';
  "
} {}
do_test pragma-9.6 {
  execsql { 
    PRAGMA temp_store_directory;
  }
} [list [pwd]]
do_test pragma-9.7 {
  catchsql { 
    PRAGMA temp_store_directory='/NON/EXISTENT/PATH/FOOBAR';
  }
} {1 {not a writable directory}}
do_test pragma-9.8 {
  execsql { 
    PRAGMA temp_store_directory='';
  }
} {}
ifcapable tempdb {
  do_test pragma-9.9 {
    execsql { 
      PRAGMA temp_store_directory;
      PRAGMA temp_store=FILE;
      CREATE TEMP TABLE temp_store_directory_test(a integer);
      INSERT INTO temp_store_directory_test values (2);
      SELECT * FROM temp_store_directory_test;
    }
  } {2}
}
do_test pragma-9.10 {
  catchsql "
    PRAGMA temp_store_directory='$pwd';
    SELECT * FROM temp_store_directory_test;
  "
} {1 {no such table: temp_store_directory_test}}
} ;# ifcapable pager_pragmas

ifcapable trigger {

do_test pragma-10.0 {
  catchsql {
    DROP TABLE main.t1;
  }
  execsql {
    PRAGMA count_changes = 1;

    CREATE TABLE t1(a PRIMARY KEY);
    CREATE TABLE t1_mirror(a);
    CREATE TABLE t1_mirror2(a);
    CREATE TRIGGER t1_bi BEFORE INSERT ON t1 BEGIN 
      INSERT INTO t1_mirror VALUES(new.a);
    END;
    CREATE TRIGGER t1_ai AFTER INSERT ON t1 BEGIN 
      INSERT INTO t1_mirror2 VALUES(new.a);
    END;
    CREATE TRIGGER t1_bu BEFORE UPDATE ON t1 BEGIN 
      UPDATE t1_mirror SET a = new.a WHERE a = old.a;
    END;
    CREATE TRIGGER t1_au AFTER UPDATE ON t1 BEGIN 
      UPDATE t1_mirror2 SET a = new.a WHERE a = old.a;
    END;
    CREATE TRIGGER t1_bd BEFORE DELETE ON t1 BEGIN 
      DELETE FROM t1_mirror WHERE a = old.a;
    END;
    CREATE TRIGGER t1_ad AFTER DELETE ON t1 BEGIN 
      DELETE FROM t1_mirror2 WHERE a = old.a;
    END;
  }
} {}

do_test pragma-10.1 {
  execsql {
    INSERT INTO t1 VALUES(randstr(10,10));
  }
} {1}
do_test pragma-10.2 {
  execsql {
    UPDATE t1 SET a = randstr(10,10);
  }
} {1}
do_test pragma-10.3 {
  execsql {
    DELETE FROM t1;
  }
} {1}

} ;# ifcapable trigger

ifcapable schema_pragmas {
  do_test pragma-11.1 {
    execsql2 {
      pragma collation_list;
    }
  } {seq 0 name NOCASE seq 1 name BINARY}
  do_test pragma-11.2 {
    db collate New_Collation blah...
    execsql {
      pragma collation_list;
    }
  } {0 New_Collation 1 NOCASE 2 BINARY}
}

ifcapable schema_pragmas&&tempdb {
  do_test pragma-12.1 {
    sqlite3 db2 test.db
    execsql {
      PRAGMA temp.table_info('abc');
    } db2
  } {}
  db2 close

  do_test pragma-12.2 {
    sqlite3 db2 test.db
    execsql {
      PRAGMA temp.default_cache_size = 200;
      PRAGMA temp.default_cache_size;
    } db2
  } {200}
  db2 close

  do_test pragma-12.3 {
    sqlite3 db2 test.db
    execsql {
      PRAGMA temp.cache_size = 400;
      PRAGMA temp.cache_size;
    } db2
  } {400}
  db2 close
}

ifcapable bloblit {

do_test pragma-13.1 {
  execsql {
    DROP TABLE IF EXISTS t4;
    PRAGMA vdbe_trace=on;
    PRAGMA vdbe_listing=on;
    PRAGMA sql_trace=on;
    CREATE TABLE t4(a INTEGER PRIMARY KEY,b);
    INSERT INTO t4(b) VALUES(x'0123456789abcdef0123456789abcdef0123456789');
    INSERT INTO t4(b) VALUES(randstr(30,30));
    INSERT INTO t4(b) VALUES(1.23456);
    INSERT INTO t4(b) VALUES(NULL);
    INSERT INTO t4(b) VALUES(0);
    INSERT INTO t4(b) SELECT b||b||b||b FROM t4;
    SELECT * FROM t4;
  }
  execsql {
    PRAGMA vdbe_trace=off;
    PRAGMA vdbe_listing=off;
    PRAGMA sql_trace=off;
  }
} {}

} ;# ifcapable bloblit 

# Reset the sqlite3_temp_directory variable for the next run of tests:
sqlite3 dbX :memory:
dbX eval {PRAGMA temp_store_directory = ""}
dbX close

finish_test