From: Eric Pouech <epouech@codeweavers.com> Signed-off-by: Eric Pouech <epouech@codeweavers.com> --- dlls/kernel32/tests/loader.c | 147 +++++++++++++++++++---------------- 1 file changed, 81 insertions(+), 66 deletions(-) diff --git a/dlls/kernel32/tests/loader.c b/dlls/kernel32/tests/loader.c index 5bb32a5fd5b..b026259d1ab 100644 --- a/dlls/kernel32/tests/loader.c +++ b/dlls/kernel32/tests/loader.c @@ -4318,65 +4318,25 @@ static PVOID WINAPI failuresyshook(const char *dll, const char *function) return (void*)0x12345678; } -static void test_ResolveDelayLoadedAPI(void) +struct test_delay_import_data +{ + BOOL func; + UINT_PTR ordinal; + BOOL succeeds; +}; + +static BOOL create_delay_import_dll(char dll_name[MAX_PATH], const struct test_delay_import_data *td, size_t num_td, + const char *test_dll, const char *test_func) { - static const char test_dll[] = "secur32.dll"; - static const char test_func[] = "SealMessage"; char temp_path[MAX_PATH]; - char dll_name[MAX_PATH]; - IMAGE_DELAYLOAD_DESCRIPTOR idd, *delaydir; - IMAGE_THUNK_DATA itd32; HANDLE hfile; - HMODULE hlib; - DWORD dummy, file_size, i; + IMAGE_NT_HEADERS nt_header; + IMAGE_DELAYLOAD_DESCRIPTOR idd; + IMAGE_THUNK_DATA itd32; WORD hint = 0; + DWORD dummy; BOOL ret; - IMAGE_NT_HEADERS nt_header; - - static const struct test_data - { - BOOL func; - UINT_PTR ordinal; - BOOL succeeds; - } td[] = - { - { - TRUE, 0, TRUE - }, - { - FALSE, IMAGE_ORDINAL_FLAG | 2, TRUE - }, - { - FALSE, IMAGE_ORDINAL_FLAG | 5, TRUE - }, - { - FALSE, IMAGE_ORDINAL_FLAG | 0, FALSE - }, - { - FALSE, IMAGE_ORDINAL_FLAG | 999, FALSE - }, - }; - - if (!pResolveDelayLoadedAPI) - { - win_skip("ResolveDelayLoadedAPI is not available\n"); - return; - } - - if (0) /* crashes on native */ - { - SetLastError(0xdeadbeef); - ok(!pResolveDelayLoadedAPI(NULL, NULL, NULL, NULL, NULL, 0), - "ResolveDelayLoadedAPI succeeded\n"); - ok(GetLastError() == 0xdeadbeef, "GetLastError changed to %lx\n", GetLastError()); - - cb_count = 0; - SetLastError(0xdeadbeef); - ok(!pResolveDelayLoadedAPI(NULL, NULL, failuredllhook, NULL, NULL, 0), - "ResolveDelayLoadedAPI succeeded\n"); - ok(GetLastError() == 0xdeadbeef, "GetLastError changed to %lx\n", GetLastError()); - ok(cb_count == 1, "Wrong callback count: %d\n", cb_count); - } + size_t i; GetTempPathA(MAX_PATH, temp_path); GetTempFileNameA(temp_path, "ldr", 0, dll_name); @@ -4385,7 +4345,7 @@ static void test_ResolveDelayLoadedAPI(void) if (hfile == INVALID_HANDLE_VALUE) { ok(0, "could not create %s\n", dll_name); - return; + return FALSE; } SetLastError(0xdeadbeef); @@ -4424,9 +4384,8 @@ static void test_ResolveDelayLoadedAPI(void) section.PointerToRawData = 0x2000; section.VirtualAddress = 0x2000; - i = ARRAY_SIZE(td); - section.SizeOfRawData = sizeof(test_dll) + sizeof(hint) + sizeof(test_func) + sizeof(HMODULE) + - 2 * (i + 1) * sizeof(IMAGE_THUNK_DATA); + section.SizeOfRawData = strlen(test_dll) + 1 + sizeof(hint) + strlen(test_func) + 1 + sizeof(HMODULE) + + 2 * (num_td + 1) * sizeof(IMAGE_THUNK_DATA); ok(section.SizeOfRawData <= 0x1000, "Too much tests, add a new section!\n"); section.Misc.VirtualSize = 0x1000; section.Characteristics = IMAGE_SCN_CNT_INITIALIZED_DATA | IMAGE_SCN_MEM_READ | IMAGE_SCN_MEM_WRITE; @@ -4440,9 +4399,9 @@ static void test_ResolveDelayLoadedAPI(void) /* delay data */ idd.Attributes.AllAttributes = 1; idd.DllNameRVA = 0x2000; - idd.ModuleHandleRVA = idd.DllNameRVA + sizeof(test_dll) + sizeof(hint) + sizeof(test_func); + idd.ModuleHandleRVA = idd.DllNameRVA + strlen(test_dll) + 1 + sizeof(hint) + strlen(test_func) + 1; idd.ImportAddressTableRVA = idd.ModuleHandleRVA + sizeof(HMODULE); - idd.ImportNameTableRVA = idd.ImportAddressTableRVA + (i + 1) * sizeof(IMAGE_THUNK_DATA); + idd.ImportNameTableRVA = idd.ImportAddressTableRVA + (num_td + 1) * sizeof(IMAGE_THUNK_DATA); idd.BoundImportAddressTableRVA = 0; idd.UnloadInformationTableRVA = 0; idd.TimeDateStamp = 0; @@ -4460,7 +4419,7 @@ static void test_ResolveDelayLoadedAPI(void) /* extended delay data */ SetLastError(0xdeadbeef); - ret = WriteFile(hfile, test_dll, sizeof(test_dll), &dummy, NULL); + ret = WriteFile(hfile, test_dll, strlen(test_dll) + 1, &dummy, NULL); ok(ret, "WriteFile error %ld\n", GetLastError()); SetLastError(0xdeadbeef); @@ -4468,12 +4427,12 @@ static void test_ResolveDelayLoadedAPI(void) ok(ret, "WriteFile error %ld\n", GetLastError()); SetLastError(0xdeadbeef); - ret = WriteFile(hfile, test_func, sizeof(test_func), &dummy, NULL); + ret = WriteFile(hfile, test_func, strlen(test_func) + 1, &dummy, NULL); ok(ret, "WriteFile error %ld\n", GetLastError()); SetFilePointer( hfile, idd.ImportAddressTableRVA, NULL, FILE_BEGIN ); - for (i = 0; i < ARRAY_SIZE(td); i++) + for (i = 0; i < num_td; i++) { /* 0x1a00 is an empty space between delay data and extended delay data, real thunks are not necessary */ itd32.u1.Function = nt_header.OptionalHeader.ImageBase + 0x1a00 + i * 0x20; @@ -4487,10 +4446,10 @@ static void test_ResolveDelayLoadedAPI(void) ret = WriteFile(hfile, &itd32, sizeof(itd32), &dummy, NULL); ok(ret, "WriteFile error %ld\n", GetLastError()); - for (i = 0; i < ARRAY_SIZE(td); i++) + for (i = 0; i < num_td; i++) { if (td[i].func) - itd32.u1.AddressOfData = idd.DllNameRVA + sizeof(test_dll); + itd32.u1.AddressOfData = idd.DllNameRVA + strlen(test_dll) + 1; else itd32.u1.Ordinal = td[i].ordinal; SetLastError(0xdeadbeef); @@ -4508,6 +4467,62 @@ static void test_ResolveDelayLoadedAPI(void) SetEndOfFile( hfile ); CloseHandle(hfile); + return TRUE; +} + +static void test_ResolveDelayLoadedAPI(void) +{ + static const char *test_dll = "secur32.dll"; + static const char *test_func = "SealMessage"; + char dll_name[MAX_PATH]; + IMAGE_DELAYLOAD_DESCRIPTOR *delaydir; + HMODULE hlib; + DWORD file_size, i; + BOOL ret; + + static const struct test_delay_import_data td[] = + { + { + TRUE, 0, TRUE + }, + { + FALSE, IMAGE_ORDINAL_FLAG | 2, TRUE + }, + { + FALSE, IMAGE_ORDINAL_FLAG | 5, TRUE + }, + { + FALSE, IMAGE_ORDINAL_FLAG | 0, FALSE + }, + { + FALSE, IMAGE_ORDINAL_FLAG | 999, FALSE + }, + }; + + if (!pResolveDelayLoadedAPI) + { + win_skip("ResolveDelayLoadedAPI is not available\n"); + return; + } + + if (0) /* crashes on native */ + { + SetLastError(0xdeadbeef); + ok(!pResolveDelayLoadedAPI(NULL, NULL, NULL, NULL, NULL, 0), + "ResolveDelayLoadedAPI succeeded\n"); + ok(GetLastError() == 0xdeadbeef, "GetLastError changed to %lx\n", GetLastError()); + + cb_count = 0; + SetLastError(0xdeadbeef); + ok(!pResolveDelayLoadedAPI(NULL, NULL, failuredllhook, NULL, NULL, 0), + "ResolveDelayLoadedAPI succeeded\n"); + ok(GetLastError() == 0xdeadbeef, "GetLastError changed to %lx\n", GetLastError()); + ok(cb_count == 1, "Wrong callback count: %d\n", cb_count); + } + + ret = create_delay_import_dll(dll_name, td, ARRAY_SIZE(td), test_dll, test_func); + ok(ret, "Couldn't create test library\n"); + SetLastError(0xdeadbeef); hlib = LoadLibraryA(dll_name); ok(hlib != NULL, "LoadLibrary error %lu\n", GetLastError()); @@ -4545,7 +4560,7 @@ static void test_ResolveDelayLoadedAPI(void) void *ret, *load; /* relocate thunk address by hand since we don't generate reloc records */ - itda[i].u1.AddressOfData += (char *)hlib - (char *)nt_header.OptionalHeader.ImageBase; + itda[i].u1.AddressOfData += (char *)hlib - (char *)nt_header_template.OptionalHeader.ImageBase; if (IMAGE_SNAP_BY_ORDINAL(itdn[i].u1.Ordinal)) load = (void *)GetProcAddress(htarget, (LPSTR)IMAGE_ORDINAL(itdn[i].u1.Ordinal)); -- GitLab https://gitlab.winehq.org/wine/wine/-/merge_requests/11052