From 4847c1d8e4745ccd63e1db06fe1a693e8a591326 Mon Sep 17 00:00:00 2001 From: Alexandre Julliard Date: Thu, 5 Oct 2023 11:45:15 +0200 Subject: [PATCH] server: Set the dynamically relocated flag when relocations are present. --- dlls/kernel32/tests/loader.c | 8 ++++++++ server/mapping.c | 21 ++++++++++++++++++--- 2 files changed, 26 insertions(+), 3 deletions(-) diff --git a/dlls/kernel32/tests/loader.c b/dlls/kernel32/tests/loader.c index 0e86a0577b1..c250fc5d52d 100644 --- a/dlls/kernel32/tests/loader.c +++ b/dlls/kernel32/tests/loader.c @@ -2153,6 +2153,7 @@ static void test_import_resolution(void) } data, *ptr; IMAGE_NT_HEADERS nt, *pnt; IMAGE_SECTION_HEADER section; + SECTION_IMAGE_INFORMATION image; int test, tls_index_save, nb_rel; #if defined(__i386__) static const UCHAR tls_init_code[] = { @@ -2192,6 +2193,7 @@ static void test_import_resolution(void) #else #define ADD_RELOC(field) data.rel.type_off[nb_rel++] = (IMAGE_REL_BASED_HIGHLOW << 12) + offsetof( struct imports, field ) #endif + winetest_push_context( "%u", test ); nt = nt_header_template; nt.FileHeader.NumberOfSections = 1; nt.FileHeader.SizeOfOptionalHeader = sizeof(IMAGE_OPTIONAL_HEADER); @@ -2363,6 +2365,11 @@ static void test_import_resolution(void) ok( GetLastError() == ERROR_BAD_EXE_FORMAT, "wrong error %lu\n", GetLastError() ); break; } + status = pNtQuerySection( mapping, SectionImageInformation, &image, sizeof(image), &size ); + ok( !status, "NtQuerySection failed %lx\n", status ); + ok( test == 6 ? !image.ImageDynamicallyRelocated : image.ImageDynamicallyRelocated, + "image flags %x\n", image.ImageFlags); + ok( !image.ImageContainsCode, "contains code %x\n", image.ImageContainsCode); ok( mapping != 0, "CreateFileMappingA failed err %lu\n", GetLastError() ); /* make sure that the address is not available */ tmp = VirtualAlloc( (void *)nt.OptionalHeader.ImageBase, 0x10000, @@ -2399,6 +2406,7 @@ static void test_import_resolution(void) break; } DeleteFileA( dll_name ); + winetest_pop_context(); #undef DATA_RVA } } diff --git a/server/mapping.c b/server/mapping.c index 2d0a0b783e2..a6adf4dfbe2 100644 --- a/server/mapping.c +++ b/server/mapping.c @@ -695,7 +695,7 @@ static unsigned int get_image_params( struct mapping *mapping, file_pos_t file_s } opt; } nt; off_t pos; - int size; + int size, has_relocs; size_t mz_size, clr_va = 0, clr_size = 0; unsigned int i; @@ -757,10 +757,15 @@ static unsigned int get_image_params( struct mapping *mapping, file_pos_t file_s mapping->image.header_size = nt.opt.hdr32.SizeOfHeaders; mapping->image.checksum = nt.opt.hdr32.CheckSum; mapping->image.image_flags = 0; + + has_relocs = (nt.opt.hdr32.NumberOfRvaAndSizes > IMAGE_DIRECTORY_ENTRY_BASERELOC && + nt.opt.hdr32.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress && + nt.opt.hdr32.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].Size && + !(nt.FileHeader.Characteristics & IMAGE_FILE_RELOCS_STRIPPED)); if (nt.opt.hdr32.SectionAlignment & page_mask) mapping->image.image_flags |= IMAGE_FLAGS_ImageMappedFlat; else if ((nt.opt.hdr32.DllCharacteristics & IMAGE_DLLCHARACTERISTICS_DYNAMIC_BASE) && - mapping->image.contains_code && !(clr_va && clr_size)) + (has_relocs || mapping->image.contains_code) && !(clr_va && clr_size)) mapping->image.image_flags |= IMAGE_FLAGS_ImageDynamicallyRelocated; break; @@ -800,10 +805,20 @@ static unsigned int get_image_params( struct mapping *mapping, file_pos_t file_s mapping->image.header_size = nt.opt.hdr64.SizeOfHeaders; mapping->image.checksum = nt.opt.hdr64.CheckSum; mapping->image.image_flags = 0; + + has_relocs = (nt.opt.hdr64.NumberOfRvaAndSizes > IMAGE_DIRECTORY_ENTRY_BASERELOC && + nt.opt.hdr64.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress && + nt.opt.hdr64.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].Size && + !(nt.FileHeader.Characteristics & IMAGE_FILE_RELOCS_STRIPPED)); if (nt.opt.hdr64.SectionAlignment & page_mask) mapping->image.image_flags |= IMAGE_FLAGS_ImageMappedFlat; + else if (nt.opt.hdr64.NumberOfRvaAndSizes > IMAGE_DIRECTORY_ENTRY_BASERELOC && + nt.opt.hdr64.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress && + nt.opt.hdr64.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].Size && + !(nt.FileHeader.Characteristics & IMAGE_FILE_RELOCS_STRIPPED)) + mapping->image.image_flags |= IMAGE_FLAGS_ImageDynamicallyRelocated; else if ((nt.opt.hdr64.DllCharacteristics & IMAGE_DLLCHARACTERISTICS_DYNAMIC_BASE) && - mapping->image.contains_code && !(clr_va && clr_size)) + (has_relocs || mapping->image.contains_code) && !(clr_va && clr_size)) mapping->image.image_flags |= IMAGE_FLAGS_ImageDynamicallyRelocated; break;