/ Check-in [cff1b36a]
Login

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

Overview
Comment:Suppress excess OP_Null opcodes caused by binary IS or IS NOT operators that are converted into unary ISNULL or NOTNULL operators.
Downloads: Tarball | ZIP archive | SQL archive
Timelines: family | ancestors | descendants | both | trunk
Files: files | file ages | folders
SHA1: cff1b36ab2c417611f59e96694005c03762788d2
User & Date: drh 2009-11-12 03:46:34
Context
2009-11-12
04:26
Suppress unnecessary OP_Noop instructions on when the right table of a LEFT JOIN uses the index-only optimization. check-in: e8aec08b user: drh tags: trunk
03:46
Suppress excess OP_Null opcodes caused by binary IS or IS NOT operators that are converted into unary ISNULL or NOTNULL operators. check-in: cff1b36a user: drh tags: trunk
03:13
Adjustments to the implementation of LIMIT so that it uses fewer opcodes. check-in: 39d5b292 user: drh tags: trunk
Changes
Hide Diffs Side-by-Side Diffs Ignore Whitespace Patch

Changes to src/parse.y.

   879    879       pOut->zStart = pOperand->zStart;
   880    880       pOut->zEnd = &pPostOp->z[pPostOp->n];
   881    881     }                           
   882    882   }
   883    883   
   884    884   expr(A) ::= expr(X) ISNULL|NOTNULL(E).   {spanUnaryPostfix(&A,pParse,@E,&X,&E);}
   885    885   expr(A) ::= expr(X) NOT NULL(E). {spanUnaryPostfix(&A,pParse,TK_NOTNULL,&X,&E);}
          886  +
          887  +%include {
          888  +  /* A routine to convert a binary TK_IS or TK_ISNOT expression into a
          889  +  ** unary TK_ISNULL or TK_NOTNULL expression. */
          890  +  static void binaryToUnaryIfNull(Parse *pParse, Expr *pY, Expr *pA, int op){
          891  +    sqlite3 *db = pParse->db;
          892  +    if( db->mallocFailed==0 && pY->op==TK_NULL ){
          893  +      pA->op = op;
          894  +      sqlite3ExprDelete(db, pA->pRight);
          895  +      pA->pRight = 0;
          896  +    }
          897  +  }
          898  +}
   886    899   
   887    900   //    expr1 IS expr2
   888    901   //    expr1 IS NOT expr2
   889    902   //
   890    903   // If expr2 is NULL then code as TK_ISNULL or TK_NOTNULL.  If expr2
   891    904   // is any other expression, code as TK_IS or TK_ISNOT.
   892    905   // 
   893    906   expr(A) ::= expr(X) IS expr(Y).     {
   894    907     spanBinaryExpr(&A,pParse,TK_IS,&X,&Y);
   895         -  if( pParse->db->mallocFailed==0  && Y.pExpr->op==TK_NULL ){
   896         -    A.pExpr->op = TK_ISNULL;
   897         -  }
          908  +  binaryToUnaryIfNull(pParse, Y.pExpr, A.pExpr, TK_ISNULL);
   898    909   }
   899    910   expr(A) ::= expr(X) IS NOT expr(Y). {
   900    911     spanBinaryExpr(&A,pParse,TK_ISNOT,&X,&Y);
   901         -  if( pParse->db->mallocFailed==0  && Y.pExpr->op==TK_NULL ){
   902         -    A.pExpr->op = TK_NOTNULL;
   903         -  }
          912  +  binaryToUnaryIfNull(pParse, Y.pExpr, A.pExpr, TK_NOTNULL);
   904    913   }
   905    914   
   906    915   %include {
   907    916     /* Construct an expression node for a unary prefix operator
   908    917     */
   909    918     static void spanUnaryPrefix(
   910    919       ExprSpan *pOut,        /* Write the new expression node here */