Duy Truong | 790f06d | 2013-02-13 16:38:12 -0800 | [diff] [blame] | 1 | /* Copyright (c) 2011-2012, The Linux Foundation. All rights reserved. |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 2 | * |
| 3 | * This program is free software; you can redistribute it and/or modify |
| 4 | * it under the terms of the GNU General Public License version 2 and |
| 5 | * only version 2 as published by the Free Software Foundation. |
| 6 | * |
| 7 | * This program is distributed in the hope that it will be useful, |
| 8 | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 9 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 10 | * GNU General Public License for more details. |
| 11 | * |
| 12 | */ |
| 13 | |
| 14 | #include <linux/init.h> |
| 15 | #include <linux/ioport.h> |
| 16 | #include <linux/platform_device.h> |
Steve Muckle | f132c6c | 2012-06-06 18:30:57 -0700 | [diff] [blame] | 17 | #include <linux/gpio.h> |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 18 | #include <linux/bootmem.h> |
| 19 | #include <asm/mach-types.h> |
| 20 | #include <asm/mach/mmc.h> |
| 21 | #include <mach/msm_bus_board.h> |
| 22 | #include <mach/board.h> |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 23 | #include <mach/gpiomux.h> |
| 24 | #include "devices.h" |
Stepan Moskovchenko | 5a83dba | 2011-12-05 17:30:17 -0800 | [diff] [blame] | 25 | #include "board-8064.h" |
Subhash Jadavani | bcd435f | 2012-04-24 18:26:49 +0530 | [diff] [blame] | 26 | #include "board-storage-common-a.h" |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 27 | |
| 28 | |
| 29 | /* APQ8064 has 4 SDCC controllers */ |
| 30 | enum sdcc_controllers { |
| 31 | SDCC1, |
| 32 | SDCC2, |
| 33 | SDCC3, |
| 34 | SDCC4, |
| 35 | MAX_SDCC_CONTROLLER |
| 36 | }; |
| 37 | |
| 38 | /* All SDCC controllers require VDD/VCC voltage */ |
| 39 | static struct msm_mmc_reg_data mmc_vdd_reg_data[MAX_SDCC_CONTROLLER] = { |
| 40 | /* SDCC1 : eMMC card connected */ |
| 41 | [SDCC1] = { |
| 42 | .name = "sdc_vdd", |
| 43 | .high_vol_level = 2950000, |
| 44 | .low_vol_level = 2950000, |
| 45 | .always_on = 1, |
| 46 | .lpm_sup = 1, |
| 47 | .lpm_uA = 9000, |
| 48 | .hpm_uA = 200000, /* 200mA */ |
| 49 | }, |
| 50 | /* SDCC3 : External card slot connected */ |
| 51 | [SDCC3] = { |
| 52 | .name = "sdc_vdd", |
| 53 | .high_vol_level = 2950000, |
| 54 | .low_vol_level = 2950000, |
Oluwafemi Adeyemi | aafeeb0 | 2012-02-20 21:01:15 -0800 | [diff] [blame] | 55 | .hpm_uA = 800000, /* 800mA */ |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 56 | } |
| 57 | }; |
| 58 | |
Subhash Jadavani | 937c750 | 2012-06-01 15:34:46 +0530 | [diff] [blame] | 59 | /* SDCC controllers may require voting for VDD IO voltage */ |
| 60 | static struct msm_mmc_reg_data mmc_vdd_io_reg_data[MAX_SDCC_CONTROLLER] = { |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 61 | /* SDCC1 : eMMC card connected */ |
| 62 | [SDCC1] = { |
Subhash Jadavani | 937c750 | 2012-06-01 15:34:46 +0530 | [diff] [blame] | 63 | .name = "sdc_vdd_io", |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 64 | .always_on = 1, |
| 65 | .high_vol_level = 1800000, |
| 66 | .low_vol_level = 1800000, |
| 67 | .hpm_uA = 200000, /* 200mA */ |
Subhash Jadavani | 937c750 | 2012-06-01 15:34:46 +0530 | [diff] [blame] | 68 | }, |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 69 | /* SDCC3 : External card slot connected */ |
| 70 | [SDCC3] = { |
Subhash Jadavani | 937c750 | 2012-06-01 15:34:46 +0530 | [diff] [blame] | 71 | .name = "sdc_vdd_io", |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 72 | .high_vol_level = 2950000, |
| 73 | .low_vol_level = 1850000, |
| 74 | .always_on = 1, |
| 75 | .lpm_sup = 1, |
| 76 | /* Max. Active current required is 16 mA */ |
| 77 | .hpm_uA = 16000, |
| 78 | /* |
| 79 | * Sleep current required is ~300 uA. But min. vote can be |
| 80 | * in terms of mA (min. 1 mA). So let's vote for 2 mA |
| 81 | * during sleep. |
| 82 | */ |
| 83 | .lpm_uA = 2000, |
| 84 | } |
| 85 | }; |
| 86 | |
| 87 | static struct msm_mmc_slot_reg_data mmc_slot_vreg_data[MAX_SDCC_CONTROLLER] = { |
| 88 | /* SDCC1 : eMMC card connected */ |
| 89 | [SDCC1] = { |
| 90 | .vdd_data = &mmc_vdd_reg_data[SDCC1], |
Subhash Jadavani | 937c750 | 2012-06-01 15:34:46 +0530 | [diff] [blame] | 91 | .vdd_io_data = &mmc_vdd_io_reg_data[SDCC1], |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 92 | }, |
| 93 | /* SDCC3 : External card slot connected */ |
| 94 | [SDCC3] = { |
| 95 | .vdd_data = &mmc_vdd_reg_data[SDCC3], |
Subhash Jadavani | 937c750 | 2012-06-01 15:34:46 +0530 | [diff] [blame] | 96 | .vdd_io_data = &mmc_vdd_io_reg_data[SDCC3], |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 97 | } |
| 98 | }; |
| 99 | |
| 100 | /* SDC1 pad data */ |
| 101 | static struct msm_mmc_pad_drv sdc1_pad_drv_on_cfg[] = { |
| 102 | {TLMM_HDRV_SDC1_CLK, GPIO_CFG_16MA}, |
| 103 | {TLMM_HDRV_SDC1_CMD, GPIO_CFG_10MA}, |
| 104 | {TLMM_HDRV_SDC1_DATA, GPIO_CFG_10MA} |
| 105 | }; |
| 106 | |
| 107 | static struct msm_mmc_pad_drv sdc1_pad_drv_off_cfg[] = { |
| 108 | {TLMM_HDRV_SDC1_CLK, GPIO_CFG_2MA}, |
| 109 | {TLMM_HDRV_SDC1_CMD, GPIO_CFG_2MA}, |
| 110 | {TLMM_HDRV_SDC1_DATA, GPIO_CFG_2MA} |
| 111 | }; |
| 112 | |
| 113 | static struct msm_mmc_pad_pull sdc1_pad_pull_on_cfg[] = { |
| 114 | {TLMM_PULL_SDC1_CLK, GPIO_CFG_NO_PULL}, |
| 115 | {TLMM_PULL_SDC1_CMD, GPIO_CFG_PULL_UP}, |
| 116 | {TLMM_PULL_SDC1_DATA, GPIO_CFG_PULL_UP} |
| 117 | }; |
| 118 | |
| 119 | static struct msm_mmc_pad_pull sdc1_pad_pull_off_cfg[] = { |
| 120 | {TLMM_PULL_SDC1_CLK, GPIO_CFG_NO_PULL}, |
Oluwafemi Adeyemi | 4e196b6 | 2012-02-15 14:29:03 -0800 | [diff] [blame] | 121 | {TLMM_PULL_SDC1_CMD, GPIO_CFG_PULL_UP}, |
| 122 | {TLMM_PULL_SDC1_DATA, GPIO_CFG_PULL_UP} |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 123 | }; |
| 124 | |
| 125 | /* SDC3 pad data */ |
| 126 | static struct msm_mmc_pad_drv sdc3_pad_drv_on_cfg[] = { |
| 127 | {TLMM_HDRV_SDC3_CLK, GPIO_CFG_8MA}, |
| 128 | {TLMM_HDRV_SDC3_CMD, GPIO_CFG_8MA}, |
| 129 | {TLMM_HDRV_SDC3_DATA, GPIO_CFG_8MA} |
| 130 | }; |
| 131 | |
| 132 | static struct msm_mmc_pad_drv sdc3_pad_drv_off_cfg[] = { |
| 133 | {TLMM_HDRV_SDC3_CLK, GPIO_CFG_2MA}, |
| 134 | {TLMM_HDRV_SDC3_CMD, GPIO_CFG_2MA}, |
| 135 | {TLMM_HDRV_SDC3_DATA, GPIO_CFG_2MA} |
| 136 | }; |
| 137 | |
| 138 | static struct msm_mmc_pad_pull sdc3_pad_pull_on_cfg[] = { |
| 139 | {TLMM_PULL_SDC3_CLK, GPIO_CFG_NO_PULL}, |
| 140 | {TLMM_PULL_SDC3_CMD, GPIO_CFG_PULL_UP}, |
| 141 | {TLMM_PULL_SDC3_DATA, GPIO_CFG_PULL_UP} |
| 142 | }; |
| 143 | |
| 144 | static struct msm_mmc_pad_pull sdc3_pad_pull_off_cfg[] = { |
| 145 | {TLMM_PULL_SDC3_CLK, GPIO_CFG_NO_PULL}, |
Oluwafemi Adeyemi | 4e196b6 | 2012-02-15 14:29:03 -0800 | [diff] [blame] | 146 | {TLMM_PULL_SDC3_CMD, GPIO_CFG_PULL_UP}, |
| 147 | {TLMM_PULL_SDC3_DATA, GPIO_CFG_PULL_UP} |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 148 | }; |
| 149 | |
| 150 | static struct msm_mmc_pad_pull_data mmc_pad_pull_data[MAX_SDCC_CONTROLLER] = { |
| 151 | [SDCC1] = { |
| 152 | .on = sdc1_pad_pull_on_cfg, |
| 153 | .off = sdc1_pad_pull_off_cfg, |
| 154 | .size = ARRAY_SIZE(sdc1_pad_pull_on_cfg) |
| 155 | }, |
| 156 | [SDCC3] = { |
| 157 | .on = sdc3_pad_pull_on_cfg, |
| 158 | .off = sdc3_pad_pull_off_cfg, |
| 159 | .size = ARRAY_SIZE(sdc3_pad_pull_on_cfg) |
| 160 | }, |
| 161 | }; |
| 162 | |
| 163 | static struct msm_mmc_pad_drv_data mmc_pad_drv_data[MAX_SDCC_CONTROLLER] = { |
| 164 | [SDCC1] = { |
| 165 | .on = sdc1_pad_drv_on_cfg, |
| 166 | .off = sdc1_pad_drv_off_cfg, |
| 167 | .size = ARRAY_SIZE(sdc1_pad_drv_on_cfg) |
| 168 | }, |
| 169 | [SDCC3] = { |
| 170 | .on = sdc3_pad_drv_on_cfg, |
| 171 | .off = sdc3_pad_drv_off_cfg, |
| 172 | .size = ARRAY_SIZE(sdc3_pad_drv_on_cfg) |
| 173 | }, |
| 174 | }; |
| 175 | |
| 176 | static struct msm_mmc_pad_data mmc_pad_data[MAX_SDCC_CONTROLLER] = { |
| 177 | [SDCC1] = { |
| 178 | .pull = &mmc_pad_pull_data[SDCC1], |
| 179 | .drv = &mmc_pad_drv_data[SDCC1] |
| 180 | }, |
| 181 | [SDCC3] = { |
| 182 | .pull = &mmc_pad_pull_data[SDCC3], |
| 183 | .drv = &mmc_pad_drv_data[SDCC3] |
| 184 | }, |
| 185 | }; |
| 186 | |
Oluwafemi Adeyemi | a46d032 | 2012-05-16 18:27:44 -0700 | [diff] [blame] | 187 | static struct msm_mmc_gpio sdc2_gpio[] = { |
| 188 | {59, "sdc2_clk"}, |
| 189 | {57, "sdc2_cmd"}, |
| 190 | {62, "sdc2_dat_0"}, |
| 191 | {61, "sdc2_dat_1"}, |
| 192 | {60, "sdc2_dat_2"}, |
| 193 | {58, "sdc2_dat_3"}, |
| 194 | }; |
| 195 | |
| 196 | static struct msm_mmc_gpio sdc4_gpio[] = { |
| 197 | {68, "sdc4_clk"}, |
| 198 | {67, "sdc4_cmd"}, |
| 199 | {66, "sdc4_dat_0"}, |
| 200 | {65, "sdc4_dat_1"}, |
| 201 | {64, "sdc4_dat_2"}, |
| 202 | {63, "sdc4_dat_3"}, |
| 203 | }; |
| 204 | |
| 205 | static struct msm_mmc_gpio_data mmc_gpio_data[MAX_SDCC_CONTROLLER] = { |
| 206 | [SDCC2] = { |
| 207 | .gpio = sdc2_gpio, |
| 208 | .size = ARRAY_SIZE(sdc2_gpio), |
| 209 | }, |
| 210 | [SDCC4] = { |
| 211 | .gpio = sdc4_gpio, |
| 212 | .size = ARRAY_SIZE(sdc4_gpio), |
| 213 | } |
| 214 | }; |
| 215 | |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 216 | static struct msm_mmc_pin_data mmc_slot_pin_data[MAX_SDCC_CONTROLLER] = { |
| 217 | [SDCC1] = { |
| 218 | .pad_data = &mmc_pad_data[SDCC1], |
| 219 | }, |
Oluwafemi Adeyemi | a46d032 | 2012-05-16 18:27:44 -0700 | [diff] [blame] | 220 | [SDCC2] = { |
| 221 | .is_gpio = 1, |
| 222 | .gpio_data = &mmc_gpio_data[SDCC2], |
| 223 | }, |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 224 | [SDCC3] = { |
| 225 | .pad_data = &mmc_pad_data[SDCC3], |
| 226 | }, |
Oluwafemi Adeyemi | a46d032 | 2012-05-16 18:27:44 -0700 | [diff] [blame] | 227 | [SDCC4] = { |
| 228 | .is_gpio = 1, |
| 229 | .gpio_data = &mmc_gpio_data[SDCC4], |
| 230 | }, |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 231 | }; |
| 232 | |
Subhash Jadavani | 55e188e | 2012-04-13 11:31:08 +0530 | [diff] [blame] | 233 | #define MSM_MPM_PIN_SDC1_DAT1 17 |
| 234 | #define MSM_MPM_PIN_SDC3_DAT1 21 |
| 235 | |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 236 | #ifdef CONFIG_MMC_MSM_SDC1_SUPPORT |
| 237 | static unsigned int sdc1_sup_clk_rates[] = { |
| 238 | 400000, 24000000, 48000000, 96000000 |
| 239 | }; |
| 240 | |
| 241 | static struct mmc_platform_data sdc1_data = { |
| 242 | .ocr_mask = MMC_VDD_27_28 | MMC_VDD_28_29, |
| 243 | #ifdef CONFIG_MMC_MSM_SDC1_8_BIT_SUPPORT |
| 244 | .mmc_bus_width = MMC_CAP_8_BIT_DATA, |
| 245 | #else |
| 246 | .mmc_bus_width = MMC_CAP_4_BIT_DATA, |
| 247 | #endif |
| 248 | .sup_clk_table = sdc1_sup_clk_rates, |
| 249 | .sup_clk_cnt = ARRAY_SIZE(sdc1_sup_clk_rates), |
Oluwafemi Adeyemi | 89ff2a1 | 2012-03-08 16:44:21 -0800 | [diff] [blame] | 250 | .nonremovable = 1, |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 251 | .pin_data = &mmc_slot_pin_data[SDCC1], |
| 252 | .vreg_data = &mmc_slot_vreg_data[SDCC1], |
Oluwafemi Adeyemi | 1e77096 | 2012-03-23 13:08:11 -0700 | [diff] [blame] | 253 | .uhs_caps = MMC_CAP_1_8V_DDR | MMC_CAP_UHS_DDR50, |
Subhash Jadavani | cb6f9ce | 2012-06-26 11:57:10 +0530 | [diff] [blame] | 254 | .uhs_caps2 = MMC_CAP2_HS200_1_8V_SDR, |
Subhash Jadavani | 55e188e | 2012-04-13 11:31:08 +0530 | [diff] [blame] | 255 | .mpm_sdiowakeup_int = MSM_MPM_PIN_SDC1_DAT1, |
Subhash Jadavani | bcd435f | 2012-04-24 18:26:49 +0530 | [diff] [blame] | 256 | .msm_bus_voting_data = &sps_to_ddr_bus_voting_data, |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 257 | }; |
| 258 | static struct mmc_platform_data *apq8064_sdc1_pdata = &sdc1_data; |
| 259 | #else |
| 260 | static struct mmc_platform_data *apq8064_sdc1_pdata; |
| 261 | #endif |
| 262 | |
Oluwafemi Adeyemi | a46d032 | 2012-05-16 18:27:44 -0700 | [diff] [blame] | 263 | #ifdef CONFIG_MMC_MSM_SDC2_SUPPORT |
| 264 | static unsigned int sdc2_sup_clk_rates[] = { |
| 265 | 400000, 24000000, 48000000 |
| 266 | }; |
| 267 | |
| 268 | static struct mmc_platform_data sdc2_data = { |
| 269 | .ocr_mask = MMC_VDD_27_28 | MMC_VDD_28_29, |
| 270 | .mmc_bus_width = MMC_CAP_4_BIT_DATA, |
| 271 | .sup_clk_table = sdc2_sup_clk_rates, |
| 272 | .sup_clk_cnt = ARRAY_SIZE(sdc2_sup_clk_rates), |
Oluwafemi Adeyemi | a46d032 | 2012-05-16 18:27:44 -0700 | [diff] [blame] | 273 | .pin_data = &mmc_slot_pin_data[SDCC2], |
| 274 | .sdiowakeup_irq = MSM_GPIO_TO_INT(61), |
| 275 | .msm_bus_voting_data = &sps_to_ddr_bus_voting_data, |
| 276 | }; |
| 277 | static struct mmc_platform_data *apq8064_sdc2_pdata = &sdc2_data; |
| 278 | #else |
| 279 | static struct mmc_platform_data *apq8064_sdc2_pdata; |
| 280 | #endif |
| 281 | |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 282 | #ifdef CONFIG_MMC_MSM_SDC3_SUPPORT |
| 283 | static unsigned int sdc3_sup_clk_rates[] = { |
Oluwafemi Adeyemi | 086ef86 | 2012-02-07 20:13:50 -0800 | [diff] [blame] | 284 | 400000, 24000000, 48000000, 96000000, 192000000 |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 285 | }; |
| 286 | |
| 287 | static struct mmc_platform_data sdc3_data = { |
| 288 | .ocr_mask = MMC_VDD_27_28 | MMC_VDD_28_29, |
| 289 | .mmc_bus_width = MMC_CAP_4_BIT_DATA, |
| 290 | .sup_clk_table = sdc3_sup_clk_rates, |
| 291 | .sup_clk_cnt = ARRAY_SIZE(sdc3_sup_clk_rates), |
| 292 | .pin_data = &mmc_slot_pin_data[SDCC3], |
| 293 | .vreg_data = &mmc_slot_vreg_data[SDCC3], |
Oluwafemi Adeyemi | 787ac48 | 2012-02-16 09:50:03 -0800 | [diff] [blame] | 294 | .wpswitch_gpio = PM8921_GPIO_PM_TO_SYS(17), |
Sujit Reddy Thumma | 8f912ea | 2012-06-22 16:18:43 +0530 | [diff] [blame] | 295 | .is_wpswitch_active_low = true, |
Oluwafemi Adeyemi | 8399967 | 2012-02-07 20:01:26 -0800 | [diff] [blame] | 296 | .status_gpio = 26, |
| 297 | .status_irq = MSM_GPIO_TO_INT(26), |
| 298 | .irq_flags = IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, |
| 299 | .is_status_gpio_active_low = 1, |
Oluwafemi Adeyemi | 086ef86 | 2012-02-07 20:13:50 -0800 | [diff] [blame] | 300 | .xpc_cap = 1, |
| 301 | .uhs_caps = (MMC_CAP_UHS_SDR12 | MMC_CAP_UHS_SDR25 | |
| 302 | MMC_CAP_UHS_SDR50 | MMC_CAP_UHS_DDR50 | |
| 303 | MMC_CAP_UHS_SDR104 | MMC_CAP_MAX_CURRENT_800), |
Subhash Jadavani | 55e188e | 2012-04-13 11:31:08 +0530 | [diff] [blame] | 304 | .mpm_sdiowakeup_int = MSM_MPM_PIN_SDC3_DAT1, |
Subhash Jadavani | bcd435f | 2012-04-24 18:26:49 +0530 | [diff] [blame] | 305 | .msm_bus_voting_data = &sps_to_ddr_bus_voting_data, |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 306 | }; |
| 307 | static struct mmc_platform_data *apq8064_sdc3_pdata = &sdc3_data; |
| 308 | #else |
| 309 | static struct mmc_platform_data *apq8064_sdc3_pdata; |
| 310 | #endif |
| 311 | |
Oluwafemi Adeyemi | a46d032 | 2012-05-16 18:27:44 -0700 | [diff] [blame] | 312 | |
| 313 | #ifdef CONFIG_MMC_MSM_SDC4_SUPPORT |
| 314 | static unsigned int sdc4_sup_clk_rates[] = { |
| 315 | 400000, 24000000, 48000000 |
| 316 | }; |
| 317 | |
| 318 | static struct mmc_platform_data sdc4_data = { |
| 319 | .ocr_mask = MMC_VDD_27_28 | MMC_VDD_28_29, |
| 320 | .mmc_bus_width = MMC_CAP_4_BIT_DATA, |
| 321 | .sup_clk_table = sdc4_sup_clk_rates, |
| 322 | .sup_clk_cnt = ARRAY_SIZE(sdc4_sup_clk_rates), |
Oluwafemi Adeyemi | a46d032 | 2012-05-16 18:27:44 -0700 | [diff] [blame] | 323 | .pin_data = &mmc_slot_pin_data[SDCC4], |
| 324 | .sdiowakeup_irq = MSM_GPIO_TO_INT(65), |
| 325 | .msm_bus_voting_data = &sps_to_ddr_bus_voting_data, |
| 326 | }; |
| 327 | static struct mmc_platform_data *apq8064_sdc4_pdata = &sdc4_data; |
| 328 | #else |
| 329 | static struct mmc_platform_data *apq8064_sdc4_pdata; |
| 330 | #endif |
| 331 | |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 332 | void __init apq8064_init_mmc(void) |
| 333 | { |
Oluwafemi Adeyemi | 784b439 | 2012-04-10 13:49:38 -0700 | [diff] [blame] | 334 | if (apq8064_sdc1_pdata) |
Oluwafemi Adeyemi | f5a3142 | 2012-03-08 16:58:45 -0800 | [diff] [blame] | 335 | apq8064_add_sdcc(1, apq8064_sdc1_pdata); |
Oluwafemi Adeyemi | 784b439 | 2012-04-10 13:49:38 -0700 | [diff] [blame] | 336 | |
Oluwafemi Adeyemi | a46d032 | 2012-05-16 18:27:44 -0700 | [diff] [blame] | 337 | if (apq8064_sdc2_pdata) |
| 338 | apq8064_add_sdcc(2, apq8064_sdc2_pdata); |
| 339 | |
Oluwafemi Adeyemi | f5a3142 | 2012-03-08 16:58:45 -0800 | [diff] [blame] | 340 | if (apq8064_sdc3_pdata) { |
Pratibhasagar V | 6bdb54a | 2012-09-27 15:42:46 +0530 | [diff] [blame] | 341 | if (machine_is_mpq8064_hrd() || machine_is_mpq8064_dtv()) { |
| 342 | apq8064_sdc3_pdata->uhs_caps &= ~(MMC_CAP_UHS_SDR12 | |
| 343 | MMC_CAP_UHS_SDR25 | MMC_CAP_UHS_DDR50 | |
| 344 | MMC_CAP_UHS_SDR50 | MMC_CAP_UHS_SDR104); |
| 345 | } |
Oluwafemi Adeyemi | 48fc326 | 2012-03-19 13:26:52 -0700 | [diff] [blame] | 346 | if (!machine_is_apq8064_cdp()) { |
| 347 | apq8064_sdc3_pdata->wpswitch_gpio = 0; |
Sujit Reddy Thumma | 8f912ea | 2012-06-22 16:18:43 +0530 | [diff] [blame] | 348 | apq8064_sdc3_pdata->is_wpswitch_active_low = false; |
Oluwafemi Adeyemi | 48fc326 | 2012-03-19 13:26:52 -0700 | [diff] [blame] | 349 | } |
Oluwafemi Adeyemi | 0d469ce | 2012-05-10 18:04:25 -0700 | [diff] [blame] | 350 | if (machine_is_mpq8064_cdp() || machine_is_mpq8064_hrd() || |
| 351 | machine_is_mpq8064_dtv()) { |
Sujit Reddy Thumma | 1710839 | 2012-06-06 14:41:47 +0530 | [diff] [blame] | 352 | int rc; |
| 353 | struct pm_gpio sd_card_det_init_cfg = { |
| 354 | .direction = PM_GPIO_DIR_IN, |
| 355 | .output_buffer = PM_GPIO_OUT_BUF_CMOS, |
| 356 | .pull = PM_GPIO_PULL_UP_30, |
| 357 | .vin_sel = PM_GPIO_VIN_S4, |
| 358 | .out_strength = PM_GPIO_STRENGTH_NO, |
| 359 | .function = PM_GPIO_FUNC_NORMAL, |
| 360 | }; |
| 361 | |
Oluwafemi Adeyemi | 0d469ce | 2012-05-10 18:04:25 -0700 | [diff] [blame] | 362 | apq8064_sdc3_pdata->status_gpio = |
| 363 | PM8921_GPIO_PM_TO_SYS(31); |
| 364 | apq8064_sdc3_pdata->status_irq = |
| 365 | PM8921_GPIO_IRQ(PM8921_IRQ_BASE, 31); |
Sujit Reddy Thumma | 1710839 | 2012-06-06 14:41:47 +0530 | [diff] [blame] | 366 | rc = pm8xxx_gpio_config(apq8064_sdc3_pdata->status_gpio, |
| 367 | &sd_card_det_init_cfg); |
| 368 | if (rc) { |
| 369 | pr_info("%s: SD_CARD_DET GPIO%d config " |
| 370 | "failed(%d)\n", __func__, |
| 371 | apq8064_sdc3_pdata->status_gpio, rc); |
| 372 | apq8064_sdc3_pdata->status_gpio = 0; |
| 373 | apq8064_sdc3_pdata->status_irq = 0; |
| 374 | } |
Oluwafemi Adeyemi | 0d469ce | 2012-05-10 18:04:25 -0700 | [diff] [blame] | 375 | } |
Subhash Jadavani | 990c8ed | 2012-07-04 12:30:48 +0530 | [diff] [blame] | 376 | if (machine_is_apq8064_cdp()) { |
| 377 | int i; |
| 378 | |
| 379 | for (i = 0; |
| 380 | i < apq8064_sdc3_pdata->pin_data->pad_data->\ |
| 381 | drv->size; |
| 382 | i++) |
| 383 | apq8064_sdc3_pdata->pin_data->pad_data->\ |
| 384 | drv->on[i].val = GPIO_CFG_10MA; |
| 385 | } |
Pratibhasagar V | 30eb4c3 | 2012-10-08 15:51:49 +0530 | [diff] [blame] | 386 | if (machine_is_mpq8064_hrd() || machine_is_mpq8064_dtv()) { |
| 387 | apq8064_sdc3_pdata->pin_data->pad_data->\ |
| 388 | drv->on[0].val = GPIO_CFG_16MA; |
| 389 | apq8064_sdc3_pdata->pin_data->pad_data->\ |
| 390 | drv->on[1].val = GPIO_CFG_10MA; |
| 391 | apq8064_sdc3_pdata->pin_data->pad_data->\ |
| 392 | drv->on[2].val = GPIO_CFG_10MA; |
| 393 | } |
Oluwafemi Adeyemi | f5a3142 | 2012-03-08 16:58:45 -0800 | [diff] [blame] | 394 | apq8064_add_sdcc(3, apq8064_sdc3_pdata); |
| 395 | } |
Oluwafemi Adeyemi | a46d032 | 2012-05-16 18:27:44 -0700 | [diff] [blame] | 396 | |
| 397 | if (apq8064_sdc4_pdata) |
| 398 | apq8064_add_sdcc(4, apq8064_sdc4_pdata); |
Stepan Moskovchenko | e438b63 | 2011-12-06 13:44:03 -0800 | [diff] [blame] | 399 | } |