blob: e8f64432ee3198c09c1dd71cafc30c15811dce77 [file] [log] [blame]
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301/* Copyright (c) 2011, Code Aurora Forum. All rights reserved.
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#include <linux/kernel.h>
14#include <linux/init.h>
15#include <linux/gpio_event.h>
Pankaj Kumar6f841742011-10-10 15:52:14 +053016#include <linux/usb/android.h>
Taniya Dasc98bfbc2011-08-23 09:58:55 +053017#include <linux/platform_device.h>
18#include <linux/io.h>
19#include <linux/gpio.h>
20#include <linux/mtd/nand.h>
21#include <linux/mtd/partitions.h>
22#include <linux/i2c.h>
23#include <linux/android_pmem.h>
24#include <linux/bootmem.h>
25#include <linux/mfd/marimba.h>
26#include <linux/power_supply.h>
Taniya Dasda408822011-09-06 12:54:06 +053027#include <linux/input/rmi_platformdata.h>
28#include <linux/input/rmi_i2c.h>
Pankaj Kumar3cec0582011-11-18 11:13:29 +053029#include <linux/regulator/consumer.h>
Taniya Dasc98bfbc2011-08-23 09:58:55 +053030#include <asm/mach/mmc.h>
31#include <asm/mach-types.h>
32#include <asm/mach/arch.h>
33#include <mach/board.h>
34#include <mach/msm_iomap.h>
35#include <mach/msm_hsusb.h>
36#include <mach/rpc_hsusb.h>
37#include <mach/rpc_pmapp.h>
38#include <mach/usbdiag.h>
Taniya Dasc98bfbc2011-08-23 09:58:55 +053039#include <mach/msm_memtypes.h>
40#include <mach/msm_serial_hs.h>
Taniya Dasc98bfbc2011-08-23 09:58:55 +053041#include <mach/pmic.h>
42#include <mach/socinfo.h>
43#include <mach/vreg.h>
44#include <mach/rpc_pmapp.h>
45#include <mach/msm_battery.h>
46#include <mach/rpc_server_handset.h>
47#include <mach/socinfo.h>
Pankaj Kumar27c02642011-09-22 15:55:55 +053048#include "board-msm7x27a-regulator.h"
Taniya Dasc98bfbc2011-08-23 09:58:55 +053049#include "devices.h"
50#include "devices-msm7x2xa.h"
51#include "pm.h"
52#include "timer.h"
Murali Nalajalaa1827842011-11-13 14:12:39 +053053#include "pm-boot.h"
Pankaj Kumar3cec0582011-11-18 11:13:29 +053054#include "board-msm7x27a-regulator.h"
Chintan Pandyacf467fc2011-12-01 17:11:11 +053055#include "board-msm7627a.h"
Taniya Dasc98bfbc2011-08-23 09:58:55 +053056
57#define PMEM_KERNEL_EBI1_SIZE 0x3A000
58#define MSM_PMEM_AUDIO_SIZE 0x5B000
59#define BAHAMA_SLAVE_ID_FM_ADDR 0x2A
60#define BAHAMA_SLAVE_ID_QMEMBIST_ADDR 0x7B
61#define BAHAMA_SLAVE_ID_FM_REG 0x02
62#define FM_GPIO 83
Rahul Kashyap8b4a7862011-12-13 18:40:54 +053063#define BT_PCM_BCLK_MODE 0x88
64#define BT_PCM_DIN_MODE 0x89
65#define BT_PCM_DOUT_MODE 0x8A
66#define BT_PCM_SYNC_MODE 0x8B
67#define FM_I2S_SD_MODE 0x8E
68#define FM_I2S_WS_MODE 0x8F
69#define FM_I2S_SCK_MODE 0x90
70#define I2C_PIN_CTL 0x15
71#define I2C_NORMAL 0x40
Taniya Dasc98bfbc2011-08-23 09:58:55 +053072
73enum {
74 GPIO_HOST_VBUS_EN = 107,
75 GPIO_BT_SYS_REST_EN = 114,
76 GPIO_WAKE_ON_WIRELESS,
77 GPIO_BACKLIGHT_EN,
Taniya Das7a22cdd2011-09-08 14:57:00 +053078 GPIO_NC,
79 GPIO_CAM_3MP_PWDN, /* CAM_VGA */
Taniya Dasc98bfbc2011-08-23 09:58:55 +053080 GPIO_WLAN_EN,
81 GPIO_CAM_5MP_SHDN_EN,
82 GPIO_CAM_5MP_RESET,
Taniya Das7a22cdd2011-09-08 14:57:00 +053083 GPIO_TP,
84 GPIO_CAM_GP_CAMIF_RESET,
Taniya Dasc98bfbc2011-08-23 09:58:55 +053085};
86
87 /* FM Platform power and shutdown routines */
88#define FPGA_MSM_CNTRL_REG2 0x90008010
89
Chintan Pandya3b2aff72011-11-25 16:26:08 +053090#if defined(CONFIG_BT) && defined(CONFIG_MARIMBA_CORE)
Rahul Kashyap8b4a7862011-12-13 18:40:54 +053091static int switch_pcm_i2s_reg_mode(int mode)
92{
93 unsigned char reg = 0;
94 int rc = -1;
95 unsigned char set = I2C_PIN_CTL; /*SET PIN CTL mode*/
96 unsigned char unset = I2C_NORMAL; /* UNSET PIN CTL MODE*/
97 struct marimba config = { .mod_id = SLAVE_ID_BAHAMA};
98
99 if (mode == 0) {
100 /* as we need to switch path to FM we need to move
101 BT AUX PCM lines to PIN CONTROL mode then move
102 FM to normal mode.*/
103 for (reg = BT_PCM_BCLK_MODE; reg <= BT_PCM_SYNC_MODE; reg++) {
104 rc = marimba_write(&config, reg, &set, 1);
105 if (rc < 0) {
106 pr_err("pcm pinctl failed = %d", rc);
107 goto err_all;
108 }
109 }
110 for (reg = FM_I2S_SD_MODE; reg <= FM_I2S_SCK_MODE; reg++) {
111 rc = marimba_write(&config, reg, &unset, 1);
112 if (rc < 0) {
113 pr_err("i2s normal failed = %d", rc);
114 goto err_all;
115 }
116 }
117 } else {
118 /* as we need to switch path to AUXPCM we need to move
119 FM I2S lines to PIN CONTROL mode then move
120 BT AUX_PCM to normal mode.*/
121 for (reg = FM_I2S_SD_MODE; reg <= FM_I2S_SCK_MODE; reg++) {
122 rc = marimba_write(&config, reg, &set, 1);
123 if (rc < 0) {
124 pr_err("i2s pinctl failed = %d", rc);
125 goto err_all;
126 }
127 }
128 for (reg = BT_PCM_BCLK_MODE; reg <= BT_PCM_SYNC_MODE; reg++) {
129 rc = marimba_write(&config, reg, &unset, 1);
130 if (rc < 0) {
131 pr_err("pcm normal failed = %d", rc);
132 goto err_all;
133 }
134 }
135 }
136
137 return 0;
138
139err_all:
140 return rc;
141}
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530142static void config_pcm_i2s_mode(int mode)
143{
144 void __iomem *cfg_ptr;
145 u8 reg2;
146
147 cfg_ptr = ioremap_nocache(FPGA_MSM_CNTRL_REG2, sizeof(char));
148
149 if (!cfg_ptr)
150 return;
151 if (mode) {
152 /*enable the pcm mode in FPGA*/
153 reg2 = readb_relaxed(cfg_ptr);
154 if (reg2 == 0) {
155 reg2 = 1;
156 writeb_relaxed(reg2, cfg_ptr);
157 }
158 } else {
159 /*enable i2s mode in FPGA*/
160 reg2 = readb_relaxed(cfg_ptr);
161 if (reg2 == 1) {
162 reg2 = 0;
163 writeb_relaxed(reg2, cfg_ptr);
164 }
165 }
166 iounmap(cfg_ptr);
167}
168
169static unsigned fm_i2s_config_power_on[] = {
170 /*FM_I2S_SD*/
171 GPIO_CFG(68, 1, GPIO_CFG_INPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
172 /*FM_I2S_WS*/
173 GPIO_CFG(70, 1, GPIO_CFG_INPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
174 /*FM_I2S_SCK*/
175 GPIO_CFG(71, 1, GPIO_CFG_INPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
176};
177
178static unsigned fm_i2s_config_power_off[] = {
179 /*FM_I2S_SD*/
180 GPIO_CFG(68, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
181 /*FM_I2S_WS*/
182 GPIO_CFG(70, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
183 /*FM_I2S_SCK*/
184 GPIO_CFG(71, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
185};
186
187static unsigned bt_config_power_on[] = {
188 /*RFR*/
189 GPIO_CFG(43, 2, GPIO_CFG_OUTPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
190 /*CTS*/
191 GPIO_CFG(44, 2, GPIO_CFG_INPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
192 /*RX*/
193 GPIO_CFG(45, 2, GPIO_CFG_INPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
194 /*TX*/
195 GPIO_CFG(46, 2, GPIO_CFG_OUTPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
196};
197static unsigned bt_config_pcm_on[] = {
198 /*PCM_DOUT*/
199 GPIO_CFG(68, 1, GPIO_CFG_OUTPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
200 /*PCM_DIN*/
201 GPIO_CFG(69, 1, GPIO_CFG_INPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
202 /*PCM_SYNC*/
203 GPIO_CFG(70, 1, GPIO_CFG_OUTPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
204 /*PCM_CLK*/
205 GPIO_CFG(71, 1, GPIO_CFG_OUTPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
206};
207static unsigned bt_config_power_off[] = {
208 /*RFR*/
209 GPIO_CFG(43, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
210 /*CTS*/
211 GPIO_CFG(44, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
212 /*RX*/
213 GPIO_CFG(45, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
214 /*TX*/
215 GPIO_CFG(46, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
216};
217static unsigned bt_config_pcm_off[] = {
218 /*PCM_DOUT*/
219 GPIO_CFG(68, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
220 /*PCM_DIN*/
221 GPIO_CFG(69, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
222 /*PCM_SYNC*/
223 GPIO_CFG(70, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
224 /*PCM_CLK*/
225 GPIO_CFG(71, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
226};
227
228
229static int config_i2s(int mode)
230{
231 int pin, rc = 0;
232
233 if (mode == FM_I2S_ON) {
234 if (machine_is_msm7627a_qrd1())
235 config_pcm_i2s_mode(0);
236 pr_err("%s mode = FM_I2S_ON", __func__);
Rahul Kashyap8b4a7862011-12-13 18:40:54 +0530237
238 rc = switch_pcm_i2s_reg_mode(0);
239 if (rc) {
240 pr_err("switch mode failed");
241 return rc;
242 }
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530243 for (pin = 0; pin < ARRAY_SIZE(fm_i2s_config_power_on);
244 pin++) {
245 rc = gpio_tlmm_config(
246 fm_i2s_config_power_on[pin],
247 GPIO_CFG_ENABLE
248 );
249 if (rc < 0)
250 return rc;
251 }
252 } else if (mode == FM_I2S_OFF) {
253 pr_err("%s mode = FM_I2S_OFF", __func__);
Rahul Kashyap8b4a7862011-12-13 18:40:54 +0530254 rc = switch_pcm_i2s_reg_mode(1);
255 if (rc) {
256 pr_err("switch mode failed");
257 return rc;
258 }
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530259 for (pin = 0; pin < ARRAY_SIZE(fm_i2s_config_power_off);
260 pin++) {
261 rc = gpio_tlmm_config(
262 fm_i2s_config_power_off[pin],
263 GPIO_CFG_ENABLE
264 );
265 if (rc < 0)
266 return rc;
267 }
268 }
269 return rc;
270}
271static int config_pcm(int mode)
272{
273 int pin, rc = 0;
274
275 if (mode == BT_PCM_ON) {
276 if (machine_is_msm7627a_qrd1())
277 config_pcm_i2s_mode(1);
278 pr_err("%s mode =BT_PCM_ON", __func__);
Rahul Kashyap8b4a7862011-12-13 18:40:54 +0530279 rc = switch_pcm_i2s_reg_mode(1);
280 if (rc) {
281 pr_err("switch mode failed");
282 return rc;
283 }
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530284 for (pin = 0; pin < ARRAY_SIZE(bt_config_pcm_on);
285 pin++) {
286 rc = gpio_tlmm_config(bt_config_pcm_on[pin],
287 GPIO_CFG_ENABLE);
288 if (rc < 0)
289 return rc;
290 }
291 } else if (mode == BT_PCM_OFF) {
292 pr_err("%s mode =BT_PCM_OFF", __func__);
Rahul Kashyap8b4a7862011-12-13 18:40:54 +0530293 rc = switch_pcm_i2s_reg_mode(0);
294 if (rc) {
295 pr_err("switch mode failed");
296 return rc;
297 }
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530298 for (pin = 0; pin < ARRAY_SIZE(bt_config_pcm_off);
299 pin++) {
300 rc = gpio_tlmm_config(bt_config_pcm_off[pin],
301 GPIO_CFG_ENABLE);
302 if (rc < 0)
303 return rc;
304 }
305
306 }
307
308 return rc;
309}
310
311static int msm_bahama_setup_pcm_i2s(int mode)
312{
313 int fm_state = 0, bt_state = 0;
314 int rc = 0;
315 struct marimba config = { .mod_id = SLAVE_ID_BAHAMA};
316
317 fm_state = marimba_get_fm_status(&config);
318 bt_state = marimba_get_bt_status(&config);
319
320 switch (mode) {
321 case BT_PCM_ON:
322 case BT_PCM_OFF:
323 if (!fm_state)
324 rc = config_pcm(mode);
325 break;
326 case FM_I2S_ON:
327 rc = config_i2s(mode);
328 break;
329 case FM_I2S_OFF:
330 if (bt_state)
331 rc = config_pcm(BT_PCM_ON);
332 else
333 rc = config_i2s(mode);
334 break;
335 default:
336 rc = -EIO;
337 pr_err("%s:Unsupported mode", __func__);
338 }
339 return rc;
340}
341
342static int bt_set_gpio(int on)
343{
344 int rc = 0;
345 struct marimba config = { .mod_id = SLAVE_ID_BAHAMA};
346
347 if (on) {
348 rc = gpio_direction_output(GPIO_BT_SYS_REST_EN, 1);
349 msleep(100);
350 } else {
351 if (!marimba_get_fm_status(&config) &&
352 !marimba_get_bt_status(&config)) {
353 gpio_set_value_cansleep(GPIO_BT_SYS_REST_EN, 0);
354 rc = gpio_direction_input(GPIO_BT_SYS_REST_EN);
355 msleep(100);
356 }
357 }
358 if (rc)
359 pr_err("%s: BT sys_reset_en GPIO : Error", __func__);
360
361 return rc;
362}
Pankaj Kumar27c02642011-09-22 15:55:55 +0530363static struct regulator *fm_regulator;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530364static int fm_radio_setup(struct marimba_fm_platform_data *pdata)
365{
366 int rc = 0;
367 const char *id = "FMPW";
368 uint32_t irqcfg;
369 struct marimba config = { .mod_id = SLAVE_ID_BAHAMA};
370 u8 value;
371
372 /* Voting for 1.8V Regulator */
Pankaj Kumar27c02642011-09-22 15:55:55 +0530373 fm_regulator = regulator_get(NULL , "msme1");
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530374 if (IS_ERR(fm_regulator)) {
Pankaj Kumar27c02642011-09-22 15:55:55 +0530375 rc = PTR_ERR(fm_regulator);
376 pr_err("%s: could not get regulator: %d\n", __func__, rc);
377 goto out;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530378 }
379
380 /* Set the voltage level to 1.8V */
Pankaj Kumar27c02642011-09-22 15:55:55 +0530381 rc = regulator_set_voltage(fm_regulator, 1800000, 1800000);
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530382 if (rc < 0) {
Pankaj Kumar27c02642011-09-22 15:55:55 +0530383 pr_err("%s: could not set voltage: %d\n", __func__, rc);
384 goto reg_free;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530385 }
386
387 /* Enabling the 1.8V regulator */
Pankaj Kumar27c02642011-09-22 15:55:55 +0530388 rc = regulator_enable(fm_regulator);
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530389 if (rc) {
Pankaj Kumar27c02642011-09-22 15:55:55 +0530390 pr_err("%s: could not enable regulator: %d\n", __func__, rc);
391 goto reg_free;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530392 }
393
394 /* Voting for 19.2MHz clock */
395 rc = pmapp_clock_vote(id, PMAPP_CLOCK_ID_D1,
396 PMAPP_CLOCK_VOTE_ON);
397 if (rc < 0) {
398 pr_err("%s: clock vote failed with :(%d)\n",
399 __func__, rc);
Pankaj Kumar27c02642011-09-22 15:55:55 +0530400 goto reg_disable;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530401 }
402
403 rc = bt_set_gpio(1);
404 if (rc) {
405 pr_err("%s: bt_set_gpio = %d", __func__, rc);
Pankaj Kumar27c02642011-09-22 15:55:55 +0530406 goto gpio_deconfig;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530407 }
408 /*re-write FM Slave Id, after reset*/
409 value = BAHAMA_SLAVE_ID_FM_ADDR;
410 rc = marimba_write_bit_mask(&config,
411 BAHAMA_SLAVE_ID_FM_REG, &value, 1, 0xFF);
412 if (rc < 0) {
413 pr_err("%s: FM Slave ID rewrite Failed = %d", __func__, rc);
Pankaj Kumar27c02642011-09-22 15:55:55 +0530414 goto gpio_deconfig;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530415 }
416 /* Configuring the FM GPIO */
417 irqcfg = GPIO_CFG(FM_GPIO, 0, GPIO_CFG_INPUT, GPIO_CFG_NO_PULL,
418 GPIO_CFG_2MA);
419
420 rc = gpio_tlmm_config(irqcfg, GPIO_CFG_ENABLE);
421 if (rc) {
422 pr_err("%s: gpio_tlmm_config(%#x)=%d\n",
423 __func__, irqcfg, rc);
Pankaj Kumar27c02642011-09-22 15:55:55 +0530424 goto gpio_deconfig;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530425 }
426
427 return 0;
428
Pankaj Kumar27c02642011-09-22 15:55:55 +0530429gpio_deconfig:
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530430 pmapp_clock_vote(id, PMAPP_CLOCK_ID_D1,
431 PMAPP_CLOCK_VOTE_OFF);
432 bt_set_gpio(0);
Pankaj Kumar27c02642011-09-22 15:55:55 +0530433reg_disable:
434 regulator_disable(fm_regulator);
435reg_free:
436 regulator_put(fm_regulator);
437 fm_regulator = NULL;
438out:
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530439 return rc;
440};
441
442static void fm_radio_shutdown(struct marimba_fm_platform_data *pdata)
443{
444 int rc;
445 const char *id = "FMPW";
446
447 /* Releasing the GPIO line used by FM */
448 uint32_t irqcfg = GPIO_CFG(FM_GPIO, 0, GPIO_CFG_INPUT, GPIO_CFG_PULL_UP,
449 GPIO_CFG_2MA);
450
451 rc = gpio_tlmm_config(irqcfg, GPIO_CFG_ENABLE);
452 if (rc)
453 pr_err("%s: gpio_tlmm_config(%#x)=%d\n",
454 __func__, irqcfg, rc);
455
456 /* Releasing the 1.8V Regulator */
Pankaj Kumar27c02642011-09-22 15:55:55 +0530457 if (!IS_ERR_OR_NULL(fm_regulator)) {
458 rc = regulator_disable(fm_regulator);
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530459 if (rc)
Pankaj Kumar27c02642011-09-22 15:55:55 +0530460 pr_err("%s: could not disable regulator: %d\n",
461 __func__, rc);
462 regulator_put(fm_regulator);
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530463 fm_regulator = NULL;
464 }
465
466 /* Voting off the clock */
467 rc = pmapp_clock_vote(id, PMAPP_CLOCK_ID_D1,
468 PMAPP_CLOCK_VOTE_OFF);
469 if (rc < 0)
470 pr_err("%s: voting off failed with :(%d)\n",
471 __func__, rc);
472 rc = bt_set_gpio(0);
473 if (rc)
474 pr_err("%s: bt_set_gpio = %d", __func__, rc);
475}
476
477static struct marimba_fm_platform_data marimba_fm_pdata = {
478 .fm_setup = fm_radio_setup,
479 .fm_shutdown = fm_radio_shutdown,
480 .irq = MSM_GPIO_TO_INT(FM_GPIO),
481 .vreg_s2 = NULL,
482 .vreg_xo_out = NULL,
483 /* Configuring the FM SoC as I2S Master */
484 .is_fm_soc_i2s_master = true,
485 .config_i2s_gpio = msm_bahama_setup_pcm_i2s,
486};
Chintan Pandya3b2aff72011-11-25 16:26:08 +0530487#endif
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530488
489static struct platform_device msm_wlan_ar6000_pm_device = {
490 .name = "wlan_ar6000_pm_dev",
491 .id = -1,
492};
493
494#if defined(CONFIG_BT) && defined(CONFIG_MARIMBA_CORE)
495
496static struct platform_device msm_bt_power_device = {
497 .name = "bt_power",
498};
499struct bahama_config_register {
500 u8 reg;
501 u8 value;
502 u8 mask;
503};
504struct bt_vreg_info {
505 const char *name;
506 unsigned int pmapp_id;
Pankaj Kumar27c02642011-09-22 15:55:55 +0530507 unsigned int min_level;
508 unsigned int max_level;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530509 unsigned int is_pin_controlled;
Pankaj Kumar27c02642011-09-22 15:55:55 +0530510 struct regulator *reg;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530511};
512static struct bt_vreg_info bt_vregs[] = {
Pankaj Kumar27c02642011-09-22 15:55:55 +0530513 {"msme1", 2, 1800000, 1800000, 0, NULL},
514 {"bt", 21, 2900000, 3050000, 1, NULL}
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530515};
516
517static int bahama_bt(int on)
518{
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530519 int rc = 0;
520 int i;
521
522 struct marimba config = { .mod_id = SLAVE_ID_BAHAMA};
523
524 struct bahama_variant_register {
525 const size_t size;
526 const struct bahama_config_register *set;
527 };
528
529 const struct bahama_config_register *p;
530
531 u8 version;
532
533 const struct bahama_config_register v10_bt_on[] = {
534 { 0xE9, 0x00, 0xFF },
535 { 0xF4, 0x80, 0xFF },
536 { 0xE4, 0x00, 0xFF },
537 { 0xE5, 0x00, 0x0F },
538#ifdef CONFIG_WLAN
539 { 0xE6, 0x38, 0x7F },
540 { 0xE7, 0x06, 0xFF },
541#endif
542 { 0xE9, 0x21, 0xFF },
543 { 0x01, 0x0C, 0x1F },
544 { 0x01, 0x08, 0x1F },
545 };
546
547 const struct bahama_config_register v20_bt_on_fm_off[] = {
548 { 0x11, 0x0C, 0xFF },
549 { 0x13, 0x01, 0xFF },
550 { 0xF4, 0x80, 0xFF },
551 { 0xF0, 0x00, 0xFF },
552 { 0xE9, 0x00, 0xFF },
553#ifdef CONFIG_WLAN
554 { 0x81, 0x00, 0x7F },
555 { 0x82, 0x00, 0xFF },
556 { 0xE6, 0x38, 0x7F },
557 { 0xE7, 0x06, 0xFF },
558#endif
559 { 0x8E, 0x15, 0xFF },
560 { 0x8F, 0x15, 0xFF },
561 { 0x90, 0x15, 0xFF },
562
563 { 0xE9, 0x21, 0xFF },
564 };
565
566 const struct bahama_config_register v20_bt_on_fm_on[] = {
567 { 0x11, 0x0C, 0xFF },
568 { 0x13, 0x01, 0xFF },
569 { 0xF4, 0x86, 0xFF },
570 { 0xF0, 0x06, 0xFF },
571 { 0xE9, 0x00, 0xFF },
572#ifdef CONFIG_WLAN
573 { 0x81, 0x00, 0x7F },
574 { 0x82, 0x00, 0xFF },
575 { 0xE6, 0x38, 0x7F },
576 { 0xE7, 0x06, 0xFF },
577#endif
578 { 0xE9, 0x21, 0xFF },
579 };
580
581 const struct bahama_config_register v10_bt_off[] = {
582 { 0xE9, 0x00, 0xFF },
583 };
584
585 const struct bahama_config_register v20_bt_off_fm_off[] = {
586 { 0xF4, 0x84, 0xFF },
587 { 0xF0, 0x04, 0xFF },
588 { 0xE9, 0x00, 0xFF }
589 };
590
591 const struct bahama_config_register v20_bt_off_fm_on[] = {
592 { 0xF4, 0x86, 0xFF },
593 { 0xF0, 0x06, 0xFF },
594 { 0xE9, 0x00, 0xFF }
595 };
596 const struct bahama_variant_register bt_bahama[2][3] = {
597 {
598 { ARRAY_SIZE(v10_bt_off), v10_bt_off },
599 { ARRAY_SIZE(v20_bt_off_fm_off), v20_bt_off_fm_off },
600 { ARRAY_SIZE(v20_bt_off_fm_on), v20_bt_off_fm_on }
601 },
602 {
603 { ARRAY_SIZE(v10_bt_on), v10_bt_on },
604 { ARRAY_SIZE(v20_bt_on_fm_off), v20_bt_on_fm_off },
605 { ARRAY_SIZE(v20_bt_on_fm_on), v20_bt_on_fm_on }
606 }
607 };
608
609 u8 offset = 0; /* index into bahama configs */
610 on = on ? 1 : 0;
611 version = marimba_read_bahama_ver(&config);
612 if ((int)version < 0 || version == BAHAMA_VER_UNSUPPORTED) {
613 dev_err(&msm_bt_power_device.dev, "%s: Bahama \
614 version read Error, version = %d \n",
615 __func__, version);
616 return -EIO;
617 }
618
619 if (version == BAHAMA_VER_2_0) {
620 if (marimba_get_fm_status(&config))
621 offset = 0x01;
622 }
623
624 p = bt_bahama[on][version + offset].set;
625
626 dev_info(&msm_bt_power_device.dev,
627 "%s: found version %d\n", __func__, version);
628
629 for (i = 0; i < bt_bahama[on][version + offset].size; i++) {
630 u8 value = (p+i)->value;
631 rc = marimba_write_bit_mask(&config,
632 (p+i)->reg,
633 &value,
634 sizeof((p+i)->value),
635 (p+i)->mask);
636 if (rc < 0) {
637 dev_err(&msm_bt_power_device.dev,
638 "%s: reg %x write failed: %d\n",
639 __func__, (p+i)->reg, rc);
640 return rc;
641 }
642 dev_dbg(&msm_bt_power_device.dev,
643 "%s: reg 0x%02x write value 0x%02x mask 0x%02x\n",
644 __func__, (p+i)->reg,
645 value, (p+i)->mask);
646 value = 0;
647 rc = marimba_read_bit_mask(&config,
648 (p+i)->reg, &value,
649 sizeof((p+i)->value), (p+i)->mask);
650 if (rc < 0)
651 dev_err(&msm_bt_power_device.dev, "%s marimba_read_bit_mask- error",
652 __func__);
653 dev_dbg(&msm_bt_power_device.dev,
654 "%s: reg 0x%02x read value 0x%02x mask 0x%02x\n",
655 __func__, (p+i)->reg,
656 value, (p+i)->mask);
657 }
658 /* Update BT Status */
659 if (on)
660 marimba_set_bt_status(&config, true);
661 else
662 marimba_set_bt_status(&config, false);
663 return rc;
664}
665static int bluetooth_switch_regulators(int on)
666{
667 int i, rc = 0;
668 const char *id = "BTPW";
669
670 for (i = 0; i < ARRAY_SIZE(bt_vregs); i++) {
Pankaj Kumar27c02642011-09-22 15:55:55 +0530671 if (IS_ERR_OR_NULL(bt_vregs[i].reg)) {
672 rc = bt_vregs[i].reg ?
673 PTR_ERR(bt_vregs[i].reg) :
674 -ENODEV;
675 dev_err(&msm_bt_power_device.dev,
676 "%s: invalid regulator handle for %s: %d\n",
677 __func__, bt_vregs[i].name, rc);
678 goto reg_disable;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530679 }
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530680
Pankaj Kumar27c02642011-09-22 15:55:55 +0530681 rc = on ? regulator_set_voltage(bt_vregs[i].reg,
682 bt_vregs[i].min_level,
683 bt_vregs[i].max_level) : 0;
684 if (rc) {
685 dev_err(&msm_bt_power_device.dev,
686 "%s: could not set voltage for %s: %d\n",
687 __func__, bt_vregs[i].name, rc);
688 goto reg_disable;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530689 }
Pankaj Kumar27c02642011-09-22 15:55:55 +0530690
691 rc = on ? regulator_enable(bt_vregs[i].reg) : 0;
692 if (rc) {
693 dev_err(&msm_bt_power_device.dev,
694 "%s: could not %sable regulator %s: %d\n",
695 __func__, "en", bt_vregs[i].name, rc);
696 goto reg_disable;
697 }
698
699 if (bt_vregs[i].is_pin_controlled) {
700 rc = pmapp_vreg_lpm_pincntrl_vote(id,
701 bt_vregs[i].pmapp_id,
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530702 PMAPP_CLOCK_ID_D1,
703 on ? PMAPP_CLOCK_VOTE_ON :
Pankaj Kumar27c02642011-09-22 15:55:55 +0530704 PMAPP_CLOCK_VOTE_OFF);
705 if (rc) {
706 dev_err(&msm_bt_power_device.dev,
707 "%s: pin control failed for %s: %d\n",
708 __func__, bt_vregs[i].name, rc);
709 goto pin_cnt_fail;
710 }
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530711 }
Pankaj Kumar27c02642011-09-22 15:55:55 +0530712 rc = on ? 0 : regulator_disable(bt_vregs[i].reg);
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530713
Pankaj Kumar27c02642011-09-22 15:55:55 +0530714 if (rc) {
715 dev_err(&msm_bt_power_device.dev,
716 "%s: could not %sable regulator %s: %d\n",
717 __func__, "dis", bt_vregs[i].name, rc);
718 goto reg_disable;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530719 }
720 }
721
722 return rc;
Pankaj Kumar27c02642011-09-22 15:55:55 +0530723pin_cnt_fail:
724 if (on)
725 regulator_disable(bt_vregs[i].reg);
726reg_disable:
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530727 while (i) {
Pankaj Kumar27c02642011-09-22 15:55:55 +0530728 if (on) {
729 i--;
730 regulator_disable(bt_vregs[i].reg);
731 regulator_put(bt_vregs[i].reg);
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530732 }
Pankaj Kumar27c02642011-09-22 15:55:55 +0530733 }
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530734 return rc;
735}
736
Pankaj Kumar27c02642011-09-22 15:55:55 +0530737static struct regulator *reg_s3;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530738static unsigned int msm_bahama_setup_power(void)
739{
740 int rc = 0;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530741
Pankaj Kumar27c02642011-09-22 15:55:55 +0530742 reg_s3 = regulator_get(NULL, "msme1");
743 if (IS_ERR(reg_s3)) {
744 rc = PTR_ERR(reg_s3);
745 pr_err("%s: could not get regulator: %d\n", __func__, rc);
746 goto out;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530747 }
Pankaj Kumar27c02642011-09-22 15:55:55 +0530748
749 rc = regulator_set_voltage(reg_s3, 1800000, 1800000);
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530750 if (rc < 0) {
Pankaj Kumar27c02642011-09-22 15:55:55 +0530751 pr_err("%s: could not set voltage: %d\n", __func__, rc);
752 goto reg_fail;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530753 }
Pankaj Kumar27c02642011-09-22 15:55:55 +0530754
755 rc = regulator_enable(reg_s3);
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530756 if (rc < 0) {
Pankaj Kumar27c02642011-09-22 15:55:55 +0530757 pr_err("%s: could not enable regulator: %d\n", __func__, rc);
758 goto reg_fail;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530759 }
760
Rahul Kashyap5e59b892011-12-12 16:54:04 +0530761 gpio_tlmm_config(GPIO_CFG(GPIO_BT_SYS_REST_EN, 0,
762 GPIO_CFG_OUTPUT, GPIO_CFG_NO_PULL,
763 GPIO_CFG_2MA), GPIO_CFG_ENABLE);
764
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530765 /*setup Bahama_sys_reset_n*/
766 rc = gpio_request(GPIO_BT_SYS_REST_EN, "bahama sys_rst_n");
767 if (rc < 0) {
768 pr_err("%s: gpio_request %d = %d\n", __func__,
769 GPIO_BT_SYS_REST_EN, rc);
Pankaj Kumar27c02642011-09-22 15:55:55 +0530770 goto reg_disable;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530771 }
Pankaj Kumar27c02642011-09-22 15:55:55 +0530772
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530773 rc = bt_set_gpio(1);
774 if (rc < 0) {
775 pr_err("%s: bt_set_gpio %d = %d\n", __func__,
776 GPIO_BT_SYS_REST_EN, rc);
777 goto gpio_fail;
778 }
Pankaj Kumar27c02642011-09-22 15:55:55 +0530779
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530780 return rc;
781
782gpio_fail:
783 gpio_free(GPIO_BT_SYS_REST_EN);
Pankaj Kumar27c02642011-09-22 15:55:55 +0530784reg_disable:
785 regulator_disable(reg_s3);
786reg_fail:
787 regulator_put(reg_s3);
788out:
789 reg_s3 = NULL;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530790 return rc;
791}
792
793static unsigned int msm_bahama_shutdown_power(int value)
794{
795 int rc = 0;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530796
Pankaj Kumar27c02642011-09-22 15:55:55 +0530797 if (IS_ERR_OR_NULL(reg_s3)) {
798 rc = reg_s3 ? PTR_ERR(reg_s3) : -ENODEV;
799 goto out;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530800 }
Pankaj Kumar27c02642011-09-22 15:55:55 +0530801
802 rc = regulator_disable(reg_s3);
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530803 if (rc) {
Pankaj Kumar27c02642011-09-22 15:55:55 +0530804 pr_err("%s: could not disable regulator: %d\n", __func__, rc);
805 goto out;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530806 }
Pankaj Kumar27c02642011-09-22 15:55:55 +0530807
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530808 if (value == BAHAMA_ID) {
809 rc = bt_set_gpio(0);
810 if (rc) {
811 pr_err("%s: bt_set_gpio = %d\n",
812 __func__, rc);
Pankaj Kumar27c02642011-09-22 15:55:55 +0530813 goto reg_enable;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530814 }
Pankaj Kumar27c02642011-09-22 15:55:55 +0530815 gpio_free(GPIO_BT_SYS_REST_EN);
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530816 }
Pankaj Kumar27c02642011-09-22 15:55:55 +0530817
818 regulator_put(reg_s3);
819 reg_s3 = NULL;
820
821 return 0;
822
823reg_enable:
824 regulator_enable(reg_s3);
825out:
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530826 return rc;
827}
828
829static unsigned int msm_bahama_core_config(int type)
830{
831 int rc = 0;
832
833 if (type == BAHAMA_ID) {
834 int i;
835 struct marimba config = { .mod_id = SLAVE_ID_BAHAMA};
836 const struct bahama_config_register v20_init[] = {
837 /* reg, value, mask */
838 { 0xF4, 0x84, 0xFF }, /* AREG */
839 { 0xF0, 0x04, 0xFF } /* DREG */
840 };
841 if (marimba_read_bahama_ver(&config) == BAHAMA_VER_2_0) {
842 for (i = 0; i < ARRAY_SIZE(v20_init); i++) {
843 u8 value = v20_init[i].value;
844 rc = marimba_write_bit_mask(&config,
845 v20_init[i].reg,
846 &value,
847 sizeof(v20_init[i].value),
848 v20_init[i].mask);
849 if (rc < 0) {
850 pr_err("%s: reg %d write failed: %d\n",
851 __func__, v20_init[i].reg, rc);
852 return rc;
853 }
854 pr_debug("%s: reg 0x%02x value 0x%02x"
855 " mask 0x%02x\n",
856 __func__, v20_init[i].reg,
857 v20_init[i].value, v20_init[i].mask);
858 }
859 }
860 }
861 rc = bt_set_gpio(0);
862 if (rc) {
863 pr_err("%s: bt_set_gpio = %d\n",
864 __func__, rc);
865 }
866 pr_debug("core type: %d\n", type);
867 return rc;
868}
869
870static int bluetooth_power(int on)
871{
872 int pin, rc = 0;
873 const char *id = "BTPW";
874 int cid = 0;
875
876 cid = adie_get_detected_connectivity_type();
877 if (cid != BAHAMA_ID) {
878 pr_err("%s: unexpected adie connectivity type: %d\n",
879 __func__, cid);
880 return -ENODEV;
881 }
882 if (on) {
883 /*setup power for BT SOC*/
884 rc = bt_set_gpio(on);
885 if (rc) {
886 pr_err("%s: bt_set_gpio = %d\n",
887 __func__, rc);
888 goto exit;
889 }
890 rc = bluetooth_switch_regulators(on);
891 if (rc < 0) {
892 pr_err("%s: bluetooth_switch_regulators rc = %d",
893 __func__, rc);
894 goto exit;
895 }
896 /*setup BT GPIO lines*/
897 for (pin = 0; pin < ARRAY_SIZE(bt_config_power_on);
898 pin++) {
899 rc = gpio_tlmm_config(bt_config_power_on[pin],
900 GPIO_CFG_ENABLE);
901 if (rc < 0) {
902 pr_err("%s: gpio_tlmm_config(%#x)=%d\n",
903 __func__,
904 bt_config_power_on[pin],
905 rc);
906 goto fail_power;
907 }
908 }
909 /*Setup BT clocks*/
910 rc = pmapp_clock_vote(id, PMAPP_CLOCK_ID_D1,
911 PMAPP_CLOCK_VOTE_ON);
912 if (rc < 0) {
913 pr_err("Failed to vote for TCXO_D1 ON\n");
914 goto fail_clock;
915 }
916 msleep(20);
917
918 /*I2C config for Bahama*/
919 rc = bahama_bt(1);
920 if (rc < 0) {
921 pr_err("%s: bahama_bt rc = %d", __func__, rc);
922 goto fail_i2c;
923 }
924 msleep(20);
925
926 /*setup BT PCM lines*/
927 rc = msm_bahama_setup_pcm_i2s(BT_PCM_ON);
928 if (rc < 0) {
929 pr_err("%s: msm_bahama_setup_pcm_i2s , rc =%d\n",
930 __func__, rc);
931 goto fail_power;
932 }
933 rc = pmapp_clock_vote(id, PMAPP_CLOCK_ID_D1,
934 PMAPP_CLOCK_VOTE_PIN_CTRL);
935 if (rc < 0)
936 pr_err("%s:Pin Control Failed, rc = %d",
937 __func__, rc);
938
939 } else {
940 rc = bahama_bt(0);
941 if (rc < 0)
942 pr_err("%s: bahama_bt rc = %d", __func__, rc);
943
944 rc = bt_set_gpio(on);
945 if (rc) {
946 pr_err("%s: bt_set_gpio = %d\n",
947 __func__, rc);
948 }
949fail_i2c:
950 rc = pmapp_clock_vote(id, PMAPP_CLOCK_ID_D1,
951 PMAPP_CLOCK_VOTE_OFF);
952 if (rc < 0)
953 pr_err("%s: Failed to vote Off D1\n", __func__);
954fail_clock:
955 for (pin = 0; pin < ARRAY_SIZE(bt_config_power_off);
956 pin++) {
957 rc = gpio_tlmm_config(bt_config_power_off[pin],
958 GPIO_CFG_ENABLE);
959 if (rc < 0) {
960 pr_err("%s: gpio_tlmm_config(%#x)=%d\n",
961 __func__, bt_config_power_off[pin], rc);
962 }
963 }
964 rc = msm_bahama_setup_pcm_i2s(BT_PCM_OFF);
965 if (rc < 0) {
966 pr_err("%s: msm_bahama_setup_pcm_i2s, rc =%d\n",
967 __func__, rc);
968 }
969fail_power:
970 rc = bluetooth_switch_regulators(0);
971 if (rc < 0) {
972 pr_err("%s: switch_regulators : rc = %d",\
973 __func__, rc);
974 goto exit;
975 }
976 }
977 return rc;
978exit:
979 pr_err("%s: failed with rc = %d", __func__, rc);
980 return rc;
981}
982
983static int __init bt_power_init(void)
984{
985 int i, rc = 0;
Pankaj Kumar27c02642011-09-22 15:55:55 +0530986 struct device *dev = &msm_bt_power_device.dev;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530987
Pankaj Kumar27c02642011-09-22 15:55:55 +0530988 for (i = 0; i < ARRAY_SIZE(bt_vregs); i++) {
989 bt_vregs[i].reg = regulator_get(dev, bt_vregs[i].name);
990 if (IS_ERR(bt_vregs[i].reg)) {
991 rc = PTR_ERR(bt_vregs[i].reg);
992 dev_err(dev, "%s: could not get regulator %s: %d\n",
993 __func__, bt_vregs[i].name, rc);
994 goto reg_get_fail;
995 }
996 }
997
998 dev->platform_data = &bluetooth_power;
Taniya Dasc98bfbc2011-08-23 09:58:55 +0530999
1000 return rc;
1001
Pankaj Kumar27c02642011-09-22 15:55:55 +05301002reg_get_fail:
1003 while (i--) {
1004 regulator_put(bt_vregs[i].reg);
1005 bt_vregs[i].reg = NULL;
1006 }
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301007 return rc;
1008}
1009
1010static struct marimba_platform_data marimba_pdata = {
1011 .slave_id[SLAVE_ID_BAHAMA_FM] = BAHAMA_SLAVE_ID_FM_ADDR,
1012 .slave_id[SLAVE_ID_BAHAMA_QMEMBIST] = BAHAMA_SLAVE_ID_QMEMBIST_ADDR,
1013 .bahama_setup = msm_bahama_setup_power,
1014 .bahama_shutdown = msm_bahama_shutdown_power,
1015 .bahama_core_config = msm_bahama_core_config,
1016 .fm = &marimba_fm_pdata,
1017};
1018
1019#endif
1020
1021#if defined(CONFIG_BT) && defined(CONFIG_MARIMBA_CORE)
1022static struct i2c_board_info bahama_devices[] = {
1023{
1024 I2C_BOARD_INFO("marimba", 0xc),
1025 .platform_data = &marimba_pdata,
1026},
1027};
1028#endif
1029
1030static struct msm_gpio qup_i2c_gpios_io[] = {
1031 { GPIO_CFG(60, 0, GPIO_CFG_OUTPUT, GPIO_CFG_NO_PULL, GPIO_CFG_8MA),
1032 "qup_scl" },
1033 { GPIO_CFG(61, 0, GPIO_CFG_OUTPUT, GPIO_CFG_NO_PULL, GPIO_CFG_8MA),
1034 "qup_sda" },
1035 { GPIO_CFG(131, 0, GPIO_CFG_OUTPUT, GPIO_CFG_NO_PULL, GPIO_CFG_8MA),
1036 "qup_scl" },
1037 { GPIO_CFG(132, 0, GPIO_CFG_OUTPUT, GPIO_CFG_NO_PULL, GPIO_CFG_8MA),
1038 "qup_sda" },
1039};
1040
1041static struct msm_gpio qup_i2c_gpios_hw[] = {
1042 { GPIO_CFG(60, 1, GPIO_CFG_INPUT, GPIO_CFG_NO_PULL, GPIO_CFG_8MA),
1043 "qup_scl" },
1044 { GPIO_CFG(61, 1, GPIO_CFG_INPUT, GPIO_CFG_NO_PULL, GPIO_CFG_8MA),
1045 "qup_sda" },
1046 { GPIO_CFG(131, 2, GPIO_CFG_INPUT, GPIO_CFG_NO_PULL, GPIO_CFG_8MA),
1047 "qup_scl" },
1048 { GPIO_CFG(132, 2, GPIO_CFG_INPUT, GPIO_CFG_NO_PULL, GPIO_CFG_8MA),
1049 "qup_sda" },
1050};
1051
1052static void gsbi_qup_i2c_gpio_config(int adap_id, int config_type)
1053{
1054 int rc;
1055
1056 if (adap_id < 0 || adap_id > 1)
1057 return;
1058
1059 /* Each adapter gets 2 lines from the table */
1060 if (config_type)
1061 rc = msm_gpios_request_enable(&qup_i2c_gpios_hw[adap_id*2], 2);
1062 else
1063 rc = msm_gpios_request_enable(&qup_i2c_gpios_io[adap_id*2], 2);
1064 if (rc < 0)
1065 pr_err("QUP GPIO request/enable failed: %d\n", rc);
1066}
1067
1068static struct msm_i2c_platform_data msm_gsbi0_qup_i2c_pdata = {
1069 .clk_freq = 100000,
1070 .msm_i2c_config_gpio = gsbi_qup_i2c_gpio_config,
1071};
1072
1073static struct msm_i2c_platform_data msm_gsbi1_qup_i2c_pdata = {
1074 .clk_freq = 100000,
1075 .msm_i2c_config_gpio = gsbi_qup_i2c_gpio_config,
1076};
1077
1078#ifdef CONFIG_ARCH_MSM7X27A
1079#define MSM_PMEM_MDP_SIZE 0x1DD1000
1080#define MSM_PMEM_ADSP_SIZE 0x1000000
1081
1082#ifdef CONFIG_FB_MSM_TRIPLE_BUFFER
1083#define MSM_FB_SIZE 0x260000
1084#else
1085#define MSM_FB_SIZE 0x195000
1086#endif
1087
1088#endif
1089
Taniya Dasda408822011-09-06 12:54:06 +05301090#if defined(CONFIG_TOUCHSCREEN_SYNAPTICS_RMI4_I2C) || \
1091defined(CONFIG_TOUCHSCREEN_SYNAPTICS_RMI4_I2C_MODULE)
1092
1093#ifndef CLEARPAD3000_ATTEN_GPIO
1094#define CLEARPAD3000_ATTEN_GPIO (48)
1095#endif
1096
1097#ifndef CLEARPAD3000_RESET_GPIO
1098#define CLEARPAD3000_RESET_GPIO (26)
1099#endif
1100
1101static int synaptics_touchpad_setup(void);
1102
1103static struct msm_gpio clearpad3000_cfg_data[] = {
1104 {GPIO_CFG(CLEARPAD3000_ATTEN_GPIO, 0, GPIO_CFG_INPUT,
1105 GPIO_CFG_NO_PULL, GPIO_CFG_6MA), "rmi4_attn"},
1106 {GPIO_CFG(CLEARPAD3000_RESET_GPIO, 0, GPIO_CFG_OUTPUT,
1107 GPIO_CFG_PULL_DOWN, GPIO_CFG_8MA), "rmi4_reset"},
1108};
1109
1110static struct rmi_XY_pair rmi_offset = {.x = 0, .y = 0};
1111static struct rmi_range rmi_clipx = {.min = 48, .max = 980};
1112static struct rmi_range rmi_clipy = {.min = 7, .max = 1647};
1113static struct rmi_f11_functiondata synaptics_f11_data = {
1114 .swap_axes = false,
1115 .flipX = false,
1116 .flipY = false,
1117 .offset = &rmi_offset,
1118 .button_height = 113,
1119 .clipX = &rmi_clipx,
1120 .clipY = &rmi_clipy,
1121};
1122
1123#define MAX_LEN 100
1124
1125static ssize_t clearpad3000_virtual_keys_register(struct kobject *kobj,
1126 struct kobj_attribute *attr, char *buf)
1127{
1128 char *virtual_keys = __stringify(EV_KEY) ":" __stringify(KEY_MENU) \
1129 ":60:830:120:60" ":" __stringify(EV_KEY) \
1130 ":" __stringify(KEY_HOME) ":180:830:120:60" \
1131 ":" __stringify(EV_KEY) ":" \
1132 __stringify(KEY_SEARCH) ":300:830:120:60" \
1133 ":" __stringify(EV_KEY) ":" \
1134 __stringify(KEY_BACK) ":420:830:120:60" "\n";
1135
1136 return snprintf(buf, strnlen(virtual_keys, MAX_LEN) + 1 , "%s",
1137 virtual_keys);
1138}
1139
1140static struct kobj_attribute clearpad3000_virtual_keys_attr = {
1141 .attr = {
1142 .name = "virtualkeys.sensor00fn11",
1143 .mode = S_IRUGO,
1144 },
1145 .show = &clearpad3000_virtual_keys_register,
1146};
1147
1148static struct attribute *virtual_key_properties_attrs[] = {
1149 &clearpad3000_virtual_keys_attr.attr,
1150 NULL
1151};
1152
1153static struct attribute_group virtual_key_properties_attr_group = {
1154 .attrs = virtual_key_properties_attrs,
1155};
1156
1157struct kobject *virtual_key_properties_kobj;
1158
1159static struct rmi_functiondata synaptics_functiondata[] = {
1160 {
1161 .function_index = RMI_F11_INDEX,
1162 .data = &synaptics_f11_data,
1163 },
1164};
1165
1166static struct rmi_functiondata_list synaptics_perfunctiondata = {
1167 .count = ARRAY_SIZE(synaptics_functiondata),
1168 .functiondata = synaptics_functiondata,
1169};
1170
1171static struct rmi_sensordata synaptics_sensordata = {
1172 .perfunctiondata = &synaptics_perfunctiondata,
1173 .rmi_sensor_setup = synaptics_touchpad_setup,
1174};
1175
1176static struct rmi_i2c_platformdata synaptics_platformdata = {
1177 .i2c_address = 0x2c,
1178 .irq_type = IORESOURCE_IRQ_LOWLEVEL,
1179 .sensordata = &synaptics_sensordata,
1180};
1181
1182static struct i2c_board_info synaptic_i2c_clearpad3k[] = {
1183 {
1184 I2C_BOARD_INFO("rmi4_ts", 0x2c),
1185 .platform_data = &synaptics_platformdata,
1186 },
1187};
1188
1189static int synaptics_touchpad_setup(void)
1190{
1191 int retval = 0;
1192
1193 virtual_key_properties_kobj =
1194 kobject_create_and_add("board_properties", NULL);
1195 if (virtual_key_properties_kobj)
1196 retval = sysfs_create_group(virtual_key_properties_kobj,
1197 &virtual_key_properties_attr_group);
1198 if (!virtual_key_properties_kobj || retval)
1199 pr_err("failed to create ft5202 board_properties\n");
1200
1201 retval = msm_gpios_request_enable(clearpad3000_cfg_data,
1202 sizeof(clearpad3000_cfg_data)/sizeof(struct msm_gpio));
1203 if (retval) {
1204 pr_err("%s:Failed to obtain touchpad GPIO %d. Code: %d.",
1205 __func__, CLEARPAD3000_ATTEN_GPIO, retval);
1206 retval = 0; /* ignore the err */
1207 }
1208 synaptics_platformdata.irq = gpio_to_irq(CLEARPAD3000_ATTEN_GPIO);
1209
1210 gpio_set_value(CLEARPAD3000_RESET_GPIO, 0);
1211 usleep(10000);
1212 gpio_set_value(CLEARPAD3000_RESET_GPIO, 1);
1213 usleep(50000);
1214
1215 return retval;
1216}
1217#endif
1218
1219
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301220static struct android_usb_platform_data android_usb_pdata = {
Pankaj Kumar6f841742011-10-10 15:52:14 +05301221 .update_pid_and_serial_num = usb_diag_update_pid_and_serial_num,
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301222};
1223
1224static struct platform_device android_usb_device = {
1225 .name = "android_usb",
1226 .id = -1,
1227 .dev = {
1228 .platform_data = &android_usb_pdata,
1229 },
1230};
1231
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301232#ifdef CONFIG_USB_EHCI_MSM_72K
1233static void msm_hsusb_vbus_power(unsigned phy_info, int on)
1234{
1235 int rc = 0;
1236 unsigned gpio;
1237
1238 gpio = GPIO_HOST_VBUS_EN;
1239
1240 rc = gpio_request(gpio, "i2c_host_vbus_en");
1241 if (rc < 0) {
1242 pr_err("failed to request %d GPIO\n", gpio);
1243 return;
1244 }
1245 gpio_direction_output(gpio, !!on);
1246 gpio_set_value_cansleep(gpio, !!on);
1247 gpio_free(gpio);
1248}
1249
1250static struct msm_usb_host_platform_data msm_usb_host_pdata = {
1251 .phy_info = (USB_PHY_INTEGRATED | USB_PHY_MODEL_45NM),
1252};
1253
1254static void __init msm7627a_init_host(void)
1255{
1256 msm_add_host(0, &msm_usb_host_pdata);
1257}
1258#endif
1259
1260#ifdef CONFIG_USB_MSM_OTG_72K
1261static int hsusb_rpc_connect(int connect)
1262{
1263 if (connect)
1264 return msm_hsusb_rpc_connect();
1265 else
1266 return msm_hsusb_rpc_close();
1267}
1268
Pankaj Kumar27c02642011-09-22 15:55:55 +05301269static struct regulator *reg_hsusb;
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301270static int msm_hsusb_ldo_init(int init)
1271{
Pankaj Kumar27c02642011-09-22 15:55:55 +05301272 int rc = 0;
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301273
Pankaj Kumar27c02642011-09-22 15:55:55 +05301274 if (init) {
1275 reg_hsusb = regulator_get(NULL, "usb");
1276 if (IS_ERR(reg_hsusb)) {
1277 rc = PTR_ERR(reg_hsusb);
1278 pr_err("%s: could not get regulator: %d\n",
1279 __func__, rc);
1280 goto out;
1281 }
1282
1283 rc = regulator_set_voltage(reg_hsusb, 3300000, 3300000);
1284 if (rc) {
1285 pr_err("%s: could not set voltage: %d\n",
1286 __func__, rc);
1287 goto reg_free;
1288 }
1289
1290 return 0;
1291 }
1292 /* else fall through */
1293reg_free:
1294 regulator_put(reg_hsusb);
1295out:
1296 reg_hsusb = NULL;
1297 return rc;
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301298}
1299
1300static int msm_hsusb_ldo_enable(int enable)
1301{
1302 static int ldo_status;
1303
Pankaj Kumar27c02642011-09-22 15:55:55 +05301304 if (IS_ERR_OR_NULL(reg_hsusb))
1305 return reg_hsusb ? PTR_ERR(reg_hsusb) : -ENODEV;
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301306
1307 if (ldo_status == enable)
1308 return 0;
1309
1310 ldo_status = enable;
1311
Pankaj Kumar27c02642011-09-22 15:55:55 +05301312 return enable ?
1313 regulator_enable(reg_hsusb) :
1314 regulator_disable(reg_hsusb);
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301315}
1316
1317#ifndef CONFIG_USB_EHCI_MSM_72K
1318static int msm_hsusb_pmic_notif_init(void (*callback)(int online), int init)
1319{
1320 int ret = 0;
1321
1322 if (init)
1323 ret = msm_pm_app_rpc_init(callback);
1324 else
1325 msm_pm_app_rpc_deinit(callback);
1326
1327 return ret;
1328}
1329#endif
1330
1331static struct msm_otg_platform_data msm_otg_pdata = {
1332#ifndef CONFIG_USB_EHCI_MSM_72K
1333 .pmic_vbus_notif_init = msm_hsusb_pmic_notif_init,
1334#else
1335 .vbus_power = msm_hsusb_vbus_power,
1336#endif
1337 .rpc_connect = hsusb_rpc_connect,
1338 .core_clk = 1,
1339 .pemp_level = PRE_EMPHASIS_WITH_20_PERCENT,
1340 .cdr_autoreset = CDR_AUTO_RESET_DISABLE,
1341 .drv_ampl = HS_DRV_AMPLITUDE_DEFAULT,
1342 .se1_gating = SE1_GATING_DISABLE,
1343 .ldo_init = msm_hsusb_ldo_init,
1344 .ldo_enable = msm_hsusb_ldo_enable,
1345 .chg_init = hsusb_chg_init,
1346 .chg_connected = hsusb_chg_connected,
1347 .chg_vbus_draw = hsusb_chg_vbus_draw,
1348};
1349#endif
1350
1351static struct msm_hsusb_gadget_platform_data msm_gadget_pdata = {
1352 .is_phy_status_timer_on = 1,
1353};
1354
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301355#ifdef CONFIG_SERIAL_MSM_HS
1356static struct msm_serial_hs_platform_data msm_uart_dm1_pdata = {
1357 .inject_rx_on_wakeup = 1,
1358 .rx_to_inject = 0xFD,
1359};
1360#endif
1361static struct msm_pm_platform_data msm7627a_pm_data[MSM_PM_SLEEP_MODE_NR] = {
1362 [MSM_PM_SLEEP_MODE_POWER_COLLAPSE] = {
1363 .idle_supported = 1,
1364 .suspend_supported = 1,
1365 .idle_enabled = 1,
1366 .suspend_enabled = 1,
1367 .latency = 16000,
1368 .residency = 20000,
1369 },
1370 [MSM_PM_SLEEP_MODE_POWER_COLLAPSE_NO_XO_SHUTDOWN] = {
1371 .idle_supported = 1,
1372 .suspend_supported = 1,
1373 .idle_enabled = 1,
1374 .suspend_enabled = 1,
1375 .latency = 12000,
1376 .residency = 20000,
1377 },
1378 [MSM_PM_SLEEP_MODE_RAMP_DOWN_AND_WAIT_FOR_INTERRUPT] = {
1379 .idle_supported = 1,
1380 .suspend_supported = 1,
1381 .idle_enabled = 0,
1382 .suspend_enabled = 1,
1383 .latency = 2000,
1384 .residency = 0,
1385 },
1386 [MSM_PM_SLEEP_MODE_WAIT_FOR_INTERRUPT] = {
1387 .idle_supported = 1,
1388 .suspend_supported = 1,
1389 .idle_enabled = 1,
1390 .suspend_enabled = 1,
1391 .latency = 2,
1392 .residency = 0,
1393 },
1394};
1395
Maheshkumar Sivasubramanianc6c55032011-10-25 16:01:32 -06001396static struct msm_pm_boot_platform_data msm_pm_boot_pdata __initdata = {
1397 .mode = MSM_PM_BOOT_CONFIG_RESET_VECTOR_VIRT,
1398 .v_addr = (uint32_t *)PAGE_OFFSET,
1399};
1400
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301401static struct android_pmem_platform_data android_pmem_adsp_pdata = {
1402 .name = "pmem_adsp",
1403 .allocator_type = PMEM_ALLOCATORTYPE_BITMAP,
1404 .cached = 1,
1405 .memory_type = MEMTYPE_EBI1,
1406};
1407
1408static struct platform_device android_pmem_adsp_device = {
1409 .name = "android_pmem",
1410 .id = 1,
1411 .dev = { .platform_data = &android_pmem_adsp_pdata },
1412};
1413
1414static unsigned pmem_mdp_size = MSM_PMEM_MDP_SIZE;
1415static int __init pmem_mdp_size_setup(char *p)
1416{
1417 pmem_mdp_size = memparse(p, NULL);
1418 return 0;
1419}
1420
1421early_param("pmem_mdp_size", pmem_mdp_size_setup);
1422
1423static unsigned pmem_adsp_size = MSM_PMEM_ADSP_SIZE;
1424static int __init pmem_adsp_size_setup(char *p)
1425{
1426 pmem_adsp_size = memparse(p, NULL);
1427 return 0;
1428}
1429
1430early_param("pmem_adsp_size", pmem_adsp_size_setup);
1431
1432static unsigned fb_size = MSM_FB_SIZE;
1433static int __init fb_size_setup(char *p)
1434{
1435 fb_size = memparse(p, NULL);
1436 return 0;
1437}
1438
1439early_param("fb_size", fb_size_setup);
1440
Taniya Das0a5303a2011-08-23 18:47:48 +05301441static struct resource msm_fb_resources[] = {
1442 {
1443 .flags = IORESOURCE_DMA,
1444 }
1445};
1446
1447static int msm_fb_detect_panel(const char *name)
1448{
1449 int ret;
1450
1451 if (!strncmp(name, "mipi_video_truly_wvga", 21))
1452 ret = 0;
1453 else
1454 ret = -ENODEV;
1455
1456 return ret;
1457}
1458
1459static int mipi_truly_set_bl(int on)
1460{
1461 gpio_set_value_cansleep(GPIO_BACKLIGHT_EN, !!on);
1462
1463 return 1;
1464}
1465
1466static struct msm_fb_platform_data msm_fb_pdata = {
1467 .detect_client = msm_fb_detect_panel,
1468};
1469
1470static struct platform_device msm_fb_device = {
1471 .name = "msm_fb",
1472 .id = 0,
1473 .num_resources = ARRAY_SIZE(msm_fb_resources),
1474 .resource = msm_fb_resources,
1475 .dev = {
1476 .platform_data = &msm_fb_pdata,
1477 }
1478};
1479
1480static struct msm_panel_common_pdata mipi_truly_pdata = {
1481 .pmic_backlight = mipi_truly_set_bl,
1482};
1483
1484static struct platform_device mipi_dsi_truly_panel_device = {
1485 .name = "mipi_truly",
1486 .id = 0,
1487 .dev = {
1488 .platform_data = &mipi_truly_pdata,
1489 }
1490};
1491
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301492#define SND(desc, num) { .name = #desc, .id = num }
1493static struct snd_endpoint snd_endpoints_list[] = {
1494 SND(HANDSET, 0),
1495 SND(MONO_HEADSET, 2),
1496 SND(HEADSET, 3),
1497 SND(SPEAKER, 6),
1498 SND(TTY_HEADSET, 8),
1499 SND(TTY_VCO, 9),
1500 SND(TTY_HCO, 10),
1501 SND(BT, 12),
1502 SND(IN_S_SADC_OUT_HANDSET, 16),
1503 SND(IN_S_SADC_OUT_SPEAKER_PHONE, 25),
1504 SND(FM_DIGITAL_STEREO_HEADSET, 26),
1505 SND(FM_DIGITAL_SPEAKER_PHONE, 27),
1506 SND(FM_DIGITAL_BT_A2DP_HEADSET, 28),
Shashi Kumar64e07602011-10-11 13:18:57 +05301507 SND(STEREO_HEADSET_AND_SPEAKER, 31),
Phani Kumar Alladad6971252011-10-19 10:50:15 +05301508 SND(CURRENT, 0x7FFFFFFE),
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301509 SND(FM_ANALOG_STEREO_HEADSET, 35),
1510 SND(FM_ANALOG_STEREO_HEADSET_CODEC, 36),
1511};
1512#undef SND
1513
1514static struct msm_snd_endpoints msm_device_snd_endpoints = {
1515 .endpoints = snd_endpoints_list,
1516 .num = sizeof(snd_endpoints_list) / sizeof(struct snd_endpoint)
1517};
1518
1519static struct platform_device msm_device_snd = {
1520 .name = "msm_snd",
1521 .id = -1,
1522 .dev = {
1523 .platform_data = &msm_device_snd_endpoints
1524 },
1525};
1526
1527#define DEC0_FORMAT ((1<<MSM_ADSP_CODEC_MP3)| \
1528 (1<<MSM_ADSP_CODEC_AAC)|(1<<MSM_ADSP_CODEC_WMA)| \
1529 (1<<MSM_ADSP_CODEC_WMAPRO)|(1<<MSM_ADSP_CODEC_AMRWB)| \
1530 (1<<MSM_ADSP_CODEC_AMRNB)|(1<<MSM_ADSP_CODEC_WAV)| \
1531 (1<<MSM_ADSP_CODEC_ADPCM)|(1<<MSM_ADSP_CODEC_YADPCM)| \
1532 (1<<MSM_ADSP_CODEC_EVRC)|(1<<MSM_ADSP_CODEC_QCELP))
1533#define DEC1_FORMAT ((1<<MSM_ADSP_CODEC_MP3)| \
1534 (1<<MSM_ADSP_CODEC_AAC)|(1<<MSM_ADSP_CODEC_WMA)| \
1535 (1<<MSM_ADSP_CODEC_WMAPRO)|(1<<MSM_ADSP_CODEC_AMRWB)| \
1536 (1<<MSM_ADSP_CODEC_AMRNB)|(1<<MSM_ADSP_CODEC_WAV)| \
1537 (1<<MSM_ADSP_CODEC_ADPCM)|(1<<MSM_ADSP_CODEC_YADPCM)| \
1538 (1<<MSM_ADSP_CODEC_EVRC)|(1<<MSM_ADSP_CODEC_QCELP))
1539#define DEC2_FORMAT ((1<<MSM_ADSP_CODEC_MP3)| \
1540 (1<<MSM_ADSP_CODEC_AAC)|(1<<MSM_ADSP_CODEC_WMA)| \
1541 (1<<MSM_ADSP_CODEC_WMAPRO)|(1<<MSM_ADSP_CODEC_AMRWB)| \
1542 (1<<MSM_ADSP_CODEC_AMRNB)|(1<<MSM_ADSP_CODEC_WAV)| \
1543 (1<<MSM_ADSP_CODEC_ADPCM)|(1<<MSM_ADSP_CODEC_YADPCM)| \
1544 (1<<MSM_ADSP_CODEC_EVRC)|(1<<MSM_ADSP_CODEC_QCELP))
1545#define DEC3_FORMAT ((1<<MSM_ADSP_CODEC_MP3)| \
1546 (1<<MSM_ADSP_CODEC_AAC)|(1<<MSM_ADSP_CODEC_WMA)| \
1547 (1<<MSM_ADSP_CODEC_WMAPRO)|(1<<MSM_ADSP_CODEC_AMRWB)| \
1548 (1<<MSM_ADSP_CODEC_AMRNB)|(1<<MSM_ADSP_CODEC_WAV)| \
1549 (1<<MSM_ADSP_CODEC_ADPCM)|(1<<MSM_ADSP_CODEC_YADPCM)| \
1550 (1<<MSM_ADSP_CODEC_EVRC)|(1<<MSM_ADSP_CODEC_QCELP))
1551#define DEC4_FORMAT (1<<MSM_ADSP_CODEC_MIDI)
1552
1553static unsigned int dec_concurrency_table[] = {
1554 /* Audio LP */
1555 (DEC0_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DMA)), 0,
1556 0, 0, 0,
1557
1558 /* Concurrency 1 */
1559 (DEC0_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1560 (DEC1_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1561 (DEC2_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1562 (DEC3_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1563 (DEC4_FORMAT),
1564
1565 /* Concurrency 2 */
1566 (DEC0_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1567 (DEC1_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1568 (DEC2_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1569 (DEC3_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1570 (DEC4_FORMAT),
1571
1572 /* Concurrency 3 */
1573 (DEC0_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1574 (DEC1_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1575 (DEC2_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1576 (DEC3_FORMAT|(1<<MSM_ADSP_MODE_NONTUNNEL)|(1<<MSM_ADSP_OP_DM)),
1577 (DEC4_FORMAT),
1578
1579 /* Concurrency 4 */
1580 (DEC0_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1581 (DEC1_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1582 (DEC2_FORMAT|(1<<MSM_ADSP_MODE_NONTUNNEL)|(1<<MSM_ADSP_OP_DM)),
1583 (DEC3_FORMAT|(1<<MSM_ADSP_MODE_NONTUNNEL)|(1<<MSM_ADSP_OP_DM)),
1584 (DEC4_FORMAT),
1585
1586 /* Concurrency 5 */
1587 (DEC0_FORMAT|(1<<MSM_ADSP_MODE_TUNNEL)|(1<<MSM_ADSP_OP_DM)),
1588 (DEC1_FORMAT|(1<<MSM_ADSP_MODE_NONTUNNEL)|(1<<MSM_ADSP_OP_DM)),
1589 (DEC2_FORMAT|(1<<MSM_ADSP_MODE_NONTUNNEL)|(1<<MSM_ADSP_OP_DM)),
1590 (DEC3_FORMAT|(1<<MSM_ADSP_MODE_NONTUNNEL)|(1<<MSM_ADSP_OP_DM)),
1591 (DEC4_FORMAT),
1592
1593 /* Concurrency 6 */
1594 (DEC0_FORMAT|(1<<MSM_ADSP_MODE_NONTUNNEL)|(1<<MSM_ADSP_OP_DM)),
1595 0, 0, 0, 0,
1596
1597 /* Concurrency 7 */
1598 (DEC0_FORMAT|(1<<MSM_ADSP_MODE_NONTUNNEL)|(1<<MSM_ADSP_OP_DM)),
1599 (DEC1_FORMAT|(1<<MSM_ADSP_MODE_NONTUNNEL)|(1<<MSM_ADSP_OP_DM)),
1600 (DEC2_FORMAT|(1<<MSM_ADSP_MODE_NONTUNNEL)|(1<<MSM_ADSP_OP_DM)),
1601 (DEC3_FORMAT|(1<<MSM_ADSP_MODE_NONTUNNEL)|(1<<MSM_ADSP_OP_DM)),
1602 (DEC4_FORMAT),
1603};
1604
1605#define DEC_INFO(name, queueid, decid, nr_codec) { .module_name = name, \
1606 .module_queueid = queueid, .module_decid = decid, \
1607 .nr_codec_support = nr_codec}
1608
1609static struct msm_adspdec_info dec_info_list[] = {
1610 DEC_INFO("AUDPLAY0TASK", 13, 0, 11), /* AudPlay0BitStreamCtrlQueue */
1611 DEC_INFO("AUDPLAY1TASK", 14, 1, 11), /* AudPlay1BitStreamCtrlQueue */
1612 DEC_INFO("AUDPLAY2TASK", 15, 2, 11), /* AudPlay2BitStreamCtrlQueue */
1613 DEC_INFO("AUDPLAY3TASK", 16, 3, 11), /* AudPlay3BitStreamCtrlQueue */
1614 DEC_INFO("AUDPLAY4TASK", 17, 4, 1), /* AudPlay4BitStreamCtrlQueue */
1615};
1616
1617static struct msm_adspdec_database msm_device_adspdec_database = {
1618 .num_dec = ARRAY_SIZE(dec_info_list),
1619 .num_concurrency_support = (ARRAY_SIZE(dec_concurrency_table) / \
1620 ARRAY_SIZE(dec_info_list)),
1621 .dec_concurrency_table = dec_concurrency_table,
1622 .dec_info_list = dec_info_list,
1623};
1624
1625static struct platform_device msm_device_adspdec = {
1626 .name = "msm_adspdec",
1627 .id = -1,
1628 .dev = {
1629 .platform_data = &msm_device_adspdec_database
1630 },
1631};
1632
1633static struct android_pmem_platform_data android_pmem_audio_pdata = {
1634 .name = "pmem_audio",
1635 .allocator_type = PMEM_ALLOCATORTYPE_BITMAP,
1636 .cached = 0,
1637 .memory_type = MEMTYPE_EBI1,
1638};
1639
1640static struct platform_device android_pmem_audio_device = {
1641 .name = "android_pmem",
1642 .id = 2,
1643 .dev = { .platform_data = &android_pmem_audio_pdata },
1644};
1645
1646static struct android_pmem_platform_data android_pmem_pdata = {
1647 .name = "pmem",
1648 .allocator_type = PMEM_ALLOCATORTYPE_BITMAP,
1649 .cached = 1,
1650 .memory_type = MEMTYPE_EBI1,
1651};
1652static struct platform_device android_pmem_device = {
1653 .name = "android_pmem",
1654 .id = 0,
1655 .dev = { .platform_data = &android_pmem_pdata },
1656};
1657
1658static u32 msm_calculate_batt_capacity(u32 current_voltage);
1659
1660static struct msm_psy_batt_pdata msm_psy_batt_data = {
1661 .voltage_min_design = 2800,
1662 .voltage_max_design = 4300,
1663 .avail_chg_sources = AC_CHG | USB_CHG ,
1664 .batt_technology = POWER_SUPPLY_TECHNOLOGY_LION,
1665 .calculate_capacity = &msm_calculate_batt_capacity,
1666};
1667
1668static u32 msm_calculate_batt_capacity(u32 current_voltage)
1669{
1670 u32 low_voltage = msm_psy_batt_data.voltage_min_design;
1671 u32 high_voltage = msm_psy_batt_data.voltage_max_design;
1672
1673 return (current_voltage - low_voltage) * 100
1674 / (high_voltage - low_voltage);
1675}
1676
1677static struct platform_device msm_batt_device = {
1678 .name = "msm-battery",
1679 .id = -1,
1680 .dev.platform_data = &msm_psy_batt_data,
1681};
1682
Taniya Das7a22cdd2011-09-08 14:57:00 +05301683#ifdef CONFIG_MSM_CAMERA
1684static uint32_t camera_off_gpio_table[] = {
1685 GPIO_CFG(15, 0, GPIO_CFG_OUTPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
1686};
1687
1688static uint32_t camera_on_gpio_table[] = {
1689 GPIO_CFG(15, 1, GPIO_CFG_OUTPUT, GPIO_CFG_PULL_DOWN, GPIO_CFG_2MA),
1690};
1691
1692static void qrd1_camera_gpio_cfg(void)
1693{
1694
1695 int rc = 0;
1696
1697 rc = gpio_request(GPIO_CAM_5MP_SHDN_EN, "ov5640");
1698 if (rc < 0)
1699 pr_err("%s: gpio_request---GPIO_CAM_5MP_SHDN_EN failed!",
1700 __func__);
1701
1702
1703 rc = gpio_tlmm_config(GPIO_CFG(GPIO_CAM_5MP_SHDN_EN, 0,
1704 GPIO_CFG_OUTPUT, GPIO_CFG_PULL_UP,
1705 GPIO_CFG_2MA), GPIO_CFG_ENABLE);
1706 if (rc < 0) {
1707 pr_err("%s: unable to enable Power Down gpio for main"
1708 "camera!\n", __func__);
1709 gpio_free(GPIO_CAM_5MP_SHDN_EN);
1710 }
1711
1712
1713 rc = gpio_request(GPIO_CAM_5MP_RESET, "ov5640");
1714 if (rc < 0) {
1715 pr_err("%s: gpio_request---GPIO_CAM_5MP_RESET failed!",
1716 __func__);
1717 gpio_free(GPIO_CAM_5MP_SHDN_EN);
1718 }
1719
1720
1721 rc = gpio_tlmm_config(GPIO_CFG(GPIO_CAM_5MP_RESET, 0,
1722 GPIO_CFG_OUTPUT, GPIO_CFG_PULL_UP,
1723 GPIO_CFG_2MA), GPIO_CFG_ENABLE);
1724 if (rc < 0) {
1725 pr_err("%s: unable to enable reset gpio for main camera!\n",
1726 __func__);
1727 gpio_free(GPIO_CAM_5MP_RESET);
1728 }
1729
1730 rc = gpio_request(GPIO_CAM_3MP_PWDN, "ov7692");
1731 if (rc < 0)
1732 pr_err("%s: gpio_request---GPIO_CAM_3MP_PWDN failed!",
1733 __func__);
1734
1735 rc = gpio_tlmm_config(GPIO_CFG(GPIO_CAM_3MP_PWDN, 0,
1736 GPIO_CFG_OUTPUT, GPIO_CFG_PULL_UP,
1737 GPIO_CFG_2MA), GPIO_CFG_ENABLE);
1738 if (rc < 0) {
1739 pr_err("%s: unable to enable Power Down gpio for front"
1740 "camera!\n", __func__);
1741 gpio_free(GPIO_CAM_3MP_PWDN);
1742 }
1743
1744 gpio_direction_output(GPIO_CAM_5MP_SHDN_EN, 1);
1745 gpio_direction_output(GPIO_CAM_5MP_RESET, 1);
1746 gpio_direction_output(GPIO_CAM_3MP_PWDN, 1);
1747}
1748
1749#endif
Pankaj Kumar27c02642011-09-22 15:55:55 +05301750static struct regulator_bulk_data regs_camera[] = {
1751 { .supply = "msme1", .min_uV = 1800000, .max_uV = 1800000 },
1752 { .supply = "gp2", .min_uV = 2850000, .max_uV = 2850000 },
1753 { .supply = "usb2", .min_uV = 1800000, .max_uV = 1800000 },
1754};
1755
1756static void __init msm_camera_vreg_init(void)
Taniya Das7a22cdd2011-09-08 14:57:00 +05301757{
1758 int rc;
1759
Pankaj Kumar27c02642011-09-22 15:55:55 +05301760 rc = regulator_bulk_get(NULL, ARRAY_SIZE(regs_camera), regs_camera);
1761 if (rc) {
1762 pr_err("%s: could not get regulators: %d\n", __func__, rc);
1763 return;
Taniya Das7a22cdd2011-09-08 14:57:00 +05301764 }
1765
Pankaj Kumar27c02642011-09-22 15:55:55 +05301766 rc = regulator_bulk_set_voltage(ARRAY_SIZE(regs_camera), regs_camera);
1767 if (rc) {
1768 pr_err("%s: could not set voltages: %d\n", __func__, rc);
1769 return;
Taniya Das7a22cdd2011-09-08 14:57:00 +05301770 }
1771}
1772
Pankaj Kumar27c02642011-09-22 15:55:55 +05301773static void msm_camera_vreg_config(int vreg_en)
1774{
1775 int rc = vreg_en ?
1776 regulator_bulk_enable(ARRAY_SIZE(regs_camera), regs_camera) :
1777 regulator_bulk_disable(ARRAY_SIZE(regs_camera), regs_camera);
1778
1779 if (rc)
1780 pr_err("%s: could not %sable regulators: %d\n",
1781 __func__, vreg_en ? "en" : "dis", rc);
1782}
Taniya Das7a22cdd2011-09-08 14:57:00 +05301783static int config_gpio_table(uint32_t *table, int len)
1784{
1785 int rc = 0, i = 0;
1786
1787 for (i = 0; i < len; i++) {
1788 rc = gpio_tlmm_config(table[i], GPIO_CFG_ENABLE);
1789 if (rc) {
1790 pr_err("%s not able to get gpio\n", __func__);
1791 for (i--; i >= 0; i--)
1792 gpio_tlmm_config(camera_off_gpio_table[i],
1793 GPIO_CFG_ENABLE);
1794 break;
1795 }
1796 }
1797 return rc;
1798}
1799
1800static int config_camera_on_gpios_rear(void)
1801{
1802 int rc = 0;
1803
1804 msm_camera_vreg_config(1);
1805
1806 rc = config_gpio_table(camera_on_gpio_table,
1807 ARRAY_SIZE(camera_on_gpio_table));
1808 if (rc < 0) {
1809 pr_err("%s: CAMSENSOR gpio table request"
1810 "failed\n", __func__);
1811 return rc;
1812 }
1813
1814 return rc;
1815}
1816
1817static void config_camera_off_gpios_rear(void)
1818{
1819 msm_camera_vreg_config(0);
1820 config_gpio_table(camera_off_gpio_table,
1821 ARRAY_SIZE(camera_off_gpio_table));
1822}
1823
1824static int config_camera_on_gpios_front(void)
1825{
1826 int rc = 0;
1827
1828 msm_camera_vreg_config(1);
1829
1830 rc = config_gpio_table(camera_on_gpio_table,
1831 ARRAY_SIZE(camera_on_gpio_table));
1832 if (rc < 0) {
1833 pr_err("%s: CAMSENSOR gpio table request"
1834 "failed\n", __func__);
1835 return rc;
1836 }
1837
1838 return rc;
1839}
1840
1841static void config_camera_off_gpios_front(void)
1842{
1843 msm_camera_vreg_config(0);
1844
1845 config_gpio_table(camera_off_gpio_table,
1846 ARRAY_SIZE(camera_off_gpio_table));
1847}
1848
1849struct msm_camera_device_platform_data msm_camera_data_rear = {
1850 .camera_gpio_on = config_camera_on_gpios_rear,
1851 .camera_gpio_off = config_camera_off_gpios_rear,
1852 .ioext.csiphy = 0xA1000000,
1853 .ioext.csisz = 0x00100000,
1854 .ioext.csiirq = INT_CSI_IRQ_1,
1855 .ioclk.mclk_clk_rate = 24000000,
1856 .ioclk.vfe_clk_rate = 192000000,
1857 .ioext.appphy = MSM_CLK_CTL_PHYS,
1858 .ioext.appsz = MSM_CLK_CTL_SIZE,
1859};
1860
1861struct msm_camera_device_platform_data msm_camera_data_front = {
1862 .camera_gpio_on = config_camera_on_gpios_front,
1863 .camera_gpio_off = config_camera_off_gpios_front,
1864 .ioext.csiphy = 0xA0F00000,
1865 .ioext.csisz = 0x00100000,
1866 .ioext.csiirq = INT_CSI_IRQ_0,
1867 .ioclk.mclk_clk_rate = 24000000,
1868 .ioclk.vfe_clk_rate = 192000000,
1869 .ioext.appphy = MSM_CLK_CTL_PHYS,
1870 .ioext.appsz = MSM_CLK_CTL_SIZE,
1871};
1872
1873#ifdef CONFIG_OV5640
1874static struct msm_camera_sensor_platform_info ov5640_sensor_info = {
1875 .mount_angle = 90
1876};
1877
1878static struct msm_camera_sensor_flash_src msm_flash_src_ov5640 = {
1879 .flash_sr_type = MSM_CAMERA_FLASH_SRC_LED,
1880 ._fsrc.led_src.led_name = "flashlight",
1881 ._fsrc.led_src.led_name_len = 10,
1882};
1883
1884static struct msm_camera_sensor_flash_data flash_ov5640 = {
1885 .flash_type = MSM_CAMERA_FLASH_LED,
1886 .flash_src = &msm_flash_src_ov5640,
1887};
1888
1889static struct msm_camera_sensor_info msm_camera_sensor_ov5640_data = {
1890 .sensor_name = "ov5640",
1891 .sensor_reset_enable = 1,
1892 .sensor_reset = GPIO_CAM_5MP_RESET,
1893 .sensor_pwd = GPIO_CAM_5MP_SHDN_EN,
1894 .vcm_pwd = 0,
1895 .vcm_enable = 0,
1896 .pdata = &msm_camera_data_rear,
1897 .flash_data = &flash_ov5640,
1898 .sensor_platform_info = &ov5640_sensor_info,
1899 .csi_if = 1,
1900};
1901
1902static struct platform_device msm_camera_sensor_ov5640 = {
1903 .name = "msm_camera_ov5640",
1904 .dev = {
1905 .platform_data = &msm_camera_sensor_ov5640_data,
1906 },
1907};
1908#endif
1909
1910#ifdef CONFIG_WEBCAM_OV7692_QRD
1911static struct msm_camera_sensor_platform_info ov7692_sensor_7627a_info = {
1912 .mount_angle = 90
1913};
1914
1915static struct msm_camera_sensor_flash_data flash_ov7692 = {
1916 .flash_type = MSM_CAMERA_FLASH_NONE,
1917};
1918
1919static struct msm_camera_sensor_info msm_camera_sensor_ov7692_data = {
1920 .sensor_name = "ov7692",
1921 .sensor_reset_enable = 0,
1922 .sensor_reset = 0,
1923 .sensor_pwd = GPIO_CAM_3MP_PWDN,
1924 .vcm_pwd = 0,
1925 .vcm_enable = 0,
1926 .pdata = &msm_camera_data_front,
1927 .flash_data = &flash_ov7692,
1928 .sensor_platform_info = &ov7692_sensor_7627a_info,
1929 .csi_if = 1,
1930};
1931
1932static struct platform_device msm_camera_sensor_ov7692 = {
1933 .name = "msm_camera_ov7692",
1934 .dev = {
1935 .platform_data = &msm_camera_sensor_ov7692_data,
1936 },
1937};
1938#endif
1939
1940static struct i2c_board_info i2c_camera_devices[] = {
1941 #ifdef CONFIG_OV5640
1942 {
1943 I2C_BOARD_INFO("ov5640", 0x78 >> 1),
1944 },
1945 #endif
1946 #ifdef CONFIG_WEBCAM_OV7692_QRD
1947 {
1948 I2C_BOARD_INFO("ov7692", 0x78),
1949 },
1950 #endif
1951};
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301952static struct platform_device *qrd1_devices[] __initdata = {
1953 &msm_device_dmov,
1954 &msm_device_smd,
1955 &msm_device_uart1,
1956 &msm_device_uart_dm1,
1957 &msm_gsbi0_qup_i2c_device,
1958 &msm_gsbi1_qup_i2c_device,
1959 &msm_device_otg,
1960 &msm_device_gadget_peripheral,
1961 &android_usb_device,
1962 &android_pmem_device,
1963 &android_pmem_adsp_device,
Taniya Das0a5303a2011-08-23 18:47:48 +05301964 &msm_fb_device,
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301965 &android_pmem_audio_device,
1966 &msm_device_snd,
1967 &msm_device_adspdec,
1968 &msm_batt_device,
Taniya Das7a22cdd2011-09-08 14:57:00 +05301969#ifdef CONFIG_OV5640
1970 &msm_camera_sensor_ov5640,
1971#endif
1972#ifdef CONFIG_WEBCAM_OV7692_QRD
1973 &msm_camera_sensor_ov7692,
1974#endif
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301975 &msm_kgsl_3d0,
1976#ifdef CONFIG_BT
1977 &msm_bt_power_device,
1978#endif
Taniya Das0a5303a2011-08-23 18:47:48 +05301979 &mipi_dsi_truly_panel_device,
Taniya Dasc98bfbc2011-08-23 09:58:55 +05301980 &msm_wlan_ar6000_pm_device,
1981 &asoc_msm_pcm,
1982 &asoc_msm_dai0,
1983 &asoc_msm_dai1,
1984};
1985
1986static unsigned pmem_kernel_ebi1_size = PMEM_KERNEL_EBI1_SIZE;
1987static int __init pmem_kernel_ebi1_size_setup(char *p)
1988{
1989 pmem_kernel_ebi1_size = memparse(p, NULL);
1990 return 0;
1991}
1992early_param("pmem_kernel_ebi1_size", pmem_kernel_ebi1_size_setup);
1993
1994static unsigned pmem_audio_size = MSM_PMEM_AUDIO_SIZE;
1995static int __init pmem_audio_size_setup(char *p)
1996{
1997 pmem_audio_size = memparse(p, NULL);
1998 return 0;
1999}
2000early_param("pmem_audio_size", pmem_audio_size_setup);
2001
2002static void __init msm_msm7627a_allocate_memory_regions(void)
2003{
Taniya Das0a5303a2011-08-23 18:47:48 +05302004 void *addr;
2005 unsigned long size;
2006
2007 size = fb_size ? : MSM_FB_SIZE;
2008 addr = alloc_bootmem_align(size, 0x1000);
2009 msm_fb_resources[0].start = __pa(addr);
2010 msm_fb_resources[0].end = msm_fb_resources[0].start + size - 1;
2011 pr_info("allocating %lu bytes at %p (%lx physical) for fb\n", size,
2012 addr, __pa(addr));
Taniya Dasc98bfbc2011-08-23 09:58:55 +05302013}
2014
2015static struct memtype_reserve msm7627a_reserve_table[] __initdata = {
2016 [MEMTYPE_SMI] = {
2017 },
2018 [MEMTYPE_EBI0] = {
2019 .flags = MEMTYPE_FLAGS_1M_ALIGN,
2020 },
2021 [MEMTYPE_EBI1] = {
2022 .flags = MEMTYPE_FLAGS_1M_ALIGN,
2023 },
2024};
2025
Taniya Das0a5303a2011-08-23 18:47:48 +05302026static struct msm_panel_common_pdata mdp_pdata = {
2027 .gpio = 97,
2028 .mdp_rev = MDP_REV_303,
2029};
2030
2031#define GPIO_LCDC_BRDG_PD 128
2032#define GPIO_LCDC_BRDG_RESET_N 129
2033#define GPIO_LCD_DSI_SEL 125
2034
2035static unsigned mipi_dsi_gpio[] = {
2036 GPIO_CFG(GPIO_LCDC_BRDG_RESET_N, 0, GPIO_CFG_OUTPUT,
2037 GPIO_CFG_NO_PULL, GPIO_CFG_2MA), /* LCDC_BRDG_RESET_N */
2038 GPIO_CFG(GPIO_LCDC_BRDG_PD, 0, GPIO_CFG_OUTPUT,
2039 GPIO_CFG_NO_PULL, GPIO_CFG_2MA), /* LCDC_BRDG_PD */
2040};
2041
2042static unsigned lcd_dsi_sel_gpio[] = {
2043 GPIO_CFG(GPIO_LCD_DSI_SEL, 0, GPIO_CFG_OUTPUT, GPIO_CFG_PULL_UP,
2044 GPIO_CFG_2MA),
2045};
2046
2047enum {
2048 DSI_SINGLE_LANE = 1,
2049 DSI_TWO_LANES,
2050};
2051
2052static int msm_fb_get_lane_config(void)
2053{
2054 pr_info("DSI_TWO_LANES\n");
2055 return DSI_TWO_LANES;
2056}
2057
2058static int mipi_truly_sel_mode(int video_mode)
2059{
2060 int rc = 0;
2061
2062 rc = gpio_request(GPIO_LCD_DSI_SEL, "lcd_dsi_sel");
2063 if (rc < 0)
2064 goto gpio_error;
2065
2066 rc = gpio_tlmm_config(lcd_dsi_sel_gpio[0], GPIO_CFG_ENABLE);
2067 if (rc)
2068 goto gpio_error;
2069
2070 rc = gpio_direction_output(GPIO_LCD_DSI_SEL, 1);
2071 if (!rc) {
2072 gpio_set_value_cansleep(GPIO_LCD_DSI_SEL, video_mode);
2073 return rc;
2074 } else {
2075 goto gpio_error;
2076 }
2077
2078gpio_error:
2079 pr_err("mipi_truly_sel_mode failed\n");
2080 gpio_free(GPIO_LCD_DSI_SEL);
2081 return rc;
2082}
2083
2084static int msm_fb_dsi_client_qrd1_reset(void)
2085{
2086 int rc = 0;
2087
2088 rc = gpio_request(GPIO_LCDC_BRDG_RESET_N, "lcdc_brdg_reset_n");
2089 if (rc < 0) {
2090 pr_err("failed to request lcd brdg reset_n\n");
2091 return rc;
2092 }
2093
2094 rc = gpio_tlmm_config(mipi_dsi_gpio[0], GPIO_CFG_ENABLE);
2095 if (rc < 0) {
2096 pr_err("Failed to enable LCDC Bridge reset enable\n");
2097 return rc;
2098 }
2099
2100 rc = gpio_direction_output(GPIO_LCDC_BRDG_RESET_N, 1);
2101 if (rc < 0) {
2102 pr_err("Failed GPIO bridge pd\n");
2103 gpio_free(GPIO_LCDC_BRDG_RESET_N);
2104 return rc;
2105 }
2106
2107 mipi_truly_sel_mode(1);
2108
2109 return rc;
2110}
2111
2112static int msm_fb_dsi_client_reset(void)
2113{
2114 int rc = 0;
2115
2116 rc = msm_fb_dsi_client_qrd1_reset();
2117 return rc;
2118}
2119
2120static int dsi_gpio_initialized;
2121
2122static int mipi_dsi_panel_qrd1_power(int on)
2123{
2124 int rc = 0;
2125
2126 if (!dsi_gpio_initialized) {
2127 rc = gpio_request(GPIO_BACKLIGHT_EN, "gpio_bkl_en");
2128 if (rc < 0)
2129 return rc;
2130
Jeevan Shriram72e4cc62011-11-10 14:57:22 +05302131 rc = gpio_tlmm_config(GPIO_CFG(GPIO_BACKLIGHT_EN, 0,
2132 GPIO_CFG_OUTPUT, GPIO_CFG_NO_PULL, GPIO_CFG_2MA),
2133 GPIO_CFG_ENABLE);
2134 if (rc < 0) {
2135 pr_err("failed GPIO_BACKLIGHT_EN tlmm config\n");
2136 return rc;
2137 }
2138
Taniya Das0a5303a2011-08-23 18:47:48 +05302139 rc = gpio_direction_output(GPIO_BACKLIGHT_EN, 1);
2140 if (rc < 0) {
2141 pr_err("failed to enable backlight\n");
2142 gpio_free(GPIO_BACKLIGHT_EN);
2143 return rc;
2144 }
2145 dsi_gpio_initialized = 1;
2146 }
2147
2148 gpio_set_value_cansleep(GPIO_BACKLIGHT_EN, !!on);
2149
2150 if (!on) {
2151 gpio_set_value_cansleep(GPIO_LCDC_BRDG_RESET_N, 1);
2152 msleep(20);
2153 gpio_set_value_cansleep(GPIO_LCDC_BRDG_RESET_N, 0);
2154 msleep(20);
2155 gpio_set_value_cansleep(GPIO_LCDC_BRDG_RESET_N, 1);
2156
2157 }
2158
2159 return rc;
2160}
2161
2162static int mipi_dsi_panel_power(int on)
2163{
2164 int rc = 0;
2165
2166 rc = mipi_dsi_panel_qrd1_power(on);
2167 return rc;
2168}
2169
2170#define MDP_303_VSYNC_GPIO 97
2171
2172#ifdef CONFIG_FB_MSM_MDP303
2173static struct mipi_dsi_platform_data mipi_dsi_pdata = {
2174 .vsync_gpio = MDP_303_VSYNC_GPIO,
2175 .dsi_power_save = mipi_dsi_panel_power,
2176 .dsi_client_reset = msm_fb_dsi_client_reset,
2177 .get_lane_config = msm_fb_get_lane_config,
2178};
2179#endif
2180
2181static void __init msm_fb_add_devices(void)
2182{
2183 msm_fb_register_device("mdp", &mdp_pdata);
2184 msm_fb_register_device("mipi_dsi", &mipi_dsi_pdata);
2185}
2186
Taniya Dasc98bfbc2011-08-23 09:58:55 +05302187static void __init size_pmem_devices(void)
2188{
2189#ifdef CONFIG_ANDROID_PMEM
2190 android_pmem_adsp_pdata.size = pmem_adsp_size;
2191 android_pmem_pdata.size = pmem_mdp_size;
2192 android_pmem_audio_pdata.size = pmem_audio_size;
2193#endif
2194}
2195
2196static void __init reserve_memory_for(struct android_pmem_platform_data *p)
2197{
2198 msm7627a_reserve_table[p->memory_type].size += p->size;
2199}
2200
2201static void __init reserve_pmem_memory(void)
2202{
2203#ifdef CONFIG_ANDROID_PMEM
2204 reserve_memory_for(&android_pmem_adsp_pdata);
2205 reserve_memory_for(&android_pmem_pdata);
2206 reserve_memory_for(&android_pmem_audio_pdata);
2207 msm7627a_reserve_table[MEMTYPE_EBI1].size += pmem_kernel_ebi1_size;
2208#endif
2209}
2210
2211static void __init msm7627a_calculate_reserve_sizes(void)
2212{
2213 size_pmem_devices();
2214 reserve_pmem_memory();
2215}
2216
2217static int msm7627a_paddr_to_memtype(unsigned int paddr)
2218{
2219 return MEMTYPE_EBI1;
2220}
2221
2222static struct reserve_info msm7627a_reserve_info __initdata = {
2223 .memtype_reserve_table = msm7627a_reserve_table,
2224 .calculate_reserve_sizes = msm7627a_calculate_reserve_sizes,
2225 .paddr_to_memtype = msm7627a_paddr_to_memtype,
2226};
2227
2228static void __init msm7627a_reserve(void)
2229{
2230 reserve_info = &msm7627a_reserve_info;
2231 msm_reserve();
2232}
2233
2234static void __init msm_device_i2c_init(void)
2235{
2236 msm_gsbi0_qup_i2c_device.dev.platform_data = &msm_gsbi0_qup_i2c_pdata;
2237 msm_gsbi1_qup_i2c_device.dev.platform_data = &msm_gsbi1_qup_i2c_pdata;
2238}
2239
2240static struct msm_handset_platform_data hs_platform_data = {
2241 .hs_name = "7k_handset",
2242 .pwr_key_delay_ms = 500, /* 0 will disable end key */
2243};
2244
2245static struct platform_device hs_pdev = {
2246 .name = "msm-handset",
2247 .id = -1,
2248 .dev = {
2249 .platform_data = &hs_platform_data,
2250 },
2251};
2252
Pankaj Kumar3cec0582011-11-18 11:13:29 +05302253static struct platform_device msm_proccomm_regulator_dev = {
2254 .name = PROCCOMM_REGULATOR_DEV_NAME,
2255 .id = -1,
2256 .dev = {
2257 .platform_data = &msm7x27a_proccomm_regulator_data
2258 }
2259};
2260
2261static void __init msm7627a_init_regulators(void)
2262{
2263 int rc = platform_device_register(&msm_proccomm_regulator_dev);
2264 if (rc)
2265 pr_err("%s: could not register regulator device: %d\n",
2266 __func__, rc);
2267}
2268
Taniya Dasc98bfbc2011-08-23 09:58:55 +05302269#define UART1DM_RX_GPIO 45
2270static void __init msm_qrd1_init(void)
2271{
2272 msm7x2x_misc_init();
Pankaj Kumar3cec0582011-11-18 11:13:29 +05302273 msm7627a_init_regulators();
Taniya Dasc98bfbc2011-08-23 09:58:55 +05302274 msm_device_i2c_init();
Taniya Das7a22cdd2011-09-08 14:57:00 +05302275 qrd1_camera_gpio_cfg();
Taniya Dasc98bfbc2011-08-23 09:58:55 +05302276#ifdef CONFIG_SERIAL_MSM_HS
2277 msm_uart_dm1_pdata.wakeup_irq = gpio_to_irq(UART1DM_RX_GPIO);
2278 msm_device_uart_dm1.dev.platform_data = &msm_uart_dm1_pdata;
2279#endif
2280
2281#ifdef CONFIG_USB_MSM_OTG_72K
2282 msm_otg_pdata.swfi_latency = msm7627a_pm_data
2283 [MSM_PM_SLEEP_MODE_RAMP_DOWN_AND_WAIT_FOR_INTERRUPT].latency;
2284 msm_device_otg.dev.platform_data = &msm_otg_pdata;
2285#endif
2286 msm_device_gadget_peripheral.dev.platform_data =
Taniya Das7a22cdd2011-09-08 14:57:00 +05302287 &msm_gadget_pdata;
Taniya Dasc98bfbc2011-08-23 09:58:55 +05302288 platform_add_devices(qrd1_devices,
Taniya Das7a22cdd2011-09-08 14:57:00 +05302289 ARRAY_SIZE(qrd1_devices));
Chintan Pandyacf467fc2011-12-01 17:11:11 +05302290 msm7627a_init_mmc();
2291
Taniya Dasc98bfbc2011-08-23 09:58:55 +05302292#ifdef CONFIG_USB_EHCI_MSM_72K
2293 msm7627a_init_host();
2294#endif
2295 msm_pm_set_platform_data(msm7627a_pm_data,
2296 ARRAY_SIZE(msm7627a_pm_data));
Maheshkumar Sivasubramanianc6c55032011-10-25 16:01:32 -06002297 BUG_ON(msm_pm_boot_init(&msm_pm_boot_pdata));
Murali Nalajalaa1827842011-11-13 14:12:39 +05302298
Taniya Das0a5303a2011-08-23 18:47:48 +05302299 msm_fb_add_devices();
Taniya Dasc98bfbc2011-08-23 09:58:55 +05302300
2301#if defined(CONFIG_BT) && defined(CONFIG_MARIMBA_CORE)
2302 i2c_register_board_info(MSM_GSBI1_QUP_I2C_BUS_ID,
Taniya Das7a22cdd2011-09-08 14:57:00 +05302303 bahama_devices,
2304 ARRAY_SIZE(bahama_devices));
Taniya Dasc98bfbc2011-08-23 09:58:55 +05302305 bt_power_init();
2306#endif
Taniya Dasda408822011-09-06 12:54:06 +05302307
Pankaj Kumar27c02642011-09-22 15:55:55 +05302308 msm_camera_vreg_init();
Taniya Das7a22cdd2011-09-08 14:57:00 +05302309 i2c_register_board_info(MSM_GSBI0_QUP_I2C_BUS_ID, i2c_camera_devices,
2310 ARRAY_SIZE(i2c_camera_devices));
2311
Taniya Dasda408822011-09-06 12:54:06 +05302312#if defined(CONFIG_TOUCHSCREEN_SYNAPTICS_RMI4_I2C) || \
2313 defined(CONFIG_TOUCHSCREEN_SYNAPTICS_RMI4_I2C_MODULE)
2314 i2c_register_board_info(MSM_GSBI1_QUP_I2C_BUS_ID,
2315 synaptic_i2c_clearpad3k,
2316 ARRAY_SIZE(synaptic_i2c_clearpad3k));
2317#endif
Taniya Dasc98bfbc2011-08-23 09:58:55 +05302318 platform_device_register(&hs_pdev);
2319
2320#ifdef CONFIG_MSM_RPC_VIBRATOR
2321 msm_init_pmic_vibrator();
2322#endif
2323}
2324
2325static void __init qrd7627a_init_early(void)
2326{
2327 msm_msm7627a_allocate_memory_regions();
2328}
2329
2330MACHINE_START(MSM7627A_QRD1, "QRD MSM7627a QRD1")
2331 .boot_params = PHYS_OFFSET + 0x100,
2332 .map_io = msm_common_io_init,
2333 .reserve = msm7627a_reserve,
2334 .init_irq = msm_init_irq,
2335 .init_machine = msm_qrd1_init,
2336 .timer = &msm_timer,
2337 .init_early = qrd7627a_init_early,
Pankaj Kumarbf8a2a32011-10-21 11:47:21 +05302338 .handle_irq = vic_handle_irq,
Taniya Dasc98bfbc2011-08-23 09:58:55 +05302339MACHINE_END