[PATCH 04/10] winex11: Use ntdll_umbstowcs and ntdll_wcstoumbs for Unicode conversion.

Jacek Caban wine at gitlab.winehq.org
Tue May 3 08:18:27 CDT 2022


From: Jacek Caban <jacek at codeweavers.com>

Signed-off-by: Jacek Caban <jacek at codeweavers.com>
---
 dlls/winex11.drv/clipboard.c | 14 ++++++-------
 dlls/winex11.drv/keyboard.c  | 12 +++++------
 dlls/winex11.drv/mouse.c     |  2 +-
 dlls/winex11.drv/window.c    |  4 ++--
 dlls/winex11.drv/wintab.c    |  6 +++---
 dlls/winex11.drv/x11drv.h    | 13 ++++++++++++
 dlls/winex11.drv/xim.c       | 39 ++++++++++++++----------------------
 7 files changed, 47 insertions(+), 43 deletions(-)

diff --git a/dlls/winex11.drv/clipboard.c b/dlls/winex11.drv/clipboard.c
index f9e6764fc0a..430bc6c1c81 100644
--- a/dlls/winex11.drv/clipboard.c
+++ b/dlls/winex11.drv/clipboard.c
@@ -358,9 +358,9 @@ static void register_win32_formats( const UINT *ids, UINT size )
             if (find_win32_format( *ids )) continue;  /* it already exists */
             if (!NtUserGetClipboardFormatName( *ids, buffer, ARRAYSIZE(buffer) ))
                 continue;  /* not a named format */
-            if (!(len = WideCharToMultiByte( CP_UNIXCP, 0, buffer, -1, NULL, 0, NULL, NULL ))) continue;
-            if (!(names[count] = malloc( len ))) continue;
-            WideCharToMultiByte( CP_UNIXCP, 0, buffer, -1, names[count], len, NULL, NULL );
+            len = lstrlenW( buffer );
+            if (!(names[count] = malloc( len * 3 + 1 ))) continue;
+            ntdll_wcstoumbs( buffer, len + 1, names[count], len * 3 + 1, FALSE );
             new_ids[count++] = *ids;
         }
         if (!count) return;
