1 | // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
2 | // for details. All rights reserved. Use of this source code is governed by a |
3 | // BSD-style license that can be found in the LICENSE file. |
4 | |
5 | #include "vm/globals.h" |
6 | #if defined(HOST_OS_WINDOWS) |
7 | |
8 | #include "vm/lockers.h" |
9 | #include "vm/native_symbol.h" |
10 | #include "vm/os.h" |
11 | #include "vm/os_thread.h" |
12 | |
13 | #include <dbghelp.h> // NOLINT |
14 | |
15 | namespace dart { |
16 | |
17 | static bool running_ = false; |
18 | static Mutex* lock_ = NULL; |
19 | |
20 | void NativeSymbolResolver::Init() { |
21 | ASSERT(running_ == false); |
22 | if (lock_ == NULL) { |
23 | lock_ = new Mutex(); |
24 | } |
25 | running_ = true; |
26 | SymSetOptions(SYMOPT_UNDNAME | SYMOPT_DEFERRED_LOADS); |
27 | HANDLE hProcess = GetCurrentProcess(); |
28 | if (!SymInitialize(hProcess, NULL, TRUE)) { |
29 | DWORD error = GetLastError(); |
30 | OS::PrintErr("Failed to init NativeSymbolResolver (SymInitialize %" Pu32 |
31 | ")\n" , |
32 | error); |
33 | return; |
34 | } |
35 | } |
36 | |
37 | void NativeSymbolResolver::Cleanup() { |
38 | MutexLocker lock(lock_); |
39 | if (!running_) { |
40 | return; |
41 | } |
42 | running_ = false; |
43 | HANDLE hProcess = GetCurrentProcess(); |
44 | if (!SymCleanup(hProcess)) { |
45 | DWORD error = GetLastError(); |
46 | OS::PrintErr("Failed to shutdown NativeSymbolResolver (SymCleanup %" Pu32 |
47 | ")\n" , |
48 | error); |
49 | } |
50 | } |
51 | |
52 | char* NativeSymbolResolver::LookupSymbolName(uword pc, uword* start) { |
53 | static const intptr_t kMaxNameLength = 2048; |
54 | static const intptr_t kSymbolInfoSize = sizeof(SYMBOL_INFO); // NOLINT. |
55 | static char buffer[kSymbolInfoSize + kMaxNameLength]; |
56 | static char name_buffer[kMaxNameLength]; |
57 | MutexLocker lock(lock_); |
58 | if (!running_) { |
59 | return NULL; |
60 | } |
61 | if (start != NULL) { |
62 | *start = NULL; |
63 | } |
64 | memset(&buffer[0], 0, sizeof(buffer)); |
65 | HANDLE hProcess = GetCurrentProcess(); |
66 | DWORD64 address = static_cast<DWORD64>(pc); |
67 | PSYMBOL_INFO pSymbol = reinterpret_cast<PSYMBOL_INFO>(&buffer[0]); |
68 | pSymbol->SizeOfStruct = kSymbolInfoSize; |
69 | pSymbol->MaxNameLen = kMaxNameLength; |
70 | DWORD64 displacement; |
71 | BOOL r = SymFromAddr(hProcess, address, &displacement, pSymbol); |
72 | if (r == FALSE) { |
73 | return NULL; |
74 | } |
75 | if (start != NULL) { |
76 | *start = pc - displacement; |
77 | } |
78 | return Utils::StrDup(pSymbol->Name); |
79 | } |
80 | |
81 | void NativeSymbolResolver::FreeSymbolName(char* name) { |
82 | free(name); |
83 | } |
84 | |
85 | bool NativeSymbolResolver::LookupSharedObject(uword pc, |
86 | uword* dso_base, |
87 | char** dso_name) { |
88 | return false; |
89 | } |
90 | |
91 | void NativeSymbolResolver::AddSymbols(const char* dso_name, |
92 | void* buffer, |
93 | size_t size) { |
94 | OS::PrintErr("warning: Dart_AddSymbols has no effect on Windows\n" ); |
95 | } |
96 | |
97 | } // namespace dart |
98 | |
99 | #endif // defined(HOST_OS_WINDOWS) |
100 | |