Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/arch/arm/samsung Implement sscom interrupt masking and a...



details:   https://anonhg.NetBSD.org/src/rev/5585c04e9220
branches:  trunk
changeset: 795471:5585c04e9220
user:      reinoud <reinoud%NetBSD.org@localhost>
date:      Mon Apr 14 21:16:15 2014 +0000

description:
Implement sscom interrupt masking and acknowledgement routines

diffstat:

 sys/arch/arm/samsung/exynos_sscom.c |  56 +++++++++++++++++++++++++++++-------
 sys/arch/arm/samsung/sscom.c        |  18 +++++++++-
 sys/arch/arm/samsung/sscom_reg.h    |   6 +---
 sys/arch/arm/samsung/sscom_var.h    |   3 +-
 4 files changed, 63 insertions(+), 20 deletions(-)

diffs (187 lines):

diff -r 8129244bde69 -r 5585c04e9220 sys/arch/arm/samsung/exynos_sscom.c
--- a/sys/arch/arm/samsung/exynos_sscom.c       Mon Apr 14 21:09:02 2014 +0000
+++ b/sys/arch/arm/samsung/exynos_sscom.c       Mon Apr 14 21:16:15 2014 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: exynos_sscom.c,v 1.1 2014/04/13 02:26:26 matt Exp $ */
+/*     $NetBSD: exynos_sscom.c,v 1.2 2014/04/14 21:16:15 reinoud Exp $ */
 
 /*
  * Copyright (c) 2014 Reinoud Zandijk
@@ -34,7 +34,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: exynos_sscom.c,v 1.1 2014/04/13 02:26:26 matt Exp $");
+__KERNEL_RCSID(0, "$NetBSD: exynos_sscom.c,v 1.2 2014/04/14 21:16:15 reinoud Exp $");
 
 #include "opt_sscom.h"
 #include "opt_ddb.h"
@@ -69,11 +69,6 @@
 static int sscom_match(device_t, cfdata_t, void *);
 static void sscom_attach(device_t, device_t, void *);
 
-/* XXX cludge for not-existing interrupt code XXX */
-#define exynos_unmask_interrupts(intbits) 
-#define exynos_mask_interrupts(intbits) 
-
-
 CFATTACH_DECL_NEW(exynos_sscom, sizeof(struct sscom_softc), sscom_match,
     sscom_attach, NULL, NULL);
 
@@ -87,6 +82,32 @@
 }
 
 static void
+exynos_unmask_interrupts(struct sscom_softc *sc, int intbits)
+{
+       int psw = disable_interrupts(IF32_bits);
+       uint32_t val;
+
+       val = bus_space_read_4(sc->sc_iot, sc->sc_ioh, SSCOM_UINTM);
+       val &= ~intbits;
+       bus_space_write_4(sc->sc_iot, sc->sc_ioh, SSCOM_UINTM, val);
+
+       restore_interrupts(psw);
+}
+
+static void
+exynos_mask_interrupts(struct sscom_softc *sc, int intbits)
+{
+       int psw = disable_interrupts(IF32_bits);
+       uint32_t val;
+
+       val = bus_space_read_4(sc->sc_iot, sc->sc_ioh, SSCOM_UINTM);
+       val |= intbits;
+       bus_space_write_4(sc->sc_iot, sc->sc_ioh, SSCOM_UINTM, val);
+
+       restore_interrupts(psw);
+}
+
+static void
 exynos_change_txrx_interrupts(struct sscom_softc *sc, bool unmask_p,
     u_int flags)
 {
@@ -96,13 +117,25 @@
        if (flags & SSCOM_HW_TXINT)
                intbits |= 1 << sc->sc_tx_irqno;
        if (unmask_p) {
-               exynos_unmask_interrupts(intbits);
+               exynos_unmask_interrupts(sc, intbits);
        } else {
-               exynos_mask_interrupts(intbits);
+               exynos_mask_interrupts(sc, intbits);
        }
 }
 
 static void
