[kernel] Wrap an exception handler around FindResource

Richard Cohen richard at daijobu.co.uk
Wed Dec 3 17:19:40 CST 2003


There was a regression when resource handling was split off into ntdll
Needed for Quicken98 - probably Quicken97 too - as reported in the AppDB.

Changelog:
	+ FindResourceA/W need to catch pagefaults
	+ Move the TRACE into the exception handler in LdrFindResource*



-------------- next part --------------
diff -u -r dlls/kernel/resource.c dlls/kernel/resource.c
--- dlls/kernel/resource.c	2003-09-08 11:25:01.000000000 +0100
+++ dlls/kernel/resource.c	2003-12-02 20:22:52.000000000 +0000
@@ -34,6 +34,8 @@
 #include "wownt32.h"
 #include "wine/winbase16.h"
 #include "wine/debug.h"
+#include "excpt.h"
+#include "wine/exception.h"
 
 WINE_DEFAULT_DEBUG_CHANNEL(resource);
 
@@ -44,6 +46,13 @@
 #define HGLOBAL_16(h32) (LOWORD(h32))
 #define HMODULE_16(h32) (LOWORD(h32))
 
+static WINE_EXCEPTION_FILTER(page_fault)
+{
+    if (GetExceptionCode() == EXCEPTION_ACCESS_VIOLATION ||
+        GetExceptionCode() == EXCEPTION_PRIV_INSTRUCTION)
+        return EXCEPTION_EXECUTE_HANDLER;
+    return EXCEPTION_CONTINUE_SEARCH;
+}
 
 /* retrieve the resource name to pass to the ntdll functions */
 static NTSTATUS get_res_nameA( LPCSTR name, UNICODE_STRING *str )
@@ -98,25 +107,35 @@
     LDR_RESOURCE_INFO info;
     const IMAGE_RESOURCE_DATA_ENTRY *entry = NULL;
 
-    TRACE( "%p %s %s %04x\n", hModule, debugstr_a(type), debugstr_a(name), lang );
+    __TRY
+    {
+	TRACE( "%p %s %s %04x\n", hModule, debugstr_a(type), debugstr_a(name), lang );
+	nameW.Buffer = typeW.Buffer = NULL;
 
-    if (!hModule) hModule = GetModuleHandleW(0);
-    else if (!HIWORD(hModule))
+	if (!hModule) hModule = GetModuleHandleW(0);
+	else if (!HIWORD(hModule))
+	{
+	    return HRSRC_32( FindResource16( HMODULE_16(hModule), name, type ) );
+	}
+
+	if ((status = get_res_nameA( name, &nameW )) != STATUS_SUCCESS) goto done;
+	if ((status = get_res_nameA( type, &typeW )) != STATUS_SUCCESS) goto done;
+	info.Type = (ULONG)typeW.Buffer;
+	info.Name = (ULONG)nameW.Buffer;
+	info.Language = lang;
+	status = LdrFindResource_U( hModule, &info, 3, &entry );
+done:
+	if (status != STATUS_SUCCESS) SetLastError( RtlNtStatusToDosError(status) );
+    }
+    __EXCEPT(page_fault)
     {
-        return HRSRC_32( FindResource16( HMODULE_16(hModule), name, type ) );
+	SetLastError(ERROR_INVALID_PARAMETER);
     }
+    __ENDTRY;  
 
-    nameW.Buffer = typeW.Buffer = NULL;
-    if ((status = get_res_nameA( name, &nameW )) != STATUS_SUCCESS) goto done;
-    if ((status = get_res_nameA( type, &typeW )) != STATUS_SUCCESS) goto done;
-    info.Type = (ULONG)typeW.Buffer;
-    info.Name = (ULONG)nameW.Buffer;
-    info.Language = lang;
-    status = LdrFindResource_U( hModule, &info, 3, &entry );
-done:
     if (HIWORD(nameW.Buffer)) HeapFree( GetProcessHeap(), 0, nameW.Buffer );
     if (HIWORD(typeW.Buffer)) HeapFree( GetProcessHeap(), 0, typeW.Buffer );
-    if (status != STATUS_SUCCESS) SetLastError( RtlNtStatusToDosError(status) );
+
     return (HRSRC)entry;
 }
 
@@ -140,47 +159,67 @@
     LDR_RESOURCE_INFO info;
     const IMAGE_RESOURCE_DATA_ENTRY *entry = NULL;
 
