1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
|
// Copyright 2012 Google Inc. All Rights Reserved.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
#ifndef NINJA_BOOTSTRAP
#include <windows.h>
#include <DbgHelp.h>
#include "util.h"
typedef BOOL (WINAPI *MiniDumpWriteDumpFunc) (
IN HANDLE,
IN DWORD,
IN HANDLE,
IN MINIDUMP_TYPE,
IN CONST PMINIDUMP_EXCEPTION_INFORMATION, OPTIONAL
IN CONST PMINIDUMP_USER_STREAM_INFORMATION, OPTIONAL
IN CONST PMINIDUMP_CALLBACK_INFORMATION OPTIONAL
);
/// Creates a windows minidump in temp folder.
void CreateWin32MiniDump(_EXCEPTION_POINTERS* pep) {
char temp_path[MAX_PATH];
GetTempPath(sizeof(temp_path), temp_path);
char temp_file[MAX_PATH];
sprintf(temp_file, "%s\\ninja_crash_dump_%d.dmp",
temp_path, GetCurrentProcessId());
// Delete any previous minidump of the same name.
DeleteFile(temp_file);
// Load DbgHelp.dll dynamically, as library is not present on all
// Windows versions.
HMODULE dbghelp = LoadLibrary("dbghelp.dll");
if (dbghelp == NULL) {
Error("failed to create minidump: LoadLibrary('dbghelp.dll'): %s",
GetLastErrorString().c_str());
return;
}
MiniDumpWriteDumpFunc mini_dump_write_dump =
(MiniDumpWriteDumpFunc)GetProcAddress(dbghelp, "MiniDumpWriteDump");
if (mini_dump_write_dump == NULL) {
Error("failed to create minidump: GetProcAddress('MiniDumpWriteDump'): %s",
GetLastErrorString().c_str());
return;
}
HANDLE hFile = CreateFileA(temp_file, GENERIC_READ | GENERIC_WRITE, 0, NULL,
CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);
if (hFile == NULL) {
Error("failed to create minidump: CreateFileA(%s): %s",
temp_file, GetLastErrorString().c_str());
return;
}
MINIDUMP_EXCEPTION_INFORMATION mdei;
mdei.ThreadId = GetCurrentThreadId();
mdei.ExceptionPointers = pep;
mdei.ClientPointers = FALSE;
MINIDUMP_TYPE mdt = (MINIDUMP_TYPE) (MiniDumpWithDataSegs |
MiniDumpWithHandleData);
BOOL rv = mini_dump_write_dump(GetCurrentProcess(), GetCurrentProcessId(),
hFile, mdt, (pep != 0) ? &mdei : 0, 0, 0);
CloseHandle(hFile);
if (!rv) {
Error("MiniDumpWriteDump failed: %s", GetLastErrorString().c_str());
return;
}
Warning("minidump created: %s", temp_file);
}
#endif // NINJA_BOOTSTRAP
|