+exynos_clear_interrupts(struct sscom_softc *sc, u_int flags)
+{
+       uint32_t val = 0;
+
+       if (flags & SSCOM_HW_RXINT)
+               val |= sc->sc_rx_irqno;
+       if (flags & SSCOM_HW_TXINT)
+               val |= sc->sc_tx_irqno;
+       bus_space_write_4(sc->sc_iot, sc->sc_ioh, SSCOM_UINTP, val);
+}
+
+static void
 sscom_attach(device_t parent, device_t self, void *aux)
 {
        struct sscom_softc *sc = device_private(self);
@@ -118,9 +151,10 @@
        sc->sc_frequency = EXYNOS_UART_FREQ;
 
        sc->sc_change_txrx_interrupts = exynos_change_txrx_interrupts;
+       sc->sc_clear_interrupts = exynos_clear_interrupts;
 
-       sc->sc_rx_irqno = 0; // S3C2800_INT_RXD0 + sa->sa_index;
-       sc->sc_tx_irqno = 0; // S3C2800_INT_TXD0 + sa->sa_index;
+       sc->sc_rx_irqno = UINT_RXD;
+       sc->sc_tx_irqno = UINT_TXD;
 
        if (!sscom_is_console(sc->sc_iot, unit, &sc->sc_ioh)
            && bus_space_map(sc->sc_iot, iobase, SSCOM_SIZE, 0, &sc->sc_ioh)) {
diff -r 8129244bde69 -r 5585c04e9220 sys/arch/arm/samsung/sscom.c
--- a/sys/arch/arm/samsung/sscom.c      Mon Apr 14 21:09:02 2014 +0000
+++ b/sys/arch/arm/samsung/sscom.c      Mon Apr 14 21:16:15 2014 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: sscom.c,v 1.1 2014/04/13 02:26:26 matt Exp $ */
+/*     $NetBSD: sscom.c,v 1.2 2014/04/14 21:16:15 reinoud Exp $ */
 
 /*
  * Copyright (c) 2002, 2003 Fujitsu Component Limited
@@ -98,7 +98,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: sscom.c,v 1.1 2014/04/13 02:26:26 matt Exp $");
+__KERNEL_RCSID(0, "$NetBSD: sscom.c,v 1.2 2014/04/14 21:16:15 reinoud Exp $");
 
 #include "opt_sscom.h"
 #include "opt_ddb.h"
@@ -424,6 +424,7 @@
 
        /* Disable interrupts before configuring the device. */
        KASSERT(sc->sc_change_txrx_interrupts != NULL);
+       KASSERT(sc->sc_clear_interrupts != NULL);
        sscom_disable_txrxint(sc);
 
 #ifdef KGDB
@@ -1818,7 +1819,18 @@
 int
 sscomintr(void *v)
 {
-       return sscomrxintr(v) + sscomtxintr(v);
+       struct sscom_softc *sc = v;
+       int clear = 0;
+
+       if (sscomrxintr(v))
+               clear |= SSCOM_HW_RXINT;
+       if (sscomtxintr(v))
+               clear |= SSCOM_HW_TXINT;
+
+       if (clear)
+               sc->sc_clear_interrupts(sc, clear);
+
+       return clear? 1: 0;
 }
 
 
diff -r 8129244bde69 -r 5585c04e9220 sys/arch/arm/samsung/sscom_reg.h
--- a/sys/arch/arm/samsung/sscom_reg.h  Mon Apr 14 21:09:02 2014 +0000
+++ b/sys/arch/arm/samsung/sscom_reg.h  Mon Apr 14 21:16:15 2014 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: sscom_reg.h,v 1.1 2014/04/13 02:26:26 matt Exp $ */
+/* $NetBSD: sscom_reg.h,v 1.2 2014/04/14 21:16:15 reinoud Exp $ */
 
 /*
  * Copyright (c) 2002, 2003 Fujitsu Component Limited
@@ -140,10 +140,6 @@
 #define   UINT_ERROR           __BIT(1)
 #define   UINT_RXD             __BIT(0)
 
-//#define      INTCTL_SRCPND   0x00    /* Interrupt request status */
-//#define      INTCTL_INTMOD   0x04    /* Interrupt mode (FIQ/IRQ) */
-//#define      INTCTL_INTMSK   0x08    /* Interrupt mask */
-
 #define        SSCOM_SIZE  0x3C
 
 #endif /* _ARM_SAMSUNG_SSCOM_REG_H_ */
diff -r 8129244bde69 -r 5585c04e9220 sys/arch/arm/samsung/sscom_var.h
--- a/sys/arch/arm/samsung/sscom_var.h  Mon Apr 14 21:09:02 2014 +0000
+++ b/sys/arch/arm/samsung/sscom_var.h  Mon Apr 14 21:16:15 2014 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: sscom_var.h,v 1.1 2014/04/13 02:26:26 matt Exp $ */
+/* $NetBSD: sscom_var.h,v 1.2 2014/04/14 21:16:15 reinoud Exp $ */
 
 /*
  * Copyright (c) 2002, 2003 Fujitsu Component Limited
@@ -184,6 +184,7 @@
        int     (*sc_read_modem_status)( struct sscom_softc * );
        void    (*sc_set_modem_control)( struct sscom_softc * );
        void    (*sc_change_txrx_interrupts)(struct sscom_softc *, bool, u_int);
+       void    (*sc_clear_interrupts)(struct sscom_softc *, u_int);
 };
 
 /* UART register address, etc. */



Home | Main Index | Thread Index | Old Index