Source-Changes-HG archive

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

[src/trunk]: src/sys/dev/sdmmc From OpenBSD:



details:   https://anonhg.NetBSD.org/src/rev/31c54c1e9520
branches:  trunk
changeset: 459217:31c54c1e9520
user:      mlelstv <mlelstv%NetBSD.org@localhost>
date:      Sun Sep 01 05:45:42 2019 +0000

description:
>From OpenBSD:
- support block length per function
- add functions to read/write regions
Decode (but not use) SDIO tuple in CIS.
Fix locking.
Add more SDIO defines (partially from version 3.0).

diffstat:

 sys/dev/sdmmc/sdmmc.c       |    5 +-
 sys/dev/sdmmc/sdmmc_cis.c   |   10 ++-
 sys/dev/sdmmc/sdmmc_io.c    |  141 ++++++++++++++++++++++++++++++++++++-------
 sys/dev/sdmmc/sdmmc_ioreg.h |   37 ++++++++++-
 sys/dev/sdmmc/sdmmcvar.h    |    7 +-
 5 files changed, 170 insertions(+), 30 deletions(-)

diffs (truncated from 431 to 300 lines):

diff -r 5a388577dab4 -r 31c54c1e9520 sys/dev/sdmmc/sdmmc.c
--- a/sys/dev/sdmmc/sdmmc.c     Sun Sep 01 05:40:39 2019 +0000
+++ b/sys/dev/sdmmc/sdmmc.c     Sun Sep 01 05:45:42 2019 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: sdmmc.c,v 1.36 2018/11/06 16:01:38 jmcneill Exp $      */
+/*     $NetBSD: sdmmc.c,v 1.37 2019/09/01 05:45:42 mlelstv Exp $       */
 /*     $OpenBSD: sdmmc.c,v 1.18 2009/01/09 10:58:38 jsg Exp $  */
 
 /*
@@ -49,7 +49,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: sdmmc.c,v 1.36 2018/11/06 16:01:38 jmcneill Exp $");
+__KERNEL_RCSID(0, "$NetBSD: sdmmc.c,v 1.37 2019/09/01 05:45:42 mlelstv Exp $");
 
 #ifdef _KERNEL_OPT
 #include "opt_sdmmc.h"
@@ -656,6 +656,7 @@
        sf->cis.product = SDMMC_PRODUCT_INVALID;
        sf->cis.function = SDMMC_FUNCTION_INVALID;
        sf->width = 1;
+       sf->blklen = sdmmc_chip_host_maxblklen(sc->sc_sct, sc->sc_sch);
 
        if (ISSET(sc->sc_flags, SMF_MEM_MODE) &&
            ISSET(sc->sc_caps, SMC_CAPS_DMA) &&
diff -r 5a388577dab4 -r 31c54c1e9520 sys/dev/sdmmc/sdmmc_cis.c
--- a/sys/dev/sdmmc/sdmmc_cis.c Sun Sep 01 05:40:39 2019 +0000
+++ b/sys/dev/sdmmc/sdmmc_cis.c Sun Sep 01 05:45:42 2019 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: sdmmc_cis.c,v 1.5 2018/01/28 14:34:06 jmcneill Exp $   */
+/*     $NetBSD: sdmmc_cis.c,v 1.6 2019/09/01 05:45:42 mlelstv Exp $    */
 /*     $OpenBSD: sdmmc_cis.c,v 1.1 2006/06/01 21:53:41 uwe Exp $       */
 
 /*
@@ -20,7 +20,7 @@
 /* Routines to decode the Card Information Structure of SD I/O cards */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: sdmmc_cis.c,v 1.5 2018/01/28 14:34:06 jmcneill Exp $");
+__KERNEL_RCSID(0, "$NetBSD: sdmmc_cis.c,v 1.6 2019/09/01 05:45:42 mlelstv Exp $");
 
 #ifdef _KERNEL_OPT
 #include "opt_sdmmc.h"
@@ -130,6 +130,7 @@
        max_blk_size = sdmmc_io_read_1(sf0, reg + 11);
        max_blk_size |= sdmmc_io_read_1(sf0, reg + 12) << 8;
 
+device_printf(dev, "MAX_BLK_SIZE%d = %d\n", sf->number, max_blk_size);
        DPRINTF(("CISTPL_FUNCE: MAX_BLK_SIZE=0x%x\n", max_blk_size));
 }
 
@@ -259,6 +260,11 @@
                        reg += tpllen;
                        break;
 
