While going through the shell32 sources I found several issues with respect of
this
and at least one of them I couldn't find in the Janitorial list.
ExtractIconW calls ExtractIconA which is mentioned but ExtractIconA calls
InternalExtractIcon16 which is a 16 bit undocumented but exported function.
I guess this should also go into the 32->16bit list somehow.
I have worked on some fix for this but have to admit that this seems a little
bit tricky. InternalExtractIcon16 also tries to open the file name with
LoadLibrary16 so if it is a 16bit DLL the requested icons will still be
extracted. PrivateExtractIcon and friends which are similar but also can
handle negative icon indices which indicates that it should be treated as
icon identifier, do as far as I can see not deal with 16bit libraries (they
ultimatively call ICO_ExtractIconExW.
This of course poses the question if the 32bit function ExtractIcon is supposed
to return icons for 16bit libraries and if so, ExtractIconEx may actually also
be required to do so.
Below is a first attempt for a patch which does most probably not try to load
resources from 16bit libraries yet.
Also how about going with InternalExtractIcon16?
Any comments to this?
Rolf Kalbermatter
Index: dlls/shell32/shell32_main.c
===================================================================
RCS file: /home/wine/wine/dlls/shell32/shell32_main.c,v
retrieving revision 1.108
diff -u -r1.108 shell32_main.c
--- dlls/shell32/shell32_main.c 21 Nov 2002 23:56:42 -0000 1.108
+++ dlls/shell32/shell32_main.c 2 Dec 2002 20:43:23 -0000
@@ -544,19 +544,18 @@
* FIXME
* if the filename is not a file return 1
*/
-HICON WINAPI ExtractIconA( HINSTANCE hInstance, LPCSTR lpszExeFileName,
- UINT nIconIndex )
-{ HGLOBAL16 handle =
InternalExtractIcon16(HINSTANCE_16(hInstance),lpszExeFileName,nIconIndex, 1);
- TRACE("\n");
- if( handle )
- {
- HICON16* ptr = (HICON16*)GlobalLock16(handle);
- HICON16 hIcon = *ptr;
-
- GlobalFree16(handle);
- return HICON_32(hIcon);
- }
- return 0;
+HICON WINAPI ExtractIconA(HINSTANCE hInstance, LPCSTR lpszFile, UINT
nIconIndex)
+{
+ HICON ret;
+ INT len = MultiByteToWideChar(CP_ACP, 0, lpszFile, -1, NULL, 0);
+ LPWSTR lpwstrFile = HeapAlloc(GetProcessHeap(), 0, len * sizeof(WCHAR));
+
+ TRACE("%p %s %d\n", hInstance, lpszFile, nIconIndex);
+
+ MultiByteToWideChar(CP_ACP, 0, lpszFile, -1, lpwstrFile, len);
+ ExtractIconW(hInstance, lpwstrFile, nIconIndex);
+ HeapFree(GetProcessHeap(), 0, lpwstrFile);
+ return ret;
}
/*************************************************************************
@@ -564,18 +563,21 @@
*
* FIXME: if the filename is not a file return 1
*/
-HICON WINAPI ExtractIconW( HINSTANCE hInstance, LPCWSTR lpszExeFileName,
- UINT nIconIndex )
-{ LPSTR exefn;
- HICON ret;
- TRACE("\n");
+HICON WINAPI ExtractIconW(HINSTANCE hInstance, LPCWSTR lpszFile, UINT
nIconIndex)
+{
+ HICON hIcon = NULL;
+
+ TRACE("(%p %s %d\n", hInstance, debugstr_w(lpszFile), nIconIndex);
- exefn = HEAP_strdupWtoA(GetProcessHeap(),0,lpszExeFileName);
- ret = ExtractIconA(hInstance,exefn,nIconIndex);
+ if (nIconIndex == -1)
+ return (HICON) PrivateExtractIconsW(lpszFile, -1, 0, 0, NULL, 0, 0, 0);
- HeapFree(GetProcessHeap(),0,exefn);
- return ret;
+ ExtractIconExW (lpszFile, nIconIndex, &hIcon, NULL, 1);
+ if (hIcon)
+ return hIcon;
+ return (HICON)1;
}
+
typedef struct
{ LPCSTR szApp;