Source-Changes-HG archive

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

[src/trunk]: src/sys/arch/arm/omap Support am335x's MMCHS2(sdhc@mainbus).



details:   https://anonhg.NetBSD.org/src/rev/08b8ddcc6980
branches:  trunk
changeset: 348115:08b8ddcc6980
user:      kiyohara <kiyohara%NetBSD.org@localhost>
date:      Tue Oct 04 16:06:42 2016 +0000

description:
Support am335x's MMCHS2(sdhc@mainbus).
  Tested on Gumstix Pepper 43C.

diffstat:

 sys/arch/arm/omap/files.omap2  |    5 +-
 sys/arch/arm/omap/omap3_sdhc.c |  390 ++++++++++++++++++++++++----------------
 2 files changed, 238 insertions(+), 157 deletions(-)

diffs (truncated from 674 to 300 lines):

diff -r 8549f78dc8a5 -r 08b8ddcc6980 sys/arch/arm/omap/files.omap2
--- a/sys/arch/arm/omap/files.omap2     Tue Oct 04 16:03:39 2016 +0000
+++ b/sys/arch/arm/omap/files.omap2     Tue Oct 04 16:06:42 2016 +0000
@@ -1,4 +1,4 @@
-#      $NetBSD: files.omap2,v 1.34 2016/10/04 15:23:40 kiyohara Exp $
+#      $NetBSD: files.omap2,v 1.35 2016/10/04 16:10:34 kiyohara Exp $
 #
 # Configuration info for Texas Instruments OMAP2/OMAP3 CPU support
 # Based on xscale/files.pxa2x0
@@ -134,8 +134,9 @@
 attach  motg at tiotg_port
 
 # SDMMC controller
+attach sdhc at mainbus with mainbussdhc
 attach sdhc at obio with obiosdhc
-file   arch/arm/omap/omap3_sdhc.c              obiosdhc
+file   arch/arm/omap/omap3_sdhc.c              mainbussdhc | obiosdhc
 
 # NAND flash controller
 device omapnand: nandbus
diff -r 8549f78dc8a5 -r 08b8ddcc6980 sys/arch/arm/omap/omap3_sdhc.c
--- a/sys/arch/arm/omap/omap3_sdhc.c    Tue Oct 04 16:03:39 2016 +0000
+++ b/sys/arch/arm/omap/omap3_sdhc.c    Tue Oct 04 16:06:42 2016 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: omap3_sdhc.c,v 1.25 2016/10/04 15:51:34 kiyohara Exp $ */
+/*     $NetBSD: omap3_sdhc.c,v 1.26 2016/10/04 16:06:42 kiyohara Exp $ */
 /*-
  * Copyright (c) 2011 The NetBSD Foundation, Inc.
  * All rights reserved.
@@ -29,7 +29,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: omap3_sdhc.c,v 1.25 2016/10/04 15:51:34 kiyohara Exp $");
+__KERNEL_RCSID(0, "$NetBSD: omap3_sdhc.c,v 1.26 2016/10/04 16:06:42 kiyohara Exp $");
 
 #include "opt_omap.h"
 #include "edma.h"
@@ -37,6 +37,7 @@
 #include <sys/param.h>
 #include <sys/systm.h>
 #include <sys/device.h>
+#include <sys/errno.h>
 #include <sys/kernel.h>
 #include <sys/proc.h>
 #include <sys/queue.h>
@@ -49,8 +50,10 @@
 #include <arm/omap/omap3_sdmmcreg.h>
 
 #ifdef TI_AM335X
+#  include <arm/mainbus/mainbus.h>
 #  include <arm/omap/am335x_prcm.h>
 #  include <arm/omap/omap2_prcm.h>
+#  include <arm/omap/omap_var.h>
 #  include <arm/omap/sitara_cm.h>
 #  include <arm/omap/sitara_cmreg.h>
 #endif
@@ -82,25 +85,19 @@
 #define SDHC_WRITE(sc, reg, val) \
        bus_space_write_4((sc)->sc_bst, (sc)->sc_sdhc_bsh, (reg), (val))
 
-static int obiosdhc_match(device_t, cfdata_t, void *);
-static void obiosdhc_attach(device_t, device_t, void *);
-static int obiosdhc_detach(device_t, int);
-
-static int obiosdhc_bus_width(struct sdhc_softc *, int);
-static int obiosdhc_rod(struct sdhc_softc *, int);
-static int obiosdhc_write_protect(struct sdhc_softc *);
-static int obiosdhc_card_detect(struct sdhc_softc *);
-
-struct obiosdhc_softc {
+struct mmchs_softc {
        struct sdhc_softc       sc;
+       bus_addr_t              sc_addr;
        bus_space_tag_t         sc_bst;
        bus_space_handle_t      sc_bsh;
        bus_space_handle_t      sc_hl_bsh;
        bus_space_handle_t      sc_sdhc_bsh;
        struct sdhc_host        *sc_hosts[1];
+       int                     sc_irq;
        void                    *sc_ih;         /* interrupt vectoring */
 
 #if NEDMA > 0
