]> www.pilppa.org Git - linux-2.6-omap-h63xx.git/blob - arch/arm/mach-omap2/mmc-twl4030.c
HSMMC: Misc clean-up for hsmmc init
[linux-2.6-omap-h63xx.git] / arch / arm / mach-omap2 / mmc-twl4030.c
1 /*
2  * linux/arch/arm/mach-omap2/mmc-twl4030.c
3  *
4  * Copyright (C) 2007-2008 Texas Instruments
5  * Copyright (C) 2008 Nokia Corporation
6  * Author: Texas Instruments
7  *
8  * This program is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License version 2 as
10  * published by the Free Software Foundation.
11  */
12 #include <linux/err.h>
13 #include <linux/io.h>
14 #include <linux/module.h>
15 #include <linux/platform_device.h>
16 #include <linux/interrupt.h>
17 #include <linux/delay.h>
18 #include <linux/gpio.h>
19 #include <linux/i2c/twl4030.h>
20
21 #include <mach/hardware.h>
22 #include <mach/control.h>
23 #include <mach/mmc.h>
24 #include <mach/board.h>
25
26 #if defined(CONFIG_MMC_OMAP_HS) || defined(CONFIG_MMC_OMAP_HS_MODULE)
27
28 #define TWL_GPIO_IMR1A          0x1C
29 #define TWL_GPIO_ISR1A          0x19
30 #define LDO_CLR                 0x00
31 #define VSEL_S2_CLR             0x40
32 #define GPIO_0_BIT_POS          (1 << 0)
33
34 #define VMMC1_DEV_GRP           0x27
35 #define VMMC1_CLR               0x00
36 #define VMMC1_315V              0x03
37 #define VMMC1_300V              0x02
38 #define VMMC1_285V              0x01
39 #define VMMC1_185V              0x00
40 #define VMMC1_DEDICATED         0x2A
41
42 #define VMMC2_DEV_GRP           0x2B
43 #define VMMC2_CLR               0x40
44 #define VMMC2_315V              0x0c
45 #define VMMC2_300V              0x0b
46 #define VMMC2_285V              0x0a
47 #define VMMC2_260V              0x08
48 #define VMMC2_185V              0x06
49 #define VMMC2_DEDICATED         0x2E
50
51 #define VMMC_DEV_GRP_P1         0x20
52
53 static u16 control_pbias_offset;
54
55 static struct hsmmc_controller {
56         u16             control_devconf_offset;
57         u32             devconf_loopback_clock;
58         int             card_detect_gpio;
59         u8              twl_vmmc_dev_grp;
60         u8              twl_mmc_dedicated;
61 } hsmmc[] = {
62         {
63                 .control_devconf_offset         = OMAP2_CONTROL_DEVCONF0,
64                 .devconf_loopback_clock         = OMAP2_MMCSDIO1ADPCLKISEL,
65                 .card_detect_gpio               = OMAP_MAX_GPIO_LINES,
66                 .twl_vmmc_dev_grp               = VMMC1_DEV_GRP,
67                 .twl_mmc_dedicated              = VMMC1_DEDICATED,
68         },
69         {
70                 /* control_devconf_offset set dynamically */
71                 .devconf_loopback_clock         = OMAP2_MMCSDIO2ADPCLKISEL,
72                 .twl_vmmc_dev_grp               = VMMC2_DEV_GRP,
73                 .twl_mmc_dedicated              = VMMC2_DEDICATED,
74         },
75  };
76
77 static int hsmmc1_card_detect(int irq)
78 {
79         return gpio_get_value_cansleep(hsmmc[0].card_detect_gpio);
80 }
81
82 /*
83  * MMC Slot Initialization.
84  */
85 static int hsmmc1_late_init(struct device *dev)
86 {
87         int ret = 0;
88
89         /*
90          * Configure TWL4030 GPIO parameters for MMC hotplug irq
91          */
92         ret = gpio_request(hsmmc[0].card_detect_gpio, "mmc0_cd");
93         if (ret)
94                 goto err;
95
96         ret = twl4030_set_gpio_debounce(0, true);
97         if (ret)
98                 goto err;
99
100         return ret;
101
102 err:
103         dev_err(dev, "Failed to configure TWL4030 GPIO IRQ\n");
104
105         return ret;
106 }
107
108 static void hsmmc1_cleanup(struct device *dev)
109 {
110         gpio_free(hsmmc[0].card_detect_gpio);
111 }
112
113 #ifdef CONFIG_PM
114
115 /*
116  * Mask and unmask MMC Card Detect Interrupt
117  * mask : 1
118  * unmask : 0
119  */
120 static int mask_cd_interrupt(int mask)
121 {
122         u8 reg = 0, ret = 0;
123
124         ret = twl4030_i2c_read_u8(TWL4030_MODULE_GPIO, &reg, TWL_GPIO_IMR1A);
125         if (ret)
126                 goto err;
127
128         reg = (mask == 1) ? (reg | GPIO_0_BIT_POS) : (reg & ~GPIO_0_BIT_POS);
129
130         ret = twl4030_i2c_write_u8(TWL4030_MODULE_GPIO, reg, TWL_GPIO_IMR1A);
131         if (ret)
132                 goto err;
133
134         ret = twl4030_i2c_read_u8(TWL4030_MODULE_GPIO, &reg, TWL_GPIO_ISR1A);
135         if (ret)
136                 goto err;
137
138         reg = (mask == 1) ? (reg | GPIO_0_BIT_POS) : (reg & ~GPIO_0_BIT_POS);
139
140         ret = twl4030_i2c_write_u8(TWL4030_MODULE_GPIO, reg, TWL_GPIO_ISR1A);
141         if (ret)
142                 goto err;
143
144 err:
145         return ret;
146 }
147
148 static int hsmmc1_suspend(struct device *dev, int slot)
149 {
150         int ret = 0;
151
152         disable_irq(TWL4030_GPIO_IRQ_NO(0));
153         ret = mask_cd_interrupt(1);
154
155         return ret;
156 }
157
158 static int hsmmc1_resume(struct device *dev, int slot)
159 {
160         int ret = 0;
161
162         enable_irq(TWL4030_GPIO_IRQ_NO(0));
163         ret = mask_cd_interrupt(0);
164
165         return ret;
166 }
167
168 #endif
169
170 /*
171  * Sets the MMC voltage in twl4030
172  */
173 static int hsmmc_twl_set_voltage(struct hsmmc_controller *c, int vdd)
174 {
175         int ret;
176         u8 vmmc, dev_grp_val;
177
178         switch (1 << vdd) {
179         case MMC_VDD_35_36:
180         case MMC_VDD_34_35:
181         case MMC_VDD_33_34:
182         case MMC_VDD_32_33:
183         case MMC_VDD_31_32:
184         case MMC_VDD_30_31:
185                 if (c->twl_vmmc_dev_grp == VMMC1_DEV_GRP)
186                         vmmc = VMMC1_315V;
187                 else
188                         vmmc = VMMC2_315V;
189                 break;
190         case MMC_VDD_29_30:
191                 if (c->twl_vmmc_dev_grp == VMMC1_DEV_GRP)
192                         vmmc = VMMC1_315V;
193                 else
194                         vmmc = VMMC2_300V;
195                 break;
196         case MMC_VDD_27_28:
197         case MMC_VDD_26_27:
198                 if (c->twl_vmmc_dev_grp == VMMC1_DEV_GRP)
199                         vmmc = VMMC1_285V;
200                 else
201                         vmmc = VMMC2_285V;
202                 break;
203         case MMC_VDD_25_26:
204         case MMC_VDD_24_25:
205         case MMC_VDD_23_24:
206         case MMC_VDD_22_23:
207         case MMC_VDD_21_22:
208         case MMC_VDD_20_21:
209                 if (c->twl_vmmc_dev_grp == VMMC1_DEV_GRP)
210                         vmmc = VMMC1_285V;
211                 else
212                         vmmc = VMMC2_260V;
213                 break;
214         case MMC_VDD_165_195:
215                 if (c->twl_vmmc_dev_grp == VMMC1_DEV_GRP)
216                         vmmc = VMMC1_185V;
217                 else
218                         vmmc = VMMC2_185V;
219                 break;
220         default:
221                 vmmc = 0;
222                 break;
223         }
224
225         if (vmmc)
226                 dev_grp_val = VMMC_DEV_GRP_P1;  /* Power up */
227         else
228                 dev_grp_val = LDO_CLR;          /* Power down */
229
230         ret = twl4030_i2c_write_u8(TWL4030_MODULE_PM_RECEIVER,
231                                         dev_grp_val, c->twl_vmmc_dev_grp);
232         if (ret)
233                 return ret;
234
235         ret = twl4030_i2c_write_u8(TWL4030_MODULE_PM_RECEIVER,
236                                         vmmc, c->twl_mmc_dedicated);
237
238         return ret;
239 }
240
241 static int hsmmc1_set_power(struct device *dev, int slot, int power_on,
242                                 int vdd)
243 {
244         u32 reg;
245         int ret = 0;
246         struct hsmmc_controller *c = &hsmmc[0];
247
248         if (power_on) {
249                 if (cpu_is_omap2430()) {
250                         reg = omap_ctrl_readl(OMAP243X_CONTROL_DEVCONF1);
251                         if ((1 << vdd) >= MMC_VDD_30_31)
252                                 reg |= OMAP243X_MMC1_ACTIVE_OVERWRITE;
253                         else
254                                 reg &= ~OMAP243X_MMC1_ACTIVE_OVERWRITE;
255                         omap_ctrl_writel(reg, OMAP243X_CONTROL_DEVCONF1);
256                 }
257
258                 /* REVISIT: Loop back clock not needed for 2430? */
259                 if (!cpu_is_omap2430()) {
260                         reg = omap_ctrl_readl(c->control_devconf_offset);
261                         reg |= OMAP2_MMCSDIO1ADPCLKISEL;
262                         omap_ctrl_writel(reg, c->control_devconf_offset);
263                 }
264
265                 reg = omap_ctrl_readl(control_pbias_offset);
266                 reg |= OMAP2_PBIASSPEEDCTRL0;
267                 reg &= ~OMAP2_PBIASLITEPWRDNZ0;
268                 omap_ctrl_writel(reg, control_pbias_offset);
269
270                 ret = hsmmc_twl_set_voltage(c, vdd);
271
272                 /* 100ms delay required for PBIAS configuration */
273                 msleep(100);
274                 reg = omap_ctrl_readl(control_pbias_offset);
275                 reg |= (OMAP2_PBIASLITEPWRDNZ0 | OMAP2_PBIASSPEEDCTRL0);
276                 if ((1 << vdd) <= MMC_VDD_165_195)
277                         reg &= ~OMAP2_PBIASLITEVMODE0;
278                 else
279                         reg |= OMAP2_PBIASLITEVMODE0;
280                 omap_ctrl_writel(reg, control_pbias_offset);
281         } else {
282                 reg = omap_ctrl_readl(control_pbias_offset);
283                 reg &= ~OMAP2_PBIASLITEPWRDNZ0;
284                 omap_ctrl_writel(reg, control_pbias_offset);
285
286                 ret = hsmmc_twl_set_voltage(c, 0);
287
288                 /* 100ms delay required for PBIAS configuration */
289                 msleep(100);
290                 reg = omap_ctrl_readl(control_pbias_offset);
291                 reg |= (OMAP2_PBIASSPEEDCTRL0 | OMAP2_PBIASLITEPWRDNZ0 |
292                         OMAP2_PBIASLITEVMODE0);
293                 omap_ctrl_writel(reg, control_pbias_offset);
294         }
295
296         return ret;
297 }
298
299 static int hsmmc2_set_power(struct device *dev, int slot, int power_on, int vdd)
300 {
301         int ret;
302
303         struct hsmmc_controller *c = &hsmmc[1];
304
305         if (power_on) {
306                 u32 reg;
307
308                 reg = omap_ctrl_readl(c->control_devconf_offset);
309                 reg |= OMAP2_MMCSDIO2ADPCLKISEL;
310                 omap_ctrl_writel(reg, c->control_devconf_offset);
311                 ret = hsmmc_twl_set_voltage(c, vdd);
312         } else {
313                 ret = hsmmc_twl_set_voltage(c, 0);
314         }
315
316         return ret;
317 }
318
319 static struct omap_mmc_platform_data mmc1_data = {
320         .nr_slots                       = 1,
321         .init                           = hsmmc1_late_init,
322         .cleanup                        = hsmmc1_cleanup,
323 #ifdef CONFIG_PM
324         .suspend                        = hsmmc1_suspend,
325         .resume                         = hsmmc1_resume,
326 #endif
327         .dma_mask                       = 0xffffffff,
328         .slots[0] = {
329                 .wire4                  = 1,
330                 .set_power              = hsmmc1_set_power,
331                 .ocr_mask               = MMC_VDD_32_33 | MMC_VDD_33_34 |
332                                                 MMC_VDD_165_195,
333                 .name                   = "first slot",
334
335                 .card_detect_irq        = TWL4030_GPIO_IRQ_NO(0),
336                 .card_detect            = hsmmc1_card_detect,
337         },
338 };
339
340 static struct omap_mmc_platform_data mmc2_data = {
341         .nr_slots                       = 1,
342         .slots[0] = {
343                 .set_power              = hsmmc2_set_power,
344                 .ocr_mask               = MMC_VDD_27_28 | MMC_VDD_28_29 |
345                                           MMC_VDD_29_30 | MMC_VDD_30_31 |
346                                           MMC_VDD_31_32 | MMC_VDD_32_33,
347                 .name                   = "second slot",
348         },
349 };
350
351 static struct omap_mmc_platform_data *hsmmc_data[OMAP34XX_NR_MMC];
352
353 void __init hsmmc_init(int controller_mask)
354 {
355         if (cpu_is_omap2430()) {
356                 control_pbias_offset = OMAP243X_CONTROL_PBIAS_LITE;
357                 hsmmc[1].control_devconf_offset = OMAP243X_CONTROL_DEVCONF1;
358         } else {
359                 control_pbias_offset = OMAP343X_CONTROL_PBIAS_LITE;
360                 hsmmc[1].control_devconf_offset = OMAP343X_CONTROL_DEVCONF1;
361         }
362
363         if (controller_mask & HSMMC1)
364                 hsmmc_data[0] = &mmc1_data;
365         if (controller_mask & HSMMC2)
366                 hsmmc_data[1] = &mmc2_data;
367         if (controller_mask & HSMMC3)
368                 pr_err("HSMMC: Unknown configuration for controller 3\n");
369         omap2_init_mmc(hsmmc_data, OMAP34XX_NR_MMC);
370 }
371
372 #endif