Commit | Line | Data |
---|---|---|
98a03287 | 1 | /* Internal interfaces for the Windows code |
3c76026d | 2 | Copyright (C) 1995-2020 Free Software Foundation, Inc. |
98a03287 TT |
3 | |
4 | This file is part of GDB. | |
5 | ||
6 | This program is free software; you can redistribute it and/or modify | |
7 | it under the terms of the GNU General Public License as published by | |
8 | the Free Software Foundation; either version 3 of the License, or | |
9 | (at your option) any later version. | |
10 | ||
11 | This program is distributed in the hope that it will be useful, | |
12 | but WITHOUT ANY WARRANTY; without even the implied warranty of | |
13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
14 | GNU General Public License for more details. | |
15 | ||
16 | You should have received a copy of the GNU General Public License | |
17 | along with this program. If not, see <http://www.gnu.org/licenses/>. */ | |
18 | ||
19 | #include "gdbsupport/common-defs.h" | |
20 | #include "nat/windows-nat.h" | |
21 | ||
4834dad0 TT |
22 | namespace windows_nat |
23 | { | |
24 | ||
3c76026d TT |
25 | HANDLE current_process_handle; |
26 | DWORD current_process_id; | |
27 | DWORD main_thread_id; | |
28 | enum gdb_signal last_sig = GDB_SIGNAL_0; | |
29 | DEBUG_EVENT current_event; | |
30 | DEBUG_EVENT last_wait_event; | |
31 | windows_thread_info *current_windows_thread; | |
32 | DWORD desired_stop_thread_id = -1; | |
33 | std::vector<pending_stop> pending_stops; | |
34 | EXCEPTION_RECORD siginfo_er; | |
35 | ||
65bafd5b TT |
36 | windows_thread_info::~windows_thread_info () |
37 | { | |
38 | CloseHandle (h); | |
39 | } | |
40 | ||
98a03287 TT |
41 | void |
42 | windows_thread_info::suspend () | |
43 | { | |
44 | if (suspended != 0) | |
45 | return; | |
46 | ||
47 | if (SuspendThread (h) == (DWORD) -1) | |
48 | { | |
49 | DWORD err = GetLastError (); | |
50 | ||
51 | /* We get Access Denied (5) when trying to suspend | |
52 | threads that Windows started on behalf of the | |
53 | debuggee, usually when those threads are just | |
54 | about to exit. | |
55 | We can get Invalid Handle (6) if the main thread | |
56 | has exited. */ | |
57 | if (err != ERROR_INVALID_HANDLE && err != ERROR_ACCESS_DENIED) | |
58 | warning (_("SuspendThread (tid=0x%x) failed. (winerr %u)"), | |
59 | (unsigned) tid, (unsigned) err); | |
60 | suspended = -1; | |
61 | } | |
62 | else | |
63 | suspended = 1; | |
64 | } | |
65 | ||
66 | void | |
67 | windows_thread_info::resume () | |
68 | { | |
69 | if (suspended > 0) | |
70 | { | |
0a4afda3 TT |
71 | stopped_at_software_breakpoint = false; |
72 | ||
98a03287 TT |
73 | if (ResumeThread (h) == (DWORD) -1) |
74 | { | |
75 | DWORD err = GetLastError (); | |
76 | warning (_("warning: ResumeThread (tid=0x%x) failed. (winerr %u)"), | |
77 | (unsigned) tid, (unsigned) err); | |
78 | } | |
79 | } | |
80 | suspended = 0; | |
81 | } | |
4834dad0 | 82 | |
9d8679cc TT |
83 | const char * |
84 | get_image_name (HANDLE h, void *address, int unicode) | |
85 | { | |
86 | #ifdef __CYGWIN__ | |
87 | static char buf[MAX_PATH]; | |
88 | #else | |
89 | static char buf[(2 * MAX_PATH) + 1]; | |
90 | #endif | |
91 | DWORD size = unicode ? sizeof (WCHAR) : sizeof (char); | |
92 | char *address_ptr; | |
93 | int len = 0; | |
94 | char b[2]; | |
95 | SIZE_T done; | |
96 | ||
97 | /* Attempt to read the name of the dll that was detected. | |
98 | This is documented to work only when actively debugging | |
99 | a program. It will not work for attached processes. */ | |
100 | if (address == NULL) | |
101 | return NULL; | |
102 | ||
103 | #ifdef _WIN32_WCE | |
104 | /* Windows CE reports the address of the image name, | |
105 | instead of an address of a pointer into the image name. */ | |
106 | address_ptr = address; | |
107 | #else | |
108 | /* See if we could read the address of a string, and that the | |
109 | address isn't null. */ | |
110 | if (!ReadProcessMemory (h, address, &address_ptr, | |
111 | sizeof (address_ptr), &done) | |
112 | || done != sizeof (address_ptr) | |
113 | || !address_ptr) | |
114 | return NULL; | |
115 | #endif | |
116 | ||
117 | /* Find the length of the string. */ | |
118 | while (ReadProcessMemory (h, address_ptr + len++ * size, &b, size, &done) | |
119 | && (b[0] != 0 || b[size - 1] != 0) && done == size) | |
120 | continue; | |
121 | ||
122 | if (!unicode) | |
123 | ReadProcessMemory (h, address_ptr, buf, len, &done); | |
124 | else | |
125 | { | |
126 | WCHAR *unicode_address = (WCHAR *) alloca (len * sizeof (WCHAR)); | |
127 | ReadProcessMemory (h, address_ptr, unicode_address, len * sizeof (WCHAR), | |
128 | &done); | |
129 | #ifdef __CYGWIN__ | |
130 | wcstombs (buf, unicode_address, MAX_PATH); | |
131 | #else | |
132 | WideCharToMultiByte (CP_ACP, 0, unicode_address, len, buf, sizeof buf, | |
133 | 0, 0); | |
134 | #endif | |
135 | } | |
136 | ||
137 | return buf; | |
138 | } | |
139 | ||
4834dad0 | 140 | } |