+       int                     sc_edmabase;
        struct edma_channel     *sc_edma_tx;
        struct edma_channel     *sc_edma_rx;
        uint16_t                sc_edma_param_tx[EDMA_MAX_PARAMS];
@@ -114,26 +111,45 @@
 #endif
 };
 
+static int obiosdhc_match(device_t, cfdata_t, void *);
+static void obiosdhc_attach(device_t, device_t, void *);
+#ifdef TI_AM335X
+static int mainbussdhc_match(device_t, cfdata_t, void *);
+static void mainbussdhc_attach(device_t, device_t, void *);
+#endif
+static int mmchs_detach(device_t, int);
+
+static int mmchs_attach(struct mmchs_softc *);
+static void mmchs_init(device_t);
+
+static int mmchs_bus_width(struct sdhc_softc *, int);
+static int mmchs_rod(struct sdhc_softc *, int);
+static int mmchs_write_protect(struct sdhc_softc *);
+static int mmchs_card_detect(struct sdhc_softc *);
+
 #if NEDMA > 0
-static int obiosdhc_edma_init(struct obiosdhc_softc *, unsigned int);
-static int obiosdhc_edma_xfer_data(struct sdhc_softc *, struct sdmmc_command *);
-static void obiosdhc_edma_done(void *);
-static int obiosdhc_edma_transfer(struct sdhc_softc *, struct sdmmc_command *);
+static int mmchs_edma_init(struct mmchs_softc *, unsigned int);
+static int mmchs_edma_xfer_data(struct sdhc_softc *, struct sdmmc_command *);
+static void mmchs_edma_done(void *);
+static int mmchs_edma_transfer(struct sdhc_softc *, struct sdmmc_command *);
 #endif
 
 #ifdef TI_AM335X
