From 2ce0e940181a04470f9937a92ae7640fe0e54646 Mon Sep 17 00:00:00 2001 From: Eric Pouech Date: Mon, 23 Jan 2012 21:36:59 +0100 Subject: [PATCH] winedbg, winedump: Embed wine build-id information info minidump, and display it. --- dlls/dbghelp/minidump.c | 42 ++++++++++++++++++++++++++++++++- programs/winedbg/tgt_minidump.c | 18 +++++++++++++- tools/winedump/minidump.c | 15 ++++++++++++ 3 files changed, 73 insertions(+), 2 deletions(-) diff --git a/dlls/dbghelp/minidump.c b/dlls/dbghelp/minidump.c index fd7eb1ace4e..b7e098bec7c 100644 --- a/dlls/dbghelp/minidump.c +++ b/dlls/dbghelp/minidump.c @@ -615,11 +615,29 @@ static unsigned dump_system_info(struct dump_context* dc) OSVERSIONINFOW osInfo; DWORD written; ULONG slen; + DWORD wine_extra = 0; + + const char *(CDECL *wine_get_build_id)(void); + void (CDECL *wine_get_host_version)(const char **sysname, const char **release); + const char* build_id = NULL; + const char* sys_name = NULL; + const char* release_name = NULL; GetSystemInfo(&sysInfo); osInfo.dwOSVersionInfoSize = sizeof(osInfo); GetVersionExW(&osInfo); + wine_get_build_id = (void *)GetProcAddress(GetModuleHandleA("ntdll.dll"), "wine_get_build_id"); + wine_get_host_version = (void *)GetProcAddress(GetModuleHandleA("ntdll.dll"), "wine_get_host_version"); + if (wine_get_build_id && wine_get_host_version) + { + /* cheat minidump system information by adding specific wine information */ + wine_extra = 4 + 4 * sizeof(slen); + build_id = wine_get_build_id(); + wine_get_host_version(&sys_name, &release_name); + wine_extra += strlen(build_id) + 1 + strlen(sys_name) + 1 + strlen(release_name) + 1; + } + mdSysInfo.ProcessorArchitecture = sysInfo.u.s.wProcessorArchitecture; mdSysInfo.ProcessorLevel = sysInfo.wProcessorLevel; mdSysInfo.ProcessorRevision = sysInfo.wProcessorRevision; @@ -630,7 +648,7 @@ static unsigned dump_system_info(struct dump_context* dc) mdSysInfo.BuildNumber = osInfo.dwBuildNumber; mdSysInfo.PlatformId = osInfo.dwPlatformId; - mdSysInfo.CSDVersionRva = dc->rva + sizeof(mdSysInfo); + mdSysInfo.CSDVersionRva = dc->rva + sizeof(mdSysInfo) + wine_extra; mdSysInfo.u1.Reserved1 = 0; mdSysInfo.u1.s.SuiteMask = VER_SUITE_TERMINAL; @@ -672,6 +690,28 @@ static unsigned dump_system_info(struct dump_context* dc) } append(dc, &mdSysInfo, sizeof(mdSysInfo)); + /* write Wine specific system information just behind the structure, and before any string */ + if (wine_extra) + { + char code[] = {'W','I','N','E'}; + + WriteFile(dc->hFile, code, 4, &written, NULL); + /* number of sub-info, so that we can extend structure if needed */ + slen = 3; + WriteFile(dc->hFile, &slen, sizeof(slen), &written, NULL); + /* we store offsets from just after the WINE marker */ + slen = 4 * sizeof(DWORD); + WriteFile(dc->hFile, &slen, sizeof(slen), &written, NULL); + slen += strlen(build_id) + 1; + WriteFile(dc->hFile, &slen, sizeof(slen), &written, NULL); + slen += strlen(sys_name) + 1; + WriteFile(dc->hFile, &slen, sizeof(slen), &written, NULL); + WriteFile(dc->hFile, build_id, strlen(build_id) + 1, &written, NULL); + WriteFile(dc->hFile, sys_name, strlen(sys_name) + 1, &written, NULL); + WriteFile(dc->hFile, release_name, strlen(release_name) + 1, &written, NULL); + dc->rva += wine_extra; + } + /* write the service pack version string after this stream. It is referenced within the stream by its RVA in the file. */ slen = lstrlenW(osInfo.szCSDVersion) * sizeof(WCHAR); diff --git a/programs/winedbg/tgt_minidump.c b/programs/winedbg/tgt_minidump.c index f5750e8942a..afa41d85439 100644 --- a/programs/winedbg/tgt_minidump.c +++ b/programs/winedbg/tgt_minidump.c @@ -174,6 +174,7 @@ static enum dbg_start minidump_do_reload(struct tgt_process_minidump_data* data) MINIDUMP_MODULE_LIST* mml; MINIDUMP_MODULE* mm; MINIDUMP_STRING* mds; + MINIDUMP_DIRECTORY* dir; WCHAR exec_name[1024]; WCHAR nameW[1024]; unsigned len; @@ -212,7 +213,7 @@ static enum dbg_start minidump_do_reload(struct tgt_process_minidump_data* data) } } - if (MiniDumpReadDumpStream(data->mapping, SystemInfoStream, NULL, &stream, NULL)) + if (MiniDumpReadDumpStream(data->mapping, SystemInfoStream, &dir, &stream, NULL)) { MINIDUMP_SYSTEM_INFO* msi = stream; const char *str; @@ -305,6 +306,21 @@ static enum dbg_start minidump_do_reload(struct tgt_process_minidump_data* data) } dbg_printf(" on Windows %s (%u)\n", str, msi->BuildNumber); /* FIXME CSD: msi->CSDVersionRva */ + + if (sizeof(MINIDUMP_SYSTEM_INFO) + 4 > dir->Location.DataSize && + msi->CSDVersionRva >= dir->Location.Rva + sizeof(MINIDUMP_SYSTEM_INFO) + 4) + { + const char* code = (const char*)stream + sizeof(MINIDUMP_SYSTEM_INFO); + const DWORD* wes; + + if (code[0] == 'W' && code[1] == 'I' && code[2] == 'N' && code[3] == 'E' && + *(wes = (const DWORD*)(code += 4)) >= 3) + { + /* assume we have wine extensions */ + dbg_printf(" [on %s, on top of %s (%s)]\n", + code + wes[1], code + wes[2], code + wes[3]); + } + } } dbg_curr_process = dbg_add_process(&be_process_minidump_io, pid, hProc); diff --git a/tools/winedump/minidump.c b/tools/winedump/minidump.c index 4cd04f305bc..ddd0ed6502c 100644 --- a/tools/winedump/minidump.c +++ b/tools/winedump/minidump.c @@ -341,6 +341,21 @@ void mdmp_dump(void) printf(" x86.AMDExtendedCpuFeatures: %x\n", msi->Cpu.X86CpuInfo.AMDExtendedCpuFeatures); } + if (sizeof(MINIDUMP_SYSTEM_INFO) + 4 > dir->Location.DataSize && + msi->CSDVersionRva >= dir->Location.Rva + 4) + { + const char* code = PRD(dir->Location.Rva + sizeof(MINIDUMP_SYSTEM_INFO), 4); + const DWORD* wes; + if (code && code[0] == 'W' && code[1] == 'I' && code[2] == 'N' && code[3] == 'E' && + *(wes = (const DWORD*)(code += 4)) >= 3) + { + /* assume we have wine extensions */ + printf(" Wine details:\n"); + printf(" build-id: %s\n", code + wes[1]); + printf(" system: %s\n", code + wes[2]); + printf(" release: %s\n", code + wes[3]); + } + } } break; case MiscInfoStream: