Re: Setting parity for remote serial

Yurij Grechishhev
2013-07-24T14:29:21Z

Updated patch for serial parity support:

diff -up ../../../gdb_old/gdb-7.6/gdb/doc/ChangeLog gdb/doc/ChangeLog
--- ../../../gdb_old/gdb-7.6/gdb/doc/ChangeLog 2013-07-10
21:55:24.921750052 +0400
+++ gdb/doc/ChangeLog 2013-07-16 18:46:31.425614819 +0400
@@ -1,3 +1,6 @@
+2013-07-16 Yurij Grechishhev <yurij.grechishhev@gmail.com>
+ * gdb.texinfo (Remote configuration): Document "set/show
+ remoteparity".
2013-04-12 Jan Kratochvil <jan.kratochvil@redhat.com>
Eli Zaretskii <eliz@gnu.org>

diff -up ../../../gdb_old/gdb-7.6/gdb/doc/gdb.texinfo gdb/doc/gdb.texinfo
--- ../../../gdb_old/gdb-7.6/gdb/doc/gdb.texinfo 2013-07-10
21:55:25.257751657 +0400
+++ gdb/doc/gdb.texinfo 2013-07-16 18:04:54.128738129 +0400
@@ -18168,6 +18168,13 @@ default is not to record at all.
Show the current setting of the file name on which to record the
serial communications.

+@item set remoteparity @var{parity}
+Set the parity for the remote serial I/O. Supported values of @var{parity} are:
+@code{even}, @code{none}, and @code{odd}. The default is @code{none}.
+
+@item show remoteparity
+Show the current parity of the serial port.
+
@item set remotetimeout @var{num}
@cindex timeout for serial communications
@cindex remote timeout

diff -up ../../../gdb_old/gdb-7.6/gdb/ChangeLog gdb/ChangeLog
--- ../../../gdb_old/gdb-7.6/gdb/ChangeLog 2013-07-10
21:55:22.485750321 +0400
+++ gdb/ChangeLog 2013-07-16 17:33:47.467613587 +0400
@@ -1,3 +1,29 @@
+2013-07-16 Yurij Grechishhev <yurij.grechishhev@gmail.com>
+ * monitor.c (monitor_open): Add serial_setparity.
+ * remote.c (remote_open_1): Likewise.
+ * ser-base.c (ser_base_serparity): New function.
+ * ser-base.h: Add ser_base_setparity declaration.
+ * serail.c: Add serial_parity declaration and definitions of
+ parity_enums and parity.
+ (set_parity): New function.
+ (serial_setparity): New function.
+ (_initialize_serial): Add set/show remoteparity command description
+ * serial.h: Add GDBPARITY_NONE, GDBPARITY_ODD, GDBPARITY_EVEN
+ definitions. Add serial_setparity declaration.
+ (serial_ops): Add setparity entry.
+ * ser-mingw.c (ser_windows_raw): Remove state.fParity and
+ state.Parity definitions.
+ (ser_windows_setparity): New function.
+ (_initialize_ser_windows): ops->setparity setting.
+ * ser-pipe.c (_initialize_ser_pipe): Likewise.
+ * ser-tcp.c (_initialize_ser_tcp): Likewise.
+ * ser-unix.c: Add hardwire_setparity declaration.
+ (hardwire_setparity): New function.
+ (_initialize_ser_hardwire): ops->setparity setting.
+ * target.h: serial_parity declaration.
+ * top.c: serial_parity definition.
+
+
2013-04-26 Joel Brobecker <brobecker@adacore.com>

* NEWS: Change "since GDB 7.5" into "in GDB 7.6".
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/cli and gdb/cli
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/common and gdb/common
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/config and gdb/config
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/contrib and gdb/contrib
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/data-directory and
gdb/data-directory
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/doc and gdb/doc
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/features and gdb/features
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/gdbserver and gdb/gdbserver
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/gnulib and gdb/gnulib
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/mi and gdb/mi
diff -up ../../../gdb_old/gdb-7.6/gdb/monitor.c gdb/monitor.c
--- ../../../gdb_old/gdb-7.6/gdb/monitor.c 2013-07-10
21:55:33.656750073 +0400
+++ gdb/monitor.c 2013-07-04 23:54:32.472595952 +0400
@@ -768,6 +768,7 @@ monitor_open (char *args, struct monitor
}
}

+ serial_setparity (monitor_desc, serial_parity);
serial_raw (monitor_desc);

serial_flush_input (monitor_desc);
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/po and gdb/po
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/python and gdb/python
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/regformats and
gdb/regformats
diff -up ../../../gdb_old/gdb-7.6/gdb/remote.c gdb/remote.c
--- ../../../gdb_old/gdb-7.6/gdb/remote.c 2013-07-10 21:55:34.645747970 +0400
+++ gdb/remote.c 2013-07-04 23:50:52.855721644 +0400
@@ -4256,6 +4256,7 @@ remote_open_1 (char *name, int from_tty,
}
}