-    TRACE( "%p %s %s %04x\n", hModule, debugstr_w(type), debugstr_w(name), lang );
-
-    if (!hModule) hModule = GetModuleHandleW(0);
-    else if (!HIWORD(hModule))
+    __TRY
     {
-        LPSTR nameA, typeA;
-        HRSRC16 ret;
+	TRACE( "%p %s %s %04x\n", hModule, debugstr_w(type), debugstr_w(name), lang );
 
-        if (HIWORD(name))
-        {
-            DWORD len = WideCharToMultiByte( CP_ACP, 0, name, -1, NULL, 0, NULL, NULL );
-            nameA = HeapAlloc( GetProcessHeap(), 0, len );
-            if (nameA) WideCharToMultiByte( CP_ACP, 0, name, -1, nameA, len, NULL, NULL );
-        }
-        else nameA = (LPSTR)name;
-
-        if (HIWORD(type))
-        {
-            DWORD len = WideCharToMultiByte( CP_ACP, 0, type, -1, NULL, 0, NULL, NULL );
-            typeA = HeapAlloc( GetProcessHeap(), 0, len );
-            if (typeA) WideCharToMultiByte( CP_ACP, 0, type, -1, typeA, len, NULL, NULL );
-        }
-        else typeA = (LPSTR)type;
-
-        ret = FindResource16( HMODULE_16(hModule), nameA, typeA );
-        if (HIWORD(nameA)) HeapFree( GetProcessHeap(), 0, nameA );
-        if (HIWORD(typeA)) HeapFree( GetProcessHeap(), 0, typeA );
-        return HRSRC_32(ret);
+	if (!hModule) hModule = GetModuleHandleW(0);
+	else if (!HIWORD(hModule))
+	{
+	    LPSTR nameA, typeA;
+	    HRSRC16 ret = 0;
+	    nameA = typeA = NULL;
+
+	    __TRY
+	    {
+		if (HIWORD(name))
+		{
+		    DWORD len = WideCharToMultiByte( CP_ACP, 0, name, -1, NULL, 0, NULL, NULL );
+		    nameA = HeapAlloc( GetProcessHeap(), 0, len );
+		    if (nameA) WideCharToMultiByte( CP_ACP, 0, name, -1, nameA, len, NULL, NULL );
+		}
+		else nameA = (LPSTR)name;
+
+		if (HIWORD(type))
+		{
+		    DWORD len = WideCharToMultiByte( CP_ACP, 0, type, -1, NULL, 0, NULL, NULL );
+		    typeA = HeapAlloc( GetProcessHeap(), 0, len );
+		    if (typeA) WideCharToMultiByte( CP_ACP, 0, type, -1, typeA, len, NULL, NULL );
+		}
+		else typeA = (LPSTR)type;
+
+		ret = FindResource16( HMODULE_16(hModule), nameA, typeA );
+	    }
+	    __EXCEPT(page_fault)
+	    {
+		SetLastError(ERROR_INVALID_PARAMETER);
+	    }
+	    __ENDTRY;
+
+	    if (HIWORD(nameA)) HeapFree( GetProcessHeap(), 0, nameA );
+	    if (HIWORD(typeA)) HeapFree( GetProcessHeap(), 0, typeA );
+	    return HRSRC_32(ret);
+	}
+
+	nameW.Buffer = typeW.Buffer = NULL;
+	if ((status = get_res_nameW( name, &nameW )) != STATUS_SUCCESS) goto done;
+	if ((status = get_res_nameW( type, &typeW )) != STATUS_SUCCESS) goto done;
+	info.Type = (ULONG)typeW.Buffer;
+	info.Name = (ULONG)nameW.Buffer;
+	info.Language = lang;
+	status = LdrFindResource_U( hModule, &info, 3, &entry );
+done:
+	if (status != STATUS_SUCCESS) SetLastError( RtlNtStatusToDosError(status) );
+    }
+    __EXCEPT(page_fault)
+    {
+	SetLastError(ERROR_INVALID_PARAMETER);
     }
+    __ENDTRY;
 
-    nameW.Buffer = typeW.Buffer = NULL;
-    if ((status = get_res_nameW( name, &nameW )) != STATUS_SUCCESS) goto done;
-    if ((status = get_res_nameW( type, &typeW )) != STATUS_SUCCESS) goto done;
-    info.Type = (ULONG)typeW.Buffer;
-    info.Name = (ULONG)nameW.Buffer;
-    info.Language = lang;
-    status = LdrFindResource_U( hModule, &info, 3, &entry );
-done:
     if (HIWORD(nameW.Buffer)) HeapFree( GetProcessHeap(), 0, nameW.Buffer );
     if (HIWORD(typeW.Buffer)) HeapFree( GetProcessHeap(), 0, typeW.Buffer );
-    if (status != STATUS_SUCCESS) SetLastError( RtlNtStatusToDosError(status) );
+
     return (HRSRC)entry;
 }
 
diff -u -r dlls/ntdll/resource.c dlls/ntdll/resource.c
--- dlls/ntdll/resource.c	2003-11-27 10:27:16.000000000 +0000
+++ dlls/ntdll/resource.c	2003-12-02 20:30:08.000000000 +0000
@@ -273,12 +273,12 @@
     const void *res;
     NTSTATUS status;
 
-    if (info) TRACE( "module %p type %s name %s lang %04lx level %ld\n",
+    __TRY
+    {
+	if (info) TRACE( "module %p type %s name %s lang %04lx level %ld\n",
                      hmod, debugstr_w((LPCWSTR)info->Type),
                      debugstr_w((LPCWSTR)info->Name), info->Language, level );
 
-    __TRY
-    {
         status = find_entry( hmod, info, level, &res, TRUE );
         if (status == STATUS_SUCCESS) *dir = res;
     }
@@ -300,12 +300,12 @@
     const void *res;
     NTSTATUS status;
 
-    if (info) TRACE( "module %p type %s name %s lang %04lx level %ld\n",
+    __TRY
+    {
+	if (info) TRACE( "module %p type %s name %s lang %04lx level %ld\n",
                      hmod, debugstr_w((LPCWSTR)info->Type),
                      debugstr_w((LPCWSTR)info->Name), info->Language, level );
 
-    __TRY
-    {
         status = find_entry( hmod, info, level, &res, FALSE );
         if (status == STATUS_SUCCESS) *entry = res;
     }


More information about the wine-patches mailing list