tegra2: Modify MMC driver to handle power and cd GPIOs
authorStephen Warren <swarren@nvidia.com>
Mon, 31 Oct 2011 06:51:36 +0000 (06:51 +0000)
committerAlbert ARIBAUD <albert.u.boot@aribaud.net>
Fri, 9 Dec 2011 16:30:08 +0000 (17:30 +0100)
Pass the GPIO numbers for power and card detect to tegra2_mmc_init(), and
modify that function to perform all required GPIO initialization. This
removes the need for board files to perform these operations.

Move board_mmc_getcd() into tegra2_mmc.c now that the driver knows which
GPIOs to use.

Update affected call-sites in seaboard.c and harmony.c. Note that this
change should make all SD ports work on Harmony, since the required GPIO
setup is now being performed.

v4: Fix prototype of tegra2_mmc_init() in board.h to match driver change.
    Remove prototype of gpio_config_mmc() from board.h

Signed-off-by: Stephen Warren <swarren@nvidia.com>
Cc: Andy Fleming <afleming@gmail.com>
Tested-by: Simon Glass <sjg@chromium.org>
Acked-by: Simon Glass <sjg@chromium.org>
Acked-by: Andy Fleming <afleming@freescale.com>
Signed-off-by: Tom Warren <twarren@nvidia.com>
board/nvidia/common/board.h
board/nvidia/harmony/harmony.c
board/nvidia/seaboard/seaboard.c
drivers/mmc/tegra2_mmc.c
drivers/mmc/tegra2_mmc.h

index 344e70283e318c7b66cf84b209f2f52a1791b99a..35acbca82bb1884a79c183d1af3406240a68e16f 100644 (file)
@@ -26,7 +26,6 @@
 
 void tegra2_start(void);
 void gpio_config_uart(void);
-void gpio_config_mmc(void);
-int tegra2_mmc_init(int dev_index, int bus_width);
+int tegra2_mmc_init(int dev_index, int bus_width, int pwr_gpio, int cd_gpio);
 
 #endif /* BOARD_H */
index f2c3867251f48322dfb9f98c5058b30db272bef0..3cbe820c95156e725ac206d4376ca0b0da7100b6 100644 (file)
@@ -25,6 +25,7 @@
 #include <asm/io.h>
 #include <asm/arch/tegra2.h>
 #include <asm/arch/pinmux.h>
+#include <asm/gpio.h>
 #ifdef CONFIG_TEGRA2_MMC
 #include <mmc.h>
 #endif
@@ -72,15 +73,6 @@ static void pin_mux_mmc(void)
        pinmux_tristate_disable(PINGRP_ATC);
 }
 
-/*
- * Routine: gpio_config_mmc
- * Description: Set GPIOs for SD card
- */
-void gpio_config_mmc(void)
-{
-       /* Not implemented for now */
-}
-
 /* this is a weak define that we are overriding */
 int board_mmc_init(bd_t *bd)
 {
@@ -88,29 +80,16 @@ int board_mmc_init(bd_t *bd)
 
        /* Enable muxes, etc. for SDMMC controllers */
        pin_mux_mmc();
-       gpio_config_mmc();
 
        debug("board_mmc_init: init SD slot J26\n");
        /* init dev 0, SD slot J26, with 4-bit bus */
        /* The board has an 8-bit bus, but 8-bit doesn't work yet */
-       tegra2_mmc_init(0, 4);
+       tegra2_mmc_init(0, 4, GPIO_PI6, GPIO_PH2);
 
        debug("board_mmc_init: init SD slot J5\n");
        /* init dev 2, SD slot J5, with 4-bit bus */
-       tegra2_mmc_init(2, 4);
+       tegra2_mmc_init(2, 4, GPIO_PT3, GPIO_PI5);
 
        return 0;
 }
-
-/* this is a weak define that we are overriding */
-int board_mmc_getcd(u8 *cd, struct mmc *mmc)
-{
-       debug("board_mmc_getcd called\n");
-       /*
-        * Hard-code CD presence for now. Need to add GPIO inputs
-        * for Harmony
-        */
-       *cd = 1;
-       return 0;
-}
 #endif
index 22a0e69f06c37412d6a9a8fef1b8cecbe4e0cdfa..356d616ab15389988fda8876430afd55805514e6 100644 (file)
@@ -87,19 +87,6 @@ static void pin_mux_mmc(void)
        pinmux_tristate_disable(PINGRP_ATC);
 }
 
