2002-03-05 Chris Demetriou <cgd@broadcom.com>
[deliverable/binutils-gdb.git] / gdb / windows-nat.c
CommitLineData
24e60978 1/* Target-vector operations for controlling win32 child processes, for GDB.
0a65a603
AC
2
3 Copyright 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002 Free
4 Software Foundation, Inc.
5
e6433c28 6 Contributed by Cygnus Solutions, A Red Hat Company.
e88c49c3 7
24e60978
SC
8 This file is part of GDB.
9
10 This program is free software; you can redistribute it and/or modify
11 it under the terms of the GNU General Public License as published by
12 the Free Software Foundation; either version 2 of the License, or
13 (at your option) any later version.
14
15 This program is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without eve nthe implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 GNU General Public License for more details.
19
20 You should have received a copy of the GNU General Public License
21 along with this program; if not, write to the Free Software
3a4b77d8 22 Foundation, Inc., 59 Temple Place - Suite 330,
4e052eda 23 Boston, MA 02111-1307, USA. */
24e60978 24
dfe7f3ac 25/* Originally by Steve Chamberlain, sac@cygnus.com */
24e60978 26
3cee93ac 27/* We assume we're being built with and will be used for cygwin. */
e88c49c3 28
24e60978 29#include "defs.h"
97da3b20 30#include "tm.h" /* required for SSE registers */
24e60978
SC
31#include "frame.h" /* required by inferior.h */
32#include "inferior.h"
33#include "target.h"
24e60978
SC
34#include "gdbcore.h"
35#include "command.h"
fa58ee11 36#include "completer.h"
4e052eda 37#include "regcache.h"
2a3d5645 38#include "top.h"
c25b74ac 39#include "i386-tdep.h"
24e60978
SC
40#include <signal.h>
41#include <sys/types.h>
42#include <fcntl.h>
cad9cd60 43#include <stdlib.h>
cad9cd60 44#include <windows.h>
1e37c281 45#include <imagehlp.h>
29fe111d 46#include <sys/cygwin.h>
cad9cd60 47
24e60978 48#include "buildsym.h"
1ef980b9
SC
49#include "symfile.h"
50#include "objfiles.h"
24e60978 51#include "gdb_string.h"
fdfa3315 52#include "gdbthread.h"
24e60978 53#include "gdbcmd.h"
1750a5ef 54#include <sys/param.h>
1e37c281 55#include <unistd.h>
24e60978 56
0714f9bf 57/* The ui's event loop. */
507f3c78 58extern int (*ui_loop_hook) (int signo);
0714f9bf
SS
59
60/* If we're not using the old Cygwin header file set, define the
61 following which never should have been in the generic Win32 API
62 headers in the first place since they were our own invention... */
63#ifndef _GNU_H_WINDOWS_H
9d3789f7 64enum
8e860359
CF
65 {
66 FLAG_TRACE_BIT = 0x100,
67 CONTEXT_DEBUGGER = (CONTEXT_FULL | CONTEXT_FLOATING_POINT)
68 };
0714f9bf 69#endif
8e860359
CF
70#include <sys/procfs.h>
71#include <psapi.h>
0714f9bf 72
97da3b20 73#ifdef HAVE_SSE_REGS
fa4ba8da
PM
74#define CONTEXT_DEBUGGER_DR CONTEXT_DEBUGGER | CONTEXT_DEBUG_REGISTERS \
75 | CONTEXT_EXTENDED_REGISTERS
97da3b20 76#else
fa4ba8da 77#define CONTEXT_DEBUGGER_DR CONTEXT_DEBUGGER | CONTEXT_DEBUG_REGISTERS
97da3b20
CF
78#endif
79
fa4ba8da
PM
80static unsigned dr[8];
81static int debug_registers_changed = 0;
82static int debug_registers_used = 0;
97da3b20 83
3cee93ac
CF
84/* The string sent by cygwin when it processes a signal.
85 FIXME: This should be in a cygwin include file. */
86#define CYGWIN_SIGNAL_STRING "cygwin: signal"
87
29fe111d 88#define CHECK(x) check (x, __FILE__,__LINE__)
dfe7f3ac 89#define DEBUG_EXEC(x) if (debug_exec) printf_unfiltered x
4e52d31c
PM
90#define DEBUG_EVENTS(x) if (debug_events) printf_unfiltered x
91#define DEBUG_MEM(x) if (debug_memory) printf_unfiltered x
92#define DEBUG_EXCEPT(x) if (debug_exceptions) printf_unfiltered x
24e60978
SC
93
94/* Forward declaration */
95extern struct target_ops child_ops;
96
a14ed312 97static void child_stop (void);
39f77062 98static int win32_child_thread_alive (ptid_t);
a14ed312 99void child_kill_inferior (void);
3cee93ac 100
7393af7c
PM
101static enum target_signal last_sig = TARGET_SIGNAL_0;
102/* Set if a signal was received from the debugged process */
103
3cee93ac
CF
104/* Thread information structure used to track information that is
105 not available in gdb's thread structure. */
106typedef struct thread_info_struct
3a4b77d8
JM
107 {
108 struct thread_info_struct *next;
109 DWORD id;
110 HANDLE h;
111 char *name;
112 int suspend_count;
113 CONTEXT context;
1e37c281 114 STACKFRAME sf;
8e860359
CF
115 }
116thread_info;
1e37c281 117
29fe111d 118static thread_info thread_head;
24e60978 119
24e60978
SC
120/* The process and thread handles for the above context. */
121
3cee93ac
CF
122static DEBUG_EVENT current_event; /* The current debug event from
123 WaitForDebugEvent */
124static HANDLE current_process_handle; /* Currently executing process */
125static thread_info *current_thread; /* Info on currently selected thread */
3a4b77d8 126static DWORD main_thread_id; /* Thread ID of the main thread */
24e60978
SC
127
128/* Counts of things. */
129static int exception_count = 0;
130static int event_count = 0;
dfe7f3ac 131static int saw_create;
24e60978
SC
132
133/* User options. */
134static int new_console = 0;
1e37c281 135static int new_group = 1;
dfe7f3ac
CF
136static int debug_exec = 0; /* show execution */
137static int debug_events = 0; /* show events from kernel */
138static int debug_memory = 0; /* show target memory accesses */
1ef980b9 139static int debug_exceptions = 0; /* show target exceptions */
dfe7f3ac
CF
140static int useshell = 0; /* use shell for subprocesses */
141
142/* Path to shell */
143static char shell[MAX_PATH + 1];
24e60978
SC
144
145/* This vector maps GDB's idea of a register's number into an address
3cee93ac 146 in the win32 exception context vector.
24e60978 147
3cee93ac 148 It also contains the bit mask needed to load the register in question.
24e60978
SC
149
150 One day we could read a reg, we could inspect the context we
151 already have loaded, if it doesn't have the bit set that we need,
152 we read that set of registers in using GetThreadContext. If the
153 context already contains what we need, we just unpack it. Then to
154 write a register, first we have to ensure that the context contains
155 the other regs of the group, and then we copy the info in and set
156 out bit. */
157
3cee93ac
CF
158#define context_offset(x) ((int)&(((CONTEXT *)NULL)->x))
159static const int mappings[] =
24e60978 160{
3a4b77d8
JM
161 context_offset (Eax),
162 context_offset (Ecx),
163 context_offset (Edx),
164 context_offset (Ebx),
165 context_offset (Esp),
166 context_offset (Ebp),
167 context_offset (Esi),
168 context_offset (Edi),
169 context_offset (Eip),
170 context_offset (EFlags),
171 context_offset (SegCs),
172 context_offset (SegSs),
173 context_offset (SegDs),
174 context_offset (SegEs),
175 context_offset (SegFs),
176 context_offset (SegGs),
177 context_offset (FloatSave.RegisterArea[0 * 10]),
178 context_offset (FloatSave.RegisterArea[1 * 10]),
179 context_offset (FloatSave.RegisterArea[2 * 10]),
180 context_offset (FloatSave.RegisterArea[3 * 10]),
181 context_offset (FloatSave.RegisterArea[4 * 10]),
182 context_offset (FloatSave.RegisterArea[5 * 10]),
183 context_offset (FloatSave.RegisterArea[6 * 10]),
184 context_offset (FloatSave.RegisterArea[7 * 10]),
1e37c281
JM
185 context_offset (FloatSave.ControlWord),
186 context_offset (FloatSave.StatusWord),
187 context_offset (FloatSave.TagWord),
188 context_offset (FloatSave.ErrorSelector),
189 context_offset (FloatSave.ErrorOffset),
190 context_offset (FloatSave.DataSelector),
191 context_offset (FloatSave.DataOffset),
d3a09475 192 context_offset (FloatSave.ErrorSelector)
97da3b20
CF
193#ifdef HAVE_SSE_REGS
194 /* XMM0-7 */ ,
441532d7
PM
195 context_offset (ExtendedRegisters[10*16]),
196 context_offset (ExtendedRegisters[11*16]),
197 context_offset (ExtendedRegisters[12*16]),
198 context_offset (ExtendedRegisters[13*16]),
199 context_offset (ExtendedRegisters[14*16]),
200 context_offset (ExtendedRegisters[15*16]),
201 context_offset (ExtendedRegisters[16*16]),
202 context_offset (ExtendedRegisters[17*16]),
203 /* MXCSR */
204 context_offset (ExtendedRegisters[24])
97da3b20 205#endif
24e60978
SC
206};
207
d3a09475
JM
208#undef context_offset
209
24e60978
SC
210/* This vector maps the target's idea of an exception (extracted
211 from the DEBUG_EVENT structure) to GDB's idea. */
212
213struct xlate_exception
214 {
215 int them;
216 enum target_signal us;
217 };
218
24e60978
SC
219static const struct xlate_exception
220 xlate[] =
221{
222 {EXCEPTION_ACCESS_VIOLATION, TARGET_SIGNAL_SEGV},
9cbf6c0e 223 {STATUS_STACK_OVERFLOW, TARGET_SIGNAL_SEGV},
24e60978
SC
224 {EXCEPTION_BREAKPOINT, TARGET_SIGNAL_TRAP},
225 {DBG_CONTROL_C, TARGET_SIGNAL_INT},
226 {EXCEPTION_SINGLE_STEP, TARGET_SIGNAL_TRAP},
7393af7c 227 {STATUS_FLOAT_DIVIDE_BY_ZERO, TARGET_SIGNAL_FPE},
24e60978
SC
228 {-1, -1}};
229
fa4ba8da
PM
230static void
231check (BOOL ok, const char *file, int line)
232{
233 if (!ok)
dfe7f3ac 234 printf_filtered ("error return %s:%d was %lu\n", file, line,
fa4ba8da
PM
235 GetLastError ());
236}
237
238
3cee93ac
CF
239/* Find a thread record given a thread id.
240 If get_context then also retrieve the context for this
241 thread. */
242static thread_info *
243thread_rec (DWORD id, int get_context)
24e60978 244{
3cee93ac
CF
245 thread_info *th;
246
3a4b77d8 247 for (th = &thread_head; (th = th->next) != NULL;)
3cee93ac
CF
248 if (th->id == id)
249 {
250 if (!th->suspend_count && get_context)
251 {
8a892701 252 if (get_context > 0 && id != current_event.dwThreadId)
3cee93ac
CF
253 th->suspend_count = SuspendThread (th->h) + 1;
254 else if (get_context < 0)
255 th->suspend_count = -1;
256
97da3b20 257 th->context.ContextFlags = CONTEXT_DEBUGGER_DR;
3cee93ac 258 GetThreadContext (th->h, &th->context);
fa4ba8da
PM
259 if (id == current_event.dwThreadId)
260 {
261 /* Copy dr values from that thread. */
262 dr[0] = th->context.Dr0;
263 dr[1] = th->context.Dr1;
264 dr[2] = th->context.Dr2;
265 dr[3] = th->context.Dr3;
266 dr[6] = th->context.Dr6;
267 dr[7] = th->context.Dr7;
268 }
3cee93ac
CF
269 }
270 return th;
271 }
272
273 return NULL;
274}
275
276/* Add a thread to the thread list */
277static thread_info *
3a4b77d8 278child_add_thread (DWORD id, HANDLE h)
3cee93ac
CF
279{
280 thread_info *th;
281
282 if ((th = thread_rec (id, FALSE)))
283 return th;
284
285 th = (thread_info *) xmalloc (sizeof (*th));
3a4b77d8 286 memset (th, 0, sizeof (*th));
3cee93ac
CF
287 th->id = id;
288 th->h = h;
289 th->next = thread_head.next;
290 thread_head.next = th;
39f77062 291 add_thread (pid_to_ptid (id));
dfe7f3ac 292 /* Set the debug registers for the new thread in they are used. */
fa4ba8da
PM
293 if (debug_registers_used)
294 {
295 /* Only change the value of the debug registers. */
296 th->context.ContextFlags = CONTEXT_DEBUG_REGISTERS;
297 CHECK (GetThreadContext (th->h, &th->context));
298 th->context.Dr0 = dr[0];
299 th->context.Dr1 = dr[1];
300 th->context.Dr2 = dr[2];
301 th->context.Dr3 = dr[3];
302 /* th->context.Dr6 = dr[6];
303 FIXME: should we set dr6 also ?? */
304 th->context.Dr7 = dr[7];
305 CHECK (SetThreadContext (th->h, &th->context));
306 th->context.ContextFlags = 0;
307 }
3cee93ac 308 return th;
24e60978
SC
309}
310
3cee93ac
CF
311/* Clear out any old thread list and reintialize it to a
312 pristine state. */
24e60978 313static void
fba45db2 314child_init_thread_list (void)
24e60978 315{
3cee93ac
CF
316 thread_info *th = &thread_head;
317
318 DEBUG_EVENTS (("gdb: child_init_thread_list\n"));
319 init_thread_list ();
320 while (th->next != NULL)
24e60978 321 {
3cee93ac
CF
322 thread_info *here = th->next;
323 th->next = here->next;
324 (void) CloseHandle (here->h);
b8c9b27d 325 xfree (here);
24e60978 326 }
3cee93ac
CF
327}
328
329/* Delete a thread from the list of threads */
330static void
331child_delete_thread (DWORD id)
332{
333 thread_info *th;
334
335 if (info_verbose)
39f77062
KB
336 printf_unfiltered ("[Deleting %s]\n", target_pid_to_str (pid_to_ptid (id)));
337 delete_thread (pid_to_ptid (id));
3cee93ac
CF
338
339 for (th = &thread_head;
340 th->next != NULL && th->next->id != id;
341 th = th->next)
342 continue;
343
344 if (th->next != NULL)
24e60978 345 {
3cee93ac
CF
346 thread_info *here = th->next;
347 th->next = here->next;
348 CloseHandle (here->h);
b8c9b27d 349 xfree (here);
24e60978
SC
350 }
351}
352
3cee93ac
CF
353static void
354do_child_fetch_inferior_registers (int r)
24e60978 355{
1e37c281
JM
356 char *context_offset = ((char *) &current_thread->context) + mappings[r];
357 long l;
358 if (r == FCS_REGNUM)
359 {
8e860359 360 l = *((long *) context_offset) & 0xffff;
1e37c281
JM
361 supply_register (r, (char *) &l);
362 }
363 else if (r == FOP_REGNUM)
364 {
8e860359 365 l = (*((long *) context_offset) >> 16) & ((1 << 11) - 1);
1e37c281
JM
366 supply_register (r, (char *) &l);
367 }
368 else if (r >= 0)
d3a09475 369 supply_register (r, context_offset);
3cee93ac 370 else
24e60978
SC
371 {
372 for (r = 0; r < NUM_REGS; r++)
3cee93ac 373 do_child_fetch_inferior_registers (r);
24e60978 374 }
3cee93ac
CF
375}
376
377static void
378child_fetch_inferior_registers (int r)
379{
39f77062 380 current_thread = thread_rec (PIDGET (inferior_ptid), TRUE);
3cee93ac
CF
381 do_child_fetch_inferior_registers (r);
382}
383
384static void
385do_child_store_inferior_registers (int r)
386{
387 if (r >= 0)
388 read_register_gen (r, ((char *) &current_thread->context) + mappings[r]);
24e60978
SC
389 else
390 {
3cee93ac
CF
391 for (r = 0; r < NUM_REGS; r++)
392 do_child_store_inferior_registers (r);
24e60978
SC
393 }
394}
395
3cee93ac
CF
396/* Store a new register value into the current thread context */
397static void
398child_store_inferior_registers (int r)
399{
39f77062 400 current_thread = thread_rec (PIDGET (inferior_ptid), TRUE);
3cee93ac
CF
401 do_child_store_inferior_registers (r);
402}
24e60978 403
1e37c281
JM
404static int psapi_loaded = 0;
405static HMODULE psapi_module_handle = NULL;
8e860359
CF
406static BOOL WINAPI (*psapi_EnumProcessModules) (HANDLE, HMODULE *, DWORD, LPDWORD) = NULL;
407static BOOL WINAPI (*psapi_GetModuleInformation) (HANDLE, HMODULE, LPMODULEINFO, DWORD) = NULL;
408static DWORD WINAPI (*psapi_GetModuleFileNameExA) (HANDLE, HMODULE, LPSTR, DWORD) = NULL;
1e37c281 409
3bccec63 410int
8e860359 411psapi_get_dll_name (DWORD BaseAddress, char *dll_name_ret)
1e37c281
JM
412{
413 DWORD len;
414 MODULEINFO mi;
415 int i;
8e860359
CF
416 HMODULE dh_buf[1];
417 HMODULE *DllHandle = dh_buf;
1e37c281
JM
418 DWORD cbNeeded;
419 BOOL ok;
420
421 if (!psapi_loaded ||
8e860359
CF
422 psapi_EnumProcessModules == NULL ||
423 psapi_GetModuleInformation == NULL ||
424 psapi_GetModuleFileNameExA == NULL)
1e37c281 425 {
8e860359
CF
426 if (psapi_loaded)
427 goto failed;
1e37c281
JM
428 psapi_loaded = 1;
429 psapi_module_handle = LoadLibrary ("psapi.dll");
430 if (!psapi_module_handle)
8e860359
CF
431 {
432 /* printf_unfiltered ("error loading psapi.dll: %u", GetLastError ()); */
433 goto failed;
434 }
435 psapi_EnumProcessModules = GetProcAddress (psapi_module_handle, "EnumProcessModules");
1e37c281
JM
436 psapi_GetModuleInformation = GetProcAddress (psapi_module_handle, "GetModuleInformation");
437 psapi_GetModuleFileNameExA = (void *) GetProcAddress (psapi_module_handle,
8e860359
CF
438 "GetModuleFileNameExA");
439 if (psapi_EnumProcessModules == NULL ||
440 psapi_GetModuleInformation == NULL ||
441 psapi_GetModuleFileNameExA == NULL)
1e37c281
JM
442 goto failed;
443 }
444
445 cbNeeded = 0;
446 ok = (*psapi_EnumProcessModules) (current_process_handle,
8e860359
CF
447 DllHandle,
448 sizeof (HMODULE),
449 &cbNeeded);
1e37c281
JM
450
451 if (!ok || !cbNeeded)
452 goto failed;
453
8e860359 454 DllHandle = (HMODULE *) alloca (cbNeeded);
1e37c281
JM
455 if (!DllHandle)
456 goto failed;
457
458 ok = (*psapi_EnumProcessModules) (current_process_handle,
8e860359
CF
459 DllHandle,
460 cbNeeded,
461 &cbNeeded);
1e37c281
JM
462 if (!ok)
463 goto failed;
464
29fe111d 465 for (i = 0; i < (int) (cbNeeded / sizeof (HMODULE)); i++)
1e37c281
JM
466 {
467 if (!(*psapi_GetModuleInformation) (current_process_handle,
8e860359
CF
468 DllHandle[i],
469 &mi,
470 sizeof (mi)))
1e37c281
JM
471 error ("Can't get module info");
472
473 len = (*psapi_GetModuleFileNameExA) (current_process_handle,
8e860359
CF
474 DllHandle[i],
475 dll_name_ret,
476 MAX_PATH);
1e37c281 477 if (len == 0)
29fe111d 478 error ("Error getting dll name: %u\n", GetLastError ());
1e37c281
JM
479
480 if ((DWORD) (mi.lpBaseOfDll) == BaseAddress)
481 return 1;
482 }
483
484failed:
485 dll_name_ret[0] = '\0';
486 return 0;
487}
488
450005e7
CF
489/* Encapsulate the information required in a call to
490 symbol_file_add_args */
8a892701
CF
491struct safe_symbol_file_add_args
492{
493 char *name;
494 int from_tty;
495 struct section_addr_info *addrs;
496 int mainline;
497 int flags;
7c5c87c0 498 struct ui_file *err, *out;
8a892701
CF
499 struct objfile *ret;
500};
501
02e423b9
CF
502/* Maintain a linked list of "so" information. */
503struct so_stuff
504{
d3ff4a77 505 struct so_stuff *next;
02e423b9 506 DWORD load_addr;
7470a420 507 int loaded;
d3ff4a77 508 struct objfile *objfile;
7470a420
CF
509 char name[1];
510} solib_start, *solib_end;
02e423b9 511
450005e7
CF
512/* Call symbol_file_add with stderr redirected. We don't care if there
513 are errors. */
8a892701
CF
514static int
515safe_symbol_file_add_stub (void *argv)
516{
517#define p ((struct safe_symbol_file_add_args *)argv)
fefd0a37 518 struct so_stuff *so = &solib_start;
02e423b9
CF
519
520 while ((so = so->next))
7470a420 521 if (so->loaded && strcasecmp (so->name, p->name) == 0)
02e423b9 522 return 0;
8a892701
CF
523 p->ret = symbol_file_add (p->name, p->from_tty, p->addrs, p->mainline, p->flags);
524 return !!p->ret;
525#undef p
526}
527
450005e7 528/* Restore gdb's stderr after calling symbol_file_add */
8a892701 529static void
7c5c87c0 530safe_symbol_file_add_cleanup (void *p)
8a892701 531{
8e860359 532#define sp ((struct safe_symbol_file_add_args *)p)
450005e7 533 gdb_flush (gdb_stderr);
7c5c87c0 534 gdb_flush (gdb_stdout);
d3ff4a77 535 ui_file_delete (gdb_stderr);
7c5c87c0 536 ui_file_delete (gdb_stdout);
d3ff4a77 537 gdb_stderr = sp->err;
9d3789f7 538 gdb_stdout = sp->out;
8e860359 539#undef sp
8a892701
CF
540}
541
450005e7 542/* symbol_file_add wrapper that prevents errors from being displayed. */
8a892701
CF
543static struct objfile *
544safe_symbol_file_add (char *name, int from_tty,
545 struct section_addr_info *addrs,
546 int mainline, int flags)
8a892701
CF
547{
548 struct safe_symbol_file_add_args p;
549 struct cleanup *cleanup;
550
7c5c87c0 551 cleanup = make_cleanup (safe_symbol_file_add_cleanup, &p);
8a892701 552
7c5c87c0
CF
553 p.err = gdb_stderr;
554 p.out = gdb_stdout;
450005e7 555 gdb_flush (gdb_stderr);
7c5c87c0 556 gdb_flush (gdb_stdout);
d3ff4a77 557 gdb_stderr = ui_file_new ();
7c5c87c0 558 gdb_stdout = ui_file_new ();
8a892701
CF
559 p.name = name;
560 p.from_tty = from_tty;
561 p.addrs = addrs;
562 p.mainline = mainline;
563 p.flags = flags;
564 catch_errors (safe_symbol_file_add_stub, &p, "", RETURN_MASK_ERROR);
565
566 do_cleanups (cleanup);
567 return p.ret;
568}
569
450005e7
CF
570/* Remember the maximum DLL length for printing in info dll command. */
571int max_dll_name_len;
572
8e860359
CF
573static void
574register_loaded_dll (const char *name, DWORD load_addr)
575{
576 struct so_stuff *so;
7470a420 577 char ppath[MAX_PATH + 1];
3f8ad85b
CF
578 char buf[MAX_PATH + 1];
579 char cwd[MAX_PATH + 1];
580 char *p;
581 WIN32_FIND_DATA w32_fd;
582 HANDLE h = FindFirstFile(name, &w32_fd);
583 size_t len;
584
6badb179
CF
585 if (h == INVALID_HANDLE_VALUE)
586 strcpy (buf, name);
587 else
3f8ad85b 588 {
c914e0cc
CF
589 FindClose (h);
590 strcpy (buf, name);
591 if (GetCurrentDirectory (MAX_PATH + 1, cwd))
592 {
593 p = strrchr (buf, '\\');
594 if (p)
595 p[1] = '\0';
596 SetCurrentDirectory (buf);
597 GetFullPathName (w32_fd.cFileName, MAX_PATH, buf, &p);
598 SetCurrentDirectory (cwd);
599 }
3f8ad85b
CF
600 }
601
602 cygwin_conv_to_posix_path (buf, ppath);
7470a420
CF
603 so = (struct so_stuff *) xmalloc (sizeof (struct so_stuff) + strlen (ppath) + 8 + 1);
604 so->loaded = 0;
8e860359 605 so->load_addr = load_addr;
d3ff4a77
CF
606 so->next = NULL;
607 so->objfile = NULL;
7470a420 608 strcpy (so->name, ppath);
8e860359
CF
609
610 solib_end->next = so;
611 solib_end = so;
3f8ad85b
CF
612 len = strlen (ppath);
613 if (len > max_dll_name_len)
614 max_dll_name_len = len;
8e860359
CF
615}
616
dfe7f3ac
CF
617char *
618get_image_name (HANDLE h, void *address, int unicode)
619{
620 static char buf[(2 * MAX_PATH) + 1];
621 DWORD size = unicode ? sizeof (WCHAR) : sizeof (char);
622 char *address_ptr;
623 int len = 0;
624 char b[2];
625 DWORD done;
626
627 /* Attempt to read the name of the dll that was detected.
628 This is documented to work only when actively debugging
629 a program. It will not work for attached processes. */
630 if (address == NULL)
631 return NULL;
632
633 ReadProcessMemory (h, address, &address_ptr, sizeof (address_ptr), &done);
634
635 /* See if we could read the address of a string, and that the
636 address isn't null. */
637
638 if (done != sizeof (address_ptr) || !address_ptr)
639 return NULL;
640
641 /* Find the length of the string */
642 do
643 {
644 ReadProcessMemory (h, address_ptr + len * size, &b, size, &done);
645 len++;
646 }
647 while ((b[0] != 0 || b[size - 1] != 0) && done == size);
648
649 if (!unicode)
650 ReadProcessMemory (h, address_ptr, buf, len, &done);
651 else
652 {
653 WCHAR *unicode_address = (WCHAR *) alloca (len * sizeof (WCHAR));
654 ReadProcessMemory (h, address_ptr, unicode_address, len * sizeof (WCHAR),
655 &done);
656
657 WideCharToMultiByte (CP_ACP, 0, unicode_address, len, buf, len, 0, 0);
658 }
659
660 return buf;
661}
662
24e60978
SC
663/* Wait for child to do something. Return pid of child, or -1 in case
664 of error; store status through argument pointer OURSTATUS. */
1750a5ef 665static int
0a65a603 666handle_load_dll (void *dummy)
24e60978 667{
3a4b77d8 668 LOAD_DLL_DEBUG_INFO *event = &current_event.u.LoadDll;
3cee93ac 669 char dll_buf[MAX_PATH + 1];
450005e7 670 char *dll_name = NULL;
450005e7 671 char *p;
3cee93ac 672
3a4b77d8 673 dll_buf[0] = dll_buf[sizeof (dll_buf) - 1] = '\0';
3cee93ac 674
1e37c281 675 if (!psapi_get_dll_name ((DWORD) (event->lpBaseOfDll), dll_buf))
8e860359 676 dll_buf[0] = dll_buf[sizeof (dll_buf) - 1] = '\0';
3cee93ac 677
1e37c281 678 dll_name = dll_buf;
24e60978 679
dfe7f3ac
CF
680 if (*dll_name == '\0')
681 dll_name = get_image_name (current_process_handle, event->lpImageName, event->fUnicode);
3cee93ac
CF
682 if (!dll_name)
683 return 1;
684
8e860359 685 register_loaded_dll (dll_name, (DWORD) event->lpBaseOfDll + 0x1000);
450005e7
CF
686
687 return 1;
688}
689
d3ff4a77 690static int
0a65a603 691handle_unload_dll (void *dummy)
d3ff4a77
CF
692{
693 DWORD lpBaseOfDll = (DWORD) current_event.u.UnloadDll.lpBaseOfDll + 0x1000;
694 struct so_stuff *so;
695
696 for (so = &solib_start; so->next != NULL; so = so->next)
697 if (so->next->load_addr == lpBaseOfDll)
698 {
699 struct so_stuff *sodel = so->next;
700 so->next = sodel->next;
701 if (!so->next)
702 solib_end = so;
703 if (sodel->objfile)
704 free_objfile (sodel->objfile);
705 xfree(sodel);
706 return 1;
707 }
708 error ("Error: dll starting at 0x%lx not found.\n", (DWORD) lpBaseOfDll);
709
710 return 0;
711}
712
450005e7
CF
713/* Return name of last loaded DLL. */
714char *
0a65a603 715child_solib_loaded_library_pathname (int pid)
450005e7 716{
8e860359 717 return !solib_end || !solib_end->name[0] ? NULL : solib_end->name;
450005e7
CF
718}
719
720/* Clear list of loaded DLLs. */
721void
722child_clear_solibs (void)
723{
724 struct so_stuff *so, *so1 = solib_start.next;
725
726 while ((so = so1) != NULL)
727 {
728 so1 = so->next;
b8c9b27d 729 xfree (so);
450005e7
CF
730 }
731
732 solib_start.next = NULL;
d3ff4a77 733 solib_start.objfile = NULL;
450005e7
CF
734 solib_end = &solib_start;
735 max_dll_name_len = sizeof ("DLL Name") - 1;
736}
737
738/* Add DLL symbol information. */
d3ff4a77 739static struct objfile *
02e423b9 740solib_symbols_add (char *name, int from_tty, CORE_ADDR load_addr)
450005e7
CF
741{
742 struct section_addr_info section_addrs;
743
3cee93ac
CF
744 /* The symbols in a dll are offset by 0x1000, which is the
745 the offset from 0 of the first byte in an image - because
8a892701 746 of the file header and the section alignment. */
3cee93ac 747
8e860359 748 if (!name || !name[0])
d3ff4a77 749 return NULL;
450005e7
CF
750
751 memset (&section_addrs, 0, sizeof (section_addrs));
0aa9cf96 752 section_addrs.other[0].name = ".text";
8e860359 753 section_addrs.other[0].addr = load_addr;
d3ff4a77 754 return safe_symbol_file_add (name, from_tty, NULL, 0, OBJF_SHARED);
450005e7
CF
755}
756
757/* Load DLL symbol info. */
758void
7470a420 759dll_symbol_command (char *args, int from_tty)
450005e7 760{
8e860359 761 int n;
450005e7 762 dont_repeat ();
8e860359 763
450005e7
CF
764 if (args == NULL)
765 error ("dll-symbols requires a file name");
766
8e860359
CF
767 n = strlen (args);
768 if (n > 4 && strcasecmp (args + n - 4, ".dll") != 0)
769 {
770 char *newargs = (char *) alloca (n + 4 + 1);
771 strcpy (newargs, args);
772 strcat (newargs, ".dll");
773 args = newargs;
774 }
775
7470a420 776 safe_symbol_file_add (args, from_tty, NULL, 0, OBJF_SHARED | OBJF_USERLOADED);
8e860359 777}
450005e7
CF
778
779/* List currently loaded DLLs. */
780void
0a65a603 781info_dll_command (char *ignore, int from_tty)
450005e7
CF
782{
783 struct so_stuff *so = &solib_start;
784
785 if (!so->next)
786 return;
787
dfe7f3ac 788 printf_filtered ("%*s Load Address\n", -max_dll_name_len, "DLL Name");
450005e7 789 while ((so = so->next) != NULL)
7c5c87c0 790 printf_filtered ("%*s %08lx\n", -max_dll_name_len, so->name, so->load_addr);
450005e7
CF
791
792 return;
24e60978
SC
793}
794
3cee93ac
CF
795/* Handle DEBUG_STRING output from child process.
796 Cygwin prepends its messages with a "cygwin:". Interpret this as
797 a Cygwin signal. Otherwise just print the string as a warning. */
798static int
799handle_output_debug_string (struct target_waitstatus *ourstatus)
800{
801 char *s;
802 int gotasig = FALSE;
803
804 if (!target_read_string
3a4b77d8 805 ((CORE_ADDR) current_event.u.DebugString.lpDebugStringData, &s, 1024, 0)
3cee93ac
CF
806 || !s || !*s)
807 return gotasig;
808
d3a09475 809 if (strncmp (s, CYGWIN_SIGNAL_STRING, sizeof (CYGWIN_SIGNAL_STRING) - 1) != 0)
3cee93ac 810 {
d3a09475 811 if (strncmp (s, "cYg", 3) != 0)
29fe111d 812 warning ("%s", s);
3cee93ac 813 }
d3a09475 814 else
3cee93ac
CF
815 {
816 char *p;
1e37c281
JM
817 int sig = strtol (s + sizeof (CYGWIN_SIGNAL_STRING) - 1, &p, 0);
818 gotasig = target_signal_from_host (sig);
0714f9bf
SS
819 ourstatus->value.sig = gotasig;
820 if (gotasig)
3cee93ac
CF
821 ourstatus->kind = TARGET_WAITKIND_STOPPED;
822 }
823
b8c9b27d 824 xfree (s);
3cee93ac
CF
825 return gotasig;
826}
24e60978 827
c1748f97
PM
828static int
829display_selector (HANDLE thread, DWORD sel)
830{
831 LDT_ENTRY info;
832 if (GetThreadSelectorEntry (thread, sel, &info))
833 {
834 int base, limit;
835 printf_filtered ("0x%03lx: ", sel);
836 if (!info.HighWord.Bits.Pres)
837 {
838 puts_filtered ("Segment not present\n");
839 return 0;
840 }
841 base = (info.HighWord.Bits.BaseHi << 24) +
842 (info.HighWord.Bits.BaseMid << 16)
843 + info.BaseLow;
844 limit = (info.HighWord.Bits.LimitHi << 16) + info.LimitLow;
845 if (info.HighWord.Bits.Granularity)
846 limit = (limit << 12) | 0xfff;
847 printf_filtered ("base=0x%08x limit=0x%08x", base, limit);
848 if (info.HighWord.Bits.Default_Big)
849 puts_filtered(" 32-bit ");
850 else
851 puts_filtered(" 16-bit ");
852 switch ((info.HighWord.Bits.Type & 0xf) >> 1)
853 {
854 case 0:
855 puts_filtered ("Data (Read-Only, Exp-up");
856 break;
857 case 1:
858 puts_filtered ("Data (Read/Write, Exp-up");
859 break;
860 case 2:
861 puts_filtered ("Unused segment (");
862 break;
863 case 3:
864 puts_filtered ("Data (Read/Write, Exp-down");
865 break;
866 case 4:
867 puts_filtered ("Code (Exec-Only, N.Conf");
868 break;
869 case 5:
870 puts_filtered ("Code (Exec/Read, N.Conf");
871 break;
872 case 6:
873 puts_filtered ("Code (Exec-Only, Conf");
874 break;
875 case 7:
876 puts_filtered ("Code (Exec/Read, Conf");
877 break;
878 default:
879 printf_filtered ("Unknown type 0x%x",info.HighWord.Bits.Type);
880 }
881 if ((info.HighWord.Bits.Type & 0x1) == 0)
882 puts_filtered(", N.Acc");
883 puts_filtered (")\n");
884 if ((info.HighWord.Bits.Type & 0x10) == 0)
885 puts_filtered("System selector ");
886 printf_filtered ("Priviledge level = %d. ", info.HighWord.Bits.Dpl);
887 if (info.HighWord.Bits.Granularity)
888 puts_filtered ("Page granular.\n");
889 else
890 puts_filtered ("Byte granular.\n");
891 return 1;
892 }
893 else
894 {
895 printf_filtered ("Invalid selector 0x%lx.\n",sel);
896 return 0;
897 }
898}
899
900static void
901display_selectors (char * args, int from_tty)
902{
903 if (!current_thread)
904 {
905 puts_filtered ("Impossible to display selectors now.\n");
906 return;
907 }
908 if (!args)
909 {
910
911 puts_filtered ("Selector $cs\n");
912 display_selector (current_thread->h,
913 current_thread->context.SegCs);
914 puts_filtered ("Selector $ds\n");
915 display_selector (current_thread->h,
916 current_thread->context.SegDs);
917 puts_filtered ("Selector $es\n");
918 display_selector (current_thread->h,
919 current_thread->context.SegEs);
920 puts_filtered ("Selector $ss\n");
921 display_selector (current_thread->h,
922 current_thread->context.SegSs);
923 puts_filtered ("Selector $fs\n");
924 display_selector (current_thread->h,
925 current_thread->context.SegFs);
926 puts_filtered ("Selector $gs\n");
927 display_selector (current_thread->h,
928 current_thread->context.SegGs);
929 }
930 else
931 {
932 int sel;
933 sel = parse_and_eval_long (args);
934 printf_filtered ("Selector \"%s\"\n",args);
935 display_selector (current_thread->h, sel);
936 }
937}
938
939static struct cmd_list_element *info_w32_cmdlist = NULL;
940
941static void
942info_w32_command (char *args, int from_tty)
943{
944 help_list (info_w32_cmdlist, "info w32 ", class_info, gdb_stdout);
945}
946
947
7393af7c 948#define DEBUG_EXCEPTION_SIMPLE(x) if (debug_exceptions) \
4e52d31c 949 printf_unfiltered ("gdb: Target exception %s at 0x%08lx\n", x, \
7393af7c
PM
950 (DWORD) current_event.u.Exception.ExceptionRecord.ExceptionAddress)
951
36339ecd 952static int
450005e7 953handle_exception (struct target_waitstatus *ourstatus)
24e60978 954{
3cee93ac 955 thread_info *th;
29fe111d 956 DWORD code = current_event.u.Exception.ExceptionRecord.ExceptionCode;
3cee93ac 957
29fe111d 958 ourstatus->kind = TARGET_WAITKIND_STOPPED;
8a892701 959
3cee93ac
CF
960 /* Record the context of the current thread */
961 th = thread_rec (current_event.dwThreadId, -1);
24e60978 962
29fe111d 963 switch (code)
24e60978 964 {
1ef980b9 965 case EXCEPTION_ACCESS_VIOLATION:
7393af7c
PM
966 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_ACCESS_VIOLATION");
967 ourstatus->value.sig = TARGET_SIGNAL_SEGV;
968 break;
969 case STATUS_STACK_OVERFLOW:
970 DEBUG_EXCEPTION_SIMPLE ("STATUS_STACK_OVERFLOW");
1ef980b9 971 ourstatus->value.sig = TARGET_SIGNAL_SEGV;
7393af7c
PM
972 break;
973 case STATUS_FLOAT_DENORMAL_OPERAND:
974 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_DENORMAL_OPERAND");
975 ourstatus->value.sig = TARGET_SIGNAL_FPE;
976 break;
977 case EXCEPTION_ARRAY_BOUNDS_EXCEEDED:
978 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_ARRAY_BOUNDS_EXCEEDED");
979 ourstatus->value.sig = TARGET_SIGNAL_FPE;
980 break;
981 case STATUS_FLOAT_INEXACT_RESULT:
982 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_INEXACT_RESULT");
983 ourstatus->value.sig = TARGET_SIGNAL_FPE;
984 break;
985 case STATUS_FLOAT_INVALID_OPERATION:
986 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_INVALID_OPERATION");
987 ourstatus->value.sig = TARGET_SIGNAL_FPE;
988 break;
989 case STATUS_FLOAT_OVERFLOW:
990 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_OVERFLOW");
991 ourstatus->value.sig = TARGET_SIGNAL_FPE;
992 break;
993 case STATUS_FLOAT_STACK_CHECK:
994 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_STACK_CHECK");
995 ourstatus->value.sig = TARGET_SIGNAL_FPE;
1ef980b9 996 break;
3b7c8b74 997 case STATUS_FLOAT_UNDERFLOW:
7393af7c
PM
998 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_UNDERFLOW");
999 ourstatus->value.sig = TARGET_SIGNAL_FPE;
1000 break;
3b7c8b74 1001 case STATUS_FLOAT_DIVIDE_BY_ZERO:
7393af7c
PM
1002 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_DIVIDE_BY_ZERO");
1003 ourstatus->value.sig = TARGET_SIGNAL_FPE;
1004 break;
3b7c8b74 1005 case STATUS_INTEGER_DIVIDE_BY_ZERO:
7393af7c 1006 DEBUG_EXCEPTION_SIMPLE ("STATUS_INTEGER_DIVIDE_BY_ZERO");
3b7c8b74 1007 ourstatus->value.sig = TARGET_SIGNAL_FPE;
3b7c8b74 1008 break;
7393af7c
PM
1009 case STATUS_INTEGER_OVERFLOW:
1010 DEBUG_EXCEPTION_SIMPLE ("STATUS_INTEGER_OVERFLOW");
1011 ourstatus->value.sig = TARGET_SIGNAL_FPE;
1ef980b9
SC
1012 break;
1013 case EXCEPTION_BREAKPOINT:
7393af7c 1014 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_BREAKPOINT");
1ef980b9
SC
1015 ourstatus->value.sig = TARGET_SIGNAL_TRAP;
1016 break;
1017 case DBG_CONTROL_C:
7393af7c 1018 DEBUG_EXCEPTION_SIMPLE ("DBG_CONTROL_C");
1ef980b9 1019 ourstatus->value.sig = TARGET_SIGNAL_INT;
5b421780
PM
1020 break;
1021 case DBG_CONTROL_BREAK:
7393af7c 1022 DEBUG_EXCEPTION_SIMPLE ("DBG_CONTROL_BREAK");
5b421780 1023 ourstatus->value.sig = TARGET_SIGNAL_INT;
1ef980b9
SC
1024 break;
1025 case EXCEPTION_SINGLE_STEP:
7393af7c 1026 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_SINGLE_STEP");
1ef980b9
SC
1027 ourstatus->value.sig = TARGET_SIGNAL_TRAP;
1028 break;
8227c82d 1029 case EXCEPTION_ILLEGAL_INSTRUCTION:
7393af7c
PM
1030 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_ILLEGAL_INSTRUCTION");
1031 ourstatus->value.sig = TARGET_SIGNAL_ILL;
1032 break;
1033 case EXCEPTION_PRIV_INSTRUCTION:
1034 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_PRIV_INSTRUCTION");
1035 ourstatus->value.sig = TARGET_SIGNAL_ILL;
1036 break;
1037 case EXCEPTION_NONCONTINUABLE_EXCEPTION:
1038 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_NONCONTINUABLE_EXCEPTION");
8227c82d
CF
1039 ourstatus->value.sig = TARGET_SIGNAL_ILL;
1040 break;
1ef980b9 1041 default:
02e423b9
CF
1042 if (current_event.u.Exception.dwFirstChance)
1043 return 0;
29fe111d 1044 printf_unfiltered ("gdb: unknown target exception 0x%08lx at 0x%08lx\n",
3a4b77d8 1045 current_event.u.Exception.ExceptionRecord.ExceptionCode,
8e860359 1046 (DWORD) current_event.u.Exception.ExceptionRecord.ExceptionAddress);
24e60978 1047 ourstatus->value.sig = TARGET_SIGNAL_UNKNOWN;
1ef980b9 1048 break;
24e60978 1049 }
24e60978 1050 exception_count++;
7393af7c 1051 last_sig = ourstatus->value.sig;
36339ecd 1052 return 1;
24e60978
SC
1053}
1054
3cee93ac
CF
1055/* Resume all artificially suspended threads if we are continuing
1056 execution */
1057static BOOL
8a892701 1058child_continue (DWORD continue_status, int id)
3cee93ac
CF
1059{
1060 int i;
1061 thread_info *th;
1062 BOOL res;
1063
7393af7c
PM
1064 DEBUG_EVENTS (("ContinueDebugEvent (cpid=%ld, ctid=%ld, %s);\n",
1065 current_event.dwProcessId, current_event.dwThreadId,
dfe7f3ac 1066 continue_status == DBG_CONTINUE ?
7393af7c 1067 "DBG_CONTINUE" : "DBG_EXCEPTION_NOT_HANDLED"));
0714f9bf
SS
1068 res = ContinueDebugEvent (current_event.dwProcessId,
1069 current_event.dwThreadId,
1070 continue_status);
1e37c281 1071 continue_status = 0;
0714f9bf 1072 if (res)
3a4b77d8 1073 for (th = &thread_head; (th = th->next) != NULL;)
29fe111d 1074 if (((id == -1) || (id == (int) th->id)) && th->suspend_count)
3cee93ac 1075 {
fa4ba8da 1076
3cee93ac
CF
1077 for (i = 0; i < th->suspend_count; i++)
1078 (void) ResumeThread (th->h);
1079 th->suspend_count = 0;
fa4ba8da
PM
1080 if (debug_registers_changed)
1081 {
1082 /* Only change the value of the debug reisters */
1083 th->context.ContextFlags = CONTEXT_DEBUG_REGISTERS;
1084 th->context.Dr0 = dr[0];
1085 th->context.Dr1 = dr[1];
1086 th->context.Dr2 = dr[2];
1087 th->context.Dr3 = dr[3];
1088 /* th->context.Dr6 = dr[6];
dfe7f3ac 1089 FIXME: should we set dr6 also ?? */
fa4ba8da
PM
1090 th->context.Dr7 = dr[7];
1091 CHECK (SetThreadContext (th->h, &th->context));
1092 th->context.ContextFlags = 0;
1093 }
3cee93ac
CF
1094 }
1095
fa4ba8da 1096 debug_registers_changed = 0;
3cee93ac
CF
1097 return res;
1098}
1099
8a892701
CF
1100/* Get the next event from the child. Return 1 if the event requires
1101 handling by WFI (or whatever).
1102 */
1e37c281 1103static int
0a65a603 1104get_child_debug_event (int pid, struct target_waitstatus *ourstatus)
1e37c281
JM
1105{
1106 BOOL debug_event;
8a892701
CF
1107 DWORD continue_status, event_code;
1108 thread_info *th = NULL;
1109 static thread_info dummy_thread_info;
450005e7 1110 int retval = 0;
1e37c281 1111
7393af7c 1112 last_sig = TARGET_SIGNAL_0;
9d3789f7 1113
8a892701 1114 if (!(debug_event = WaitForDebugEvent (&current_event, 1000)))
29fe111d 1115 goto out;
1e37c281
JM
1116
1117 event_count++;
1118 continue_status = DBG_CONTINUE;
1e37c281 1119
8a892701 1120 event_code = current_event.dwDebugEventCode;
450005e7 1121 ourstatus->kind = TARGET_WAITKIND_SPURIOUS;
8a892701
CF
1122
1123 switch (event_code)
1e37c281
JM
1124 {
1125 case CREATE_THREAD_DEBUG_EVENT:
1126 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%x code=%s)\n",
8a892701
CF
1127 (unsigned) current_event.dwProcessId,
1128 (unsigned) current_event.dwThreadId,
1129 "CREATE_THREAD_DEBUG_EVENT"));
dfe7f3ac
CF
1130 if (saw_create != 1)
1131 break;
1e37c281 1132 /* Record the existence of this thread */
8a892701
CF
1133 th = child_add_thread (current_event.dwThreadId,
1134 current_event.u.CreateThread.hThread);
1e37c281
JM
1135 if (info_verbose)
1136 printf_unfiltered ("[New %s]\n",
39f77062
KB
1137 target_pid_to_str (
1138 pid_to_ptid (current_event.dwThreadId)));
450005e7 1139 retval = current_event.dwThreadId;
1e37c281
JM
1140 break;
1141
1142 case EXIT_THREAD_DEBUG_EVENT:
1143 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
8a892701
CF
1144 (unsigned) current_event.dwProcessId,
1145 (unsigned) current_event.dwThreadId,
1146 "EXIT_THREAD_DEBUG_EVENT"));
dfe7f3ac
CF
1147 if (saw_create != 1)
1148 break;
1e37c281 1149 child_delete_thread (current_event.dwThreadId);
8a892701 1150 th = &dummy_thread_info;
1e37c281
JM
1151 break;
1152
1153 case CREATE_PROCESS_DEBUG_EVENT:
1154 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
8a892701
CF
1155 (unsigned) current_event.dwProcessId,
1156 (unsigned) current_event.dwThreadId,
1157 "CREATE_PROCESS_DEBUG_EVENT"));
700b351b 1158 CloseHandle (current_event.u.CreateProcessInfo.hFile);
dfe7f3ac
CF
1159 if (++saw_create != 1)
1160 {
1161 CloseHandle (current_event.u.CreateProcessInfo.hProcess);
1162 break;
1163 }
1e37c281 1164
dfe7f3ac 1165 current_process_handle = current_event.u.CreateProcessInfo.hProcess;
9d3789f7 1166 main_thread_id = current_event.dwThreadId;
1e37c281 1167 /* Add the main thread */
9d3789f7 1168#if 0
450005e7
CF
1169 th = child_add_thread (current_event.dwProcessId,
1170 current_event.u.CreateProcessInfo.hProcess);
9d3789f7
CF
1171#endif
1172 th = child_add_thread (main_thread_id,
8a892701 1173 current_event.u.CreateProcessInfo.hThread);
9d3789f7 1174 retval = ourstatus->value.related_pid = current_event.dwThreadId;
1e37c281
JM
1175 break;
1176
1177 case EXIT_PROCESS_DEBUG_EVENT:
1178 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
8a892701
CF
1179 (unsigned) current_event.dwProcessId,
1180 (unsigned) current_event.dwThreadId,
1181 "EXIT_PROCESS_DEBUG_EVENT"));
dfe7f3ac
CF
1182 if (saw_create != 1)
1183 break;
1e37c281
JM
1184 ourstatus->kind = TARGET_WAITKIND_EXITED;
1185 ourstatus->value.integer = current_event.u.ExitProcess.dwExitCode;
1186 CloseHandle (current_process_handle);
9d3789f7 1187 retval = main_thread_id;
8a892701 1188 break;
1e37c281
JM
1189
1190 case LOAD_DLL_DEBUG_EVENT:
1191 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
8a892701
CF
1192 (unsigned) current_event.dwProcessId,
1193 (unsigned) current_event.dwThreadId,
1194 "LOAD_DLL_DEBUG_EVENT"));
700b351b 1195 CloseHandle (current_event.u.LoadDll.hFile);
dfe7f3ac
CF
1196 if (saw_create != 1)
1197 break;
8a892701 1198 catch_errors (handle_load_dll, NULL, (char *) "", RETURN_MASK_ALL);
1e37c281 1199 registers_changed (); /* mark all regs invalid */
450005e7
CF
1200 ourstatus->kind = TARGET_WAITKIND_LOADED;
1201 ourstatus->value.integer = 0;
9d3789f7 1202 retval = main_thread_id;
1e37c281
JM
1203 break;
1204
1205 case UNLOAD_DLL_DEBUG_EVENT:
1206 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
8a892701
CF
1207 (unsigned) current_event.dwProcessId,
1208 (unsigned) current_event.dwThreadId,
1209 "UNLOAD_DLL_DEBUG_EVENT"));
dfe7f3ac
CF
1210 if (saw_create != 1)
1211 break;
d3ff4a77
CF
1212 catch_errors (handle_unload_dll, NULL, (char *) "", RETURN_MASK_ALL);
1213 registers_changed (); /* mark all regs invalid */
1214 /* ourstatus->kind = TARGET_WAITKIND_UNLOADED;
3bccec63 1215 does not exist yet. */
d3ff4a77 1216 break;
1e37c281
JM
1217
1218 case EXCEPTION_DEBUG_EVENT:
1219 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
8a892701
CF
1220 (unsigned) current_event.dwProcessId,
1221 (unsigned) current_event.dwThreadId,
1222 "EXCEPTION_DEBUG_EVENT"));
dfe7f3ac
CF
1223 if (saw_create != 1)
1224 break;
02e423b9
CF
1225 if (handle_exception (ourstatus))
1226 retval = current_event.dwThreadId;
1e37c281
JM
1227 break;
1228
8a892701 1229 case OUTPUT_DEBUG_STRING_EVENT: /* message from the kernel */
1e37c281 1230 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
8a892701
CF
1231 (unsigned) current_event.dwProcessId,
1232 (unsigned) current_event.dwThreadId,
1233 "OUTPUT_DEBUG_STRING_EVENT"));
dfe7f3ac
CF
1234 if (saw_create != 1)
1235 break;
8e860359 1236 if (handle_output_debug_string (ourstatus))
9d3789f7 1237 retval = main_thread_id;
1e37c281 1238 break;
9d3789f7 1239
1e37c281 1240 default:
dfe7f3ac
CF
1241 if (saw_create != 1)
1242 break;
29fe111d
CF
1243 printf_unfiltered ("gdb: kernel event for pid=%ld tid=%ld\n",
1244 (DWORD) current_event.dwProcessId,
1245 (DWORD) current_event.dwThreadId);
1246 printf_unfiltered (" unknown event code %ld\n",
1e37c281
JM
1247 current_event.dwDebugEventCode);
1248 break;
1249 }
1250
dfe7f3ac 1251 if (!retval || saw_create != 1)
8a892701 1252 CHECK (child_continue (continue_status, -1));
450005e7 1253 else
9d3789f7 1254 {
8e860359 1255 current_thread = th ? : thread_rec (current_event.dwThreadId, TRUE);
39f77062 1256 inferior_ptid = pid_to_ptid (retval);
9d3789f7 1257 }
1e37c281
JM
1258
1259out:
450005e7 1260 return retval;
1e37c281
JM
1261}
1262
1e37c281 1263/* Wait for interesting events to occur in the target process. */
39f77062
KB
1264static ptid_t
1265child_wait (ptid_t ptid, struct target_waitstatus *ourstatus)
24e60978 1266{
39f77062
KB
1267 int pid = PIDGET (ptid);
1268
24e60978
SC
1269 /* We loop when we get a non-standard exception rather than return
1270 with a SPURIOUS because resume can try and step or modify things,
3cee93ac 1271 which needs a current_thread->h. But some of these exceptions mark
24e60978
SC
1272 the birth or death of threads, which mean that the current thread
1273 isn't necessarily what you think it is. */
1274
1275 while (1)
450005e7
CF
1276 {
1277 int retval = get_child_debug_event (pid, ourstatus);
1278 if (retval)
39f77062 1279 return pid_to_ptid (retval);
450005e7
CF
1280 else
1281 {
1282 int detach = 0;
3cee93ac 1283
450005e7
CF
1284 if (ui_loop_hook != NULL)
1285 detach = ui_loop_hook (0);
0714f9bf 1286
450005e7
CF
1287 if (detach)
1288 child_kill_inferior ();
1289 }
1290 }
24e60978
SC
1291}
1292
9d3789f7
CF
1293static void
1294do_initial_child_stuff (DWORD pid)
1295{
1296 extern int stop_after_trap;
fa4ba8da 1297 int i;
9d3789f7 1298
7393af7c 1299 last_sig = TARGET_SIGNAL_0;
9d3789f7
CF
1300 event_count = 0;
1301 exception_count = 0;
fa4ba8da 1302 debug_registers_changed = 0;
dfe7f3ac 1303 debug_registers_used = 0;
fa4ba8da
PM
1304 for (i = 0; i < sizeof (dr) / sizeof (dr[0]); i++)
1305 dr[i] = 0;
9d3789f7
CF
1306 current_event.dwProcessId = pid;
1307 memset (&current_event, 0, sizeof (current_event));
1308 push_target (&child_ops);
1309 child_init_thread_list ();
1310 child_clear_solibs ();
1311 clear_proceed_status ();
1312 init_wait_for_inferior ();
1313
1314 target_terminal_init ();
1315 target_terminal_inferior ();
1316
1317 while (1)
1318 {
1319 stop_after_trap = 1;
1320 wait_for_inferior ();
1321 if (stop_signal != TARGET_SIGNAL_TRAP)
1322 resume (0, stop_signal);
1323 else
1324 break;
1325 }
1326 stop_after_trap = 0;
1327 return;
1328}
1329
02cc9f49
CV
1330/* Since Windows XP, detaching from a process is supported by Windows.
1331 The following code tries loading the appropriate functions dynamically.
1332 If loading these functions succeeds use them to actually detach from
1333 the inferior process, otherwise behave as usual, pretending that
1334 detach has worked. */
1335static BOOL WINAPI (*DebugSetProcessKillOnExit)(BOOL);
1336static BOOL WINAPI (*DebugActiveProcessStop)(DWORD);
1337
1338static int
1339has_detach_ability ()
1340{
1341 static HMODULE kernel32 = NULL;
1342
1343 if (!kernel32)
1344 kernel32 = LoadLibrary ("kernel32.dll");
1345 if (kernel32)
1346 {
1347 if (!DebugSetProcessKillOnExit)
1348 DebugSetProcessKillOnExit = GetProcAddress (kernel32,
1349 "DebugSetProcessKillOnExit");
1350 if (!DebugActiveProcessStop)
1351 DebugActiveProcessStop = GetProcAddress (kernel32,
1352 "DebugActiveProcessStop");
1353 if (DebugSetProcessKillOnExit && DebugActiveProcessStop)
1354 return 1;
1355 }
1356 return 0;
1357}
24e60978 1358
02cc9f49 1359/* Attach to process PID, then initialize for debugging it. */
24e60978 1360static void
fba45db2 1361child_attach (char *args, int from_tty)
24e60978
SC
1362{
1363 BOOL ok;
559e75c0 1364 DWORD pid;
24e60978
SC
1365
1366 if (!args)
1367 error_no_arg ("process-id to attach");
1368
559e75c0 1369 pid = strtoul (args, 0, 0);
9d3789f7 1370 ok = DebugActiveProcess (pid);
24e60978
SC
1371
1372 if (!ok)
1373 error ("Can't attach to process.");
1374
02cc9f49
CV
1375 if (has_detach_ability ())
1376 {
1377 attach_flag = 1;
1378 DebugSetProcessKillOnExit (FALSE);
1379 }
1380
24e60978
SC
1381 if (from_tty)
1382 {
1383 char *exec_file = (char *) get_exec_file (0);
1384
1385 if (exec_file)
1386 printf_unfiltered ("Attaching to program `%s', %s\n", exec_file,
39f77062 1387 target_pid_to_str (pid_to_ptid (pid)));
24e60978
SC
1388 else
1389 printf_unfiltered ("Attaching to %s\n",
39f77062 1390 target_pid_to_str (pid_to_ptid (pid)));
24e60978
SC
1391
1392 gdb_flush (gdb_stdout);
1393 }
1394
9d3789f7
CF
1395 do_initial_child_stuff (pid);
1396 target_terminal_ours ();
24e60978
SC
1397}
1398
24e60978 1399static void
0a65a603 1400child_detach (char *args, int from_tty)
24e60978 1401{
02cc9f49
CV
1402 int detached = 1;
1403
1404 if (has_detach_ability ())
1405 {
1406 delete_command (NULL, 0);
1407 child_continue (DBG_CONTINUE, -1);
1408 if (!DebugActiveProcessStop (current_event.dwProcessId))
3bccec63 1409 {
02cc9f49
CV
1410 error ("Can't detach process %lu (error %lu)",
1411 current_event.dwProcessId, GetLastError ());
1412 detached = 0;
3bccec63 1413 }
02cc9f49
CV
1414 DebugSetProcessKillOnExit (FALSE);
1415 }
1416 if (detached && from_tty)
24e60978
SC
1417 {
1418 char *exec_file = get_exec_file (0);
1419 if (exec_file == 0)
1420 exec_file = "";
02cc9f49
CV
1421 printf_unfiltered ("Detaching from program: %s, Pid %lu\n", exec_file,
1422 current_event.dwProcessId);
24e60978
SC
1423 gdb_flush (gdb_stdout);
1424 }
39f77062 1425 inferior_ptid = null_ptid;
24e60978
SC
1426 unpush_target (&child_ops);
1427}
1428
24e60978
SC
1429/* Print status information about what we're accessing. */
1430
1431static void
0a65a603 1432child_files_info (struct target_ops *ignore)
24e60978
SC
1433{
1434 printf_unfiltered ("\tUsing the running image of %s %s.\n",
39f77062 1435 attach_flag ? "attached" : "child", target_pid_to_str (inferior_ptid));
24e60978
SC
1436}
1437
1438/* ARGSUSED */
1439static void
0a65a603 1440child_open (char *arg, int from_tty)
24e60978
SC
1441{
1442 error ("Use the \"run\" command to start a Unix child process.");
1443}
1444
39f77062 1445/* Start an inferior win32 child process and sets inferior_ptid to its pid.
24e60978
SC
1446 EXEC_FILE is the file to run.
1447 ALLARGS is a string containing the arguments to the program.
1448 ENV is the environment vector to pass. Errors reported with error(). */
1449
24e60978 1450static void
fba45db2 1451child_create_inferior (char *exec_file, char *allargs, char **env)
24e60978 1452{
1750a5ef
SC
1453 char *winenv;
1454 char *temp;
3a4b77d8 1455 int envlen;
1750a5ef 1456 int i;
24e60978
SC
1457 STARTUPINFO si;
1458 PROCESS_INFORMATION pi;
24e60978
SC
1459 BOOL ret;
1460 DWORD flags;
eb708f2e 1461 char *args;
dfe7f3ac
CF
1462 char real_path[MAXPATHLEN];
1463 char *toexec;
24e60978
SC
1464
1465 if (!exec_file)
450005e7 1466 error ("No executable specified, use `target exec'.\n");
24e60978
SC
1467
1468 memset (&si, 0, sizeof (si));
1469 si.cb = sizeof (si);
1470
dfe7f3ac
CF
1471 if (!useshell || !shell[0])
1472 {
1473 flags = DEBUG_ONLY_THIS_PROCESS;
1474 cygwin_conv_to_win32_path (exec_file, real_path);
1475 toexec = real_path;
1476 }
1477 else
1478 {
eeb25b8a
PM
1479 char *newallargs = alloca (sizeof (" -c 'exec '") + strlen (exec_file)
1480 + strlen (allargs) + 2);
dfe7f3ac
CF
1481 sprintf (newallargs, " -c 'exec %s %s'", exec_file, allargs);
1482 allargs = newallargs;
1483 toexec = shell;
1484 flags = DEBUG_PROCESS;
1485 }
eb708f2e 1486
eeb25b8a
PM
1487 if (new_group)
1488 flags |= CREATE_NEW_PROCESS_GROUP;
1489
1490 if (new_console)
1491 flags |= CREATE_NEW_CONSOLE;
1492
dfe7f3ac
CF
1493 args = alloca (strlen (toexec) + strlen (allargs) + 2);
1494 strcpy (args, toexec);
eb708f2e
SC
1495 strcat (args, " ");
1496 strcat (args, allargs);
1497
e88c49c3
DE
1498 /* Prepare the environment vars for CreateProcess. */
1499 {
1500 /* This code use to assume all env vars were file names and would
1501 translate them all to win32 style. That obviously doesn't work in the
2dcfc9c7
DE
1502 general case. The current rule is that we only translate PATH.
1503 We need to handle PATH because we're about to call CreateProcess and
1504 it uses PATH to find DLL's. Fortunately PATH has a well-defined value
1505 in both posix and win32 environments. cygwin.dll will change it back
1506 to posix style if necessary. */
e88c49c3
DE
1507
1508 static const char *conv_path_names[] =
3a4b77d8
JM
1509 {
1510 "PATH=",
1511 0
1512 };
e88c49c3
DE
1513
1514 /* CreateProcess takes the environment list as a null terminated set of
1515 strings (i.e. two nulls terminate the list). */
1516
1517 /* Get total size for env strings. */
1518 for (envlen = 0, i = 0; env[i] && *env[i]; i++)
1519 {
2dcfc9c7 1520 int j, len;
e88c49c3 1521
2dcfc9c7
DE
1522 for (j = 0; conv_path_names[j]; j++)
1523 {
1524 len = strlen (conv_path_names[j]);
1525 if (strncmp (conv_path_names[j], env[i], len) == 0)
e88c49c3 1526 {
29fe111d 1527 if (cygwin_posix_path_list_p (env[i] + len))
2dcfc9c7 1528 envlen += len
29fe111d 1529 + cygwin_posix_to_win32_path_list_buf_size (env[i] + len);
2dcfc9c7
DE
1530 else
1531 envlen += strlen (env[i]) + 1;
1532 break;
e88c49c3 1533 }
e88c49c3 1534 }
2dcfc9c7 1535 if (conv_path_names[j] == NULL)
e88c49c3
DE
1536 envlen += strlen (env[i]) + 1;
1537 }
1538
1539 winenv = alloca (envlen + 1);
1540
1541 /* Copy env strings into new buffer. */
3cee93ac 1542 for (temp = winenv, i = 0; env[i] && *env[i]; i++)
e88c49c3 1543 {
2dcfc9c7 1544 int j, len;
e88c49c3 1545
2dcfc9c7
DE
1546 for (j = 0; conv_path_names[j]; j++)
1547 {
1548 len = strlen (conv_path_names[j]);
1549 if (strncmp (conv_path_names[j], env[i], len) == 0)
e88c49c3 1550 {
29fe111d 1551 if (cygwin_posix_path_list_p (env[i] + len))
e88c49c3
DE
1552 {
1553 memcpy (temp, env[i], len);
29fe111d 1554 cygwin_posix_to_win32_path_list (env[i] + len, temp + len);
e88c49c3 1555 }
2dcfc9c7
DE
1556 else
1557 strcpy (temp, env[i]);
1558 break;
e88c49c3 1559 }
e88c49c3 1560 }
2dcfc9c7 1561 if (conv_path_names[j] == NULL)
e88c49c3 1562 strcpy (temp, env[i]);
2dcfc9c7 1563
e88c49c3
DE
1564 temp += strlen (temp) + 1;
1565 }
1566
1567 /* Final nil string to terminate new env. */
1568 *temp = 0;
1569 }
1750a5ef 1570
1750a5ef 1571 ret = CreateProcess (0,
3a4b77d8 1572 args, /* command line */
24e60978
SC
1573 NULL, /* Security */
1574 NULL, /* thread */
1575 TRUE, /* inherit handles */
1576 flags, /* start flags */
1750a5ef 1577 winenv,
24e60978
SC
1578 NULL, /* current directory */
1579 &si,
1580 &pi);
1581 if (!ret)
3a4b77d8 1582 error ("Error creating process %s, (error %d)\n", exec_file, GetLastError ());
24e60978 1583
700b351b
CF
1584 CloseHandle (pi.hThread);
1585 CloseHandle (pi.hProcess);
dfe7f3ac
CF
1586
1587 if (useshell && shell[0] != '\0')
1588 saw_create = -1;
1589 else
1590 saw_create = 0;
1591
9d3789f7 1592 do_initial_child_stuff (pi.dwProcessId);
d3a09475 1593
8e860359 1594 /* child_continue (DBG_CONTINUE, -1); */
1e37c281 1595 proceed ((CORE_ADDR) - 1, TARGET_SIGNAL_0, 0);
24e60978
SC
1596}
1597
1598static void
fba45db2 1599child_mourn_inferior (void)
24e60978 1600{
8a892701 1601 (void) child_continue (DBG_CONTINUE, -1);
fa4ba8da 1602 i386_cleanup_dregs();
24e60978
SC
1603 unpush_target (&child_ops);
1604 generic_mourn_inferior ();
1605}
1606
24e60978
SC
1607/* Send a SIGINT to the process group. This acts just like the user typed a
1608 ^C on the controlling terminal. */
1609
b607efe7 1610static void
fba45db2 1611child_stop (void)
24e60978 1612{
1ef980b9 1613 DEBUG_EVENTS (("gdb: GenerateConsoleCtrlEvent (CTRLC_EVENT, 0)\n"));
1e37c281 1614 CHECK (GenerateConsoleCtrlEvent (CTRL_C_EVENT, current_event.dwProcessId));
3a4b77d8 1615 registers_changed (); /* refresh register state */
24e60978
SC
1616}
1617
1618int
eb708f2e 1619child_xfer_memory (CORE_ADDR memaddr, char *our, int len,
0a65a603
AC
1620 int write, struct mem_attrib *mem,
1621 struct target_ops *target)
24e60978
SC
1622{
1623 DWORD done;
1624 if (write)
1625 {
29fe111d
CF
1626 DEBUG_MEM (("gdb: write target memory, %d bytes at 0x%08lx\n",
1627 len, (DWORD) memaddr));
3cee93ac
CF
1628 WriteProcessMemory (current_process_handle, (LPVOID) memaddr, our,
1629 len, &done);
1630 FlushInstructionCache (current_process_handle, (LPCVOID) memaddr, len);
24e60978
SC
1631 }
1632 else
1633 {
29fe111d
CF
1634 DEBUG_MEM (("gdb: read target memory, %d bytes at 0x%08lx\n",
1635 len, (DWORD) memaddr));
3cee93ac
CF
1636 ReadProcessMemory (current_process_handle, (LPCVOID) memaddr, our, len,
1637 &done);
24e60978
SC
1638 }
1639 return done;
1640}
1641
1642void
1643child_kill_inferior (void)
1644{
3cee93ac
CF
1645 CHECK (TerminateProcess (current_process_handle, 0));
1646
b5edcb45
ILT
1647 for (;;)
1648 {
8a892701 1649 if (!child_continue (DBG_CONTINUE, -1))
b5edcb45 1650 break;
3cee93ac 1651 if (!WaitForDebugEvent (&current_event, INFINITE))
b5edcb45 1652 break;
3cee93ac 1653 if (current_event.dwDebugEventCode == EXIT_PROCESS_DEBUG_EVENT)
b5edcb45
ILT
1654 break;
1655 }
1656
3cee93ac
CF
1657 CHECK (CloseHandle (current_process_handle));
1658
1659 /* this may fail in an attached process so don't check. */
1660 (void) CloseHandle (current_thread->h);
3a4b77d8 1661 target_mourn_inferior (); /* or just child_mourn_inferior? */
24e60978
SC
1662}
1663
1664void
39f77062 1665child_resume (ptid_t ptid, int step, enum target_signal sig)
24e60978 1666{
3cee93ac 1667 thread_info *th;
7393af7c
PM
1668 DWORD continue_status = DBG_CONTINUE;
1669
39f77062 1670 int pid = PIDGET (ptid);
8a892701 1671
7393af7c
PM
1672 if (sig != TARGET_SIGNAL_0)
1673 {
1674 if (current_event.dwDebugEventCode != EXCEPTION_DEBUG_EVENT)
1675 {
1676 DEBUG_EXCEPT(("Cannot continue with signal %d here.\n",sig));
1677 }
1678 else if (sig == last_sig)
1679 continue_status = DBG_EXCEPTION_NOT_HANDLED;
1680 else
1681#if 0
1682/* This code does not seem to work, because
1683 the kernel does probably not consider changes in the ExceptionRecord
dfe7f3ac 1684 structure when passing the exception to the inferior.
7393af7c
PM
1685 Note that this seems possible in the exception handler itself. */
1686 {
1687 int i;
1688 for (i = 0; xlate[i].them != -1; i++)
1689 if (xlate[i].us == sig)
1690 {
1691 current_event.u.Exception.ExceptionRecord.ExceptionCode =
1692 xlate[i].them;
1693 continue_status = DBG_EXCEPTION_NOT_HANDLED;
1694 break;
1695 }
1696 if (continue_status == DBG_CONTINUE)
1697 {
1698 DEBUG_EXCEPT(("Cannot continue with signal %d.\n",sig));
1699 }
1700 }
1701#endif
dfe7f3ac 1702 DEBUG_EXCEPT(("Can only continue with recieved signal %d.\n",
7393af7c
PM
1703 last_sig));
1704 }
1705
1706 last_sig = TARGET_SIGNAL_0;
24e60978 1707
3cee93ac
CF
1708 DEBUG_EXEC (("gdb: child_resume (pid=%d, step=%d, sig=%d);\n",
1709 pid, step, sig));
1710
1711 /* Get context for currently selected thread */
1712 th = thread_rec (current_event.dwThreadId, FALSE);
450005e7 1713 if (th)
24e60978 1714 {
450005e7
CF
1715 if (step)
1716 {
1717 /* Single step by setting t bit */
1718 child_fetch_inferior_registers (PS_REGNUM);
1719 th->context.EFlags |= FLAG_TRACE_BIT;
1720 }
24e60978 1721
450005e7
CF
1722 if (th->context.ContextFlags)
1723 {
fa4ba8da
PM
1724 if (debug_registers_changed)
1725 {
dfe7f3ac
CF
1726 th->context.Dr0 = dr[0];
1727 th->context.Dr1 = dr[1];
1728 th->context.Dr2 = dr[2];
1729 th->context.Dr3 = dr[3];
1730 /* th->context.Dr6 = dr[6];
1731 FIXME: should we set dr6 also ?? */
1732 th->context.Dr7 = dr[7];
fa4ba8da 1733 }
450005e7
CF
1734 CHECK (SetThreadContext (th->h, &th->context));
1735 th->context.ContextFlags = 0;
1736 }
24e60978
SC
1737 }
1738
3cee93ac
CF
1739 /* Allow continuing with the same signal that interrupted us.
1740 Otherwise complain. */
24e60978 1741
8a892701 1742 child_continue (continue_status, pid);
24e60978
SC
1743}
1744
1745static void
fba45db2 1746child_prepare_to_store (void)
24e60978
SC
1747{
1748 /* Do nothing, since we can store individual regs */
1749}
1750
1751static int
fba45db2 1752child_can_run (void)
24e60978
SC
1753{
1754 return 1;
1755}
1756
1757static void
0a65a603 1758child_close (int x)
24e60978 1759{
39f77062 1760 DEBUG_EVENTS (("gdb: child_close, inferior_ptid=%d\n",
3bccec63 1761 PIDGET (inferior_ptid)));
24e60978 1762}
1ef980b9 1763
3a4b77d8 1764struct target_ops child_ops;
c719b714 1765
3a4b77d8
JM
1766static void
1767init_child_ops (void)
24e60978 1768{
3a4b77d8
JM
1769 child_ops.to_shortname = "child";
1770 child_ops.to_longname = "Win32 child process";
1771 child_ops.to_doc = "Win32 child process (started by the \"run\" command).";
1772 child_ops.to_open = child_open;
1773 child_ops.to_close = child_close;
1774 child_ops.to_attach = child_attach;
1775 child_ops.to_detach = child_detach;
1776 child_ops.to_resume = child_resume;
1777 child_ops.to_wait = child_wait;
1778 child_ops.to_fetch_registers = child_fetch_inferior_registers;
1779 child_ops.to_store_registers = child_store_inferior_registers;
1780 child_ops.to_prepare_to_store = child_prepare_to_store;
1781 child_ops.to_xfer_memory = child_xfer_memory;
1782 child_ops.to_files_info = child_files_info;
1783 child_ops.to_insert_breakpoint = memory_insert_breakpoint;
1784 child_ops.to_remove_breakpoint = memory_remove_breakpoint;
1785 child_ops.to_terminal_init = terminal_init_inferior;
1786 child_ops.to_terminal_inferior = terminal_inferior;
1787 child_ops.to_terminal_ours_for_output = terminal_ours_for_output;
1788 child_ops.to_terminal_ours = terminal_ours;
1789 child_ops.to_terminal_info = child_terminal_info;
1790 child_ops.to_kill = child_kill_inferior;
1791 child_ops.to_load = 0;
1792 child_ops.to_lookup_symbol = 0;
1793 child_ops.to_create_inferior = child_create_inferior;
1794 child_ops.to_mourn_inferior = child_mourn_inferior;
1795 child_ops.to_can_run = child_can_run;
1796 child_ops.to_notice_signals = 0;
1797 child_ops.to_thread_alive = win32_child_thread_alive;
d3a09475 1798 child_ops.to_pid_to_str = cygwin_pid_to_str;
3a4b77d8
JM
1799 child_ops.to_stop = child_stop;
1800 child_ops.to_stratum = process_stratum;
1801 child_ops.DONT_USE = 0;
1802 child_ops.to_has_all_memory = 1;
1803 child_ops.to_has_memory = 1;
1804 child_ops.to_has_stack = 1;
1805 child_ops.to_has_registers = 1;
1806 child_ops.to_has_execution = 1;
1807 child_ops.to_sections = 0;
1808 child_ops.to_sections_end = 0;
1809 child_ops.to_magic = OPS_MAGIC;
c719b714 1810}
24e60978
SC
1811
1812void
fba45db2 1813_initialize_inftarg (void)
24e60978 1814{
fa58ee11 1815 struct cmd_list_element *c;
dfe7f3ac 1816 const char *sh;
fa58ee11 1817
3a4b77d8 1818 init_child_ops ();
1ef980b9 1819
fa58ee11
EZ
1820 c = add_com ("dll-symbols", class_files, dll_symbol_command,
1821 "Load dll library symbols from FILE.");
1822 c->completer = filename_completer;
450005e7 1823
dfe7f3ac
CF
1824 sh = getenv ("SHELL");
1825 if (!sh)
1826 sh = "/bin/sh";
1827 if (access (sh, X_OK) != 0)
1828 {
1829 shell[0] = '\0';
1830 useshell = 0;
1831 }
1832 else
1833 {
1834 cygwin_conv_to_win32_path (sh, shell);
1835 useshell = 1;
1836 }
1837
450005e7
CF
1838 add_com_alias ("sharedlibrary", "dll-symbols", class_alias, 1);
1839
dfe7f3ac
CF
1840 add_show_from_set (add_set_cmd ("shell", class_support, var_boolean,
1841 (char *) &useshell,
1842 "Set use of shell to start subprocess.",
1843 &setlist),
1844 &showlist);
1845
450005e7 1846 add_show_from_set (add_set_cmd ("new-console", class_support, var_boolean,
8e860359
CF
1847 (char *) &new_console,
1848 "Set creation of new console when creating child process.",
1849 &setlist),
1850 &showlist);
24e60978 1851
450005e7 1852 add_show_from_set (add_set_cmd ("new-group", class_support, var_boolean,
8e860359
CF
1853 (char *) &new_group,
1854 "Set creation of new group when creating child process.",
1855 &setlist),
1856 &showlist);
24e60978 1857
450005e7 1858 add_show_from_set (add_set_cmd ("debugexec", class_support, var_boolean,
8e860359
CF
1859 (char *) &debug_exec,
1860 "Set whether to display execution in child process.",
1861 &setlist),
1862 &showlist);
1ef980b9 1863
450005e7 1864 add_show_from_set (add_set_cmd ("debugevents", class_support, var_boolean,
8e860359
CF
1865 (char *) &debug_events,
1866 "Set whether to display kernel events in child process.",
1867 &setlist),
1868 &showlist);
1ef980b9 1869
450005e7 1870 add_show_from_set (add_set_cmd ("debugmemory", class_support, var_boolean,
8e860359
CF
1871 (char *) &debug_memory,
1872 "Set whether to display memory accesses in child process.",
1873 &setlist),
1874 &showlist);
1ef980b9 1875
450005e7 1876 add_show_from_set (add_set_cmd ("debugexceptions", class_support, var_boolean,
8e860359
CF
1877 (char *) &debug_exceptions,
1878 "Set whether to display kernel exceptions in child process.",
1879 &setlist),
1880 &showlist);
1ef980b9 1881
450005e7
CF
1882 add_info ("dll", info_dll_command, "Status of loaded DLLs.");
1883 add_info_alias ("sharedlibrary", "dll", 1);
1884
c1748f97
PM
1885 add_prefix_cmd ("w32", class_info, info_w32_command,
1886 "Print information specific to Win32 debugging.",
1887 &info_w32_cmdlist, "info w32 ", 0, &infolist);
1888
1889 add_cmd ("selector", class_info, display_selectors,
1890 "Display selectors infos.",
1891 &info_w32_cmdlist);
1892
24e60978
SC
1893 add_target (&child_ops);
1894}
3cee93ac 1895
fa4ba8da
PM
1896/* Hardware watchpoint support, adapted from go32-nat.c code. */
1897
1898/* Pass the address ADDR to the inferior in the I'th debug register.
1899 Here we just store the address in dr array, the registers will be
1900 actually set up when child_continue is called. */
1901void
1902cygwin_set_dr (int i, CORE_ADDR addr)
1903{
1904 if (i < 0 || i > 3)
1905 internal_error (__FILE__, __LINE__,
1906 "Invalid register %d in cygwin_set_dr.\n", i);
1907 dr[i] = (unsigned) addr;
1908 debug_registers_changed = 1;
1909 debug_registers_used = 1;
1910}
1911
1912/* Pass the value VAL to the inferior in the DR7 debug control
1913 register. Here we just store the address in D_REGS, the watchpoint
1914 will be actually set up in child_wait. */
1915void
1916cygwin_set_dr7 (unsigned val)
1917{
1918 dr[7] = val;
1919 debug_registers_changed = 1;
1920 debug_registers_used = 1;
1921}
1922
1923/* Get the value of the DR6 debug status register from the inferior.
1924 Here we just return the value stored in dr[6]
1925 by the last call to thread_rec for current_event.dwThreadId id. */
1926unsigned
1927cygwin_get_dr6 (void)
1928{
1929 return dr[6];
1930}
1931
1932
3cee93ac
CF
1933/* Determine if the thread referenced by "pid" is alive
1934 by "polling" it. If WaitForSingleObject returns WAIT_OBJECT_0
1935 it means that the pid has died. Otherwise it is assumed to be alive. */
1936static int
39f77062 1937win32_child_thread_alive (ptid_t ptid)
3cee93ac 1938{
39f77062
KB
1939 int pid = PIDGET (ptid);
1940
3a4b77d8
JM
1941 return WaitForSingleObject (thread_rec (pid, FALSE)->h, 0) == WAIT_OBJECT_0 ?
1942 FALSE : TRUE;
3cee93ac
CF
1943}
1944
1945/* Convert pid to printable format. */
1946char *
39f77062 1947cygwin_pid_to_str (ptid_t ptid)
3cee93ac
CF
1948{
1949 static char buf[80];
39f77062
KB
1950 int pid = PIDGET (ptid);
1951
29fe111d 1952 if ((DWORD) pid == current_event.dwProcessId)
b69571f5 1953 sprintf (buf, "process %d", pid);
3cee93ac 1954 else
b69571f5 1955 sprintf (buf, "thread %ld.0x%x", current_event.dwProcessId, pid);
3cee93ac
CF
1956 return buf;
1957}
8e860359
CF
1958
1959static int
1960core_dll_symbols_add (char *dll_name, DWORD base_addr)
1961{
1962 struct objfile *objfile;
1963 char *objfile_basename;
1964 const char *dll_basename;
1965
1966 if (!(dll_basename = strrchr (dll_name, '/')))
1967 dll_basename = dll_name;
1968 else
1969 dll_basename++;
1970
1971 ALL_OBJFILES (objfile)
1972 {
1973 objfile_basename = strrchr (objfile->name, '/');
1974
1975 if (objfile_basename &&
1976 strcmp (dll_basename, objfile_basename + 1) == 0)
1977 {
1978 printf_unfiltered ("%08lx:%s (symbols previously loaded)\n",
1979 base_addr, dll_name);
1980 goto out;
1981 }
1982 }
1983
1984 register_loaded_dll (dll_name, base_addr + 0x1000);
02e423b9 1985 solib_symbols_add (dll_name, 0, (CORE_ADDR) base_addr + 0x1000);
8e860359
CF
1986
1987out:
1988 return 1;
1989}
1990
1991typedef struct
1992{
1993 struct target_ops *target;
1994 bfd_vma addr;
1995}
1996map_code_section_args;
1997
1998static void
554cb486 1999map_single_dll_code_section (bfd * abfd, asection * sect, void *obj)
8e860359
CF
2000{
2001 int old;
2002 int update_coreops;
2003 struct section_table *new_target_sect_ptr;
2004
2005 map_code_section_args *args = (map_code_section_args *) obj;
2006 struct target_ops *target = args->target;
2007 if (sect->flags & SEC_CODE)
2008 {
2009 update_coreops = core_ops.to_sections == target->to_sections;
2010
2011 if (target->to_sections)
2012 {
2013 old = target->to_sections_end - target->to_sections;
2014 target->to_sections = (struct section_table *)
2015 xrealloc ((char *) target->to_sections,
2016 (sizeof (struct section_table)) * (1 + old));
2017 }
2018 else
2019 {
2020 old = 0;
2021 target->to_sections = (struct section_table *)
2022 xmalloc ((sizeof (struct section_table)));
2023 }
2024 target->to_sections_end = target->to_sections + (1 + old);
2025
2026 /* Update the to_sections field in the core_ops structure
3bccec63 2027 if needed. */
8e860359
CF
2028 if (update_coreops)
2029 {
2030 core_ops.to_sections = target->to_sections;
2031 core_ops.to_sections_end = target->to_sections_end;
2032 }
2033 new_target_sect_ptr = target->to_sections + old;
2034 new_target_sect_ptr->addr = args->addr + bfd_section_vma (abfd, sect);
2035 new_target_sect_ptr->endaddr = args->addr + bfd_section_vma (abfd, sect) +
2036 bfd_section_size (abfd, sect);;
2037 new_target_sect_ptr->the_bfd_section = sect;
2038 new_target_sect_ptr->bfd = abfd;
2039 }
2040}
2041
2042static int
2043dll_code_sections_add (const char *dll_name, int base_addr, struct target_ops *target)
2044{
2045 bfd *dll_bfd;
2046 map_code_section_args map_args;
2047 asection *lowest_sect;
2048 char *name;
2049 if (dll_name == NULL || target == NULL)
2050 return 0;
66ed1d85 2051 name = xstrdup (dll_name);
8e860359
CF
2052 dll_bfd = bfd_openr (name, "pei-i386");
2053 if (dll_bfd == NULL)
2054 return 0;
2055
2056 if (bfd_check_format (dll_bfd, bfd_object))
2057 {
2058 lowest_sect = bfd_get_section_by_name (dll_bfd, ".text");
2059 if (lowest_sect == NULL)
2060 return 0;
2061 map_args.target = target;
2062 map_args.addr = base_addr - bfd_section_vma (dll_bfd, lowest_sect);
2063
554cb486 2064 bfd_map_over_sections (dll_bfd, &map_single_dll_code_section, (void *) (&map_args));
8e860359
CF
2065 }
2066
2067 return 1;
2068}
2069
2070static void
554cb486 2071core_section_load_dll_symbols (bfd * abfd, asection * sect, void *obj)
8e860359
CF
2072{
2073 struct target_ops *target = (struct target_ops *) obj;
2074
2075 DWORD base_addr;
2076
2077 int dll_name_size;
2078 char *dll_name = NULL;
2079 char *buf = NULL;
2080 struct win32_pstatus *pstatus;
2081 char *p;
2082
2083 if (strncmp (sect->name, ".module", 7))
2084 return;
2085
2086 buf = (char *) xmalloc (sect->_raw_size + 1);
2087 if (!buf)
2088 {
2089 printf_unfiltered ("memory allocation failed for %s\n", sect->name);
2090 goto out;
2091 }
2092 if (!bfd_get_section_contents (abfd, sect, buf, 0, sect->_raw_size))
2093 goto out;
2094
2095 pstatus = (struct win32_pstatus *) buf;
2096
2097 memmove (&base_addr, &(pstatus->data.module_info.base_address), sizeof (base_addr));
2098 dll_name_size = pstatus->data.module_info.module_name_size;
2099 if (offsetof (struct win32_pstatus, data.module_info.module_name) + dll_name_size > sect->_raw_size)
2100 goto out;
2101
2102 dll_name = (char *) xmalloc (dll_name_size + 1);
2103 if (!dll_name)
2104 {
2105 printf_unfiltered ("memory allocation failed for %s\n", sect->name);
2106 goto out;
2107 }
2108 strncpy (dll_name, pstatus->data.module_info.module_name, dll_name_size);
2109
2110 while ((p = strchr (dll_name, '\\')))
2111 *p = '/';
2112
2113 if (!core_dll_symbols_add (dll_name, (DWORD) base_addr))
2114 printf_unfiltered ("%s: Failed to load dll symbols.\n", dll_name);
2115
2116 if (!dll_code_sections_add (dll_name, (DWORD) base_addr + 0x1000, target))
2117 printf_unfiltered ("%s: Failed to map dll code sections.\n", dll_name);
2118
2119out:
2120 if (buf)
b8c9b27d 2121 xfree (buf);
8e860359 2122 if (dll_name)
b8c9b27d 2123 xfree (dll_name);
8e860359
CF
2124 return;
2125}
2126
2127void
0a65a603
AC
2128child_solib_add (char *filename, int from_tty, struct target_ops *target,
2129 int readsyms)
8e860359 2130{
990f9fe3
FF
2131 if (!readsyms)
2132 return;
8e860359
CF
2133 if (core_bfd)
2134 {
2135 child_clear_solibs ();
2136 bfd_map_over_sections (core_bfd, &core_section_load_dll_symbols, target);
2137 }
2138 else
2139 {
2140 if (solib_end && solib_end->name)
d3ff4a77 2141 solib_end->objfile = solib_symbols_add (solib_end->name, from_tty,
3bccec63 2142 solib_end->load_addr);
8e860359
CF
2143 }
2144}
2145
2146static void
2147fetch_elf_core_registers (char *core_reg_sect,
2148 unsigned core_reg_size,
2149 int which,
2150 CORE_ADDR reg_addr)
2151{
2152 int r;
2153 if (core_reg_size < sizeof (CONTEXT))
2154 {
2155 error ("Core file register section too small (%u bytes).", core_reg_size);
2156 return;
2157 }
2158 for (r = 0; r < NUM_REGS; r++)
2159 supply_register (r, core_reg_sect + mappings[r]);
2160}
2161
2162static struct core_fns win32_elf_core_fns =
2163{
2164 bfd_target_elf_flavour,
2165 default_check_format,
2166 default_core_sniffer,
2167 fetch_elf_core_registers,
2168 NULL
2169};
2170
2171void
0613c401 2172_initialize_core_win32 (void)
8e860359
CF
2173{
2174 add_core_fns (&win32_elf_core_fns);
2175}
2a3d5645
CF
2176
2177void
2178_initialize_check_for_gdb_ini (void)
2179{
2180 char *homedir;
2181 if (inhibit_gdbinit)
2182 return;
2183
2184 homedir = getenv ("HOME");
2185 if (homedir)
2186 {
2187 char *p;
2188 char *oldini = (char *) alloca (strlen (homedir) +
2189 sizeof ("/gdb.ini"));
2190 strcpy (oldini, homedir);
2191 p = strchr (oldini, '\0');
2192 if (p > oldini && p[-1] != '/')
2193 *p++ = '/';
2194 strcpy (p, "gdb.ini");
2195 if (access (oldini, 0) == 0)
2196 {
2197 int len = strlen (oldini);
2198 char *newini = alloca (len + 1);
dfe7f3ac 2199 sprintf (newini, "%.*s.gdbinit",
58fa08f0 2200 (int) (len - (sizeof ("gdb.ini") - 1)), oldini);
2a3d5645
CF
2201 warning ("obsolete '%s' found. Rename to '%s'.", oldini, newini);
2202 }
2203 }
2204}
This page took 0.481948 seconds and 4 git commands to generate.