Refinements to NULL processing: NULLs are indistinct for DISTINCT and UNION.
Multiplying a NULL by zero yields zero. In a CASE expression, a NULL comparison
is considered false, not NULL.  With these changes, NULLs in SQLite now work
the same as in PostgreSQL and in Oracle. (CVS 600)

FossilOrigin-Name: da61aa1d238539dff9c43fd9f464d311e28d669f
diff --git a/src/expr.c b/src/expr.c
index 25f0ebd..c414e39 100644
--- a/src/expr.c
+++ b/src/expr.c
@@ -12,7 +12,7 @@
 ** This file contains routines used for analyzing expressions and
 ** for generating VDBE code that evaluates expressions in SQLite.
 **
-** $Id: expr.c,v 1.65 2002/05/30 02:35:12 drh Exp $
+** $Id: expr.c,v 1.66 2002/05/31 15:51:25 drh Exp $
 */
 #include "sqliteInt.h"
 
@@ -933,9 +933,7 @@
     }
     case TK_CASE: {
       int expr_end_label;
-      int null_result_label;
       int jumpInst;
-      int nullBypassInst;
       int addr;
       int nExpr;
       int i;
@@ -945,44 +943,32 @@
       assert(pExpr->pList->nExpr > 0);
       nExpr = pExpr->pList->nExpr;
       expr_end_label = sqliteVdbeMakeLabel(v);
-      null_result_label = sqliteVdbeMakeLabel(v);
       if( pExpr->pLeft ){
         sqliteExprCode(pParse, pExpr->pLeft);
-        nullBypassInst = sqliteVdbeAddOp(v, OP_IsNull, -1, 0);
       }
       for(i=0; i<nExpr; i=i+2){
         sqliteExprCode(pParse, pExpr->pList->a[i].pExpr);
-        sqliteVdbeAddOp(v, OP_IsNull, -1, null_result_label);
         if( pExpr->pLeft ){
           sqliteVdbeAddOp(v, OP_Dup, 1, 1);
-          jumpInst = sqliteVdbeAddOp(v, OP_Ne, 0, 0);
+          jumpInst = sqliteVdbeAddOp(v, OP_Ne, 1, 0);
+          sqliteVdbeAddOp(v, OP_Pop, 1, 0);
         }else{
-          jumpInst = sqliteVdbeAddOp(v, OP_IfNot, 0, 0);
+          jumpInst = sqliteVdbeAddOp(v, OP_IfNot, 1, 0);
         }
         sqliteExprCode(pParse, pExpr->pList->a[i+1].pExpr);
         sqliteVdbeAddOp(v, OP_Goto, 0, expr_end_label);
-        if( i>=nExpr-2 ){
-          sqliteVdbeResolveLabel(v, null_result_label);
-          sqliteVdbeAddOp(v, OP_Pop, 1, 0);
-          if( pExpr->pRight!=0 ){
-            sqliteVdbeAddOp(v, OP_String, 0, 0);
-            sqliteVdbeAddOp(v, OP_Goto, 0, expr_end_label);
-          }
-        }
         addr = sqliteVdbeCurrentAddr(v);
         sqliteVdbeChangeP2(v, jumpInst, addr);
       }
+      if( pExpr->pLeft ){
+        sqliteVdbeAddOp(v, OP_Pop, 1, 0);
+      }
       if( pExpr->pRight ){
         sqliteExprCode(pParse, pExpr->pRight);
       }else{
         sqliteVdbeAddOp(v, OP_String, 0, 0);
       }
       sqliteVdbeResolveLabel(v, expr_end_label);
-      if( pExpr->pLeft ){
-        sqliteVdbeAddOp(v, OP_Pull, 1, 0);
-        sqliteVdbeAddOp(v, OP_Pop, 1, 0);
-        sqliteVdbeChangeP2(v, nullBypassInst, sqliteVdbeCurrentAddr(v));
-      }
     }
     break;
   }