1 /* Top level support for Mac interface to GDB, the GNU debugger.
2 Copyright 1994 Free Software Foundation, Inc.
3 Contributed by Cygnus Support. Written by Stan Shebs for Cygnus.
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 even the 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., 675 Mass Ave, Cambridge, MA 02139, USA. */
28 #include <Resources.h>
29 #include <QuickDraw.h>
37 #include <ToolUtils.h>
48 #include <GestaltEqu.h>
49 #include <PPCToolbox.h>
50 #include <AppleEvents.h>
51 #include <StandardFile.h>
55 #define QD(whatever) (qd.##whatever)
56 #define QDPat(whatever) (&(qd.##whatever))
60 #define QD(whatever) (whatever)
63 #define p2c(pstr,cbuf) \
64 strncpy(cbuf, ((char *) (pstr) + 1), pstr[0]); \
67 #define pascalify(STR) \
68 sprintf(tmpbuf, " %s", STR); \
69 tmpbuf[0] = strlen(STR);
72 #include "call-cmds.h"
77 #include "breakpoint.h"
79 #include "expression.h"
92 Rect dragrect
= { -32000, -32000, 32000, 32000 };
97 /* Globals for the console window. */
99 WindowPtr console_window
;
101 ControlHandle console_v_scrollbar
;
103 Rect console_v_scroll_rect
;
105 TEHandle console_text
;
107 Rect console_text_rect
;
109 /* This will go away eventually. */
110 gdb_has_a_terminal () { return 1; }
116 int eventloopdone
= 0;
126 /* Do the standard Mac environment setup. */
127 InitGraf (&QD (thePort
));
129 FlushEvents (everyEvent
, 0);
136 /* Color Quickdraw is different from Classic QD. */
138 hasColorQD
= se
.hasColorQD
;
142 sizerect
.bottom
= 1000;
143 sizerect
.right
= 1000;
145 sizerect
.bottom
= screenBits
.bounds
.bottom
- screenBits
.bounds
.top
;
146 sizerect
.right
= screenBits
.bounds
.right
- screenBits
.bounds
.left
;
149 /* Set up the menus. */
150 menubar
= GetNewMBar (mbMain
);
151 SetMenuBar (menubar
);
152 /* Add the DAs etc as usual. */
153 menu
= GetMHandle (mApple
);
155 AddResMenu (menu
, 'DRVR');
159 /* Create the main window we're going to play in. */
161 console_window
= GetNewCWindow (wConsole
, NULL
, (WindowPtr
) -1L);
163 console_window
= GetNewWindow (wConsole
, NULL
, (WindowPtr
) -1L);
165 if (0) DebugStr("\pnear beginning");
166 SetPort (console_window
);
167 console_text_rect
= console_window
->portRect
;
168 console_text_rect
.bottom
-= sbarwid
- 1;
169 console_text_rect
.right
-= sbarwid
- 1;
170 console_text
= TENew (&console_text_rect
, &console_text_rect
);
171 TESetSelect (0, 32767, console_text
);
172 TEDelete (console_text
);
173 TEInsert ("(gdb)", strlen("(gdb)"), console_text
);
175 console_v_scroll_rect
= console_window
->portRect
;
176 console_v_scroll_rect
.bottom
-= sbarwid
- 1;
177 console_v_scroll_rect
.left
= console_v_scroll_rect
.right
- sbarwid
;
178 console_v_scrollbar
=
179 NewControl (console_window
, &console_v_scroll_rect
,
180 "\p", 1, 0, 0, 0, scrollBarProc
, 0L);
182 ShowWindow (console_window
);
183 SelectWindow (console_window
);
184 /* force_update (console_window); */
192 int eventloopdone
= 0;
202 /* Figure out if the WaitNextEvent Trap is available. */
204 (NGetTrapAddress (0x60, ToolTrap
) != NGetTrapAddress (0x9f, ToolTrap
));
205 /* Pass WNE an empty region the 1st time thru. */
206 cursorRgn
= NewRgn ();
207 /* Go into the main event-handling loop. */
208 while (!eventloopdone
)
210 /* Use WaitNextEvent if it is available, otherwise GetNextEvent. */
213 get_global_mouse (&mouse
);
214 adjust_cursor (mouse
, cursorRgn
);
215 gotevent
= WaitNextEvent (everyEvent
, &event
, 0L, cursorRgn
);
220 gotevent
= GetNextEvent (everyEvent
, &event
);
222 /* First decide if the event is for a dialog or is just any old event. */
223 if (FrontWindow () != nil
&& IsDialogEvent (&event
))
228 /* Handle all the modeless dialogs here. */
229 if (DialogSelect (&event
, &dialog
, &itemhit
))
235 /* Make sure we have the right cursor before handling the event. */
236 adjust_cursor (event
.where
, cursorRgn
);
242 get_global_mouse (mouse
)
247 OSEventAvail (0, &evt
);
251 adjust_cursor (mouse
, region
)
257 /* Decipher an event, maybe do something with it. */
262 short part
, err
, rslt
= 0;
271 /* See if the click happened in a special part of the screen. */
272 part
= FindWindow (evt
->where
, &win
);
277 do_menu_command (MenuSelect (evt
->where
));
280 SystemClick (evt
, win
);
283 if (win
!= FrontWindow ())
285 /* Bring the clicked-on window to the front. */
287 /* Fix the menu to match the new front window. */
289 /* We always want to discard the event now, since clicks in a
290 windows are often irreversible actions. */
292 /* Mouse clicks in the front window do something useful. */
293 do_mouse_down (win
, evt
);
296 /* Standard drag behavior, no tricks necessary. */
297 DragWindow (win
, evt
->where
, &dragrect
);
300 grow_window (win
, evt
->where
);
304 zoom_window (win
, evt
->where
, part
);
313 key
= evt
->message
& charCodeMask
;
314 /* Check for menukey equivalents. */
315 if (evt
->modifiers
& cmdKey
)
317 if (evt
->what
== keyDown
)
320 do_menu_command (MenuKey (key
));
325 if (evt
->what
== keyDown
)
327 /* Random keypress, interpret it. */
328 do_keyboard_command (key
);
333 activate_window ((WindowPtr
) evt
->message
, evt
->modifiers
& activeFlag
);
336 update_window ((WindowPtr
) evt
->message
);
339 /* Call DIBadMount in response to a diskEvt, so that the user can format
340 a floppy. (from DTS Sample) */
341 if (HiWord (evt
->message
) != noErr
)
343 SetPt (&pnt
, 50, 50);
344 err
= DIBadMount (pnt
, evt
->message
);
348 /* Grab only a single byte. */
349 switch ((evt
->message
>> 24) & 0xFF)
354 inbackground
= !(evt
->message
& 1);
355 activate_window (FrontWindow (), !inbackground
);
359 case kHighLevelEvent
:
360 AEProcessAppleEvent (evt
);
371 grow_window (win
, where
)
379 winsize
= GrowWindow (win
, where
, &sizerect
);
384 EraseRect (&win
->portRect
);
385 h
= LoWord (winsize
);
386 v
= HiWord (winsize
);
387 SizeWindow (win
, h
, v
, 1);
388 if (win
== console_window
)
390 MoveControl(console_v_scrollbar
, h
- sbarwid
, 0);
391 SizeControl(console_v_scrollbar
, sbarwid
+ 1, v
- sbarwid
+ 1);
393 InvalRect (&win
->portRect
);
398 zoom_window (win
, where
, part
)
410 do_mouse_down (win
, event
)
416 ControlHandle control
;
418 if (1 /*is_app_window(win)*/)
421 mouse
= event
->where
;
422 GlobalToLocal (&mouse
);
423 part
= FindControl(mouse
, win
, &control
);
424 if (control
== console_v_scrollbar
)
430 TEClick (mouse
, 0, console_text
);
435 activate_window (win
, activate
)
439 if (win
== nil
) return;
440 /* It's convenient to make the activated window also be the
444 /* Activate the console window's scrollbar. */
445 if (win
== console_window
)
446 HiliteControl (console_v_scrollbar
, (activate
? 0 : 255));
452 int controls
= 1, growbox
= 0;
455 /* Set the updating window to be the current grafport. */
458 /* recalc_depths(); */
460 if (win
== console_window
)
467 UpdateControls (win
, win
->visRgn
);
478 do_menu_command (which
)
481 short menuid
, menuitem
;
490 menuid
= HiWord (which
);
491 menuitem
= LoWord (which
);
498 /* Alert(aAbout, nil); */
501 GetItem (GetMHandle (mApple
), menuitem
, daname
);
502 daRefNum
= OpenDeskAcc (daname
);
514 /* handledbyda = SystemEdit(menuitem-1); */
531 char commandbuf
[1000];
533 do_keyboard_command (key
)
536 int startpos
, endpos
, i
;
538 char buf
[10], *text_str
, *command
;
541 if (key
== '\015' || key
== '\003')
543 /* (should) Interpret the line as a command. */
544 text
= TEGetText (console_text
);
545 HLock ((Handle
) text
);
546 startpos
= (*console_text
)->selStart
;
547 endpos
= (*console_text
)->selEnd
;
548 if (startpos
!= endpos
)
550 strncpy (commandbuf
+ 1, *text
+ startpos
, endpos
- startpos
);
551 commandbuf
[1 + endpos
- startpos
] = 0;
552 command
= commandbuf
+ 1;
556 DebugStr("\plooking for command");
557 last_newline
= strrchr(*text
+startpos
, '\n');
560 strncpy (commandbuf
+ 1,
562 last_newline
- (*text
+startpos
));
563 commandbuf
[1 + last_newline
- (*text
+startpos
)] = 0;
564 command
= commandbuf
+ 1;
571 HUnlock ((Handle
) text
);
572 commandbuf
[0] = strlen(command
);
573 DebugStr(commandbuf
);
575 /* Insert a newline and redraw before doing the command. */
577 TEInsert (buf
, 1, console_text
);
578 TESetSelect (100000, 100000, console_text
);
581 execute_command (commandbuf
, 0);
582 bpstat_do_actions (&stop_bpstat
);
584 else if (0 /* editing chars... */)
589 /* A self-inserting character. */
591 TEInsert (buf
, 1, console_text
);
592 TESetSelect (100000, 100000, console_text
);
602 SetPort (console_window
);
603 TEUpdate (&(console_window
->portRect
), console_text
);
605 /* adjust_help_scrollbar(); */
608 /* Cause an update of a window's entire contents. */
615 if (win
== nil
) return;
618 EraseRect (&win
->portRect
);
619 InvalRect (&win
->portRect
);
623 adjust_console_scrollbars ()
625 int lines
, newmax
, value
;
627 lines
= (*console_text
)->nLines
;
628 newmax
= lines
- (((*console_text
)->viewRect
.bottom
- (*console_text
)->viewRect
.top
)
629 / (*console_text
)->lineHeight
);
630 if (newmax
< 0) newmax
= 0;
631 SetCtlMax (console_v_scrollbar
, newmax
);
632 value
= ((*console_text
)->viewRect
.top
- (*console_text
)->destRect
.top
)
633 / (*console_text
)->lineHeight
;
634 SetCtlValue (console_v_scrollbar
, value
);
637 /* Readline substitute. */
640 readline (char *prrompt
)
642 return gdb_readline (prrompt
);
645 char *rl_completer_word_break_characters
;
647 char *rl_completer_quote_characters
;
649 int (*rl_completion_entry_function
) ();
653 char *rl_line_buffer
;
655 char *rl_readline_name
;
657 /* History substitute. */
660 add_history (char *buf
)
665 stifle_history (int n
)
675 read_history (char *name
)
680 write_history (char *name
)
685 history_expand (char *x
, char **y
)
690 history_get (int xxx
)
698 filename_completion_function (char *text
, char *name
)
704 tilde_expand (char *str
)
706 return strsave (str
);
709 /* Modified versions of standard I/O. */
716 hacked_fprintf (FILE *fp
, const char *fmt
, ...)
722 if (mac_app
&& (fp
== stdout
|| fp
== stderr
))
726 ret
= vsprintf(buf
, fmt
, ap
);
727 TEInsert (buf
, strlen(buf
), console_text
);
728 TESetSelect (100000, 100000, console_text
);
732 ret
= vfprintf (fp
, fmt
, ap
);
740 hacked_printf (const char *fmt
, ...)
748 ret
= hacked_vfprintf(stdout
, fmt
, ap
);
751 ret
= vfprintf (stdout
, fmt
, ap
);
759 hacked_vfprintf (FILE *fp
, const char *format
, va_list args
)
761 if (mac_app
&& (fp
== stdout
|| fp
== stderr
))
766 ret
= vsprintf(buf
, format
, args
);
767 TEInsert (buf
, strlen(buf
), console_text
);
768 TESetSelect (100000, 100000, console_text
);
773 return vfprintf (fp
, format
, args
);
778 hacked_fputs (const char *s
, FILE *fp
)
780 if (mac_app
&& (fp
== stdout
|| fp
== stderr
))
782 TEInsert (s
, strlen(s
), console_text
);
783 TESetSelect (100000, 100000, console_text
);
788 return fputs (s
, fp
);
793 hacked_fputc (const char c
, FILE *fp
)
795 if (mac_app
&& (fp
== stdout
|| fp
== stderr
))
800 TEInsert (buf
, 1, console_text
);
801 TESetSelect (100000, 100000, console_text
);
806 return fputc (c
, fp
);
811 hacked_putc (const char c
, FILE *fp
)
813 if (mac_app
&& (fp
== stdout
|| fp
== stderr
))
818 TEInsert (buf
, 1, console_text
);
819 TESetSelect (100000, 100000, console_text
);
823 return fputc (c
, fp
);
828 hacked_fflush (FILE *fp
)
830 if (mac_app
&& (fp
== stdout
|| fp
== stderr
))