Alexandre Julliard : kernelbase: Fix assumptions about 0-size output buffer in ntdll Unicode conversion functions.

Alexandre Julliard julliard at winehq.org
Tue Dec 3 16:13:10 CST 2019


Module: wine
Branch: master
Commit: 94d2b4742c358e15d336d4a48e2c1354efa5de5c
URL:    https://source.winehq.org/git/wine.git/?a=commit;h=94d2b4742c358e15d336d4a48e2c1354efa5de5c

Author: Alexandre Julliard <julliard at winehq.org>
Date:   Tue Dec  3 08:30:36 2019 +0100

kernelbase: Fix assumptions about 0-size output buffer in ntdll Unicode conversion functions.

Signed-off-by: Alexandre Julliard <julliard at winehq.org>

---

 dlls/kernelbase/file.c     | 21 ++++++++++++++++++---
 dlls/kernelbase/registry.c | 16 +++++++++-------
 dlls/kernelbase/string.c   |  3 +--
 3 files changed, 28 insertions(+), 12 deletions(-)

diff --git a/dlls/kernelbase/file.c b/dlls/kernelbase/file.c
index 77a7398580..23ca5629a3 100644
--- a/dlls/kernelbase/file.c
+++ b/dlls/kernelbase/file.c
@@ -292,10 +292,25 @@ DWORD file_name_WtoA( LPCWSTR src, INT srclen, LPSTR dest, INT destlen )
     DWORD ret;
 
     if (srclen < 0) srclen = lstrlenW( src ) + 1;
-    if (oem_file_apis)
-        RtlUnicodeToOemN( dest, destlen, &ret, src, srclen * sizeof(WCHAR) );
+    if (!destlen)
+    {
+        if (oem_file_apis)
+        {
+            UNICODE_STRING strW;
+            strW.Buffer = (WCHAR *)src;
+            strW.Length = srclen * sizeof(WCHAR);
+            ret = RtlUnicodeStringToOemSize( &strW ) - 1;
+        }
+        else
+            RtlUnicodeToMultiByteSize( &ret, src, srclen * sizeof(WCHAR) );
+    }
     else
-        RtlUnicodeToMultiByteN( dest, destlen, &ret, src, srclen * sizeof(WCHAR) );
+    {
+        if (oem_file_apis)
+            RtlUnicodeToOemN( dest, destlen, &ret, src, srclen * sizeof(WCHAR) );
+        else
+            RtlUnicodeToMultiByteN( dest, destlen, &ret, src, srclen * sizeof(WCHAR) );
+    }
     return ret;
 }
 
diff --git a/dlls/kernelbase/registry.c b/dlls/kernelbase/registry.c
index d3364dbcee..1fee41ec5e 100644
--- a/dlls/kernelbase/registry.c
+++ b/dlls/kernelbase/registry.c
@@ -915,7 +915,7 @@ LSTATUS WINAPI RegQueryInfoKeyA( HKEY hkey, LPSTR class, LPDWORD class_len, LPDW
     NTSTATUS status;
     char buffer[256], *buf_ptr = buffer;
     KEY_FULL_INFORMATION *info = (KEY_FULL_INFORMATION *)buffer;
-    DWORD total_size, len;
+    DWORD total_size;
 
     TRACE( "(%p,%p,%d,%p,%p,%p,%p,%p,%p,%p,%p)\n", hkey, class, class_len ? *class_len : 0,
            reserved, subkeys, max_subkey, values, max_value, max_data, security, modif );
@@ -940,19 +940,21 @@ LSTATUS WINAPI RegQueryInfoKeyA( HKEY hkey, LPSTR class, LPDWORD class_len, LPDW
 
         if (status) goto done;
 
-        len = 0;
-        if (class && class_len) len = *class_len;
-        RtlUnicodeToMultiByteN( class, len, class_len,
-                                (WCHAR *)(buf_ptr + info->ClassOffset), info->ClassLength );
-        if (len)
+        if (class && class_len && *class_len)
         {
-            if (*class_len + 1 > len)
+            DWORD len = *class_len;
+            RtlUnicodeToMultiByteN( class, len, class_len,
+                                    (WCHAR *)(buf_ptr + info->ClassOffset), info->ClassLength );
+            if (*class_len == len)
             {
                 status = STATUS_BUFFER_OVERFLOW;
                 *class_len -= 1;
             }
             class[*class_len] = 0;
         }
+        else if (class_len)
+            RtlUnicodeToMultiByteSize( class_len,
+                                       (WCHAR *)(buf_ptr + info->ClassOffset), info->ClassLength );
     }
     else status = STATUS_SUCCESS;
 
diff --git a/dlls/kernelbase/string.c b/dlls/kernelbase/string.c
index 7bea47942e..668fd4fa37 100644
--- a/dlls/kernelbase/string.c
+++ b/dlls/kernelbase/string.c
@@ -1382,8 +1382,7 @@ INT WINAPI DECLSPEC_HOTPATCH LoadStringA(HINSTANCE instance, UINT resource_id, L
 
         while (id--) p += *p + 1;
 
-        if (buflen != 1)
-            RtlUnicodeToMultiByteN(buffer, buflen - 1, &retval, p + 1, *p * sizeof(WCHAR));
+        RtlUnicodeToMultiByteN(buffer, buflen - 1, &retval, p + 1, *p * sizeof(WCHAR));
     }
     buffer[retval] = 0;
     TRACE("returning %s\n", debugstr_a(buffer));




More information about the wine-cvs mailing list