+ serial_setparity(remote_desc, serial_parity);
serial_raw (remote_desc);

/* If there is something sitting in the buffer we might take it as a
diff -up ../../../gdb_old/gdb-7.6/gdb/ser-base.c gdb/ser-base.c
--- ../../../gdb_old/gdb-7.6/gdb/ser-base.c 2013-07-10
21:55:24.161873687 +0400
+++ gdb/ser-base.c 2013-07-05 00:28:55.795720278 +0400
@@ -536,6 +536,14 @@ ser_base_setbaudrate (struct serial *scb
return 0; /* Never fails! */
}

+
+int
+ser_base_setparity (struct serial *scb, int num)
+{
+ return 0; /* Never fails! */
+}
+
+
int
ser_base_setstopbits (struct serial *scb, int num)
{
diff -up ../../../gdb_old/gdb-7.6/gdb/ser-base.h gdb/ser-base.h
--- ../../../gdb_old/gdb-7.6/gdb/ser-base.h 2013-07-10
21:55:24.168750025 +0400
+++ gdb/ser-base.h 2013-07-05 00:30:36.017596667 +0400
@@ -43,6 +43,7 @@ extern int ser_base_noflush_set_tty_stat
serial_ttystate old_ttystate);
extern int ser_base_setbaudrate (struct serial *scb, int rate);
extern int ser_base_setstopbits (struct serial *scb, int rate);
+extern int ser_base_setparity (struct serial *scb, int parity);
extern int ser_base_drain_output (struct serial *scb);

extern int ser_base_write (struct serial *scb, const char *str, int len);
diff -up ../../../gdb_old/gdb-7.6/gdb/serial.c gdb/serial.c
--- ../../../gdb_old/gdb-7.6/gdb/serial.c 2013-07-10 21:55:35.224750365 +0400
+++ gdb/serial.c 2013-07-10 20:41:31.899897384 +0400
@@ -26,6 +26,9 @@

extern void _initialize_serial (void);

+/* Parity for serial port */
+extern int serial_parity;
+
/* Is serial being debugged? */

static unsigned int global_serial_debug_p;
@@ -53,10 +56,29 @@ static const char logbase_ascii[] = "asc
static const char *const logbase_enums[] =
{logbase_hex, logbase_octal, logbase_ascii, NULL};
static const char *serial_logbase = logbase_ascii;
-

static int serial_current_type = 0;

+/* Parity for serial port */
+static const char parity_none[] = "none";
+static const char parity_odd[] = "odd";
+static const char parity_even[] = "even";
+static const char *const parity_enums[] =
+{parity_none, parity_odd, parity_even, NULL};
+static const char *parity = parity_none;
+
+static void
+set_parity (char *ignore_args, int from_tty, struct cmd_list_element *c)
+{
+ if (parity == parity_odd)
+ serial_parity = GDBPARITY_ODD;
+ else if (parity == parity_even)
+ serial_parity = GDBPARITY_EVEN;
+ else
+ serial_parity = GDBPARITY_NONE;
+}
+
+
/* Log char CH of type CHTYPE, with TIMEOUT. */

/* Define bogus char to represent a BREAK. Should be careful to choose a value
@@ -521,6 +543,12 @@ serial_setstopbits (struct serial *scb,
}

int
+serial_setparity (struct serial*scb, int parity)
+{
+ return scb->ops->setparity (scb, parity);
+}
+
+int
serial_can_async_p (struct serial *scb)
{
return (scb->ops->async != NULL);
@@ -658,6 +686,15 @@ Show numerical base for remote session l
NULL, /* FIXME: i18n: */
&setlist, &showlist);

