1 --- a/arch/arm/mach-omap2/board-n8x0.c
2 +++ b/arch/arm/mach-omap2/board-n8x0.c
4 #include <linux/spi/spi.h>
5 #include <linux/usb/musb.h>
6 #include <sound/tlv320aic3x.h>
7 +#include <linux/input.h>
8 +#include <linux/i2c/lm8323.h>
9 +#include <linux/spi/tsc2005.h>
11 #include <asm/mach/arch.h>
12 #include <asm/mach-types.h>
15 #include <plat/serial.h>
16 #include <plat/cbus.h>
17 +#include <plat/gpio-switch.h>
21 @@ -43,6 +47,221 @@ static int slot1_cover_open;
22 static int slot2_cover_open;
23 static struct device *mmc_device;
25 +/* We map the FN key as LALT to workaround an X keycode problem.
26 + * The XKB map needs to be adjusted to support this. */
27 +#define MAP_FN_AS_LEFTALT
29 +static s16 rx44_keymap[LM8323_KEYMAP_SIZE] = {
34 + [0x05] = KEY_BACKSPACE,
46 + [0x14] = KEY_APOSTROPHE,
53 + [0x1c] = KEY_LEFTSHIFT, /* Actually, this is both shift keys */
57 + [0x22] = KEY_SEMICOLON,
60 +#ifdef MAP_FN_AS_LEFTALT
61 + [0x2b] = KEY_LEFTALT,
69 + [0x32] = KEY_RIGHTCTRL,
73 + [0x3c] = KEY_COMPOSE,
89 + [0x75] = KEY_KPENTER,
92 +static struct lm8323_platform_data lm8323_pdata = {
93 + .repeat = 0, /* Repeat is handled in userspace for now. */
94 + .keymap = rx44_keymap,
97 + .debounce_time = 12,
100 + .name = "Internal keyboard",
101 + .pwm_names[0] = "n810::keyboard",
102 + .pwm_names[1] = "n810::cover",
105 +#define OMAP_TAG_NOKIA_BT 0x4e01
107 +struct omap_bluetooth_config {
110 + u8 host_wakeup_gpio;
117 +static struct platform_device n8x0_bt_device = {
120 + .num_resources = 0,
123 +void __init n8x0_bt_init(void)
125 + const struct omap_bluetooth_config *bt_config;
127 + bt_config = (void *) omap_get_config(OMAP_TAG_NOKIA_BT,
128 + struct omap_bluetooth_config);
129 + n8x0_bt_device.dev.platform_data = (void *) bt_config;
130 + if (platform_device_register(&n8x0_bt_device) < 0)
134 +#define RX51_TSC2005_RESET_GPIO 94
135 +#define RX51_TSC2005_IRQ_GPIO 106
137 +#ifdef CONFIG_TOUCHSCREEN_TSC2005
138 +static struct tsc2005_platform_data tsc2005_config;
139 +static void rx51_tsc2005_set_reset(bool enable)
141 + gpio_set_value(RX51_TSC2005_RESET_GPIO, enable);
144 +static struct omap2_mcspi_device_config tsc2005_mcspi_config = {
146 + .single_channel = 1,
150 +static void __init tsc2005_set_config(void)
152 + const struct omap_lcd_config *conf;
154 + conf = omap_get_config(OMAP_TAG_LCD, struct omap_lcd_config);
155 + if (conf != NULL) {
156 +#ifdef CONFIG_TOUCHSCREEN_TSC2005
157 + if (strcmp(conf->panel_name, "lph8923") == 0) {
158 + tsc2005_config.ts_x_plate_ohm = 180;
159 + tsc2005_config.ts_hw_avg = 0;
160 + tsc2005_config.ts_ignore_last = 0;
161 + tsc2005_config.ts_touch_pressure = 1500;
162 + tsc2005_config.ts_stab_time = 100;
163 + tsc2005_config.ts_pressure_max = 2048;
164 + tsc2005_config.ts_pressure_fudge = 2;
165 + tsc2005_config.ts_x_max = 4096;
166 + tsc2005_config.ts_x_fudge = 4;
167 + tsc2005_config.ts_y_max = 4096;
168 + tsc2005_config.ts_y_fudge = 7;
169 + tsc2005_config.set_reset = rx51_tsc2005_set_reset;
170 + } else if (strcmp(conf->panel_name, "ls041y3") == 0) {
171 + tsc2005_config.ts_x_plate_ohm = 280;
172 + tsc2005_config.ts_hw_avg = 0;
173 + tsc2005_config.ts_ignore_last = 0;
174 + tsc2005_config.ts_touch_pressure = 1500;
175 + tsc2005_config.ts_stab_time = 1000;
176 + tsc2005_config.ts_pressure_max = 2048;
177 + tsc2005_config.ts_pressure_fudge = 2;
178 + tsc2005_config.ts_x_max = 4096;
179 + tsc2005_config.ts_x_fudge = 4;
180 + tsc2005_config.ts_y_max = 4096;
181 + tsc2005_config.ts_y_fudge = 7;
182 + tsc2005_config.set_reset = rx51_tsc2005_set_reset;
184 + printk(KERN_ERR "Unknown panel type, set default "
185 + "touchscreen configuration\n");
186 + tsc2005_config.ts_x_plate_ohm = 200;
187 + tsc2005_config.ts_stab_time = 100;
193 +static struct omap2_mcspi_device_config mipid_mcspi_config = {
195 + .single_channel = 1,
198 +extern struct mipid_platform_data n8x0_mipid_platform_data;
200 +extern void n8x0_mipid_init(void);
201 +extern void n8x0_blizzard_init(void);
203 +static struct omap_gpio_switch n8x0_gpio_switches[] __initdata = {
205 + .name = "headphone",
207 + .debounce_rising = 200,
208 + .debounce_falling = 200,
212 + .debounce_rising = 200,
213 + .debounce_falling = 200,
215 + .name = "cam_turn",
217 + .debounce_rising = 100,
218 + .debounce_falling = 100,
222 + .debounce_rising = 200,
223 + .debounce_falling = 200,
227 + .debounce_rising = 200,
228 + .debounce_falling = 200,
232 +static void __init n8x0_gpio_switches_init(void)
234 + /* The switches are actually registered through ATAG mechanism.
235 + * This just updates the parameters (thus .gpio is -1) */
236 + omap_register_gpio_switches(n8x0_gpio_switches,
237 + ARRAY_SIZE(n8x0_gpio_switches));
240 #define TUSB6010_ASYNC_CS 1
241 #define TUSB6010_SYNC_CS 4
242 #define TUSB6010_GPIO_INT 58
243 @@ -146,12 +365,29 @@ static struct omap2_mcspi_device_config
245 static struct spi_board_info n800_spi_board_info[] __initdata = {
247 + .modalias = "lcd_mipid",
250 + .max_speed_hz = 4000000,
251 + .controller_data= &mipid_mcspi_config,
252 + .platform_data = &n8x0_mipid_platform_data,
255 .modalias = "p54spi",
258 .max_speed_hz = 48000000,
259 .controller_data = &p54spi_mcspi_config,
262 + .modalias = "tsc2005",
265 + .irq = OMAP_GPIO_IRQ(RX51_TSC2005_IRQ_GPIO),
266 + .max_speed_hz = 6000000,
267 + .controller_data = &tsc2005_mcspi_config,
268 + .platform_data = &tsc2005_config,
272 #if defined(CONFIG_MTD_ONENAND_OMAP2) || \
273 @@ -727,6 +963,11 @@ static struct aic3x_pdata n810_aic33_dat
276 static struct i2c_board_info n810_i2c_board_info_2[] __initdata = {
278 + I2C_BOARD_INFO("lm8323", 0x45),
279 + .irq = OMAP_GPIO_IRQ(109),
280 + .platform_data = &lm8323_pdata,
283 I2C_BOARD_INFO("tlv320aic3x", 0x18),
284 .platform_data = &n810_aic33_data,
285 @@ -796,9 +1037,12 @@ static inline void board_serial_init(voi
286 static void __init n8x0_init_machine(void)
288 omap2420_mux_init(board_mux, OMAP_PACKAGE_ZAC);
289 + n8x0_gpio_switches_init();
293 /* FIXME: add n810 spi devices */
294 + tsc2005_set_config();
295 spi_register_board_info(n800_spi_board_info,
296 ARRAY_SIZE(n800_spi_board_info));
297 omap_register_i2c_bus(1, 400, n8x0_i2c_board_info_1,
298 @@ -808,6 +1052,8 @@ static void __init n8x0_init_machine(voi
299 i2c_register_board_info(2, n810_i2c_board_info_2,
300 ARRAY_SIZE(n810_i2c_board_info_2));
303 + n8x0_blizzard_init();
304 gpmc_onenand_init(board_onenand_data);
308 +++ b/arch/arm/mach-omap2/board-n8x0-lcd.c
311 + * linux/arch/arm/mach-omap2/board-n8x0.c
313 + * Copyright (C) 2005-2009 Nokia Corporation
314 + * Author: Juha Yrjola <juha.yrjola@nokia.com>
316 + * Modified from mach-omap2/board-generic.c
318 + * This program is free software; you can redistribute it and/or modify
319 + * it under the terms of the GNU General Public License version 2 as
320 + * published by the Free Software Foundation.
323 +#include <linux/clk.h>
324 +#include <linux/delay.h>
325 +#include <linux/gpio.h>
326 +#include <linux/omapfb.h>
328 +#include <plat/lcd_mipid.h>
329 +#include <plat/blizzard.h>
331 +#include <../drivers/cbus/tahvo.h>
333 +#define N8X0_BLIZZARD_POWERDOWN_GPIO 15
337 +static void mipid_shutdown(struct mipid_platform_data *pdata)
339 + if (pdata->nreset_gpio != -1) {
340 + pr_info("shutdown LCD\n");
341 + gpio_set_value(pdata->nreset_gpio, 0);
346 +struct mipid_platform_data n8x0_mipid_platform_data = {
347 + .shutdown = mipid_shutdown,
350 +void __init n8x0_mipid_init(void)
352 + const struct omap_lcd_config *conf;
355 + conf = omap_get_config(OMAP_TAG_LCD, struct omap_lcd_config);
356 + if (conf != NULL) {
357 + n8x0_mipid_platform_data.nreset_gpio = conf->nreset_gpio;
358 + n8x0_mipid_platform_data.data_lines = conf->data_lines;
359 + if (conf->nreset_gpio != -1) {
360 + err = gpio_request(conf->nreset_gpio, "MIPID nreset");
362 + printk(KERN_ERR "N8x0 MIPID failed to request nreset GPIO %d\n",
363 + conf->nreset_gpio);
365 + err = gpio_direction_output(conf->nreset_gpio, 1);
367 + printk(KERN_ERR "N8x0 MIPID failed to set nreset GPIO %d\n",
368 + conf->nreset_gpio);
372 + printk(KERN_INFO "N8x0 MIPID config loaded");
375 + printk(KERN_INFO "N8x0 MIPID config not provided");
379 +// Epson Blizzard LCD Controller
382 + struct clk *sys_ck;
385 +static int blizzard_get_clocks(void)
387 + blizzard.sys_ck = clk_get(0, "osc_ck");
388 + if (IS_ERR(blizzard.sys_ck)) {
389 + printk(KERN_ERR "can't get Blizzard clock\n");
390 + return PTR_ERR(blizzard.sys_ck);
395 +static unsigned long blizzard_get_clock_rate(struct device *dev)
397 + return clk_get_rate(blizzard.sys_ck);
400 +static void blizzard_enable_clocks(int enable)
403 + clk_enable(blizzard.sys_ck);
405 + clk_disable(blizzard.sys_ck);
408 +static void blizzard_power_up(struct device *dev)
410 + /* Vcore to 1.475V */
411 + tahvo_set_clear_reg_bits(0x07, 0, 0xf);
414 + blizzard_enable_clocks(1);
415 + gpio_set_value(N8X0_BLIZZARD_POWERDOWN_GPIO, 1);
418 +static void blizzard_power_down(struct device *dev)
420 + gpio_set_value(N8X0_BLIZZARD_POWERDOWN_GPIO, 0);
421 + blizzard_enable_clocks(0);
423 + /* Vcore to 1.005V */
424 + tahvo_set_clear_reg_bits(0x07, 0xf, 0);
427 +static struct blizzard_platform_data n8x0_blizzard_data = {
428 + .power_up = blizzard_power_up,
429 + .power_down = blizzard_power_down,
430 + .get_clock_rate = blizzard_get_clock_rate,
434 +void __init n8x0_blizzard_init(void)
438 + r = gpio_request(N8X0_BLIZZARD_POWERDOWN_GPIO, "Blizzard pd");
441 + printk(KERN_ERR "Can't get N8x0 Blizzard powerdown GPIO %d\n", N8X0_BLIZZARD_POWERDOWN_GPIO);
444 + gpio_direction_output(N8X0_BLIZZARD_POWERDOWN_GPIO, 1);
446 + blizzard_get_clocks();
447 + omapfb_set_ctrl_platform_data(&n8x0_blizzard_data);
449 + printk(KERN_INFO "N8x0 Blizzard initialized");
451 --- a/arch/arm/mach-omap2/Makefile
452 +++ b/arch/arm/mach-omap2/Makefile
453 @@ -177,6 +177,7 @@ obj-$(CONFIG_MACH_OMAP_3430SDP) += boar
456 obj-$(CONFIG_MACH_NOKIA_N8X0) += board-n8x0.o
457 +obj-$(CONFIG_MACH_NOKIA_N8X0) += board-n8x0-lcd.o
458 obj-$(CONFIG_MACH_NOKIA_RM680) += board-rm680.o \
462 +++ b/arch/arm/plat-omap/include/plat/cbus.h
465 + * cbus.h - CBUS platform_data definition
467 + * Copyright (C) 2004 - 2009 Nokia Corporation
469 + * Written by Felipe Balbi <felipe.balbi@nokia.com>
471 + * This file is subject to the terms and conditions of the GNU General
472 + * Public License. See the file "COPYING" in the main directory of this
473 + * archive for more details.
475 + * This program is distributed in the hope that it will be useful,
476 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
477 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
478 + * GNU General Public License for more details.
480 + * You should have received a copy of the GNU General Public License
481 + * along with this program; if not, write to the Free Software
482 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
485 +#ifndef __PLAT_CBUS_H
486 +#define __PLAT_CBUS_H
488 +#define CBUS_RETU_DEVICE_ID 0x01
489 +#define CBUS_TAHVO_DEVICE_ID 0x02
491 +struct cbus_host_platform_data {
497 +struct cbus_retu_platform_data {
503 +#endif /* __PLAT_CBUS_H */
504 --- a/arch/arm/plat-omap/include/plat/irqs.h
505 +++ b/arch/arm/plat-omap/include/plat/irqs.h
507 #define TWL_IRQ_END TWL6030_IRQ_END
510 -#define NR_IRQS TWL_IRQ_END
512 +#define OMAP_GPMC_IRQ_BASE (TWL_IRQ_END)
513 +#define OMAP_GPMC_NR_IRQS 7
514 +#define OMAP_GPMC_IRQ_END (OMAP_GPMC_IRQ_BASE + OMAP_GPMC_NR_IRQS)
516 +#define CBUS_RETU_IRQ_BASE OMAP_GPMC_IRQ_END
517 +#ifdef CONFIG_CBUS_RETU
518 +#define CBUS_RETU_NR_IRQS 16
520 +#define CBUS_RETU_NR_IRQS 0
522 +#define CBUS_RETU_IRQ_END (CBUS_RETU_IRQ_BASE + CBUS_RETU_NR_IRQS)
524 +#define NR_IRQS CBUS_RETU_IRQ_END
526 #define OMAP_IRQ_BIT(irq) (1 << ((irq) % 32))
528 --- a/arch/arm/mach-omap2/omap_hwmod_2420_data.c
529 +++ b/arch/arm/mach-omap2/omap_hwmod_2420_data.c
530 @@ -673,6 +673,7 @@ static struct omap_hwmod_ocp_if *omap242
532 static struct omap_hwmod omap2420_gpio1_hwmod = {
534 + .flags = HWMOD_INIT_NO_RESET, /* Workaround: Don't reset the n810 MIPID */
535 .mpu_irqs = omap242x_gpio1_irqs,
536 .mpu_irqs_cnt = ARRAY_SIZE(omap242x_gpio1_irqs),
537 .main_clk = "gpios_fck",