+               case PCMCIA_CISTPL_SDIO:
+                       aprint_normal_dev(dev, "SDIO function\n");
+                       reg += tpllen;
+                       break;
+
                default:
                        /*
                         * Tuple codes between 80h-8Fh are vendor unique.
diff -r 5a388577dab4 -r 31c54c1e9520 sys/dev/sdmmc/sdmmc_io.c
--- a/sys/dev/sdmmc/sdmmc_io.c  Sun Sep 01 05:40:39 2019 +0000
+++ b/sys/dev/sdmmc/sdmmc_io.c  Sun Sep 01 05:45:42 2019 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: sdmmc_io.c,v 1.14 2018/10/14 17:37:40 jdolecek Exp $   */
+/*     $NetBSD: sdmmc_io.c,v 1.15 2019/09/01 05:45:42 mlelstv Exp $    */
 /*     $OpenBSD: sdmmc_io.c,v 1.10 2007/09/17 01:33:33 krw Exp $       */
 
 /*
@@ -20,7 +20,7 @@
 /* Routines for SD I/O cards. */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: sdmmc_io.c,v 1.14 2018/10/14 17:37:40 jdolecek Exp $");
+__KERNEL_RCSID(0, "$NetBSD: sdmmc_io.c,v 1.15 2019/09/01 05:45:42 mlelstv Exp $");
 
 #ifdef _KERNEL_OPT
 #include "opt_sdmmc.h"
@@ -194,6 +194,8 @@
 
        SDMMC_LOCK(sc);
 
+       sf->blklen = sdmmc_chip_host_maxblklen(sc->sc_sct, sc->sc_sch);
+
        if (sf->number == 0) {
                reg = sdmmc_io_read_1(sf, SD_IO_CCCR_CAPABILITY);
                if (!(reg & CCCR_CAPS_LSC) || (reg & CCCR_CAPS_4BLS)) {
@@ -395,8 +397,8 @@
        cmd.c_flags = SCF_CMD_AC | SCF_RSP_R5;
        cmd.c_data = datap;
        cmd.c_datalen = datalen;
-       cmd.c_blklen = MIN(datalen,
-           sdmmc_chip_host_maxblklen(sc->sc_sct,sc->sc_sch));
+       cmd.c_blklen = MIN(datalen, sf->blklen);
+
        if (!ISSET(arg, SD_ARG_CMD53_WRITE))
                cmd.c_flags |= SCF_CMD_READ;
 
@@ -476,21 +478,26 @@
 sdmmc_io_read_multi_1(struct sdmmc_function *sf, int reg, u_char *data,
     int datalen)
 {
-       int error;
+       int blocks, bytes, error = 0;
 
        /* Don't lock */
 
-       while (datalen > SD_ARG_CMD53_LENGTH_MAX) {
+       while (datalen >= sf->blklen) {
+               //blocks = imin(datalen / sf->blklen,
+               //              SD_ARG_CMD53_LENGTH_MAX);
+               blocks = 1;
+               bytes = blocks * sf->blklen;
                error = sdmmc_io_rw_extended(sf->sc, sf, reg, data,
-                   SD_ARG_CMD53_LENGTH_MAX, SD_ARG_CMD53_READ);
+                   bytes, SD_ARG_CMD53_READ);
                if (error)
                        goto error;
-               data += SD_ARG_CMD53_LENGTH_MAX;
-               datalen -= SD_ARG_CMD53_LENGTH_MAX;
+               data += bytes;
+               datalen -= bytes;
        }
 
-       error = sdmmc_io_rw_extended(sf->sc, sf, reg, data, datalen,
-           SD_ARG_CMD53_READ);
+       if (datalen)
+               error = sdmmc_io_rw_extended(sf->sc, sf, reg, data, datalen,
+                   SD_ARG_CMD53_READ);
 error:
        return error;
 }
@@ -499,21 +506,85 @@
 sdmmc_io_write_multi_1(struct sdmmc_function *sf, int reg, u_char *data,
     int datalen)
 {
-       int error;
+       int blocks, bytes, error = 0;
+
+       /* Don't lock */
+
+       while (datalen >= sf->blklen) {
+               //blocks = imin(datalen / sf->blklen,
+               //             SD_ARG_CMD53_LENGTH_MAX);
+               blocks = 1;
+               bytes = blocks * sf->blklen;
+               error = sdmmc_io_rw_extended(sf->sc, sf, reg, data,
+                   bytes, SD_ARG_CMD53_WRITE);
+               if (error)
+                       goto error;
+               data += bytes;
+               datalen -= bytes;
+       }
+
+       if (datalen)
+               error = sdmmc_io_rw_extended(sf->sc, sf, reg, data, datalen,
+                   SD_ARG_CMD53_WRITE);
+error:
+       return error;
+}
+
+
+int
+sdmmc_io_read_region_1(struct sdmmc_function *sf, int reg, u_char *data,
+    int datalen)
+{
+       int blocks, bytes, error = 0;
 
        /* Don't lock */
 
-       while (datalen > SD_ARG_CMD53_LENGTH_MAX) {
+       while (datalen >= sf->blklen) {
+               //blocks = imin(datalen / sf->blklen,
+               //              SD_ARG_CMD53_LENGTH_MAX);
+               blocks = 1;
+               bytes = blocks * sf->blklen;
                error = sdmmc_io_rw_extended(sf->sc, sf, reg, data,
-                   SD_ARG_CMD53_LENGTH_MAX, SD_ARG_CMD53_WRITE);
+                   bytes, SD_ARG_CMD53_READ | SD_ARG_CMD53_INCREMENT);
                if (error)
                        goto error;
-               data += SD_ARG_CMD53_LENGTH_MAX;
-               datalen -= SD_ARG_CMD53_LENGTH_MAX;
+               reg += bytes;
+               data += bytes;
+               datalen -= bytes;
        }
 
-       error = sdmmc_io_rw_extended(sf->sc, sf, reg, data, datalen,
-           SD_ARG_CMD53_WRITE);
+       if (datalen)
+               error = sdmmc_io_rw_extended(sf->sc, sf, reg, data, datalen,
+                   SD_ARG_CMD53_READ | SD_ARG_CMD53_INCREMENT);
+error:
+       return error;
+}
+
+int
+sdmmc_io_write_region_1(struct sdmmc_function *sf, int reg, u_char *data,
+    int datalen)
+{
+       int blocks, bytes, error = 0;
+
+       /* Don't lock */
+
+       while (datalen >= sf->blklen) {
+               //blocks = imin(datalen / sf->blklen,
+               //              SD_ARG_CMD53_LENGTH_MAX);
+               blocks = 1;
+               bytes = blocks * sf->blklen;
+               error = sdmmc_io_rw_extended(sf->sc, sf, reg, data,
+                   bytes, SD_ARG_CMD53_WRITE | SD_ARG_CMD53_INCREMENT);
+               if (error)
+                       goto error;
+               reg += bytes;
+               data += bytes;
+               datalen -= bytes;
+       }
+
+       if (datalen)
+               error = sdmmc_io_rw_extended(sf->sc, sf, reg, data, datalen,
+                   SD_ARG_CMD53_WRITE | SD_ARG_CMD53_INCREMENT);
 error:
        return error;
 }
@@ -539,7 +610,8 @@
 {
        u_char data = CCCR_CTL_RES;
 
-       if (sdmmc_io_rw_direct(sc, NULL, SD_IO_CCCR_CTL, &data, SD_ARG_CMD52_WRITE) == 0)
+       if (sdmmc_io_rw_direct(sc, NULL, SD_IO_CCCR_CTL, &data,
+           SD_ARG_CMD52_WRITE) == 0)
                sdmmc_delay(100000);
 }
 
@@ -597,11 +669,9 @@
        uint8_t reg;
 
        SDMMC_LOCK(sc);
-       mutex_enter(&sc->sc_intr_task_mtx);
        reg = sdmmc_io_read_1(sf0, SD_IO_CCCR_FN_INTEN);
        reg |= 1 << sf->number;
        sdmmc_io_write_1(sf0, SD_IO_CCCR_FN_INTEN, reg);
-       mutex_exit(&sc->sc_intr_task_mtx);
        SDMMC_UNLOCK(sc);
 }
 
@@ -613,11 +683,9 @@
        uint8_t reg;
 
        SDMMC_LOCK(sc);
-       mutex_enter(&sc->sc_intr_task_mtx);
        reg = sdmmc_io_read_1(sf0, SD_IO_CCCR_FN_INTEN);
        reg &= ~(1 << sf->number);
        sdmmc_io_write_1(sf0, SD_IO_CCCR_FN_INTEN, reg);
-       mutex_exit(&sc->sc_intr_task_mtx);
        SDMMC_UNLOCK(sc);
 }
 
