File:  [ELWIX - Embedded LightWeight unIX -] / embedaddon / sqlite3 / test / quota.test
Revision 1.1.1.1 (vendor branch): download - view: text, annotated - select for diffs - revision graph
Tue Feb 21 17:04:16 2012 UTC (12 years, 10 months ago) by misho
Branches: sqlite3, MAIN
CVS tags: v3_7_10, HEAD
sqlite3

    1: # 2010 September 1
    2: #
    3: # The author disclaims copyright to this source code.  In place of
    4: # a legal notice, here is a blessing:
    5: #
    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.
    9: #
   10: #***********************************************************************
   11: #
   12: 
   13: set testdir [file dirname $argv0]
   14: source $testdir/tester.tcl
   15: source $testdir/malloc_common.tcl
   16: 
   17: unset -nocomplain defaultVfs
   18: set defaultVfs [file_control_vfsname db]
   19: db close
   20: 
   21: do_test quota-1.1 { sqlite3_quota_initialize nosuchvfs 1 } {SQLITE_ERROR}
   22: do_test quota-1.2 { sqlite3_quota_initialize "" 1 }        {SQLITE_OK}
   23: do_test quota-1.3 { sqlite3_quota_initialize "" 1 }        {SQLITE_MISUSE}
   24: do_test quota-1.4 { sqlite3_quota_shutdown }               {SQLITE_OK}
   25: 
   26: do_test quota-1.5 { sqlite3_quota_initialize "" 0 }        {SQLITE_OK}
   27: do_test quota-1.6 { sqlite3_quota_shutdown }               {SQLITE_OK}
   28: do_test quota-1.7 { sqlite3_quota_initialize "" 1 }        {SQLITE_OK}
   29: do_test quota-1.8 { sqlite3_quota_shutdown }               {SQLITE_OK}
   30: 
   31: 
   32: #-------------------------------------------------------------------------
   33: # Some simple warm-body tests with a single database file in rollback 
   34: # mode:
   35: #
   36: #   quota-2.1.*: Test that SQLITE_FULL is returned if the database would
   37: #                exceed the configured quota.
   38: #
   39: #   quota-2.2.*: Test that SQLITE_FULL is not returned and the database
   40: #                grows if the callback extends the quota when the database
   41: #                attempts to grow beyond the configured quota.
   42: #
   43: #   quota-2.3.*: Open and close a db that is not part of any quota group. At
   44: #                one point this was causing mutex refs to be leaked.
   45: #
   46: #   quota-2.4.*: Try to shutdown the quota system before closing the db
   47: #                file. Check that this fails and the quota system still works
   48: #                afterwards. Then close the database and successfully shut
   49: #                down the quota system.
   50: #   
   51: sqlite3_quota_initialize "" 1
   52: 
   53: unset -nocomplain quota_request_ok
   54: proc quota_check {filename limitvar size} {
   55:   upvar $limitvar limit
   56: 
   57:   lappend ::quota [set limit] $size
   58:   if {[info exists ::quota_request_ok]} { set limit $size }
   59: }
   60: 
   61: do_test quota-2.1.1 {
   62:   sqlite3_quota_set *test.db 4096 quota_check
   63: } {SQLITE_OK}
   64: do_test quota-2.1.2 {
   65:   sqlite3 db test.db
   66:   execsql {
   67:     PRAGMA page_size=1024;
   68:     PRAGMA auto_vacuum=OFF;
   69:     PRAGMA journal_mode=DELETE;
   70:   }
   71:   set ::quota [list]
   72:   execsql {
   73:     CREATE TABLE t1(a, b);
   74:     INSERT INTO t1 VALUES(1, randomblob(1100));
   75:     INSERT INTO t1 VALUES(2, randomblob(1100));
   76:   }
   77:   set ::quota
   78: } {}
   79: do_test quota-2.1.2.1 {
   80:   file_control_vfsname db
   81: } quota/$defaultVfs
   82: do_test quota-2.1.3 { file size test.db } {4096}
   83: do_test quota-2.1.4 {
   84:   catchsql { INSERT INTO t1 VALUES(3, randomblob(1100)) }
   85: } {1 {database or disk is full}}
   86: do_test quota-2.1.5 { set ::quota } {4096 5120}
   87: 
   88: set ::quota_request_ok 1
   89: set ::quota [list]
   90: do_test quota-2.2.1 {
   91:   execsql { INSERT INTO t1 VALUES(3, randomblob(1100)) }
   92: } {}
   93: do_test quota-2.2.2 { set ::quota } {4096 5120}
   94: do_test quota-2.2.3 { file size test.db } {5120}
   95: unset ::quota_request_ok
   96: 
   97: do_test quota-2.3.1 {
   98:   sqlite3 db2 bak.db
   99:   db2 close
  100: } {}
  101: 
  102: do_test quota-2.4.1 {
  103:   sqlite3_quota_shutdown
  104: } {SQLITE_MISUSE}
  105: set ::quota [list]
  106: do_test quota-2.4.2 {
  107:   catchsql { INSERT INTO t1 VALUES(3, randomblob(1100)) }
  108: } {1 {database or disk is full}}
  109: do_test quota-2.4.3 { set ::quota } {5120 6144}
  110: do_test quota-2.4.4 { file size test.db } {5120}
  111: do_test quota-2.4.99 {
  112:   db close
  113:   sqlite3_quota_shutdown
  114: } {SQLITE_OK}
  115: 
  116: #-------------------------------------------------------------------------
  117: # Try some tests with more than one connection to a database file. Still
  118: # in rollback mode.
  119: #
  120: #   quota-3.1.*: Two connections to a single database file.
  121: #
  122: #   quota-3.2.*: Two connections to each of several database files (that
  123: #                are in the same quota group).
  124: #
  125: proc quota_check {filename limitvar size} {
  126:   upvar $limitvar limit
  127:   lappend ::quota [set limit] $size
  128:   if {[info exists ::quota_request_ok]} { set limit $size }
  129: }
  130: 
  131: do_test quota-3.1.1 {
  132:   forcedelete test.db
  133:   sqlite3_quota_initialize "" 1
  134:   sqlite3_quota_set *test.db 4096 quota_check
  135: } {SQLITE_OK}
  136: do_test quota-3.1.2 {
  137:   sqlite3 db test.db
  138:   execsql {
  139:     PRAGMA page_size = 1024;
  140:     PRAGMA journal_mode = delete;
  141:     PRAGMA auto_vacuum = off;
  142:     CREATE TABLE t1(a PRIMARY KEY, b);
  143:     INSERT INTO t1 VALUES(1, 'one');
  144:   }
  145:   file size test.db
  146: } {3072}
  147: do_test quota-3.1.3 {
  148:   sqlite3 db2 test.db
  149:   set ::quota [list]
  150:   execsql { CREATE TABLE t2(a, b) } db2
  151:   set ::quota
  152: } {}
  153: do_test quota-3.1.4 {
  154:   catchsql { CREATE TABLE t3(a, b) }
  155: } {1 {database or disk is full}}
  156: do_test quota-3.1.5 {
  157:   set ::quota_request_ok 1
  158:   execsql { CREATE TABLE t3(a, b) }
  159: } {}
  160: do_test quota-3.1.6 {
  161:   db close
  162:   db2 close
  163:   sqlite3_quota_set *test.db 0 {}
  164: } {SQLITE_OK}
  165: 
  166: do_test quota-3.2.1 {
  167:   delete_file force test.db test2.db 
  168: 
  169:   sqlite3_quota_set * 4096 {}
  170:   sqlite3 db1a test.db
  171:   sqlite3 db2a test2.db
  172: 
  173:   foreach db {db1a db2a} {
  174:     execsql {
  175:       PRAGMA page_size = 1024;
  176:       PRAGMA journal_mode = delete;
  177:       PRAGMA auto_vacuum = off;
  178:       CREATE TABLE t1(a, b);
  179:     } $db
  180:   }
  181: 
  182:   sqlite3 db1b test.db
  183:   sqlite3 db2b test2.db
  184: 
  185:   list [file size test.db] [file size test2.db]
  186: } {2048 2048}
  187: 
  188: catch { unset ::quota_request_ok }
  189: 
  190: do_test quota-3.2.2 { execsql { INSERT INTO t1 VALUES('x', 'y') } db1a } {}
  191: do_test quota-3.2.3 { execsql { INSERT INTO t1 VALUES('v', 'w') } db1b } {}
  192: do_test quota-3.2.4 { execsql { INSERT INTO t1 VALUES('t', 'u') } db2a } {}
  193: do_test quota-3.2.5 { execsql { INSERT INTO t1 VALUES('r', 's') } db2b } {}
  194: 
  195: do_test quota-3.2.6 { 
  196:   catchsql { INSERT INTO t1 VALUES(randomblob(500), randomblob(500)) } db1a
  197: } {1 {database or disk is full}}
  198: do_test quota-3.2.7 { 
  199:   catchsql { INSERT INTO t1 VALUES(randomblob(500), randomblob(500)) } db1b
  200: } {1 {database or disk is full}}
  201: do_test quota-3.2.8 { 
  202:   catchsql { INSERT INTO t1 VALUES(randomblob(500), randomblob(500)) } db2a
  203: } {1 {database or disk is full}}
  204: do_test quota-3.2.9 { 
  205:   catchsql { INSERT INTO t1 VALUES(randomblob(500), randomblob(500)) } db2b
  206: } {1 {database or disk is full}}
  207: 
  208: set ::quota [list]
  209: proc quota_callback {file limitvar size} {
  210:   upvar $limitvar limit
  211:   if {$::tcl_platform(platform)=="windows"} {
  212:     set file [ lindex [string map {\\ \/} $file] 0 ]
  213:   }
  214:   lappend ::quota $file $size
  215:   set limit 0
  216: }
  217: sqlite3_quota_set * 4096 quota_callback
  218: do_test quota-3.3.1 { 
  219:   execsql { INSERT INTO t1 VALUES(randomblob(500), randomblob(500)) } db1a
  220:   execsql { INSERT INTO t1 VALUES(randomblob(500), randomblob(500)) } db1b
  221:   execsql { INSERT INTO t1 VALUES(randomblob(500), randomblob(500)) } db2a
  222:   execsql { INSERT INTO t1 VALUES(randomblob(500), randomblob(500)) } db2b
  223:   set ::quota
  224: } [list [file join [pwd] test.db] 5120]
  225: 
  226: do_test quota-3.2.X {
  227:   foreach db {db1a db2a db2b db1b} { catch { $db close } }
  228:   sqlite3_quota_set * 0 {}
  229: } {SQLITE_OK}
  230: 
  231: #-------------------------------------------------------------------------
  232: # Quotas are deleted when unused and when their limit is set to zero
  233: #
  234: 
  235: # Return a list of all currently defined quotas.  Each quota is identified
  236: # by its pattern.
  237: proc quota_list {} {
  238:   set allq {}
  239:   foreach q [sqlite3_quota_dump] {
  240:     lappend allq [lindex $q 0]
  241:   }
  242:   return [lsort $allq]
  243: }
  244: proc quota_size {name} {
  245:   set allq {}
  246:   foreach q [sqlite3_quota_dump] {
  247:     if {[lindex $q 0]==$name} {return [lindex $q 2]}
  248:   }
  249:   return 0
  250: }
  251: 
  252: do_test quota-4.1.1 {
  253:   sqlite3_quota_set *test.db 0 {}
  254:   quota_list
  255: } {}
  256: do_test quota-4.1.2 {
  257:   sqlite3_quota_set *test.db 4096 {}
  258:   quota_list
  259: } {*test.db}
  260: do_test quota-4.1.3 {
  261:   sqlite3_quota_set *test2.db 0 {}
  262:   quota_list
  263: } {*test.db}
  264: do_test quota-4.1.4 {
  265:   sqlite3_quota_set *test2.db 100000 {}
  266:   quota_list
  267: } {*test.db *test2.db}
  268: do_test quota-4.1.5 {
  269:   sqlite3_quota_set *test.db 0 {}
  270:   quota_list
  271: } {*test2.db}
  272: do_test quota-4.1.6 {
  273:   forcedelete test2.db test2.db-journal test2.db-wal
  274:   sqlite3 db test2.db
  275:   db eval {CREATE TABLE t2(x); INSERT INTO t2 VALUES('tab-t2');}
  276:   quota_list
  277: } {*test2.db}
  278: do_test quota-4.1.7 {
  279:   catchsql {INSERT INTO t2 VALUES(zeroblob(200000))}
  280: } {1 {database or disk is full}}
  281: do_test quota-4.1.8 {
  282:   sqlite3 db2 test2.db
  283:   db2 eval {SELECT * FROM t2}
  284: } {tab-t2}
  285: do_test quota-4.1.9 {
  286:   sqlite3_quota_set *test2.db 0 {}
  287:   catchsql {INSERT INTO t2 VALUES(zeroblob(200000))}
  288: } {0 {}}
  289: do_test quota-4.1.10 {
  290:   quota_list
  291: } {*test2.db}
  292: do_test quota-4.1.11 {
  293:   db2 close
  294:   quota_list
  295: } {*test2.db}
  296: do_test quota-4.1.12 {
  297:   db close
  298:   quota_list
  299: } {}
  300: 
  301: do_test quota-4.2.1 {
  302:   sqlite3_quota_set A 1000 {}
  303:   sqlite3_quota_set B 1000 {}
  304:   sqlite3_quota_set C 1000 {}
  305:   sqlite3_quota_set D 1000 {}
  306:   quota_list
  307: } {A B C D}
  308: do_test quota-4.2.2 {
  309:   sqlite3_quota_set C 0 {}
  310:   sqlite3_quota_set B 0 {}
  311:   quota_list
  312: } {A D}
  313: do_test quota-4.2.3 {
  314:   sqlite3_quota_set A 0 {}
  315:   sqlite3_quota_set D 0 {}
  316:   quota_list
  317: } {}
  318: do_test quota-4.2.4 {
  319:   sqlite3_quota_set A 1000 {}
  320:   sqlite3_quota_set B 1000 {}
  321:   sqlite3_quota_set C 1000 {}
  322:   sqlite3_quota_set A 0 {}
  323:   sqlite3_quota_set B 0 {}
  324:   sqlite3_quota_set C 0 {}
  325:   quota_list
  326: } {}
  327: do_test quota-4.2.5 {
  328:   sqlite3_quota_set A 1000 {}
  329:   sqlite3_quota_set B 1000 {}
  330:   sqlite3_quota_set C 1000 {}
  331:   sqlite3_quota_set C 0 {}
  332:   sqlite3_quota_set B 0 {}
  333:   sqlite3_quota_set A 0 {}
  334:   quota_list
  335: } {}
  336: 
  337: do_test quota-4.3.1 {
  338:   sqlite3_quota_set A 1000 quota_callback
  339:   sqlite3 db A
  340:   sqlite3_quota_set A 0 quota_callback
  341:   db close
  342:   quota_list
  343: } {}
  344: 
  345: unset -nocomplain quotagroup
  346: if {$tcl_platform(platform)=="windows"} {
  347:   set quotagroup *\\quota-test-A?.db
  348: } else {
  349:   set quotagroup */quota-test-A?.db
  350: } 
  351: foreach file [glob -nocomplain quota-test-A*] {
  352:   forcedelete $file
  353: }
  354: do_test quota-4.4.1 {
  355:   set ::quota {}
  356:   sqlite3_quota_set $::quotagroup 10000 quota_callback
  357:   file delete -force ./quota-test-A1.db ./quota-test-A2.db
  358:   sqlite3 db ./quota-test-A1.db
  359:   db eval {
  360:      CREATE TABLE t1(x);
  361:      INSERT INTO t1 VALUES(randomblob(5000));
  362:   }
  363:   quota_list
  364: } [list $quotagroup]
  365: do_test quota-4.4.2 {
  366:   expr {$::quota==""}
  367: } {1}
  368: do_test quota-4.4.3 {
  369:   db close
  370:   sqlite3 db ./quota-test-A2.db
  371:   db eval {
  372:      CREATE TABLE t1(x);
  373:      INSERT INTO t1 VALUES(randomblob(5000));
  374:   }
  375:   quota_list
  376: } [list $quotagroup]
  377: do_test quota-4.4.4 {
  378:   expr {$::quota!=""}
  379: } {1}
  380: do_test quota-4.4.5 {
  381:   db close
  382:   sqlite3_quota_set $::quotagroup 0 {}
  383:   sqlite3_quota_dump
  384: } {}
  385: do_test quota-4.4.6 {
  386:   sqlite3_quota_set $quotagroup 10000 quota_callback
  387:   sqlite3 db quota-test-A1.db
  388:   db eval {SELECT count(*) FROM sqlite_master}
  389:   quota_size $quotagroup
  390: } [file size quota-test-A1.db]
  391: do_test quota-4.4.7 {
  392:   sqlite3_quota_file quota-test-A2.db
  393:   quota_size $::quotagroup
  394: } [expr {[file size quota-test-A1.db]+[file size quota-test-A2.db]}]
  395: 
  396: unset -nocomplain quotagroup
  397: if {$tcl_platform(platform)=="windows"} {
  398:   set quotagroup *\\quota-test-B*
  399: } else {
  400:   set quotagroup */quota-test-B*
  401: } 
  402: foreach file [glob -nocomplain quota-test-B*] {
  403:   forcedelete $file
  404: }
  405: do_test quota-4.5.1 {
  406:   sqlite3_quota_set $::quotagroup 100000 quota_callback
  407:   quota_size $::quotagroup
  408: } {0}
  409: do_test quota-4.5.2 {
  410:   sqlite3_quota_file quota-test-B1.txt
  411:   quota_size $::quotagroup
  412: } {0}
  413: proc add_to_file {name n} {
  414:   set out [open $name a]
  415:   fconfigure $out -translation binary
  416:   puts -nonewline $out [string repeat x $n]
  417:   close $out
  418: }
  419: do_test quota-4.5.3 {
  420:   add_to_file quota-test-B1.txt 123
  421:   sqlite3_quota_file quota-test-B1.txt
  422:   quota_size $::quotagroup
  423: } {123}
  424: do_test quota-4.5.4 {
  425:   add_to_file quota-test-B2.txt 234
  426:   sqlite3_quota_file quota-test-B2.txt
  427:   quota_size $::quotagroup
  428: } {357}
  429: do_test quota-4.5.5 {
  430:   add_to_file quota-test-B1.txt 2000
  431:   sqlite3_quota_file quota-test-B1.txt
  432:   quota_size $::quotagroup
  433: } {2357}
  434: do_test quota-4.5.6 {
  435:   forcedelete quota-test-B1.txt
  436:   sqlite3_quota_file quota-test-B1.txt
  437:   quota_size $::quotagroup
  438: } {234}
  439: do_test quota-4.5.7 {
  440:   forcedelete quota-test-B2.txt
  441:   sqlite3_quota_file quota-test-B2.txt
  442:   quota_size $::quotagroup
  443: } {0}
  444: do_test quota-4.5.8 {
  445:   add_to_file quota-test-B3.txt 1234
  446:   sqlite3_quota_file quota-test-B3.txt
  447:   quota_size $::quotagroup
  448: } {1234}
  449: do_test quota-4.5.9 {
  450:   sqlite3_quota_set $quotagroup 0 {}
  451:   quota_size $::quotagroup
  452: } {0}
  453: 
  454: do_test quota-4.9.1 {
  455:   db close
  456:   sqlite3_quota_set A 1000 quota_callback
  457:   sqlite3_quota_shutdown
  458: } {SQLITE_OK}
  459: do_test quota-4.9.2 {
  460:   quota_list
  461: } {}
  462: 
  463: #-------------------------------------------------------------------------
  464: # The following tests test that the quota VFS handles malloc and IO 
  465: # errors.
  466: #
  467: 
  468: sqlite3_quota_initialize "" 1
  469: sqlite3_quota_set *test.db 4096 {}
  470: 
  471: do_faultsim_test quota-5.1 -prep {
  472:   catch {db close}
  473: } -body {
  474:   sqlite3 db test2.db
  475: }
  476: do_faultsim_test quota-5.2 -prep {
  477:   catch {db close}
  478: } -body {
  479:   sqlite3 db test.db
  480: }
  481: 
  482: catch { db close }
  483: forcedelete test.db
  484: 
  485: do_test quota-5.3.prep {
  486:   sqlite3 db test.db
  487:   execsql {
  488:     PRAGMA auto_vacuum = 1;
  489:     PRAGMA page_size = 1024;
  490:     CREATE TABLE t1(a, b);
  491:     INSERT INTO t1 VALUES(10, zeroblob(1200));
  492:   }
  493:   faultsim_save_and_close
  494: } {}
  495: do_faultsim_test quota-5.3 -prep {
  496:   faultsim_restore_and_reopen
  497: } -body {
  498:   execsql { DELETE FROM t1 }
  499: }
  500: 
  501: do_test quota-5.4.1 {
  502:   catch { db close }
  503:   forcedelete test.db
  504:   file mkdir test.db
  505:   list [catch { sqlite3 db test.db } msg] $msg
  506: } {1 {unable to open database file}}
  507: 
  508: do_faultsim_test quota-5.5 -prep {
  509:   catch { sqlite3_quota_shutdown }
  510: } -body {
  511:   sqlite3_quota_initialize "" 1
  512: }
  513: 
  514: do_faultsim_test quota-5.6 -prep {
  515:   catch { sqlite3_quota_shutdown }
  516:   sqlite3_quota_initialize "" 1
  517: } -body {
  518:   sqlite3_quota_set * 4096 {}
  519: }
  520: 
  521: catch { sqlite3_quota_shutdown }
  522: finish_test

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>