2001-02-14 Michael Chastain <chastain@redhat.com>
[deliverable/binutils-gdb.git] / gdb / go32-nat.c
CommitLineData
e49d4fa6 1/* Native debugging support for Intel x86 running DJGPP.
8e65ff28 2 Copyright 1997, 1999, 2001 Free Software Foundation, Inc.
e49d4fa6
SS
3 Written by Robert Hoehne.
4
c5aa993b 5 This file is part of GDB.
e49d4fa6 6
c5aa993b
JM
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.
e49d4fa6 11
c5aa993b
JM
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
e49d4fa6 16
c5aa993b
JM
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. */
e49d4fa6
SS
21
22#include <fcntl.h>
23
24#include "defs.h"
e49d4fa6 25#include "inferior.h"
03f2053f 26#include "gdb_wait.h"
e49d4fa6
SS
27#include "gdbcore.h"
28#include "command.h"
29#include "floatformat.h"
0fff5247 30#include "buildsym.h"
e49d4fa6 31
c5aa993b 32#include <stdio.h> /* required for __DJGPP_MINOR__ */
e49d4fa6
SS
33#include <stdlib.h>
34#include <string.h>
53a5351d 35#include <errno.h>
c2c6d25f 36#include <unistd.h>
53a5351d
JM
37#include <io.h>
38#include <dpmi.h>
e49d4fa6
SS
39#include <debug/v2load.h>
40#include <debug/dbgcom.h>
53a5351d
JM
41#if __DJGPP_MINOR__ > 2
42#include <debug/redir.h>
43#endif
e49d4fa6 44
b83266a0
SS
45#if __DJGPP_MINOR__ < 3
46/* This code will be provided from DJGPP 2.03 on. Until then I code it
47 here */
c5aa993b
JM
48typedef struct
49 {
50 unsigned short sig0;
51 unsigned short sig1;
52 unsigned short sig2;
53 unsigned short sig3;
54 unsigned short exponent:15;
55 unsigned short sign:1;
56 }
57NPXREG;
58
59typedef struct
60 {
61 unsigned int control;
62 unsigned int status;
63 unsigned int tag;
64 unsigned int eip;
65 unsigned int cs;
66 unsigned int dataptr;
67 unsigned int datasel;
68 NPXREG reg[8];
69 }
70NPX;
b83266a0
SS
71
72static NPX npx;
73
c5aa993b
JM
74static void save_npx (void); /* Save the FPU of the debugged program */
75static void load_npx (void); /* Restore the FPU of the debugged program */
b83266a0
SS
76
77/* ------------------------------------------------------------------------- */
78/* Store the contents of the NPX in the global variable `npx'. */
c5aa993b 79/* *INDENT-OFF* */
b83266a0
SS
80
81static void
82save_npx (void)
83{
84 asm ("inb $0xa0, %%al
c5aa993b
JM
85 testb $0x20, %%al
86 jz 1f
87 xorb %% al, %%al
88 outb %% al, $0xf0
89 movb $0x20, %%al
90 outb %% al, $0xa0
91 outb %% al, $0x20
b83266a0 921:
c5aa993b
JM
93 fnsave % 0
94 fwait "
95: "=m" (npx)
96: /* No input */
97: "%eax");
b83266a0 98}
c5aa993b
JM
99
100/* *INDENT-ON* */
101
102
103
104
105
b83266a0
SS
106/* ------------------------------------------------------------------------- */
107/* Reload the contents of the NPX from the global variable `npx'. */
108
109static void
110load_npx (void)
111{
c5aa993b 112asm ("frstor %0":"=m" (npx));
b83266a0 113}
53a5351d
JM
114/* ------------------------------------------------------------------------- */
115/* Stubs for the missing redirection functions. */
116typedef struct {
117 char *command;
118 int redirected;
119} cmdline_t;
120
121void redir_cmdline_delete (cmdline_t *ptr) {ptr->redirected = 0;}
122int redir_cmdline_parse (const char *args, cmdline_t *ptr)
123{
124 return -1;
125}
126int redir_to_child (cmdline_t *ptr)
127{
128 return 1;
129}
130int redir_to_debugger (cmdline_t *ptr)
131{
132 return 1;
133}
134int redir_debug_init (cmdline_t *ptr) { return 0; }
b83266a0
SS
135#endif /* __DJGPP_MINOR < 3 */
136
e49d4fa6
SS
137extern void _initialize_go32_nat (void);
138
53a5351d
JM
139typedef enum { wp_insert, wp_remove, wp_count } wp_op;
140
141/* This holds the current reference counts for each debug register. */
142static int dr_ref_count[4];
143
e49d4fa6
SS
144extern char **environ;
145
146#define SOME_PID 42
147
e49d4fa6 148static int prog_has_started = 0;
c5aa993b
JM
149static void go32_open (char *name, int from_tty);
150static void go32_close (int quitting);
151static void go32_attach (char *args, int from_tty);
152static void go32_detach (char *args, int from_tty);
153static void go32_resume (int pid, int step, enum target_signal siggnal);
154static int go32_wait (int pid, struct target_waitstatus *status);
155static void go32_fetch_registers (int regno);
156static void store_register (int regno);
157static void go32_store_registers (int regno);
158static void go32_prepare_to_store (void);
159static int go32_xfer_memory (CORE_ADDR memaddr, char *myaddr, int len,
a17b5c4e
EZ
160 int write,
161 struct mem_attrib *attrib,
162 struct target_ops *target);
c5aa993b
JM
163static void go32_files_info (struct target_ops *target);
164static void go32_stop (void);
165static void go32_kill_inferior (void);
166static void go32_create_inferior (char *exec_file, char *args, char **env);
53a5351d 167static void cleanup_dregs (void);
c5aa993b
JM
168static void go32_mourn_inferior (void);
169static int go32_can_run (void);
53a5351d
JM
170static int go32_insert_aligned_watchpoint (CORE_ADDR waddr, CORE_ADDR addr,
171 int len, int rw);
172static int go32_remove_aligned_watchpoint (CORE_ADDR waddr, CORE_ADDR addr,
173 int len, int rw);
174static int go32_handle_nonaligned_watchpoint (wp_op what, CORE_ADDR waddr,
175 CORE_ADDR addr, int len, int rw);
b83266a0
SS
176
177static struct target_ops go32_ops;
c5aa993b
JM
178static void go32_terminal_init (void);
179static void go32_terminal_inferior (void);
180static void go32_terminal_ours (void);
e49d4fa6 181
53a5351d 182#define r_ofs(x) (offsetof(TSS,x))
e49d4fa6
SS
183
184static struct
185{
53a5351d
JM
186 size_t tss_ofs;
187 size_t size;
e49d4fa6
SS
188}
189regno_mapping[] =
190{
0fff5247
EZ
191 {r_ofs (tss_eax), 4}, /* normal registers, from a_tss */
192 {r_ofs (tss_ecx), 4},
193 {r_ofs (tss_edx), 4},
194 {r_ofs (tss_ebx), 4},
195 {r_ofs (tss_esp), 4},
196 {r_ofs (tss_ebp), 4},
197 {r_ofs (tss_esi), 4},
198 {r_ofs (tss_edi), 4},
199 {r_ofs (tss_eip), 4},
200 {r_ofs (tss_eflags), 4},
201 {r_ofs (tss_cs), 2},
202 {r_ofs (tss_ss), 2},
203 {r_ofs (tss_ds), 2},
204 {r_ofs (tss_es), 2},
205 {r_ofs (tss_fs), 2},
206 {r_ofs (tss_gs), 2},
207 {0, 10}, /* 8 FP registers, from npx.reg[] */
208 {1, 10},
209 {2, 10},
210 {3, 10},
211 {4, 10},
212 {5, 10},
213 {6, 10},
214 {7, 10},
53a5351d 215 /* The order of the next 7 registers must be consistent
0fff5247
EZ
216 with their numbering in config/i386/tm-i386.h, which see. */
217 {0, 2}, /* control word, from npx */
218 {4, 2}, /* status word, from npx */
219 {8, 2}, /* tag word, from npx */
220 {16, 2}, /* last FP exception CS from npx */
221 {12, 4}, /* last FP exception EIP from npx */
222 {24, 2}, /* last FP exception operand selector from npx */
223 {20, 4}, /* last FP exception operand offset from npx */
224 {18, 2} /* last FP opcode from npx */
e49d4fa6
SS
225};
226
227static struct
228 {
229 int go32_sig;
0fff5247 230 enum target_signal gdb_sig;
e49d4fa6
SS
231 }
232sig_map[] =
233{
0fff5247
EZ
234 {0, TARGET_SIGNAL_FPE},
235 {1, TARGET_SIGNAL_TRAP},
53a5351d
JM
236 /* Exception 2 is triggered by the NMI. DJGPP handles it as SIGILL,
237 but I think SIGBUS is better, since the NMI is usually activated
238 as a result of a memory parity check failure. */
0fff5247
EZ
239 {2, TARGET_SIGNAL_BUS},
240 {3, TARGET_SIGNAL_TRAP},
241 {4, TARGET_SIGNAL_FPE},
242 {5, TARGET_SIGNAL_SEGV},
243 {6, TARGET_SIGNAL_ILL},
244 {7, TARGET_SIGNAL_EMT}, /* no-coprocessor exception */
245 {8, TARGET_SIGNAL_SEGV},
246 {9, TARGET_SIGNAL_SEGV},
247 {10, TARGET_SIGNAL_BUS},
248 {11, TARGET_SIGNAL_SEGV},
249 {12, TARGET_SIGNAL_SEGV},
250 {13, TARGET_SIGNAL_SEGV},
251 {14, TARGET_SIGNAL_SEGV},
252 {16, TARGET_SIGNAL_FPE},
253 {17, TARGET_SIGNAL_BUS},
254 {31, TARGET_SIGNAL_ILL},
255 {0x1b, TARGET_SIGNAL_INT},
256 {0x75, TARGET_SIGNAL_FPE},
257 {0x78, TARGET_SIGNAL_ALRM},
258 {0x79, TARGET_SIGNAL_INT},
259 {0x7a, TARGET_SIGNAL_QUIT},
260 {-1, TARGET_SIGNAL_LAST}
e49d4fa6
SS
261};
262
53a5351d
JM
263static struct {
264 enum target_signal gdb_sig;
265 int djgpp_excepno;
266} excepn_map[] = {
0fff5247
EZ
267 {TARGET_SIGNAL_0, -1},
268 {TARGET_SIGNAL_ILL, 6}, /* Invalid Opcode */
269 {TARGET_SIGNAL_EMT, 7}, /* triggers SIGNOFP */
270 {TARGET_SIGNAL_SEGV, 13}, /* GPF */
271 {TARGET_SIGNAL_BUS, 17}, /* Alignment Check */
53a5351d
JM
272 /* The rest are fake exceptions, see dpmiexcp.c in djlsr*.zip for
273 details. */
0fff5247
EZ
274 {TARGET_SIGNAL_TERM, 0x1b}, /* triggers Ctrl-Break type of SIGINT */
275 {TARGET_SIGNAL_FPE, 0x75},
276 {TARGET_SIGNAL_INT, 0x79},
277 {TARGET_SIGNAL_QUIT, 0x7a},
278 {TARGET_SIGNAL_ALRM, 0x78}, /* triggers SIGTIMR */
279 {TARGET_SIGNAL_PROF, 0x78},
280 {TARGET_SIGNAL_LAST, -1}
53a5351d
JM
281};
282
e49d4fa6 283static void
0fff5247 284go32_open (char *name ATTRIBUTE_UNUSED, int from_tty ATTRIBUTE_UNUSED)
e49d4fa6 285{
53a5351d 286 printf_unfiltered ("Done. Use the \"run\" command to run the program.\n");
e49d4fa6
SS
287}
288
289static void
0fff5247 290go32_close (int quitting ATTRIBUTE_UNUSED)
e49d4fa6
SS
291{
292}
293
294static void
0fff5247 295go32_attach (char *args ATTRIBUTE_UNUSED, int from_tty ATTRIBUTE_UNUSED)
e49d4fa6 296{
53a5351d
JM
297 error ("\
298You cannot attach to a running program on this platform.\n\
299Use the `run' command to run DJGPP programs.");
e49d4fa6
SS
300}
301
302static void
0fff5247 303go32_detach (char *args ATTRIBUTE_UNUSED, int from_tty ATTRIBUTE_UNUSED)
e49d4fa6
SS
304{
305}
306
307static int resume_is_step;
53a5351d 308static int resume_signal = -1;
e49d4fa6
SS
309
310static void
0fff5247 311go32_resume (int pid ATTRIBUTE_UNUSED, int step, enum target_signal siggnal)
c5aa993b 312{
53a5351d
JM
313 int i;
314
c5aa993b 315 resume_is_step = step;
53a5351d
JM
316
317 if (siggnal != TARGET_SIGNAL_0 && siggnal != TARGET_SIGNAL_TRAP)
318 {
0fff5247
EZ
319 for (i = 0, resume_signal = -1;
320 excepn_map[i].gdb_sig != TARGET_SIGNAL_LAST; i++)
53a5351d
JM
321 if (excepn_map[i].gdb_sig == siggnal)
322 {
323 resume_signal = excepn_map[i].djgpp_excepno;
324 break;
325 }
326 if (resume_signal == -1)
327 printf_unfiltered ("Cannot deliver signal %s on this platform.\n",
328 target_signal_to_name (siggnal));
329 }
c5aa993b 330}
e49d4fa6 331
53a5351d
JM
332static char child_cwd[FILENAME_MAX];
333
e49d4fa6 334static int
0fff5247 335go32_wait (int pid ATTRIBUTE_UNUSED, struct target_waitstatus *status)
e49d4fa6
SS
336{
337 int i;
53a5351d 338 unsigned char saved_opcode;
0fff5247 339 unsigned long INT3_addr = 0;
53a5351d 340 int stepping_over_INT = 0;
e49d4fa6 341
53a5351d 342 a_tss.tss_eflags &= 0xfeff; /* reset the single-step flag (TF) */
e49d4fa6 343 if (resume_is_step)
53a5351d
JM
344 {
345 /* If the next instruction is INT xx or INTO, we need to handle
346 them specially. Intel manuals say that these instructions
347 reset the single-step flag (a.k.a. TF). However, it seems
348 that, at least in the DPMI environment, and at least when
349 stepping over the DPMI interrupt 31h, the problem is having
350 TF set at all when INT 31h is executed: the debuggee either
351 crashes (and takes the system with it) or is killed by a
352 SIGTRAP.
353
354 So we need to emulate single-step mode: we put an INT3 opcode
355 right after the INT xx instruction, let the debuggee run
356 until it hits INT3 and stops, then restore the original
357 instruction which we overwrote with the INT3 opcode, and back
358 up the debuggee's EIP to that instruction. */
359 read_child (a_tss.tss_eip, &saved_opcode, 1);
360 if (saved_opcode == 0xCD || saved_opcode == 0xCE)
361 {
362 unsigned char INT3_opcode = 0xCC;
363
364 INT3_addr
365 = saved_opcode == 0xCD ? a_tss.tss_eip + 2 : a_tss.tss_eip + 1;
366 stepping_over_INT = 1;
367 read_child (INT3_addr, &saved_opcode, 1);
368 write_child (INT3_addr, &INT3_opcode, 1);
369 }
370 else
371 a_tss.tss_eflags |= 0x0100; /* normal instruction: set TF */
372 }
373
374 /* The special value FFFFh in tss_trap indicates to run_child that
375 tss_irqn holds a signal to be delivered to the debuggee. */
376 if (resume_signal <= -1)
377 {
378 a_tss.tss_trap = 0;
379 a_tss.tss_irqn = 0xff;
380 }
e49d4fa6 381 else
53a5351d
JM
382 {
383 a_tss.tss_trap = 0xffff; /* run_child looks for this */
384 a_tss.tss_irqn = resume_signal;
385 }
386
387 /* The child might change working directory behind our back. The
388 GDB users won't like the side effects of that when they work with
389 relative file names, and GDB might be confused by its current
390 directory not being in sync with the truth. So we always make a
391 point of changing back to where GDB thinks is its cwd, when we
392 return control to the debugger, but restore child's cwd before we
393 run it. */
3a45aed8
EZ
394 /* Initialize child_cwd, before the first call to run_child and not
395 in the initialization, so the child get also the changed directory
396 set with the gdb-command "cd ..." */
397 if (!*child_cwd)
398 /* Initialize child's cwd with the current one. */
399 getcwd (child_cwd, sizeof (child_cwd));
400
53a5351d 401 chdir (child_cwd);
e49d4fa6 402
b83266a0 403#if __DJGPP_MINOR__ < 3
53a5351d 404 load_npx ();
b83266a0 405#endif
e49d4fa6 406 run_child ();
b83266a0 407#if __DJGPP_MINOR__ < 3
53a5351d 408 save_npx ();
b83266a0 409#endif
e49d4fa6 410
53a5351d
JM
411 /* Did we step over an INT xx instruction? */
412 if (stepping_over_INT && a_tss.tss_eip == INT3_addr + 1)
413 {
414 /* Restore the original opcode. */
415 a_tss.tss_eip--; /* EIP points *after* the INT3 instruction */
416 write_child (a_tss.tss_eip, &saved_opcode, 1);
417 /* Simulate a TRAP exception. */
418 a_tss.tss_irqn = 1;
419 a_tss.tss_eflags |= 0x0100;
420 }
421
422 getcwd (child_cwd, sizeof (child_cwd)); /* in case it has changed */
423 chdir (current_directory);
424
e49d4fa6
SS
425 if (a_tss.tss_irqn == 0x21)
426 {
427 status->kind = TARGET_WAITKIND_EXITED;
428 status->value.integer = a_tss.tss_eax & 0xff;
429 }
430 else
431 {
432 status->value.sig = TARGET_SIGNAL_UNKNOWN;
433 status->kind = TARGET_WAITKIND_STOPPED;
434 for (i = 0; sig_map[i].go32_sig != -1; i++)
435 {
436 if (a_tss.tss_irqn == sig_map[i].go32_sig)
437 {
53a5351d 438#if __DJGPP_MINOR__ < 3
e49d4fa6
SS
439 if ((status->value.sig = sig_map[i].gdb_sig) !=
440 TARGET_SIGNAL_TRAP)
441 status->kind = TARGET_WAITKIND_SIGNALLED;
53a5351d
JM
442#else
443 status->value.sig = sig_map[i].gdb_sig;
444#endif
e49d4fa6
SS
445 break;
446 }
447 }
448 }
449 return SOME_PID;
450}
451
452static void
453go32_fetch_registers (int regno)
454{
c5aa993b 455 /*JHW */
e49d4fa6
SS
456 int end_reg = regno + 1; /* just one reg initially */
457
458 if (regno < 0) /* do the all registers */
459 {
460 regno = 0; /* start at first register */
461 /* # regs in table */
462 end_reg = sizeof (regno_mapping) / sizeof (regno_mapping[0]);
463 }
464
465 for (; regno < end_reg; regno++)
466 {
467 if (regno < 16)
468 supply_register (regno,
469 (char *) &a_tss + regno_mapping[regno].tss_ofs);
470 else if (regno < 24)
471 supply_register (regno,
472 (char *) &npx.reg[regno_mapping[regno].tss_ofs]);
0fff5247
EZ
473 else if (regno < 32)
474 {
475 unsigned regval;
476
477 switch (regno_mapping[regno].size)
478 {
479 case 2:
480 regval = *(unsigned short *)
481 ((char *) &npx + regno_mapping[regno].tss_ofs);
482 regval &= 0xffff;
483 if (regno == FOP_REGNUM && regval)
484 /* Feature: restore the 5 bits of the opcode
485 stripped by FSAVE/FNSAVE. */
486 regval |= 0xd800;
487 break;
488 case 4:
489 regval = *(unsigned *)
490 ((char *) &npx + regno_mapping[regno].tss_ofs);
491 break;
492 default:
8e65ff28 493 internal_error (__FILE__, __LINE__, "\
0fff5247
EZ
494Invalid native size for register no. %d in go32_fetch_register.", regno);
495 }
496 supply_register (regno, (char *) &regval);
497 }
e49d4fa6 498 else
8e65ff28
AC
499 internal_error (__FILE__, __LINE__,
500 "Invalid register no. %d in go32_fetch_register.",
4ce44c66 501 regno);
e49d4fa6
SS
502 }
503}
504
505static void
506store_register (int regno)
507{
508 void *rp;
509 void *v = (void *) &registers[REGISTER_BYTE (regno)];
510
511 if (regno < 16)
512 rp = (char *) &a_tss + regno_mapping[regno].tss_ofs;
513 else if (regno < 24)
514 rp = (char *) &npx.reg[regno_mapping[regno].tss_ofs];
0fff5247 515 else if (regno < 32)
e49d4fa6
SS
516 rp = (char *) &npx + regno_mapping[regno].tss_ofs;
517 else
8e65ff28
AC
518 internal_error (__FILE__, __LINE__,
519 "Invalid register no. %d in store_register.", regno);
e49d4fa6 520 memcpy (rp, v, regno_mapping[regno].size);
0fff5247
EZ
521 if (regno == FOP_REGNUM)
522 *(short *)rp &= 0x07ff; /* strip high 5 bits, in case they added them */
e49d4fa6
SS
523}
524
525static void
526go32_store_registers (int regno)
527{
0fff5247 528 unsigned r;
e49d4fa6
SS
529
530 if (regno >= 0)
531 store_register (regno);
532 else
533 {
534 for (r = 0; r < sizeof (regno_mapping) / sizeof (regno_mapping[0]); r++)
535 store_register (r);
536 }
537}
538
539static void
540go32_prepare_to_store (void)
541{
542}
543
544static int
545go32_xfer_memory (CORE_ADDR memaddr, char *myaddr, int len, int write,
a17b5c4e 546 struct mem_attrib *attrib ATTRIBUTE_UNUSED,
0fff5247 547 struct target_ops *target ATTRIBUTE_UNUSED)
e49d4fa6
SS
548{
549 if (write)
550 {
551 if (write_child (memaddr, myaddr, len))
552 {
553 return 0;
554 }
555 else
556 {
557 return len;
558 }
559 }
560 else
561 {
562 if (read_child (memaddr, myaddr, len))
563 {
564 return 0;
565 }
566 else
567 {
568 return len;
569 }
570 }
571}
572
53a5351d
JM
573static cmdline_t child_cmd; /* parsed child's command line kept here */
574
e49d4fa6 575static void
0fff5247 576go32_files_info (struct target_ops *target ATTRIBUTE_UNUSED)
e49d4fa6 577{
53a5351d 578 printf_unfiltered ("You are running a DJGPP V2 program.\n");
e49d4fa6
SS
579}
580
581static void
582go32_stop (void)
583{
584 normal_stop ();
585 cleanup_client ();
586 inferior_pid = 0;
587 prog_has_started = 0;
588}
589
590static void
591go32_kill_inferior (void)
592{
53a5351d
JM
593 redir_cmdline_delete (&child_cmd);
594 resume_signal = -1;
595 resume_is_step = 0;
e49d4fa6
SS
596 unpush_target (&go32_ops);
597}
598
599static void
600go32_create_inferior (char *exec_file, char *args, char **env)
601{
602 jmp_buf start_state;
603 char *cmdline;
604 char **env_save = environ;
605
0fff5247
EZ
606 /* If no exec file handed to us, get it from the exec-file command -- with
607 a good, common error message if none is specified. */
608 if (exec_file == 0)
609 exec_file = get_exec_file (1);
610
e49d4fa6
SS
611 if (prog_has_started)
612 {
b83266a0 613 go32_stop ();
e49d4fa6
SS
614 go32_kill_inferior ();
615 }
53a5351d
JM
616 resume_signal = -1;
617 resume_is_step = 0;
3a45aed8
EZ
618
619 /* Initialize child's cwd as empty to be initialized when starting
620 the child. */
621 *child_cwd = 0;
622
53a5351d
JM
623 /* Init command line storage. */
624 if (redir_debug_init (&child_cmd) == -1)
8e65ff28
AC
625 internal_error (__FILE__, __LINE__,
626 "Cannot allocate redirection storage: not enough memory.\n");
53a5351d
JM
627
628 /* Parse the command line and create redirections. */
629 if (strpbrk (args, "<>"))
630 {
631 if (redir_cmdline_parse (args, &child_cmd) == 0)
632 args = child_cmd.command;
633 else
634 error ("Syntax error in command line.");
635 }
636 else
c2d11a7d 637 child_cmd.command = xstrdup (args);
e49d4fa6
SS
638
639 cmdline = (char *) alloca (strlen (args) + 4);
640 cmdline[0] = strlen (args);
641 strcpy (cmdline + 1, args);
642 cmdline[strlen (args) + 1] = 13;
643
644 environ = env;
645
646 if (v2loadimage (exec_file, cmdline, start_state))
647 {
648 environ = env_save;
649 printf_unfiltered ("Load failed for image %s\n", exec_file);
650 exit (1);
651 }
652 environ = env_save;
653
654 edi_init (start_state);
53a5351d
JM
655#if __DJGPP_MINOR__ < 3
656 save_npx ();
657#endif
e49d4fa6
SS
658
659 inferior_pid = SOME_PID;
660 push_target (&go32_ops);
661 clear_proceed_status ();
662 insert_breakpoints ();
2acceee2 663 proceed ((CORE_ADDR) -1, TARGET_SIGNAL_0, 0);
b83266a0 664 prog_has_started = 1;
e49d4fa6
SS
665}
666
667static void
668go32_mourn_inferior (void)
669{
53a5351d
JM
670 /* We need to make sure all the breakpoint enable bits in the DR7
671 register are reset when the inferior exits. Otherwise, if they
672 rerun the inferior, the uncleared bits may cause random SIGTRAPs,
673 failure to set more watchpoints, and other calamities. It would
674 be nice if GDB itself would take care to remove all breakpoints
675 at all times, but it doesn't, probably under an assumption that
676 the OS cleans up when the debuggee exits. */
677 cleanup_dregs ();
e49d4fa6
SS
678 go32_kill_inferior ();
679 generic_mourn_inferior ();
680}
681
682static int
683go32_can_run (void)
684{
685 return 1;
686}
687
e49d4fa6
SS
688/* Hardware watchpoint support. */
689
690#define DR_STATUS 6
691#define DR_CONTROL 7
692#define DR_ENABLE_SIZE 2
693#define DR_LOCAL_ENABLE_SHIFT 0
694#define DR_GLOBAL_ENABLE_SHIFT 1
695#define DR_LOCAL_SLOWDOWN 0x100
696#define DR_GLOBAL_SLOWDOWN 0x200
697#define DR_CONTROL_SHIFT 16
698#define DR_CONTROL_SIZE 4
53a5351d 699#define DR_RW_READWRITE 0x3
e49d4fa6
SS
700#define DR_RW_WRITE 0x1
701#define DR_CONTROL_MASK 0xf
702#define DR_ENABLE_MASK 0x3
703#define DR_LEN_1 0x0
704#define DR_LEN_2 0x4
705#define DR_LEN_4 0xc
706
707#define D_REGS edi.dr
708#define CONTROL D_REGS[DR_CONTROL]
709#define STATUS D_REGS[DR_STATUS]
710
711#define IS_REG_FREE(index) \
53a5351d 712 (!(CONTROL & (3 << (DR_ENABLE_SIZE * (index)))))
e49d4fa6
SS
713
714#define LOCAL_ENABLE_REG(index) \
53a5351d 715 (CONTROL |= (1 << (DR_LOCAL_ENABLE_SHIFT + DR_ENABLE_SIZE * (index))))
e49d4fa6
SS
716
717#define GLOBAL_ENABLE_REG(index) \
53a5351d 718 (CONTROL |= (1 << (DR_GLOBAL_ENABLE_SHIFT + DR_ENABLE_SIZE * (index))))
e49d4fa6
SS
719
720#define DISABLE_REG(index) \
53a5351d 721 (CONTROL &= ~(3 << (DR_ENABLE_SIZE * (index))))
e49d4fa6
SS
722
723#define SET_LOCAL_EXACT() \
724 (CONTROL |= DR_LOCAL_SLOWDOWN)
725
726#define SET_GLOBAL_EXACT() \
727 (CONTROL |= DR_GLOBAL_SLOWDOWN)
728
53a5351d
JM
729#define RESET_LOCAL_EXACT() \
730 (CONTROL &= ~(DR_LOCAL_SLOWDOWN))
731
732#define RESET_GLOBAL_EXACT() \
733 (CONTROL &= ~(DR_GLOBAL_SLOWDOWN))
734
e49d4fa6
SS
735#define SET_BREAK(index,address) \
736 do {\
53a5351d 737 CONTROL &= ~(DR_CONTROL_MASK << (DR_CONTROL_SHIFT + DR_CONTROL_SIZE * (index)));\
e49d4fa6 738 D_REGS[index] = address;\
c2c6d25f 739 dr_ref_count[index]++;\
e49d4fa6
SS
740 } while(0)
741
742#define SET_WATCH(index,address,rw,len) \
743 do {\
744 SET_BREAK(index,address);\
53a5351d 745 CONTROL |= ((len)|(rw)) << (DR_CONTROL_SHIFT + DR_CONTROL_SIZE * (index));\
e49d4fa6
SS
746 } while (0)
747
53a5351d
JM
748#define IS_WATCH(index) \
749 (CONTROL & (DR_CONTROL_MASK << (DR_CONTROL_SHIFT + DR_CONTROL_SIZE*(index))))
750
c2c6d25f 751#define WATCH_HIT(index) ((STATUS & (1 << (index))) && IS_WATCH(index))
e49d4fa6 752
53a5351d
JM
753#define DR_DEF(index) \
754 ((CONTROL >> (DR_CONTROL_SHIFT + DR_CONTROL_SIZE * (index))) & 0x0f)
755
756
757#if 0 /* use debugging macro */
758#define SHOW_DR(text,len) \
e49d4fa6 759do { \
53a5351d 760 if (!getenv ("GDB_SHOW_DR")) break; \
e49d4fa6 761 fprintf(stderr,"%08x %08x ",edi.dr[7],edi.dr[6]); \
53a5351d
JM
762 fprintf(stderr,"%08x %d %08x %d ", \
763 edi.dr[0],dr_ref_count[0],edi.dr[1],dr_ref_count[1]); \
764 fprintf(stderr,"%08x %d %08x %d ", \
765 edi.dr[2],dr_ref_count[2],edi.dr[3],dr_ref_count[3]); \
766 fprintf(stderr,(len)?"(%s:%d)\n":"(%s)\n",#text,len); \
e49d4fa6
SS
767} while (0)
768#else
53a5351d 769#define SHOW_DR(text,len) do {} while (0)
e49d4fa6
SS
770#endif
771
53a5351d
JM
772static void
773cleanup_dregs (void)
774{
775 int i;
776
777 CONTROL = 0;
778 STATUS = 0;
779 for (i = 0; i < 4; i++)
780 {
781 D_REGS[i] = 0;
782 dr_ref_count[i] = 0;
783 }
784}
785
e49d4fa6
SS
786/* Insert a watchpoint. */
787
788int
0fff5247
EZ
789go32_insert_watchpoint (int pid ATTRIBUTE_UNUSED, CORE_ADDR addr,
790 int len, int rw)
e49d4fa6 791{
53a5351d 792 int ret = go32_insert_aligned_watchpoint (addr, addr, len, rw);
e49d4fa6 793
53a5351d 794 SHOW_DR (insert_watch, len);
e49d4fa6
SS
795 return ret;
796}
797
798static int
53a5351d 799go32_insert_aligned_watchpoint (CORE_ADDR waddr, CORE_ADDR addr,
e49d4fa6
SS
800 int len, int rw)
801{
802 int i;
803 int read_write_bits, len_bits;
804
53a5351d
JM
805 /* Values of rw: 0 - write, 1 - read, 2 - access (read and write).
806 However, x86 doesn't support read-only data breakpoints. */
807 read_write_bits = rw ? DR_RW_READWRITE : DR_RW_WRITE;
808
809 switch (len)
810 {
811 case 4:
812 len_bits = DR_LEN_4;
813 break;
814 case 2:
815 len_bits = DR_LEN_2;
816 break;
817 case 1:
818 len_bits = DR_LEN_1;
819 break;
820 default:
821 /* The debug registers only have 2 bits for the length, so
822 so this value will always fail the loop below. */
823 len_bits = 0x10;
824 }
825
826 /* Look for an occupied debug register with the same address and the
827 same RW and LEN definitions. If we find one, we can use it for
828 this watchpoint as well (and save a register). */
829 for (i = 0; i < 4; i++)
830 {
831 if (!IS_REG_FREE (i) && D_REGS[i] == addr
0fff5247 832 && DR_DEF (i) == (unsigned)(len_bits | read_write_bits))
e49d4fa6 833 {
53a5351d
JM
834 dr_ref_count[i]++;
835 return 0;
e49d4fa6 836 }
53a5351d
JM
837 }
838
839 /* Look for a free debug register. */
840 for (i = 0; i <= 3; i++)
841 {
842 if (IS_REG_FREE (i))
843 break;
844 }
e49d4fa6
SS
845
846 /* No more debug registers! */
847 if (i > 3)
848 return -1;
849
53a5351d
JM
850 if (len == 2)
851 {
852 if (addr % 2)
853 return go32_handle_nonaligned_watchpoint (wp_insert, waddr, addr,
854 len, rw);
855 }
e49d4fa6 856 else if (len == 4)
53a5351d
JM
857 {
858 if (addr % 4)
859 return go32_handle_nonaligned_watchpoint (wp_insert, waddr, addr,
860 len, rw);
861 }
862 else if (len != 1)
863 return go32_handle_nonaligned_watchpoint (wp_insert, waddr, addr, len, rw);
e49d4fa6
SS
864
865 SET_WATCH (i, addr, read_write_bits, len_bits);
866 LOCAL_ENABLE_REG (i);
867 SET_LOCAL_EXACT ();
53a5351d
JM
868 SET_GLOBAL_EXACT ();
869 return 0;
e49d4fa6
SS
870}
871
872static int
53a5351d 873go32_handle_nonaligned_watchpoint (wp_op what, CORE_ADDR waddr, CORE_ADDR addr,
e49d4fa6
SS
874 int len, int rw)
875{
876 int align;
877 int size;
53a5351d 878 int rv = 0, status = 0;
e49d4fa6 879
184a103e 880 static int size_try_array[4][4] =
e49d4fa6 881 {
184a103e
EZ
882 { 1, 1, 1, 1 }, /* trying size one */
883 { 2, 1, 2, 1 }, /* trying size two */
884 { 2, 1, 2, 1 }, /* trying size three */
885 { 4, 1, 2, 1 } /* trying size four */
e49d4fa6
SS
886 };
887
888 while (len > 0)
889 {
890 align = addr % 4;
184a103e
EZ
891 /* Four is the maximum length a 386 debug register can watch. */
892 size = size_try_array[len > 4 ? 3 : len - 1][align];
53a5351d
JM
893 if (what == wp_insert)
894 status = go32_insert_aligned_watchpoint (waddr, addr, size, rw);
895 else if (what == wp_remove)
896 status = go32_remove_aligned_watchpoint (waddr, addr, size, rw);
897 else if (what == wp_count)
898 rv++;
899 else
d03cef9d 900 status = EINVAL;
53a5351d
JM
901 /* We keep the loop going even after a failure, because some of
902 the other aligned watchpoints might still succeed, e.g. if
903 they watch addresses that are already watched, and thus just
904 increment the reference counts of occupied debug registers.
905 If we break out of the loop too early, we could cause those
906 addresses watched by other watchpoints to be disabled when
907 GDB reacts to our failure to insert this watchpoint and tries
908 to remove it. */
909 if (status)
910 rv = status;
e49d4fa6
SS
911 addr += size;
912 len -= size;
913 }
914 return rv;
915}
916
917/* Remove a watchpoint. */
918
919int
0fff5247
EZ
920go32_remove_watchpoint (int pid ATTRIBUTE_UNUSED, CORE_ADDR addr,
921 int len, int rw)
53a5351d
JM
922{
923 int ret = go32_remove_aligned_watchpoint (addr, addr, len, rw);
924
925 SHOW_DR (remove_watch, len);
926 return ret;
927}
928
929static int
930go32_remove_aligned_watchpoint (CORE_ADDR waddr, CORE_ADDR addr,
931 int len, int rw)
e49d4fa6
SS
932{
933 int i;
53a5351d
JM
934 int read_write_bits, len_bits;
935
936 /* Values of rw: 0 - write, 1 - read, 2 - access (read and write).
937 However, x86 doesn't support read-only data breakpoints. */
938 read_write_bits = rw ? DR_RW_READWRITE : DR_RW_WRITE;
939
940 switch (len)
941 {
942 case 4:
943 len_bits = DR_LEN_4;
944 break;
945 case 2:
946 len_bits = DR_LEN_2;
947 break;
948 case 1:
949 len_bits = DR_LEN_1;
950 break;
951 default:
952 /* The debug registers only have 2 bits for the length, so
953 so this value will always fail the loop below. */
954 len_bits = 0x10;
955 }
956
957 if (len == 2)
958 {
959 if (addr % 2)
960 return go32_handle_nonaligned_watchpoint (wp_remove, waddr, addr,
961 len, rw);
962 }
963 else if (len == 4)
964 {
965 if (addr % 4)
966 return go32_handle_nonaligned_watchpoint (wp_remove, waddr, addr,
967 len, rw);
968 }
969 else if (len != 1)
970 return go32_handle_nonaligned_watchpoint (wp_remove, waddr, addr, len, rw);
e49d4fa6
SS
971
972 for (i = 0; i <= 3; i++)
973 {
53a5351d 974 if (!IS_REG_FREE (i) && D_REGS[i] == addr
0fff5247 975 && DR_DEF (i) == (unsigned)(len_bits | read_write_bits))
e49d4fa6 976 {
53a5351d
JM
977 dr_ref_count[i]--;
978 if (dr_ref_count[i] == 0)
979 DISABLE_REG (i);
e49d4fa6
SS
980 }
981 }
53a5351d
JM
982 RESET_LOCAL_EXACT ();
983 RESET_GLOBAL_EXACT ();
e49d4fa6
SS
984
985 return 0;
986}
987
53a5351d
JM
988/* Can we use debug registers to watch a region whose address is ADDR
989 and whose length is LEN bytes? */
990
991int
992go32_region_ok_for_watchpoint (CORE_ADDR addr, int len)
993{
994 /* Compute how many aligned watchpoints we would need to cover this
995 region. */
996 int nregs = go32_handle_nonaligned_watchpoint (wp_count, addr, addr, len, 0);
997
998 return nregs <= 4 ? 1 : 0;
999}
1000
1001/* Check if stopped by a data watchpoint. If so, return the address
1002 whose access triggered the watchpoint. */
e49d4fa6
SS
1003
1004CORE_ADDR
0fff5247 1005go32_stopped_by_watchpoint (int pid ATTRIBUTE_UNUSED, int data_watchpoint)
e49d4fa6
SS
1006{
1007 int i, ret = 0;
1008 int status;
1009
1010 status = edi.dr[DR_STATUS];
53a5351d 1011 SHOW_DR (stopped_by, 0);
e49d4fa6
SS
1012 for (i = 0; i <= 3; i++)
1013 {
53a5351d 1014 if (WATCH_HIT (i) && data_watchpoint)
e49d4fa6 1015 {
53a5351d 1016 SHOW_DR (WP_HIT, 0);
e49d4fa6
SS
1017 ret = D_REGS[i];
1018 }
1019 }
e49d4fa6
SS
1020
1021 return ret;
1022}
1023
1024/* Remove a breakpoint. */
1025
1026int
0fff5247 1027go32_remove_hw_breakpoint (CORE_ADDR addr, void *shadow ATTRIBUTE_UNUSED)
e49d4fa6
SS
1028{
1029 int i;
1030 for (i = 0; i <= 3; i++)
1031 {
53a5351d 1032 if (!IS_REG_FREE (i) && D_REGS[i] == addr && DR_DEF (i) == 0)
e49d4fa6 1033 {
53a5351d
JM
1034 dr_ref_count[i]--;
1035 if (dr_ref_count[i] == 0)
1036 DISABLE_REG (i);
e49d4fa6
SS
1037 }
1038 }
53a5351d 1039 SHOW_DR (remove_hw, 0);
e49d4fa6
SS
1040 return 0;
1041}
1042
1043int
0fff5247 1044go32_insert_hw_breakpoint (CORE_ADDR addr, void *shadow ATTRIBUTE_UNUSED)
e49d4fa6
SS
1045{
1046 int i;
e49d4fa6 1047
53a5351d
JM
1048 /* Look for an occupied debug register with the same address and the
1049 same RW and LEN definitions. If we find one, we can use it for
1050 this breakpoint as well (and save a register). */
1051 for (i = 0; i < 4; i++)
1052 {
1053 if (!IS_REG_FREE (i) && D_REGS[i] == addr && DR_DEF (i) == 0)
1054 {
1055 dr_ref_count[i]++;
1056 SHOW_DR (insert_hw, 0);
1057 return 0;
1058 }
1059 }
1060
e49d4fa6
SS
1061 /* Look for a free debug register. */
1062 for (i = 0; i <= 3; i++)
1063 {
1064 if (IS_REG_FREE (i))
1065 break;
1066 }
1067
53a5351d
JM
1068 /* No more debug registers? */
1069 if (i < 4)
1070 {
1071 SET_BREAK (i, addr);
1072 LOCAL_ENABLE_REG (i);
1073 }
1074 SHOW_DR (insert_hw, 0);
e49d4fa6 1075
d03cef9d 1076 return i < 4 ? 0 : EBUSY;
e49d4fa6
SS
1077}
1078
53a5351d
JM
1079/* Put the device open on handle FD into either raw or cooked
1080 mode, return 1 if it was in raw mode, zero otherwise. */
1081
1082static int
1083device_mode (int fd, int raw_p)
1084{
1085 int oldmode, newmode;
1086 __dpmi_regs regs;
1087
1088 regs.x.ax = 0x4400;
1089 regs.x.bx = fd;
1090 __dpmi_int (0x21, &regs);
1091 if (regs.x.flags & 1)
1092 return -1;
1093 newmode = oldmode = regs.x.dx;
1094
1095 if (raw_p)
1096 newmode |= 0x20;
1097 else
1098 newmode &= ~0x20;
1099
1100 if (oldmode & 0x80) /* Only for character dev */
1101 {
1102 regs.x.ax = 0x4401;
1103 regs.x.bx = fd;
1104 regs.x.dx = newmode & 0xff; /* Force upper byte zero, else it fails */
1105 __dpmi_int (0x21, &regs);
1106 if (regs.x.flags & 1)
1107 return -1;
1108 }
1109 return (oldmode & 0x20) == 0x20;
1110}
1111
1112
1113static int inf_mode_valid = 0;
1114static int inf_terminal_mode;
1115
1116/* This semaphore is needed because, amazingly enough, GDB calls
1117 target.to_terminal_ours more than once after the inferior stops.
1118 But we need the information from the first call only, since the
1119 second call will always see GDB's own cooked terminal. */
1120static int terminal_is_ours = 1;
1121
cce74817
JM
1122static void
1123go32_terminal_init (void)
1124{
53a5351d
JM
1125 inf_mode_valid = 0; /* reinitialize, in case they are restarting child */
1126 terminal_is_ours = 1;
cce74817
JM
1127}
1128
1129static void
0fff5247 1130go32_terminal_info (char *args ATTRIBUTE_UNUSED, int from_tty ATTRIBUTE_UNUSED)
cce74817 1131{
53a5351d
JM
1132 printf_unfiltered ("Inferior's terminal is in %s mode.\n",
1133 !inf_mode_valid
1134 ? "default" : inf_terminal_mode ? "raw" : "cooked");
1135
1136#if __DJGPP_MINOR__ > 2
1137 if (child_cmd.redirection)
1138 {
1139 int i;
1140
1141 for (i = 0; i < DBG_HANDLES; i++)
c5aa993b 1142 {
53a5351d
JM
1143 if (child_cmd.redirection[i]->file_name)
1144 printf_unfiltered ("\tFile handle %d is redirected to `%s'.\n",
1145 i, child_cmd.redirection[i]->file_name);
1146 else if (_get_dev_info (child_cmd.redirection[i]->inf_handle) == -1)
1147 printf_unfiltered
1148 ("\tFile handle %d appears to be closed by inferior.\n", i);
1149 /* Mask off the raw/cooked bit when comparing device info words. */
1150 else if ((_get_dev_info (child_cmd.redirection[i]->inf_handle) & 0xdf)
1151 != (_get_dev_info (i) & 0xdf))
1152 printf_unfiltered
1153 ("\tFile handle %d appears to be redirected by inferior.\n", i);
c5aa993b 1154 }
53a5351d
JM
1155 }
1156#endif
1157}
1158
1159static void
1160go32_terminal_inferior (void)
1161{
1162 /* Redirect standard handles as child wants them. */
1163 errno = 0;
1164 if (redir_to_child (&child_cmd) == -1)
1165 {
1166 redir_to_debugger (&child_cmd);
1167 error ("Cannot redirect standard handles for program: %s.",
1168 strerror (errno));
1169 }
1170 /* set the console device of the inferior to whatever mode
1171 (raw or cooked) we found it last time */
1172 if (terminal_is_ours)
1173 {
1174 if (inf_mode_valid)
1175 device_mode (0, inf_terminal_mode);
1176 terminal_is_ours = 0;
1177 }
cce74817
JM
1178}
1179
1180static void
1181go32_terminal_ours (void)
1182{
53a5351d
JM
1183 /* Switch to cooked mode on the gdb terminal and save the inferior
1184 terminal mode to be restored when it is resumed */
1185 if (!terminal_is_ours)
1186 {
1187 inf_terminal_mode = device_mode (0, 0);
1188 if (inf_terminal_mode != -1)
1189 inf_mode_valid = 1;
1190 else
1191 /* If device_mode returned -1, we don't know what happens with
1192 handle 0 anymore, so make the info invalid. */
1193 inf_mode_valid = 0;
1194 terminal_is_ours = 1;
1195
1196 /* Restore debugger's standard handles. */
1197 errno = 0;
1198 if (redir_to_debugger (&child_cmd) == -1)
1199 {
1200 redir_to_child (&child_cmd);
1201 error ("Cannot redirect standard handles for debugger: %s.",
1202 strerror (errno));
1203 }
1204 }
cce74817
JM
1205}
1206
e49d4fa6
SS
1207static void
1208init_go32_ops (void)
1209{
1210 go32_ops.to_shortname = "djgpp";
1211 go32_ops.to_longname = "djgpp target process";
1212 go32_ops.to_doc =
1213 "Program loaded by djgpp, when gdb is used as an external debugger";
1214 go32_ops.to_open = go32_open;
1215 go32_ops.to_close = go32_close;
53a5351d 1216 go32_ops.to_attach = go32_attach;
e49d4fa6
SS
1217 go32_ops.to_detach = go32_detach;
1218 go32_ops.to_resume = go32_resume;
1219 go32_ops.to_wait = go32_wait;
1220 go32_ops.to_fetch_registers = go32_fetch_registers;
1221 go32_ops.to_store_registers = go32_store_registers;
1222 go32_ops.to_prepare_to_store = go32_prepare_to_store;
1223 go32_ops.to_xfer_memory = go32_xfer_memory;
1224 go32_ops.to_files_info = go32_files_info;
1225 go32_ops.to_insert_breakpoint = memory_insert_breakpoint;
1226 go32_ops.to_remove_breakpoint = memory_remove_breakpoint;
cce74817
JM
1227 go32_ops.to_terminal_init = go32_terminal_init;
1228 go32_ops.to_terminal_inferior = go32_terminal_inferior;
53a5351d 1229 go32_ops.to_terminal_ours_for_output = go32_terminal_ours;
cce74817 1230 go32_ops.to_terminal_ours = go32_terminal_ours;
53a5351d 1231 go32_ops.to_terminal_info = go32_terminal_info;
e49d4fa6
SS
1232 go32_ops.to_kill = go32_kill_inferior;
1233 go32_ops.to_create_inferior = go32_create_inferior;
1234 go32_ops.to_mourn_inferior = go32_mourn_inferior;
1235 go32_ops.to_can_run = go32_can_run;
1236 go32_ops.to_stop = go32_stop;
1237 go32_ops.to_stratum = process_stratum;
1238 go32_ops.to_has_all_memory = 1;
1239 go32_ops.to_has_memory = 1;
1240 go32_ops.to_has_stack = 1;
1241 go32_ops.to_has_registers = 1;
1242 go32_ops.to_has_execution = 1;
1243 go32_ops.to_magic = OPS_MAGIC;
53a5351d 1244
3a45aed8
EZ
1245 /* Initialize child's cwd as empty to be initialized when starting
1246 the child. */
1247 *child_cwd = 0;
53a5351d
JM
1248
1249 /* Initialize child's command line storage. */
1250 if (redir_debug_init (&child_cmd) == -1)
8e65ff28
AC
1251 internal_error (__FILE__, __LINE__,
1252 "Cannot allocate redirection storage: not enough memory.\n");
0fff5247
EZ
1253
1254 /* We are always processing GCC-compiled programs. */
1255 processing_gcc_compilation = 2;
e49d4fa6
SS
1256}
1257
1258void
1259_initialize_go32_nat (void)
1260{
1261 init_go32_ops ();
1262 add_target (&go32_ops);
1263}
53a5351d
JM
1264
1265pid_t
1266tcgetpgrp (int fd)
1267{
1268 if (isatty (fd))
1269 return SOME_PID;
1270 errno = ENOTTY;
1271 return -1;
1272}
1273
1274int
1275tcsetpgrp (int fd, pid_t pgid)
1276{
1277 if (isatty (fd) && pgid == SOME_PID)
1278 return 0;
1279 errno = pgid == SOME_PID ? ENOTTY : ENOSYS;
1280 return -1;
1281}
This page took 0.141279 seconds and 4 git commands to generate.