Subject: PR 12547 (console break signal ignored if DDB not defined)
To: None <tech-kern@netbsd.org>
From: Chuck Silvers <chuq@chuq.com>
List: tech-kern
Date: 03/09/2002 16:37:12
--u3/rZRmxL6MmkK24
Content-Type: text/plain; charset=us-ascii
Content-Disposition: inline

to fix PR 12547, I propose to add an extra "cookie" argument to
cn_check_magic() and cn_trap().  on platforms that have a firmware
monitor such as the sparc, this cookie can be used to pass the
console driver's softc pointer to (eg.) zs_abort(), which will
drop into the monitor like before the cnmagic changes.
(currently zs_abort() is defined on several platforms but is unused).

I've tested the attached changes on sparc and sparc64 (an ultra2).
the "com" parts are untested but should be harmless.
comments?

-Chuck

--u3/rZRmxL6MmkK24
Content-Type: text/plain; charset=us-ascii
Content-Disposition: attachment; filename="diff.cnmagic"

Index: sys/ddb/ddbvar.h
===================================================================
RCS file: /cvsroot/syssrc/sys/ddb/ddbvar.h,v
retrieving revision 1.3
diff -u -r1.3 ddbvar.h
--- sys/ddb/ddbvar.h	2002/02/15 07:33:55	1.3
+++ sys/ddb/ddbvar.h	2002/03/10 00:29:38
@@ -45,6 +45,7 @@
 
 extern	int db_onpanic;
 extern	int db_fromconsole;
+extern	int db_active;
 
 int ddb_sysctl(int *, u_int, void *, size_t *, void *, size_t, struct proc *);
 
Index: sys/sys/systm.h
===================================================================
RCS file: /cvsroot/syssrc/sys/sys/systm.h,v
retrieving revision 1.141
diff -u -r1.141 systm.h
--- sys/sys/systm.h	2002/03/04 02:24:37	1.141
+++ sys/sys/systm.h	2002/03/10 00:29:39
@@ -345,7 +345,7 @@
 
 /* Override db_console() in MD headers */
 #ifndef cn_trap
-#define cn_trap()	console_debugger()
+#define cn_trap(c)	console_debugger()
 #endif
 #ifndef cn_isconsole
 #define cn_isconsole(d)	(cn_tab != NULL && (d) == cn_tab->cn_dev)
@@ -357,14 +357,14 @@
 int cn_get_magic __P((char *magic, int len));
 /* This should be called for each byte read */
 #ifndef cn_check_magic
