diff --git a/manifest b/manifest index 1e706f6843..f7cf4c926f 100644 --- a/manifest +++ b/manifest @@ -1,5 +1,5 @@ -C Make\ssqlite3_count_changes()\sand\stotal_changes()\swork\swith\s"DELETE\sFROM\s".\s(CVS\s5844) -D 2008-10-27T13:59:34 +C If\san\sSQLITE_DELETE\sauthorization\scallback\sreturns\sSQLITE_IGNORE,\sproceed\swith\sthe\sdelete\soperation\sbut\sdisable\sthe\struncate\soptimization.\s(CVS\s5845) +D 2008-10-27T15:34:33 F Makefile.arm-wince-mingw32ce-gcc fcd5e9cd67fe88836360bb4f9ef4cb7f8e2fb5a0 F Makefile.in 3fe17eccd87d385b5adc9766828716cfdd154d6b F Makefile.linux-gcc d53183f4aa6a9192d249731c90dbdffbd2c68654 @@ -106,7 +106,7 @@ F src/build.c d6d55f97abcb6f17ac3e9e7a1dd8c0db67db34fd F src/callback.c e970e5beddbdb23f89a6d05cb1a6419d9f755624 F src/complete.c cb14e06dbe79dee031031f0d9e686ff306afe07c F src/date.c 6f4277fa56d8c1b8e70c0bde838c9e99609f5ec0 -F src/delete.c b0b7c499ccf28c1857905c9cf42f4ddc49bf7331 +F src/delete.c f77efc8c63e656316e038b9bff014c6fd7b13f00 F src/expr.c 2b1945314fdc661fb04306cb86bd8516cfd12d4a F src/fault.c dc88c821842157460750d2d61a8a8b4197d047ff F src/func.c 8431b40a7843d1024145684d303c55b4ee087bbe @@ -218,8 +218,9 @@ F test/attach.test 75a5d22f88e730967d68f2c9f95e786e3953d8e3 F test/attach2.test a295d2d7061adcee5884ef4a93c7c96a82765437 F test/attach3.test 7b92dc8e40c1ebca9732ca6f2d3fefbd46f196df F test/attachmalloc.test cf8cf17d183de357b1147a9baacbdfc85b940b61 -F test/auth.test 9eb4b6b99eee54c95711c74c4b9694acf4d850ed +F test/auth.test 0e901aeb399f766fd58f5e19b8b9a09e2df9a341 F test/auth2.test ee3ba272e2b975e913afc9b041ee75706e190005 +F test/auth3.test b3308950d3839a45193cdcd0473432e33fe38b61 F test/autoinc.test ab549b48b389cabd92967b86c379ec8b31fa6c16 F test/autovacuum.test 61260e25744189ff766f61ca3df23c1eeec0060e F test/autovacuum_ioerr2.test 598b0663074d3673a9c1bc9a16e80971313bafe6 @@ -651,7 +652,7 @@ F tool/speedtest16.c c8a9c793df96db7e4933f0852abb7a03d48f2e81 F tool/speedtest2.tcl ee2149167303ba8e95af97873c575c3e0fab58ff F tool/speedtest8.c 2902c46588c40b55661e471d7a86e4dd71a18224 F tool/speedtest8inst1.c 293327bc76823f473684d589a8160bde1f52c14e -P 297ad90dd3a69002e6e4175e9e3938b3a627574d -R a6b93c46cddb9e42feecabc035375dbb +P e68e4282adb9003aa297d033aeb5d9cadee215cd +R 7698d63a46c3061737eee132dee3f7c9 U danielk1977 -Z 98ec3e2e89a662c96092f7315cee2195 +Z 43f7a2c2ff97da790b34dc2cf861e4e2 diff --git a/manifest.uuid b/manifest.uuid index 10af588145..e3198fdaa1 100644 --- a/manifest.uuid +++ b/manifest.uuid @@ -1 +1 @@ -e68e4282adb9003aa297d033aeb5d9cadee215cd \ No newline at end of file +65a2e131732399f0f14f982eb0689482fdb87b6c \ No newline at end of file diff --git a/src/delete.c b/src/delete.c index 382f1a67f0..5f1f9027d8 100644 --- a/src/delete.c +++ b/src/delete.c @@ -12,7 +12,7 @@ ** This file contains C code routines that are called by the parser ** in order to generate code for DELETE FROM statements. ** -** $Id: delete.c,v 1.184 2008/10/27 13:59:34 danielk1977 Exp $ +** $Id: delete.c,v 1.185 2008/10/27 15:34:33 danielk1977 Exp $ */ #include "sqliteInt.h" @@ -234,6 +234,7 @@ void sqlite3DeleteFrom( NameContext sNC; /* Name context to resolve expressions in */ int iDb; /* Database number */ int memCnt = -1; /* Memory cell used for change counting */ + int rcauth; /* Value returned by authorization callback */ #ifndef SQLITE_OMIT_TRIGGER int isView; /* True if attempting to delete from a view */ @@ -281,7 +282,9 @@ void sqlite3DeleteFrom( iDb = sqlite3SchemaToIndex(db, pTab->pSchema); assert( iDbnDb ); zDb = db->aDb[iDb].zName; - if( sqlite3AuthCheck(pParse, SQLITE_DELETE, pTab->zName, 0, zDb) ){ + rcauth = sqlite3AuthCheck(pParse, SQLITE_DELETE, pTab->zName, 0, zDb); + assert( rcauth==SQLITE_OK || rcauth==SQLITE_DENY || rcauth==SQLITE_IGNORE ); + if( rcauth==SQLITE_DENY ){ goto delete_from_cleanup; } assert(!isView || triggers_exist); @@ -370,7 +373,7 @@ void sqlite3DeleteFrom( ** It is easier just to erase the whole table. Note, however, that ** this means that the row change count will be incorrect. */ - if( pWhere==0 && !triggers_exist && !IsVirtual(pTab) ){ + if( rcauth==SQLITE_OK && pWhere==0 && !triggers_exist && !IsVirtual(pTab) ){ assert( !isView ); sqlite3VdbeAddOp3(v, OP_Clear, pTab->tnum, iDb, memCnt); if( !pParse->nested ){ diff --git a/test/auth.test b/test/auth.test index ada28d2d0c..1cb2e324c3 100644 --- a/test/auth.test +++ b/test/auth.test @@ -12,7 +12,7 @@ # focus of this script is testing the sqlite3_set_authorizer() API # and related functionality. # -# $Id: auth.test,v 1.43 2008/07/02 13:13:52 danielk1977 Exp $ +# $Id: auth.test,v 1.44 2008/10/27 15:34:33 danielk1977 Exp $ # set testdir [file dirname $argv0] @@ -418,7 +418,10 @@ do_test auth-1.49 { } {0 {}} do_test auth-1.50 { execsql {SELECT * FROM t2} -} {11 2 33} +} {} +do_test auth-1.50.2 { + execsql {INSERT INTO t2 VALUES(11, 2, 33)} +} {} do_test auth-1.51 { proc auth {code arg1 arg2 arg3 arg4} { diff --git a/test/auth3.test b/test/auth3.test new file mode 100644 index 0000000000..0d99cac765 --- /dev/null +++ b/test/auth3.test @@ -0,0 +1,111 @@ +# 2008 October 27 +# +# 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. +# +#*********************************************************************** +# +# Test that the truncate optimization is disabled if the SQLITE_DELETE +# authorization callback returns SQLITE_IGNORE. +# +# $Id: auth3.test,v 1.1 2008/10/27 15:34:33 danielk1977 Exp $ +# + +set testdir [file dirname $argv0] +source $testdir/tester.tcl + +# disable this test if the SQLITE_OMIT_AUTHORIZATION macro is +# defined during compilation. +if {[catch {db auth {}} msg]} { + finish_test + return +} + +# Disable the statement cache for these tests. +# +db cache size 0 + +db authorizer ::auth +proc auth {code arg1 arg2 arg3 arg4} { + if {$code=="SQLITE_DELETE"} { + return $::authcode + } + return SQLITE_OK +} + +#-------------------------------------------------------------------------- +# The following tests - auth3-1.* - test that return values of SQLITE_DENY, +# SQLITE_IGNORE, SQLITE_OK and are correctly handled when returned +# by an SQLITE_DELETE authorization callback triggered by a +# "DELETE FROM " statement. +# +do_test auth3-1.1 { + execsql { + CREATE TABLE t1(a,b,c); + INSERT INTO t1 VALUES(1, 2, 3); + INSERT INTO t1 VALUES(4, 5, 6); + } +} {} +do_test auth3.1.2 { + set ::authcode SQLITE_DENY + catchsql { DELETE FROM t1 } +} {1 {not authorized}} +do_test auth3.1.3 { + set ::authcode SQLITE_INVALID + catchsql { DELETE FROM t1 } +} {1 {illegal return value (1) from the authorization function - should be SQLITE_OK, SQLITE_IGNORE, or SQLITE_DENY}} +do_test auth3.1.4 { + execsql { SELECT * FROM t1 } +} {1 2 3 4 5 6} +do_test auth3-1.5 { + set ::authcode SQLITE_IGNORE + execsql { + DELETE FROM t1; + SELECT * FROM t1; + } +} {} +do_test auth3-1.6 { + set ::authcode SQLITE_OK + execsql { + INSERT INTO t1 VALUES(1, 2, 3); + INSERT INTO t1 VALUES(4, 5, 6); + DELETE FROM t1; + SELECT * FROM t1; + } +} {} + +#-------------------------------------------------------------------------- +# These tests - auth3-2.* - test that returning SQLITE_IGNORE really does +# disable the truncate optimization. +# +do_test auth3-2.1 { + set ::authcode SQLITE_OK + execsql { + INSERT INTO t1 VALUES(1, 2, 3); + INSERT INTO t1 VALUES(4, 5, 6); + } + set sqlite_search_count 0 + execsql { + DELETE FROM t1; + } + set sqlite_search_count +} {0} + +do_test auth3-2.2 { + set ::authcode SQLITE_IGNORE + execsql { + INSERT INTO t1 VALUES(1, 2, 3); + INSERT INTO t1 VALUES(4, 5, 6); + } + set sqlite_search_count 0 + execsql { + DELETE FROM t1; + } + set sqlite_search_count +} {1} + +finish_test