[2/7] msi: Use strcmpW instead of lstrcmpW to compare database strings.
Hans Leidekker
hans at codeweavers.com
Wed Oct 6 08:43:54 CDT 2010
An installer I have here uses \1 and \2 as delimiters in property strings.
It turns out that on Wine lstrcmp("\1", "\2") returns 0, not -1, which causes
the string table implementation to return the wrong value. This should be fixed,
but it's better if database string comparisons do not depend on thread locale.
---
dlls/msi/cond.y | 28 ++++++++++++++--------------
dlls/msi/record.c | 3 ++-
dlls/msi/string.c | 4 ++--
dlls/msi/table.c | 30 ++++++++++++++++++------------
dlls/msi/where.c | 3 ++-
5 files changed, 38 insertions(+), 30 deletions(-)
diff --git a/dlls/msi/cond.y b/dlls/msi/cond.y
index 03ea493..93e2e01 100644
--- a/dlls/msi/cond.y
+++ b/dlls/msi/cond.y
@@ -466,7 +466,7 @@ static INT compare_substring( LPCWSTR a, INT operator, LPCWSTR b )
int l = lstrlenW( a );
int r = lstrlenW( b );
if (r > l) return 0;
- return 0 == lstrcmpW( a + (l - r), b );
+ return strcmpW( a + (l - r), b ) == 0;
}
case COND_ILHS:
return 0 == strncmpiW( a, b, lstrlenW( b ) );
@@ -475,7 +475,7 @@ static INT compare_substring( LPCWSTR a, INT operator, LPCWSTR b )
int l = lstrlenW( a );
int r = lstrlenW( b );
if (r > l) return 0;
- return 0 == lstrcmpiW( a + (l - r), b );
+ return strcmpiW( a + (l - r), b ) == 0;
}
default:
ERR("invalid substring operator\n");
@@ -500,29 +500,29 @@ static INT compare_string( LPCWSTR a, INT operator, LPCWSTR b, BOOL convert )
switch (operator)
{
case COND_LT:
- return -1 == lstrcmpW( a, b );
+ return strcmpW( a, b ) < 0;
case COND_GT:
- return 1 == lstrcmpW( a, b );
+ return strcmpW( a, b ) > 0;
case COND_EQ:
- return 0 == lstrcmpW( a, b );
+ return strcmpW( a, b ) == 0;
case COND_NE:
- return 0 != lstrcmpW( a, b );
+ return strcmpW( a, b ) != 0;
case COND_GE:
- return -1 != lstrcmpW( a, b );
+ return strcmpW( a, b ) >= 0;
case COND_LE:
- return 1 != lstrcmpW( a, b );
+ return strcmpW( a, b ) <= 0;
case COND_ILT:
- return -1 == lstrcmpiW( a, b );
+ return strcmpiW( a, b ) < 0;
case COND_IGT:
- return 1 == lstrcmpiW( a, b );
+ return strcmpiW( a, b ) > 0;
case COND_IEQ:
- return 0 == lstrcmpiW( a, b );
+ return strcmpiW( a, b ) == 0;
case COND_INE:
- return 0 != lstrcmpiW( a, b );
+ return strcmpiW( a, b ) != 0;
case COND_IGE:
- return -1 != lstrcmpiW( a, b );
+ return strcmpiW( a, b ) >= 0;
case COND_ILE:
- return 1 != lstrcmpiW( a, b );
+ return strcmpiW( a, b ) <= 0;
default:
ERR("invalid string operator\n");
return 0;
diff --git a/dlls/msi/record.c b/dlls/msi/record.c
index 7bc8281..fc30f79 100644
--- a/dlls/msi/record.c
+++ b/dlls/msi/record.c
@@ -27,6 +27,7 @@
#include "winuser.h"
#include "winerror.h"
#include "wine/debug.h"
+#include "wine/unicode.h"
#include "msi.h"
#include "msiquery.h"
#include "msipriv.h"
@@ -1016,7 +1017,7 @@ BOOL MSI_RecordsAreEqual(MSIRECORD *a, MSIRECORD *b)
break;
case MSIFIELD_WSTR:
- if (lstrcmpW(a->fields[i].u.szwVal, b->fields[i].u.szwVal))
+ if (strcmpW(a->fields[i].u.szwVal, b->fields[i].u.szwVal))
return FALSE;
break;
diff --git a/dlls/msi/string.c b/dlls/msi/string.c
index 21b1db2..80057b8 100644
--- a/dlls/msi/string.c
+++ b/dlls/msi/string.c
@@ -163,7 +163,7 @@ static int find_insert_index( const string_table *st, UINT string_id )
while (low <= high)
{
i = (low + high) / 2;
- c = lstrcmpW( st->strings[string_id].str, st->strings[st->sorted[i]].str );
+ c = strcmpW( st->strings[string_id].str, st->strings[st->sorted[i]].str );
if (c < 0)
high = i - 1;
@@ -403,7 +403,7 @@ UINT msi_string2idW( const string_table *st, LPCWSTR str, UINT *id )
while (low <= high)
{
i = (low + high) / 2;
- c = lstrcmpW( str, st->strings[st->sorted[i]].str );
+ c = strcmpW( str, st->strings[st->sorted[i]].str );
if (c < 0)
high = i - 1;
diff --git a/dlls/msi/table.c b/dlls/msi/table.c
index 9fbb0a1..cc39dbc 100644
--- a/dlls/msi/table.c
+++ b/dlls/msi/table.c
@@ -1300,10 +1300,13 @@ static UINT get_table_value_from_record( MSITABLEVIEW *tv, MSIRECORD *rec, UINT
else if ( columninfo.type & MSITYPE_STRING )
{
LPCWSTR sval = MSI_RecordGetString( rec, iField );
-
- r = msi_string2idW(tv->db->strings, sval, pvalue);
- if (r != ERROR_SUCCESS)
- return ERROR_NOT_FOUND;
+ if (sval)
+ {
+ r = msi_string2idW(tv->db->strings, sval, pvalue);
+ if (r != ERROR_SUCCESS)
+ return ERROR_NOT_FOUND;
+ }
+ else *pvalue = 0;
}
else if ( 2 == bytes_per_column( tv->db, &columninfo ) )
{
@@ -1386,7 +1389,6 @@ static UINT TABLE_set_row( struct tagMSIVIEW *view, UINT row, MSIRECORD *rec, UI
LPCWSTR sval = MSI_RecordGetString( rec, i + 1 );
val = msi_addstringW( tv->db->strings, sval, -1, 1,
persistent ? StringPersistent : StringNonPersistent );
-
}
else
{
@@ -2588,15 +2590,19 @@ static UINT* msi_record_to_row( const MSITABLEVIEW *tv, MSIRECORD *rec )
! MSITYPE_IS_BINARY(tv->columns[i].type) )
{
str = MSI_RecordGetString( rec, i+1 );
- r = msi_string2idW( tv->db->strings, str, &data[i] );
-
- /* if there's no matching string in the string table,
- these keys can't match any record, so fail now. */
- if( ERROR_SUCCESS != r )
+ if (str)
{
- msi_free( data );
- return NULL;
+ r = msi_string2idW( tv->db->strings, str, &data[i] );
+
+ /* if there's no matching string in the string table,
+ these keys can't match any record, so fail now. */
+ if( ERROR_SUCCESS != r )
+ {
+ msi_free( data );
+ return NULL;
+ }
}
+ else data[i] = 0;
}
else
{
diff --git a/dlls/msi/where.c b/dlls/msi/where.c
index 4c4db49..7cafa2a 100644
--- a/dlls/msi/where.c
+++ b/dlls/msi/where.c
@@ -24,6 +24,7 @@
#include "winbase.h"
#include "winerror.h"
#include "wine/debug.h"
+#include "wine/unicode.h"
#include "msi.h"
#include "msiquery.h"
#include "objbase.h"
@@ -306,7 +307,7 @@ static UINT STRCMP_Evaluate( MSIWHEREVIEW *wv, UINT row, const struct expr *cond
else if( r_str && ! l_str )
sr = -1;
else
- sr = lstrcmpW( l_str, r_str );
+ sr = strcmpW( l_str, r_str );
*val = ( cond->u.expr.op == OP_EQ && ( sr == 0 ) ) ||
( cond->u.expr.op == OP_NE && ( sr != 0 ) );
--
1.7.1
More information about the wine-patches
mailing list