1 /* Target-vector operations for controlling win32 child processes, for GDB.
2 Copyright 1995, 1996, 1997, 1998 Free Software Foundation, Inc.
3 Contributed by Cygnus Support.
5 This file is part of GDB.
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 2 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without eve nthe implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program; if not, write to the Free Software
19 Foundation, Inc., 59 Temple Place - Suite 330,
20 Boston, MA 02111-1307, USA.
23 /* by Steve Chamberlain, sac@cygnus.com */
25 /* We assume we're being built with and will be used for cygwin. */
28 #include "frame.h" /* required by inferior.h */
35 #include <sys/types.h>
41 #else /* other WIN32 compiler */
48 #include "gdb_string.h"
49 #include "gdbthread.h"
51 #include <sys/param.h>
54 /* The ui's event loop. */
55 extern int (*ui_loop_hook
) PARAMS ((int signo
));
57 /* If we're not using the old Cygwin header file set, define the
58 following which never should have been in the generic Win32 API
59 headers in the first place since they were our own invention... */
60 #ifndef _GNU_H_WINDOWS_H
61 #define FLAG_TRACE_BIT 0x100
62 #define CONTEXT_DEBUGGER (CONTEXT_FULL | CONTEXT_FLOATING_POINT)
65 /* The string sent by cygwin when it processes a signal.
66 FIXME: This should be in a cygwin include file. */
67 #define CYGWIN_SIGNAL_STRING "cygwin: signal"
69 #define CHECK(x) check (x, __FILE__,__LINE__)
70 #define DEBUG_EXEC(x) if (debug_exec) printf x
71 #define DEBUG_EVENTS(x) if (debug_events) printf x
72 #define DEBUG_MEM(x) if (debug_memory) printf x
73 #define DEBUG_EXCEPT(x) if (debug_exceptions) printf x
75 /* Forward declaration */
76 extern struct target_ops child_ops
;
78 static void child_stop
PARAMS ((void));
79 static int win32_child_thread_alive
PARAMS ((int));
80 void child_kill_inferior
PARAMS ((void));
82 static int last_sig
= 0; /* Set if a signal was received from the
85 /* Thread information structure used to track information that is
86 not available in gdb's thread structure. */
87 typedef struct thread_info_struct
89 struct thread_info_struct
*next
;
98 static thread_info thread_head
=
101 /* The process and thread handles for the above context. */
103 static DEBUG_EVENT current_event
; /* The current debug event from
105 static HANDLE current_process_handle
; /* Currently executing process */
106 static thread_info
*current_thread
; /* Info on currently selected thread */
107 static DWORD main_thread_id
; /* Thread ID of the main thread */
109 /* Counts of things. */
110 static int exception_count
= 0;
111 static int event_count
= 0;
114 static int new_console
= 0;
115 static int new_group
= 0;
116 static int debug_exec
= 0; /* show execution */
117 static int debug_events
= 0; /* show events from kernel */
118 static int debug_memory
= 0; /* show target memory accesses */
119 static int debug_exceptions
= 0; /* show target exceptions */
121 /* This vector maps GDB's idea of a register's number into an address
122 in the win32 exception context vector.
124 It also contains the bit mask needed to load the register in question.
126 One day we could read a reg, we could inspect the context we
127 already have loaded, if it doesn't have the bit set that we need,
128 we read that set of registers in using GetThreadContext. If the
129 context already contains what we need, we just unpack it. Then to
130 write a register, first we have to ensure that the context contains
131 the other regs of the group, and then we copy the info in and set
134 #define context_offset(x) ((int)&(((CONTEXT *)NULL)->x))
135 static const int mappings
[] =
137 context_offset (Eax
),
138 context_offset (Ecx
),
139 context_offset (Edx
),
140 context_offset (Ebx
),
141 context_offset (Esp
),
142 context_offset (Ebp
),
143 context_offset (Esi
),
144 context_offset (Edi
),
145 context_offset (Eip
),
146 context_offset (EFlags
),
147 context_offset (SegCs
),
148 context_offset (SegSs
),
149 context_offset (SegDs
),
150 context_offset (SegEs
),
151 context_offset (SegFs
),
152 context_offset (SegGs
),
153 context_offset (FloatSave
.RegisterArea
[0 * 10]),
154 context_offset (FloatSave
.RegisterArea
[1 * 10]),
155 context_offset (FloatSave
.RegisterArea
[2 * 10]),
156 context_offset (FloatSave
.RegisterArea
[3 * 10]),
157 context_offset (FloatSave
.RegisterArea
[4 * 10]),
158 context_offset (FloatSave
.RegisterArea
[5 * 10]),
159 context_offset (FloatSave
.RegisterArea
[6 * 10]),
160 context_offset (FloatSave
.RegisterArea
[7 * 10]),
163 /* This vector maps the target's idea of an exception (extracted
164 from the DEBUG_EVENT structure) to GDB's idea. */
166 struct xlate_exception
169 enum target_signal us
;
172 static const struct xlate_exception
175 {EXCEPTION_ACCESS_VIOLATION
, TARGET_SIGNAL_SEGV
},
176 {STATUS_STACK_OVERFLOW
, TARGET_SIGNAL_SEGV
},
177 {EXCEPTION_BREAKPOINT
, TARGET_SIGNAL_TRAP
},
178 {DBG_CONTROL_C
, TARGET_SIGNAL_INT
},
179 {EXCEPTION_SINGLE_STEP
, TARGET_SIGNAL_TRAP
},
182 /* Find a thread record given a thread id.
183 If get_context then also retrieve the context for this
186 thread_rec (DWORD id
, int get_context
)
190 for (th
= &thread_head
; (th
= th
->next
) != NULL
;)
193 if (!th
->suspend_count
&& get_context
)
196 th
->suspend_count
= SuspendThread (th
->h
) + 1;
197 else if (get_context
< 0)
198 th
->suspend_count
= -1;
200 th
->context
.ContextFlags
= CONTEXT_DEBUGGER
;
201 GetThreadContext (th
->h
, &th
->context
);
209 /* Add a thread to the thread list */
211 child_add_thread (DWORD id
, HANDLE h
)
215 if ((th
= thread_rec (id
, FALSE
)))
218 th
= (thread_info
*) xmalloc (sizeof (*th
));
219 memset (th
, 0, sizeof (*th
));
222 th
->next
= thread_head
.next
;
223 thread_head
.next
= th
;
228 /* Clear out any old thread list and reintialize it to a
231 child_init_thread_list ()
233 thread_info
*th
= &thread_head
;
235 DEBUG_EVENTS (("gdb: child_init_thread_list\n"));
237 while (th
->next
!= NULL
)
239 thread_info
*here
= th
->next
;
240 th
->next
= here
->next
;
241 (void) CloseHandle (here
->h
);
246 /* Delete a thread from the list of threads */
248 child_delete_thread (DWORD id
)
253 printf_unfiltered ("[Deleting %s]\n", target_pid_to_str (id
));
256 for (th
= &thread_head
;
257 th
->next
!= NULL
&& th
->next
->id
!= id
;
261 if (th
->next
!= NULL
)
263 thread_info
*here
= th
->next
;
264 th
->next
= here
->next
;
265 CloseHandle (here
->h
);
271 check (BOOL ok
, const char *file
, int line
)
274 printf_filtered ("error return %s:%d was %d\n", file
, line
, GetLastError ());
278 do_child_fetch_inferior_registers (int r
)
281 supply_register (r
, ((char *) ¤t_thread
->context
) + mappings
[r
]);
284 for (r
= 0; r
< NUM_REGS
; r
++)
285 do_child_fetch_inferior_registers (r
);
290 child_fetch_inferior_registers (int r
)
292 current_thread
= thread_rec (inferior_pid
, TRUE
);
293 do_child_fetch_inferior_registers (r
);
297 do_child_store_inferior_registers (int r
)
300 read_register_gen (r
, ((char *) ¤t_thread
->context
) + mappings
[r
]);
303 for (r
= 0; r
< NUM_REGS
; r
++)
304 do_child_store_inferior_registers (r
);
308 /* Store a new register value into the current thread context */
310 child_store_inferior_registers (int r
)
312 current_thread
= thread_rec (inferior_pid
, TRUE
);
313 do_child_store_inferior_registers (r
);
316 /* Wait for child to do something. Return pid of child, or -1 in case
317 of error; store status through argument pointer OURSTATUS. */
320 handle_load_dll (PTR dummy
)
322 LOAD_DLL_DEBUG_INFO
*event
= ¤t_event
.u
.LoadDll
;
325 char dll_buf
[MAX_PATH
+ 1];
326 char *p
, *dll_name
= NULL
;
327 struct objfile
*objfile
;
328 MEMORY_BASIC_INFORMATION minfo
;
330 dll_buf
[0] = dll_buf
[sizeof (dll_buf
) - 1] = '\0';
332 /* The following code attempts to find the name of the dll by reading the
333 name from the processes memory. Unfortunately it doesn't work right.
334 Doing this the "right way" for Windows is very difficult. FIXME */
336 memset (&minfo
, 0, sizeof minfo
);
337 if (VirtualQueryEx (current_process_handle
, (LPCVOID
) event
->lpBaseOfDll
,
338 &minfo
, sizeof (minfo
)) && minfo
.BaseAddress
)
341 IMAGE_DOS_HEADER
*hmm0
= (IMAGE_DOS_HEADER
*) minfo
.BaseAddress
;
342 HMODULE hmm
= (HMODULE
) (((DWORD
) hmm0
) + hmm0
->e_lfanew
);
344 if ((len
= GetModuleFileName (hmm
, dll_buf
, MAX_PATH
)))
347 dll_name
[len
] = '\0';
352 /* Attempt to read the name of the dll that was detected.
353 This is documented to work only when actively debugging
354 a program. It will not work for attached processes. */
355 if (dll_name
== NULL
|| *dll_name
== '\0')
357 int size
= event
->fUnicode
? sizeof (WCHAR
) : sizeof (char);
361 ReadProcessMemory (current_process_handle
,
362 (LPCVOID
) event
->lpImageName
,
363 (char *) &dll_name_ptr
,
364 sizeof (dll_name_ptr
), &done
);
366 /* See if we could read the address of a string, and that the
367 address isn't null. */
369 if (done
!= sizeof (dll_name_ptr
) || !dll_name_ptr
)
374 ReadProcessMemory (current_process_handle
,
375 (LPCVOID
) (dll_name_ptr
+ len
* size
),
381 while ((b
[0] != 0 || b
[size
- 1] != 0) && done
== size
);
383 dll_name
= alloca (len
);
387 WCHAR
*unicode_dll_name
= (WCHAR
*) alloca (len
* sizeof (WCHAR
));
388 ReadProcessMemory (current_process_handle
,
389 (LPCVOID
) dll_name_ptr
,
391 len
* sizeof (WCHAR
),
394 WideCharToMultiByte (CP_ACP
, 0,
395 unicode_dll_name
, len
,
396 dll_name
, len
, 0, 0);
400 ReadProcessMemory (current_process_handle
,
401 (LPCVOID
) dll_name_ptr
,
411 while ((p
= strchr (dll_name
, '\\')))
414 /* The symbols in a dll are offset by 0x1000, which is the
415 the offset from 0 of the first byte in an image - because
416 of the file header and the section alignment.
418 FIXME: Is this the real reason that we need the 0x1000 ? */
420 printf_unfiltered ("%x:%s", event
->lpBaseOfDll
, dll_name
);
421 symbol_file_add (dll_name
, 0, (int) event
->lpBaseOfDll
+ 0x1000, 0, 0, 0, 0, 1);
422 printf_unfiltered ("\n");
427 /* Handle DEBUG_STRING output from child process.
428 Cygwin prepends its messages with a "cygwin:". Interpret this as
429 a Cygwin signal. Otherwise just print the string as a warning. */
431 handle_output_debug_string (struct target_waitstatus
*ourstatus
)
436 if (!target_read_string
437 ((CORE_ADDR
) current_event
.u
.DebugString
.lpDebugStringData
, &s
, 1024, 0)
441 if (strncmp (s
, CYGWIN_SIGNAL_STRING
, sizeof (CYGWIN_SIGNAL_STRING
) - 1))
448 /*last_sig = */ strtol (s
+ sizeof (CYGWIN_SIGNAL_STRING
) - 1, &p
, 0);
449 gotasig
= target_signal_from_host (last_sig
);
450 ourstatus
->value
.sig
= gotasig
;
452 ourstatus
->kind
= TARGET_WAITKIND_STOPPED
;
460 handle_exception (struct target_waitstatus
*ourstatus
)
466 ourstatus
->kind
= TARGET_WAITKIND_STOPPED
;
468 /* Record the context of the current thread */
469 th
= thread_rec (current_event
.dwThreadId
, -1);
471 switch (current_event
.u
.Exception
.ExceptionRecord
.ExceptionCode
)
473 case EXCEPTION_ACCESS_VIOLATION
:
474 DEBUG_EXCEPT (("gdb: Target exception ACCESS_VIOLATION at 0x%08x\n",
475 current_event
.u
.Exception
.ExceptionRecord
.ExceptionAddress
));
476 ourstatus
->value
.sig
= TARGET_SIGNAL_SEGV
;
478 case STATUS_STACK_OVERFLOW
:
479 DEBUG_EXCEPT (("gdb: Target exception STACK_OVERFLOW at 0x%08x\n",
480 current_event
.u
.Exception
.ExceptionRecord
.ExceptionAddress
));
481 ourstatus
->value
.sig
= TARGET_SIGNAL_SEGV
;
483 case EXCEPTION_BREAKPOINT
:
484 DEBUG_EXCEPT (("gdb: Target exception BREAKPOINT at 0x%08x\n",
485 current_event
.u
.Exception
.ExceptionRecord
.ExceptionAddress
));
486 ourstatus
->value
.sig
= TARGET_SIGNAL_TRAP
;
489 DEBUG_EXCEPT (("gdb: Target exception CONTROL_C at 0x%08x\n",
490 current_event
.u
.Exception
.ExceptionRecord
.ExceptionAddress
));
491 ourstatus
->value
.sig
= TARGET_SIGNAL_INT
;
492 /* User typed CTRL-C. Continue with this status */
493 last_sig
= SIGINT
; /* FIXME - should check pass state */
495 case EXCEPTION_SINGLE_STEP
:
496 DEBUG_EXCEPT (("gdb: Target exception SINGLE_STEP at 0x%08x\n",
497 current_event
.u
.Exception
.ExceptionRecord
.ExceptionAddress
));
498 ourstatus
->value
.sig
= TARGET_SIGNAL_TRAP
;
501 /* This may be a structured exception handling exception. In
502 that case, we want to let the program try to handle it, and
503 only break if we see the exception a second time. */
504 if (current_event
.u
.Exception
.dwFirstChance
)
507 printf_unfiltered ("gdb: unknown target exception 0x%08x at 0x%08x\n",
508 current_event
.u
.Exception
.ExceptionRecord
.ExceptionCode
,
509 current_event
.u
.Exception
.ExceptionRecord
.ExceptionAddress
);
510 ourstatus
->value
.sig
= TARGET_SIGNAL_UNKNOWN
;
517 /* Resume all artificially suspended threads if we are continuing
520 child_continue (DWORD continue_status
, int id
)
526 DEBUG_EVENTS (("ContinueDebugEvent (cpid=%d, ctid=%d, DBG_CONTINUE);\n",
527 current_event
.dwProcessId
, current_event
.dwThreadId
));
528 res
= ContinueDebugEvent (current_event
.dwProcessId
,
529 current_event
.dwThreadId
,
532 for (th
= &thread_head
; (th
= th
->next
) != NULL
;)
533 if (((id
== -1) || (id
== th
->id
)) && th
->suspend_count
)
535 for (i
= 0; i
< th
->suspend_count
; i
++)
536 (void) ResumeThread (th
->h
);
537 th
->suspend_count
= 0;
544 child_wait (int pid
, struct target_waitstatus
*ourstatus
)
546 /* We loop when we get a non-standard exception rather than return
547 with a SPURIOUS because resume can try and step or modify things,
548 which needs a current_thread->h. But some of these exceptions mark
549 the birth or death of threads, which mean that the current thread
550 isn't necessarily what you think it is. */
554 DWORD continue_status
;
555 BOOL debug_event
= WaitForDebugEvent (¤t_event
, 20);
564 continue_status
= DBG_CONTINUE
;
566 switch (current_event
.dwDebugEventCode
)
568 case CREATE_THREAD_DEBUG_EVENT
:
569 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%x code=%s)\n",
570 current_event
.dwProcessId
, current_event
.dwThreadId
,
571 "CREATE_THREAD_DEBUG_EVENT"));
572 /* Record the existence of this thread */
573 child_add_thread (current_event
.dwThreadId
,
574 current_event
.u
.CreateThread
.hThread
);
576 printf_unfiltered ("[New %s]\n",
577 target_pid_to_str (current_event
.dwThreadId
));
580 case EXIT_THREAD_DEBUG_EVENT
:
581 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
582 current_event
.dwProcessId
, current_event
.dwThreadId
,
583 "EXIT_THREAD_DEBUG_EVENT"));
584 child_delete_thread (current_event
.dwThreadId
);
587 case CREATE_PROCESS_DEBUG_EVENT
:
588 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
589 current_event
.dwProcessId
, current_event
.dwThreadId
,
590 "CREATE_PROCESS_DEBUG_EVENT"));
591 current_process_handle
= current_event
.u
.CreateProcessInfo
.hProcess
;
593 main_thread_id
= inferior_pid
= current_event
.dwThreadId
;
594 /* Add the main thread */
595 current_thread
= child_add_thread (inferior_pid
,
596 current_event
.u
.CreateProcessInfo
.hThread
);
599 case EXIT_PROCESS_DEBUG_EVENT
:
600 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
601 current_event
.dwProcessId
, current_event
.dwThreadId
,
602 "EXIT_PROCESS_DEBUG_EVENT"));
603 ourstatus
->kind
= TARGET_WAITKIND_EXITED
;
604 ourstatus
->value
.integer
= current_event
.u
.ExitProcess
.dwExitCode
;
605 CloseHandle (current_process_handle
);
606 return current_event
.dwProcessId
;
609 case LOAD_DLL_DEBUG_EVENT
:
610 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
611 current_event
.dwProcessId
, current_event
.dwThreadId
,
612 "LOAD_DLL_DEBUG_EVENT"));
613 catch_errors (handle_load_dll
, NULL
, "", RETURN_MASK_ALL
);
614 registers_changed (); /* mark all regs invalid */
617 case UNLOAD_DLL_DEBUG_EVENT
:
618 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
619 current_event
.dwProcessId
, current_event
.dwThreadId
,
620 "UNLOAD_DLL_DEBUG_EVENT"));
621 break; /* FIXME: don't know what to do here */
623 case EXCEPTION_DEBUG_EVENT
:
624 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
625 current_event
.dwProcessId
, current_event
.dwThreadId
,
626 "EXCEPTION_DEBUG_EVENT"));
627 if (handle_exception (ourstatus
))
628 return current_event
.dwThreadId
;
629 continue_status
= DBG_EXCEPTION_NOT_HANDLED
;
632 case OUTPUT_DEBUG_STRING_EVENT
: /* message from the kernel */
633 DEBUG_EVENTS (("gdb: kernel event for pid=%d tid=%d code=%s)\n",
634 current_event
.dwProcessId
, current_event
.dwThreadId
,
635 "OUTPUT_DEBUG_STRING_EVENT"));
636 if (handle_output_debug_string (ourstatus
))
637 return main_thread_id
;
640 printf_unfiltered ("gdb: kernel event for pid=%d tid=%d\n",
641 current_event
.dwProcessId
,
642 current_event
.dwThreadId
);
643 printf_unfiltered (" unknown event code %d\n",
644 current_event
.dwDebugEventCode
);
648 CHECK (child_continue (continue_status
, -1));
654 if (ui_loop_hook
!= NULL
)
655 detach
= ui_loop_hook (0);
658 child_kill_inferior ();
663 /* Attach to process PID, then initialize for debugging it. */
666 child_attach (args
, from_tty
)
673 error_no_arg ("process-id to attach");
675 current_event
.dwProcessId
= strtoul (args
, 0, 0);
677 ok
= DebugActiveProcess (current_event
.dwProcessId
);
680 error ("Can't attach to process.");
687 char *exec_file
= (char *) get_exec_file (0);
690 printf_unfiltered ("Attaching to program `%s', %s\n", exec_file
,
691 target_pid_to_str (current_event
.dwProcessId
));
693 printf_unfiltered ("Attaching to %s\n",
694 target_pid_to_str (current_event
.dwProcessId
));
696 gdb_flush (gdb_stdout
);
699 push_target (&child_ops
);
703 child_detach (args
, from_tty
)
709 char *exec_file
= get_exec_file (0);
712 printf_unfiltered ("Detaching from program: %s %s\n", exec_file
,
713 target_pid_to_str (inferior_pid
));
714 gdb_flush (gdb_stdout
);
717 unpush_target (&child_ops
);
720 /* Print status information about what we're accessing. */
723 child_files_info (ignore
)
724 struct target_ops
*ignore
;
726 printf_unfiltered ("\tUsing the running image of %s %s.\n",
727 attach_flag
? "attached" : "child", target_pid_to_str (inferior_pid
));
732 child_open (arg
, from_tty
)
736 error ("Use the \"run\" command to start a Unix child process.");
739 /* Start an inferior win32 child process and sets inferior_pid to its pid.
740 EXEC_FILE is the file to run.
741 ALLARGS is a string containing the arguments to the program.
742 ENV is the environment vector to pass. Errors reported with error(). */
745 child_create_inferior (exec_file
, allargs
, env
)
750 char real_path
[MAXPATHLEN
];
757 PROCESS_INFORMATION pi
;
758 struct target_waitstatus dummy
;
765 error ("No executable specified, use `target exec'.\n");
768 memset (&si
, 0, sizeof (si
));
771 cygwin32_conv_to_win32_path (exec_file
, real_path
);
773 flags
= DEBUG_ONLY_THIS_PROCESS
;
776 flags
|= CREATE_NEW_PROCESS_GROUP
;
779 flags
|= CREATE_NEW_CONSOLE
;
781 args
= alloca (strlen (real_path
) + strlen (allargs
) + 2);
783 strcpy (args
, real_path
);
786 strcat (args
, allargs
);
788 /* Prepare the environment vars for CreateProcess. */
790 /* This code use to assume all env vars were file names and would
791 translate them all to win32 style. That obviously doesn't work in the
792 general case. The current rule is that we only translate PATH.
793 We need to handle PATH because we're about to call CreateProcess and
794 it uses PATH to find DLL's. Fortunately PATH has a well-defined value
795 in both posix and win32 environments. cygwin.dll will change it back
796 to posix style if necessary. */
798 static const char *conv_path_names
[] =
804 /* CreateProcess takes the environment list as a null terminated set of
805 strings (i.e. two nulls terminate the list). */
807 /* Get total size for env strings. */
808 for (envlen
= 0, i
= 0; env
[i
] && *env
[i
]; i
++)
812 for (j
= 0; conv_path_names
[j
]; j
++)
814 len
= strlen (conv_path_names
[j
]);
815 if (strncmp (conv_path_names
[j
], env
[i
], len
) == 0)
817 if (cygwin32_posix_path_list_p (env
[i
] + len
))
819 + cygwin32_posix_to_win32_path_list_buf_size (env
[i
] + len
);
821 envlen
+= strlen (env
[i
]) + 1;
825 if (conv_path_names
[j
] == NULL
)
826 envlen
+= strlen (env
[i
]) + 1;
829 winenv
= alloca (envlen
+ 1);
831 /* Copy env strings into new buffer. */
832 for (temp
= winenv
, i
= 0; env
[i
] && *env
[i
]; i
++)
836 for (j
= 0; conv_path_names
[j
]; j
++)
838 len
= strlen (conv_path_names
[j
]);
839 if (strncmp (conv_path_names
[j
], env
[i
], len
) == 0)
841 if (cygwin32_posix_path_list_p (env
[i
] + len
))
843 memcpy (temp
, env
[i
], len
);
844 cygwin32_posix_to_win32_path_list (env
[i
] + len
, temp
+ len
);
847 strcpy (temp
, env
[i
]);
851 if (conv_path_names
[j
] == NULL
)
852 strcpy (temp
, env
[i
]);
854 temp
+= strlen (temp
) + 1;
857 /* Final nil string to terminate new env. */
861 ret
= CreateProcess (0,
862 args
, /* command line */
865 TRUE
, /* inherit handles */
866 flags
, /* start flags */
868 NULL
, /* current directory */
872 error ("Error creating process %s, (error %d)\n", exec_file
, GetLastError ());
877 current_process_handle
= pi
.hProcess
;
878 current_event
.dwProcessId
= pi
.dwProcessId
;
879 memset (¤t_event
, 0, sizeof (current_event
));
880 inferior_pid
= current_event
.dwThreadId
= pi
.dwThreadId
;
881 push_target (&child_ops
);
882 child_init_thread_list ();
883 init_wait_for_inferior ();
884 clear_proceed_status ();
885 target_terminal_init ();
886 target_terminal_inferior ();
888 /* Ignore the first trap */
889 child_wait (inferior_pid
, &dummy
);
891 proceed ((CORE_ADDR
) - 1, TARGET_SIGNAL_0
, 0);
895 child_mourn_inferior ()
897 (void) child_continue (DBG_CONTINUE
, -1);
898 unpush_target (&child_ops
);
899 generic_mourn_inferior ();
902 /* Send a SIGINT to the process group. This acts just like the user typed a
903 ^C on the controlling terminal. */
908 DEBUG_EVENTS (("gdb: GenerateConsoleCtrlEvent (CTRLC_EVENT, 0)\n"));
909 CHECK (GenerateConsoleCtrlEvent (CTRL_C_EVENT
, 0));
910 registers_changed (); /* refresh register state */
914 child_xfer_memory (CORE_ADDR memaddr
, char *our
, int len
,
915 int write
, struct target_ops
*target
)
920 DEBUG_MEM (("gdb: write target memory, %d bytes at 0x%08x\n",
922 WriteProcessMemory (current_process_handle
, (LPVOID
) memaddr
, our
,
924 FlushInstructionCache (current_process_handle
, (LPCVOID
) memaddr
, len
);
928 DEBUG_MEM (("gdb: read target memory, %d bytes at 0x%08x\n",
930 ReadProcessMemory (current_process_handle
, (LPCVOID
) memaddr
, our
, len
,
937 child_kill_inferior (void)
939 CHECK (TerminateProcess (current_process_handle
, 0));
943 if (!child_continue (DBG_CONTINUE
, -1))
945 if (!WaitForDebugEvent (¤t_event
, INFINITE
))
947 if (current_event
.dwDebugEventCode
== EXIT_PROCESS_DEBUG_EVENT
)
951 CHECK (CloseHandle (current_process_handle
));
953 /* this may fail in an attached process so don't check. */
954 (void) CloseHandle (current_thread
->h
);
955 target_mourn_inferior (); /* or just child_mourn_inferior? */
959 child_resume (int pid
, int step
, enum target_signal sig
)
963 DWORD continue_status
= last_sig
> 0 && last_sig
< NSIG
?
964 DBG_EXCEPTION_NOT_HANDLED
: DBG_CONTINUE
;
966 DEBUG_EXEC (("gdb: child_resume (pid=%d, step=%d, sig=%d);\n",
969 /* Get context for currently selected thread */
970 th
= thread_rec (current_event
.dwThreadId
, FALSE
);
974 /* Single step by setting t bit */
975 child_fetch_inferior_registers (PS_REGNUM
);
976 th
->context
.EFlags
|= FLAG_TRACE_BIT
;
980 if (th
->context
.ContextFlags
)
982 CHECK (SetThreadContext (th
->h
, &th
->context
));
983 th
->context
.ContextFlags
= 0;
986 /* Allow continuing with the same signal that interrupted us.
987 Otherwise complain. */
988 if (sig
&& sig
!= last_sig
)
989 fprintf_unfiltered (gdb_stderr
, "Can't send signals to the child. signal %d\n", sig
);
992 child_continue (continue_status
, pid
);
996 child_prepare_to_store ()
998 /* Do nothing, since we can store individual regs */
1010 DEBUG_EVENTS (("gdb: child_close, inferior_pid=%d\n", inferior_pid
));
1013 struct target_ops child_ops
;
1016 init_child_ops (void)
1018 child_ops
.to_shortname
= "child";
1019 child_ops
.to_longname
= "Win32 child process";
1020 child_ops
.to_doc
= "Win32 child process (started by the \"run\" command).";
1021 child_ops
.to_open
= child_open
;
1022 child_ops
.to_close
= child_close
;
1023 child_ops
.to_attach
= child_attach
;
1024 child_ops
.to_detach
= child_detach
;
1025 child_ops
.to_resume
= child_resume
;
1026 child_ops
.to_wait
= child_wait
;
1027 child_ops
.to_fetch_registers
= child_fetch_inferior_registers
;
1028 child_ops
.to_store_registers
= child_store_inferior_registers
;
1029 child_ops
.to_prepare_to_store
= child_prepare_to_store
;
1030 child_ops
.to_xfer_memory
= child_xfer_memory
;
1031 child_ops
.to_files_info
= child_files_info
;
1032 child_ops
.to_insert_breakpoint
= memory_insert_breakpoint
;
1033 child_ops
.to_remove_breakpoint
= memory_remove_breakpoint
;
1034 child_ops
.to_terminal_init
= terminal_init_inferior
;
1035 child_ops
.to_terminal_inferior
= terminal_inferior
;
1036 child_ops
.to_terminal_ours_for_output
= terminal_ours_for_output
;
1037 child_ops
.to_terminal_ours
= terminal_ours
;
1038 child_ops
.to_terminal_info
= child_terminal_info
;
1039 child_ops
.to_kill
= child_kill_inferior
;
1040 child_ops
.to_load
= 0;
1041 child_ops
.to_lookup_symbol
= 0;
1042 child_ops
.to_create_inferior
= child_create_inferior
;
1043 child_ops
.to_mourn_inferior
= child_mourn_inferior
;
1044 child_ops
.to_can_run
= child_can_run
;
1045 child_ops
.to_notice_signals
= 0;
1046 child_ops
.to_thread_alive
= win32_child_thread_alive
;
1047 child_ops
.to_stop
= child_stop
;
1048 child_ops
.to_stratum
= process_stratum
;
1049 child_ops
.DONT_USE
= 0;
1050 child_ops
.to_has_all_memory
= 1;
1051 child_ops
.to_has_memory
= 1;
1052 child_ops
.to_has_stack
= 1;
1053 child_ops
.to_has_registers
= 1;
1054 child_ops
.to_has_execution
= 1;
1055 child_ops
.to_sections
= 0;
1056 child_ops
.to_sections_end
= 0;
1057 child_ops
.to_magic
= OPS_MAGIC
;
1061 _initialize_inftarg ()
1063 struct cmd_list_element
*c
;
1067 (add_set_cmd ("new-console", class_support
, var_boolean
,
1068 (char *) &new_console
,
1069 "Set creation of new console when creating child process.",
1074 (add_set_cmd ("new-group", class_support
, var_boolean
,
1075 (char *) &new_group
,
1076 "Set creation of new group when creating child process.",
1081 (add_set_cmd ("debugexec", class_support
, var_boolean
,
1082 (char *) &debug_exec
,
1083 "Set whether to display execution in child process.",
1088 (add_set_cmd ("debugevents", class_support
, var_boolean
,
1089 (char *) &debug_events
,
1090 "Set whether to display kernel events in child process.",
1095 (add_set_cmd ("debugmemory", class_support
, var_boolean
,
1096 (char *) &debug_memory
,
1097 "Set whether to display memory accesses in child process.",
1102 (add_set_cmd ("debugexceptions", class_support
, var_boolean
,
1103 (char *) &debug_exceptions
,
1104 "Set whether to display kernel exceptions in child process.",
1108 add_target (&child_ops
);
1111 /* Determine if the thread referenced by "pid" is alive
1112 by "polling" it. If WaitForSingleObject returns WAIT_OBJECT_0
1113 it means that the pid has died. Otherwise it is assumed to be alive. */
1115 win32_child_thread_alive (int pid
)
1117 return WaitForSingleObject (thread_rec (pid
, FALSE
)->h
, 0) == WAIT_OBJECT_0
?
1121 /* Convert pid to printable format. */
1123 cygwin_pid_to_str (int pid
)
1125 static char buf
[80];
1126 if (pid
== current_event
.dwProcessId
)
1127 sprintf (buf
, "process %d", pid
);
1129 sprintf (buf
, "thread %d.0x%x", current_event
.dwProcessId
, pid
);