aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authordrh <drh@noemail.net>2019-10-16 14:56:03 +0000
committerdrh <drh@noemail.net>2019-10-16 14:56:03 +0000
commit2da8d6fe7428fb9f82b5224b7adb9c65098e459c (patch)
treee0fa6a062edffd9cd959ee1b75080a190a2e54a3 /src
parent4ec3e820a00c5372972a0f1b143b2797b21ffb9f (diff)
downloadsqlite-2da8d6fe7428fb9f82b5224b7adb9c65098e459c.tar.gz
sqlite-2da8d6fe7428fb9f82b5224b7adb9c65098e459c.zip
If an AFTER DELETE trigger fires when a conflict row is deleted by REPLACE
conflict resolution, make sure the conflict really has been resolved and that the trigger did not recreate the row before continuing. Ticket [a8a4847a2d96f5de] FossilOrigin-Name: eea1e7aa57e74c4329003f4550168e2aed9e33d2301a3ba84b10781a9cebbc1b
Diffstat (limited to 'src')
-rw-r--r--src/insert.c9
1 files changed, 9 insertions, 0 deletions
diff --git a/src/insert.c b/src/insert.c
index d9078b89d..690845a7d 100644
--- a/src/insert.c
+++ b/src/insert.c
@@ -1582,6 +1582,8 @@ void sqlite3GenerateConstraintChecks(
sqlite3MultiWrite(pParse);
sqlite3GenerateRowDelete(pParse, pTab, pTrigger, iDataCur, iIdxCur,
regNewData, 1, 0, OE_Replace, 1, -1);
+ sqlite3VdbeAddOp3(v, OP_NotExists, iDataCur, addrRowidOk, regNewData);
+ sqlite3RowidConstraint(pParse, OE_Abort, pTab);
}else{
#ifdef SQLITE_ENABLE_PREUPDATE_HOOK
assert( HasRowid(pTab) );
@@ -1829,16 +1831,23 @@ void sqlite3GenerateConstraintChecks(
}
default: {
Trigger *pTrigger = 0;
+ int bRetryConstraintCheck = 0;
assert( onError==OE_Replace );
if( db->flags&SQLITE_RecTriggers ){
pTrigger = sqlite3TriggersExist(pParse, pTab, TK_DELETE, 0, 0);
}
if( pTrigger || sqlite3FkRequired(pParse, pTab, 0, 0) ){
sqlite3MultiWrite(pParse);
+ bRetryConstraintCheck = 1;
}
sqlite3GenerateRowDelete(pParse, pTab, pTrigger, iDataCur, iIdxCur,
regR, nPkField, 0, OE_Replace,
(pIdx==pPk ? ONEPASS_SINGLE : ONEPASS_OFF), iThisCur);
+ if( bRetryConstraintCheck ){
+ sqlite3VdbeAddOp4Int(v, OP_NoConflict, iThisCur, addrUniqueOk,
+ regIdx, pIdx->nKeyCol); VdbeCoverage(v);
+ sqlite3UniqueConstraint(pParse, OE_Abort, pIdx);
+ }
seenReplace = 1;
break;
}