+ add_setshow_enum_cmd ("remoteparity", no_class, parity_enums,
+ &parity, _("\
+Set parity for remote serial I/O"), _("\
+Show parity for remote serial I/O"), NULL,
+ set_parity,
+ NULL, /* FIXME: i18n: */
+ &setlist, &showlist);
+
+
add_setshow_zuinteger_cmd ("serial", class_maintenance,
&global_serial_debug_p, _("\
Set serial debugging."), _("\
diff -up ../../../gdb_old/gdb-7.6/gdb/serial.h gdb/serial.h
--- ../../../gdb_old/gdb-7.6/gdb/serial.h 2013-07-10 21:55:33.445749528 +0400
+++ gdb/serial.h 2013-07-10 20:17:17.705956716 +0400
@@ -177,6 +177,14 @@ extern int serial_noflush_set_tty_state

extern int serial_setbaudrate (struct serial *scb, int rate);

+/* Set parity for serial port. Return 0 for success, -1 for failure */
+
+#define GDBPARITY_NONE 0
+#define GDBPARITY_ODD 1
+#define GDBPARITY_EVEN 2
+
+extern int serial_setparity (struct serial *scb, int parity);
+
/* Set the number of stop bits to the value specified. Returns 0 for
success, -1 for failure. */

@@ -272,6 +280,7 @@ struct serial_ops
serial_ttystate);
int (*setbaudrate) (struct serial *, int rate);
int (*setstopbits) (struct serial *, int num);
+ int (*setparity) (struct serial *, int parity);
/* Wait for output to drain. */
int (*drain_output) (struct serial *);
/* Change the serial device into/out of asynchronous mode, call
diff -up ../../../gdb_old/gdb-7.6/gdb/ser-mingw.c gdb/ser-mingw.c
--- ../../../gdb_old/gdb-7.6/gdb/ser-mingw.c 2013-07-10
21:55:24.185807109 +0400
+++ gdb/ser-mingw.c 2013-07-16 16:01:35.854613120 +0400
@@ -156,7 +156,6 @@ ser_windows_raw (struct serial *scb)
if (GetCommState (h, &state) == 0)
return;

- state.fParity = FALSE;
state.fOutxCtsFlow = FALSE;
state.fOutxDsrFlow = FALSE;
state.fDtrControl = DTR_CONTROL_ENABLE;
@@ -166,7 +165,6 @@ ser_windows_raw (struct serial *scb)
state.fNull = FALSE;
state.fAbortOnError = FALSE;
state.ByteSize = 8;
- state.Parity = NOPARITY;

scb->current_timeout = 0;

@@ -202,6 +200,36 @@ ser_windows_setstopbits (struct serial *
}

static int
+ser_windows_setparity (struct serial *scb, int parity)
+{
+ HANDLE h = (HANDLE) _get_osfhandle (scb->fd);
+ DCB state;
+
+ if (GetCommState (h, &state) == 0)
+ return -1;
+
+ switch (parity)
+ {
+ case GDBPARITY_NONE:
+ state.Parity = NOPARITY;
+ state.fParity = FALSE;
+ break;
+ case GDBPARITY_ODD:
+ state.Parity = ODDPARITY;
+ state.fParity = TRUE;
+ break;
+ case GDBPARITY_EVEN:
+ state.Parity = EVENPARITY;
+ state.fParity = TRUE;
+ break;
+ default:
+ return 1;
+ }
+
+ return (SetCommState (h, &state) != 0) ? 0 : -1;
+}
+
+static int
ser_windows_setbaudrate (struct serial *scb, int rate)
{
HANDLE h = (HANDLE) _get_osfhandle (scb->fd);
@@ -1250,6 +1278,7 @@ _initialize_ser_windows (void)

ops->go_raw = ser_windows_raw;
ops->setbaudrate = ser_windows_setbaudrate;
+ ops->setparity = ser_windows_setparity;
ops->setstopbits = ser_windows_setstopbits;
ops->drain_output = ser_windows_drain_output;
ops->readchar = ser_base_readchar;
@@ -1303,6 +1332,7 @@ _initialize_ser_windows (void)
ops->print_tty_state = ser_base_print_tty_state;
ops->noflush_set_tty_state = ser_base_noflush_set_tty_state;
ops->setbaudrate = ser_base_setbaudrate;
+ ops->setparity = ser_base_setparity;
ops->setstopbits = ser_base_setstopbits;
ops->drain_output = ser_base_drain_output;
ops->async = ser_base_async;
@@ -1338,6 +1368,7 @@ _initialize_ser_windows (void)
ops->print_tty_state = ser_base_print_tty_state;
ops->noflush_set_tty_state = ser_base_noflush_set_tty_state;
ops->setbaudrate = ser_base_setbaudrate;
+ ops->setparity = ser_base_setparity;
ops->setstopbits = ser_base_setstopbits;
ops->drain_output = ser_base_drain_output;
ops->async = ser_base_async;
diff -up ../../../gdb_old/gdb-7.6/gdb/ser-pipe.c gdb/ser-pipe.c
--- ../../../gdb_old/gdb-7.6/gdb/ser-pipe.c 2013-07-10
21:55:24.185807109 +0400
+++ gdb/ser-pipe.c 2013-07-10 20:58:32.921749511 +0400
@@ -233,6 +233,7 @@ _initialize_ser_pipe (void)
ops->print_tty_state = ser_base_print_tty_state;
ops->noflush_set_tty_state = ser_base_noflush_set_tty_state;
ops->setbaudrate = ser_base_setbaudrate;
+ ops->setparity = ser_base_setparity;
ops->setstopbits = ser_base_setstopbits;
ops->drain_output = ser_base_drain_output;
ops->async = ser_base_async;
diff -up ../../../gdb_old/gdb-7.6/gdb/ser-tcp.c gdb/ser-tcp.c
--- ../../../gdb_old/gdb-7.6/gdb/ser-tcp.c 2013-07-10
21:55:24.200748354 +0400
+++ gdb/ser-tcp.c 2013-07-05 00:33:53.026598227 +0400
@@ -396,6 +396,7 @@ _initialize_ser_tcp (void)
ops->print_tty_state = ser_base_print_tty_state;
ops->noflush_set_tty_state = ser_base_noflush_set_tty_state;
ops->setbaudrate = ser_base_setbaudrate;
+ ops->setparity = ser_base_setparity;
ops->setstopbits = ser_base_setstopbits;
ops->drain_output = ser_base_drain_output;
ops->async = ser_base_async;
diff -up ../../../gdb_old/gdb-7.6/gdb/ser-unix.c gdb/ser-unix.c
--- ../../../gdb_old/gdb-7.6/gdb/ser-unix.c 2013-07-10
21:55:24.229751815 +0400
+++ gdb/ser-unix.c 2013-07-16 16:05:07.242612139 +0400
@@ -99,6 +99,7 @@ static int hardwire_flush_output (struct
static int hardwire_flush_input (struct serial *);
static int hardwire_send_break (struct serial *);
static int hardwire_setstopbits (struct serial *, int);
+static int hardwire_setparity (struct serial *, int);

void _initialize_ser_hardwire (void);

@@ -893,6 +894,46 @@ hardwire_setstopbits (struct serial *scb
return set_tty_state (scb, &state);
}

+static int
+hardwire_setparity (struct serial *scb, int parity)
+{
+ struct hardwire_ttystate state;
+ int newparity = 0;
+
+ if (get_tty_state (scb, &state))
+ return -1;
+
+ switch (parity)
+ {
+ case GDBPARITY_NONE:
+ newparity = 0;
+ break;
+ case GDBPARITY_ODD:
+ newparity = PARENB | PARODD;
+ break;
+ case GDBPARITY_EVEN:
+ newparity = PARENB;
+ break;
+ default:
+ return 1;
+ }
+
+#ifdef HAVE_TERMIOS
+ state.termios.c_cflag |= newparity;
+#endif
+
+#ifdef HAVE_TERMIO
+ state.termio.c_cflag |= newparity;
+#endif
+
+#ifdef HAVE_SGTTY
+ return 0; /* sgtty doesn't support this */
+#endif
+
+ return set_tty_state (scb, &state);
+}
+
+
static void
hardwire_close (struct serial *scb)
{
@@ -929,6 +970,7 @@ _initialize_ser_hardwire (void)
ops->print_tty_state = hardwire_print_tty_state;
ops->noflush_set_tty_state = hardwire_noflush_set_tty_state;
ops->setbaudrate = hardwire_setbaudrate;
+ ops->setparity = hardwire_setparity;
ops->setstopbits = hardwire_setstopbits;
ops->drain_output = hardwire_drain_output;
ops->async = ser_base_async;
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/stubs and gdb/stubs
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/syscalls and gdb/syscalls
diff -up ../../../gdb_old/gdb-7.6/gdb/target.h gdb/target.h
--- ../../../gdb_old/gdb-7.6/gdb/target.h 2013-07-10 21:55:36.818749395 +0400
+++ gdb/target.h 2013-07-05 00:36:15.025597655 +0400
@@ -1961,6 +1961,10 @@ extern int remote_debug;

/* Speed in bits per second, or -1 which means don't mess with the speed. */
extern int baud_rate;
+
+/* Parity for serial port */
+extern int serial_parity;
+
/* Timeout limit for response from target. */
extern int remote_timeout;

Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/testsuite and gdb/testsuite
diff -up ../../../gdb_old/gdb-7.6/gdb/top.c gdb/top.c
--- ../../../gdb_old/gdb-7.6/gdb/top.c 2013-07-10 21:55:32.033750880 +0400
+++ gdb/top.c 2013-07-10 20:55:06.711827223 +0400
@@ -159,6 +159,9 @@ int server_command;

int baud_rate = -1;

+/* Parity for serial port */
+int serial_parity = GDBPARITY_NONE;
+
/* Timeout limit for response from target. */

/* The default value has been changed many times over the years. It
Common subdirectories: ../../../gdb_old/gdb-7.6/gdb/tui and gdb/tui

--
With best regards!
____________________________

Yurij Grechishhev
Bauman State Technical University,
Department of Computer Systems and Networks