Commit fc380e06 authored by Eric Pouech's avatar Eric Pouech Committed by Alexandre Julliard

dbghelp: Separate alternate debug file lookup functions.

Split in two different (and disjoint) the functions for checking that an alternate debug file matches the expected one - the first based on crc - the second based on GNU build-id Signed-off-by: 's avatarEric Pouech <eric.pouech@gmail.com> Signed-off-by: 's avatarAlexandre Julliard <julliard@winehq.org>
parent c58d9cf7
......@@ -467,12 +467,13 @@ static BOOL module_is_container_loaded(const struct process* pcs,
return FALSE;
}
static BOOL image_check_debug_link(const WCHAR* file, struct image_file_map* fmap, DWORD link_crc)
static BOOL image_check_debug_link_crc(const WCHAR* file, struct image_file_map* fmap, DWORD link_crc)
{
DWORD read_bytes;
HANDLE handle;
WCHAR *path;
WORD magic;
DWORD crc;
BOOL ret;
path = get_dos_file_name(file);
......@@ -480,15 +481,12 @@ static BOOL image_check_debug_link(const WCHAR* file, struct image_file_map* fma
heap_free(path);
if (handle == INVALID_HANDLE_VALUE) return FALSE;
if (link_crc)
crc = calc_crc32(handle);
if (crc != link_crc)
{
DWORD crc = calc_crc32(handle);
if (crc != link_crc)
{
WARN("Bad CRC for file %s (got %08x while expecting %08x)\n", debugstr_w(file), crc, link_crc);
CloseHandle(handle);
return FALSE;
}
WARN("Bad CRC for file %s (got %08x while expecting %08x)\n", debugstr_w(file), crc, link_crc);
CloseHandle(handle);
return FALSE;
}
SetFilePointer(handle, 0, 0, FILE_BEGIN);
......@@ -500,6 +498,49 @@ static BOOL image_check_debug_link(const WCHAR* file, struct image_file_map* fma
return ret;
}
static BOOL image_check_debug_link_gnu_id(const WCHAR* file, struct image_file_map* fmap, const BYTE* id, unsigned idlen)
{
struct image_section_map buildid_sect;
DWORD read_bytes;
HANDLE handle;
WCHAR *path;
WORD magic;
BOOL ret;
path = get_dos_file_name(file);
handle = CreateFileW(path, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, 0, NULL);
heap_free(path);
if (handle == INVALID_HANDLE_VALUE) return FALSE;
TRACE("Located debug information file at %s\n", debugstr_w(file));
if (ReadFile(handle, &magic, sizeof(magic), &read_bytes, NULL) && magic == IMAGE_DOS_SIGNATURE)
ret = pe_map_file(handle, fmap, DMT_PE);
else
ret = elf_map_handle(handle, fmap);
CloseHandle(handle);
if (ret && image_find_section(fmap, ".note.gnu.build-id", &buildid_sect))
{
const UINT32* note;
note = (const UINT32*)image_map_section(&buildid_sect);
if (note != IMAGE_NO_MAP)
{
/* the usual ELF note structure: name-size desc-size type <name> <desc> */
if (note[2] == NOTE_GNU_BUILD_ID)
{
if (note[1] == idlen && !memcmp(note + 3 + ((note[0] + 3) >> 2), id, idlen))
return TRUE;
WARN("mismatch in buildid information for %s\n", wine_dbgstr_w(file));
}
}
image_unmap_section(&buildid_sect);
image_unmap_file(fmap);
}
return FALSE;
}
/******************************************************************
* image_locate_debug_link
*
......@@ -548,12 +589,12 @@ static BOOL image_locate_debug_link(const struct module* module, struct image_fi
/* testing execdir/filename */
MultiByteToWideChar(CP_UNIXCP, 0, filename, -1, slash, filename_len);
if (image_check_debug_link(p, fmap_link, crc)) goto found;
if (image_check_debug_link_crc(p, fmap_link, crc)) goto found;
/* testing execdir/.debug/filename */
memcpy(slash, dotDebugW, sizeof(dotDebugW));
MultiByteToWideChar(CP_UNIXCP, 0, filename, -1, slash + ARRAY_SIZE(dotDebugW), filename_len);
if (image_check_debug_link(p, fmap_link, crc)) goto found;
if (image_check_debug_link_crc(p, fmap_link, crc)) goto found;
if (module->real_path)
{
......@@ -562,7 +603,7 @@ static BOOL image_locate_debug_link(const struct module* module, struct image_fi
if ((slash2 = wcsrchr(slash, '/'))) slash = slash2 + 1;
if ((slash2 = wcsrchr(slash, '\\'))) slash = slash2 + 1;
MultiByteToWideChar(CP_UNIXCP, 0, filename, -1, slash, filename_len);
if (image_check_debug_link(p, fmap_link, crc)) goto found;
if (image_check_debug_link_crc(p, fmap_link, crc)) goto found;
}
/* testing globaldebugdir/execdir/filename */
......@@ -570,10 +611,10 @@ static BOOL image_locate_debug_link(const struct module* module, struct image_fi
memcpy(p, globalDebugDirW, globalDebugDirLen * sizeof(WCHAR));
slash += globalDebugDirLen;
MultiByteToWideChar(CP_UNIXCP, 0, filename, -1, slash, filename_len);
if (image_check_debug_link(p, fmap_link, crc)) goto found;
if (image_check_debug_link_crc(p, fmap_link, crc)) goto found;
/* finally testing filename */
if (image_check_debug_link(slash, fmap_link, crc)) goto found;
if (image_check_debug_link_crc(slash, fmap_link, crc)) goto found;
WARN("Couldn't locate or map %s\n", filename);
......@@ -632,33 +673,11 @@ static BOOL image_locate_build_id_target(struct image_file_map* fmap, const BYTE
memcpy(z, dotDebug0W, sizeof(dotDebug0W));
TRACE("checking %s\n", wine_dbgstr_w(p));
if (image_check_debug_link(p, fmap_link, 0))
if (image_check_debug_link_gnu_id(p, fmap_link, idend - idlen, idlen))
{
struct image_section_map buildid_sect;
if (image_find_section(fmap_link, ".note.gnu.build-id", &buildid_sect))
{
const UINT32* note;
note = (const UINT32*)image_map_section(&buildid_sect);
if (note != IMAGE_NO_MAP)
{
/* the usual ELF note structure: name-size desc-size type <name> <desc> */
if (note[2] == NOTE_GNU_BUILD_ID)
{
if (note[1] == idlen &&
!memcmp(note + 3 + ((note[0] + 3) >> 2), idend - idlen, idlen))
{
TRACE("Located debug information file at %s\n", debugstr_w(p));
HeapFree(GetProcessHeap(), 0, p);
fmap->alternate = fmap_link;
return TRUE;
}
WARN("mismatch in buildid information for %s\n", wine_dbgstr_w(p));
}
}
image_unmap_section(&buildid_sect);
}
image_unmap_file(fmap_link);
HeapFree(GetProcessHeap(), 0, p);
fmap->alternate = fmap_link;
return TRUE;
}
TRACE("not found\n");
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment