1 /* Target-vector operations for controlling windows child processes, for GDB.
3 Copyright (C) 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004,
4 2005, 2006, 2007, 2008, 2009 Free Software Foundation, Inc.
6 Contributed by Cygnus Solutions, A Red Hat Company.
8 This file is part of GDB.
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 3 of the License, or
13 (at your option) any later version.
15 This program is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 GNU General Public License for more details.
20 You should have received a copy of the GNU General Public License
21 along with this program. If not, see <http://www.gnu.org/licenses/>. */
23 /* Originally by Steve Chamberlain, sac@cygnus.com */
26 #include "frame.h" /* required by inferior.h */
29 #include "exceptions.h"
32 #include "completer.h"
36 #include <sys/types.h>
43 #include <sys/cygwin.h>
50 #include "gdb_obstack.h"
51 #include "gdb_string.h"
52 #include "gdbthread.h"
54 #include <sys/param.h>
59 #include "xml-support.h"
61 #include "i386-tdep.h"
62 #include "i387-tdep.h"
64 #include "windows-tdep.h"
65 #include "windows-nat.h"
67 #define DebugActiveProcessStop dyn_DebugActiveProcessStop
68 #define DebugBreakProcess dyn_DebugBreakProcess
69 #define DebugSetProcessKillOnExit dyn_DebugSetProcessKillOnExit
70 #define EnumProcessModules dyn_EnumProcessModules
71 #define GetModuleFileNameExA dyn_GetModuleFileNameExA
72 #define GetModuleInformation dyn_GetModuleInformation
74 /* Since Windows XP, detaching from a process is supported by Windows.
75 The following code tries loading the appropriate functions dynamically.
76 If loading these functions succeeds use them to actually detach from
77 the inferior process, otherwise behave as usual, pretending that
79 static BOOL
WINAPI (*DebugActiveProcessStop
) (DWORD
);
80 static BOOL
WINAPI (*DebugBreakProcess
) (HANDLE
);
81 static BOOL
WINAPI (*DebugSetProcessKillOnExit
) (BOOL
);
82 static BOOL
WINAPI (*EnumProcessModules
) (HANDLE
, HMODULE
*, DWORD
,
84 static DWORD
WINAPI (*GetModuleFileNameExA
) (HANDLE
, HMODULE
, LPSTR
,
86 static BOOL
WINAPI (*GetModuleInformation
) (HANDLE
, HMODULE
, LPMODULEINFO
,
89 static struct target_ops windows_ops
;
92 /* The starting and ending address of the cygwin1.dll text segment. */
93 static CORE_ADDR cygwin_load_start
;
94 static CORE_ADDR cygwin_load_end
;
97 static int have_saved_context
; /* True if we've saved context from a cygwin signal. */
98 static CONTEXT saved_context
; /* Containes the saved context from a cygwin signal. */
100 /* If we're not using the old Cygwin header file set, define the
101 following which never should have been in the generic Win32 API
102 headers in the first place since they were our own invention... */
103 #ifndef _GNU_H_WINDOWS_H
106 FLAG_TRACE_BIT
= 0x100,
107 CONTEXT_DEBUGGER
= (CONTEXT_FULL
| CONTEXT_FLOATING_POINT
)
111 #ifndef CONTEXT_EXTENDED_REGISTERS
112 /* This macro is only defined on ia32. It only makes sense on this target,
113 so define it as zero if not already defined. */
114 #define CONTEXT_EXTENDED_REGISTERS 0
117 #define CONTEXT_DEBUGGER_DR CONTEXT_DEBUGGER | CONTEXT_DEBUG_REGISTERS \
118 | CONTEXT_EXTENDED_REGISTERS
120 static uintptr_t dr
[8];
121 static int debug_registers_changed
;
122 static int debug_registers_used
;
123 #define DR6_CLEAR_VALUE 0xffff0ff0
125 /* The string sent by cygwin when it processes a signal.
126 FIXME: This should be in a cygwin include file. */
127 #ifndef _CYGWIN_SIGNAL_STRING
128 #define _CYGWIN_SIGNAL_STRING "cYgSiGw00f"
131 #define CHECK(x) check (x, __FILE__,__LINE__)
132 #define DEBUG_EXEC(x) if (debug_exec) printf_unfiltered x
133 #define DEBUG_EVENTS(x) if (debug_events) printf_unfiltered x
134 #define DEBUG_MEM(x) if (debug_memory) printf_unfiltered x
135 #define DEBUG_EXCEPT(x) if (debug_exceptions) printf_unfiltered x
137 static void windows_stop (ptid_t
);
138 static int windows_thread_alive (struct target_ops
*, ptid_t
);
139 static void windows_kill_inferior (struct target_ops
*);
141 static enum target_signal last_sig
= TARGET_SIGNAL_0
;
142 /* Set if a signal was received from the debugged process */
144 /* Thread information structure used to track information that is
145 not available in gdb's thread structure. */
146 typedef struct thread_info_struct
148 struct thread_info_struct
*next
;
159 static thread_info thread_head
;
161 /* The process and thread handles for the above context. */
163 static DEBUG_EVENT current_event
; /* The current debug event from
165 static HANDLE current_process_handle
; /* Currently executing process */
166 static thread_info
*current_thread
; /* Info on currently selected thread */
167 static DWORD main_thread_id
; /* Thread ID of the main thread */
169 /* Counts of things. */
170 static int exception_count
= 0;
171 static int event_count
= 0;
172 static int saw_create
;
173 static int open_process_used
= 0;
176 static int new_console
= 0;
178 static int cygwin_exceptions
= 0;
180 static int new_group
= 1;
181 static int debug_exec
= 0; /* show execution */
182 static int debug_events
= 0; /* show events from kernel */
183 static int debug_memory
= 0; /* show target memory accesses */
184 static int debug_exceptions
= 0; /* show target exceptions */
185 static int useshell
= 0; /* use shell for subprocesses */
187 /* This vector maps GDB's idea of a register's number into an offset
188 in the windows exception context vector.
190 It also contains the bit mask needed to load the register in question.
192 The contents of this table can only be computed by the units
193 that provide CPU-specific support for Windows native debugging.
194 These units should set the table by calling
195 windows_set_context_register_offsets.
197 One day we could read a reg, we could inspect the context we
198 already have loaded, if it doesn't have the bit set that we need,
199 we read that set of registers in using GetThreadContext. If the
200 context already contains what we need, we just unpack it. Then to
201 write a register, first we have to ensure that the context contains
202 the other regs of the group, and then we copy the info in and set
205 static const int *mappings
;
207 /* This vector maps the target's idea of an exception (extracted
208 from the DEBUG_EVENT structure) to GDB's idea. */
210 struct xlate_exception
213 enum target_signal us
;
216 static const struct xlate_exception
219 {EXCEPTION_ACCESS_VIOLATION
, TARGET_SIGNAL_SEGV
},
220 {STATUS_STACK_OVERFLOW
, TARGET_SIGNAL_SEGV
},
221 {EXCEPTION_BREAKPOINT
, TARGET_SIGNAL_TRAP
},
222 {DBG_CONTROL_C
, TARGET_SIGNAL_INT
},
223 {EXCEPTION_SINGLE_STEP
, TARGET_SIGNAL_TRAP
},
224 {STATUS_FLOAT_DIVIDE_BY_ZERO
, TARGET_SIGNAL_FPE
},
227 /* Set the MAPPINGS static global to OFFSETS.
228 See the description of MAPPINGS for more details. */
231 windows_set_context_register_offsets (const int *offsets
)
237 check (BOOL ok
, const char *file
, int line
)
240 printf_filtered ("error return %s:%d was %lu\n", file
, line
,
244 /* Find a thread record given a thread id. If GET_CONTEXT is not 0,
245 then also retrieve the context for this thread. If GET_CONTEXT is
246 negative, then don't suspend the thread. */
248 thread_rec (DWORD id
, int get_context
)
252 for (th
= &thread_head
; (th
= th
->next
) != NULL
;)
255 if (!th
->suspended
&& get_context
)
257 if (get_context
> 0 && id
!= current_event
.dwThreadId
)
259 if (SuspendThread (th
->h
) == (DWORD
) -1)
261 DWORD err
= GetLastError ();
262 warning (_("SuspendThread failed. (winerr %d)"),
268 else if (get_context
< 0)
270 th
->reload_context
= 1;
278 /* Add a thread to the thread list. */
280 windows_add_thread (ptid_t ptid
, HANDLE h
)
285 gdb_assert (ptid_get_tid (ptid
) != 0);
287 id
= ptid_get_tid (ptid
);
289 if ((th
= thread_rec (id
, FALSE
)))
292 th
= XZALLOC (thread_info
);
295 th
->next
= thread_head
.next
;
296 thread_head
.next
= th
;
298 /* Set the debug registers for the new thread if they are used. */
299 if (debug_registers_used
)
301 /* Only change the value of the debug registers. */
302 th
->context
.ContextFlags
= CONTEXT_DEBUG_REGISTERS
;
303 CHECK (GetThreadContext (th
->h
, &th
->context
));
304 th
->context
.Dr0
= dr
[0];
305 th
->context
.Dr1
= dr
[1];
306 th
->context
.Dr2
= dr
[2];
307 th
->context
.Dr3
= dr
[3];
308 th
->context
.Dr6
= DR6_CLEAR_VALUE
;
309 th
->context
.Dr7
= dr
[7];
310 CHECK (SetThreadContext (th
->h
, &th
->context
));
311 th
->context
.ContextFlags
= 0;
316 /* Clear out any old thread list and reintialize it to a
319 windows_init_thread_list (void)
321 thread_info
*th
= &thread_head
;
323 DEBUG_EVENTS (("gdb: windows_init_thread_list\n"));
325 while (th
->next
!= NULL
)
327 thread_info
*here
= th
->next
;
328 th
->next
= here
->next
;
331 thread_head
.next
= NULL
;
334 /* Delete a thread from the list of threads */
336 windows_delete_thread (ptid_t ptid
)
341 gdb_assert (ptid_get_tid (ptid
) != 0);
343 id
= ptid_get_tid (ptid
);
346 printf_unfiltered ("[Deleting %s]\n", target_pid_to_str (ptid
));
347 delete_thread (ptid
);
349 for (th
= &thread_head
;
350 th
->next
!= NULL
&& th
->next
->id
!= id
;
354 if (th
->next
!= NULL
)
356 thread_info
*here
= th
->next
;
357 th
->next
= here
->next
;
363 do_windows_fetch_inferior_registers (struct regcache
*regcache
, int r
)
365 char *context_offset
= ((char *) ¤t_thread
->context
) + mappings
[r
];
366 struct gdbarch
*gdbarch
= get_regcache_arch (regcache
);
367 struct gdbarch_tdep
*tdep
= gdbarch_tdep (gdbarch
);
371 return; /* Windows sometimes uses a non-existent thread id in its
374 if (current_thread
->reload_context
)
376 #ifdef __COPY_CONTEXT_SIZE
377 if (have_saved_context
)
379 /* Lie about where the program actually is stopped since cygwin has informed us that
380 we should consider the signal to have occurred at another location which is stored
381 in "saved_context. */
382 memcpy (¤t_thread
->context
, &saved_context
, __COPY_CONTEXT_SIZE
);
383 have_saved_context
= 0;
388 thread_info
*th
= current_thread
;
389 th
->context
.ContextFlags
= CONTEXT_DEBUGGER_DR
;
390 GetThreadContext (th
->h
, &th
->context
);
391 /* Copy dr values from that thread.
392 But only if there were not modified since last stop. PR gdb/2388 */
393 if (!debug_registers_changed
)
395 dr
[0] = th
->context
.Dr0
;
396 dr
[1] = th
->context
.Dr1
;
397 dr
[2] = th
->context
.Dr2
;
398 dr
[3] = th
->context
.Dr3
;
399 dr
[6] = th
->context
.Dr6
;
400 dr
[7] = th
->context
.Dr7
;
403 current_thread
->reload_context
= 0;
406 if (r
== I387_FISEG_REGNUM (tdep
))
408 l
= *((long *) context_offset
) & 0xffff;
409 regcache_raw_supply (regcache
, r
, (char *) &l
);
411 else if (r
== I387_FOP_REGNUM (tdep
))
413 l
= (*((long *) context_offset
) >> 16) & ((1 << 11) - 1);
414 regcache_raw_supply (regcache
, r
, (char *) &l
);
417 regcache_raw_supply (regcache
, r
, context_offset
);
420 for (r
= 0; r
< gdbarch_num_regs (gdbarch
); r
++)
421 do_windows_fetch_inferior_registers (regcache
, r
);
426 windows_fetch_inferior_registers (struct target_ops
*ops
,
427 struct regcache
*regcache
, int r
)
429 current_thread
= thread_rec (ptid_get_tid (inferior_ptid
), TRUE
);
430 /* Check if current_thread exists. Windows sometimes uses a non-existent
431 thread id in its events */
433 do_windows_fetch_inferior_registers (regcache
, r
);
437 do_windows_store_inferior_registers (const struct regcache
*regcache
, int r
)
440 /* Windows sometimes uses a non-existent thread id in its events */;
442 regcache_raw_collect (regcache
, r
,
443 ((char *) ¤t_thread
->context
) + mappings
[r
]);
446 for (r
= 0; r
< gdbarch_num_regs (get_regcache_arch (regcache
)); r
++)
447 do_windows_store_inferior_registers (regcache
, r
);
451 /* Store a new register value into the current thread context */
453 windows_store_inferior_registers (struct target_ops
*ops
,
454 struct regcache
*regcache
, int r
)
456 current_thread
= thread_rec (ptid_get_tid (inferior_ptid
), TRUE
);
457 /* Check if current_thread exists. Windows sometimes uses a non-existent
458 thread id in its events */
460 do_windows_store_inferior_registers (regcache
, r
);
463 /* Get the name of a given module at at given base address. If base_address
464 is zero return the first loaded module (which is always the name of the
467 get_module_name (LPVOID base_address
, char *dll_name_ret
)
473 HMODULE
*DllHandle
= dh_buf
; /* Set to temporary storage for initial query */
476 char pathbuf
[PATH_MAX
+ 1]; /* Temporary storage prior to converting to
479 char *pathbuf
= dll_name_ret
; /* Just copy directly to passed-in arg */
483 /* Find size of buffer needed to handle list of modules loaded in inferior */
484 if (!EnumProcessModules (current_process_handle
, DllHandle
,
485 sizeof (HMODULE
), &cbNeeded
) || !cbNeeded
)
488 /* Allocate correct amount of space for module list */
489 DllHandle
= (HMODULE
*) alloca (cbNeeded
);
493 /* Get the list of modules */
494 if (!EnumProcessModules (current_process_handle
, DllHandle
, cbNeeded
,
498 for (i
= 0; i
< (int) (cbNeeded
/ sizeof (HMODULE
)); i
++)
500 /* Get information on this module */
501 if (!GetModuleInformation (current_process_handle
, DllHandle
[i
],
503 error (_("Can't get module info"));
505 if (!base_address
|| mi
.lpBaseOfDll
== base_address
)
507 /* Try to find the name of the given module */
508 len
= GetModuleFileNameExA (current_process_handle
,
509 DllHandle
[i
], pathbuf
, MAX_PATH
);
511 error (_("Error getting dll name: %u."), (unsigned) GetLastError ());
513 /* Cygwin prefers that the path be in /x/y/z format */
514 cygwin_conv_to_full_posix_path (pathbuf
, dll_name_ret
);
516 return 1; /* success */
521 dll_name_ret
[0] = '\0';
522 return 0; /* failure */
525 /* Encapsulate the information required in a call to
526 symbol_file_add_args */
527 struct safe_symbol_file_add_args
531 struct section_addr_info
*addrs
;
534 struct ui_file
*err
, *out
;
538 /* Maintain a linked list of "so" information. */
544 static struct so_list solib_start
, *solib_end
;
546 /* Call symbol_file_add with stderr redirected. We don't care if there
549 safe_symbol_file_add_stub (void *argv
)
551 #define p ((struct safe_symbol_file_add_args *) argv)
552 p
->ret
= symbol_file_add (p
->name
, p
->from_tty
, p
->addrs
, p
->mainline
, p
->flags
);
557 /* Restore gdb's stderr after calling symbol_file_add */
559 safe_symbol_file_add_cleanup (void *p
)
561 #define sp ((struct safe_symbol_file_add_args *)p)
562 gdb_flush (gdb_stderr
);
563 gdb_flush (gdb_stdout
);
564 ui_file_delete (gdb_stderr
);
565 ui_file_delete (gdb_stdout
);
566 gdb_stderr
= sp
->err
;
567 gdb_stdout
= sp
->out
;
571 /* symbol_file_add wrapper that prevents errors from being displayed. */
572 static struct objfile
*
573 safe_symbol_file_add (char *name
, int from_tty
,
574 struct section_addr_info
*addrs
,
575 int mainline
, int flags
)
577 struct safe_symbol_file_add_args p
;
578 struct cleanup
*cleanup
;
580 cleanup
= make_cleanup (safe_symbol_file_add_cleanup
, &p
);
584 gdb_flush (gdb_stderr
);
585 gdb_flush (gdb_stdout
);
586 gdb_stderr
= ui_file_new ();
587 gdb_stdout
= ui_file_new ();
589 p
.from_tty
= from_tty
;
591 p
.mainline
= mainline
;
593 catch_errors (safe_symbol_file_add_stub
, &p
, "", RETURN_MASK_ERROR
);
595 do_cleanups (cleanup
);
599 static struct so_list
*
600 windows_make_so (const char *name
, LPVOID load_addr
)
603 char buf
[MAX_PATH
+ 1];
604 char cwd
[MAX_PATH
+ 1];
606 WIN32_FIND_DATA w32_fd
;
607 HANDLE h
= FindFirstFile(name
, &w32_fd
);
608 MEMORY_BASIC_INFORMATION m
;
610 if (h
== INVALID_HANDLE_VALUE
)
616 if (GetCurrentDirectory (MAX_PATH
+ 1, cwd
))
618 p
= strrchr (buf
, '\\');
621 SetCurrentDirectory (buf
);
622 GetFullPathName (w32_fd
.cFileName
, MAX_PATH
, buf
, &p
);
623 SetCurrentDirectory (cwd
);
627 if (strcasecmp (buf
, "ntdll.dll") == 0)
629 GetSystemDirectory (buf
, sizeof (buf
));
630 strcat (buf
, "\\ntdll.dll");
632 so
= XZALLOC (struct so_list
);
633 so
->lm_info
= (struct lm_info
*) xmalloc (sizeof (struct lm_info
));
634 so
->lm_info
->load_addr
= load_addr
;
635 strcpy (so
->so_original_name
, name
);
637 strcpy (so
->so_name
, buf
);
639 cygwin_conv_to_posix_path (buf
, so
->so_name
);
640 /* Record cygwin1.dll .text start/end. */
641 p
= strchr (so
->so_name
, '\0') - (sizeof ("/cygwin1.dll") - 1);
642 if (p
>= so
->so_name
&& strcasecmp (p
, "/cygwin1.dll") == 0)
645 asection
*text
= NULL
;
648 abfd
= bfd_openr (so
->so_name
, "pei-i386");
653 if (bfd_check_format (abfd
, bfd_object
))
654 text
= bfd_get_section_by_name (abfd
, ".text");
662 /* The symbols in a dll are offset by 0x1000, which is the the
663 offset from 0 of the first byte in an image - because of the
664 file header and the section alignment. */
665 cygwin_load_start
= (CORE_ADDR
) (uintptr_t) ((char *) load_addr
+ 0x1000);
666 cygwin_load_end
= cygwin_load_start
+ bfd_section_size (abfd
, text
);
676 get_image_name (HANDLE h
, void *address
, int unicode
)
678 static char buf
[(2 * MAX_PATH
) + 1];
679 DWORD size
= unicode
? sizeof (WCHAR
) : sizeof (char);
685 /* Attempt to read the name of the dll that was detected.
686 This is documented to work only when actively debugging
687 a program. It will not work for attached processes. */
691 /* See if we could read the address of a string, and that the
692 address isn't null. */
693 if (!ReadProcessMemory (h
, address
, &address_ptr
, sizeof (address_ptr
), &done
)
694 || done
!= sizeof (address_ptr
) || !address_ptr
)
697 /* Find the length of the string */
698 while (ReadProcessMemory (h
, address_ptr
+ len
++ * size
, &b
, size
, &done
)
699 && (b
[0] != 0 || b
[size
- 1] != 0) && done
== size
)
703 ReadProcessMemory (h
, address_ptr
, buf
, len
, &done
);
706 WCHAR
*unicode_address
= (WCHAR
*) alloca (len
* sizeof (WCHAR
));
707 ReadProcessMemory (h
, address_ptr
, unicode_address
, len
* sizeof (WCHAR
),
710 WideCharToMultiByte (CP_ACP
, 0, unicode_address
, len
, buf
, len
, 0, 0);
716 /* Wait for child to do something. Return pid of child, or -1 in case
717 of error; store status through argument pointer OURSTATUS. */
719 handle_load_dll (void *dummy
)
721 LOAD_DLL_DEBUG_INFO
*event
= ¤t_event
.u
.LoadDll
;
722 char dll_buf
[MAX_PATH
+ 1];
723 char *dll_name
= NULL
;
725 dll_buf
[0] = dll_buf
[sizeof (dll_buf
) - 1] = '\0';
727 if (!get_module_name (event
->lpBaseOfDll
, dll_buf
))
728 dll_buf
[0] = dll_buf
[sizeof (dll_buf
) - 1] = '\0';
732 if (*dll_name
== '\0')
733 dll_name
= get_image_name (current_process_handle
,
734 event
->lpImageName
, event
->fUnicode
);
738 solib_end
->next
= windows_make_so (dll_name
, event
->lpBaseOfDll
);
739 solib_end
= solib_end
->next
;
741 DEBUG_EVENTS (("gdb: Loading dll \"%s\" at %p.\n", solib_end
->so_name
,
742 solib_end
->lm_info
->load_addr
));
748 windows_free_so (struct so_list
*so
)
756 handle_unload_dll (void *dummy
)
758 LPVOID lpBaseOfDll
= current_event
.u
.UnloadDll
.lpBaseOfDll
;
761 for (so
= &solib_start
; so
->next
!= NULL
; so
= so
->next
)
762 if (so
->next
->lm_info
->load_addr
== lpBaseOfDll
)
764 struct so_list
*sodel
= so
->next
;
765 so
->next
= sodel
->next
;
768 DEBUG_EVENTS (("gdb: Unloading dll \"%s\".\n", sodel
->so_name
));
770 windows_free_so (sodel
);
771 solib_add (NULL
, 0, NULL
, auto_solib_add
);
775 error (_("Error: dll starting at %p not found."), lpBaseOfDll
);
780 /* Clear list of loaded DLLs. */
782 windows_clear_solib (void)
784 solib_start
.next
= NULL
;
785 solib_end
= &solib_start
;
788 /* Load DLL symbol info. */
790 dll_symbol_command (char *args
, int from_tty
)
796 error (_("dll-symbols requires a file name"));
799 if (n
> 4 && strcasecmp (args
+ n
- 4, ".dll") != 0)
801 char *newargs
= (char *) alloca (n
+ 4 + 1);
802 strcpy (newargs
, args
);
803 strcat (newargs
, ".dll");
807 safe_symbol_file_add (args
, from_tty
, NULL
, 0, OBJF_SHARED
| OBJF_USERLOADED
);
810 /* Handle DEBUG_STRING output from child process.
811 Cygwin prepends its messages with a "cygwin:". Interpret this as
812 a Cygwin signal. Otherwise just print the string as a warning. */
814 handle_output_debug_string (struct target_waitstatus
*ourstatus
)
819 if (!target_read_string
820 ((CORE_ADDR
) (uintptr_t) current_event
.u
.DebugString
.lpDebugStringData
,
824 else if (strncmp (s
, _CYGWIN_SIGNAL_STRING
, sizeof (_CYGWIN_SIGNAL_STRING
) - 1) != 0)
827 if (strncmp (s
, "cYg", 3) != 0)
831 #ifdef __COPY_CONTEXT_SIZE
834 /* Got a cygwin signal marker. A cygwin signal is followed by the signal number
835 itself and then optionally followed by the thread id and address to saved context
836 within the DLL. If these are supplied, then the given thread is assumed to have
837 issued the signal and the context from the thread is assumed to be stored at the
838 given address in the inferior. Tell gdb to treat this like a real signal. */
840 int sig
= strtol (s
+ sizeof (_CYGWIN_SIGNAL_STRING
) - 1, &p
, 0);
841 int gotasig
= target_signal_from_host (sig
);
842 ourstatus
->value
.sig
= gotasig
;
847 ourstatus
->kind
= TARGET_WAITKIND_STOPPED
;
848 retval
= strtoul (p
, &p
, 0);
850 retval
= main_thread_id
;
851 else if ((x
= (LPCVOID
) strtoul (p
, &p
, 0))
852 && ReadProcessMemory (current_process_handle
, x
,
853 &saved_context
, __COPY_CONTEXT_SIZE
, &n
)
854 && n
== __COPY_CONTEXT_SIZE
)
855 have_saved_context
= 1;
856 current_event
.dwThreadId
= retval
;
867 display_selector (HANDLE thread
, DWORD sel
)
870 if (GetThreadSelectorEntry (thread
, sel
, &info
))
873 printf_filtered ("0x%03lx: ", sel
);
874 if (!info
.HighWord
.Bits
.Pres
)
876 puts_filtered ("Segment not present\n");
879 base
= (info
.HighWord
.Bits
.BaseHi
<< 24) +
880 (info
.HighWord
.Bits
.BaseMid
<< 16)
882 limit
= (info
.HighWord
.Bits
.LimitHi
<< 16) + info
.LimitLow
;
883 if (info
.HighWord
.Bits
.Granularity
)
884 limit
= (limit
<< 12) | 0xfff;
885 printf_filtered ("base=0x%08x limit=0x%08x", base
, limit
);
886 if (info
.HighWord
.Bits
.Default_Big
)
887 puts_filtered(" 32-bit ");
889 puts_filtered(" 16-bit ");
890 switch ((info
.HighWord
.Bits
.Type
& 0xf) >> 1)
893 puts_filtered ("Data (Read-Only, Exp-up");
896 puts_filtered ("Data (Read/Write, Exp-up");
899 puts_filtered ("Unused segment (");
902 puts_filtered ("Data (Read/Write, Exp-down");
905 puts_filtered ("Code (Exec-Only, N.Conf");
908 puts_filtered ("Code (Exec/Read, N.Conf");
911 puts_filtered ("Code (Exec-Only, Conf");
914 puts_filtered ("Code (Exec/Read, Conf");
917 printf_filtered ("Unknown type 0x%x",info
.HighWord
.Bits
.Type
);
919 if ((info
.HighWord
.Bits
.Type
& 0x1) == 0)
920 puts_filtered(", N.Acc");
921 puts_filtered (")\n");
922 if ((info
.HighWord
.Bits
.Type
& 0x10) == 0)
923 puts_filtered("System selector ");
924 printf_filtered ("Priviledge level = %d. ", info
.HighWord
.Bits
.Dpl
);
925 if (info
.HighWord
.Bits
.Granularity
)
926 puts_filtered ("Page granular.\n");
928 puts_filtered ("Byte granular.\n");
933 printf_filtered ("Invalid selector 0x%lx.\n",sel
);
939 display_selectors (char * args
, int from_tty
)
943 puts_filtered ("Impossible to display selectors now.\n");
949 puts_filtered ("Selector $cs\n");
950 display_selector (current_thread
->h
,
951 current_thread
->context
.SegCs
);
952 puts_filtered ("Selector $ds\n");
953 display_selector (current_thread
->h
,
954 current_thread
->context
.SegDs
);
955 puts_filtered ("Selector $es\n");
956 display_selector (current_thread
->h
,
957 current_thread
->context
.SegEs
);
958 puts_filtered ("Selector $ss\n");
959 display_selector (current_thread
->h
,
960 current_thread
->context
.SegSs
);
961 puts_filtered ("Selector $fs\n");
962 display_selector (current_thread
->h
,
963 current_thread
->context
.SegFs
);
964 puts_filtered ("Selector $gs\n");
965 display_selector (current_thread
->h
,
966 current_thread
->context
.SegGs
);
971 sel
= parse_and_eval_long (args
);
972 printf_filtered ("Selector \"%s\"\n",args
);
973 display_selector (current_thread
->h
, sel
);
977 static struct cmd_list_element
*info_w32_cmdlist
= NULL
;
980 info_w32_command (char *args
, int from_tty
)
982 help_list (info_w32_cmdlist
, "info w32 ", class_info
, gdb_stdout
);
986 #define DEBUG_EXCEPTION_SIMPLE(x) if (debug_exceptions) \
987 printf_unfiltered ("gdb: Target exception %s at %p\n", x, \
988 current_event.u.Exception.ExceptionRecord.ExceptionAddress)
991 handle_exception (struct target_waitstatus
*ourstatus
)
994 DWORD code
= current_event
.u
.Exception
.ExceptionRecord
.ExceptionCode
;
996 ourstatus
->kind
= TARGET_WAITKIND_STOPPED
;
998 /* Record the context of the current thread */
999 th
= thread_rec (current_event
.dwThreadId
, -1);
1003 case EXCEPTION_ACCESS_VIOLATION
:
1004 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_ACCESS_VIOLATION");
1005 ourstatus
->value
.sig
= TARGET_SIGNAL_SEGV
;
1008 /* See if the access violation happened within the cygwin DLL itself. Cygwin uses
1009 a kind of exception handling to deal with passed-in invalid addresses. gdb
1010 should not treat these as real SEGVs since they will be silently handled by
1011 cygwin. A real SEGV will (theoretically) be caught by cygwin later in the process
1012 and will be sent as a cygwin-specific-signal. So, ignore SEGVs if they show up
1013 within the text segment of the DLL itself. */
1015 CORE_ADDR addr
= (CORE_ADDR
) (uintptr_t) current_event
.u
.Exception
.ExceptionRecord
.ExceptionAddress
;
1016 if ((!cygwin_exceptions
&& (addr
>= cygwin_load_start
&& addr
< cygwin_load_end
))
1017 || (find_pc_partial_function (addr
, &fn
, NULL
, NULL
)
1018 && strncmp (fn
, "KERNEL32!IsBad", strlen ("KERNEL32!IsBad")) == 0))
1023 case STATUS_STACK_OVERFLOW
:
1024 DEBUG_EXCEPTION_SIMPLE ("STATUS_STACK_OVERFLOW");
1025 ourstatus
->value
.sig
= TARGET_SIGNAL_SEGV
;
1027 case STATUS_FLOAT_DENORMAL_OPERAND
:
1028 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_DENORMAL_OPERAND");
1029 ourstatus
->value
.sig
= TARGET_SIGNAL_FPE
;
1031 case EXCEPTION_ARRAY_BOUNDS_EXCEEDED
:
1032 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_ARRAY_BOUNDS_EXCEEDED");
1033 ourstatus
->value
.sig
= TARGET_SIGNAL_FPE
;
1035 case STATUS_FLOAT_INEXACT_RESULT
:
1036 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_INEXACT_RESULT");
1037 ourstatus
->value
.sig
= TARGET_SIGNAL_FPE
;
1039 case STATUS_FLOAT_INVALID_OPERATION
:
1040 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_INVALID_OPERATION");
1041 ourstatus
->value
.sig
= TARGET_SIGNAL_FPE
;
1043 case STATUS_FLOAT_OVERFLOW
:
1044 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_OVERFLOW");
1045 ourstatus
->value
.sig
= TARGET_SIGNAL_FPE
;
1047 case STATUS_FLOAT_STACK_CHECK
:
1048 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_STACK_CHECK");
1049 ourstatus
->value
.sig
= TARGET_SIGNAL_FPE
;
1051 case STATUS_FLOAT_UNDERFLOW
:
1052 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_UNDERFLOW");
1053 ourstatus
->value
.sig
= TARGET_SIGNAL_FPE
;
1055 case STATUS_FLOAT_DIVIDE_BY_ZERO
:
1056 DEBUG_EXCEPTION_SIMPLE ("STATUS_FLOAT_DIVIDE_BY_ZERO");
1057 ourstatus
->value
.sig
= TARGET_SIGNAL_FPE
;
1059 case STATUS_INTEGER_DIVIDE_BY_ZERO
:
1060 DEBUG_EXCEPTION_SIMPLE ("STATUS_INTEGER_DIVIDE_BY_ZERO");
1061 ourstatus
->value
.sig
= TARGET_SIGNAL_FPE
;
1063 case STATUS_INTEGER_OVERFLOW
:
1064 DEBUG_EXCEPTION_SIMPLE ("STATUS_INTEGER_OVERFLOW");
1065 ourstatus
->value
.sig
= TARGET_SIGNAL_FPE
;
1067 case EXCEPTION_BREAKPOINT
:
1068 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_BREAKPOINT");
1069 ourstatus
->value
.sig
= TARGET_SIGNAL_TRAP
;
1072 DEBUG_EXCEPTION_SIMPLE ("DBG_CONTROL_C");
1073 ourstatus
->value
.sig
= TARGET_SIGNAL_INT
;
1075 case DBG_CONTROL_BREAK
:
1076 DEBUG_EXCEPTION_SIMPLE ("DBG_CONTROL_BREAK");
1077 ourstatus
->value
.sig
= TARGET_SIGNAL_INT
;
1079 case EXCEPTION_SINGLE_STEP
:
1080 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_SINGLE_STEP");
1081 ourstatus
->value
.sig
= TARGET_SIGNAL_TRAP
;
1083 case EXCEPTION_ILLEGAL_INSTRUCTION
:
1084 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_ILLEGAL_INSTRUCTION");
1085 ourstatus
->value
.sig
= TARGET_SIGNAL_ILL
;
1087 case EXCEPTION_PRIV_INSTRUCTION
:
1088 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_PRIV_INSTRUCTION");
1089 ourstatus
->value
.sig
= TARGET_SIGNAL_ILL
;
1091 case EXCEPTION_NONCONTINUABLE_EXCEPTION
:
1092 DEBUG_EXCEPTION_SIMPLE ("EXCEPTION_NONCONTINUABLE_EXCEPTION");
1093 ourstatus
->value
.sig
= TARGET_SIGNAL_ILL
;
1096 /* Treat unhandled first chance exceptions specially. */
1097 if (current_event
.u
.Exception
.dwFirstChance
)
1099 printf_unfiltered ("gdb: unknown target exception 0x%08lx at %p\n",
1100 current_event
.u
.Exception
.ExceptionRecord
.ExceptionCode
,
1101 current_event
.u
.Exception
.ExceptionRecord
.ExceptionAddress
);
1102 ourstatus
->value
.sig
= TARGET_SIGNAL_UNKNOWN
;
1106 last_sig
= ourstatus
->value
.sig
;
1110 /* Resume all artificially suspended threads if we are continuing
1113 windows_continue (DWORD continue_status
, int id
)
1119 DEBUG_EVENTS (("ContinueDebugEvent (cpid=%ld, ctid=%ld, %s);\n",
1120 current_event
.dwProcessId
, current_event
.dwThreadId
,
1121 continue_status
== DBG_CONTINUE
?
1122 "DBG_CONTINUE" : "DBG_EXCEPTION_NOT_HANDLED"));
1124 for (th
= &thread_head
; (th
= th
->next
) != NULL
;)
1125 if ((id
== -1 || id
== (int) th
->id
)
1128 if (debug_registers_changed
)
1130 th
->context
.ContextFlags
|= CONTEXT_DEBUG_REGISTERS
;
1131 th
->context
.Dr0
= dr
[0];
1132 th
->context
.Dr1
= dr
[1];
1133 th
->context
.Dr2
= dr
[2];
1134 th
->context
.Dr3
= dr
[3];
1135 th
->context
.Dr6
= DR6_CLEAR_VALUE
;
1136 th
->context
.Dr7
= dr
[7];
1138 if (th
->context
.ContextFlags
)
1140 CHECK (SetThreadContext (th
->h
, &th
->context
));
1141 th
->context
.ContextFlags
= 0;
1143 if (th
->suspended
> 0)
1144 (void) ResumeThread (th
->h
);
1148 res
= ContinueDebugEvent (current_event
.dwProcessId
,
1149 current_event
.dwThreadId
,
1152 debug_registers_changed
= 0;
1156 /* Called in pathological case where Windows fails to send a
1157 CREATE_PROCESS_DEBUG_EVENT after an attach. */
1159 fake_create_process (void)
1161 current_process_handle
= OpenProcess (PROCESS_ALL_ACCESS
, FALSE
,
1162 current_event
.dwProcessId
);
1163 if (current_process_handle
!= NULL
)
1164 open_process_used
= 1;
1167 error (_("OpenProcess call failed, GetLastError = %lud\n"),
1169 /* We can not debug anything in that case. */
1171 main_thread_id
= current_event
.dwThreadId
;
1172 current_thread
= windows_add_thread (ptid_build (current_event
.dwProcessId
, 0,
1173 current_event
.dwThreadId
),
1174 current_event
.u
.CreateThread
.hThread
);
1175 return main_thread_id
;
1179 windows_resume (struct target_ops
*ops
,
1180 ptid_t ptid
, int step
, enum target_signal sig
)
1183 DWORD continue_status
= DBG_CONTINUE
;
1185 /* A specific PTID means `step only this thread id'. */
1186 int resume_all
= ptid_equal (ptid
, minus_one_ptid
);
1188 /* If we're continuing all threads, it's the current inferior that
1189 should be handled specially. */
1191 ptid
= inferior_ptid
;
1193 if (sig
!= TARGET_SIGNAL_0
)
1195 if (current_event
.dwDebugEventCode
!= EXCEPTION_DEBUG_EVENT
)
1197 DEBUG_EXCEPT(("Cannot continue with signal %d here.\n",sig
));
1199 else if (sig
== last_sig
)
1200 continue_status
= DBG_EXCEPTION_NOT_HANDLED
;
1203 /* This code does not seem to work, because
1204 the kernel does probably not consider changes in the ExceptionRecord
1205 structure when passing the exception to the inferior.
1206 Note that this seems possible in the exception handler itself. */
1209 for (i
= 0; xlate
[i
].them
!= -1; i
++)
1210 if (xlate
[i
].us
== sig
)
1212 current_event
.u
.Exception
.ExceptionRecord
.ExceptionCode
=
1214 continue_status
= DBG_EXCEPTION_NOT_HANDLED
;
1217 if (continue_status
== DBG_CONTINUE
)
1219 DEBUG_EXCEPT(("Cannot continue with signal %d.\n",sig
));
1223 DEBUG_EXCEPT(("Can only continue with recieved signal %d.\n",
1227 last_sig
= TARGET_SIGNAL_0
;
1229 DEBUG_EXEC (("gdb: windows_resume (pid=%d, tid=%ld, step=%d, sig=%d);\n",
1230 ptid_get_pid (ptid
), ptid_get_tid (ptid
), step
, sig
));
1232 /* Get context for currently selected thread */
1233 th
= thread_rec (ptid_get_tid (inferior_ptid
), FALSE
);
1238 /* Single step by setting t bit */
1239 windows_fetch_inferior_registers (ops
,
1240 get_current_regcache (),
1241 gdbarch_ps_regnum (current_gdbarch
));
1242 th
->context
.EFlags
|= FLAG_TRACE_BIT
;
1245 if (th
->context
.ContextFlags
)
1247 if (debug_registers_changed
)
1249 th
->context
.Dr0
= dr
[0];
1250 th
->context
.Dr1
= dr
[1];
1251 th
->context
.Dr2
= dr
[2];
1252 th
->context
.Dr3
= dr
[3];
1253 th
->context
.Dr6
= DR6_CLEAR_VALUE
;
1254 th
->context
.Dr7
= dr
[7];
1256 CHECK (SetThreadContext (th
->h
, &th
->context
));
1257 th
->context
.ContextFlags
= 0;
1261 /* Allow continuing with the same signal that interrupted us.
1262 Otherwise complain. */
1265 windows_continue (continue_status
, -1);
1267 windows_continue (continue_status
, ptid_get_tid (ptid
));
1270 /* Ctrl-C handler used when the inferior is not run in the same console. The
1271 handler is in charge of interrupting the inferior using DebugBreakProcess.
1272 Note that this function is not available prior to Windows XP. In this case
1273 we emit a warning. */
1275 ctrl_c_handler (DWORD event_type
)
1277 const int attach_flag
= current_inferior ()->attach_flag
;
1279 /* Only handle Ctrl-C event. Ignore others. */
1280 if (event_type
!= CTRL_C_EVENT
)
1283 /* If the inferior and the debugger share the same console, do nothing as
1284 the inferior has also received the Ctrl-C event. */
1285 if (!new_console
&& !attach_flag
)
1288 if (!DebugBreakProcess (current_process_handle
))
1290 Could not interrupt program. Press Ctrl-c in the program console."));
1292 /* Return true to tell that Ctrl-C has been handled. */
1296 /* Get the next event from the child. Return 1 if the event requires
1297 handling by WFI (or whatever). */
1299 get_windows_debug_event (struct target_ops
*ops
,
1300 int pid
, struct target_waitstatus
*ourstatus
)
1303 DWORD continue_status
, event_code
;
1305 static thread_info dummy_thread_info
;
1308 last_sig
= TARGET_SIGNAL_0
;
1310 if (!(debug_event
= WaitForDebugEvent (¤t_event
, 1000)))
1314 continue_status
= DBG_CONTINUE
;
1316 event_code
= current_event
.dwDebugEventCode
;
1317 ourstatus
->kind
= TARGET_WAITKIND_SPURIOUS
;
1319 have_saved_context
= 0;
1323 case CREATE_THREAD_DEBUG_EVENT
:
1324 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%x code=%s)\n",
1325 (unsigned) current_event
.dwProcessId
,
1326 (unsigned) current_event
.dwThreadId
,
1327 "CREATE_THREAD_DEBUG_EVENT"));
1328 if (saw_create
!= 1)
1330 struct inferior
*inf
;
1331 inf
= find_inferior_pid (current_event
.dwProcessId
);
1332 if (!saw_create
&& inf
->attach_flag
)
1334 /* Kludge around a Windows bug where first event is a create
1335 thread event. Caused when attached process does not have
1337 retval
= fake_create_process ();
1343 /* Record the existence of this thread */
1344 retval
= current_event
.dwThreadId
;
1345 th
= windows_add_thread (ptid_build (current_event
.dwProcessId
, 0,
1346 current_event
.dwThreadId
),
1347 current_event
.u
.CreateThread
.hThread
);
1350 case EXIT_THREAD_DEBUG_EVENT
:
1351 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
1352 (unsigned) current_event
.dwProcessId
,
1353 (unsigned) current_event
.dwThreadId
,
1354 "EXIT_THREAD_DEBUG_EVENT"));
1355 if (current_event
.dwThreadId
!= main_thread_id
)
1357 windows_delete_thread (ptid_build (current_event
.dwProcessId
, 0,
1358 current_event
.dwThreadId
));
1359 th
= &dummy_thread_info
;
1363 case CREATE_PROCESS_DEBUG_EVENT
:
1364 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
1365 (unsigned) current_event
.dwProcessId
,
1366 (unsigned) current_event
.dwThreadId
,
1367 "CREATE_PROCESS_DEBUG_EVENT"));
1368 CloseHandle (current_event
.u
.CreateProcessInfo
.hFile
);
1369 if (++saw_create
!= 1)
1372 current_process_handle
= current_event
.u
.CreateProcessInfo
.hProcess
;
1374 windows_delete_thread (ptid_build (current_event
.dwProcessId
, 0,
1376 main_thread_id
= current_event
.dwThreadId
;
1377 /* Add the main thread */
1378 th
= windows_add_thread (ptid_build (current_event
.dwProcessId
, 0,
1379 current_event
.dwThreadId
),
1380 current_event
.u
.CreateProcessInfo
.hThread
);
1381 retval
= current_event
.dwThreadId
;
1384 case EXIT_PROCESS_DEBUG_EVENT
:
1385 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
1386 (unsigned) current_event
.dwProcessId
,
1387 (unsigned) current_event
.dwThreadId
,
1388 "EXIT_PROCESS_DEBUG_EVENT"));
1389 if (saw_create
!= 1)
1391 ourstatus
->kind
= TARGET_WAITKIND_EXITED
;
1392 ourstatus
->value
.integer
= current_event
.u
.ExitProcess
.dwExitCode
;
1393 retval
= main_thread_id
;
1396 case LOAD_DLL_DEBUG_EVENT
:
1397 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
1398 (unsigned) current_event
.dwProcessId
,
1399 (unsigned) current_event
.dwThreadId
,
1400 "LOAD_DLL_DEBUG_EVENT"));
1401 CloseHandle (current_event
.u
.LoadDll
.hFile
);
1402 if (saw_create
!= 1)
1404 catch_errors (handle_load_dll
, NULL
, (char *) "", RETURN_MASK_ALL
);
1405 ourstatus
->kind
= TARGET_WAITKIND_LOADED
;
1406 ourstatus
->value
.integer
= 0;
1407 retval
= main_thread_id
;
1410 case UNLOAD_DLL_DEBUG_EVENT
:
1411 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
1412 (unsigned) current_event
.dwProcessId
,
1413 (unsigned) current_event
.dwThreadId
,
1414 "UNLOAD_DLL_DEBUG_EVENT"));
1415 if (saw_create
!= 1)
1417 catch_errors (handle_unload_dll
, NULL
, (char *) "", RETURN_MASK_ALL
);
1418 ourstatus
->kind
= TARGET_WAITKIND_LOADED
;
1419 ourstatus
->value
.integer
= 0;
1420 retval
= main_thread_id
;
1423 case EXCEPTION_DEBUG_EVENT
:
1424 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
1425 (unsigned) current_event
.dwProcessId
,
1426 (unsigned) current_event
.dwThreadId
,
1427 "EXCEPTION_DEBUG_EVENT"));
1428 if (saw_create
!= 1)
1430 switch (handle_exception (ourstatus
))
1433 continue_status
= DBG_EXCEPTION_NOT_HANDLED
;
1436 retval
= current_event
.dwThreadId
;
1440 continue_status
= -1;
1445 case OUTPUT_DEBUG_STRING_EVENT
: /* message from the kernel */
1446 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
1447 (unsigned) current_event
.dwProcessId
,
1448 (unsigned) current_event
.dwThreadId
,
1449 "OUTPUT_DEBUG_STRING_EVENT"));
1450 if (saw_create
!= 1)
1452 retval
= handle_output_debug_string (ourstatus
);
1456 if (saw_create
!= 1)
1458 printf_unfiltered ("gdb: kernel event for pid=%ld tid=%ld\n",
1459 (DWORD
) current_event
.dwProcessId
,
1460 (DWORD
) current_event
.dwThreadId
);
1461 printf_unfiltered (" unknown event code %ld\n",
1462 current_event
.dwDebugEventCode
);
1466 if (!retval
|| saw_create
!= 1)
1468 if (continue_status
== -1)
1469 windows_resume (ops
, minus_one_ptid
, 0, 1);
1471 CHECK (windows_continue (continue_status
, -1));
1475 inferior_ptid
= ptid_build (current_event
.dwProcessId
, 0,
1477 current_thread
= th
?: thread_rec (current_event
.dwThreadId
, TRUE
);
1484 /* Wait for interesting events to occur in the target process. */
1486 windows_wait (struct target_ops
*ops
,
1487 ptid_t ptid
, struct target_waitstatus
*ourstatus
)
1491 target_terminal_ours ();
1493 /* We loop when we get a non-standard exception rather than return
1494 with a SPURIOUS because resume can try and step or modify things,
1495 which needs a current_thread->h. But some of these exceptions mark
1496 the birth or death of threads, which mean that the current thread
1497 isn't necessarily what you think it is. */
1503 /* If the user presses Ctrl-c while the debugger is waiting
1504 for an event, he expects the debugger to interrupt his program
1505 and to get the prompt back. There are two possible situations:
1507 - The debugger and the program do not share the console, in
1508 which case the Ctrl-c event only reached the debugger.
1509 In that case, the ctrl_c handler will take care of interrupting
1510 the inferior. Note that this case is working starting with
1511 Windows XP. For Windows 2000, Ctrl-C should be pressed in the
1514 - The debugger and the program share the same console, in which
1515 case both debugger and inferior will receive the Ctrl-c event.
1516 In that case the ctrl_c handler will ignore the event, as the
1517 Ctrl-c event generated inside the inferior will trigger the
1518 expected debug event.
1520 FIXME: brobecker/2008-05-20: If the inferior receives the
1521 signal first and the delay until GDB receives that signal
1522 is sufficiently long, GDB can sometimes receive the SIGINT
1523 after we have unblocked the CTRL+C handler. This would
1524 lead to the debugger stopping prematurely while handling
1525 the new-thread event that comes with the handling of the SIGINT
1526 inside the inferior, and then stop again immediately when
1527 the user tries to resume the execution in the inferior.
1528 This is a classic race that we should try to fix one day. */
1529 SetConsoleCtrlHandler (&ctrl_c_handler
, TRUE
);
1530 retval
= get_windows_debug_event (ops
, pid
, ourstatus
);
1531 SetConsoleCtrlHandler (&ctrl_c_handler
, FALSE
);
1534 return ptid_build (current_event
.dwProcessId
, 0, retval
);
1539 if (deprecated_ui_loop_hook
!= NULL
)
1540 detach
= deprecated_ui_loop_hook (0);
1543 windows_kill_inferior (ops
);
1549 do_initial_windows_stuff (struct target_ops
*ops
, DWORD pid
, int attaching
)
1551 extern int stop_after_trap
;
1553 struct inferior
*inf
;
1554 struct thread_info
*tp
;
1556 last_sig
= TARGET_SIGNAL_0
;
1558 exception_count
= 0;
1559 open_process_used
= 0;
1560 debug_registers_changed
= 0;
1561 debug_registers_used
= 0;
1562 for (i
= 0; i
< sizeof (dr
) / sizeof (dr
[0]); i
++)
1565 cygwin_load_start
= cygwin_load_end
= 0;
1567 current_event
.dwProcessId
= pid
;
1568 memset (¤t_event
, 0, sizeof (current_event
));
1570 disable_breakpoints_in_shlibs ();
1571 windows_clear_solib ();
1572 clear_proceed_status ();
1573 init_wait_for_inferior ();
1575 inf
= add_inferior (pid
);
1576 inf
->attach_flag
= attaching
;
1578 /* Make the new process the current inferior, so terminal handling
1579 can rely on it. When attaching, we don't know about any thread
1580 id here, but that's OK --- nothing should be referencing the
1581 current thread until we report an event out of windows_wait. */
1582 inferior_ptid
= pid_to_ptid (pid
);
1584 terminal_init_inferior_with_pgrp (pid
);
1585 target_terminal_inferior ();
1587 inf
->stop_soon
= STOP_QUIETLY
;
1590 stop_after_trap
= 1;
1591 wait_for_inferior (0);
1592 tp
= inferior_thread ();
1593 if (tp
->stop_signal
!= TARGET_SIGNAL_TRAP
)
1594 resume (0, tp
->stop_signal
);
1599 inf
->stop_soon
= NO_STOP_QUIETLY
;
1600 stop_after_trap
= 0;
1604 /* Try to set or remove a user privilege to the current process. Return -1
1605 if that fails, the previous setting of that privilege otherwise.
1607 This code is copied from the Cygwin source code and rearranged to allow
1608 dynamically loading of the needed symbols from advapi32 which is only
1609 available on NT/2K/XP. */
1611 set_process_privilege (const char *privilege
, BOOL enable
)
1613 static HMODULE advapi32
= NULL
;
1614 static BOOL
WINAPI (*OpenProcessToken
)(HANDLE
, DWORD
, PHANDLE
);
1615 static BOOL
WINAPI (*LookupPrivilegeValue
)(LPCSTR
, LPCSTR
, PLUID
);
1616 static BOOL
WINAPI (*AdjustTokenPrivileges
)(HANDLE
, BOOL
, PTOKEN_PRIVILEGES
,
1617 DWORD
, PTOKEN_PRIVILEGES
, PDWORD
);
1619 HANDLE token_hdl
= NULL
;
1621 TOKEN_PRIVILEGES new_priv
, orig_priv
;
1625 if (GetVersion () >= 0x80000000) /* No security availbale on 9x/Me */
1630 if (!(advapi32
= LoadLibrary ("advapi32.dll")))
1632 if (!OpenProcessToken
)
1634 (void *) GetProcAddress (advapi32
, "OpenProcessToken");
1635 if (!LookupPrivilegeValue
)
1636 LookupPrivilegeValue
=
1637 (void *) GetProcAddress (advapi32
, "LookupPrivilegeValueA");
1638 if (!AdjustTokenPrivileges
)
1639 AdjustTokenPrivileges
=
1640 (void *) GetProcAddress (advapi32
, "AdjustTokenPrivileges");
1641 if (!OpenProcessToken
|| !LookupPrivilegeValue
|| !AdjustTokenPrivileges
)
1648 if (!OpenProcessToken (GetCurrentProcess (),
1649 TOKEN_QUERY
| TOKEN_ADJUST_PRIVILEGES
,
1653 if (!LookupPrivilegeValue (NULL
, privilege
, &restore_priv
))
1656 new_priv
.PrivilegeCount
= 1;
1657 new_priv
.Privileges
[0].Luid
= restore_priv
;
1658 new_priv
.Privileges
[0].Attributes
= enable
? SE_PRIVILEGE_ENABLED
: 0;
1660 if (!AdjustTokenPrivileges (token_hdl
, FALSE
, &new_priv
,
1661 sizeof orig_priv
, &orig_priv
, &size
))
1664 /* Disabled, otherwise every `attach' in an unprivileged user session
1665 would raise the "Failed to get SE_DEBUG_NAME privilege" warning in
1666 windows_attach(). */
1667 /* AdjustTokenPrivileges returns TRUE even if the privilege could not
1668 be enabled. GetLastError () returns an correct error code, though. */
1669 if (enable
&& GetLastError () == ERROR_NOT_ALL_ASSIGNED
)
1673 ret
= orig_priv
.Privileges
[0].Attributes
== SE_PRIVILEGE_ENABLED
? 1 : 0;
1677 CloseHandle (token_hdl
);
1682 /* Attach to process PID, then initialize for debugging it. */
1684 windows_attach (struct target_ops
*ops
, char *args
, int from_tty
)
1690 error_no_arg (_("process-id to attach"));
1692 if (set_process_privilege (SE_DEBUG_NAME
, TRUE
) < 0)
1694 printf_unfiltered ("Warning: Failed to get SE_DEBUG_NAME privilege\n");
1695 printf_unfiltered ("This can cause attach to fail on Windows NT/2K/XP\n");
1698 pid
= strtoul (args
, 0, 0); /* Windows pid */
1700 windows_init_thread_list ();
1701 ok
= DebugActiveProcess (pid
);
1707 /* Try fall back to Cygwin pid */
1708 pid
= cygwin_internal (CW_CYGWIN_PID_TO_WINPID
, pid
);
1711 ok
= DebugActiveProcess (pid
);
1716 error (_("Can't attach to process."));
1718 DebugSetProcessKillOnExit (FALSE
);
1722 char *exec_file
= (char *) get_exec_file (0);
1725 printf_unfiltered ("Attaching to program `%s', %s\n", exec_file
,
1726 target_pid_to_str (pid_to_ptid (pid
)));
1728 printf_unfiltered ("Attaching to %s\n",
1729 target_pid_to_str (pid_to_ptid (pid
)));
1731 gdb_flush (gdb_stdout
);
1734 do_initial_windows_stuff (ops
, pid
, 1);
1735 target_terminal_ours ();
1739 windows_detach (struct target_ops
*ops
, char *args
, int from_tty
)
1744 windows_resume (ops
, ptid
, 0, TARGET_SIGNAL_0
);
1746 if (!DebugActiveProcessStop (current_event
.dwProcessId
))
1748 error (_("Can't detach process %lu (error %lu)"),
1749 current_event
.dwProcessId
, GetLastError ());
1752 DebugSetProcessKillOnExit (FALSE
);
1754 if (detached
&& from_tty
)
1756 char *exec_file
= get_exec_file (0);
1759 printf_unfiltered ("Detaching from program: %s, Pid %lu\n", exec_file
,
1760 current_event
.dwProcessId
);
1761 gdb_flush (gdb_stdout
);
1764 inferior_ptid
= null_ptid
;
1765 detach_inferior (current_event
.dwProcessId
);
1767 unpush_target (ops
);
1771 windows_pid_to_exec_file (int pid
)
1773 static char path
[MAX_PATH
+ 1];
1776 /* Try to find exe name as symlink target of /proc/<pid>/exe */
1778 char procexe
[sizeof ("/proc/4294967295/exe")];
1779 sprintf (procexe
, "/proc/%u/exe", pid
);
1780 nchars
= readlink (procexe
, path
, sizeof(path
));
1781 if (nchars
> 0 && nchars
< sizeof (path
))
1783 path
[nchars
] = '\0'; /* Got it */
1788 /* If we get here then either Cygwin is hosed, this isn't a Cygwin version
1789 of gdb, or we're trying to debug a non-Cygwin windows executable. */
1790 if (!get_module_name (0, path
))
1796 /* Print status information about what we're accessing. */
1799 windows_files_info (struct target_ops
*ignore
)
1801 struct inferior
*inf
= current_inferior ();
1803 printf_unfiltered ("\tUsing the running image of %s %s.\n",
1804 inf
->attach_flag
? "attached" : "child",
1805 target_pid_to_str (inferior_ptid
));
1809 windows_open (char *arg
, int from_tty
)
1811 error (_("Use the \"run\" command to start a Unix child process."));
1814 /* Start an inferior windows child process and sets inferior_ptid to its pid.
1815 EXEC_FILE is the file to run.
1816 ALLARGS is a string containing the arguments to the program.
1817 ENV is the environment vector to pass. Errors reported with error(). */
1820 windows_create_inferior (struct target_ops
*ops
, char *exec_file
,
1821 char *allargs
, char **in_env
, int from_tty
)
1824 PROCESS_INFORMATION pi
;
1828 char real_path
[MAXPATHLEN
];
1830 char shell
[MAX_PATH
+ 1]; /* Path to shell */
1834 int ostdin
, ostdout
, ostderr
;
1838 const char *inferior_io_terminal
= get_inferior_io_terminal ();
1841 error (_("No executable specified, use `target exec'."));
1843 memset (&si
, 0, sizeof (si
));
1844 si
.cb
= sizeof (si
);
1849 flags
= DEBUG_ONLY_THIS_PROCESS
;
1850 cygwin_conv_to_win32_path (exec_file
, real_path
);
1856 sh
= getenv ("SHELL");
1859 cygwin_conv_to_win32_path (sh
, shell
);
1860 newallargs
= alloca (sizeof (" -c 'exec '") + strlen (exec_file
)
1861 + strlen (allargs
) + 2);
1862 sprintf (newallargs
, " -c 'exec %s %s'", exec_file
, allargs
);
1863 allargs
= newallargs
;
1865 flags
= DEBUG_PROCESS
;
1869 flags
= DEBUG_ONLY_THIS_PROCESS
;
1873 flags
|= CREATE_NEW_PROCESS_GROUP
;
1876 flags
|= CREATE_NEW_CONSOLE
;
1878 args
= alloca (strlen (toexec
) + strlen (allargs
) + 2);
1879 strcpy (args
, toexec
);
1881 strcat (args
, allargs
);
1884 /* Prepare the environment vars for CreateProcess. */
1885 cygwin_internal (CW_SYNC_WINENV
);
1887 if (!inferior_io_terminal
)
1888 tty
= ostdin
= ostdout
= ostderr
= -1;
1891 tty
= open (inferior_io_terminal
, O_RDWR
| O_NOCTTY
);
1894 print_sys_errmsg (inferior_io_terminal
, errno
);
1895 ostdin
= ostdout
= ostderr
= -1;
1908 if (!inferior_io_terminal
)
1909 tty
= INVALID_HANDLE_VALUE
;
1912 SECURITY_ATTRIBUTES sa
;
1913 sa
.nLength
= sizeof(sa
);
1914 sa
.lpSecurityDescriptor
= 0;
1915 sa
.bInheritHandle
= TRUE
;
1916 tty
= CreateFileA (inferior_io_terminal
, GENERIC_READ
| GENERIC_WRITE
,
1917 0, &sa
, OPEN_EXISTING
, FILE_ATTRIBUTE_NORMAL
, 0);
1918 if (tty
== INVALID_HANDLE_VALUE
)
1919 warning (_("Warning: Failed to open TTY %s, error %#x."),
1920 inferior_io_terminal
, (unsigned) GetLastError ());
1924 si
.hStdOutput
= tty
;
1926 si
.dwFlags
|= STARTF_USESTDHANDLES
;
1931 windows_init_thread_list ();
1932 ret
= CreateProcess (0,
1933 args
, /* command line */
1934 NULL
, /* Security */
1936 TRUE
, /* inherit handles */
1937 flags
, /* start flags */
1938 NULL
, /* environment */
1939 NULL
, /* current directory */
1955 if (tty
!= INVALID_HANDLE_VALUE
)
1960 error (_("Error creating process %s, (error %d)."),
1961 exec_file
, (unsigned) GetLastError ());
1963 CloseHandle (pi
.hThread
);
1964 CloseHandle (pi
.hProcess
);
1966 if (useshell
&& shell
[0] != '\0')
1971 do_initial_windows_stuff (ops
, pi
.dwProcessId
, 0);
1973 /* windows_continue (DBG_CONTINUE, -1); */
1977 windows_mourn_inferior (struct target_ops
*ops
)
1979 (void) windows_continue (DBG_CONTINUE
, -1);
1980 i386_cleanup_dregs();
1981 if (open_process_used
)
1983 CHECK (CloseHandle (current_process_handle
));
1984 open_process_used
= 0;
1986 unpush_target (ops
);
1987 generic_mourn_inferior ();
1990 /* Send a SIGINT to the process group. This acts just like the user typed a
1991 ^C on the controlling terminal. */
1994 windows_stop (ptid_t ptid
)
1996 DEBUG_EVENTS (("gdb: GenerateConsoleCtrlEvent (CTRLC_EVENT, 0)\n"));
1997 CHECK (GenerateConsoleCtrlEvent (CTRL_C_EVENT
, current_event
.dwProcessId
));
1998 registers_changed (); /* refresh register state */
2002 windows_xfer_memory (CORE_ADDR memaddr
, gdb_byte
*our
, int len
,
2003 int write
, struct mem_attrib
*mem
,
2004 struct target_ops
*target
)
2009 DEBUG_MEM (("gdb: write target memory, %d bytes at 0x%08lx\n",
2010 len
, (DWORD
) (uintptr_t) memaddr
));
2011 if (!WriteProcessMemory (current_process_handle
,
2012 (LPVOID
) (uintptr_t) memaddr
, our
,
2015 FlushInstructionCache (current_process_handle
,
2016 (LPCVOID
) (uintptr_t) memaddr
, len
);
2020 DEBUG_MEM (("gdb: read target memory, %d bytes at 0x%08lx\n",
2021 len
, (DWORD
) (uintptr_t) memaddr
));
2022 if (!ReadProcessMemory (current_process_handle
,
2023 (LPCVOID
) (uintptr_t) memaddr
, our
,
2031 windows_kill_inferior (struct target_ops
*ops
)
2033 CHECK (TerminateProcess (current_process_handle
, 0));
2037 if (!windows_continue (DBG_CONTINUE
, -1))
2039 if (!WaitForDebugEvent (¤t_event
, INFINITE
))
2041 if (current_event
.dwDebugEventCode
== EXIT_PROCESS_DEBUG_EVENT
)
2045 target_mourn_inferior (); /* or just windows_mourn_inferior? */
2049 windows_prepare_to_store (struct regcache
*regcache
)
2051 /* Do nothing, since we can store individual regs */
2055 windows_can_run (void)
2061 windows_close (int x
)
2063 DEBUG_EVENTS (("gdb: windows_close, inferior_ptid=%d\n",
2064 PIDGET (inferior_ptid
)));
2067 /* Convert pid to printable format. */
2069 windows_pid_to_str (struct target_ops
*ops
, ptid_t ptid
)
2071 static char buf
[80];
2073 if (ptid_get_tid (ptid
) != 0)
2075 snprintf (buf
, sizeof (buf
), "Thread %d.0x%lx",
2076 ptid_get_pid (ptid
), ptid_get_tid (ptid
));
2080 return normal_pid_to_str (ptid
);
2084 windows_xfer_shared_libraries (struct target_ops
*ops
,
2085 enum target_object object
, const char *annex
,
2086 gdb_byte
*readbuf
, const gdb_byte
*writebuf
,
2087 ULONGEST offset
, LONGEST len
)
2089 struct obstack obstack
;
2097 obstack_init (&obstack
);
2098 obstack_grow_str (&obstack
, "<library-list>\n");
2099 for (so
= solib_start
.next
; so
; so
= so
->next
)
2100 windows_xfer_shared_library (so
->so_name
, (CORE_ADDR
) (uintptr_t) so
->lm_info
->load_addr
,
2102 obstack_grow_str0 (&obstack
, "</library-list>\n");
2104 buf
= obstack_finish (&obstack
);
2105 len_avail
= strlen (buf
);
2106 if (offset
>= len_avail
)
2109 if (len
> len_avail
- offset
)
2110 len
= len_avail
- offset
;
2111 memcpy (readbuf
, buf
+ offset
, len
);
2113 obstack_free (&obstack
, NULL
);
2118 windows_xfer_partial (struct target_ops
*ops
, enum target_object object
,
2119 const char *annex
, gdb_byte
*readbuf
,
2120 const gdb_byte
*writebuf
, ULONGEST offset
, LONGEST len
)
2124 case TARGET_OBJECT_MEMORY
:
2126 return (*ops
->deprecated_xfer_memory
) (offset
, readbuf
,
2127 len
, 0/*read*/, NULL
, ops
);
2129 return (*ops
->deprecated_xfer_memory
) (offset
, (gdb_byte
*) writebuf
,
2130 len
, 1/*write*/, NULL
, ops
);
2133 case TARGET_OBJECT_LIBRARIES
:
2134 return windows_xfer_shared_libraries (ops
, object
, annex
, readbuf
,
2135 writebuf
, offset
, len
);
2138 if (ops
->beneath
!= NULL
)
2139 return ops
->beneath
->to_xfer_partial (ops
->beneath
, object
, annex
,
2140 readbuf
, writebuf
, offset
, len
);
2146 init_windows_ops (void)
2148 windows_ops
.to_shortname
= "child";
2149 windows_ops
.to_longname
= "Win32 child process";
2150 windows_ops
.to_doc
= "Win32 child process (started by the \"run\" command).";
2151 windows_ops
.to_open
= windows_open
;
2152 windows_ops
.to_close
= windows_close
;
2153 windows_ops
.to_attach
= windows_attach
;
2154 windows_ops
.to_attach_no_wait
= 1;
2155 windows_ops
.to_detach
= windows_detach
;
2156 windows_ops
.to_resume
= windows_resume
;
2157 windows_ops
.to_wait
= windows_wait
;
2158 windows_ops
.to_fetch_registers
= windows_fetch_inferior_registers
;
2159 windows_ops
.to_store_registers
= windows_store_inferior_registers
;
2160 windows_ops
.to_prepare_to_store
= windows_prepare_to_store
;
2161 windows_ops
.deprecated_xfer_memory
= windows_xfer_memory
;
2162 windows_ops
.to_xfer_partial
= windows_xfer_partial
;
2163 windows_ops
.to_files_info
= windows_files_info
;
2164 windows_ops
.to_insert_breakpoint
= memory_insert_breakpoint
;
2165 windows_ops
.to_remove_breakpoint
= memory_remove_breakpoint
;
2166 windows_ops
.to_terminal_init
= terminal_init_inferior
;
2167 windows_ops
.to_terminal_inferior
= terminal_inferior
;
2168 windows_ops
.to_terminal_ours_for_output
= terminal_ours_for_output
;
2169 windows_ops
.to_terminal_ours
= terminal_ours
;
2170 windows_ops
.to_terminal_save_ours
= terminal_save_ours
;
2171 windows_ops
.to_terminal_info
= child_terminal_info
;
2172 windows_ops
.to_kill
= windows_kill_inferior
;
2173 windows_ops
.to_create_inferior
= windows_create_inferior
;
2174 windows_ops
.to_mourn_inferior
= windows_mourn_inferior
;
2175 windows_ops
.to_can_run
= windows_can_run
;
2176 windows_ops
.to_thread_alive
= windows_thread_alive
;
2177 windows_ops
.to_pid_to_str
= windows_pid_to_str
;
2178 windows_ops
.to_stop
= windows_stop
;
2179 windows_ops
.to_stratum
= process_stratum
;
2180 windows_ops
.to_has_all_memory
= 1;
2181 windows_ops
.to_has_memory
= 1;
2182 windows_ops
.to_has_stack
= 1;
2183 windows_ops
.to_has_registers
= 1;
2184 windows_ops
.to_has_execution
= 1;
2185 windows_ops
.to_pid_to_exec_file
= windows_pid_to_exec_file
;
2186 i386_use_watchpoints (&windows_ops
);
2188 windows_ops
.to_magic
= OPS_MAGIC
;
2192 set_windows_aliases (char *argv0
)
2194 add_info_alias ("dll", "sharedlibrary", 1);
2198 _initialize_windows_nat (void)
2200 struct cmd_list_element
*c
;
2202 init_windows_ops ();
2204 c
= add_com ("dll-symbols", class_files
, dll_symbol_command
,
2205 _("Load dll library symbols from FILE."));
2206 set_cmd_completer (c
, filename_completer
);
2208 add_com_alias ("sharedlibrary", "dll-symbols", class_alias
, 1);
2211 add_setshow_boolean_cmd ("shell", class_support
, &useshell
, _("\
2212 Set use of shell to start subprocess."), _("\
2213 Show use of shell to start subprocess."), NULL
,
2215 NULL
, /* FIXME: i18n: */
2216 &setlist
, &showlist
);
2218 add_setshow_boolean_cmd ("cygwin-exceptions", class_support
, &cygwin_exceptions
, _("\
2219 Break when an exception is detected in the Cygwin DLL itself."), _("\
2220 Show whether gdb breaks on exceptions in the Cygwin DLL itself."), NULL
,
2222 NULL
, /* FIXME: i18n: */
2223 &setlist
, &showlist
);
2226 add_setshow_boolean_cmd ("new-console", class_support
, &new_console
, _("\
2227 Set creation of new console when creating child process."), _("\
2228 Show creation of new console when creating child process."), NULL
,
2230 NULL
, /* FIXME: i18n: */
2231 &setlist
, &showlist
);
2233 add_setshow_boolean_cmd ("new-group", class_support
, &new_group
, _("\
2234 Set creation of new group when creating child process."), _("\
2235 Show creation of new group when creating child process."), NULL
,
2237 NULL
, /* FIXME: i18n: */
2238 &setlist
, &showlist
);
2240 add_setshow_boolean_cmd ("debugexec", class_support
, &debug_exec
, _("\
2241 Set whether to display execution in child process."), _("\
2242 Show whether to display execution in child process."), NULL
,
2244 NULL
, /* FIXME: i18n: */
2245 &setlist
, &showlist
);
2247 add_setshow_boolean_cmd ("debugevents", class_support
, &debug_events
, _("\
2248 Set whether to display kernel events in child process."), _("\
2249 Show whether to display kernel events in child process."), NULL
,
2251 NULL
, /* FIXME: i18n: */
2252 &setlist
, &showlist
);
2254 add_setshow_boolean_cmd ("debugmemory", class_support
, &debug_memory
, _("\
2255 Set whether to display memory accesses in child process."), _("\
2256 Show whether to display memory accesses in child process."), NULL
,
2258 NULL
, /* FIXME: i18n: */
2259 &setlist
, &showlist
);
2261 add_setshow_boolean_cmd ("debugexceptions", class_support
,
2262 &debug_exceptions
, _("\
2263 Set whether to display kernel exceptions in child process."), _("\
2264 Show whether to display kernel exceptions in child process."), NULL
,
2266 NULL
, /* FIXME: i18n: */
2267 &setlist
, &showlist
);
2269 add_prefix_cmd ("w32", class_info
, info_w32_command
,
2270 _("Print information specific to Win32 debugging."),
2271 &info_w32_cmdlist
, "info w32 ", 0, &infolist
);
2273 add_cmd ("selector", class_info
, display_selectors
,
2274 _("Display selectors infos."),
2276 add_target (&windows_ops
);
2277 deprecated_init_ui_hook
= set_windows_aliases
;
2280 /* Hardware watchpoint support, adapted from go32-nat.c code. */
2282 /* Pass the address ADDR to the inferior in the I'th debug register.
2283 Here we just store the address in dr array, the registers will be
2284 actually set up when windows_continue is called. */
2286 cygwin_set_dr (int i
, CORE_ADDR addr
)
2289 internal_error (__FILE__
, __LINE__
,
2290 _("Invalid register %d in cygwin_set_dr.\n"), i
);
2292 debug_registers_changed
= 1;
2293 debug_registers_used
= 1;
2296 /* Pass the value VAL to the inferior in the DR7 debug control
2297 register. Here we just store the address in D_REGS, the watchpoint
2298 will be actually set up in windows_wait. */
2300 cygwin_set_dr7 (unsigned val
)
2303 debug_registers_changed
= 1;
2304 debug_registers_used
= 1;
2307 /* Get the value of the DR6 debug status register from the inferior.
2308 Here we just return the value stored in dr[6]
2309 by the last call to thread_rec for current_event.dwThreadId id. */
2311 cygwin_get_dr6 (void)
2316 /* Determine if the thread referenced by "ptid" is alive
2317 by "polling" it. If WaitForSingleObject returns WAIT_OBJECT_0
2318 it means that the thread has died. Otherwise it is assumed to be alive. */
2320 windows_thread_alive (struct target_ops
*ops
, ptid_t ptid
)
2324 gdb_assert (ptid_get_tid (ptid
) != 0);
2325 tid
= ptid_get_tid (ptid
);
2327 return WaitForSingleObject (thread_rec (tid
, FALSE
)->h
, 0) == WAIT_OBJECT_0
?
2332 _initialize_check_for_gdb_ini (void)
2335 if (inhibit_gdbinit
)
2338 homedir
= getenv ("HOME");
2342 char *oldini
= (char *) alloca (strlen (homedir
) +
2343 sizeof ("/gdb.ini"));
2344 strcpy (oldini
, homedir
);
2345 p
= strchr (oldini
, '\0');
2346 if (p
> oldini
&& p
[-1] != '/')
2348 strcpy (p
, "gdb.ini");
2349 if (access (oldini
, 0) == 0)
2351 int len
= strlen (oldini
);
2352 char *newini
= alloca (len
+ 1);
2353 sprintf (newini
, "%.*s.gdbinit",
2354 (int) (len
- (sizeof ("gdb.ini") - 1)), oldini
);
2355 warning (_("obsolete '%s' found. Rename to '%s'."), oldini
, newini
);
2360 /* Define dummy functions which always return error for the rare cases where
2361 these functions could not be found. */
2363 bad_DebugActiveProcessStop (DWORD w
)
2368 bad_DebugBreakProcess (HANDLE w
)
2373 bad_DebugSetProcessKillOnExit (BOOL w
)
2378 bad_EnumProcessModules (HANDLE w
, HMODULE
*x
, DWORD y
, LPDWORD z
)
2383 bad_GetModuleFileNameExA (HANDLE w
, HMODULE x
, LPSTR y
, DWORD z
)
2388 bad_GetModuleInformation (HANDLE w
, HMODULE x
, LPMODULEINFO y
, DWORD z
)
2393 /* Load any functions which may not be available in ancient versions
2396 _initialize_loadable (void)
2400 hm
= LoadLibrary ("kernel32.dll");
2403 dyn_DebugActiveProcessStop
= (void *)
2404 GetProcAddress (hm
, "DebugActiveProcessStop");
2405 dyn_DebugBreakProcess
= (void *)
2406 GetProcAddress (hm
, "DebugBreakProcess");
2407 dyn_DebugSetProcessKillOnExit
= (void *)
2408 GetProcAddress (hm
, "DebugSetProcessKillOnExit");
2411 /* Set variables to dummy versions of these processes if the function
2412 wasn't found in kernel32.dll. */
2413 if (!dyn_DebugBreakProcess
)
2414 dyn_DebugBreakProcess
= bad_DebugBreakProcess
;
2415 if (!dyn_DebugActiveProcessStop
|| !dyn_DebugSetProcessKillOnExit
)
2417 dyn_DebugActiveProcessStop
= bad_DebugActiveProcessStop
;
2418 dyn_DebugSetProcessKillOnExit
= bad_DebugSetProcessKillOnExit
;
2421 /* Load optional functions used for retrieving filename information
2422 associated with the currently debugged process or its dlls. */
2423 hm
= LoadLibrary ("psapi.dll");
2426 dyn_EnumProcessModules
= (void *)
2427 GetProcAddress (hm
, "EnumProcessModules");
2428 dyn_GetModuleInformation
= (void *)
2429 GetProcAddress (hm
, "GetModuleInformation");
2430 dyn_GetModuleFileNameExA
= (void *)
2431 GetProcAddress (hm
, "GetModuleFileNameExA");
2434 if (!dyn_EnumProcessModules
|| !dyn_GetModuleInformation
|| !dyn_GetModuleFileNameExA
)
2436 /* Set variables to dummy versions of these processes if the function
2437 wasn't found in psapi.dll. */
2438 dyn_EnumProcessModules
= bad_EnumProcessModules
;
2439 dyn_GetModuleInformation
= bad_GetModuleInformation
;
2440 dyn_GetModuleFileNameExA
= bad_GetModuleFileNameExA
;
2441 /* This will probably fail on Windows 9x/Me. Let the user know that we're
2442 missing some functionality. */
2443 warning(_("cannot automatically find executable file or library to read symbols. Use \"file\" or \"dll\" command to load executable/libraries directly."));