Mike McCormack : msi: Comparisons with null in conditions are special.

Alexandre Julliard julliard at wine.codeweavers.com
Thu Dec 7 14:23:39 CST 2006


Module: wine
Branch: master
Commit: 9dce96b3155ce07dffa4f5b0712fbcaad9ba3e2c
URL:    http://source.winehq.org/git/wine.git/?a=commit;h=9dce96b3155ce07dffa4f5b0712fbcaad9ba3e2c

Author: Mike McCormack <mike at codeweavers.com>
Date:   Wed Dec  6 22:29:08 2006 +0900

msi: Comparisons with null in conditions are special.

---

 dlls/msi/cond.y |   99 ++++++++++++++++++++++++++++++++++++++++---------------
 1 files changed, 72 insertions(+), 27 deletions(-)

diff --git a/dlls/msi/cond.y b/dlls/msi/cond.y
index 9cfb001..d19127b 100644
--- a/dlls/msi/cond.y
+++ b/dlls/msi/cond.y
@@ -431,59 +431,104 @@ static INT compare_substring( LPCWSTR a,
     case COND_ISS:
         return strstriW( a, b ) ? 1 : 0;
     case COND_LHS:
-    	return 0 == strncmpW( a, b, lstrlenW( b ) );
+        return 0 == strncmpW( a, b, lstrlenW( b ) );
     case COND_RHS:
-    	return 0 == lstrcmpW( a + (lstrlenW( a ) - lstrlenW( b )), b );
+        return 0 == lstrcmpW( a + (lstrlenW( a ) - lstrlenW( b )), b );
     case COND_ILHS:
-    	return 0 == strncmpiW( a, b, lstrlenW( b ) );
+        return 0 == strncmpiW( a, b, lstrlenW( b ) );
     case COND_IRHS:
         return 0 == lstrcmpiW( a + (lstrlenW( a ) - lstrlenW( b )), b );
     default:
-    	ERR("invalid substring operator\n");
+        ERR("invalid substring operator\n");
         return 0;
     }
     return 0;
 }
 
+static BOOL is_empty( LPCWSTR p )
+{
+    return !p || !p[0];
+}
+
+static BOOL is_alphaless( LPCWSTR p )
+{
+    while (*p)
+    {
+        if (isalphaW( *p ) || (*p == '_'))
+             return FALSE;
+        p++;
+    }
+    return TRUE;
+}
+
 static INT compare_string( LPCWSTR a, INT operator, LPCWSTR b )
 {
+    int r;
+
     if (operator >= COND_SS && operator <= COND_RHS)
         return compare_substring( a, operator, b );
-	
-    /* null and empty string are equivalent */
-    if (!a) a = szEmpty;
-    if (!b) b = szEmpty;
 
-    /* a or b may be NULL */
+    if (is_empty( a ) && is_empty( b ))
+        r = 0;
+
+    else if (is_empty( a ) && is_alphaless( b ))
+        r = 1;
+
+    else if (is_empty( b ) && is_alphaless( a ))
+        r = -1;
+
+    else
+    {
+        /* null and empty string are equivalent */
+        if (!a) a = szEmpty;
+        if (!b) b = szEmpty;
+
+        switch (operator)
+        {
+        case COND_LT:
+        case COND_GT:
+        case COND_EQ:
+        case COND_NE:
+        case COND_GE:
+        case COND_LE:
+            r = lstrcmpW( a, b );
+            break;
+        case COND_ILT:
+        case COND_IGT:
+        case COND_IEQ:
+        case COND_INE:
+        case COND_IGE:
+        case COND_ILE:
+            r = lstrcmpiW( a, b );
+            break;
+        default:
+            ERR("invalid string operator\n");
+            return 0;
+        }
+    }
+
     switch (operator)
     {
     case COND_LT:
-        return -1 == lstrcmpW( a, b );
-    case COND_GT:
-        return  1 == lstrcmpW( a, b );
-    case COND_EQ:
-        return  0 == lstrcmpW( a, b );
-    case COND_NE:
-        return  0 != lstrcmpW( a, b );
-    case COND_GE:
-        return -1 != lstrcmpW( a, b );
-    case COND_LE:
-        return  1 != lstrcmpW( a, b );
     case COND_ILT:
-        return -1 == lstrcmpiW( a, b );
+        return -1 == r;
+    case COND_GT:
     case COND_IGT:
-        return  1 == lstrcmpiW( a, b );
+        return  1 == r;
+    case COND_EQ:
     case COND_IEQ:
-        return  0 == lstrcmpiW( a, b );
+        return  0 == r;
+    case COND_NE:
     case COND_INE:
-        return  0 != lstrcmpiW( a, b );
+        return  0 != r;
+    case COND_GE:
     case COND_IGE:
-        return -1 != lstrcmpiW( a, b );
+        return -1 != r;
+    case COND_LE:
     case COND_ILE:
-        return  1 != lstrcmpiW( a, b );
+        return  1 != r;
     default:
         ERR("invalid string operator\n");
-        return 0;
     }
     return 0;
 }




More information about the wine-cvs mailing list