/ Check-in [6acbdba5]
Login

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Simplification to the implementation of OP_Insert.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA3-256:6acbdba59e9df4313a6232d925a70390acdc43dfa380b4fba7bb8bd442d6e728
User & Date: drh 2018-01-12 19:33:18
Context
2018-01-12
23:38
Add the sqlite3_value_nochange() API, usable from within the xUpdate method of a virtual table to discover whether or not a column was unchanged at the SQL level. check-in: dec3ea4e user: drh tags: trunk
21:00
Add the experimental sqlite3_value_nochange() interface usable by xUpdate methods of virtual tables to see if a column has actually changed values. check-in: 8b7be15e user: drh tags: sqlite3_value_nochange
19:33
Simplification to the implementation of OP_Insert. check-in: 6acbdba5 user: drh tags: trunk
19:20
Fix error handling in sqlite3session_diff() when it is invoked for table "sqlite_stat1". check-in: 874285e4 user: dan tags: trunk
Changes
Hide Diffs Side-by-Side Diffs Ignore Whitespace Patch

Changes to src/vdbe.c.

  4411   4411   case OP_InsertInt: {
  4412   4412     Mem *pData;       /* MEM cell holding data for the record to be inserted */
  4413   4413     Mem *pKey;        /* MEM cell holding key  for the record */
  4414   4414     VdbeCursor *pC;   /* Cursor to table into which insert is written */
  4415   4415     int seekResult;   /* Result of prior seek or 0 if no USESEEKRESULT flag */
  4416   4416     const char *zDb;  /* database name - used by the update hook */
  4417   4417     Table *pTab;      /* Table structure - used by update and pre-update hooks */
  4418         -  int op;           /* Opcode for update hook: SQLITE_UPDATE or SQLITE_INSERT */
  4419   4418     BtreePayload x;   /* Payload to be inserted */
  4420   4419   
  4421         -  op = 0;
  4422   4420     pData = &aMem[pOp->p2];
  4423   4421     assert( pOp->p1>=0 && pOp->p1<p->nCursor );
  4424   4422     assert( memIsValid(pData) );
  4425   4423     pC = p->apCsr[pOp->p1];
  4426   4424     assert( pC!=0 );
  4427   4425     assert( pC->eCurType==CURTYPE_BTREE );
  4428   4426     assert( pC->uc.pCursor!=0 );
................................................................................
  4442   4440     }
  4443   4441   
  4444   4442     if( pOp->p4type==P4_TABLE && HAS_UPDATE_HOOK(db) ){
  4445   4443       assert( pC->iDb>=0 );
  4446   4444       zDb = db->aDb[pC->iDb].zDbSName;
  4447   4445       pTab = pOp->p4.pTab;
  4448   4446       assert( (pOp->p5 & OPFLAG_ISNOOP) || HasRowid(pTab) );
  4449         -    op = ((pOp->p5 & OPFLAG_ISUPDATE) ? SQLITE_UPDATE : SQLITE_INSERT);
  4450   4447     }else{
  4451         -    pTab = 0; /* Not needed.  Silence a compiler warning. */
         4448  +    pTab = 0;
  4452   4449       zDb = 0;  /* Not needed.  Silence a compiler warning. */
  4453   4450     }
  4454   4451   
  4455   4452   #ifdef SQLITE_ENABLE_PREUPDATE_HOOK
  4456   4453     /* Invoke the pre-update hook, if any */
  4457         -  if( pOp->p4type==P4_TABLE ){
         4454  +  if( pTab ){
  4458   4455       if( db->xPreUpdateCallback && !(pOp->p5 & OPFLAG_ISUPDATE) ){
  4459   4456         sqlite3VdbePreUpdateHook(p, pC, SQLITE_INSERT, zDb, pTab, x.nKey,pOp->p2);
  4460   4457       }
  4461         -    if( op && pTab->aCol==0 ){
  4462         -      assert( sqlite3_stricmp(pTab->zName, "sqlite_stat1")==0 );
  4463         -      op = 0;
         4458  +    if( db->xUpdateCallback==0 || pTab->aCol==0 ){
         4459  +      /* Prevent post-update hook from running in cases when it should not */
         4460  +      pTab = 0;
  4464   4461       }
  4465   4462     }
  4466   4463     if( pOp->p5 & OPFLAG_ISNOOP ) break;
  4467   4464   #endif
  4468   4465   
  4469   4466     if( pOp->p5 & OPFLAG_NCHANGE ) p->nChange++;
  4470   4467     if( pOp->p5 & OPFLAG_LASTROWID ) db->lastRowid = x.nKey;
................................................................................
  4482   4479         (pOp->p5 & (OPFLAG_APPEND|OPFLAG_SAVEPOSITION)), seekResult
  4483   4480     );
  4484   4481     pC->deferredMoveto = 0;
  4485   4482     pC->cacheStatus = CACHE_STALE;
  4486   4483   
  4487   4484     /* Invoke the update-hook if required. */
  4488   4485     if( rc ) goto abort_due_to_error;
  4489         -  if( db->xUpdateCallback && op ){
  4490         -    assert( pTab->aCol );
  4491         -    db->xUpdateCallback(db->pUpdateArg, op, zDb, pTab->zName, x.nKey);
         4486  +  if( pTab ){
         4487  +    assert( db->xUpdateCallback!=0 );
         4488  +    assert( pTab->aCol!=0 );
         4489  +    db->xUpdateCallback(db->pUpdateArg,
         4490  +           (pOp->p5 & OPFLAG_ISUPDATE) ? SQLITE_UPDATE : SQLITE_INSERT,
         4491  +           zDb, pTab->zName, x.nKey);
  4492   4492     }
  4493   4493     break;
  4494   4494   }
  4495   4495   
  4496   4496   /* Opcode: Delete P1 P2 P3 P4 P5
  4497   4497   **
  4498   4498   ** Delete the record at which the P1 cursor is currently pointing.