/ Check-in [42138891]
Login

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

Overview
Comment:Add an assert() to help verify that OP_AggInverse is never called on an accumulator that has not previously been processed by OP_AggStep.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA3-256: 4213889103fa37f3f11802aea81989522048a0752820603dd556f612128ddfee
User & Date: drh 2018-07-07 19:36:04
Context
2018-07-07
19:47
Add ALWAYS() macros on results of sqlite3_aggregate_context() calls in xInverse() implements, since they can never fail. check-in: fdef2a92 user: drh tags: trunk
19:36
Add an assert() to help verify that OP_AggInverse is never called on an accumulator that has not previously been processed by OP_AggStep. check-in: 42138891 user: drh tags: trunk
17:38
Add missing VdbeCoverage() macro to window.c. check-in: 63f4d306 user: dan tags: trunk
Changes
Hide Diffs Side-by-Side Diffs Ignore Whitespace Patch

Changes to src/vdbe.c.

  1151   1151     int cnt;
  1152   1152     u16 nullFlag;
  1153   1153     pOut = out2Prerelease(p, pOp);
  1154   1154     cnt = pOp->p3-pOp->p2;
  1155   1155     assert( pOp->p3<=(p->nMem+1 - p->nCursor) );
  1156   1156     pOut->flags = nullFlag = pOp->p1 ? (MEM_Null|MEM_Cleared) : MEM_Null;
  1157   1157     pOut->n = 0;
         1158  +#ifdef SQLITE_DEBUG
         1159  +  pOut->uTemp = 0;
         1160  +#endif
  1158   1161     while( cnt>0 ){
  1159   1162       pOut++;
  1160   1163       memAboutToChange(p, pOut);
  1161   1164       sqlite3VdbeMemSetNull(pOut);
  1162   1165       pOut->flags = nullFlag;
  1163   1166       pOut->n = 0;
  1164   1167       cnt--;
................................................................................
  6347   6350     pCtx->iOp = (int)(pOp - aOp);
  6348   6351     pCtx->pVdbe = p;
  6349   6352     pCtx->skipFlag = 0;
  6350   6353     pCtx->isError = 0;
  6351   6354     pCtx->argc = n;
  6352   6355     pOp->p4type = P4_FUNCCTX;
  6353   6356     pOp->p4.pCtx = pCtx;
         6357  +
         6358  +  /* OP_AggInverse must have P1==1 and OP_AggStep must have P1==0 */
  6354   6359     assert( pOp->p1==(pOp->opcode==OP_AggInverse) );
         6360  +
  6355   6361     pOp->opcode = OP_AggStep1;
  6356   6362     /* Fall through into OP_AggStep */
  6357   6363   }
  6358   6364   case OP_AggStep1: {
  6359   6365     int i;
  6360   6366     sqlite3_context *pCtx;
  6361   6367     Mem *pMem;
  6362   6368   
  6363   6369     assert( pOp->p4type==P4_FUNCCTX );
  6364   6370     pCtx = pOp->p4.pCtx;
  6365   6371     pMem = &aMem[pOp->p3];
         6372  +
         6373  +#ifdef SQLITE_DEBUG
         6374  +  if( pOp->p1 ){
         6375  +    /* This is an OP_AggInverse call.  Verify that xStep has always
         6376  +    ** been called at least once prior to any xInverse call. */
         6377  +    assert( pMem->uTemp==0x1122e0e3 );
         6378  +  }else{
         6379  +    /* This is an OP_AggStep call.  Mark it as such. */
         6380  +    pMem->uTemp = 0x1122e0e3;
         6381  +  }
         6382  +#endif
  6366   6383   
  6367   6384     /* If this function is inside of a trigger, the register array in aMem[]
  6368   6385     ** might change from one evaluation to the next.  The next block of code
  6369   6386     ** checks to see if the register array has changed, and if so it
  6370   6387     ** reinitializes the relavant parts of the sqlite3_context object */
  6371   6388     if( pCtx->pMem != pMem ){
  6372   6389       pCtx->pMem = pMem;