diff options
author | grog <grog@FreeBSD.org> | 2000-04-25 01:41:57 +0000 |
---|---|---|
committer | grog <grog@FreeBSD.org> | 2000-04-25 01:41:57 +0000 |
commit | 097f16c8b74bbae63bf56d45609317041687fd69 (patch) | |
tree | 1a5e2ef34bf5bc37a2c7e8651f8856b070198840 | |
parent | 66cb354e5f41156c29df4f9cce2d547df63fdfe4 (diff) | |
download | FreeBSD-src-097f16c8b74bbae63bf56d45609317041687fd69.zip FreeBSD-src-097f16c8b74bbae63bf56d45609317041687fd69.tar.gz |
Fix a long-standing bug which caused massive character loss in remote
serial gdb: interrupts were causing either overruns or stealing
characters. Put splhigh() around the routines which transfer packets
across the line. Since this happens when the system is halted in
debug, this doesn't cause any particular problem. Now it is possible
to run the link at 115,200 bps.
PR: (not assigned yet, must be in limbo somewhere)
Add partial support for detecting non-existent gdb devices.
Add $FreeBSD$ tag.
-rw-r--r-- | sys/amd64/amd64/amd64-gdbstub.c | 20 | ||||
-rw-r--r-- | sys/i386/i386/i386-gdbstub.c | 20 |
2 files changed, 30 insertions, 10 deletions
diff --git a/sys/amd64/amd64/amd64-gdbstub.c b/sys/amd64/amd64/amd64-gdbstub.c index a2323ce..71c4719 100644 --- a/sys/amd64/amd64/amd64-gdbstub.c +++ b/sys/amd64/amd64/amd64-gdbstub.c @@ -91,6 +91,7 @@ * $m0,10#2a +$00010203040506070809101112131415#42 * ****************************************************************************/ +/* $FreeBSD$ */ #include <sys/param.h> #include <sys/reboot.h> @@ -104,10 +105,10 @@ #include "sio.h" #include "opt_ddb.h" -void gdb_handle_exception (db_regs_t *, int, int); +int gdb_handle_exception (db_regs_t *, int, int); #if NSIO == 0 -void +int gdb_handle_exception (db_regs_t *raw_regs, int type, int code) { } @@ -185,7 +186,9 @@ getpacket (char *buffer) int i; int count; unsigned char ch; + int s; + s = splhigh (); do { /* wait around for the start character, ignore all other characters */ @@ -236,6 +239,7 @@ getpacket (char *buffer) } } while (checksum != xmitcsum); + splx (s); } /* send the packet in buffer. */ @@ -246,8 +250,10 @@ putpacket (char *buffer) unsigned char checksum; int count; unsigned char ch; + int s; /* $<packet info>#<checksum>. */ + s = splhigh (); do { /* @@ -279,6 +285,7 @@ putpacket (char *buffer) putDebugChar (hexchars[checksum & 0xf]); } while ((getDebugChar () & 0x7f) != '+'); + splx (s); } static char remcomInBuffer[BUFMAX]; @@ -418,7 +425,7 @@ hexToInt(char **ptr, int *intValue) /* * This function does all command procesing for interfacing to gdb. */ -void +int gdb_handle_exception (db_regs_t *raw_regs, int type, int code) { int sigval; @@ -492,6 +499,8 @@ gdb_handle_exception (db_regs_t *raw_regs, int type, int code) while (1) { + if (gdbdev == NODEV) /* somebody's removed it */ + return 1; /* get out of here */ remcomOutBuffer[0] = 0; getpacket (remcomInBuffer); @@ -507,7 +516,7 @@ gdb_handle_exception (db_regs_t *raw_regs, int type, int code) case 'D': /* detach; say OK and turn off gdb */ putpacket(remcomOutBuffer); boothowto &= ~RB_GDB; - return; + return 0; case 'g': /* return the value of the CPU registers */ mem2hex ((vm_offset_t)®isters, remcomOutBuffer, NUMREGBYTES); @@ -606,12 +615,13 @@ gdb_handle_exception (db_regs_t *raw_regs, int type, int code) raw_regs->tf_ss = registers.ss; raw_regs->tf_ds = registers.ds; raw_regs->tf_es = registers.es; - return; + return 0; } /* switch */ /* reply to the request */ putpacket (remcomOutBuffer); } + return 0; } #endif /* NSIO > 0 */ diff --git a/sys/i386/i386/i386-gdbstub.c b/sys/i386/i386/i386-gdbstub.c index a2323ce..71c4719 100644 --- a/sys/i386/i386/i386-gdbstub.c +++ b/sys/i386/i386/i386-gdbstub.c @@ -91,6 +91,7 @@ * $m0,10#2a +$00010203040506070809101112131415#42 * ****************************************************************************/ +/* $FreeBSD$ */ #include <sys/param.h> #include <sys/reboot.h> @@ -104,10 +105,10 @@ #include "sio.h" #include "opt_ddb.h" -void gdb_handle_exception (db_regs_t *, int, int); +int gdb_handle_exception (db_regs_t *, int, int); #if NSIO == 0 -void +int gdb_handle_exception (db_regs_t *raw_regs, int type, int code) { } @@ -185,7 +186,9 @@ getpacket (char *buffer) int i; int count; unsigned char ch; + int s; + s = splhigh (); do { /* wait around for the start character, ignore all other characters */ @@ -236,6 +239,7 @@ getpacket (char *buffer) } } while (checksum != xmitcsum); + splx (s); } /* send the packet in buffer. */ @@ -246,8 +250,10 @@ putpacket (char *buffer) unsigned char checksum; int count; unsigned char ch; + int s; /* $<packet info>#<checksum>. */ + s = splhigh (); do { /* @@ -279,6 +285,7 @@ putpacket (char *buffer) putDebugChar (hexchars[checksum & 0xf]); } while ((getDebugChar () & 0x7f) != '+'); + splx (s); } static char remcomInBuffer[BUFMAX]; @@ -418,7 +425,7 @@ hexToInt(char **ptr, int *intValue) /* * This function does all command procesing for interfacing to gdb. */ -void +int gdb_handle_exception (db_regs_t *raw_regs, int type, int code) { int sigval; @@ -492,6 +499,8 @@ gdb_handle_exception (db_regs_t *raw_regs, int type, int code) while (1) { + if (gdbdev == NODEV) /* somebody's removed it */ + return 1; /* get out of here */ remcomOutBuffer[0] = 0; getpacket (remcomInBuffer); @@ -507,7 +516,7 @@ gdb_handle_exception (db_regs_t *raw_regs, int type, int code) case 'D': /* detach; say OK and turn off gdb */ putpacket(remcomOutBuffer); boothowto &= ~RB_GDB; - return; + return 0; case 'g': /* return the value of the CPU registers */ mem2hex ((vm_offset_t)®isters, remcomOutBuffer, NUMREGBYTES); @@ -606,12 +615,13 @@ gdb_handle_exception (db_regs_t *raw_regs, int type, int code) raw_regs->tf_ss = registers.ss; raw_regs->tf_ds = registers.ds; raw_regs->tf_es = registers.es; - return; + return 0; } /* switch */ /* reply to the request */ putpacket (remcomOutBuffer); } + return 0; } #endif /* NSIO > 0 */ |