The branch main has been updated by mw:

URL: 
https://cgit.FreeBSD.org/src/commit/?id=f0a9d7d7995641901e3132242d1d9bf22dc333f6

commit f0a9d7d7995641901e3132242d1d9bf22dc333f6
Author:     Marcin Wojtas <m...@freebsd.org>
AuthorDate: 2021-04-22 10:54:41 +0000
Commit:     Marcin Wojtas <m...@freebsd.org>
CommitDate: 2021-05-14 08:29:31 +0000

    sdhci_fsl_fdt.c: Add a missing call to mmc_fdt_parse.
    
    Add a missing call to mmc_fdt_parse, without it some dts properties
    are not parsed.
    
    Submitted by: Lukasz Hajec <l...@semihalf.com>
    Reviewed by: manu
    Obtained from: Semihalf
    Sponsored by: Alstom Group
    Differential Revision: https://reviews.freebsd.org/D30122
---
 sys/dev/sdhci/sdhci_fsl_fdt.c | 110 ++++++++++++++++++++++++++++++++++++++++--
 1 file changed, 106 insertions(+), 4 deletions(-)

diff --git a/sys/dev/sdhci/sdhci_fsl_fdt.c b/sys/dev/sdhci/sdhci_fsl_fdt.c
index 695176a17218..c2330a679963 100644
--- a/sys/dev/sdhci/sdhci_fsl_fdt.c
+++ b/sys/dev/sdhci/sdhci_fsl_fdt.c
@@ -45,6 +45,7 @@ __FBSDID("$FreeBSD$");
 #include <dev/extres/clk/clk.h>
 #include <dev/mmc/bridge.h>
 #include <dev/mmc/mmcbrvar.h>
+#include <dev/mmc/mmc_fdt_helpers.h>
 #include <dev/ofw/ofw_bus.h>
 #include <dev/ofw/ofw_bus_subr.h>
 #include <dev/sdhci/sdhci.h>
@@ -96,11 +97,13 @@ struct sdhci_fsl_fdt_softc {
        struct resource                         *irq_res;
        void                                    *irq_cookie;
        uint32_t                                baseclk_hz;
+       uint32_t                                maxclk_hz;
        struct sdhci_fdt_gpio                   *gpio;
        struct sdhci_slot                       slot;
        bool                                    slot_init_done;
        uint32_t                                cmd_and_mode;
        uint16_t                                sdclk_bits;
+       struct mmc_fdt_helper                   fdt_helper;
 
        uint32_t (* read)(struct sdhci_fsl_fdt_softc *, bus_size_t);
        void (* write)(struct sdhci_fsl_fdt_softc *, bus_size_t, uint32_t);
@@ -194,9 +197,9 @@ fsl_sdhc_fdt_set_clock(struct sdhci_fsl_fdt_softc *sc, 
uint16_t val)
            ((val >> SDHCI_DIVIDER_HI_SHIFT) & SDHCI_DIVIDER_HI_MASK) <<
            SDHCI_DIVIDER_MASK_LEN;
        if (div == 0)
-               freq = sc->baseclk_hz;
+               freq = sc->maxclk_hz;
        else
-               freq = sc->baseclk_hz / (2 * div);
+               freq = sc->maxclk_hz / (2 * div);
 
        for (prescale = 2; freq < sc->baseclk_hz / (prescale * 16); )
                prescale <<= 1;
@@ -445,6 +448,86 @@ sdhci_fsl_fdt_irq(void *arg)
        return;
 }
 
+static int
+sdhci_fsl_fdt_update_ios(device_t brdev, device_t reqdev)
+{
+       int err;
+       struct sdhci_fsl_fdt_softc *sc;
+       struct mmc_ios *ios;
+       struct sdhci_slot *slot;
+
+       err = sdhci_generic_update_ios(brdev, reqdev);
+       if (err != 0)
+               return (err);
+
+       sc = device_get_softc(brdev);
+       slot = device_get_ivars(reqdev);
+       ios = &slot->host.ios;
+
+       switch (ios->power_mode) {
+       case power_on:
+               break;
+       case power_off:
+               if (bootverbose)
+                       device_printf(sc->dev, "Powering down sd/mmc\n");
+
+               if (sc->fdt_helper.vmmc_supply)
+                       regulator_disable(sc->fdt_helper.vmmc_supply);
+               if (sc->fdt_helper.vqmmc_supply)
+                       regulator_disable(sc->fdt_helper.vqmmc_supply);
+               break;
+       case power_up:
+               if (bootverbose)
+                       device_printf(sc->dev, "Powering up sd/mmc\n");
+
+               if (sc->fdt_helper.vmmc_supply)
+                       regulator_enable(sc->fdt_helper.vmmc_supply);
+               if (sc->fdt_helper.vqmmc_supply)
+                       regulator_enable(sc->fdt_helper.vqmmc_supply);
+               break;
+       };
+
+       return (0);
+}
+
+static int
+sdhci_fsl_fdt_switch_vccq(device_t brdev, device_t reqdev)
+{
+       struct sdhci_fsl_fdt_softc *sc;
+       struct sdhci_slot *slot;
+       int uvolt, err;
+
+       err = sdhci_generic_switch_vccq(brdev, reqdev);
+       if (err != 0)
+               return (err);
+
+       sc = device_get_softc(brdev);
+
+       if (sc->fdt_helper.vqmmc_supply == NULL)
+               return EOPNOTSUPP;
+
+       slot = device_get_ivars(reqdev);
+       switch (slot->host.ios.vccq) {
+       case vccq_180:
+               uvolt = 1800000;
+               break;
+       case vccq_330:
+               uvolt = 3300000;
+               break;
+       default:
+               return EINVAL;
+       }
+
+       err = regulator_set_voltage(sc->fdt_helper.vqmmc_supply, uvolt, uvolt);
+       if (err != 0) {
+               device_printf(sc->dev,
+                   "Cannot set vqmmc to %d<->%d\n", uvolt, uvolt);
+               return (err);
+       }
+
+       return (0);
+}
+
 static int
 sdhci_fsl_fdt_get_ro(device_t bus, device_t child)
 {
@@ -463,10 +546,24 @@ sdhci_fsl_fdt_get_card_present(device_t dev, struct 
sdhci_slot *slot)
        return (sdhci_fdt_gpio_get_present(sc->gpio));
 }
 