@@ -405,7 +405,7 @@ static void register_x11_formats( const Atom *atoms, UINT size )
 
         for (i = pos = 0; i < count; i++)
         {
-            if (MultiByteToWideChar( CP_UNIXCP, 0, names[i], -1, buffer, 256 ) &&
+            if (ntdll_umbstowcs( names[i], strlen( names[i] ) + 1, buffer, ARRAYSIZE(buffer) ) &&
                 (ids[pos] = register_clipboard_format( buffer )))
                 new_atoms[pos++] = new_atoms[i];
             XFree( names[i] );
@@ -759,7 +759,8 @@ static void *import_compound_text( Atom type, const void *data, size_t size, siz
 
     len = strlen(srcstr[0]) + 1;
     if (!(ret = malloc( (len * 2 + 1) * sizeof(WCHAR) ))) return NULL;
-    count = MultiByteToWideChar( CP_UNIXCP, 0, srcstr[0], len, ret + len, len );
+
+    count = ntdll_umbstowcs( srcstr[0], len, ret + len, len );
     ret = unicode_text_from_string( ret, ret + len, count, ret_size );
 
     XFreeStringList(srcstr);
@@ -1282,8 +1283,7 @@ static BOOL export_compound_text( Display *display, Window win, Atom prop, Atom
 
 
     if (!(text = malloc( size / sizeof(WCHAR) * 3 ))) return FALSE;
-    len = WideCharToMultiByte( CP_UNIXCP, 0, data, size / sizeof(WCHAR),
-                               text, size / sizeof(WCHAR) * 3, NULL, NULL );
+    len = ntdll_wcstoumbs( data, size / sizeof(WCHAR), text, size / sizeof(WCHAR) * 3, FALSE );
     string_from_unicode_text( text, len, &len );
 
     if (target == x11drv_atom(COMPOUND_TEXT))
diff --git a/dlls/winex11.drv/keyboard.c b/dlls/winex11.drv/keyboard.c
index fac97ef7e35..9337f8bf6e9 100644
--- a/dlls/winex11.drv/keyboard.c
+++ b/dlls/winex11.drv/keyboard.c
@@ -1904,7 +1904,7 @@ SHORT X11DRV_VkKeyScanEx( WCHAR wChar, HKL hkl )
     /* FIXME: what happens if wChar is not a Latin1 character and CP_UNIXCP
      * is UTF-8 (multibyte encoding)?
      */
-    if (!WideCharToMultiByte(CP_UNIXCP, 0, &wChar, 1, &cChar, 1, NULL, NULL))
+    if (!ntdll_wcstoumbs( &wChar, 1, &cChar, 1, FALSE ))
     {
         WARN("no translation from unicode to CP_UNIXCP for 0x%02x\n", wChar);
         return -1;
@@ -2100,7 +2100,7 @@ UINT X11DRV_MapVirtualKeyEx( UINT wCode, UINT wMapType, HKL hkl )
             if (len)
             {
                 WCHAR wch;
-                if (MultiByteToWideChar(CP_UNIXCP, 0, s, len, &wch, 1)) ret = toupperW(wch);
+                if (ntdll_umbstowcs( s, len, &wch, 1 )) ret = toupperW(wch);
             }
             break;
         }
@@ -2208,7 +2208,7 @@ INT X11DRV_GetKeyNameText( LONG lParam, LPWSTR lpBuffer, INT nSize )
               pthread_mutex_unlock( &kbd_mutex );
               TRACE("found scan=%04x keyc=%u keysym=%lx modified_string=%s\n",
                     scanCode, keyc, keys, debugstr_an(name,idx-name));
-              rc = MultiByteToWideChar(CP_UNIXCP, 0, name, idx-name+1, lpBuffer, nSize);
+              rc = ntdll_umbstowcs( name, idx - name + 1, lpBuffer, nSize );
               if (!rc) rc = nSize;
               lpBuffer[--rc] = 0;
               return rc;
@@ -2220,7 +2220,7 @@ INT X11DRV_GetKeyNameText( LONG lParam, LPWSTR lpBuffer, INT nSize )
           pthread_mutex_unlock( &kbd_mutex );
           TRACE("found scan=%04x keyc=%u keysym=%04x vkey=%04x string=%s\n",
                 scanCode, keyc, (int)keys, vkey, debugstr_a(name));
-          rc = MultiByteToWideChar(CP_UNIXCP, 0, name, -1, lpBuffer, nSize);
+          rc = ntdll_umbstowcs( name, strlen(name) + 1, lpBuffer, nSize );
           if (!rc) rc = nSize;
           lpBuffer[--rc] = 0;
           return rc;
@@ -2515,7 +2515,7 @@ INT X11DRV_ToUnicodeEx( UINT virtKey, UINT scanCode, const BYTE *lpKeyState,
 	dead_char = KEYBOARD_MapDeadKeysym(keysym);
 	if (dead_char)
         {
-	    MultiByteToWideChar(CP_UNIXCP, 0, &dead_char, 1, bufW, bufW_size);
+	    ntdll_umbstowcs( &dead_char, 1, bufW, bufW_size );
 	    ret = -1;
             goto found;
         }
@@ -2611,7 +2611,7 @@ INT X11DRV_ToUnicodeEx( UINT virtKey, UINT scanCode, const BYTE *lpKeyState,
 	if(ret)
 	{
 	    TRACE_(key)("Translating char 0x%02x to unicode\n", *(BYTE *)lpChar);
-	    ret = MultiByteToWideChar(CP_UNIXCP, 0, lpChar, ret, bufW, bufW_size);
+            ret = ntdll_umbstowcs(  lpChar, ret, bufW, bufW_size );
 	}
     }
 
diff --git a/dlls/winex11.drv/mouse.c b/dlls/winex11.drv/mouse.c
index d87cff079ec..1a5230300a3 100644
--- a/dlls/winex11.drv/mouse.c
+++ b/dlls/winex11.drv/mouse.c
@@ -1084,7 +1084,7 @@ static Cursor create_xcursor_system_cursor( const ICONINFOEXW *info )
         {
             const WCHAR *valueW = (const WCHAR *)value->Data;
             if (!valueW[0]) return 0; /* force standard cursor */
-            if (!WideCharToMultiByte( CP_UNIXCP, 0, valueW, -1, valueA, sizeof(valueA), NULL, NULL ))
+            if (!ntdll_wcstoumbs( valueW, lstrlenW(valueW) + 1, valueA, sizeof(valueA), FALSE ))
                 valueA[0] = 0;
             goto done;
         }
diff --git a/dlls/winex11.drv/window.c b/dlls/winex11.drv/window.c
index 3b0ccd8d22a..79970f55444 100644
--- a/dlls/winex11.drv/window.c
+++ b/dlls/winex11.drv/window.c
@@ -443,9 +443,9 @@ static void sync_window_text( Display *display, Window win, const WCHAR *text )
 
     /* allocate new buffer for window text */
     len = lstrlenW( text );
-    count = WideCharToMultiByte(CP_UNIXCP, 0, text, -1, NULL, 0, NULL, NULL);
+    count = len * 3 + 1;
     if (!(buffer = malloc( count ))) return;
-    WideCharToMultiByte(CP_UNIXCP, 0, text, -1, buffer, count, NULL, NULL);
+    ntdll_wcstoumbs( text, len + 1, buffer, count, FALSE );
 
     RtlUnicodeToUTF8N( NULL, 0, &count, text, len * sizeof(WCHAR) );
     if (!(utf8_buffer = malloc( count )))
diff --git a/dlls/winex11.drv/wintab.c b/dlls/winex11.drv/wintab.c
index 331601c3325..aa0d7be2fd0 100644
--- a/dlls/winex11.drv/wintab.c
+++ b/dlls/winex11.drv/wintab.c
@@ -27,7 +27,6 @@
 
 #include "windef.h"
 #include "winbase.h"
-#include "winnls.h"
 #include "x11drv.h"
 #include "wine/unicode.h"
 #include "wine/debug.h"
@@ -616,7 +615,7 @@ BOOL CDECL X11DRV_LoadTabletInfo(HWND hwnddefault)
                 WARN("Unable to open device %s\n",target->name);
                 break;
             }
-            MultiByteToWideChar(CP_UNIXCP, 0, target->name, -1, cursor.NAME, WT_MAX_NAME_LEN);
+            ntdll_umbstowcs(target->name, strlen(target->name) + 1, cursor.NAME, WT_MAX_NAME_LEN);
 
             if (! is_tablet_cursor(target->name, device_type))
             {
@@ -1031,7 +1030,8 @@ int CDECL X11DRV_AttachEventQueueToTablet(HWND hOwner)
         if (!gSysCursor[cur_loop].ACTIVE) continue;
 
         /* the cursor name fits in the buffer because too long names are skipped */
-        WideCharToMultiByte(CP_UNIXCP, 0, gSysCursor[cur_loop].NAME, -1, cursorNameA, WT_MAX_NAME_LEN, NULL, NULL);
+        ntdll_wcstoumbs(gSysCursor[cur_loop].NAME, lstrlenW(gSysCursor[cur_loop].NAME) + 1,
+                        cursorNameA, WT_MAX_NAME_LEN, FALSE);
         for (loop=0; loop < num_devices; loop ++)
             if (strcmp(devices[loop].name, cursorNameA) == 0)
                 target = &devices[loop];
diff --git a/dlls/winex11.drv/x11drv.h b/dlls/winex11.drv/x11drv.h
index 4298ae429ed..2ff6bb00eb6 100644
--- a/dlls/winex11.drv/x11drv.h
+++ b/dlls/winex11.drv/x11drv.h
@@ -62,6 +62,7 @@ typedef int Status;
 #include "ntgdi.h"
 #include "wine/gdi_driver.h"
 #include "unixlib.h"
+#include "winnls.h"
 #include "wine/list.h"
 
 #define MAX_DASHLEN 16
@@ -916,4 +917,16 @@ static inline UINT asciiz_to_unicode( WCHAR *dst, const char *src )
     return (p - dst) * sizeof(WCHAR);
 }
 
+/* FIXME: remove once we may use ntdll.so version */
+
+static inline DWORD ntdll_umbstowcs( const char *src, DWORD srclen, WCHAR *dst, DWORD dstlen )
+{
+    return MultiByteToWideChar( CP_UNIXCP, 0, src, srclen, dst, dstlen );
+}
+
+static inline int ntdll_wcstoumbs( const WCHAR *src, DWORD srclen, char *dst, DWORD dstlen, BOOL strict )
+{
+    return WideCharToMultiByte( CP_UNIXCP, 0, src, srclen, dst, dstlen, NULL, NULL );
+}
+
 #endif  /* __WINE_X11DRV_H */
diff --git a/dlls/winex11.drv/xim.c b/dlls/winex11.drv/xim.c
index 6adf2475de7..ec4be2e0c5d 100644
--- a/dlls/winex11.drv/xim.c
+++ b/dlls/winex11.drv/xim.c
@@ -101,23 +101,20 @@ static void X11DRV_ImmSetInternalString(DWORD dwOffset,
 
 void X11DRV_XIMLookupChars( const char *str, DWORD count )
 {
-    DWORD dwOutput;
-    WCHAR *wcOutput;
+    WCHAR *output;
+    DWORD len;
     HWND focus;
 
     TRACE("%p %u\n", str, count);
 
-    dwOutput = MultiByteToWideChar(CP_UNIXCP, 0, str, count, NULL, 0);
-    wcOutput = HeapAlloc(GetProcessHeap(), 0, sizeof(WCHAR) * dwOutput);
-    if (wcOutput == NULL)
-        return;
-    MultiByteToWideChar(CP_UNIXCP, 0, str, count, wcOutput, dwOutput);
+    if (!(output = malloc( count * sizeof(WCHAR) ))) return;
+    len = ntdll_umbstowcs( str, count, output, count );
 
     if ((focus = GetFocus()))
         IME_UpdateAssociation(focus);
 
-    IME_SetResultString(wcOutput, dwOutput);
-    HeapFree(GetProcessHeap(), 0, wcOutput);
+    IME_SetResultString( output, len );
+    free( output );
 }
 
 static BOOL XIMPreEditStateNotifyCallback(XIC xic, XPointer p, XPointer data)
@@ -173,24 +170,18 @@ static void XIMPreEditDrawCallback(XIM ic, XPointer client_data,
         {
             if (! P_DR->text->encoding_is_wchar)
             {
-                DWORD dwOutput;
-                WCHAR *wcOutput;
+                size_t text_len;
+                WCHAR *output;
 
                 TRACE("multibyte\n");
-                dwOutput = MultiByteToWideChar(CP_UNIXCP, 0,
-                           P_DR->text->string.multi_byte, -1,
-                           NULL, 0);
-                wcOutput = HeapAlloc(GetProcessHeap(), 0, sizeof (WCHAR) * dwOutput);
-                if (wcOutput)
+                text_len = strlen( P_DR->text->string.multi_byte );
+                if ((output = malloc( text_len * sizeof(WCHAR) )))
                 {
-                    dwOutput = MultiByteToWideChar(CP_UNIXCP, 0,
-                               P_DR->text->string.multi_byte, -1,
-                               wcOutput, dwOutput);
-
-                    /* ignore null */
-                    dwOutput --;
-                    X11DRV_ImmSetInternalString (sel, len, wcOutput, dwOutput);
-                    HeapFree(GetProcessHeap(), 0, wcOutput);
+                    text_len = ntdll_umbstowcs( P_DR->text->string.multi_byte, text_len,
+                                                output, text_len );
+
+                    X11DRV_ImmSetInternalString( sel, len, output, text_len );
+                    free( output );
                 }
             }
             else
-- 
GitLab


https://gitlab.winehq.org/wine/wine/-/merge_requests/28



More information about the wine-devel mailing list