00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017 #include "config.h"
00018
00019 #include <stdlib.h>
00020 #include <sys/types.h>
00021 #include "wine/winestring.h"
00022 #include "wine/windef.h"
00023 #include "wine/pe_image.h"
00024 #include "wine/module.h"
00025 #include "wine/heap.h"
00026
00027
00028
00029 #include "wine/debugtools.h"
00030 #include "ext.h"
00031
00032
00033
00034
00035
00036
00037 static PE_MODREF*
00038 HMODULE32toPE_MODREF(HMODULE hmod) {
00039 WINE_MODREF *wm;
00040
00041 wm = MODULE32_LookupHMODULE( hmod );
00042 if (!wm || wm->type!=MODULE32_PE)
00043 return NULL;
00044 return &(wm->binfmt.pe);
00045 }
00046
00047
00048
00049
00050
00051
00052
00053 PIMAGE_RESOURCE_DIRECTORY GetResDirEntryW(PIMAGE_RESOURCE_DIRECTORY resdirptr,
00054 LPCWSTR name,DWORD root,
00055 WIN_BOOL allowdefault)
00056 {
00057 int entrynum;
00058 PIMAGE_RESOURCE_DIRECTORY_ENTRY entryTable;
00059 int namelen;
00060
00061 if (HIWORD(name)) {
00062 if (name[0]=='#') {
00063 char buf[10];
00064
00065 lstrcpynWtoA(buf,name+1,10);
00066 return GetResDirEntryW(resdirptr,(LPCWSTR)atoi(buf),root,allowdefault);
00067 }
00068 entryTable = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) (
00069 (BYTE *) resdirptr +
00070 sizeof(IMAGE_RESOURCE_DIRECTORY));
00071 namelen = lstrlenW(name);
00072 for (entrynum = 0; entrynum < resdirptr->NumberOfNamedEntries; entrynum++)
00073 {
00074 PIMAGE_RESOURCE_DIR_STRING_U str =
00075 (PIMAGE_RESOURCE_DIR_STRING_U) (root +
00076 entryTable[entrynum].u1.s.NameOffset);
00077 if(namelen != str->Length)
00078 continue;
00079 if(wcsnicmp(name,str->NameString,str->Length)==0)
00080 return (PIMAGE_RESOURCE_DIRECTORY) (
00081 root +
00082 entryTable[entrynum].u2.s.OffsetToDirectory);
00083 }
00084 return NULL;
00085 } else {
00086 entryTable = (PIMAGE_RESOURCE_DIRECTORY_ENTRY) (
00087 (BYTE *) resdirptr +
00088 sizeof(IMAGE_RESOURCE_DIRECTORY) +
00089 resdirptr->NumberOfNamedEntries * sizeof(IMAGE_RESOURCE_DIRECTORY_ENTRY));
00090 for (entrynum = 0; entrynum < resdirptr->NumberOfIdEntries; entrynum++)
00091 if ((DWORD)entryTable[entrynum].u1.Name == (DWORD)name)
00092 return (PIMAGE_RESOURCE_DIRECTORY) (
00093 root +
00094 entryTable[entrynum].u2.s.OffsetToDirectory);
00095
00096 if (allowdefault && !name && resdirptr->NumberOfIdEntries)
00097 return (PIMAGE_RESOURCE_DIRECTORY) (
00098 root +
00099 entryTable[0].u2.s.OffsetToDirectory);
00100 return NULL;
00101 }
00102 }
00103
00104
00105
00106
00107 PIMAGE_RESOURCE_DIRECTORY GetResDirEntryA( PIMAGE_RESOURCE_DIRECTORY resdirptr,
00108 LPCSTR name, DWORD root,
00109 WIN_BOOL allowdefault )
00110 {
00111 PIMAGE_RESOURCE_DIRECTORY retv;
00112 LPWSTR nameW = HIWORD(name)? HEAP_strdupAtoW( GetProcessHeap(), 0, name )
00113 : (LPWSTR)name;
00114
00115 retv = GetResDirEntryW( resdirptr, nameW, root, allowdefault );
00116
00117 if ( HIWORD(name) ) HeapFree( GetProcessHeap(), 0, nameW );
00118
00119 return retv;
00120 }
00121
00122
00123
00124
00125 HANDLE PE_FindResourceExW(
00126 WINE_MODREF *wm,LPCWSTR name,LPCWSTR type,WORD lang
00127 ) {
00128 PIMAGE_RESOURCE_DIRECTORY resdirptr;
00129 DWORD root;
00130 HANDLE result;
00131 PE_MODREF *pem = &(wm->binfmt.pe);
00132
00133 if (!pem || !pem->pe_resource)
00134 return 0;
00135
00136 resdirptr = pem->pe_resource;
00137 root = (DWORD) resdirptr;
00138 if ((resdirptr = GetResDirEntryW(resdirptr, type, root, FALSE)) == NULL)
00139 return 0;
00140 if ((resdirptr = GetResDirEntryW(resdirptr, name, root, FALSE)) == NULL)
00141 return 0;
00142 result = (HANDLE)GetResDirEntryW(resdirptr, (LPCWSTR)(UINT)lang, root, FALSE);
00143
00144 if(!result)
00145 return (HANDLE)GetResDirEntryW(resdirptr, (LPCWSTR)0, root, TRUE);
00146 return result;
00147 }
00148
00149
00150
00151
00152
00153 HANDLE PE_LoadResource( WINE_MODREF *wm, HANDLE hRsrc )
00154 {
00155 if (!hRsrc || !wm || wm->type!=MODULE32_PE)
00156 return 0;
00157 return (HANDLE) (wm->module + ((PIMAGE_RESOURCE_DATA_ENTRY)hRsrc)->OffsetToData);
00158 }
00159
00160
00161
00162
00163
00164 DWORD PE_SizeofResource( HINSTANCE hModule, HANDLE hRsrc )
00165 {
00166
00167 if (!hRsrc)
00168 return 0;
00169 return ((PIMAGE_RESOURCE_DATA_ENTRY)hRsrc)->Size;
00170 }
00171
00172
00173
00174
00175 WIN_BOOL
00176 PE_EnumResourceTypesA(HMODULE hmod,ENUMRESTYPEPROCA lpfun,LONG lparam) {
00177 PE_MODREF *pem = HMODULE32toPE_MODREF(hmod);
00178 int i;
00179 PIMAGE_RESOURCE_DIRECTORY resdir;
00180 PIMAGE_RESOURCE_DIRECTORY_ENTRY et;
00181 WIN_BOOL ret;
00182 HANDLE heap = GetProcessHeap();
00183
00184 if (!pem || !pem->pe_resource)
00185 return FALSE;
00186
00187 resdir = (PIMAGE_RESOURCE_DIRECTORY)pem->pe_resource;
00188 et =(PIMAGE_RESOURCE_DIRECTORY_ENTRY)((LPBYTE)resdir+sizeof(IMAGE_RESOURCE_DIRECTORY));
00189 ret = FALSE;
00190 for (i=0;i<resdir->NumberOfNamedEntries+resdir->NumberOfIdEntries;i++) {
00191 LPSTR name;
00192
00193 if (et[i].u1.s.NameIsString)
00194 name = HEAP_strdupWtoA(heap,0,(LPWSTR)((LPBYTE)pem->pe_resource+et[i].u1.s.NameOffset));
00195 else
00196 name = (LPSTR)(int)et[i].u1.Id;
00197 ret = lpfun(hmod,name,lparam);
00198 if (HIWORD(name))
00199 HeapFree(heap,0,name);
00200 if (!ret)
00201 break;
00202 }
00203 return ret;
00204 }
00205
00206
00207
00208
00209 WIN_BOOL
00210 PE_EnumResourceTypesW(HMODULE hmod,ENUMRESTYPEPROCW lpfun,LONG lparam) {
00211 PE_MODREF *pem = HMODULE32toPE_MODREF(hmod);
00212 int i;
00213 PIMAGE_RESOURCE_DIRECTORY resdir;
00214 PIMAGE_RESOURCE_DIRECTORY_ENTRY et;
00215 WIN_BOOL ret;
00216
00217 if (!pem || !pem->pe_resource)
00218 return FALSE;
00219
00220 resdir = (PIMAGE_RESOURCE_DIRECTORY)pem->pe_resource;
00221 et =(PIMAGE_RESOURCE_DIRECTORY_ENTRY)((LPBYTE)resdir+sizeof(IMAGE_RESOURCE_DIRECTORY));
00222 ret = FALSE;
00223 for (i=0;i<resdir->NumberOfNamedEntries+resdir->NumberOfIdEntries;i++) {
00224 LPWSTR type;
00225 if (et[i].u1.s.NameIsString)
00226 type = (LPWSTR)((LPBYTE)pem->pe_resource+et[i].u1.s.NameOffset);
00227 else
00228 type = (LPWSTR)(int)et[i].u1.Id;
00229
00230 ret = lpfun(hmod,type,lparam);
00231 if (!ret)
00232 break;
00233 }
00234 return ret;
00235 }
00236
00237
00238
00239
00240 WIN_BOOL
00241 PE_EnumResourceNamesA(
00242 HMODULE hmod,LPCSTR type,ENUMRESNAMEPROCA lpfun,LONG lparam
00243 ) {
00244 PE_MODREF *pem = HMODULE32toPE_MODREF(hmod);
00245 int i;
00246 PIMAGE_RESOURCE_DIRECTORY resdir;
00247 PIMAGE_RESOURCE_DIRECTORY_ENTRY et;
00248 WIN_BOOL ret;
00249 HANDLE heap = GetProcessHeap();
00250 LPWSTR typeW;
00251
00252 if (!pem || !pem->pe_resource)
00253 return FALSE;
00254 resdir = (PIMAGE_RESOURCE_DIRECTORY)pem->pe_resource;
00255 if (HIWORD(type))
00256 typeW = HEAP_strdupAtoW(heap,0,type);
00257 else
00258 typeW = (LPWSTR)type;
00259 resdir = GetResDirEntryW(resdir,typeW,(DWORD)pem->pe_resource,FALSE);
00260 if (HIWORD(typeW))
00261 HeapFree(heap,0,typeW);
00262 if (!resdir)
00263 return FALSE;
00264 et =(PIMAGE_RESOURCE_DIRECTORY_ENTRY)((LPBYTE)resdir+sizeof(IMAGE_RESOURCE_DIRECTORY));
00265 ret = FALSE;
00266 for (i=0;i<resdir->NumberOfNamedEntries+resdir->NumberOfIdEntries;i++) {
00267 LPSTR name;
00268
00269 if (et[i].u1.s.NameIsString)
00270 name = HEAP_strdupWtoA(heap,0,(LPWSTR)((LPBYTE)pem->pe_resource+et[i].u1.s.NameOffset));
00271 else
00272 name = (LPSTR)(int)et[i].u1.Id;
00273 ret = lpfun(hmod,type,name,lparam);
00274 if (HIWORD(name)) HeapFree(heap,0,name);
00275 if (!ret)
00276 break;
00277 }
00278 return ret;
00279 }
00280
00281
00282
00283
00284 WIN_BOOL
00285 PE_EnumResourceNamesW(
00286 HMODULE hmod,LPCWSTR type,ENUMRESNAMEPROCW lpfun,LONG lparam
00287 ) {
00288 PE_MODREF *pem = HMODULE32toPE_MODREF(hmod);
00289 int i;
00290 PIMAGE_RESOURCE_DIRECTORY resdir;
00291 PIMAGE_RESOURCE_DIRECTORY_ENTRY et;
00292 WIN_BOOL ret;
00293
00294 if (!pem || !pem->pe_resource)
00295 return FALSE;
00296
00297 resdir = (PIMAGE_RESOURCE_DIRECTORY)pem->pe_resource;
00298 resdir = GetResDirEntryW(resdir,type,(DWORD)pem->pe_resource,FALSE);
00299 if (!resdir)
00300 return FALSE;
00301 et =(PIMAGE_RESOURCE_DIRECTORY_ENTRY)((LPBYTE)resdir+sizeof(IMAGE_RESOURCE_DIRECTORY));
00302 ret = FALSE;
00303 for (i=0;i<resdir->NumberOfNamedEntries+resdir->NumberOfIdEntries;i++) {
00304 LPWSTR name;
00305 if (et[i].u1.s.NameIsString)
00306 name = (LPWSTR)((LPBYTE)pem->pe_resource+et[i].u1.s.NameOffset);
00307 else
00308 name = (LPWSTR)(int)et[i].u1.Id;
00309 ret = lpfun(hmod,type,name,lparam);
00310 if (!ret)
00311 break;
00312 }
00313 return ret;
00314 }
00315
00316
00317
00318
00319 WIN_BOOL
00320 PE_EnumResourceLanguagesA(
00321 HMODULE hmod,LPCSTR name,LPCSTR type,ENUMRESLANGPROCA lpfun,
00322 LONG lparam
00323 ) {
00324 PE_MODREF *pem = HMODULE32toPE_MODREF(hmod);
00325 int i;
00326 PIMAGE_RESOURCE_DIRECTORY resdir;
00327 PIMAGE_RESOURCE_DIRECTORY_ENTRY et;
00328 WIN_BOOL ret;
00329 HANDLE heap = GetProcessHeap();
00330 LPWSTR nameW,typeW;
00331
00332 if (!pem || !pem->pe_resource)
00333 return FALSE;
00334
00335 resdir = (PIMAGE_RESOURCE_DIRECTORY)pem->pe_resource;
00336 if (HIWORD(name))
00337 nameW = HEAP_strdupAtoW(heap,0,name);
00338 else
00339 nameW = (LPWSTR)name;
00340 resdir = GetResDirEntryW(resdir,nameW,(DWORD)pem->pe_resource,FALSE);
00341 if (HIWORD(nameW))
00342 HeapFree(heap,0,nameW);
00343 if (!resdir)
00344 return FALSE;
00345 if (HIWORD(type))
00346 typeW = HEAP_strdupAtoW(heap,0,type);
00347 else
00348 typeW = (LPWSTR)type;
00349 resdir = GetResDirEntryW(resdir,typeW,(DWORD)pem->pe_resource,FALSE);
00350 if (HIWORD(typeW))
00351 HeapFree(heap,0,typeW);
00352 if (!resdir)
00353 return FALSE;
00354 et =(PIMAGE_RESOURCE_DIRECTORY_ENTRY)((LPBYTE)resdir+sizeof(IMAGE_RESOURCE_DIRECTORY));
00355 ret = FALSE;
00356 for (i=0;i<resdir->NumberOfNamedEntries+resdir->NumberOfIdEntries;i++) {
00357
00358 ret = lpfun(hmod,name,type,et[i].u1.Id,lparam);
00359 if (!ret)
00360 break;
00361 }
00362 return ret;
00363 }
00364
00365
00366
00367
00368 WIN_BOOL
00369 PE_EnumResourceLanguagesW(
00370 HMODULE hmod,LPCWSTR name,LPCWSTR type,ENUMRESLANGPROCW lpfun,
00371 LONG lparam
00372 ) {
00373 PE_MODREF *pem = HMODULE32toPE_MODREF(hmod);
00374 int i;
00375 PIMAGE_RESOURCE_DIRECTORY resdir;
00376 PIMAGE_RESOURCE_DIRECTORY_ENTRY et;
00377 WIN_BOOL ret;
00378
00379 if (!pem || !pem->pe_resource)
00380 return FALSE;
00381
00382 resdir = (PIMAGE_RESOURCE_DIRECTORY)pem->pe_resource;
00383 resdir = GetResDirEntryW(resdir,name,(DWORD)pem->pe_resource,FALSE);
00384 if (!resdir)
00385 return FALSE;
00386 resdir = GetResDirEntryW(resdir,type,(DWORD)pem->pe_resource,FALSE);
00387 if (!resdir)
00388 return FALSE;
00389 et =(PIMAGE_RESOURCE_DIRECTORY_ENTRY)((LPBYTE)resdir+sizeof(IMAGE_RESOURCE_DIRECTORY));
00390 ret = FALSE;
00391 for (i=0;i<resdir->NumberOfNamedEntries+resdir->NumberOfIdEntries;i++) {
00392 ret = lpfun(hmod,name,type,et[i].u1.Id,lparam);
00393 if (!ret)
00394 break;
00395 }
00396 return ret;
00397 }