@@ -719,3 +787,30 @@
 
        sdmmc_chip_card_intr_ack(sc->sc_sct, sc->sc_sch);
 }
+
+int
+sdmmc_io_set_blocklen(struct sdmmc_softc *sc, struct sdmmc_function *sf,
+     int blklen)
+{
+       struct sdmmc_function *sf0 = sc->sc_fn0;
+       int error = EINVAL;
+
+       SDMMC_LOCK(sc);
+
+       if (blklen <= 0 ||
+           blklen > sdmmc_chip_host_maxblklen(sc->sc_sct, sc->sc_sch))
+               goto err;
+
+       sdmmc_io_write_1(sf0, SD_IO_FBR(sf->number) +
+           SD_IO_FBR_BLOCKLEN, blklen & 0xff);
+       sdmmc_io_write_1(sf0, SD_IO_FBR(sf->number) +
+           SD_IO_FBR_BLOCKLEN + 1, (blklen >> 8) & 0xff);
+
+       sf->blklen = blklen;
+       error = 0;
+
+err:
+       SDMMC_UNLOCK(sc);
+
+       return error;
+}
diff -r 5a388577dab4 -r 31c54c1e9520 sys/dev/sdmmc/sdmmc_ioreg.h
--- a/sys/dev/sdmmc/sdmmc_ioreg.h       Sun Sep 01 05:40:39 2019 +0000
+++ b/sys/dev/sdmmc/sdmmc_ioreg.h       Sun Sep 01 05:45:42 2019 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: sdmmc_ioreg.h,v 1.3 2019/07/24 05:45:42 msaitoh Exp $  */
+/*     $NetBSD: sdmmc_ioreg.h,v 1.4 2019/09/01 05:45:42 mlelstv Exp $  */



Home | Main Index | Thread Index | Old Index