-/*
- * Routine: gpio_config_mmc
- * Description: Set GPIOs for SDMMC3 SDIO slot.
- */
-void gpio_config_mmc(void)
-{
-       /* Set EN_VDDIO_SD (GPIO I6) */
-       gpio_direction_output(GPIO_PI6, 1);
-
-       /* Config pin as GPI for Card Detect (GPIO I5) */
-       gpio_direction_input(GPIO_PI5);
-}
-
 /* this is a weak define that we are overriding */
 int board_mmc_init(bd_t *bd)
 {
@@ -107,31 +94,15 @@ int board_mmc_init(bd_t *bd)
 
        /* Enable muxes, etc. for SDMMC controllers */
        pin_mux_mmc();
-       gpio_config_mmc();
 
        debug("board_mmc_init: init eMMC\n");
        /* init dev 0, eMMC chip, with 4-bit bus */
        /* The board has an 8-bit bus, but 8-bit doesn't work yet */
-       tegra2_mmc_init(0, 4);
+       tegra2_mmc_init(0, 4, -1, -1);
 
        debug("board_mmc_init: init SD slot\n");
        /* init dev 1, SD slot, with 4-bit bus */
-       tegra2_mmc_init(1, 4);
-
-       return 0;
-}
-
-/* this is a weak define that we are overriding */
-int board_mmc_getcd(u8 *cd, struct mmc *mmc)
-{
-       debug("board_mmc_getcd called\n");
-       *cd = 1;                        /* Assume card is inserted, or eMMC */
-
-       if (IS_SD(mmc)) {
-               /* Seaboard SDMMC3 = SDIO3_CD = GPIO_PI5 */
-               if (gpio_get_value(GPIO_PI5))
-                       *cd = 0;
-       }
+       tegra2_mmc_init(1, 4, GPIO_PI6, GPIO_PI5);
 
        return 0;
 }
index ccf48bbb17ca918f72513c1841c52f461a5623b9..035a8687df724361098b780fc1d7860f314faabd 100644 (file)
@@ -21,6 +21,7 @@
 
 #include <common.h>
 #include <mmc.h>
+#include <asm/gpio.h>
 #include <asm/io.h>
 #include <asm/arch/clk_rst.h>
 #include <asm/arch/clock.h>
@@ -473,20 +474,37 @@ static int mmc_core_init(struct mmc *mmc)
        return 0;
 }
 
-static int tegra2_mmc_initialize(int dev_index, int bus_width)
+int tegra2_mmc_init(int dev_index, int bus_width, int pwr_gpio, int cd_gpio)
 {
        struct mmc_host *host;
+       char gpusage[12]; /* "SD/MMCn PWR" or "SD/MMCn CD" */
        struct mmc *mmc;
 
-       debug(" mmc_initialize called\n");
+       debug(" tegra2_mmc_init: index %d, bus width %d "
+               "pwr_gpio %d cd_gpio %d\n",
+               dev_index, bus_width, pwr_gpio, cd_gpio);
 
        host = &mmc_host[dev_index];
 
        host->clock = 0;
+       host->pwr_gpio = pwr_gpio;
+       host->cd_gpio = cd_gpio;
        tegra2_get_setup(host, dev_index);
 
        clock_start_periph_pll(host->mmc_id, CLOCK_ID_PERIPH, 20000000);
 
+       if (host->pwr_gpio >= 0) {
+               sprintf(gpusage, "SD/MMC%d PWR", dev_index);
+               gpio_request(host->pwr_gpio, gpusage);
+               gpio_direction_output(host->pwr_gpio, 1);
+       }
+
+       if (host->cd_gpio >= 0) {
+               sprintf(gpusage, "SD/MMC%d CD", dev_index);
+               gpio_request(host->cd_gpio, gpusage);
+               gpio_direction_input(host->cd_gpio);
+       }
+
        mmc = &mmc_dev[dev_index];
 
        sprintf(mmc->name, "Tegra2 SD/MMC");
@@ -518,9 +536,21 @@ static int tegra2_mmc_initialize(int dev_index, int bus_width)
        return 0;
 }
 
-int tegra2_mmc_init(int dev_index, int bus_width)
+/* this is a weak define that we are overriding */
+int board_mmc_getcd(u8 *cd, struct mmc *mmc)
 {
-       debug(" tegra2_mmc_init: index %d, bus width %d\n",
-               dev_index, bus_width);
-       return tegra2_mmc_initialize(dev_index, bus_width);
+       struct mmc_host *host = (struct mmc_host *)mmc->priv;
+
+       debug("board_mmc_getcd called\n");
+
+       *cd = 1; /* Assume card is inserted, or eMMC */
+
+       if (IS_SD(mmc)) {
+               if (host->cd_gpio >= 0) {
+                       if (gpio_get_value(host->cd_gpio))
+                               *cd = 0;
+               }
+       }
+
+       return 0;
 }
index 671583c42219af4df4848c27fc09d4ba521c1e18..b2f6c5baad059c81479f83fb9f9a187d2cf162fa 100644 (file)
@@ -123,9 +123,11 @@ struct mmc_host {
        unsigned int clock;     /* Current clock (MHz) */
        unsigned int base;      /* Base address, SDMMC1/2/3/4 */
        enum periph_id mmc_id;  /* Peripheral ID: PERIPH_ID_... */
+       int pwr_gpio;           /* Power GPIO */
+       int cd_gpio;            /* Change Detect GPIO */
 };
 
-int tegra2_mmc_init(int dev_index, int bus_width);
+int tegra2_mmc_init(int dev_index, int bus_width, int pwr_gpio, int cd_gpio);
 
 #endif /* __ASSEMBLY__ */
 #endif /* __TEGRA2_MMC_H_ */