-struct am335x_sdhc {
+struct am335x_mmchs {
        const char *as_name;
+       const char *as_parent_name;
        bus_addr_t as_base_addr;
        int as_intr;
        struct omap_module as_module;
 };
 
-static const struct am335x_sdhc am335x_sdhc[] = {
-       /* XXX All offset by 0x100 because of the am335x's mmc registers.  */
-       { "MMCHS0", SDMMC1_BASE_TIAM335X, 64, { AM335X_PRCM_CM_PER, 0x3c } },
-       { "MMC1",   SDMMC2_BASE_TIAM335X, 28, { AM335X_PRCM_CM_PER, 0xf4 } },
-       { "MMCHS2", SDMMC3_BASE_TIAM335X, 29, { AM335X_PRCM_CM_WKUP, 0xf8 } },
+static const struct am335x_mmchs am335x_mmchs[] = {
+       { "MMCHS0", "obio",
+           SDMMC1_BASE_TIAM335X, 64, { AM335X_PRCM_CM_PER, 0x3c } },
+       { "MMC1",   "obio",
+           SDMMC2_BASE_TIAM335X, 28, { AM335X_PRCM_CM_PER, 0xf4 } },
+       { "MMCHS2", "mainbus",
+           SDMMC3_BASE_TIAM335X, 29, { AM335X_PRCM_CM_PER, 0xf8 } },
 };
 
 struct am335x_padconf {
@@ -155,17 +171,14 @@
 };
 #endif
 
-CFATTACH_DECL_NEW(obiosdhc, sizeof(struct obiosdhc_softc),
-    obiosdhc_match, obiosdhc_attach, obiosdhc_detach, NULL);
+CFATTACH_DECL_NEW(obiosdhc, sizeof(struct mmchs_softc),
+    obiosdhc_match, obiosdhc_attach, mmchs_detach, NULL);
 
 static int
 obiosdhc_match(device_t parent, cfdata_t cf, void *aux)
 {
-#if defined(OMAP_3430) || defined(OMAP_3530) || defined(OMAP4)
        struct obio_attach_args * const oa = aux;
-#endif
 #ifdef TI_AM335X
-       struct obio_attach_args * const oa = aux;
        size_t i;
 #endif
 
@@ -189,9 +202,10 @@
 #endif
 
 #ifdef TI_AM335X
-       for (i = 0; i < __arraycount(am335x_sdhc); i++)
-               if ((oa->obio_addr == am335x_sdhc[i].as_base_addr) &&
-                   (oa->obio_intr == am335x_sdhc[i].as_intr))
+       for (i = 0; i < __arraycount(am335x_mmchs); i++)
+               if (device_is_a(parent, am335x_mmchs[i].as_parent_name) &&
+                   (oa->obio_addr == am335x_mmchs[i].as_base_addr) &&
+                   (oa->obio_intr == am335x_mmchs[i].as_intr))
                        return 1;
 #endif
 
@@ -201,31 +215,104 @@
 static void
 obiosdhc_attach(device_t parent, device_t self, void *aux)
 {
-       struct obiosdhc_softc * const sc = device_private(self);
+       struct mmchs_softc * const sc = device_private(self);
        struct obio_attach_args * const oa = aux;
-       prop_dictionary_t prop = device_properties(self);
-       uint32_t clkd, stat;
-       int error, timo, clksft, n;
-       bool support8bit = false;
-       const char *transfer_mode = "PIO";
-#if defined(OMAP4)
-       uint32_t v;
-       int x, y;
-#endif
-#ifdef TI_AM335X
-       size_t i;
-#endif
-
-       prop_dictionary_get_bool(prop, "8bit", &support8bit);
+       int error;
 
        sc->sc.sc_dmat = oa->obio_dmat;
        sc->sc.sc_dev = self;
+       sc->sc_addr = oa->obio_addr;
+       sc->sc_bst = oa->obio_iot;
+       sc->sc_irq = oa->obio_intr;
+#if defined(TI_AM335X)
+       sc->sc_edmabase = oa->obio_edmabase;
+#endif
+
+#if defined(TI_AM335X)
+       error = bus_space_map(sc->sc_bst, oa->obio_addr + OMAP4_SDMMC_HL_SIZE,
+           oa->obio_size - OMAP4_SDMMC_HL_SIZE, 0, &sc->sc_bsh);
+#elif defined(OMAP4)
+       error = bus_space_map(sc->sc_bst, oa->obio_addr, oa->obio_size, 0,
+           &sc->sc_hl_bsh);
+       if (error == 0)
+               error = bus_space_subregion(sc->sc_bst, sc->sc_hl_bsh,
+                   OMAP4_SDMMC_HL_SIZE, oa->obio_size - OMAP4_SDMMC_HL_SIZE,
+                   &sc->sc_bsh);
+#else
+       error = bus_space_map(sc->sc_bst, oa->obio_addr, oa->obio_size, 0,
+           &sc->sc_bsh);
+#endif
+       if (error != 0) {
+               aprint_error("can't map registers: %d\n", error);
+               return;
+       }
+
+       if (mmchs_attach(sc) == 0)
+               mmchs_init(self);
+}
+
+#ifdef TI_AM335X
+CFATTACH_DECL_NEW(mainbussdhc, sizeof(struct mmchs_softc),
+    mainbussdhc_match, mainbussdhc_attach, mmchs_detach, NULL);
+
+static int
+mainbussdhc_match(device_t parent, cfdata_t cf, void *aux)
+{
+       struct mainbus_attach_args * const mb = aux;
+       int i;
+
+       for (i = 0; i < __arraycount(am335x_mmchs); i++)
+               if (device_is_a(parent, am335x_mmchs[i].as_parent_name) &&
+                   (mb->mb_iobase == am335x_mmchs[i].as_base_addr) &&
+                   (mb->mb_irq == am335x_mmchs[i].as_intr))
+                       return 1;
+       return 0;
+}
+
+static void
+mainbussdhc_attach(device_t parent, device_t self, void *aux)
+{
+       struct mmchs_softc * const sc = device_private(self);
+       struct mainbus_attach_args * const mb = aux;
+       int error;
+
+       sc->sc.sc_dmat = &omap_bus_dma_tag;
+       sc->sc.sc_dev = self;
+       sc->sc_addr = mb->mb_iobase;
+       sc->sc_bst = &omap_bs_tag;
+       sc->sc_irq = mb->mb_irq;
+       sc->sc_edmabase = -1;
+
+       error = bus_space_map(sc->sc_bst, mb->mb_iobase + OMAP4_SDMMC_HL_SIZE,
+           mb->mb_iosize - OMAP4_SDMMC_HL_SIZE, 0, &sc->sc_bsh);
+       if (error != 0) {
+               aprint_error("can't map registers: %d\n", error);
+               return;
+       }
+
+       if (mmchs_attach(sc) == 0)
+               /* Ensure attach prcm, icu and edma. */
+               config_defer(self, mmchs_init);
+}
+#endif
+
+static int
+mmchs_attach(struct mmchs_softc *sc)
+{
+       device_t dev = sc->sc.sc_dev;
+       prop_dictionary_t prop = device_properties(dev);
+       int error;
+       bool support8bit = false, dualvolt = false;
+
+       prop_dictionary_get_bool(prop, "8bit", &support8bit);
+       prop_dictionary_get_bool(prop, "dual-volt", &dualvolt);
+
        sc->sc.sc_flags |= SDHC_FLAG_32BIT_ACCESS;
        sc->sc.sc_flags |= SDHC_FLAG_NO_LED_ON;
        sc->sc.sc_flags |= SDHC_FLAG_RSP136_CRC;
        if (support8bit)
                sc->sc.sc_flags |= SDHC_FLAG_8BIT_MODE;
-#if defined(OMAP_3430) || /* XXX until TI_DM37XX has working omap_devid() */ defined(TI_DM37XX)
+#if defined(OMAP_3430)
        sc->sc.sc_flags |= SDHC_FLAG_SINGLE_ONLY;
 #elif defined(OMAP_3530) || defined(TI_DM37XX)
        /*
@@ -258,52 +345,54 @@
         * mode configuration (MMCHS_HCTL.HSPE=0).



Home | Main Index | Thread Index | Old Index