-#define cn_check_magic(d, k, s)						\
+#define cn_check_magic(d, k, s, c)					\
 	do {								\
 		if (cn_isconsole(d)) {					\
 			int v = (s).cnm_magic[(s).cnm_state];		\
 			if ((k) == CNS_MAGIC_VAL(v)) {			\
 				(s).cnm_state = CNS_MAGIC_NEXT(v);	\
 				if ((s).cnm_state == CNS_TERM) {	\
-					cn_trap();			\
+					cn_trap((c));			\
 					(s).cnm_state = 0;		\
 				}					\
 			} else {					\
Index: share/man/man9/cnmagic.9
===================================================================
RCS file: /cvsroot/sharesrc/share/man/man9/cnmagic.9,v
retrieving revision 1.8
diff -u -r1.8 cnmagic.9
--- share/man/man9/cnmagic.9	2002/02/13 08:18:38	1.8
+++ share/man/man9/cnmagic.9	2002/03/10 00:29:39
@@ -48,11 +48,11 @@
 .Fd #include \*[Lt]sys/systm.h\*[Gt]
 .Va typedef struct cnm_state cnm_state_t;
 .Ft void
-.Fn cn_trap
+.Fn cn_trap "void *cookie"
 .Ft int
 .Fn cn_isconsole "dev_t dev"
 .Ft void
-.Fn cn_check_magic "dev_t dev" "int k" "cnm_state_t *cnms"
+.Fn cn_check_magic "dev_t dev" "int k" "cnm_state_t *cnms" "void *cookie"
 .Ft void
 .Fn cn_init_magic "cnm_state_t *cnms"
 .Ft int
@@ -103,12 +103,12 @@
 Initialize the console magic state pointed to by
 .Fa cnm
 to a usable state.
-.It Fn "void cnm_trap"
+.It Fn "void cn_trap" "void *cookie"
 .Pp
 Trap into the kernel debugger or ROM monitor.  By default this
 routine is defined to be
 .Fn console_debugger
-but can be overridden in MI header files.
+but can be overridden in MD header files.
 .It Fn "int cn_isconsole" "dev_t dev"
 .Pp
 Determine whether a given
@@ -118,7 +118,7 @@
 is the same as
 .Va cn_tab-\*[Gt]cn_dev
 but can be overridden in MI header files.
-.It Fn "void cn_check_magic" "dev_t dev" "int k" "cnm_state_t *cnms"
+.It Fn "void cn_check_magic" "dev_t dev" "int k" "cnm_state_t *cnms" "void *cookie"
 .Pp
 All input should be passed through
 .Fn cn_check_magic
@@ -132,9 +132,11 @@
 it runs the input value
 .Fa k
 through the state machine.  If the state machine completes a match
-of the current console magic sequence
+of the current console magic sequence,
 .Fn cn_trap
-is called.  Some input may need to be translated to state machine
+is called with
+.Fa cookie
+as an argument.  Some input may need to be translated to state machine
 values such as the serial line
 .Li BREAK
 sequence.
Index: sys/arch/evbarm/dev/plcom.c
===================================================================
RCS file: /cvsroot/syssrc/sys/arch/evbarm/dev/plcom.c,v
retrieving revision 1.2
diff -u -r1.2 plcom.c
--- sys/arch/evbarm/dev/plcom.c	2001/11/20 08:43:22	1.2
+++ sys/arch/evbarm/dev/plcom.c	2002/03/10 00:29:43
@@ -119,7 +119,7 @@
  * Callers of cn_check_magic must declare int cn_trapped = 0;
  * XXX: this is *ugly*!
  */
-#define cn_trap()				\
+#define cn_trap(c)				\
 	do {					\
 		console_debugger();		\
 		cn_trapped = 1;			\
@@ -1809,7 +1809,7 @@
 				if (ISSET(rsr, RSR_BE)) {
 					int cn_trapped = 0;
 					cn_check_magic(sc->sc_tty->t_dev,
-					    CNC_BREAK, plcom_cnm_state);
+					    CNC_BREAK, plcom_cnm_state, sc);
 					if (cn_trapped)
 						continue;
 #if defined(KGDB)
@@ -1822,8 +1822,8 @@
 				}
 
 				put[1] = rsr;
-				cn_check_magic(sc->sc_tty->t_dev,
-					       put[0], plcom_cnm_state);
+				cn_check_magic(sc->sc_tty->t_dev, put[0],
+				    plcom_cnm_state, sc);
 				if (cn_trapped) {
 					fr = bus_space_read_1(iot, ioh,
 					    plcom_fr);
@@ -2072,7 +2072,7 @@
 		extern int db_active;
 		if (!db_active)
 #endif
-			cn_check_magic(dev, c, plcom_cnm_state);
+			cn_check_magic(dev, c, plcom_cnm_state, NULL);
 	}
 	splx(s);
 	return c;
@@ -2091,7 +2091,7 @@
 		int cn_trapped = 0;
 		cin = bus_space_read_1(iot, ioh, plcom_dr);
 		stat = bus_space_read_1(iot, ioh, plcom_iir);
-		cn_check_magic(dev, cin, plcom_cnm_state);
+		cn_check_magic(dev, cin, plcom_cnm_state, NULL);
 		plcom_readahead[plcom_readaheadcount++] = cin;
 	}
 
Index: sys/arch/mvme68k/include/z8530var.h
===================================================================
RCS file: /cvsroot/syssrc/sys/arch/mvme68k/include/z8530var.h,v
retrieving revision 1.7
diff -u -r1.7 z8530var.h
--- sys/arch/mvme68k/include/z8530var.h	2001/05/31 18:46:09	1.7
+++ sys/arch/mvme68k/include/z8530var.h	2002/03/10 00:29:44
@@ -75,3 +75,5 @@
 /* Interrupt priority for the SCC chip; needs to match ZSHARD_PRI. */
 #define splzs()		splserial()
 
+#undef cn_trap
+#define cn_trap(c) zs_abort((c))
Index: sys/arch/sparc/dev/zs.c
===================================================================
RCS file: /cvsroot/syssrc/sys/arch/sparc/dev/zs.c,v
retrieving revision 1.84
diff -u -r1.84 zs.c
--- sys/arch/sparc/dev/zs.c	2001/09/26 20:53:06	1.84
+++ sys/arch/sparc/dev/zs.c	2002/03/10 00:29:48
@@ -59,6 +59,8 @@
 #include <sys/time.h>
 #include <sys/syslog.h>
 
+#include <ddb/ddbvar.h>
+
 #include <machine/bsd_openprom.h>
 #include <machine/autoconf.h>
 #include <machine/intr.h>
@@ -784,7 +786,12 @@
 #if defined(KGDB)
 	zskgdb(cs);
 #elif defined(DDB)
-	Debugger();
+	if (db_fromconsole) {
+		if (!db_active)
+			Debugger();
+		else
+			callrom();
+	}
 #else
 	printf("stopping on keyboard abort\n");
 	callrom();
Index: sys/arch/sparc/include/z8530var.h
===================================================================
RCS file: /cvsroot/syssrc/sys/arch/sparc/include/z8530var.h,v
retrieving revision 1.3
diff -u -r1.3 z8530var.h
--- sys/arch/sparc/include/z8530var.h	2000/03/19 13:45:23	1.3
+++ sys/arch/sparc/include/z8530var.h	2002/03/10 00:29:48
@@ -89,3 +89,6 @@
 #define ZSCCF_CHANNEL 0
 #define ZSCCF_CHANNEL_DEFAULT -1
 #endif
+
+#undef cn_trap
+#define cn_trap(c) zs_abort((c))
Index: sys/arch/sparc64/dev/pcons.c
===================================================================
RCS file: /cvsroot/syssrc/sys/arch/sparc64/dev/pcons.c,v
retrieving revision 1.8
diff -u -r1.8 pcons.c
--- sys/arch/sparc64/dev/pcons.c	2001/10/05 21:53:56	1.8
+++ sys/arch/sparc64/dev/pcons.c	2002/03/10 00:29:50
@@ -289,7 +289,7 @@
 	char ch;
 	
 	while (OF_read(stdin, &ch, 1) > 0) {
-		cn_check_magic(tp->t_dev, ch, pcons_cnm_state);
+		cn_check_magic(tp->t_dev, ch, pcons_cnm_state, sc);
 		if (tp && (tp->t_state & TS_ISOPEN))
 			(*tp->t_linesw->l_rint)(ch, tp);
 	}
Index: sys/arch/sparc64/dev/zs.c
===================================================================
RCS file: /cvsroot/syssrc/sys/arch/sparc64/dev/zs.c,v
retrieving revision 1.31
diff -u -r1.31 zs.c
--- sys/arch/sparc64/dev/zs.c	2001/10/05 21:53:56	1.31
+++ sys/arch/sparc64/dev/zs.c	2002/03/10 00:29:51
@@ -70,7 +70,7 @@
 #include <dev/cons.h>
 #include <dev/ic/z8530reg.h>
 #include <dev/sun/kbd_ms_ttyvar.h>
-#include <ddb/db_output.h>
+#include <ddb/ddbvar.h>
 
 #include <sparc64/dev/cons.h>
 
@@ -707,9 +707,7 @@
 #if defined(KGDB)
 	zskgdb(cs);
 #elif defined(DDB)
-	{
-		extern int db_active;
-		
+	if (db_fromconsole) {
 		if (!db_active)
 			Debugger();
 		else
Index: sys/arch/sparc64/include/z8530var.h
===================================================================
RCS file: /cvsroot/syssrc/sys/arch/sparc64/include/z8530var.h,v
retrieving revision 1.4
diff -u -r1.4 z8530var.h
--- sys/arch/sparc64/include/z8530var.h	2000/11/08 23:41:42	1.4
+++ sys/arch/sparc64/include/z8530var.h	2002/03/10 00:29:52
@@ -100,3 +100,6 @@
 #define ZSCCF_CHANNEL 0
 #define ZSCCF_CHANNEL_DEFAULT -1
 #endif
+
+#undef cn_trap
+#define cn_trap(c) zs_abort((c))
Index: sys/arch/sun3/include/z8530var.h
===================================================================
RCS file: /cvsroot/syssrc/sys/arch/sun3/include/z8530var.h,v
retrieving revision 1.7
diff -u -r1.7 z8530var.h
--- sys/arch/sun3/include/z8530var.h	1999/08/20 03:53:50	1.7
+++ sys/arch/sun3/include/z8530var.h	2002/03/10 00:29:53
@@ -78,3 +78,6 @@
 #define ZSCCF_CHANNEL 0
 #define ZSCCF_CHANNEL_DEFAULT -1
 #endif
+
+#undef cn_trap
+#define cn_trap(c) zs_abort((c))
Index: sys/dev/ic/com.c
===================================================================
RCS file: /cvsroot/syssrc/sys/dev/ic/com.c,v
retrieving revision 1.193
diff -u -r1.193 com.c
--- sys/dev/ic/com.c	2001/11/20 08:43:45	1.193
+++ sys/dev/ic/com.c	2002/03/10 00:30:01
@@ -94,7 +94,7 @@
  * Callers of cn_check_magic must declare int cn_trapped = 0;
  * XXX: this is *ugly*!
  */
-#define cn_trap()				\
+#define cn_trap(c)				\
 	do {					\
 		console_debugger();		\
 		cn_trapped = 1;			\
@@ -2043,8 +2043,8 @@
 		lsr = bus_space_read_1(iot, ioh, com_lsr);
 		if (ISSET(lsr, LSR_BI)) {
 			int cn_trapped = 0;
-			cn_check_magic(sc->sc_tty->t_dev,
-				       CNC_BREAK, com_cnm_state);
+			cn_check_magic(sc->sc_tty->t_dev, CNC_BREAK,
+			    com_cnm_state, sc);
 			if (cn_trapped)
 				continue;
 #if defined(KGDB)
@@ -2061,8 +2061,8 @@
 				int cn_trapped = 0;
 				put[0] = bus_space_read_1(iot, ioh, com_data);
 				put[1] = lsr;
-				cn_check_magic(sc->sc_tty->t_dev,
-					       put[0], com_cnm_state);
+				cn_check_magic(sc->sc_tty->t_dev, put[0],
+				    com_cnm_state, sc);
 				if (cn_trapped) {
 					lsr = bus_space_read_1(iot, ioh, com_lsr);
 					if (!ISSET(lsr, LSR_RCV_MASK))
@@ -2303,7 +2303,7 @@
 		extern int db_active;
 		if (!db_active)
 #endif
-			cn_check_magic(dev, c, com_cnm_state);
+			cn_check_magic(dev, c, com_cnm_state, NULL);
 	}
 	splx(s);
 	return (c);
@@ -2325,7 +2325,7 @@
 		int cn_trapped = 0;
 		cin = bus_space_read_1(iot, ioh, com_data);
 		stat = bus_space_read_1(iot, ioh, com_iir);
-		cn_check_magic(dev, cin, com_cnm_state);
+		cn_check_magic(dev, cin, com_cnm_state, NULL);
 		com_readahead[com_readaheadcount++] = cin;
 	}
 
Index: sys/dev/ic/z8530tty.c
===================================================================
RCS file: /cvsroot/syssrc/sys/dev/ic/z8530tty.c,v
retrieving revision 1.78
diff -u -r1.78 z8530tty.c
--- sys/dev/ic/z8530tty.c	2001/11/13 13:14:46	1.78
+++ sys/dev/ic/z8530tty.c	2002/03/10 00:30:04
@@ -1408,7 +1408,7 @@
 			zs_write_csr(cs, ZSWR0_RESET_ERRORS);
 		}
 
-		cn_check_magic(zst->zst_tty->t_dev, c, zstty_cnm_state);
+		cn_check_magic(zst->zst_tty->t_dev, c, zstty_cnm_state, cs);
 		put[0] = c;
 		put[1] = rr1;
 		put += 2;
@@ -1519,7 +1519,8 @@
 	 * even when interrupts are locking up the machine.
 	 */
 	if (ISSET(rr0, ZSRR0_BREAK))
-		cn_check_magic(zst->zst_tty->t_dev, CNC_BREAK, zstty_cnm_state);
+		cn_check_magic(zst->zst_tty->t_dev, CNC_BREAK, zstty_cnm_state,
+		    cs);
 
 	if (!force)
 		delta = rr0 ^ cs->cs_rr0;

--u3/rZRmxL6MmkK24--