|
|
DataMuseum.dkPresents historical artifacts from the history of: DKUUG/EUUG Conference tapes |
This is an automatic "excavation" of a thematic subset of
See our Wiki for more about DKUUG/EUUG Conference tapes Excavated with: AutoArchaeologist - Free & Open Source Software. |
top - metrics - downloadIndex: T d
Length: 8717 (0x220d)
Types: TextFile
Names: »debugger.c,v«
└─⟦a05ed705a⟧ Bits:30007078 DKUUG GNU 2/12/89
└─⟦34cc4e2f7⟧ »./UNRELEASED/xgdb3.2.tar.Z«
└─⟦80fac5d7c⟧
└─⟦this⟧ »./RCS/debugger.c,v«
head 1.1;
access ;
symbols ;
locks hubbard:1.1; strict;
comment @ * @;
1.1
date 89.07.05.15.35.57; author hubbard; state Exp;
branches ;
next ;
desc
@Initial checkin, Beta version 0.1.
@
1.1
log
@Initial revision
@
text
@\f
#ifndef lint
static char rcsid[] = "$Header$";
#endif
/*
*
* Copyright 1988, 1989
* PCS Computer Systeme, GmbH
* Munich, West Germany
*
* All rights reserved.
*
* This is unsupported software and is subject to change without notice.
* PCS makes no representations about the suitability of this software
* for any purpose. It is supplied "as is" without express or implied
* warranty.
*
* Permission to use, copy, modify, and distribute this software and its
* documentation for any purpose and without fee is hereby granted, provided
* that the above copyright notice appear in all copies and that both that
* copyright notice and this permission notice appear in supporting
* documentation, and that the name of PCS Computer Systeme not be used in
* advertising or publicity pertaining to distribution of the software
* without specific, written prior permission.
*
*/
/*
* Author: Jordan K. Hubbard
* For: PCS Computer Systems, GmbH.
* Why: Because we like you.
* When: February 10th, 1989.
*
* $Log$
*
*/
#include "xgdb.h"
/*
* Debugger independant commands. These are routines that will probably
* work with just about any debugger, but maybe not yours. Only guaranteed
* to work with gdb.
*/
/* Confirm a quit */
void quitp(w, client_data, data)
Widget w;
caddr_t client_data, data;
{
static void quit(), dont_quit();
static char *quit_msg = "Are you sure you want to quit?";
Entry("quitp");
yesOrNo(NULL, quit_msg, strlen(quit_msg), quit, dont_quit);
Leave_void;
}
/* Refuse quit. */
static void dont_quit(w, client_data, data)
Widget w;
caddr_t client_data, data;
{
Entry("dont_quit");
XtPopdown((Widget)client_data);
Leave_void;
}
/* Kill the debugger and exit */
static void quit(w, client_data, data)
Widget w;
caddr_t client_data;
caddr_t data;
{
Entry("quit");
if (entryOnQueue(&ProcQueue, DebuggerProcess))
nukeProcess(DebuggerProcess);
XtDestroyWidget(Toplevel);
exit(0);
/* NOTREACHED */
Leave_void;
}
void restart(w, client_data, data)
Widget w;
caddr_t client_data;
caddr_t data;
{
Entry("restart");
/* If the debugger lives, kill it. */
if (entryOnQueue(&ProcQueue, DebuggerProcess))
nukeProcess(DebuggerProcess);
DebuggerProcess = launchProcess(app_resources.debugger, DebuggerArgs,
processDebuggerOutput, NULL,
handleDebuggerTermination);
if (!DebuggerProcess)
puke_and_die("Can't restart debugger '%s'", app_resources.debugger);
DebuggerProcess->view = &Output;
setInitialDebuggerState(DebuggerProcess);
Leave_void;
}
/*
* The following routines deal with output redirection.
*/
static struct {
View *defaultView;
View *currentView;
Parser *currentParser, *defaultParser;
Boolean installView;
Boolean state;
} Diversion;
/*
* Close output diversion shell view.
*/
static void closeDiversion(w, client_data, data)
Widget w;
caddr_t client_data, data;
{
View *cls;
FieldAttributes fla;
Entry("closeDiversion");
cls = (View *)client_data;
/*
* Are we closing the current view, or just a previous one?
*/
if (cls == Diversion.currentView) {
if (!entryOnQueue(&ParserQueue, Diversion.defaultParser))
replaceQueueEntry(&ParserQueue, Diversion.currentParser,
Diversion.defaultParser);
/* Set the debugger output area's label back */
fla.label = app_resources.debugger;
changeField(nameToField(app_resources.debugger, OutputButtons),
FldLabel, &fla);
Diversion.currentView = (View *)NULL;
Diversion.state = FALSE;
}
viewDestroyShell(cls);
Leave_void;
}
static void divertToView(P_ARGS)
P_ARG_DECL;
{
Entry("divertToView");
if (s && len && *len)
viewAppendText(Diversion.currentView, s, *len);
Leave_void;
}
static void createDiversion(name)
String name;
{
char msg[256];
static SimpleField btns[] = {
{ "close", closeDiversion },
{ NULL, NULL },
};
FieldAttributes fla;
Entry("createDiversion");
ii = 0;
Diversion.currentView = viewCreateShell(name,
convertSimpleToField(btns, NULL),
ttyWidgetClass,
aa, ii);
Diversion.installView = FALSE;
replaceQueueEntry(&ParserQueue, Diversion.defaultParser,
Diversion.currentParser);
sprintf(msg, "Redirect to %s", name);
fla.label = msg;
changeField(nameToField(app_resources.debugger, OutputButtons), FldLabel,
&fla);
Leave_void;
}
void redirectOutput(w, client_data, data)
Widget w;
caddr_t client_data;
caddr_t data;
{
FieldAttributes fla;
Entry("redirectOutput");
Diversion.state = !Diversion.state;
if (Diversion.state) {
if (!Diversion.currentParser)
Diversion.currentParser = createParser(divertToView);
if (!Diversion.defaultParser)
Diversion.defaultParser = Generic;
if (!Diversion.defaultView)
Diversion.defaultView = (View *)client_data;
Diversion.installView = TRUE;
fla.label = "waiting for command...";
changeField(nameToField(app_resources.debugger, OutputButtons),
FldLabel, &fla);
}
else {
if (!entryOnQueue(&ParserQueue, Diversion.defaultParser))
replaceQueueEntry(&ParserQueue, Diversion.currentParser,
Diversion.defaultParser);
Diversion.installView = FALSE;
Diversion.currentView = (View *)NULL;
fla.label = app_resources.debugger;
changeField(nameToField(app_resources.debugger, OutputButtons),
FldLabel, &fla);
}
Leave_void;
}
void sendToDebugger(w, client_data, data)
Widget w;
caddr_t client_data, data;
{
char name[256], *cp, *cp2;
String tmp = (String)data;
Entry("sendToDebugger");
if (Diversion.installView) {
/* Figure out what to name the diversion */
name[0] = '\0';
/* If there's something in the input area, take that. */
cp = getInputAsString(0, 0);
if (cp) {
if (cp2 = (String)oneLine(cp))
strncpy(name, cp2, 255);
XtFree(cp);
}
/* No? Ok, how about the first line of the command? */
else if ((cp = (String)oneLine(tmp)) && strlen(cp))
strncpy(name, cp, 255);
else /* Still no? Ok.. */
strcpy(name, "<diverted output>");
createDiversion(name);
}
sendToProcess(DebuggerProcess, tmp);
dbg_state.S_userInput = TRUE; /* last input was interactive */
Leave_void;
}
void interruptDebugger(w, client_data, data)
Widget w;
caddr_t client_data, data;
{
Entry("interruptDebugger");
sendProcessSignal(DebuggerProcess, SIGINT);
Leave_void;
}
/*
* Turn array of bytes (source for Input) into proper C string. If term
* is non-zero, make sure string ends with it. If start is non-zero,
* concatenate the new string to it.
*/
String getInputAsString(start, term)
String start;
char term;
{
String tmp;
int len, nlen;
Entry("getInputAsString");
/*
* an XtGetValues on XtNlength (yes, with the addr of len) doesn't
* work! Hence this cruft.
*/
XtTextSetInsertionPoint(Input, MAX_CMD_LEN + 1);
len = XtTextGetInsertionPoint(Input);
if (!len && !start && !term)
Leave(NULL);
nlen = len + (term ? 2 : 1) + (start ? strlen(start) : 0);
tmp = XtMalloc(nlen);
if (start) {
strcpy(tmp, start);
if (len)
strncat(tmp, DebuggerCommandBuffer, len);
}
else if (len)
strncpy(tmp, DebuggerCommandBuffer, len);
if (term && tmp[nlen - 2] != term) {
tmp[nlen - 2] = '\n';
tmp[nlen - 1] = '\0';
}
else
tmp[nlen - 1] = '\0';
Leave(tmp);
}
/*
* Respond to a question from the debugger requiring a yes or no
* answer.
*/
void debuggerYesOrNo(T_PROC_ARGS)
T_PROC_DECL;
{
static void debuggerSendYes(), debuggerSendNo(); /* below */
Entry("debuggerYesOrNo");
yesOrNo(p, s, len, debuggerSendYes, debuggerSendNo);
Leave_void;
}
static void debuggerSendYes(w, client_data, data)
Widget w;
caddr_t client_data, data;
{
Entry("debuggerSendYes");
sendToProcess(DebuggerProcess, "y\n");
XtPopdown((Widget)client_data);
Leave_void;
}
static void debuggerSendNo(w, client_data, data)
Widget w;
caddr_t client_data, data;
{
Entry("DebuggerSendNo");
sendToProcess(DebuggerProcess, "n\n");
XtPopdown((Widget)client_data);
Leave_void;
}
@