+static void
+sdhci_fsl_fdt_of_parse(device_t dev)
+{
+       struct sdhci_fsl_fdt_softc *sc;
+       phandle_t node;
+
+       sc = device_get_softc(dev);
+       node = ofw_bus_get_node(dev);
+
+       /* Call mmc_fdt_parse in order to get mmc related properties. */
+       mmc_fdt_parse(dev, node, &sc->fdt_helper, &sc->slot.host);
+}
+
 static int
 sdhci_fsl_fdt_attach(device_t dev)
 {
        struct sdhci_fsl_fdt_softc *sc;
+       struct mmc_host *host;
        uint32_t val, buf_order;
        uintptr_t ocd_data;
        uint64_t clk_hz;
@@ -481,6 +578,7 @@ sdhci_fsl_fdt_attach(device_t dev)
        sc->soc_data = (struct sdhci_fsl_fdt_soc_data *)ocd_data;
        sc->dev = dev;
        sc->slot.quirks = sc->soc_data->quirks;
+       host = &sc->slot.host;
 
        rid = 0;
        sc->mem_res = bus_alloc_resource_any(dev, SYS_RES_MEMORY, &rid,
@@ -534,6 +632,9 @@ sdhci_fsl_fdt_attach(device_t dev)
                buf_order = SDHCI_FSL_PROT_CTRL_BYTE_SWAP;
        }
 
+       sdhci_fsl_fdt_of_parse(dev);
+       sc->maxclk_hz = host->f_max ? host->f_max : sc->baseclk_hz;
+
        /*
         * Setting this register affects byte order in SDHCI_BUFFER only.
         * If the eSDHC block is connected over a big-endian bus, the data
@@ -555,7 +656,7 @@ sdhci_fsl_fdt_attach(device_t dev)
        WR4(sc, SDHCI_CLOCK_CONTROL, val & ~SDHCI_FSL_CLK_SDCLKEN);
        val = RD4(sc, SDHCI_FSL_ESDHC_CTRL);
        WR4(sc, SDHCI_FSL_ESDHC_CTRL, val | SDHCI_FSL_ESDHC_CTRL_CLK_DIV2);
-       sc->slot.max_clk = sc->baseclk_hz;
+       sc->slot.max_clk = sc->maxclk_hz;
        sc->gpio = sdhci_fdt_gpio_setup(dev, &sc->slot);
 
        /*
@@ -656,11 +757,12 @@ static const device_method_t sdhci_fsl_fdt_methods[] = {
        DEVMETHOD(bus_write_ivar,               sdhci_generic_write_ivar),
 
        /* MMC bridge interface. */
-       DEVMETHOD(mmcbr_update_ios,             sdhci_generic_update_ios),
        DEVMETHOD(mmcbr_request,                sdhci_generic_request),
        DEVMETHOD(mmcbr_get_ro,                 sdhci_fsl_fdt_get_ro),
        DEVMETHOD(mmcbr_acquire_host,           sdhci_generic_acquire_host),
        DEVMETHOD(mmcbr_release_host,           sdhci_generic_release_host),
+       DEVMETHOD(mmcbr_switch_vccq,            sdhci_fsl_fdt_switch_vccq),
+       DEVMETHOD(mmcbr_update_ios,             sdhci_fsl_fdt_update_ios),
 
        /* SDHCI accessors. */
        DEVMETHOD(sdhci_read_1,                 sdhci_fsl_fdt_read_1),
_______________________________________________
dev-commits-src-main@freebsd.org mailing list
https://lists.freebsd.org/mailman/listinfo/dev-commits-src-main
To unsubscribe, send any mail to "dev-commits-src-main-unsubscr...@freebsd.org"

Reply via email to