-C Add\sthe\sability\sto\sDROP\sone\sor\smore\sobjects\sof\sthe\ssame\sclass\nin\sa\ssingle\sstatement\sby\slisting\sthe\sobjects\sas\smultiple\sarguments\sto\sthe\nDROP\scommand.
-D 2024-02-29T13:44:15.183
+C Attempt\sto\sfix\smulti-object\sDROP.\s\sWorking\sbetter,\sbut\sstill\snot\sperfect.
+D 2024-02-29T19:40:38.822
F .fossil-settings/empty-dirs dbb81e8fc0401ac46a1491ab34a7f2c7c0452f2f06b54ebb845d024ca8283ef1
F .fossil-settings/ignore-glob 35175cdfcf539b2318cb04a9901442804be81cd677d8b889fcc9149c21f239ea
F LICENSE.md df5091916dbb40e6e9686186587125e1b2ff51f022cc334e886c19a0e9982724
F src/btree.c 285b493d843e7ba8ef78b6ae7d31238e904901dbc0c484f7904de4cf18fd8802
F src/btree.h 55066f513eb095db935169dab1dc2f7c7a747ef223c533f5d4ad4dfed346cbd0
F src/btreeInt.h 98aadb6dcb77b012cab2574d6a728fad56b337fc946839b9898c4b4c969e30b6
-F src/build.c 786e47a8ccefa14fbdca52e22bc51dbe24074a9c7dbe4f2afd2050736a7352c5
+F src/build.c 25384963d1b9d6ebc73777bc7c1112973ba36ea8a8ca9f0a39bd94c047ba24eb
F src/callback.c db3a45e376deff6a16c0058163fe0ae2b73a2945f3f408ca32cf74960b28d490
F src/complete.c a3634ab1e687055cd002e11b8f43eb75c17da23e
F src/ctime.c 23331529e654be40ca97d171cbbffe9b3d4c71cc53b78fe5501230675952da8b
F src/delete.c cb766727c78e715f9fb7ec8a7d03658ed2a3016343ca687acfcec9083cdca500
F src/expr.c 2803f5e7e3458ced24c0de48ec3640cd7a68ec61350d99c9f30b1bcd6640bd61
F src/fault.c 460f3e55994363812d9d60844b2a6de88826e007
-F src/fkey.c a47610f0a5c6cb0ad79f8fcef039c01833dec0c751bb695f28dc0ec6a4c3ba00
+F src/fkey.c b7ecbc98b4da91d03e3435ca6abc167efa30f6691b090820969c4be625739e45
F src/func.c 4204c56196847faefef57fa14e43b8e4d65eb8d7e65318abe463472e3fd148cb
F src/global.c 765a0656d6cbf043cb272ff0ae38f39cc46713539ffe6793258ed3eb4b188b52
F src/hash.c 9ee4269fb1d6632a6fecfb9479c93a1f29271bddbbaf215dd60420bcb80c7220
F src/sqlite.h.in 19a2db3995a699bd7f6dfb423856242bfceb7ec849a93c91d241d19fc28d9f0f
F src/sqlite3.rc 5121c9e10c3964d5755191c80dd1180c122fc3a8
F src/sqlite3ext.h 3f046c04ea3595d6bfda99b781926b17e672fd6d27da2ba6d8d8fc39981dcb54
-F src/sqliteInt.h 58b7295a748ca5ed9e211510205b4a66a24c68f864225b81e19d4cf6038b40a1
+F src/sqliteInt.h bdb0bba047cd39c8733c14131c379a91f3d1f437c57f11270db14860ab09dffd
F src/sqliteLimit.h 6878ab64bdeb8c24a1d762d45635e34b96da21132179023338c93f820eee6728
F src/status.c cb11f8589a6912af2da3bb1ec509a94dd8ef27df4d4c1a97e0bcf2309ece972b
F src/table.c 0f141b58a16de7e2fbe81c308379e7279f4c6b50eb08efeec5892794a0ba30d1
F src/threads.c 4ae07fa022a3dc7c5beb373cf744a85d3c5c6c3c
F src/tokenize.c 3f703cacdab728d7741e5a6ac242006d74fe1c2754d4f03ed889d7253259bd68
F src/treeview.c c6fc972683fd00f975d8b32a81c1f25d2fb7d4035366bf45c9f5622d3ccd70ee
-F src/trigger.c a23049b9771927763ade8389fb6a0494324bad15394893895f6aa4e346e6b295
+F src/trigger.c a6fd09ef8b4613db9b9db046ff5abacda4bf517a09da889031d22c7c18ac6c49
F src/update.c 6904814dd62a7a93bbb86d9f1419c7f134a9119582645854ab02b36b676d9f92
F src/upsert.c fa125a8d3410ce9a97b02cb50f7ae68a2476c405c76aa692d3acf6b8586e9242
F src/utf.c f23165685a67b4caf8ec08fb274cb3f319103decfb2a980b7cfd55d18dfa855e
F test/distinct.test 691c9e850b0d0b56b66e7e235453198cb4cf0760e324b7403d3c5abbeab0a014
F test/distinct2.test bb71cc7b5e58e895787f9910a788c254f679928d324732d063fe9bc202ecbe71
F test/distinctagg.test 40d7169ae5846caaf62c6e307d2ca3c333daf9b6f7cde888956a339a97afe85f
-F test/drop-many.test 30dd091a4fd0a04b1a38e70c93f69c55749e62a3d895ac5e09277cd97caa5bbf w test/drop1.test
+F test/drop-many.test 30dd091a4fd0a04b1a38e70c93f69c55749e62a3d895ac5e09277cd97caa5bbf
F test/e_blobbytes.test 4c01dfe4f12087b92b20705a3fdfded45dc4ed16d5a211fed4e1d2786ba68a52
F test/e_blobclose.test 692fc02a058476c2222a63d97e3f3b2b809c1842e5525ded7f854d540ac2e075
F test/e_blobopen.test 29f6055ee453b8e679fe9570c4d3acfedbef821622c5dad16875148c5952ef50
F vsixtest/vsixtest.vcxproj.data 2ed517e100c66dc455b492e1a33350c1b20fbcdc
F vsixtest/vsixtest.vcxproj.filters 37e51ffedcdb064aad6ff33b6148725226cd608e
F vsixtest/vsixtest_TemporaryKey.pfx e5b1b036facdb453873e7084e1cae9102ccc67a0
-P 803481f25020f3c25941f1e7d1a8071937820dea951e8798198b0b0fa3fb48ce
-R b06b7d333b1bcab630a4dab891f8b26c
+P 2266086cf08ee710338667d1cf0b1e81ce7380101707db272ce27124404068a0
+R d3490d0df600a6062bf18828bf499fc3
U drh
-Z 594e686b84606bfb7b18560464880c6c
+Z 68bbccadbf2f82f26c1558f6e4711d24
# Remove this line to create a well-formed Fossil manifest.
-2266086cf08ee710338667d1cf0b1e81ce7380101707db272ce27124404068a0
\ No newline at end of file
+02f9fc73eef80f528097581580977aae46942baac2d7fb205c52f7f25472f2a8
\ No newline at end of file
*/
void sqlite3DropTable(Parse *pParse, SrcList *pName, int isView, int noErr){
Table *pTab;
- Vdbe *v;
sqlite3 *db = pParse->db;
int iDb;
int ii;
+ (void)sqlite3GetVdbe(pParse);
sqlite3ReadSchema(pParse);
assert( pName!=0 || pParse->nErr!=0 );
for(ii=0; pParse->nErr==0 && ii<pName->nSrc; ii++){
break;
}
#endif
+ /* If this table or view has appeared previously in the list of tables
+ ** or views to be dropped, then the prior appearance is sufficient so
+ ** skip this one. */
+ if( ii>0 ){
+ int jj;
+ for(jj=0; jj<ii && pName->a[jj].pTab!=pTab; jj++){}
+ if( jj<ii ) continue;
+ }
- /* Generate code to remove the table from the schema table
- ** on disk.
- */
- v = sqlite3GetVdbe(pParse);
- if( v ){
+ /* Remember the table for use in the second pass */
+ pName->a[ii].pTab = pTab;
+ pTab->nTabRef++;
+ }
+
+ for(ii=0; pParse->nErr==0 && ii<pName->nSrc; ii++){
+ pTab = pName->a[ii].pTab;
+ if( pTab ){
+ iDb = sqlite3SchemaToIndex(db, pTab->pSchema);
+
+ /* Generate code to clear this table from sqlite_statN and to
+ ** cascade foreign key constraints.
+ */
sqlite3BeginWriteOperation(pParse, 1, iDb);
- if( !isView ){
+ if( IsOrdinaryTable(pTab) ){
sqlite3ClearStatTables(pParse, iDb, "tbl", pTab->zName);
- sqlite3FkDropTable(pParse, pName, pTab);
+ sqlite3FkDropTable(pParse, &pName->a[ii], pTab);
}
+ }
+ }
+
+ /* Generate code to actually delete the tables/views in a second pass. */
+ for(ii=0; pParse->nErr==0 && ii<pName->nSrc; ii++){
+ pTab = pName->a[ii].pTab;
+ if( pTab ){
+ iDb = sqlite3SchemaToIndex(db, pTab->pSchema);
sqlite3CodeDropTable(pParse, pTab, iDb, isView);
}
}
*/
void sqlite3DropIndex(Parse *pParse, SrcList *pName, int ifExists){
Index *pIndex;
- Vdbe *v;
sqlite3 *db = pParse->db;
+ Vdbe *v;
int iDb;
int ii;
}
#endif
+ /* Skip over redundant DROP INDEXes */
+ if( ii>0 ){
+ int jj;
+ for(jj=0; jj<ii; jj++){
+ if( pName->a[jj].addrFillSub!=iDb ) continue;
+ if( pName->a[jj].regReturn!=pIndex->tnum ) continue;
+ break;
+ }
+ if( jj<ii ) continue;
+ }
+ pName->a[ii].addrFillSub = iDb;
+ pName->a[ii].regReturn = pIndex->tnum;
+
/* Generate code to remove the index and from the schema table */
v = sqlite3GetVdbe(pParse);
- if( v ){
- sqlite3BeginWriteOperation(pParse, 1, iDb);
- sqlite3NestedParse(pParse,
- "DELETE FROM %Q." LEGACY_SCHEMA_TABLE
- " WHERE name=%Q AND type='index'",
- db->aDb[iDb].zDbSName, pIndex->zName
- );
- sqlite3ClearStatTables(pParse, iDb, "idx", pIndex->zName);
- sqlite3ChangeCookie(pParse, iDb);
- destroyRootPage(pParse, pIndex->tnum, iDb);
- sqlite3VdbeAddOp4(v, OP_DropIndex, iDb, 0, 0, pIndex->zName, 0);
- }
+ if( v==0 ) break;
+ sqlite3BeginWriteOperation(pParse, 1, iDb);
+ sqlite3NestedParse(pParse,
+ "DELETE FROM %Q." LEGACY_SCHEMA_TABLE
+ " WHERE name=%Q AND type='index'",
+ db->aDb[iDb].zDbSName, pIndex->zName
+ );
+ sqlite3ClearStatTables(pParse, iDb, "idx", pIndex->zName);
+ sqlite3ChangeCookie(pParse, iDb);
+ destroyRootPage(pParse, pIndex->tnum, iDb);
+ sqlite3VdbeAddOp4(v, OP_DropIndex, iDb, 0, 0, pIndex->zName, 0);
}
sqlite3SrcListDelete(db, pName);
}
** the table from the database. Triggers are disabled while running this
** DELETE, but foreign key actions are not.
*/
-void sqlite3FkDropTable(Parse *pParse, SrcList *pName, Table *pTab){
+void sqlite3FkDropTable(Parse *pParse, SrcItem *pName, Table *pTab){
sqlite3 *db = pParse->db;
if( (db->flags&SQLITE_ForeignKeys) && IsOrdinaryTable(pTab) ){
int iSkip = 0;
Vdbe *v = sqlite3GetVdbe(pParse);
+ SrcList *pSrc;
assert( v ); /* VDBE has already been allocated */
assert( IsOrdinaryTable(pTab) );
}
pParse->disableTriggers = 1;
- sqlite3DeleteFrom(pParse, sqlite3SrcListDup(db, pName, 0), 0, 0, 0);
+ pSrc = sqlite3SrcListAppend(pParse, 0, 0, 0);
+ if( pSrc ){
+ pSrc->a[0].zDatabase = sqlite3DbStrDup(db, pName->zDatabase);
+ pSrc->a[0].zName = sqlite3DbStrDup(db, pName->zName);
+ sqlite3DeleteFrom(pParse, pSrc, 0, 0, 0);
+ }
pParse->disableTriggers = 0;
/* If the DELETE has generated immediate foreign key constraint
union {
Index *pIBIndex; /* Index structure corresponding to u1.zIndexedBy */
CteUse *pCteUse; /* CTE Usage info when fg.isCte is true */
+ Trigger *pTrig; /* Trigger in argument list of DROP TRIGGER */
} u2;
};
*/
#if !defined(SQLITE_OMIT_FOREIGN_KEY) && !defined(SQLITE_OMIT_TRIGGER)
void sqlite3FkCheck(Parse*, Table*, int, int, int*, int);
- void sqlite3FkDropTable(Parse*, SrcList *, Table*);
+ void sqlite3FkDropTable(Parse*, SrcItem*, Table*);
void sqlite3FkActions(Parse*, Table*, ExprList*, int, int*, int);
int sqlite3FkRequired(Parse*, Table*, int*, int);
u32 sqlite3FkOldmask(Parse*, Table*);
pTrigger = sqlite3HashFind(&(db->aDb[j].pSchema->trigHash), zName);
if( pTrigger ) break;
}
+ pName->a[ii].u2.pTrig = pTrigger;
if( !pTrigger ){
if( !noErr ){
sqlite3ErrorMsg(pParse, "no such trigger: %S", pName->a+ii);
testcase( ii>0 );
testcase( ii+1<pName->nSrc );
pParse->checkSchema = 1;
- }else{
- sqlite3DropTriggerPtr(pParse, pTrigger);
+ continue;
+ }
+ if( ii>0 ){
+ int jj;
+ for(jj=0; jj<ii; jj++){
+ if( pName->a[jj].u2.pTrig==pTrigger ) break;
+ }
+ if( jj<ii ) continue;
}
+ sqlite3DropTriggerPtr(pParse, pTrigger);
}
sqlite3SrcListDelete(db, pName);
}