PERFORCE change 36441 for review
Marcel Moolenaar
marcel at FreeBSD.org
Tue Aug 19 12:07:28 PDT 2003
http://perforce.freebsd.org/chv.cgi?CH=36441
Change 36441 by marcel at marcel_nfs on 2003/08/19 12:06:59
Pass the modem and line signals to the software interrupt
handler in the low order 16 bits of the ttypend variable.
Redefine the UART_IPEND_* constants accordingly. We still
need to act upon signal changes.
Affected files ...
.. //depot/projects/uart/dev/uart/uart_bus.h#15 edit
.. //depot/projects/uart/dev/uart/uart_core.c#20 edit
Differences ...
==== //depot/projects/uart/dev/uart/uart_bus.h#15 (text+ko) ====
@@ -37,12 +37,20 @@
#define UART_FLUSH_RECEIVER UART_DRAIN_RECEIVER
#define UART_FLUSH_TRANSMITTER UART_DRAIN_TRANSMITTER
-/* Interrupt sources (in priority order). See also uart_core.c */
-#define UART_IPEND_OVERRUN 0x0001
-#define UART_IPEND_BREAK 0x0002
-#define UART_IPEND_RXREADY 0x0004
-#define UART_IPEND_SIGCHG 0x0008
-#define UART_IPEND_TXIDLE 0x0010
+/*
+ * Interrupt sources (in priority order). See also uart_core.c
+ * Note that the low order 16 bits are used to pass modem signals
+ * from the hardware interrupt handler to the software interrupt
+ * handler. See UART_SIG_* and UART_SIGMASK_* below.
+ */
+#define UART_IPEND_OVERRUN 0x010000
+#define UART_IPEND_BREAK 0x020000
+#define UART_IPEND_RXREADY 0x040000
+#define UART_IPEND_SIGCHG 0x080000
+#define UART_IPEND_TXIDLE 0x100000
+
+#define UART_IPEND_MASK 0x1f0000
+#define UART_IPEND_SIGMASK 0x00ffff
/* Received character status bits. */
#define UART_STAT_BREAK 0x0100
==== //depot/projects/uart/dev/uart/uart_core.c#20 (text+ko) ====
@@ -180,13 +180,13 @@
{
struct uart_softc *sc = arg;
struct tty *tp;
- int c, pend, xc;
+ int c, pend, sig, xc;
if (sc->sc_leaving)
return;
pend = atomic_readandclear_32(&sc->sc_ttypend);
- if (pend == 0)
+ if (!(pend & UART_IPEND_MASK))
return;
tp = sc->sc_tty;
@@ -203,6 +203,13 @@
}
}
+ if (pend & UART_IPEND_SIGCHG) {
+ sig = pend & UART_IPEND_SIGMASK;
+ /*
+ * TODO: process signals.
+ */
+ }
+
if (pend & UART_IPEND_TXIDLE) {
tp->t_state &= ~TS_BUSY;
(*linesw[tp->t_line].l_start)(tp);
@@ -293,16 +300,23 @@
/*
* Line or modem status change (OOB signalling).
+ * We pass the signals to the software interrupt handler for further
+ * processing. Note that we merge the delta bits, but set the state
+ * bits. This is to avoid loosing state transitions due to having more
+ * than 1 hardware interrupt between software interrupts.
*/
static void
uart_intr_sigchg(struct uart_softc *sc)
{
- int sig;
+ int new, old, sig;
sig = UART_GETSIG(sc);
- /*
- * TODO: process the signals.
- */
+ do {
+ old = sc->sc_ttypend;
+ new = old & ~UART_SIGMASK_STATE;
+ new |= sig & UART_IPEND_SIGMASK;
+ new |= UART_IPEND_SIGCHG;
+ } while (!atomic_cmpset_32(&sc->sc_ttypend, old, new));
}
/*
More information about the p4-projects
mailing list