aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJim Kingdon <jkingdon@engr.sgi.com>1993-07-28 06:45:35 +0000
committerJim Kingdon <jkingdon@engr.sgi.com>1993-07-28 06:45:35 +0000
commit704deef2c0830b00aca6614989cf7944b38ebeba (patch)
tree8faf989eee64b6419088445e6e4587246f389b6c
parent157ea89d778f04125d60b9d2d8a80831b632bb38 (diff)
downloadgdb-704deef2c0830b00aca6614989cf7944b38ebeba.zip
gdb-704deef2c0830b00aca6614989cf7944b38ebeba.tar.gz
gdb-704deef2c0830b00aca6614989cf7944b38ebeba.tar.bz2
* serial.h, ser-{unix,go32,tcp}.c: Add flush_input and send_break.
* nindy-share/*, remote-nindy.c: Extensive hacking to make it conform to GDB conventions like using memcpy not bcopy, serial.h, etc. This is to make it host on Solaris, AIX, etc. * Makefile.in: Reflect removed nindy-share files.
-rw-r--r--gdb/ChangeLog6
-rw-r--r--gdb/remote-nindy.c349
-rw-r--r--gdb/ser-go32.c7
-rw-r--r--gdb/ser-tcp.c8
-rw-r--r--gdb/ser-unix.c42
-rw-r--r--gdb/serial.h16
6 files changed, 244 insertions, 184 deletions
diff --git a/gdb/ChangeLog b/gdb/ChangeLog
index 43e156c..fa4cf8d 100644
--- a/gdb/ChangeLog
+++ b/gdb/ChangeLog
@@ -2,7 +2,11 @@ Tue Jul 27 12:07:38 1993 Jim Kingdon (kingdon@lioth.cygnus.com)
* remote-udi.c: Remove old comment about download not implemented.
- * serial.h, ser-{unix,go32,tcp}.c: Add flush_input.
+ * serial.h, ser-{unix,go32,tcp}.c: Add flush_input and send_break.
+ * nindy-share/*, remote-nindy.c: Extensive hacking to make it
+ conform to GDB conventions like using memcpy not bcopy, serial.h,
+ etc. This is to make it host on Solaris, AIX, etc.
+ * Makefile.in: Reflect removed nindy-share files.
* stack.c (print_frame_info): Revise comment about `pathological'
case (there was a wrong FIXME about text labels; also asm() can
diff --git a/gdb/remote-nindy.c b/gdb/remote-nindy.c
index 55efac7..dd027bf 100644
--- a/gdb/remote-nindy.c
+++ b/gdb/remote-nindy.c
@@ -113,8 +113,11 @@ NINDY ROM monitor at the other end of the line.
#include <sys/ioctl.h>
#include <sys/file.h>
#include <ctype.h>
+#include "serial.h"
+#if 0
#include "nindy-share/ttycntl.h"
#include "nindy-share/demux.h"
+#endif
#include "nindy-share/env.h"
#include "nindy-share/stop.h"
@@ -139,7 +142,9 @@ char *nindy_ttyname; /* name of tty to talk to nindy on, or null */
#define TRUE 1
#define FALSE 0
-int nindy_fd = 0; /* Descriptor for I/O to NINDY */
+/* From nindy-share/nindy.c. */
+extern serial_t nindy_serial;
+
static int have_regs = 0; /* 1 iff regs read since i960 last halted */
static int regs_changed = 0; /* 1 iff regs were modified since last read */
@@ -157,55 +162,15 @@ nindy_fetch_registers PARAMS ((int));
static void
nindy_store_registers PARAMS ((int));
-/* FIXME, we can probably use the normal terminal_inferior stuff here.
- We have to do terminal_inferior and then set up the passthrough
- settings initially. Thereafter, terminal_ours and terminal_inferior
- will automatically swap the settings around for us. */
-
-/* Restore TTY to normal operation */
-
-static TTY_STRUCT orig_tty; /* TTY attributes before entering passthrough */
-
-static void
-restore_tty()
-{
- ioctl( 0, TIOCSETN, &orig_tty );
-}
-
-
-/* Recover from ^Z or ^C while remote process is running */
-
-static void (*old_ctrlc)(); /* Signal handlers before entering passthrough */
-
-#ifdef SIGTSTP
-static void (*old_ctrlz)();
-#endif
-
-static
-#ifdef USG
-void
-#endif
-cleanup()
-{
- restore_tty();
- signal(SIGINT, old_ctrlc);
-#ifdef SIGTSTP
- signal(SIGTSTP, old_ctrlz);
-#endif
- error("\n\nYou may need to reset the 80960 and/or reload your program.\n");
-}
-
-/* Clean up anything that needs cleaning when losing control. */
-
static char *savename;
static void
nindy_close (quitting)
int quitting;
{
- if (nindy_fd)
- close (nindy_fd);
- nindy_fd = 0;
+ if (nindy_serial != NULL)
+ SERIAL_CLOSE (nindy_serial);
+ nindy_serial = NULL;
if (savename)
free (savename);
@@ -229,25 +194,24 @@ nindy_open (name, from_tty)
nindy_close (0);
- have_regs = regs_changed = 0;
- dcache_init();
+ have_regs = regs_changed = 0;
+ dcache_init();
- /* Allow user to interrupt the following -- we could hang if
- * there's no NINDY at the other end of the remote tty.
- */
- immediate_quit++;
- nindy_fd = ninConnect( name, baud_rate? baud_rate: "9600",
- nindy_initial_brk, !from_tty, nindy_old_protocol );
- immediate_quit--;
+ /* Allow user to interrupt the following -- we could hang if there's
+ no NINDY at the other end of the remote tty. */
+ immediate_quit++;
+ ninConnect(name, baud_rate ? baud_rate : "9600",
+ nindy_initial_brk, !from_tty, nindy_old_protocol);
+ immediate_quit--;
- if ( nindy_fd < 0 ){
- nindy_fd = 0;
- error( "Can't open tty '%s'", name );
- }
+ if (nindy_serial == NULL)
+ {
+ perror_with_name (name);
+ }
- savename = savestring (name, strlen (name));
- push_target (&nindy_ops);
- target_fetch_registers(-1);
+ savename = savestring (name, strlen (name));
+ push_target (&nindy_ops);
+ target_fetch_registers(-1);
}
/* User-initiated quit of nindy operations. */
@@ -307,6 +271,27 @@ nindy_resume (step, siggnal)
have_regs = 0;
ninGo( step );
}
+
+/* FIXME, we can probably use the normal terminal_inferior stuff here.
+ We have to do terminal_inferior and then set up the passthrough
+ settings initially. Thereafter, terminal_ours and terminal_inferior
+ will automatically swap the settings around for us. */
+
+struct clean_up_tty_args {
+ serial_ttystate state;
+ serial_t serial;
+};
+
+static void
+clean_up_tty (ptrarg)
+ PTR ptrarg;
+{
+ struct clean_up_tty_args *args = (struct clean_up_tty_args *) ptrarg;
+ SERIAL_SET_TTY_STATE (args->serial, args->state);
+ free (args->state);
+ warning ("\n\n\
+You may need to reset the 80960 and/or reload your program.\n");
+}
/* Wait until the remote machine stops. While waiting, operate in passthrough
* mode; i.e., pass everything NINDY sends to stdout, and everything from
@@ -319,107 +304,120 @@ static int
nindy_wait( status )
WAITTYPE *status;
{
- DEMUX_DECL; /* OS-dependent data needed by DEMUX... macros */
- char buf[500]; /* FIXME, what is "500" here? */
- int i, n;
- unsigned char stop_exit;
- unsigned char stop_code;
- TTY_STRUCT tty;
- long ip_value, fp_value, sp_value; /* Reg values from stop */
-
-
- WSETEXIT( (*status), 0 );
-
- /* OPERATE IN PASSTHROUGH MODE UNTIL NINDY SENDS A DLE CHARACTER */
-
- /* Save current tty attributes, set up signals to restore them.
- */
- ioctl( 0, TIOCGETP, &orig_tty );
- old_ctrlc = signal( SIGINT, cleanup );
-#ifdef SIGTSTP
- old_ctrlz = signal( SIGTSTP, cleanup );
-#endif
-
- /* Pass input from keyboard to NINDY as it arrives.
- * NINDY will interpret <CR> and perform echo.
- */
- tty = orig_tty;
- TTY_NINDYTERM( tty );
- ioctl( 0, TIOCSETN, &tty );
-
- while ( 1 ){
- /* Go to sleep until there's something for us on either
- * the remote port or stdin.
- */
-
- DEMUX_WAIT( nindy_fd );
-
- /* Pass input through to correct place */
+ fd_set fds;
+ char buf[500]; /* FIXME, what is "500" here? */
+ int i, n;
+ unsigned char stop_exit;
+ unsigned char stop_code;
+ struct clean_up_tty_args tty_args;
+ struct cleanup *old_cleanups;
+ long ip_value, fp_value, sp_value; /* Reg values from stop */
+
+ WSETEXIT( (*status), 0 );
+
+ /* OPERATE IN PASSTHROUGH MODE UNTIL NINDY SENDS A DLE CHARACTER */
+
+ /* Save current tty attributes, and restore them when done. */
+ tty_args.serial = SERIAL_FDOPEN (0);
+ tty_args.state = SERIAL_GET_TTY_STATE (tty_args.serial);
+ old_cleanups = make_cleanup (clean_up_tty, &tty_args);
+
+ /* Pass input from keyboard to NINDY as it arrives. NINDY will interpret
+ <CR> and perform echo. */
+ /* This used to set CBREAK and clear ECHO and CRMOD. I hope this is close
+ enough. */
+ SERIAL_RAW (tty_args.serial);
+
+ while (1)
+ {
+ /* Wait for input on either the remote port or stdin. */
+ FD_ZERO (&fds);
+ FD_SET (0, &fds);
+ FD_SET (nindy_serial->fd, &fds);
+ if (select (nindy_serial->fd + 1, &fds, 0, 0, 0) <= 0)
+ continue;
+
+ /* Pass input through to correct place */
+ if (FD_ISSET (0, &fds))
+ {
+ /* Input on stdin */
+ n = read (0, buf, sizeof (buf));
+ if (n)
+ {
+ SERIAL_WRITE (nindy_serial, buf, n );
+ }
+ }
- n = DEMUX_READ( 0, buf, sizeof(buf) );
- if ( n ){ /* Input on stdin */
- write( nindy_fd, buf, n );
+ if (FD_ISSET (nindy_serial->fd, &fds))
+ {
+ /* Input on remote */
+ n = read (nindy_serial->fd, buf, sizeof (buf));
+ if (n)
+ {
+ /* Write out any characters in buffer preceding DLE */
+ i = non_dle( buf, n );
+ if ( i > 0 )
+ {
+ write (1, buf, i);
}
- n = DEMUX_READ( nindy_fd, buf, sizeof(buf) );
- if ( n ){ /* Input on remote */
- /* Write out any characters in buffer preceding DLE */
- i = non_dle( buf, n );
- if ( i > 0 ){
- write( 1, buf, i );
- }
-
- if ( i != n ){
- /* There *was* a DLE in the buffer */
- stop_exit = ninStopWhy( &stop_code,
- &ip_value, &fp_value, &sp_value);
- if ( !stop_exit && (stop_code==STOP_SRQ) ){
- immediate_quit++;
- ninSrq();
- immediate_quit--;
- } else {
- /* Get out of loop */
- supply_register (IP_REGNUM,
- (char *)&ip_value);
- supply_register (FP_REGNUM,
- (char *)&fp_value);
- supply_register (SP_REGNUM,
- (char *)&sp_value);
- break;
- }
- }
+ if (i != n)
+ {
+ /* There *was* a DLE in the buffer */
+ stop_exit = ninStopWhy(&stop_code,
+ &ip_value, &fp_value, &sp_value);
+ if (!stop_exit && (stop_code == STOP_SRQ))
+ {
+ immediate_quit++;
+ ninSrq();
+ immediate_quit--;
+ }
+ else
+ {
+ /* Get out of loop */
+ supply_register (IP_REGNUM,
+ (char *)&ip_value);
+ supply_register (FP_REGNUM,
+ (char *)&fp_value);
+ supply_register (SP_REGNUM,
+ (char *)&sp_value);
+ break;
+ }
}
+ }
}
+ }
- signal( SIGINT, old_ctrlc );
-#ifdef SIGTSTP
- signal( SIGTSTP, old_ctrlz );
-#endif
- restore_tty();
-
- if ( stop_exit ){ /* User program exited */
- WSETEXIT( (*status), stop_code );
- } else { /* Fault or trace */
- switch (stop_code){
- case STOP_GDB_BPT:
- case TRACE_STEP:
- /* Make it look like a VAX trace trap */
- stop_code = SIGTRAP;
- break;
- default:
- /* The target is not running Unix, and its
- faults/traces do not map nicely into Unix signals.
- Make sure they do not get confused with Unix signals
- by numbering them with values higher than the highest
- legal Unix signal. code in i960_print_fault(),
- called via PRINT_RANDOM_SIGNAL, will interpret the
- value. */
- stop_code += NSIG;
- break;
- }
- WSETSTOP( (*status), stop_code );
+ do_cleanups (old_cleanups);
+
+ if (stop_exit)
+ {
+ /* User program exited */
+ WSETEXIT ((*status), stop_code);
+ }
+ else
+ {
+ /* Fault or trace */
+ switch (stop_code)
+ {
+ case STOP_GDB_BPT:
+ case TRACE_STEP:
+ /* Breakpoint or single stepping. */
+ stop_code = SIGTRAP;
+ break;
+ default:
+ /* The target is not running Unix, and its faults/traces do
+ not map nicely into Unix signals. Make sure they do not
+ get confused with Unix signals by numbering them with
+ values higher than the highest legal Unix signal. code
+ in i960_print_fault(), called via PRINT_RANDOM_SIGNAL,
+ will interpret the value. */
+ stop_code += NSIG;
+ break;
}
- return inferior_pid;
+ WSETSTOP ((*status), stop_code);
+ }
+ return inferior_pid;
}
/* Read the remote registers into the block REGS. */
@@ -446,11 +444,11 @@ nindy_fetch_registers(regno)
ninRegsGet( (char *) &nindy_regs );
immediate_quit--;
- bcopy (nindy_regs.local_regs, &registers[REGISTER_BYTE (R0_REGNUM)], 16*4);
- bcopy (nindy_regs.global_regs, &registers[REGISTER_BYTE (G0_REGNUM)], 16*4);
- bcopy (nindy_regs.pcw_acw, &registers[REGISTER_BYTE (PCW_REGNUM)], 2*4);
- bcopy (nindy_regs.ip, &registers[REGISTER_BYTE (IP_REGNUM)], 1*4);
- bcopy (nindy_regs.tcw, &registers[REGISTER_BYTE (TCW_REGNUM)], 1*4);
+ memcpy (&registers[REGISTER_BYTE (R0_REGNUM)], nindy_regs.local_regs, 16*4);
+ memcpy (&registers[REGISTER_BYTE (G0_REGNUM)], nindy_regs.global_regs, 16*4);
+ memcpy (&registers[REGISTER_BYTE (PCW_REGNUM)], nindy_regs.pcw_acw, 2*4);
+ memcpy (&registers[REGISTER_BYTE (IP_REGNUM)], nindy_regs.ip, 1*4);
+ memcpy (&registers[REGISTER_BYTE (TCW_REGNUM)], nindy_regs.tcw, 1*4);
for (regnum = FP0_REGNUM; regnum < FP0_REGNUM + 4; regnum++) {
dub = unpack_double (builtin_type_double,
&nindy_regs.fp_as_double[8 * (regnum - FP0_REGNUM)],
@@ -478,11 +476,11 @@ nindy_store_registers(regno)
int regnum, inv;
double dub;
- bcopy (&registers[REGISTER_BYTE (R0_REGNUM)], nindy_regs.local_regs, 16*4);
- bcopy (&registers[REGISTER_BYTE (G0_REGNUM)], nindy_regs.global_regs, 16*4);
- bcopy (&registers[REGISTER_BYTE (PCW_REGNUM)], nindy_regs.pcw_acw, 2*4);
- bcopy (&registers[REGISTER_BYTE (IP_REGNUM)], nindy_regs.ip, 1*4);
- bcopy (&registers[REGISTER_BYTE (TCW_REGNUM)], nindy_regs.tcw, 1*4);
+ memcpy (nindy_regs.local_regs, &registers[REGISTER_BYTE (R0_REGNUM)], 16*4);
+ memcpy (nindy_regs.global_regs, &registers[REGISTER_BYTE (G0_REGNUM)], 16*4);
+ memcpy (nindy_regs.pcw_acw, &registers[REGISTER_BYTE (PCW_REGNUM)], 2*4);
+ memcpy (nindy_regs.ip, &registers[REGISTER_BYTE (IP_REGNUM)], 1*4);
+ memcpy (nindy_regs.tcw, &registers[REGISTER_BYTE (TCW_REGNUM)], 1*4);
/* Float regs. Only works on IEEE_FLOAT hosts. FIXME! */
for (regnum = FP0_REGNUM; regnum < FP0_REGNUM + 4; regnum++) {
ieee_extended_to_double (&ext_format_i960,
@@ -493,8 +491,7 @@ nindy_store_registers(regno)
This mostly works but not quite. */
dub = unpack_double (builtin_type_double, (char *)&dub, &inv);
/* dub now in target byte order */
- bcopy ((char *)&dub, &nindy_regs.fp_as_double[8 * (regnum - FP0_REGNUM)],
- 8);
+ memcpy (&nindy_regs.fp_as_double[8 * (regnum - FP0_REGNUM)], &dub, 8);
}
immediate_quit++;
@@ -565,7 +562,7 @@ nindy_xfer_inferior_memory(memaddr, myaddr, len, write, target)
/* Copy data to be written over corresponding part of buffer */
- bcopy (myaddr, (char *) buffer + (memaddr & (sizeof (int) - 1)), len);
+ memcpy ((char *) buffer + (memaddr & (sizeof (int) - 1)), myaddr, len);
/* Write the entire buffer. */
@@ -590,7 +587,7 @@ nindy_xfer_inferior_memory(memaddr, myaddr, len, write, target)
}
/* Copy appropriate bytes out of the buffer. */
- bcopy ((char *) buffer + (memaddr & (sizeof (int) - 1)), myaddr, len);
+ memcpy (myaddr, (char *) buffer + (memaddr & (sizeof (int) - 1)), len);
}
return len;
}
@@ -808,13 +805,15 @@ reset_command(args, from_tty)
char *args;
int from_tty;
{
- if ( !nindy_fd ){
- error( "No target system to reset -- use 'target nindy' command.");
- }
- if ( query("Really reset the target system?",0,0) ){
- send_break( nindy_fd );
- tty_flush( nindy_fd );
- }
+ if (nindy_serial == NULL)
+ {
+ error( "No target system to reset -- use 'target nindy' command.");
+ }
+ if ( query("Really reset the target system?",0,0) )
+ {
+ SERIAL_SEND_BREAK (nindy_serial);
+ tty_flush (nindy_serial);
+ }
}
void
diff --git a/gdb/ser-go32.c b/gdb/ser-go32.c
index ff1bdf1..905526d 100644
--- a/gdb/ser-go32.c
+++ b/gdb/ser-go32.c
@@ -267,10 +267,9 @@ go32_open (scb, name)
}
static int
-go32_flush_output (scb)
+go32_noop (scb)
serial_t scb;
{
- /* No need to flush, because there is no buffering. */
return 0;
}
@@ -378,7 +377,9 @@ static struct serial_ops go32_ops =
go32_close,
go32_readchar,
go32_write,
- go32_flush_output,
+ go32_noop, /* flush output */
+ go32_noop, /* flush input */
+ go32_noop, /* send break -- currently used only for nindy */
go32_raw,
go32_get_tty_state,
go32_set_tty_state,
diff --git a/gdb/ser-tcp.c b/gdb/ser-tcp.c
index 6ff79aa..f492bc1 100644
--- a/gdb/ser-tcp.c
+++ b/gdb/ser-tcp.c
@@ -141,11 +141,9 @@ tcp_set_tty_state(scb, ttystate)
}
static int
-tcp_flush_output (scb)
+tcp_return_0 (scb)
serial_t scb;
{
- /* This is only used by utils.c on stdout, so it doesn't need to work
- for tcp. */
return 0;
}
@@ -309,7 +307,9 @@ static struct serial_ops tcp_ops =
tcp_close,
tcp_readchar,
tcp_write,
- tcp_flush_output,
+ tcp_return_0, /* flush output */
+ tcp_return_0, /* flush input */
+ tcp_return_0, /* send break */
tcp_raw,
tcp_get_tty_state,
tcp_set_tty_state,
diff --git a/gdb/ser-unix.c b/gdb/ser-unix.c
index 5f07ade..1f8d738 100644
--- a/gdb/ser-unix.c
+++ b/gdb/ser-unix.c
@@ -326,6 +326,46 @@ hardwire_flush_output (scb)
#endif
}
+static int
+hardwire_flush_input (scb)
+ serial_t scb;
+{
+#ifdef HAVE_TERMIOS
+ return tcflush (scb->fd, TCIFLUSH);
+#endif
+
+#ifdef HAVE_TERMIO
+ return ioctl (scb->fd, TCFLSH, 0);
+#endif
+
+#ifdef HAVE_SGTTY
+ /* This flushes both input and output, but we can't do better. */
+ return ioctl (scb->fd, TIOCFLUSH, 0);
+#endif
+}
+
+static int
+hardwire_send_break (scb)
+ serial_t scb;
+{
+ int status;
+
+#ifdef HAVE_TERMIOS
+ return tcsendbreak (scb->fd, 0);
+#endif
+
+#ifdef HAVE_TERMIO
+ return ioctl (scb->fd, TCSBRK, 0);
+#endif
+
+#ifdef HAVE_SGTTY
+ status = ioctl (scb->fd, TIOCSBRK, 0);
+ usleep (250000);
+ status = ioctl (scb->fd, TIOCCBRK, 0);
+ return status;
+#endif
+}
+
static void
hardwire_raw(scb)
serial_t scb;
@@ -607,6 +647,8 @@ static struct serial_ops hardwire_ops =
hardwire_readchar,
hardwire_write,
hardwire_flush_output,
+ hardwire_flush_input,
+ hardwire_send_break,
hardwire_raw,
hardwire_get_tty_state,
hardwire_set_tty_state,
diff --git a/gdb/serial.h b/gdb/serial.h
index 630ed43..a9dba27 100644
--- a/gdb/serial.h
+++ b/gdb/serial.h
@@ -42,6 +42,8 @@ struct serial_ops {
int (*readchar) PARAMS ((serial_t, int timeout));
int (*write) PARAMS ((serial_t, const char *str, int len));
int (*flush_output) PARAMS ((serial_t));
+ int (*flush_input) PARAMS ((serial_t));
+ int (*send_break) PARAMS ((serial_t));
void (*go_raw) PARAMS ((serial_t));
serial_ttystate (*get_tty_state) PARAMS ((serial_t));
int (*set_tty_state) PARAMS ((serial_t, serial_ttystate));
@@ -72,11 +74,23 @@ serial_t serial_fdopen PARAMS ((int fd));
#define SERIAL_FDOPEN(FD) serial_fdopen(FD)
-/* Flush pending output. */
+/* Flush pending output. Might also flush input (if this system can't flush
+ only output). */
#define SERIAL_FLUSH_OUTPUT(SERIAL_T) \
((SERIAL_T)->ops->flush_output((SERIAL_T)))
+/* Flush pending input. Might also flush output (if this system can't flush
+ only input). */
+
+#define SERIAL_FLUSH_INPUT(SERIAL_T)\
+ ((*(SERIAL_T)->ops->flush_input) ((SERIAL_T)))
+
+/* Send a break between 0.25 and 0.5 seconds long. */
+
+#define SERIAL_SEND_BREAK(SERIAL_T) \
+ ((*(SERIAL_T)->ops->send_break) (SERIAL_T))
+
/* Turn the port into raw mode. */
#define SERIAL_RAW(SERIAL_T) (SERIAL_T)->ops->go_raw((SERIAL_T))