summaryrefslogtreecommitdiff
path: root/packages/linux/linux-ezx/ezx_core.patch
diff options
context:
space:
mode:
Diffstat (limited to 'packages/linux/linux-ezx/ezx_core.patch')
-rw-r--r--packages/linux/linux-ezx/ezx_core.patch15352
1 files changed, 0 insertions, 15352 deletions
diff --git a/packages/linux/linux-ezx/ezx_core.patch b/packages/linux/linux-ezx/ezx_core.patch
deleted file mode 100644
index 88867f621a..0000000000
--- a/packages/linux/linux-ezx/ezx_core.patch
+++ /dev/null
@@ -1,15352 +0,0 @@
-This is the core patch adding EZX support to the kernel
-
-Index: linux-2.6.16.5-a/arch/arm/boot/compressed/head-xscale.S
-===================================================================
---- linux-2.6.16.5-a.orig/arch/arm/boot/compressed/head-xscale.S 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/arch/arm/boot/compressed/head-xscale.S 2006-05-04 17:07:04.000000000 +0200
-@@ -54,3 +54,6 @@
- str r1, [r0, #0x18]
- #endif
-
-+#ifdef CONFIG_ARCH_EZX
-+ mov r7, #MACH_TYPE_EZX
-+#endif
-Index: linux-2.6.16.5-a/arch/arm/boot/compressed/head.S
-===================================================================
---- linux-2.6.16.5-a.orig/arch/arm/boot/compressed/head.S 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/arch/arm/boot/compressed/head.S 2006-05-04 17:07:04.000000000 +0200
-@@ -10,6 +10,7 @@
- #include <linux/config.h>
- #include <linux/linkage.h>
-
-+#define DEBUG
- /*
- * Debugging stuff
- *
-@@ -111,6 +112,11 @@
- mov r0, r0
- .endr
-
-+ inituart r10, r11
-+
-+ mov r1, #0x300 @ mach_id 0x363 is official EZX
-+ orr r1, r1, #0x63 @ bootloader JUMP doesn't set r1
-+
- b 1f
- .word 0x016f2818 @ Magic numbers to help the loader
- .word start @ absolute load/run zImage address
-@@ -137,6 +143,10 @@
- teqp pc, #0x0c000003 @ turn off interrupts
- #endif
-
-+ addruart r11
-+ mov r10, #'d'
-+ senduart r10, r11
-+
- /*
- * Note that some cache flushing and other stuff may
- * be needed here - is there an Angel SWI call for this?
-Index: linux-2.6.16.5-a/arch/arm/kernel/apm.c
-===================================================================
---- linux-2.6.16.5-a.orig/arch/arm/kernel/apm.c 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/arch/arm/kernel/apm.c 2006-05-04 17:07:04.000000000 +0200
-@@ -605,3 +605,7 @@
- wake_up_interruptible(&kapmd_wait);
- }
- EXPORT_SYMBOL(apm_queue_event);
-+
-+void pm_do_poweroff(void)
-+{ /* FIXME */
-+}
-Index: linux-2.6.16.5-a/arch/arm/mach-pxa/Kconfig
-===================================================================
---- linux-2.6.16.5-a.orig/arch/arm/mach-pxa/Kconfig 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/arch/arm/mach-pxa/Kconfig 2006-05-04 17:07:29.000000000 +0200
-@@ -1,5 +1,8 @@
- if ARCH_PXA
-
-+config PXA_EZX
-+ bool
-+
- menu "Intel PXA2xx Implementations"
-
- choice
-@@ -30,6 +33,18 @@
- SL-C3000 (Spitz), SL-C3100 (Borzoi) or SL-C6000x (Tosa)
- handheld computer.
-
-+config PXA_EZX_E680
-+ bool "Motorola E680 GSM Phone"
-+ select PXA27x
-+ select IWMMXT
-+ select PXA_EZX
-+
-+config PXA_EZX_A780
-+ bool "Motorola A780 GSM Phone"
-+ select PXA27x
-+ select IWMMXT
-+ select PXA_EZX
-+
- endchoice
-
- if PXA_SHARPSL
-Index: linux-2.6.16.5-a/arch/arm/mach-pxa/Makefile
-===================================================================
---- linux-2.6.16.5-a.orig/arch/arm/mach-pxa/Makefile 2006-05-04 17:06:55.000000000 +0200
-+++ linux-2.6.16.5-a/arch/arm/mach-pxa/Makefile 2006-05-04 17:07:04.000000000 +0200
-@@ -5,7 +5,7 @@
- # Common support (must be linked before board specific support)
- obj-y += generic.o irq.o dma.o time.o
- obj-$(CONFIG_PXA25x) += pxa25x.o
--obj-$(CONFIG_PXA27x) += pxa27x.o
-+obj-$(CONFIG_PXA27x) += pxa27x.o sram.o
-
- # Specific board support
- obj-$(CONFIG_ARCH_LUBBOCK) += lubbock.o
-@@ -16,6 +16,7 @@
- obj-$(CONFIG_MACH_AKITA) += akita-ioexp.o
- obj-$(CONFIG_MACH_POODLE) += poodle.o
- obj-$(CONFIG_MACH_TOSA) += tosa.o
-+obj-$(CONFIG_PXA_EZX) += ezx.o
-
- # Support for blinky lights
- led-y := leds.o
-Index: linux-2.6.16.5-a/arch/arm/mach-pxa/ezx-compat.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/arch/arm/mach-pxa/ezx-compat.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,24 @@
-+
-+int set_GPIO_IRQ_edge(int irq, int type)
-+{
-+ int mytype;
-+
-+ switch (type) {
-+ case GPIO_FALLING_EDGE:
-+ mytype = IRQT_FALLING;
-+ break;
-+ case GPIO_RISING_EDGE:
-+ mytype = IRQT_RISING;
-+ break;
-+ case GPIO_BOTH_EDGES:
-+ mytype = IRQT_BOTHEDGE;
-+ break;
-+ default:
-+ return -EINVAL;
-+ break;
-+ }
-+
-+ return set_irq_type(irq, mytype);
-+}
-+
-+
-Index: linux-2.6.16.5-a/arch/arm/mach-pxa/ezx.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/arch/arm/mach-pxa/ezx.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,567 @@
-+/*
-+ * linux/arch/arm/mach-ezx/a780.c
-+ *
-+ * Support for the Motorola Ezx A780 Development Platform.
-+ *
-+ * Author: Zhuang Xiaofan
-+ * Created: Nov 25, 2003
-+ * Copyright: Motorola Inc.
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ */
-+
-+#include <linux/init.h>
-+#include <linux/major.h>
-+#include <linux/fs.h>
-+#include <linux/interrupt.h>
-+#include <linux/sched.h>
-+#include <linux/bitops.h>
-+#include <linux/mmc/host.h>
-+#include <linux/fb.h>
-+#include <linux/apm_bios.h>
-+#include <linux/delay.h>
-+#include <linux/platform_device.h>
-+
-+#include <asm/types.h>
-+#include <asm/setup.h>
-+#include <asm/memory.h>
-+#include <asm/mach-types.h>
-+#include <asm/hardware.h>
-+#include <asm/irq.h>
-+
-+#include <asm/mach/arch.h>
-+#include <asm/mach/map.h>
-+#include <asm/mach/irq.h>
-+
-+#include <asm/arch/irq.h>
-+#include <asm/arch/mmc.h>
-+#include <asm/arch/udc.h>
-+#include <asm/arch/ohci.h>
-+#include <asm/arch/pxafb.h>
-+#include <asm/arch/pxa-regs.h>
-+#include <asm/arch/ezx.h>
-+
-+#include "generic.h"
-+#include <linux/tty.h>
-+#include <linux/apm_bios.h>
-+
-+#include "../../../drivers/misc/ezx/ezx-emu.h"
-+
-+#define FIRST_STEP 2
-+#define LAST_STEP 3
-+#define BP_RDY_TIMEOUT 0x000c0000
-+
-+extern void usb_send_readurb(void);
-+extern void pm_do_poweroff(void);
-+
-+
-+/* check power down condition */
-+inline void check_power_off(void)
-+{
-+ if (!(GPIO_is_high(GPIO_BB_WDI2))) {
-+#ifdef CONFIG_PM
-+ pm_do_poweroff();
-+#endif
-+ }
-+}
-+
-+/* OHCI Controller */
-+
-+static int ezx_ohci_init(struct device *dev)
-+{
-+ /* for A780 support (connected with Neptune) */
-+ pxa_gpio_mode(GPIO30_USB_P3_2); /* GPIO30 - USB_P3_2/ICL_TXENB */
-+ pxa_gpio_mode(GPIO31_USB_P3_6); /* GPIO31 - USB_P3_6/ICL_VPOUT */
-+ pxa_gpio_mode(GPIO90_USB_P3_5); /* GPIO90 - USB_P3_5/ICL_VPIN */
-+ pxa_gpio_mode(GPIO91_USB_P3_1); /* GPIO91 - USB_P3_1/ICL_XRXD */
-+ pxa_gpio_mode(GPIO56_USB_P3_4); /* GPIO56 - USB_P3_4/ICL_VMOUT */
-+ pxa_gpio_mode(GPIO113_USB_P3_3);/* GPIO113 - USB_P3_3/ICL_VMIN */
-+ UP3OCR = 0x00000002;
-+
-+ UHCHR = UHCHR & ~(UHCHR_SSEP2 | UHCHR_SSEP3 | UHCHR_SSE);
-+
-+ return 0;
-+}
-+
-+static struct pxaohci_platform_data ezx_ohci_platform_data = {
-+ .port_mode = PMM_NPS_MODE,
-+ .init = ezx_ohci_init,
-+};
-+
-+/* MMC/SD Device */
-+
-+static struct pxamci_platform_data ezx_mci_platform_data;
-+
-+static int ezx_mci_init(struct device *dev,
-+ irqreturn_t (*ezx_detect_int)(int, void *, struct pt_regs *),
-+ void *data)
-+{
-+ int err;
-+ printk("%s entered\n", __FUNCTION__);
-+
-+ /* Setup GPIO for PXA27x MMC/SD controller */
-+ pxa_gpio_mode(GPIO32_MMCCLK_MD);
-+ pxa_gpio_mode(GPIO112_MMCCMD_MD);
-+ pxa_gpio_mode(GPIO92_MMCDAT0_MD);
-+ pxa_gpio_mode(GPIO109_MMCDAT1_MD);
-+ pxa_gpio_mode(GPIO110_MMCDAT2_MD);
-+ pxa_gpio_mode(GPIO111_MMCDAT3_MD);
-+
-+ SSP_PCAP_MMCSD_poweron();
-+
-+ ezx_mci_platform_data.detect_delay = msecs_to_jiffies(250);
-+
-+ err = request_irq(0x49, ezx_detect_int, SA_INTERRUPT,
-+ "MMC card detect", data);
-+ if (err) {
-+ printk(KERN_ERR "ezx_mci_detect: MMC/SD: can't request "
-+ "MMC card detect IRQ\n");
-+ return -1;
-+ }
-+
-+ set_GPIO_IRQ_edge(0x0b, GPIO_BOTH_EDGES);
-+
-+ return 0;
-+}
-+
-+static int ezx_mci_get_ro(struct device *dev)
-+{
-+ printk("%s entered\n", __FUNCTION__);
-+ return (GPLR3 & 0x800);
-+ // return GPIO_is_high(96+4);
-+ /* this is only e680, i guess */
-+}
-+
-+static void ezx_mci_setpower(struct device *dev, unsigned int vdd)
-+{
-+ printk("%s entered\n", __FUNCTION__);
-+ /* FIXME: implement this */
-+ SSP_PCAP_MMCSD_poweron();
-+}
-+
-+static void ezx_mci_exit(struct device *dev, void *data)
-+{
-+ printk("%s entered\n", __FUNCTION__);
-+ SSP_PCAP_MMCSD_poweroff();
-+ free_irq(0x49, data);
-+}
-+
-+static struct pxamci_platform_data ezx_mci_platform_data = {
-+ .ocr_mask = MMC_VDD_27_28, //|MMC_VDD_32_33|MMC_VDD_33_34,
-+ .init = ezx_mci_init,
-+ .get_ro = ezx_mci_get_ro,
-+ .setpower = ezx_mci_setpower,
-+ .exit = ezx_mci_exit,
-+};
-+
-+/* USB Device Controller */
-+
-+static int udc_connected_status;
-+
-+static void ezx_udc_command(int cmd)
-+{
-+ switch (cmd) {
-+ case PXA2XX_UDC_CMD_DISCONNECT:
-+ printk(KERN_NOTICE "USB cmd disconnect\n");
-+ pcap_switch_off_usb();
-+ udc_connected_status = 0;
-+ break;
-+ case PXA2XX_UDC_CMD_CONNECT:
-+ printk(KERN_NOTICE "USB cmd connect\n");
-+ pcap_switch_on_usb();
-+ udc_connected_status = 1;
-+ break;
-+ }
-+}
-+
-+static int ezx_udc_is_connected(void)
-+{
-+ return udc_connected_status;
-+}
-+
-+static struct pxa2xx_udc_mach_info ezx_udc_info __initdata = {
-+ .udc_is_connected = ezx_udc_is_connected,
-+ .udc_command = ezx_udc_command,
-+};
-+
-+/* pxafb */
-+
-+#define BKLIGHT_PRESCALE 2
-+#define BKLIGHT_PERIOD 49
-+#define DEFAULT_DUTYCYCLE 25
-+#define MAX_DUTYCYCLE (BKLIGHT_PERIOD+1)
-+#define MIN_DUTYCYCLE 0
-+
-+static void pxafb_backlight_power(int on)
-+{
-+ if (on) {
-+ CKEN |= CKEN0_PWM0;
-+ PWM_CTRL0 = BKLIGHT_PRESCALE;
-+ PWM_PERVAL0 = BKLIGHT_PERIOD;
-+ PWM_PWDUTY0 = DEFAULT_DUTYCYCLE;
-+
-+ GPDR0 |= 0x00010000; //PWM0 is GPIO16
-+ pxa_gpio_mode(GPIO16_PWM0_MD);
-+ } else {
-+#if 0
-+ PWM_PWDUTY0 = 0;
-+ GAFR0_U &=
-+#endif
-+ }
-+}
-+
-+//#define mdelay(x) udelay((x)*1000)
-+
-+static void pxafb_lcd_power(int on)
-+{
-+ if (on) {
-+ mdelay(1);
-+ GPSR3 = 0x00100000;
-+ mdelay(10);
-+ GPCR3 = 0x00100000;
-+ GPDR3 |= 0x00100000;
-+ } else {
-+#if 0
-+ GPSR3 = 0x00100000;
-+ PGSR3 |= 0x00100000;
-+ mdelay(41);
-+#endif
-+ }
-+}
-+
-+static struct pxafb_mach_info ezx_fb_info __initdata = {
-+ .pixclock = 150000,
-+ .xres = 240,
-+ .yres = 320,
-+ .bpp = 16,
-+
-+ .hsync_len = 10,
-+ .left_margin = 20,
-+ .right_margin = 10,
-+
-+ .vsync_len = 2,
-+ .upper_margin = 3,
-+ .lower_margin = 2,
-+
-+ .sync = FB_SYNC_HOR_HIGH_ACT | FB_SYNC_VERT_HIGH_ACT,
-+
-+ .lccr0 = 0x002008F8,
-+ .lccr3 = 0x0430FF09,
-+
-+ .pxafb_backlight_power = &pxafb_backlight_power,
-+ .pxafb_lcd_power = &pxafb_lcd_power,
-+};
-+
-+
-+/* backlight */
-+/* keyboard */
-+/* touch screen */
-+
-+/* SSP device */
-+
-+struct platform_device ezx_ssp_pcap_device = {
-+ .name = "ezx-ssp-pcap",
-+ .dev = {
-+ //.parent = ,
-+ },
-+ .id = -1,
-+};
-+
-+
-+static int step = FIRST_STEP;
-+void handshake(void)
-+{
-+ /* step 1: check MCU_INT_SW or BP_RDY is low (now it is checked in apboot) */
-+ if (step == 1) {
-+ int timeout = BP_RDY_TIMEOUT;
-+
-+ /* config MCU_INT_SW, BP_RDY as input */
-+ GPDR(GPIO_MCU_INT_SW) &= ~GPIO_bit(GPIO_MCU_INT_SW);
-+ GPDR(GPIO_BP_RDY) &= ~GPIO_bit(GPIO_BP_RDY);
-+
-+ while ( timeout -- ) {
-+ if ( (!(GPIO_is_high(GPIO_MCU_INT_SW)))
-+ || (!(GPIO_is_high(GPIO_BP_RDY))) ) {
-+ step ++;
-+ break;
-+ }
-+
-+ check_power_off();
-+ }
-+ }
-+
-+ /* step 2: wait BP_RDY is low */
-+ if (step == 2) {
-+ if (!(GPIO_is_high(GPIO_BP_RDY))) {
-+
-+ /* config MCU_INT_SW as output */
-+ pxa_gpio_mode(GPIO_MCU_INT_SW | GPIO_OUT);
-+ clr_GPIO(GPIO_MCU_INT_SW);
-+
-+ step ++;
-+ }
-+ }
-+
-+ /* step 3: wait BP_RDY is high */
-+ if (step == 3) {
-+ if (GPIO_is_high(GPIO_BP_RDY)) {
-+ step ++;
-+ //FIXME delay_bklight();
-+ set_GPIO(GPIO_MCU_INT_SW);
-+ }
-+ }
-+}
-+
-+#ifdef CONFIG_APM
-+static unsigned long idle_limit = 0;
-+int pm_handle_irq(int irq)
-+{
-+
-+ //FIXME: extern unsigned long idle_limit;
-+ //FIXME: extern int can_idle, can_sleep;
-+ static unsigned long tmp_jiffy; /* for temporary store of jiffies */
-+
-+ /*
-+ * if idle_limit is zero, never enter idle.
-+ * if not OS timer, reset idle timer count
-+ */
-+ if (idle_limit == 0) {
-+ tmp_jiffy = jiffies;
-+ return irq;
-+ }
-+#if 0
-+ if (irq != IRQ_OST0) {
-+ tmp_jiffy = jiffies;
-+ can_idle = 0;
-+ can_sleep = 0;
-+ } else if (jiffies > tmp_jiffy + idle_limit) {
-+
-+ /*
-+ * I think this is enough to prevent from reentering here
-+ * due to jiffies will be stoped
-+ */
-+ tmp_jiffy = jiffies;
-+
-+ /* if pm idle timer expired, queue event */
-+ apm_queue_event(KRNL_PROC_INACT);
-+ can_idle = 1;
-+ }
-+#endif
-+
-+ return irq;
-+}
-+
-+irqreturn_t bp_wdi_intr(int irq, void *dev_id, struct pt_regs *regs)
-+{
-+ apm_queue_event(KRNL_BP_WDI);
-+ return IRQ_HANDLED;
-+}
-+
-+static struct irqaction bp_wdi_irq = {
-+ .name = "BP wdi",
-+ .handler = &bp_wdi_intr,
-+};
-+#endif
-+
-+int handshake_pass(void)
-+{
-+ return (step > LAST_STEP);
-+}
-+
-+static irqreturn_t bp_rdy_intr(int irq, void *dev_id, struct pt_regs *regs)
-+{
-+ static int usbipc_ready = 0;
-+
-+ if (!usbipc_ready) {
-+ handshake();
-+ if (handshake_pass()) {
-+ disable_irq(IRQ_GPIO(GPIO_BB_WDI2));
-+
-+ /* set bp_rdy handle for usb ipc */
-+ set_GPIO_IRQ_edge(GPIO_BP_RDY, GPIO_FALLING_EDGE);
-+ usbipc_ready = 1;
-+ }
-+ } else
-+ // FIXME usb_send_readurb();
-+ {}
-+
-+ return IRQ_HANDLED;
-+}
-+
-+static struct irqaction bp_rdy_irq = {
-+ .name = "BP rdy",
-+ .handler = bp_rdy_intr,
-+};
-+
-+static irqreturn_t bp_wdi2_intr(int irq, void *dev_id, struct pt_regs *regs)
-+{
-+#ifdef CONFIG_PM
-+ pm_do_poweroff();
-+#endif
-+ return IRQ_HANDLED;
-+}
-+
-+static struct irqaction bp_wdi2_irq = {
-+ .name = "BP wdi2",
-+ .handler = bp_wdi2_intr,
-+};
-+
-+
-+static struct resource ezx_bp_resources[] = {
-+ [0] = {
-+ .start = GPIO_BP_RDY,
-+ .end = GPIO_BP_RDY,
-+ .flags = IORESOURCE_IRQ,
-+ },
-+ [1] = {
-+ .start = GPIO_BB_WDI2,
-+ .end = GPIO_BB_WDI2,
-+ .flags = IORESOURCE_IRQ,
-+ },
-+#ifdef CONFIG_APM
-+ [2] = {
-+ .start = GPIO_BB_WDI,
-+ .end = GPIO_BB_WDI,
-+ .flags = IORESOURCE_IRQ,
-+ },
-+#endif
-+};
-+
-+static struct platform_device ezx_bp_device = {
-+ .name = "ezx-bp",
-+ .dev = {
-+ //.parent =
-+ //.platform_data =
-+ },
-+ .id = -1,
-+ .num_resources = ARRAY_SIZE(ezx_bp_resources),
-+ .resource = ezx_bp_resources,
-+};
-+
-+static void __init ezx_init_gpio_irq(void)
-+{
-+#ifdef CONFIG_APM
-+ set_GPIO_IRQ_edge(GPIO_BB_WDI, GPIO_FALLING_EDGE);
-+ setup_irq(IRQ_GPIO(GPIO_BB_WDI), &bp_wdi_irq);
-+#endif
-+ set_GPIO_IRQ_edge(GPIO_BP_RDY, GPIO_BOTH_EDGES);
-+ setup_irq(IRQ_GPIO(GPIO_BP_RDY), &bp_rdy_irq);
-+
-+ set_GPIO_IRQ_edge(GPIO_BB_WDI2, GPIO_FALLING_EDGE);
-+ setup_irq(IRQ_GPIO(GPIO_BB_WDI2), &bp_wdi2_irq);
-+}
-+
-+static void __init a780_init_irq(void)
-+{
-+ pxa_init_irq();
-+
-+ /* init ezx specfic gpio irq */
-+ ezx_init_gpio_irq();
-+
-+ check_power_off();
-+ handshake();
-+ if (handshake_pass()) {
-+ disable_irq(IRQ_GPIO(GPIO_BP_RDY));
-+ disable_irq(IRQ_GPIO(GPIO_BB_WDI2));
-+ }
-+}
-+
-+static struct platform_device *devices[] __initdata = {
-+ &ezx_bp_device,
-+ &ezx_ssp_pcap_device,
-+};
-+
-+static void __init
-+fixup_a780(struct machine_desc *desc, struct tag *tag,
-+ char **cmdline, struct meminfo *mi)
-+{
-+ screen_info.orig_video_cols = 30;
-+ screen_info.orig_video_lines = 80;
-+}
-+
-+static void __init a780_init(void)
-+{
-+ CKEN = CKEN9_OSTIMER | CKEN22_MEMC | CKEN5_STUART;
-+
-+ /* set BB_RESET PIN out put high */
-+ pxa_gpio_mode(GPIO_BB_RESET|GPIO_OUT);
-+ set_GPIO(GPIO_BB_RESET);
-+
-+ pxa_gpio_mode(GPIO_ICL_FFRXD_MD);
-+ pxa_gpio_mode(GPIO_ICL_FFTXD_MD);
-+ pxa_gpio_mode(GPIO_ICL_FFCTS_MD);
-+ pxa_gpio_mode(GPIO_ICL_FFRTS_MD);
-+
-+ pxa_gpio_mode(GPIO42_BTRXD_MD);
-+ pxa_gpio_mode(GPIO43_BTTXD_MD);
-+ pxa_gpio_mode(GPIO44_BTCTS_MD);
-+ pxa_gpio_mode(GPIO45_BTRTS_MD);
-+
-+ /* clear EMU MUX1/MUX2 (low) to close the audio path to EMU */
-+ pxa_gpio_mode(GPIO_EMU_MUX1|GPIO_OUT);
-+ clr_GPIO(GPIO_EMU_MUX1);
-+ pxa_gpio_mode(GPIO_EMU_MUX2|GPIO_OUT);
-+ clr_GPIO(GPIO_EMU_MUX2);
-+
-+#if defined(CONFIG_ARCH_EZX_E680)
-+ pxa_gpio_mode(GPIO46_STRXD_MD);
-+ pxa_gpio_mode(GPIO47_STTXD_MD);
-+
-+ /* setup sleep mode values */
-+ PWER = 0xc000f803; // disable usb 0xdc00f803;
-+ PFER = 0x0000f803;
-+ PRER = 0x00001802;
-+ // keypad wakeup (PKWR,PGSR3) should be in keypad.c
-+ PGSR0 = 0x00000010;
-+ PGSR1 = 0x02800000;
-+ PGSR2 = 0x00040000;
-+ PGSR3 = 0x00000000;
-+ PCFR = PCFR_DC_EN | PCFR_FS | PCFR_FP | PCFR_OPDE;
-+ PSLR = 0x05800f00;
-+
-+#elif defined(CONFIG_ARCH_EZX_A780)
-+
-+ /* Standard UART */
-+ pxa_gpio_mode(GPIO46_STRXD_MD);
-+ pxa_gpio_mode(GPIO47_STTXD_MD);
-+
-+ /* setup sleep mode values */
-+ PWER = 0xc0007803; // disable usb, GPIO15 NC
-+ PFER = 0x00007803;
-+ PRER = 0x00001802;
-+ // keypad wakeup (PKWR,PGSR3) should be in keypad.c
-+ PGSR0 = 0x00000010;
-+ PGSR1 = 0x02800000;
-+ PGSR2 = 0x00040000;
-+ PGSR3 = 0x00000008;
-+ PCFR = PCFR_DC_EN | PCFR_FS | PCFR_FP | PCFR_OPDE;
-+ PSLR = 0x05800f00;
-+
-+#endif
-+ set_pxa_fb_info(&ezx_fb_info);
-+ pxa_set_udc_info(&ezx_udc_info);
-+ pxa_set_mci_info(&ezx_mci_platform_data);
-+ pxa_set_ohci_info(&ezx_ohci_platform_data);
-+
-+ ssp_pcap_init();
-+
-+ /* try to configure USB connector as FFUART */
-+ emu_switch_to(EMU_SWITCH_TO_UART);
-+
-+ platform_add_devices(devices, ARRAY_SIZE(devices));
-+}
-+
-+MACHINE_START(EZX, "Motorola Ezx Platform")
-+ /* Maintainer: Harald Welte <laforge@gnumonks.org> */
-+ .phys_ram = 0xa0000000,
-+ .phys_io = 0x40000000,
-+ .io_pg_offst = (io_p2v(0x40000000) >> 18) & 0xfffc,
-+ .boot_params = 0xa0000100,
-+ .fixup = fixup_a780,
-+ .map_io = pxa_map_io,
-+ .init_irq = a780_init_irq,
-+ .timer = &pxa_timer,
-+ .init_machine = a780_init,
-+MACHINE_END
-Index: linux-2.6.16.5-a/arch/arm/mach-pxa/irq.c
-===================================================================
---- linux-2.6.16.5-a.orig/arch/arm/mach-pxa/irq.c 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/arch/arm/mach-pxa/irq.c 2006-05-04 17:07:04.000000000 +0200
-@@ -25,6 +25,8 @@
- #include "generic.h"
-
-
-+#include "ezx-compat.c"
-+
- /*
- * This is for peripheral IRQs internal to the PXA chip.
- */
-Index: linux-2.6.16.5-a/arch/arm/mach-pxa/sram.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/arch/arm/mach-pxa/sram.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,104 @@
-+/*
-+ * linux/arch/arm/mach-wmmx/sram.c
-+ *
-+ * Bulverde Internal Memory stuff
-+ *
-+ * Created: Sep 05, 2003
-+ * Copyright: MontaVista Software Inc.
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License as published by
-+ * the Free Software Foundation; either version 2 of the License, or
-+ * (at your option) any later version.
-+ *
-+ * This program is distributed in the hope that it will be useful,
-+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
-+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-+ * GNU General Public License for more details.
-+ *
-+ * You should have received a copy of the GNU General Public License
-+ * along with this program; if not, write to the Free Software
-+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
-+ *
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/init.h>
-+#include <linux/config.h>
-+#include <linux/sched.h>
-+#include <linux/kernel.h>
-+#include <linux/errno.h>
-+#include <linux/spinlock.h>
-+
-+#include <asm/system.h>
-+#include <asm/irq.h>
-+#include <asm/hardware.h>
-+#include <asm/arch-pxa/pxa-regs.h>
-+
-+#define SRAM_MEM_VIRT io_p2v(SRAM_MEM_PHYS)
-+
-+#define SRAM_DELAY_STANDBY_TIME 255
-+
-+static spinlock_t sram_spinlock;
-+static volatile int sram_locked = 0;
-+
-+static int __init sram_init (void) {
-+ /* Enable clock */
-+ pxa_set_cken(CKEN20_IM, 1);
-+
-+ /* All the banks are
-+ * - Automatic wakeup enabled
-+ * - Enter Stand-by after 255 ms
-+ */
-+ IMPMCR = IMPMCR_PC3_AUTO_MODE |
-+ IMPMCR_PC2_AUTO_MODE |
-+ IMPMCR_PC1_AUTO_MODE |
-+ IMPMCR_PC0_AUTO_MODE |
-+ IMPMCR_AW3 | IMPMCR_AW2 |
-+ IMPMCR_AW1 | IMPMCR_AW0 |
-+ SRAM_DELAY_STANDBY_TIME;
-+
-+ return 0;
-+}
-+
-+int sram_access_obtain(unsigned long *pmem, unsigned long *psize) {
-+
-+ int flags;
-+
-+ spin_lock_irqsave(&sram_spinlock, flags);
-+
-+ if (sram_locked != 0) {
-+ spin_unlock_irqrestore(&sram_spinlock, flags);
-+ return -EAGAIN;
-+ }
-+
-+ sram_locked = 1;
-+
-+ spin_unlock_irqrestore(&sram_spinlock, flags);
-+
-+ *pmem = SRAM_MEM_VIRT;
-+ *psize = SRAM_SIZE;
-+
-+ return 0;
-+}
-+
-+int sram_access_release(unsigned long *pmem, unsigned long *psize)
-+{
-+ if ((*pmem != SRAM_MEM_VIRT) ||
-+ (*psize != SRAM_SIZE)){
-+ return -EINVAL;
-+ }
-+
-+ *pmem = 0;
-+ *psize = 0;
-+
-+ sram_locked = 0;
-+
-+ return 0;
-+}
-+
-+EXPORT_SYMBOL(sram_access_obtain);
-+EXPORT_SYMBOL(sram_access_release);
-+
-+__initcall(sram_init);
-+
-Index: linux-2.6.16.5-a/arch/arm/mm/init.c
-===================================================================
---- linux-2.6.16.5-a.orig/arch/arm/mm/init.c 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/arch/arm/mm/init.c 2006-05-04 17:07:04.000000000 +0200
-@@ -230,6 +230,10 @@
- #endif
- if (res_size)
- reserve_bootmem_node(pgdat, PHYS_OFFSET, res_size);
-+#ifdef CONFIG_ARCH_EZX
-+ /* reserve the first page memory for exiting sleep and user off */
-+ reserve_bootmem_node(pgdat, PHYS_OFFSET, PAGE_SIZE);
-+#endif
- }
-
- void __init build_mem_type_table(void);
-Index: linux-2.6.16.5-a/include/asm-arm/arch-pxa/debug-macro.S
-===================================================================
---- linux-2.6.16.5-a.orig/include/asm-arm/arch-pxa/debug-macro.S 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/include/asm-arm/arch-pxa/debug-macro.S 2006-05-04 17:07:04.000000000 +0200
-@@ -14,15 +14,59 @@
- #include "hardware.h"
-
- .macro addruart,rx
-- mrc p15, 0, \rx, c1, c0
-- tst \rx, #1 @ MMU enabled?
-- moveq \rx, #0x40000000 @ physical
-- movne \rx, #io_p2v(0x40000000) @ virtual
-- orr \rx, \rx, #0x00100000
-+@ mrc p15, 0, \rx, c1, c0
-+@ tst \rx, #1 @ MMU enabled?
-+ mov \rx, #0x40000000 @ physical
-+@ moveq \rx, #0x40000000 @ physical
-+@ movne \rx, #io_p2v(0x40000000) @ virtual
-+ orr \rx, \rx, #0x00700000
-+ .endm
-+
-+ .macro inituart,rd,rx
-+ ldr \rd, =0x41300004 @ CKEN
-+ ldr \rx, [\rd]
-+ orr \rx, \rx, #0x20
-+ str \rx, [\rd]
-+
-+ ldr \rd, =0x40E0005C
-+ ldr \rx, [\rd]
-+ bic \rx, \rx, #0xF0000000 @ clear GPIO46/47 config
-+ orr \rx, \rx, #0x60000000 @ set GPIO46: AF2, GPIO47: AF1
-+ str \rx, [\rd]
-+ ldr \rd, =0x40E00010
-+ ldr \rx, [\rd]
-+ bic \rx, \rx, #0x0000c000 @ clear GPIO46/47 direction
-+ orr \rx, \rx, #0x00008000 @ set GPIO 47 out, 46 in
-+ str \rx, [\rd]
-+
-+ addruart \rd
-+ mov \rx, #0x83 @ DLAB = 1
-+ strb \rx, [\rd, #0x0c]
-+
-+ mov \rx, #0x08 @ Divisor 8 => 115200 bps
-+ strb \rx, [\rd, #0x00]
-+
-+ mov \rx, #0x00
-+ strb \rx, [\rd, #0x04] @ Divisor high = 0
-+
-+ mov \rx, #0x03
-+ strb \rx, [\rd, #0x0c] @ DLAB = 0, n81
-+
-+ mov \rx, #0x00
-+ strb \rx, [\rd, #0x10] @ MCR = 0
-+
-+ mov \rx, #0x00
-+ strb \rx, [\rd, #0x28] @ disable autobaud
-+
-+ mov \rx, #0x40
-+ strb \rx, [\rd, #0x04] @ IER UUE (UART Enable)
- .endm
-
- .macro senduart,rd,rx
-- str \rd, [\rx, #0]
-+1000: ldr r12, [\rx, #0x14]
-+ tst r12, #(1 << 6)
-+ beq 1000b
-+ strb \rd, [\rx, #0]
- .endm
-
- .macro busyuart,rd,rx
-Index: linux-2.6.16.5-a/include/asm-arm/arch-pxa/ezx-compat.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/include/asm-arm/arch-pxa/ezx-compat.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,14 @@
-+#ifndef _EZX_COMPAT_H
-+#define _EZX_COMPAT_H
-+
-+#define GPIO_is_high(x) (GPLR(x) & GPIO_bit(x))
-+#define set_GPIO(x) (GPSR(x) = GPIO_bit(x))
-+#define clr_GPIO(x) (GPCR(x) = GPIO_bit(x))
-+
-+#define GPIO_FALLING_EDGE 1
-+#define GPIO_RISING_EDGE 2
-+#define GPIO_BOTH_EDGES 3
-+
-+extern int set_GPIO_IRQ_edge(int irq, int type);
-+
-+#endif
-Index: linux-2.6.16.5-a/include/asm-arm/arch-pxa/ezx.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/include/asm-arm/arch-pxa/ezx.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,221 @@
-+/*
-+ * linux/include/asm-arm/arch-pxa/ezx.h
-+ *
-+ * Specific macro defines for Motorola Ezx Development Platform
-+ *
-+ * Author: Zhuang Xiaofan
-+ * Created: Nov 25, 2003
-+ * Copyright: Motorola Inc.
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ */
-+
-+/* support E680 p3 and ealier PCB */
-+//#define E680_P3_AND_EARLY
-+
-+/*
-+ * Flags in memory for sleep use
-+ */
-+#define FLAG_ADDR PHYS_OFFSET
-+#define RESUME_ADDR (PHYS_OFFSET + 4)
-+#define BPSIG_ADDR (PHYS_OFFSET + 8)
-+
-+#define USER_OFF_FLAG 0x5a5a5a5a
-+#define SLEEP_FLAG 0x6b6b6b6b
-+#define OFF_FLAG 0x7c7c7c7c
-+#define REFLASH_FLAG 0x0C1D2E3F
-+#define PASS_THRU_FLAG 0x12345678
-+
-+#define WDI_FLAG 0xbb00dead
-+#define NO_FLAG 0xaa00dead
-+
-+/*
-+ * GPIO control pin, have to change when hardware lock down
-+ */
-+
-+#ifdef E680_P3_AND_EARLY
-+
-+/* shakehand with BP's PIN */
-+#define GPIO_BP_RDY 0 /* BP_RDY */
-+#define GPIO_BB_WDI 13 /* BB_WDI */
-+#define GPIO_BB_WDI2 3 /* BB_WDI2 */
-+#define GPIO_BB_RESET 57 /* BB_RESET */
-+#define GPIO_MCU_INT_SW 115 /* MCU_INT_SW */
-+#define GPIO_TC_MM_EN 89 /* TC_MM_EN */
-+
-+/* control PCAP direct PIN */
-+#define GPIO_WDI_AP 4 /* WDI_AP */
-+#define GPIO_SYS_RESTART 55 /* restart PCAP power */
-+#define GPIO_AP_STANDBY 28 /* make pcap enter standby mode */
-+
-+/* communicate with PCAP's PIN */
-+#define GPIO_PCAP_SEC_INT 1 /* PCAP interrupt PIN to AP */
-+#define GPIO_SPI_CLK 23 /* PCAP SPI port clock */
-+#define GPIO_SPI_CE 24 /* PCAP SPI port SSPFRM */
-+#define GPIO_SPI_MOSI 25 /* PCAP SPI port SSPTXD */
-+#define GPIO_SPI_MISO 26 /* PCAP SPI port SSPRXD */
-+
-+/* blue tooth control PIN */
-+#define GPIO_BT_WAKEUP 2 /* AP wake up bluetooth module */
-+#define GPIO_BT_HOSTWAKE 14 /* bluetooth module wake up Ap module */
-+#define GPIO_BT_RESET 56 /* AP reset bluetooth module */
-+
-+/* control LCD high - OFF low -- ON */
-+#define GPIO_LCD_OFF 116 /* control LCD */
-+
-+/* FFUART PIN */
-+#define GPIO_ICL_FFRXD_MD (34 | GPIO_ALT_FN_1_IN)
-+#define GPIO_ICL_FFCTS_MD (35 | GPIO_ALT_FN_1_IN)
-+#define GPIO_ICL_FFTXD_MD (39 | GPIO_ALT_FN_2_OUT)
-+#define GPIO_ICL_FFRTS_MD (41 | GPIO_ALT_FN_2_OUT)
-+
-+#elif defined(A780_P1_AND_EARLY)
-+
-+/* shakehand with BP's PIN */
-+#define GPIO_BP_RDY 0 /* BP_RDY */
-+#define GPIO_BB_WDI 13 /* BB_WDI */
-+#define GPIO_BB_WDI2 3 /* BB_WDI2 */
-+#define GPIO_BB_RESET 82 /* BB_RESET */
-+#define GPIO_MCU_INT_SW 57 /* MCU_INT_SW */
-+#define GPIO_TC_MM_EN 89 /* TC_MM_EN */
-+
-+/* control PCAP direct PIN */
-+#define GPIO_WDI_AP 4 /* WDI_AP */
-+#define GPIO_SYS_RESTART 55 /* restart PCAP power */
-+#define GPIO_AP_STANDBY 28 /* make pcap enter standby mode */
-+
-+/* communicate with PCAP's PIN */
-+#define GPIO_PCAP_SEC_INT 1 /* PCAP interrupt PIN to AP */
-+#define GPIO_SPI_CLK 29 /* PCAP SPI port clock */
-+#define GPIO_SPI_CE 24 /* PCAP SPI port SSPFRM */
-+#define GPIO_SPI_MOSI 25 /* PCAP SPI port SSPTXD */
-+#define GPIO_SPI_MISO 26 /* PCAP SPI port SSPRXD */
-+
-+/* blue tooth control PIN */
-+#define GPIO_BT_WAKEUP 2 /* AP wake up bluetooth module */
-+#define GPIO_BT_HOSTWAKE 14 /* bluetooth module wake up Ap module */
-+#define GPIO_BT_RESET 56 /* AP reset bluetooth module */
-+
-+/* control LCD high - OFF low -- ON */
-+#define GPIO_LCD_OFF 116 /* control LCD */
-+
-+/* FFUART PIN */
-+#define GPIO_ICL_FFRXD_MD (53 | GPIO_ALT_FN_1_IN)
-+#define GPIO_ICL_FFCTS_MD (35 | GPIO_ALT_FN_1_IN)
-+#define GPIO_ICL_FFTXD_MD (39 | GPIO_ALT_FN_2_OUT)
-+#define GPIO_ICL_FFRTS_MD (41 | GPIO_ALT_FN_2_OUT)
-+
-+#else
-+
-+/* shakehand with BP's PIN */
-+#define GPIO_BP_RDY 0 /* BP_RDY */
-+#define GPIO_BB_WDI 13 /* BB_WDI */
-+#define GPIO_BB_WDI2 3 /* BB_WDI2 */
-+#define GPIO_BB_RESET 82 /* BB_RESET */
-+#define GPIO_MCU_INT_SW 57 /* MCU_INT_SW */
-+#define GPIO_TC_MM_EN 99 /* TC_MM_EN */
-+
-+/* control PCAP direct PIN */
-+#define GPIO_WDI_AP 4 /* WDI_AP */
-+#define GPIO_SYS_RESTART 55 /* restart PCAP power */
-+//#define GPIO_AP_STANDBY 28 /* make pcap enter standby mode */
-+
-+/* communicate with PCAP's PIN */
-+#define GPIO_PCAP_SEC_INT 1 /* PCAP interrupt PIN to AP */
-+#define GPIO_SPI_CLK 29 /* PCAP SPI port clock */
-+#define GPIO_SPI_CE 24 /* PCAP SPI port SSPFRM */
-+#define GPIO_SPI_MOSI 25 /* PCAP SPI port SSPTXD */
-+#define GPIO_SPI_MISO 26 /* PCAP SPI port SSPRXD */
-+
-+/* blue tooth control PIN */
-+#define GPIO_BT_WAKEUP 28 /* AP wake up bluetooth module */
-+#define GPIO_BT_HOSTWAKE 14 /* AP wake up bluetooth module */
-+#define GPIO_BT_RESET 48 /* AP reset bluetooth module */
-+
-+/* control LCD high - OFF low -- ON */
-+#define GPIO_LCD_OFF 116 /* control LCD */
-+
-+/* FFUART PIN */
-+#define GPIO_ICL_FFRXD_MD (53 | GPIO_ALT_FN_1_IN)
-+#define GPIO_ICL_FFCTS_MD (35 | GPIO_ALT_FN_1_IN)
-+#define GPIO_ICL_FFTXD_MD (39 | GPIO_ALT_FN_2_OUT)
-+#define GPIO_ICL_FFRTS_MD (41 | GPIO_ALT_FN_2_OUT)
-+
-+#endif
-+/*
-+ * ezx platform, wake up source edge detect bit
-+ */
-+#define PEDR_INT_SEC 1
-+
-+#define GPIO_FLIP_PIN 12
-+/*E680 screen lock button*/
-+
-+#define GPIO_LOCK_SCREEN_PIN GPIO_FLIP_PIN
-+
-+/* MMC interface */
-+#define GPIO_MMC_DETECT 11
-+#define GPIO_MMC_CLK 32
-+#define GPIO_MMC_DATA0 92
-+#define GPIO_MMC_WP 107
-+#define GPIO_MMC_DATA1 109
-+#define GPIO_MMC_DATA2 110
-+#define GPIO_MMC_DATA3 111
-+#define GPIO_MMC_CMD 112
-+
-+/* interface function */
-+#define GPIO_MMC_CLK_MD (GPIO_MMC_CLK | GPIO_ALT_FN_2_OUT)
-+#define GPIO_MMC_DATA0_MD (GPIO_MMC_DATA0 | GPIO_ALT_FN_1_IN | GPIO_ALT_FN_1_OUT)
-+#define GPIO_MMC_DATA1_MD (GPIO_MMC_DATA1 | GPIO_ALT_FN_1_IN | GPIO_ALT_FN_1_OUT)
-+#define GPIO_MMC_DATA2_MD (GPIO_MMC_DATA2 | GPIO_ALT_FN_1_IN | GPIO_ALT_FN_1_OUT)
-+#define GPIO_MMC_DATA3_MD (GPIO_MMC_DATA3 | GPIO_ALT_FN_1_IN | GPIO_ALT_FN_1_OUT)
-+
-+#define GPIO_MMC_CMD_MD (GPIO_MMC_CMD | GPIO_ALT_FN_1_IN | GPIO_ALT_FN_1_OUT)
-+
-+/* EMU GPIO 119 ---MUX2 120 --- MUX1 */
-+#define GPIO_EMU_MUX1 120
-+#define GPIO_EMU_MUX2 119
-+#define GPIO_SNP_INT_CTL 86
-+#define GPIO_SNP_INT_IN 87
-+
-+
-+/* audio related pins */
-+#define AP_13MHZ_OUTPUT_PIN 9
-+
-+#ifdef CONFIG_ARCH_EZX_E680
-+#define GPIO_VA_SEL_BUL 79
-+#define GPIO_FLT_SEL_BUL 80 /* out filter select pin */
-+#define GPIO_MIDI_RESET 78 /* GPIO used by MIDI chipset */
-+#define GPIO_MIDI_CS 33
-+#define GPIO_MIDI_IRQ 15
-+#define GPIO_MIDI_NPWE 49
-+#define GPIO_MIDI_RDY 18
-+#endif
-+
-+#ifdef CONFIG_ARCH_EZX_A780
-+#define GPIO_HW_ATTENUATE_A780 96 /* hw noise attenuation be used or bypassed, for receiver or louderspeaker mode */
-+#endif
-+
-+
-+/* bp status pin */
-+#define GPIO_BP_STATE 41
-+
-+/* define usb related pin */
-+#define GPIO34_TXENB 34
-+#define GPIO35_XRXD 35
-+#define GPIO36_VMOUT 36
-+#define GPIO39_VPOUT 39
-+#define GPIO40_VPIN 40
-+#define GPIO53_VMIN 53
-+
-+/* USB client 6 pin defination */
-+#define GPIO34_TXENB_MD (GPIO34_TXENB | GPIO_ALT_FN_1_OUT)
-+#define GPIO35_XRXD_MD (GPIO35_XRXD | GPIO_ALT_FN_2_IN )
-+#define GPIO36_VMOUT_MD (GPIO36_VMOUT | GPIO_ALT_FN_1_OUT)
-+#define GPIO39_VPOUT_MD (GPIO39_VPOUT | GPIO_ALT_FN_1_OUT)
-+#define GPIO40_VPIN_MD (GPIO40_VPIN | GPIO_ALT_FN_3_IN )
-+#define GPIO53_VMIN_MD (GPIO53_VMIN | GPIO_ALT_FN_2_IN )
-+
-+#define GPIO53_FFRXD_MD (53 | GPIO_ALT_FN_1_IN)
-+
-Index: linux-2.6.16.5-a/include/asm-arm/arch-pxa/hardware.h
-===================================================================
---- linux-2.6.16.5-a.orig/include/asm-arm/arch-pxa/hardware.h 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/include/asm-arm/arch-pxa/hardware.h 2006-05-04 17:07:04.000000000 +0200
-@@ -62,6 +62,7 @@
-
- #ifndef __ASSEMBLY__
-
-+#include <asm/arch-pxa/ezx-compat.h>
- /*
- * Handy routine to set GPIO alternate functions
- */
-Index: linux-2.6.16.5-a/include/asm-arm/arch-pxa/pxa-regs.h
-===================================================================
---- linux-2.6.16.5-a.orig/include/asm-arm/arch-pxa/pxa-regs.h 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/include/asm-arm/arch-pxa/pxa-regs.h 2006-05-04 17:07:04.000000000 +0200
-@@ -856,6 +856,8 @@
- #define UP2OCR_HXOE (1 << 17) /* Host Port 2 Transceiver Output Enable */
- #define UP2OCR_SEOS (1 << 24) /* Single-Ended Output Select */
-
-+#define UP3OCR __REG(0x40600024) /* USB Port 3 Output Control register */
-+
- #define UDCCSN(x) __REG2(0x40600100, (x) << 2)
- #define UDCCSR0 __REG(0x40600100) /* UDC Control/Status register - Endpoint 0 */
- #define UDCCSR0_SA (1 << 7) /* Setup Active */
-@@ -1259,6 +1261,7 @@
- #define GPIO33_nCS_5 33 /* chip select 5 */
- #define GPIO34_FFRXD 34 /* FFUART receive */
- #define GPIO34_MMCCS0 34 /* MMC Chip Select 0 */
-+#define GPIO34_USB_P2_2 34 /* USB Port2 Pin 2 */
- #define GPIO35_FFCTS 35 /* FFUART Clear to send */
- #define GPIO36_FFDCD 36 /* FFUART Data carrier detect */
- #define GPIO37_FFDSR 37 /* FFUART data set ready */
-@@ -1382,22 +1385,29 @@
- #define GPIO29_SDATA_IN_AC97_MD (29 | GPIO_ALT_FN_1_IN)
- #define GPIO29_SDATA_IN_I2S_MD (29 | GPIO_ALT_FN_2_IN)
- #define GPIO30_SDATA_OUT_AC97_MD (30 | GPIO_ALT_FN_2_OUT)
-+#define GPIO30_USB_P3_2 (30 | GPIO_ALT_FN_3_OUT)
- #define GPIO30_SDATA_OUT_I2S_MD (30 | GPIO_ALT_FN_1_OUT)
- #define GPIO31_SYNC_I2S_MD (31 | GPIO_ALT_FN_1_OUT)
- #define GPIO31_SYNC_AC97_MD (31 | GPIO_ALT_FN_2_OUT)
-+#define GPIO31_USB_P3_6 (31 | GPIO_ALT_FN_3_OUT)
- #define GPIO32_SDATA_IN1_AC97_MD (32 | GPIO_ALT_FN_1_IN)
- #define GPIO32_SYSCLK_I2S_MD (32 | GPIO_ALT_FN_1_OUT)
- #define GPIO32_MMCCLK_MD ( 32 | GPIO_ALT_FN_2_OUT)
- #define GPIO33_nCS_5_MD (33 | GPIO_ALT_FN_2_OUT)
- #define GPIO34_FFRXD_MD (34 | GPIO_ALT_FN_1_IN)
-+#define GPIO34_USB_P2_2_MD (34 | GPIO_ALT_FN_1_OUT)
- #define GPIO34_MMCCS0_MD (34 | GPIO_ALT_FN_2_OUT)
- #define GPIO35_FFCTS_MD (35 | GPIO_ALT_FN_1_IN)
-+#define GPIO35_USB_P2_1_MD (35 | GPIO_ALT_FN_2_IN)
- #define GPIO36_FFDCD_MD (36 | GPIO_ALT_FN_1_IN)
-+#define GPIO36_USB_P2_4_MD (36 | GPIO_ALT_FN_1_OUT)
- #define GPIO37_FFDSR_MD (37 | GPIO_ALT_FN_1_IN)
- #define GPIO38_FFRI_MD (38 | GPIO_ALT_FN_1_IN)
- #define GPIO39_MMCCS1_MD (39 | GPIO_ALT_FN_1_OUT)
- #define GPIO39_FFTXD_MD (39 | GPIO_ALT_FN_2_OUT)
-+#define GPIO39_USB_P2_6_MD (39 | GPIO_ALT_FN_1_OUT)
- #define GPIO40_FFDTR_MD (40 | GPIO_ALT_FN_2_OUT)
-+#define GPIO40_USB_P2_5_MD (40 | GPIO_ALT_FN_3_IN)
- #define GPIO41_FFRTS_MD (41 | GPIO_ALT_FN_2_OUT)
- #define GPIO42_BTRXD_MD (42 | GPIO_ALT_FN_1_IN)
- #define GPIO42_HWRXD_MD (42 | GPIO_ALT_FN_3_IN)
-@@ -1422,13 +1432,16 @@
- #define GPIO51_HWRTS_MD (51 | GPIO_ALT_FN_1_OUT)
- #define GPIO51_nPIOW_MD (51 | GPIO_ALT_FN_2_OUT)
- #define GPIO52_nPCE_1_MD (52 | GPIO_ALT_FN_2_OUT)
--#define GPIO53_nPCE_2_MD (53 | GPIO_ALT_FN_2_OUT)
- #define GPIO53_MMCCLK_MD (53 | GPIO_ALT_FN_1_OUT)
-+#define GPIO53_nPCE_2_MD (53 | GPIO_ALT_FN_2_OUT)
-+#define GPIO53_FFRXD_MD (53 | GPIO_ALT_FN_1_IN)
-+#define GPIO53_USB_P2_3_MD (53 | GPIO_ALT_FN_2_IN)
- #define GPIO54_MMCCLK_MD (54 | GPIO_ALT_FN_1_OUT)
- #define GPIO54_nPCE_2_MD (54 | GPIO_ALT_FN_2_OUT)
- #define GPIO54_pSKTSEL_MD (54 | GPIO_ALT_FN_2_OUT)
- #define GPIO55_nPREG_MD (55 | GPIO_ALT_FN_2_OUT)
- #define GPIO56_nPWAIT_MD (56 | GPIO_ALT_FN_1_IN)
-+#define GPIO56_USB_P3_4 (56 | GPIO_ALT_FN_1_OUT)
- #define GPIO57_nIOIS16_MD (57 | GPIO_ALT_FN_1_IN)
- #define GPIO58_LDD_0_MD (58 | GPIO_ALT_FN_2_OUT)
- #define GPIO59_LDD_1_MD (59 | GPIO_ALT_FN_2_OUT)
-@@ -1471,6 +1484,8 @@
- #define GPIO84_NSSP_TX (84 | GPIO_ALT_FN_1_OUT)
- #define GPIO84_NSSP_RX (84 | GPIO_ALT_FN_2_IN)
- #define GPIO85_nPCE_1_MD (85 | GPIO_ALT_FN_1_OUT)
-+#define GPIO90_USB_P3_5 (90 | GPIO_ALT_FN_2_IN)
-+#define GPIO91_USB_P3_1 (91 | GPIO_ALT_FN_2_IN)
- #define GPIO92_MMCDAT0_MD (92 | GPIO_ALT_FN_1_OUT)
- #define GPIO104_pSKTSEL_MD (104 | GPIO_ALT_FN_1_OUT)
- #define GPIO109_MMCDAT1_MD (109 | GPIO_ALT_FN_1_OUT)
-@@ -1481,6 +1496,7 @@
- #define GPIO112_MMCCMD_MD (112 | GPIO_ALT_FN_1_OUT)
- #define GPIO113_I2S_SYSCLK_MD (113 | GPIO_ALT_FN_1_OUT)
- #define GPIO113_AC97_RESET_N_MD (113 | GPIO_ALT_FN_2_OUT)
-+#define GPIO113_USB_P3_3 (113 | GPIO_ALT_FN_3_IN)
- #define GPIO117_I2CSCL_MD (117 | GPIO_ALT_FN_1_OUT)
- #define GPIO118_I2CSDA_MD (118 | GPIO_ALT_FN_1_IN)
-
-@@ -1496,6 +1512,7 @@
- #define PFER __REG(0x40F00014) /* Power Manager GPIO Falling-Edge Detect Enable Register */
- #define PEDR __REG(0x40F00018) /* Power Manager GPIO Edge Detect Status Register */
- #define PCFR __REG(0x40F0001C) /* Power Manager General Configuration Register */
-+#define PGSR(x) (__REG(0x40F00020 + ((unsigned long)(x)/32 * 4)))
- #define PGSR0 __REG(0x40F00020) /* Power Manager GPIO Sleep State Register for GP[31-0] */
- #define PGSR1 __REG(0x40F00024) /* Power Manager GPIO Sleep State Register for GP[63-32] */
- #define PGSR2 __REG(0x40F00028) /* Power Manager GPIO Sleep State Register for GP[84-64] */
-Index: linux-2.6.16.5-a/include/asm-arm/arch-pxa/uncompress.h
-===================================================================
---- linux-2.6.16.5-a.orig/include/asm-arm/arch-pxa/uncompress.h 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/include/asm-arm/arch-pxa/uncompress.h 2006-05-04 17:07:04.000000000 +0200
-@@ -14,12 +14,12 @@
- #define STUART ((volatile unsigned long *)0x40700000)
- #define HWUART ((volatile unsigned long *)0x41600000)
-
--#define UART FFUART
-+#define UART STUART
-
-
- static __inline__ void putc(char c)
- {
-- while (!(UART[5] & 0x20));
-+ while (!(UART[5] & 0x40));
- UART[0] = c;
- }
-
-Index: linux-2.6.16.5-a/drivers/misc/ezx/ssp_pcap.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/ssp_pcap.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,673 @@
-+/* (c) Copyright Motorola Beijing 2002 all rights reserved.
-+
-+ Project Name : EZX
-+ Project No. :
-+ Title :
-+ File Name :
-+ Description :
-+
-+ ************** REVISION HISTORY **********************************************
-+ Date Author Reference
-+ ======== ========== ==========================
-+ 2002-07-01 weiqiang lin create
-+*/
-+#ifndef SSP_PCAP_H
-+#define SSP_PCAP_H
-+
-+#ifdef __cplusplus
-+extern "C" {
-+#endif
-+
-+#define SSP_vibrate_start_command() SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_AUX_VREG_V_VIB_EN); \
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_AUX_VREG_V_VIB_EN)
-+
-+#define SSP_vibrate_stop_command() SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_AUX_VREG_V_VIB_EN); \
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_AUX_VREG_V_VIB_EN)
-+
-+#define SSP_PCAP_REGISTER_VALUE_LENGTH 16
-+
-+#define SSP_PCAP_REGISTER_WRITE_OP_BIT 0x80000000
-+#define SSP_PCAP_REGISTER_READ_OP_BIT 0x00000000
-+
-+#define SSP_PCAP_REGISTER_VALUE_UP_WORD_MASK 0xffff0000
-+#define SSP_PCAP_REGISTER_VALUE_DOWN_WORD_MASK 0x0000ffff
-+
-+#define SSP_PCAP_REGISTER_VALUE_MASK 0x01ffffff
-+#define SSP_PCAP_REGISTER_VALUE_MASK 0x01ffffff
-+#define SSP_PCAP_REGISTER_ADDRESS_MASK 0x7c000000
-+#define SSP_PCAP_REGISTER_ADDRESS_SHIFT 26
-+#define SSP_PCAP_REGISTER_NUMBER 32
-+
-+#define SSP_PCAP_ADC_START_VALUE_SET_MASK 0xfffffc00
-+#define SSP_PCAP_ADC_START_VALUE 0x000001dd
-+
-+
-+#define SSP_PCAP_PHONE_CDC_CLOCK_MASK 0x000001c0
-+#define SSP_PCAP_STEREO_SAMPLE_RATE_MASK 0x00000f00
-+#define SSP_PCAP_STEREO_BCLK_TIME_SLOT_MASK 0x00018000
-+#define SSP_PCAP_STEREO_CLOCK_MASK 0x0000001c
-+#define SSP_PCAP_DIGITAL_AUDIO_MODE_MASK 0x00006000
-+#define SSP_PCAP_TOUCH_PANEL_POSITION_DETECT_MODE_MASK 0x000e0000
-+#define SSP_PCAP_MONO_PGA_MASK 0x00180000
-+
-+#define SSP_PCAP_VIBRATOR_VOLTAGE_LEVEL_MASK 0x00300000
-+
-+#define SSP_PCAP_AUDIO_IN_GAIN_MASK 0x0000001f
-+#define SSP_PCAP_AUDIO_IN_GAIN_SHIFT 0
-+#define SSP_PCAP_AUDIO_OUT_GAIN_MASK 0x0001e000
-+#define SSP_PCAP_AUDIO_OUT_GAIN_SHIFT 13
-+
-+
-+#define SSP_PCAP_ADD1_VALUE_MASK 0x000003ff
-+#define SSP_PCAP_ADD1_VALUE_SHIFT 0
-+#define SSP_PCAP_ADD2_VALUE_MASK 0x000ffc00
-+#define SSP_PCAP_ADD2_VALUE_SHIFT 10
-+
-+
-+#define PCAP_AUDIO_IN_GAIN_MAX_VALUE 31
-+#define PCAP_AUDIO_OUT_GAIN_MAX_VALUE 15
-+
-+#define PCAP_CLEAR_INTERRUPT_REGISTER 0x00141fdf
-+#define PCAP_MASK_ALL_INTERRUPT 0x0013ffff
-+
-+#define SSP_PCAP_TS_KEEPER_TIMER 100 /* 1 second */
-+#define START_ADC_DELAY_TIMER 1991 /* 540 us */
-+
-+#define SSP_SEND_PM_ALART_INTERVAL 1000 *HZ/1000 /* 1 second */
-+#define SSP_SEND_MSG_USB_ACCESSORY_INFO_DEBOUNCE 200 *HZ/1000 /* 200ms */
-+
-+struct ssp_interrupt_info
-+{
-+ u32 type;
-+ u32 status;
-+ void* privdata;
-+};
-+
-+#ifndef U8
-+#define U8 unsigned char
-+#endif
-+
-+#ifndef U32
-+#define U32 unsigned long
-+#endif
-+
-+#ifndef U16
-+#define U16 unsigned short
-+#endif
-+
-+#ifndef P_U16
-+#define P_U16 U16*
-+#endif
-+
-+#ifndef P_U32
-+#define P_U32 U32*
-+#endif
-+
-+#define SSP_SELECT_BUFFER (volatile unsigned long *)(0xf4000000)
-+
-+#define SSP_SR_RNE 0x00000008
-+#define SSP_PCAP_BASE 0x00001000
-+/************************ STRUCTURES, ENUMS, AND TYPEDEFS **************************/
-+typedef enum accessoryStatus
-+{
-+ ACCESSORY_DEVICE_STATUS_DETACHED = 0,
-+ ACCESSORY_DEVICE_STATUS_ATTACHED ,
-+ ACCESSORY_DEVICE_STATUS_UNKNOW =0x000000ff
-+}ACCESSORY_DEVICE_STATUS;
-+
-+typedef enum accessoryType
-+{
-+ ACCESSORY_DEVICE_NONE = 0,
-+ ACCESSORY_DEVICE_SERIAL_PORT ,
-+ ACCESSORY_DEVICE_USB_PORT ,
-+ ACCESSORY_DEVICE_UNKNOW =0x000000ff
-+}ACCESSORY_TYPE;
-+
-+typedef enum pcapReturnStatus
-+{
-+ SSP_PCAP_SUCCESS = 0,
-+ SSP_PCAP_ERROR_REGISTER = SSP_PCAP_BASE+1,
-+ SSP_PCAP_ERROR_VALUE = SSP_PCAP_BASE+2,
-+
-+ SSP_PCAP_NOT_RUN = SSP_PCAP_BASE+0xff
-+}SSP_PCAP_STATUS;
-+
-+typedef enum pcapPortType
-+{
-+ SSP_PCAP_SERIAL_PORT = 0x00000000,
-+ SSP_PCAP_LOW_USB_PORT = 0x00000001,
-+ SSP_PCAP_HIGH_USB_PORT = 0x00000002,
-+ SSP_PCAP_UNKNOW_PORT = 0x000000ff
-+}SSP_PCAP_PORT_TYPE;
-+
-+typedef enum pcapInitDriverType
-+{
-+ SSP_PCAP_TS_OPEN = 0x00000000,
-+ SSP_PCAP_AUDIO_OPEN = 0x00000001,
-+ SSP_PCAP_UNKNOW_DRIVER_OPEN = 0x000000ff
-+}SSP_PCAP_INIT_DRIVER_TYPE;
-+
-+
-+typedef enum pcapReturnBitStatus
-+{
-+ SSP_PCAP_BIT_ZERO = 0x00000000,
-+ SSP_PCAP_BIT_ONE = 0x00000001,
-+ SSP_PCAP_BIT_ERROR = 0xff000000
-+}SSP_PCAP_BIT_STATUS;
-+
-+typedef enum pcapCDCClkType
-+{
-+ PCAP_CDC_CLK_IN_13M0 = 0x00000000,
-+ PCAP_CDC_CLK_IN_15M36 = 0x00000040,
-+ PCAP_CDC_CLK_IN_16M8 = 0x00000080,
-+ PCAP_CDC_CLK_IN_19M44 = 0x000000c0,
-+ PCAP_CDC_CLK_IN_26M0 = 0x00000100
-+}PHONE_CDC_CLOCK_TYPE;
-+
-+typedef enum pcapST_SR
-+{
-+ PCAP_ST_SAMPLE_RATE_8K = 0x00000000,
-+ PCAP_ST_SAMPLE_RATE_11K = 0x00000100,
-+ PCAP_ST_SAMPLE_RATE_12K = 0x00000200,
-+ PCAP_ST_SAMPLE_RATE_16K = 0x00000300,
-+ PCAP_ST_SAMPLE_RATE_22K = 0x00000400,
-+ PCAP_ST_SAMPLE_RATE_24K = 0x00000500,
-+ PCAP_ST_SAMPLE_RATE_32K = 0x00000600,
-+ PCAP_ST_SAMPLE_RATE_44K = 0x00000700,
-+ PCAP_ST_SAMPLE_RATE_48K = 0x00000800
-+}ST_SAMPLE_RATE_TYPE;
-+
-+typedef enum pcapST_BCLK
-+{
-+ PCAP_ST_BCLK_SLOT_16 = 0x00000000,
-+ PCAP_ST_BCLK_SLOT_8 = 0x00008000,
-+ PCAP_ST_BCLK_SLOT_4 = 0x00010000,
-+ PCAP_ST_BCLK_SLOT_2 = 0x00018000,
-+}ST_BCLK_TIME_SLOT_TYPE;
-+
-+typedef enum pcapST_CLK
-+{
-+ PCAP_ST_CLK_PLL_CLK_IN_13M0 = 0x00000000,
-+ PCAP_ST_CLK_PLL_CLK_IN_15M36 = 0x00000004,
-+ PCAP_ST_CLK_PLL_CLK_IN_16M8 = 0x00000008,
-+ PCAP_ST_CLK_PLL_CLK_IN_19M44 = 0x0000000c,
-+ PCAP_ST_CLK_PLL_CLK_IN_26M0 = 0x00000010,
-+ PCAP_ST_CLK_PLL_CLK_IN_EXT_MCLK = 0x00000014,
-+ PCAP_ST_CLK_PLL_CLK_IN_FSYNC = 0x00000018,
-+ PCAP_ST_CLK_PLL_CLK_IN_BITCLK = 0x0000001c
-+}ST_CLK_TYPE;
-+
-+typedef enum pcapDigitalAudioInterfaceMode
-+{
-+ PCAP_DIGITAL_AUDIO_INTERFACE_NORMAL = 0x00000000,
-+ PCAP_DIGITAL_AUDIO_INTERFACE_NETWORK = 0x00002000,
-+ PCAP_DIGITAL_AUDIO_INTERFACE_I2S = 0x00004000
-+}DIG_AUD_MODE_TYPE;
-+
-+typedef enum pcapMono
-+{
-+ PCAP_MONO_PGA_R_L_STEREO = 0x00000000,
-+ PCAP_MONO_PGA_RL = 0x00080000,
-+ PCAP_MONO_PGA_RL_3DB = 0x00100000,
-+ PCAP_MONO_PGA_RL_6DB = 0x00180000
-+}MONO_TYPE;
-+
-+typedef enum pcapVibratorVoltageLevel
-+{
-+ PCAP_VIBRATOR_VOLTAGE_LEVEL0 = 0x00000000,
-+ PCAP_VIBRATOR_VOLTAGE_LEVEL1 = 0x00100000,
-+ PCAP_VIBRATOR_VOLTAGE_LEVEL2 = 0x00200000,
-+ PCAP_VIBRATOR_VOLTAGE_LEVEL3 = 0x00300000
-+}VibratorVoltageLevel_TYPE;
-+
-+typedef enum pcapTouchScreenMode
-+{
-+ PCAP_TS_POSITION_X_MEASUREMENT = 0x00000000,
-+ PCAP_TS_POSITION_XY_MEASUREMENT = 0x00020000,
-+ PCAP_TS_PRESSURE_MEASUREMENT = 0x00040000,
-+ PCAP_TS_PLATE_X_MEASUREMENT = 0x00060000,
-+ PCAP_TS_PLATE_Y_MEASUREMENT = 0x00080000,
-+ PCAP_TS_STANDBY_MODE = 0x000a0000,
-+ PCAP_TS_NONTS_MODE = 0x000c0000
-+}TOUCH_SCREEN_DETECT_TYPE;
-+
-+typedef enum pcapADJRegister
-+{
-+ SSP_PCAP_ADJ_ISR_REGISTER = 0x00,
-+ SSP_PCAP_ADJ_MSR_REGISTER = 0x01,
-+ SSP_PCAP_ADJ_PSTAT_REGISTER = 0x02,
-+ SSP_PCAP_ADJ_VREG2_REGISTER = 0x06,
-+ SSP_PCAP_ADJ_AUX_VREG_REGISTER = 0x07,
-+ SSP_PCAP_ADJ_BATT_DAC_REGISTER = 0x08,
-+ SSP_PCAP_ADJ_ADC1_REGISTER = 0x09,
-+ SSP_PCAP_ADJ_ADC2_REGISTER = 0x0a,
-+ SSP_PCAP_ADJ_AUD_CODEC_REGISTER = 0x0b,
-+ SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER = 0x0c,
-+ SSP_PCAP_ADJ_ST_DAC_REGISTER = 0x0d,
-+ SSP_PCAP_ADJ_BUSCTRL_REGISTER = 0x14,
-+ SSP_PCAP_ADJ_PERIPH_REGISTER = 0x15,
-+ SSP_PCAP_ADJ_LOWPWR_CTRL_REGISTER = 0x18,
-+ SSP_PCAP_ADJ_TX_AUD_AMPS_REGISTER = 0x1a,
-+ SSP_PCAP_ADJ_GP_REG_REGISTER = 0x1b
-+}SSP_PCAP_SECONDARY_PROCESSOR_REGISTER;
-+
-+typedef enum pcapADJBit_SetType
-+{
-+ SSP_PCAP_ADJ_BIT_ISR_ADCDONEI = 0x00000001,
-+ SSP_PCAP_ADJ_BIT_ISR_TSI = 0x00000002,
-+ SSP_PCAP_ADJ_BIT_ISR_1HZI = 0x00000004,
-+ SSP_PCAP_ADJ_BIT_ISR_WHI = 0x00000008,
-+ SSP_PCAP_ADJ_BIT_ISR_WLI = 0x00000010,
-+ SSP_PCAP_ADJ_BIT_ISR_TODAI = 0x00000020,
-+ SSP_PCAP_ADJ_BIT_ISR_USB4VI = 0x00000040,
-+ SSP_PCAP_ADJ_BIT_ISR_ONOFFI = 0x00000080,
-+ SSP_PCAP_ADJ_BIT_ISR_ONOFF2I = 0x00000100,
-+ SSP_PCAP_ADJ_BIT_ISR_USB1VI = 0x00000200,
-+ SSP_PCAP_ADJ_BIT_ISR_MOBPORTI = 0x00000400,
-+ SSP_PCAP_ADJ_BIT_ISR_MB2I = 0x00000800,
-+ SSP_PCAP_ADJ_BIT_ISR_A1I = 0x00001000,
-+ SSP_PCAP_ADJ_BIT_ISR_STI = 0x00002000,
-+ SSP_PCAP_ADJ_BIT_ISR_PCI = 0x00004000,
-+ SSP_PCAP_ADJ_BIT_ISR_WARMI = 0x00008000,
-+ SSP_PCAP_ADJ_BIT_ISR_EOLI = 0x00010000,
-+ SSP_PCAP_ADJ_BIT_ISR_CLKI = 0x00020000,
-+ SSP_PCAP_ADJ_BIT_ISR_SYS_RSTI = 0x00040000,
-+ SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I = 0x00100000,
-+ SSP_PCAP_ADJ_BIT_ISR_SOFT_RESETI = 0x00200000,
-+ SSP_PCAP_ADJ_BIT_ISR_MNEXBI = 0x00400000,
-+
-+ SSP_PCAP_ADJ_BIT_MSR_ADCDONEM = 0x04000001,
-+ SSP_PCAP_ADJ_BIT_MSR_TSM = 0x04000002,
-+ SSP_PCAP_ADJ_BIT_MSR_1HZM = 0x04000004,
-+ SSP_PCAP_ADJ_BIT_MSR_WHM = 0x04000008,
-+ SSP_PCAP_ADJ_BIT_MSR_WLM = 0x04000010,
-+ SSP_PCAP_ADJ_BIT_MSR_TODAM = 0x04000020,
-+ SSP_PCAP_ADJ_BIT_MSR_USB4VM = 0x04000040,
-+ SSP_PCAP_ADJ_BIT_MSR_ONOFFM = 0x04000080,
-+ SSP_PCAP_ADJ_BIT_MSR_ONOFF2M = 0x04000100,
-+ SSP_PCAP_ADJ_BIT_MSR_USB1VM = 0x04000200,
-+ SSP_PCAP_ADJ_BIT_MSR_MOBPORTM = 0x04000400,
-+ SSP_PCAP_ADJ_BIT_MSR_MB2M = 0x04000800,
-+ SSP_PCAP_ADJ_BIT_MSR_A1M = 0x04001000,
-+ SSP_PCAP_ADJ_BIT_MSR_STM = 0x04002000,
-+ SSP_PCAP_ADJ_BIT_MSR_PCM = 0x04004000,
-+ SSP_PCAP_ADJ_BIT_MSR_WARMM = 0x04008000,
-+ SSP_PCAP_ADJ_BIT_MSR_EOLM = 0x04010000,
-+ SSP_PCAP_ADJ_BIT_MSR_CLKM = 0x04020000,
-+ SSP_PCAP_ADJ_BIT_MSR_SYS_RSTM = 0x04040000,
-+ SSP_PCAP_ADJ_BIT_MSR_ADCDONE2M = 0x04100000,
-+ SSP_PCAP_ADJ_BIT_MSR_SOFT_RESETM = 0x04200000,
-+ SSP_PCAP_ADJ_BIT_MSR_MNEXBM = 0x04400000,
-+
-+ SSP_PCAP_ADJ_BIT_PSTAT_USBDET_4V = 0x08000040,
-+ SSP_PCAP_ADJ_BIT_PSTAT_ONOFFSNS = 0x08000080,
-+ SSP_PCAP_ADJ_BIT_PSTAT_ONOFFSNS2 = 0x08000100,
-+ SSP_PCAP_ADJ_BIT_PSTAT_USBDET_1V = 0x08000200,
-+ SSP_PCAP_ADJ_BIT_PSTAT_MOBSENSB = 0x08000400,
-+ SSP_PCAP_ADJ_BIT_PSTAT_MB2SNS = 0x08000800,
-+ SSP_PCAP_ADJ_BIT_PSTAT_A1SNS = 0x08001000,
-+ SSP_PCAP_ADJ_BIT_PSTAT_MSTB = 0x08002000,
-+ SSP_PCAP_ADJ_BIT_PSTAT_EOL_STAT = 0x08010000,
-+ SSP_PCAP_ADJ_BIT_PSTAT_CLK_STAT = 0x08020000,
-+ SSP_PCAP_ADJ_BIT_PSTAT_SYS_RST = 0x08040000,
-+ SSP_PCAP_ADJ_BIT_PSTAT_BATTFBSNS = 0x08080000,
-+ SSP_PCAP_ADJ_BIT_PSTAT_BATT_DET_IN_SNS = 0x08200000,
-+ SSP_PCAP_ADJ_BIT_PSTAT_MNEXBSNS = 0x08400000,
-+ SSP_PCAP_ADJ_BIT_PSTAT_WARM_SYS_RST = 0x08800000,
-+
-+ SSP_PCAP_ADJ_BIT_VREG2_V1_STBY = 0x18000001,
-+ SSP_PCAP_ADJ_BIT_VREG2_V2_STBY = 0x18000002,
-+ SSP_PCAP_ADJ_BIT_VREG2_V3_STBY = 0x18000004,
-+ SSP_PCAP_ADJ_BIT_VREG2_V4_STBY = 0x18000008,
-+ SSP_PCAP_ADJ_BIT_VREG2_V5_STBY = 0x18000010,
-+ SSP_PCAP_ADJ_BIT_VREG2_V6_STBY = 0x18000020,
-+ SSP_PCAP_ADJ_BIT_VREG2_V7_STBY = 0x18000040,
-+ SSP_PCAP_ADJ_BIT_VREG2_V8_STBY = 0x18000080,
-+ SSP_PCAP_ADJ_BIT_VREG2_V9_STBY = 0x18000100,
-+ SSP_PCAP_ADJ_BIT_VREG2_V10_STBY = 0x18000200,
-+ SSP_PCAP_ADJ_BIT_VREG2_V1_LOWPWR = 0x18000400,
-+ SSP_PCAP_ADJ_BIT_VREG2_V2_LOWPWR = 0x18000800,
-+ SSP_PCAP_ADJ_BIT_VREG2_V3_LOWPWR = 0x18001000,
-+ SSP_PCAP_ADJ_BIT_VREG2_V4_LOWPWR = 0x18002000,
-+ SSP_PCAP_ADJ_BIT_VREG2_V5_LOWPWR = 0x18004000,
-+ SSP_PCAP_ADJ_BIT_VREG2_V6_LOWPWR = 0x18008000,
-+ SSP_PCAP_ADJ_BIT_VREG2_V7_LOWPWR = 0x18010000,
-+ SSP_PCAP_ADJ_BIT_VREG2_V8_LOWPWR = 0x18020000,
-+ SSP_PCAP_ADJ_BIT_VREG2_V9_LOWPWR = 0x18040000,
-+ SSP_PCAP_ADJ_BIT_VREG2_V10_LOWPWR = 0x18080000,
-+
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX1_EN = 0x1c000002,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX1_0 = 0x1c000004,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX1_1 = 0x1c000008,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX2_EN = 0x1c000010,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX2_0 = 0x1c000020,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX2_1 = 0x1c000040,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX3_EN = 0x1c000080,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX3_0 = 0x1c000100,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX3_1 = 0x1c000200,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX3_2 = 0x1c000400,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX3_3 = 0x1c000800,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX4_EN = 0x1c001000,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX4_0 = 0x1c002000,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX4_1 = 0x1c004000,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VSIM2_EN = 0x1c010000,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VSIM_EN = 0x1c020000,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VSIM_0 = 0x1c040000,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_V_VIB_EN = 0x1c080000,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_V_VIB_0 = 0x1c100000,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_V_VIB_1 = 0x1c200000,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX1_STBY = 0x1c400000,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX1_LOWPWR = 0x1c800000,
-+ SSP_PCAP_ADJ_BIT_AUX_VREG_SW3_STBY = 0x1d000000,
-+
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_DAC0 = 0x20000001,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_DAC1 = 0x20000002,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_DAC2 = 0x20000004,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_DAC3 = 0x20000008,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_DAC4 = 0x20000010,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_DAC5 = 0x20000020,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_DAC6 = 0x20000040,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_DAC7 = 0x20000080,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_B_FDBK = 0x20000100,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_EXT_ISENSE = 0x20000200,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_V_COIN0 = 0x20000400,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_V_COIN1 = 0x20000800,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_V_COIN2 = 0x20001000,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_V_COIN3 = 0x20002000,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_I_COIN = 0x20004000,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_COIN_CH_EN = 0x20008000,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_EOL_SEL0 = 0x20020000,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_EOL_SEL1 = 0x20040000,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_EOL_SEL2 = 0x20080000,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_EOL_CMP_EN = 0x20100000,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_BATT_DET_EN = 0x20200000,
-+ SSP_PCAP_ADJ_BIT_BATT_DAC_THERMBIAS_CTRL = 0x20400000,
-+
-+ SSP_PCAP_ADJ_BIT_ADC1_ADEN = 0x24000001,
-+ SSP_PCAP_ADJ_BIT_ADC1_RAND = 0x24000002,
-+ SSP_PCAP_ADJ_BIT_ADC1_AD_SEL1 = 0x24000004,
-+ SSP_PCAP_ADJ_BIT_ADC1_AD_SEL2 = 0x24000008,
-+ SSP_PCAP_ADJ_BIT_ADC1_ADA10 = 0x24000010,
-+ SSP_PCAP_ADJ_BIT_ADC1_ADA11 = 0x24000020,
-+ SSP_PCAP_ADJ_BIT_ADC1_ADA12 = 0x24000040,
-+ SSP_PCAP_ADJ_BIT_ADC1_ADA20 = 0x24000080,
-+ SSP_PCAP_ADJ_BIT_ADC1_ADA21 = 0x24000100,
-+ SSP_PCAP_ADJ_BIT_ADC1_ADA22 = 0x24000200,
-+ SSP_PCAP_ADJ_BIT_ADC1_ATO0 = 0x24000400,
-+ SSP_PCAP_ADJ_BIT_ADC1_ATO1 = 0x24000800,
-+ SSP_PCAP_ADJ_BIT_ADC1_ATO2 = 0x24001000,
-+ SSP_PCAP_ADJ_BIT_ADC1_ATO3 = 0x24002000,
-+ SSP_PCAP_ADJ_BIT_ADC1_ATOX = 0x24004000,
-+ SSP_PCAP_ADJ_BIT_ADC1_MTR1 = 0x24008000,
-+ SSP_PCAP_ADJ_BIT_ADC1_MTR2 = 0x24010000,
-+ SSP_PCAP_ADJ_BIT_ADC1_TS_M0 = 0x24020000,
-+ SSP_PCAP_ADJ_BIT_ADC1_TS_M1 = 0x24040000,
-+ SSP_PCAP_ADJ_BIT_ADC1_TS_M2 = 0x24080000,
-+ SSP_PCAP_ADJ_BIT_ADC1_TS_REF_LOWPWR = 0x24100000,
-+ SSP_PCAP_ADJ_BIT_ADC1_TS_REFENB = 0x24200000,
-+ SSP_PCAP_ADJ_BIT_ADC1_BATT_I_POLARITY = 0x24400000,
-+ SSP_PCAP_ADJ_BIT_ADC1_BATT_I_ADC = 0x24800000,
-+
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD10 = 0x28000001,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD11 = 0x28000002,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD12 = 0x28000004,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD13 = 0x28000008,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD14 = 0x28000010,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD15 = 0x28000020,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD16 = 0x28000040,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD17 = 0x28000080,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD18 = 0x28000100,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD19 = 0x28000200,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD20 = 0x28000400,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD21 = 0x28000800,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD22 = 0x28001000,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD23 = 0x28002000,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD24 = 0x28004000,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD25 = 0x28008000,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD26 = 0x28010000,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD27 = 0x28020000,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD28 = 0x28040000,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADD29 = 0x28080000,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADINC1 = 0x28100000,
-+ SSP_PCAP_ADJ_BIT_ADC2_ADINC2 = 0x28200000,
-+ SSP_PCAP_ADJ_BIT_ADC2_ASC = 0x28400000,
-+
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_AUDIHPF = 0x2c000001,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_SMB = 0x2c000002,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_AUDOHPF = 0x2c000004,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_CD_TS = 0x2c000008,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_DLM = 0x2c000010,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_ADITH = 0x2c000020,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_CDC_CLK0 = 0x2c000040,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_CDC_CLK1 = 0x2c000080,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_CDC_CLK2 = 0x2c000100,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_CLK_INV = 0x2c000200,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_FS_INV = 0x2c000400,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_DF_RESET = 0x2c000800,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_CDC_EN = 0x2c001000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_CDC_CLK_EN = 0x2c002000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_FS_8K_16K = 0x2c004000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_DIG_AUD_IN = 0x2c008000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_CLK_IN_SEL = 0x2c010000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_MIC2_MUX = 0x2c020000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_MIC2IG0 = 0x2c040000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_MIC2IG1 = 0x2c080000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_MIC2IG2 = 0x2c100000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_MIC2IG3 = 0x2c200000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_MIC2IG4 = 0x2c400000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_MIC2IG_PRI_ADJ = 0x2c800000,
-+ SSP_PCAP_ADJ_BIT_AUD_CODEC_CDC_PRI_ADJ = 0x2c200000,
-+
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_A1_EN = 0x30000001,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_A2_EN = 0x30000002,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_A4_EN = 0x30000010,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_ARIGHT_EN = 0x30000020,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_ALEFT_EN = 0x30000040,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_CD_BYP = 0x30000080,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_CDC_SW = 0x30000100,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_ST_DAC_SW = 0x30000200,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_PGA_IN_SW = 0x30000400,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_PGA_R_EN = 0x30000800,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_PGA_L_EN = 0x30001000,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_AUDOG0 = 0x30002000,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_AUDOG1 = 0x30004000,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_AUDOG2 = 0x30008000,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_AUDOG3 = 0x30010000,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_A1CTRL = 0x30020000,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_MONO0 = 0x30080000,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_MONO1 = 0x30100000,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_AUDOG_PRI_ADJ = 0x30200000,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_MONO_PRI_ADJ = 0x30400000,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_RX_PRI_ADJ0 = 0x30800000,
-+ SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_RX_PRI_ADJ1 = 0x31000000,
-+
-+ SSP_PCAP_ADJ_BIT_ST_DAC_SMB_ST_DAC = 0x34000001,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_STDET_EN = 0x34000002,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_ST_CLK0 = 0x34000004,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_ST_CLK1 = 0x34000008,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_ST_CLK2 = 0x34000010,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_ST_CLK_EN = 0x34000020,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_DF_RESET_ST_DAC = 0x34000040,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_ST_DAC_EN = 0x34000080,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_SR0 = 0x34000100,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_SR1 = 0x34000200,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_SR2 = 0x34000400,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_SR3 = 0x34000800,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_DIG_AUD_IN_ST_DAC = 0x34001000,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_DIG_AUD_FS0 = 0x34002000,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_DIG_AUD_FS1 = 0x34004000,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_BCLK0 = 0x34008000,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_BCLK1 = 0x34010000,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_ST_CLK_INV = 0x34020000,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_ST_FS_INV = 0x34040000,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_ST_DAC_CLK_IN_SEL = 0x34080000,
-+ SSP_PCAP_ADJ_BIT_ST_DAC_ST_DAC_PRI_ADJ = 0x35000000,
-+
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_FSENB = 0x50000001,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_USB_SUSPEND = 0x50000002,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PU = 0x50000004,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PD = 0x50000008,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN = 0x50000010,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PS = 0x50000020,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_MSTR_EN = 0x50000040,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_VBUS_PD_ENB = 0x50000080,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_CURRLIM = 0x50000100,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB = 0x50000200,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_RS232_DIR = 0x50000400,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_SE0_CONN = 0x50000800,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PDM = 0x50001000,
-+ SSP_PCAP_ADJ_BIT_BUSCTRL_BUS_PRI_ADJ = 0x51000000,
-+
-+ SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL0 = 0x54000001,
-+ SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL1 = 0x54000002,
-+ SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL2 = 0x54000004,
-+ SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL3 = 0x54000008,
-+ SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL4 = 0x54000010,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDR_EN = 0x54000020,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDG_EN = 0x54000040,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDR_CTRL0 = 0x54000080,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDR_CTRL1 = 0x54000100,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDR_CTRL2 = 0x54000200,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDR_CTRL3 = 0x54000400,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDG_CTRL0 = 0x54000800,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDG_CTRL1 = 0x54001000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDG_CTRL2 = 0x54002000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDG_CTRL3 = 0x54004000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDR_I0 = 0x54008000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDR_I1 = 0x54010000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDG_I0 = 0x54020000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_LEDG_I1 = 0x54040000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_SKIP = 0x54080000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL0 = 0x54100000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL1 = 0x54200000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL2 = 0x54400000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL3 = 0x54800000,
-+ SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL4 = 0x55000000,
-+
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VAUX2_STBY = 0x60000001,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VAUX2_LOWPWR = 0x60000002,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VAUX3_STBY = 0x60000004,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VAUX3_LOWPWR = 0x60000008,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VAUX4_STBY = 0x60000010,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VAUX4_LOWPWR = 0x60000020,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VSIM_LOWPWR = 0x60000040,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VSIM2_LOWPWR = 0x60000080,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW1_MODE00 = 0x60000100,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW1_MODE01 = 0x60000200,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW1_MODE10 = 0x60000400,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW1_MODE11 = 0x60000800,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW10_DVS = 0x60001000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW11_DVS = 0x60002000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW12_DVS = 0x60004000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW13_DVS = 0x60008000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW2_MODE00 = 0x60010000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW2_MODE01 = 0x60020000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW2_MODE10 = 0x60040000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW2_MODE11 = 0x60080000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW20_DVS = 0x60100000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW21_DVS = 0x60200000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW22_DVS = 0x60400000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW23_DVS = 0x60800000,
-+ SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VC_STBY = 0x61000000,
-+
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_AUDIG0 = 0x68000001,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_AUDIG1 = 0x68000002,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_AUDIG2 = 0x68000004,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_AUDIG3 = 0x68000008,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_AUDIG4 = 0x68000010,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_A3_EN = 0x68000020,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_A3_MUX = 0x68000040,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_A5_EN = 0x68000080,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_A5_MUX = 0x68000100,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_EXT_MIC_MUX = 0x68000200,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_MB_ON2 = 0x68000400,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_MB_ON1 = 0x68000800,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_A1ID_TX = 0x68001000,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_A1_CONFIG = 0x68002000,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_AHS_CONFIG = 0x68004000,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_A2_CONFIG = 0x68008000,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_AUDIO_LOWPWR = 0x68080000,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_AUDIO_STBY = 0x68100000,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_V2_EN_2 = 0x68200000,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_AUDIG_PRI_ADJ = 0x68400000,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_TX_PRI_ADJ0 = 0x68800000,
-+ SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_TX_PRI_ADJ1 = 0x69000000,
-+
-+ SSP_PCAP_ADJ_BIT_SYS_RST_CLR = 0x6c000001,
-+ SSP_PCAP_ADJ_BIT_SYS_RST_MODE0 = 0x6c000002,
-+ SSP_PCAP_ADJ_BIT_SYS_RST_MODE1 = 0x6c000004,
-+ SSP_PCAP_ADJ_BIT_SYS_VFLASH_0 = 0x6c000008,
-+ SSP_PCAP_ADJ_BIT_SYS_VFLASH_1 = 0x6c000010,
-+ SSP_PCAP_ADJ_BIT_SYS_MID_SELECT = 0x6c000020,
-+ SSP_PCAP_ADJ_BIT_SYS_MID_FET = 0x6c000040,
-+ SSP_PCAP_ADJ_BIT_SYS_MAIN_LOW = 0x6c000080,
-+ SSP_PCAP_ADJ_BIT_SYS_BATTFB_DIS = 0x6c000100,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG9 = 0x6c000200,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG10 = 0x6c000400,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG11 = 0x6c000800,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG12 = 0x6c001000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG13 = 0x6c002000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG14 = 0x6c004000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG15 = 0x6c008000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG16 = 0x6c010000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG17 = 0x6c020000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG18 = 0x6c040000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG19 = 0x6c080000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG20 = 0x6c100000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG21 = 0x6c200000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG22 = 0x6c400000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG23 = 0x6c800000,
-+ SSP_PCAP_ADJ_BIT_SYS_GP_REG24 = 0x6d000000
-+
-+}SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE;
-+
-+/************************ FUNCTION PROTOTYPES **************************************/
-+extern void ssp_pcap_init(void);
-+extern void ssp_pcap_release(void);
-+
-+extern void ssp_pcap_open(SSP_PCAP_INIT_DRIVER_TYPE portType);
-+extern void ssp_pcap_close(void);
-+
-+extern void ssp_pcap_intoSleep_callBack(void);
-+extern void ssp_pcap_wakeUp_callBack(void);
-+
-+
-+extern SSP_PCAP_STATUS SSP_PCAP_write_data_to_PCAP(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER ssp_pcap_register,U32 ssp_pcap_register_value);
-+extern SSP_PCAP_STATUS SSP_PCAP_read_data_from_PCAP(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER ssp_pcap_register,P_U32 p_ssp_pcap_register_value);
-+
-+extern SSP_PCAP_STATUS SSP_PCAP_bit_set(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE ssp_pcap_bit ) ;
-+extern SSP_PCAP_STATUS SSP_PCAP_bit_clean(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE ssp_pcap_bit ) ;
-+extern SSP_PCAP_BIT_STATUS SSP_PCAP_get_bit_from_buffer(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE ssp_pcap_bit ) ;
-+extern SSP_PCAP_BIT_STATUS SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE ssp_pcap_bit ) ;
-+extern U32 SSP_PCAP_get_register_value_from_buffer(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER ssp_pcap_register ) ;
-+
-+extern SSP_PCAP_STATUS SSP_PCAP_TSI_mode_set(TOUCH_SCREEN_DETECT_TYPE mode_Type );
-+extern SSP_PCAP_STATUS SSP_PCAP_TSI_start_XY_read(void);
-+extern SSP_PCAP_STATUS SSP_PCAP_TSI_get_XY_value(P_U16 p_x,P_U16 p_y);
-+extern SSP_PCAP_STATUS SSP_PCAP_CDC_CLK_set(PHONE_CDC_CLOCK_TYPE clkType);
-+
-+extern SSP_PCAP_STATUS SSP_PCAP_CDC_SR_set(ST_SAMPLE_RATE_TYPE srType);
-+extern SSP_PCAP_STATUS SSP_PCAP_BCLK_set(ST_BCLK_TIME_SLOT_TYPE bclkType);
-+extern SSP_PCAP_STATUS SSP_PCAP_STCLK_set(ST_CLK_TYPE stClkType);
-+extern SSP_PCAP_STATUS SSP_PCAP_DIG_AUD_FS_set(DIG_AUD_MODE_TYPE fsType);
-+extern SSP_PCAP_STATUS SSP_PCAP_AUDIG_set(U32 audioInGain);
-+extern SSP_PCAP_STATUS SSP_PCAP_MONO_set(MONO_TYPE monoType);
-+extern SSP_PCAP_STATUS SSP_PCAP_AUDOG_set(U32 audioOutGain);
-+
-+extern SSP_PCAP_STATUS SSP_PCAP_V_VIB_level_set(VibratorVoltageLevel_TYPE VIBLevelType);
-+extern SSP_PCAP_STATUS SSP_PCAP_configure_USB_UART_transeiver(SSP_PCAP_PORT_TYPE portType);
-+extern SSP_PCAP_BIT_STATUS SSP_PCAP_get_audio_in_status(void);
-+
-+/* for log */
-+extern void pcap_log_add_pure_data(u8* pData,u32 len);
-+extern void pcap_log_add_data(u8* pData,u32 len);
-+
-+/* screen lock on/off handler */
-+extern void ssp_pcap_screenlock_lock(u32 data);
-+extern void ssp_pcap_screenlock_unlock(u32 data);
-+
-+#ifdef __cplusplus
-+}
-+#endif
-+
-+#endif
-Index: linux-2.6.16.5-a/drivers/misc/ezx/ssp_pcap_main.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/ssp_pcap_main.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,2568 @@
-+/* (c) Copyright Motorola 2002, All rights reserved.
-+ Motorola Confidential Proprietary
-+ Contains confidential proprietary information of Motorola, Inc.
-+ Reverse engineering is prohibited.
-+ The copyright notice does not imply publication.
-+
-+ Project Name : EZX
-+ Project No. :
-+ Title :
-+ File Name :
-+ Description :
-+
-+ ************** REVISION HISTORY **********************************************
-+ Date Author Reference
-+ ======== ========== ==========================
-+ 2002-07-02 weiqiang lin create
-+ 2004-02-09 weiqiang lin update PM for Bulverde OS libdd74345.
-+ 2004-04-13 weiqiang lin update accessory usb attach and detach
-+ 2004-04-27 weiqiang lin send the USB accessory detach/attach information to PM
-+ 2004-05-11 weiqiang lin after sleep TC_MM_EN will be high else will be low
-+ 2004-06-24 Cheng Xuefeng remove the SSP_PCAP_configure_USB_UART_transeiver()
-+ 2004-08-19 weiqiang lin after sleep set SW1 output 1.3V and low power mode and when headset button press/release, send an event to PM
-+ 2004-08-31 weiqiang lin remove the headset button press/release event to PM.
-+*/
-+
-+#ifdef __cplusplus
-+extern "C" {
-+#endif
-+
-+#include <linux/config.h>
-+#include <linux/module.h>
-+#include <linux/kernel.h>
-+#include <linux/sched.h>
-+#include <linux/errno.h>
-+#include <linux/string.h>
-+#include <linux/interrupt.h>
-+#include <linux/slab.h>
-+#include <linux/fb.h>
-+#include <linux/delay.h>
-+#include <linux/pm.h>
-+#include <linux/init.h>
-+#include <linux/apm_bios.h>
-+
-+#include <asm/hardware.h>
-+#include <asm/io.h>
-+#include <asm/irq.h>
-+
-+#include <asm/arch/pxa-regs.h>
-+#include <asm/arch/ezx.h>
-+#ifndef TRUE
-+#define TRUE 1
-+#endif
-+
-+#ifndef FALSE
-+#define FALSE 0
-+#endif
-+
-+#include "ssp_pcap.h"
-+//#define SSP_PCAP_OPERATE_WITH_SPI
-+
-+static u32 ssp_pcap_operate_pin_with_inverter;
-+static u32 ssp_pcap_rxd_pin_with_inverter;
-+//#define SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+
-+#ifdef _DEBUG_BOARD
-+#define SSP_PCAP_DEBUG_BOARD
-+#endif
-+
-+/* 0 -- unlock 1- lock */
-+static u32 ssp_pcap_screenlock_status;
-+static struct timer_list ssp_pcap_screenlock_timer;
-+static void ssp_pcap_screenlock_lockhandler(u32 data);
-+
-+static struct timer_list ssp_start_adc_timer;
-+static struct timer_list ssp_tsi_timer;
-+static struct timer_list ssp_usb_accessory_debounce_timer;
-+
-+static U32 ssp_pcap_status = 0;
-+static U32 ssp_pcap_registerValue[SSP_PCAP_REGISTER_NUMBER] = {0};
-+
-+SSP_PCAP_BIT_STATUS SSP_PCAP_get_audio_in_status(void);
-+SSP_PCAP_STATUS SSP_PCAP_write_data_to_PCAP(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER ssp_pcap_register,U32 ssp_pcap_register_value);
-+SSP_PCAP_STATUS SSP_PCAP_read_data_from_PCAP(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER ssp_pcap_register,P_U32 p_ssp_pcap_register_value);
-+
-+SSP_PCAP_STATUS SSP_PCAP_bit_set(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE ssp_pcap_bit ) ;
-+SSP_PCAP_STATUS SSP_PCAP_bit_clean(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE ssp_pcap_bit ) ;
-+SSP_PCAP_BIT_STATUS SSP_PCAP_get_bit_from_buffer(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE ssp_pcap_bit ) ;
-+SSP_PCAP_BIT_STATUS SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE ssp_pcap_bit ) ;
-+U32 SSP_PCAP_get_register_value_from_buffer(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER ssp_pcap_register ) ;
-+
-+#ifdef SSP_PCAP_OPERATE_WITH_SPI
-+static wait_queue_head_t ssp_pcap_send_wait;
-+static U32 ssp_pcap_readValue;
-+static void ssp_interrupt_routine(int irq, void *dev_id, struct pt_regs *regs );
-+void ssp_put_intoData(U32 pcapValue);
-+#endif
-+
-+static spinlock_t pcapoperation_lock = SPIN_LOCK_UNLOCKED;
-+static void ssp_pcap_interrupt_routine(int irq, void *dev_id, struct pt_regs *regs );
-+//static U32 ssp_pcapRegisterReadOut = 0;
-+
-+//static void usb_hardware_switch(void);
-+
-+//static struct timer_list usb_switch_timer;
-+
-+void ssp_pcap_init(void);
-+void ssp_pcap_release(void);
-+void ssp_pcap_clear_int(void);
-+void ssp_pcap_intoSleepCallBack(void);
-+void ssp_pcap_wakeUpCallBack(void);
-+
-+extern int usb_gpio_init(void);
-+extern int stop_usb(void);
-+static void ssp_tsi_keeper(u32 data);
-+static void ssp_usb_accessory_debounce_handler(u32 data);
-+
-+extern void ezx_ts_dataReadok_interrupt(int irq,void* dev_id, struct pt_regs *regs);
-+extern void ezx_ts_touch_interrupt(int irq,void* dev_id, struct pt_regs *regs);
-+void (*headjack_change_interrupt_routine)(int ch,void *dev_id,struct pt_regs *regs);
-+void (*mic_change_interrupt_routine)(int ch,void *dev_id,struct pt_regs *regs);
-+//extern u8 pxafb_ezx_getLCD_status(void);
-+
-+int (*cable_hotplug_attach)(ACCESSORY_DEVICE_STATUS status);
-+static struct ssp_interrupt_info sspUsbAccessoryInfo;
-+
-+void SSP_PCAP_MMCSD_poweroff(void)
-+{
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX2_EN);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX2_EN);
-+}
-+EXPORT_SYMBOL(SSP_PCAP_MMCSD_poweroff);
-+
-+void SSP_PCAP_MMCSD_poweron(void)
-+{
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX2_EN);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX2_EN);
-+}
-+EXPORT_SYMBOL(SSP_PCAP_MMCSD_poweron);
-+
-+static void accessory_bus_detect_handler(ACCESSORY_TYPE type,ACCESSORY_DEVICE_STATUS status,void* privdata )
-+{
-+ sspUsbAccessoryInfo.type = (u32)type;
-+ sspUsbAccessoryInfo.status = (u32)status;
-+ sspUsbAccessoryInfo.privdata = privdata;
-+ del_timer(&ssp_usb_accessory_debounce_timer);
-+ ssp_usb_accessory_debounce_timer.data = ( unsigned long ) &sspUsbAccessoryInfo;
-+ /* 2 seconds protect timer */
-+ ssp_usb_accessory_debounce_timer.expires = jiffies + SSP_SEND_MSG_USB_ACCESSORY_INFO_DEBOUNCE;
-+ add_timer(&ssp_usb_accessory_debounce_timer);
-+ return;
-+}
-+
-+static void ssp_usb_accessory_debounce_handler(u32 data)
-+{
-+ struct ssp_interrupt_info * pMyInfo;
-+ ACCESSORY_TYPE type;
-+ ACCESSORY_DEVICE_STATUS status;
-+
-+ pMyInfo = (struct ssp_interrupt_info *)data;
-+ type = ( ACCESSORY_TYPE) pMyInfo->type;
-+ status = ( ACCESSORY_DEVICE_STATUS) pMyInfo->status;
-+
-+ switch(type)
-+ {
-+ case ACCESSORY_DEVICE_USB_PORT:
-+ if (cable_hotplug_attach)
-+ (*cable_hotplug_attach)(status);
-+ switch(status)
-+ {
-+ case ACCESSORY_DEVICE_STATUS_DETACHED:
-+ apm_queue_event(KRNL_ACCS_DETACH);
-+ break;
-+ case ACCESSORY_DEVICE_STATUS_ATTACHED:
-+ apm_queue_event(KRNL_ACCS_ATTACH);
-+ break;
-+ default:
-+ break;
-+ }
-+ break;
-+ default:
-+ break;
-+ }
-+ return;
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION: log system stored in buffer. it can output via FFUART. also you can change a little to other output mode.
-+
-+ INPUTS: none.
-+
-+
-+ OUTPUTS: none.
-+
-+
-+ IMPORTANT NOTES: the macro PCAP_LOG_FFUART_OUT is a switch.
-+ it is auto-output to FFUART every PCAP_LOG_OUTPUT_TIMER seconds
-+
-+
-+---------------------------------------------------------------------------*/
-+/* record log system by linwq */
-+//#define PCAP_LOG_FFUART_OUT
-+
-+#ifdef PCAP_LOG_FFUART_OUT
-+static struct timer_list pcap_outlog_timer;
-+
-+#define PCAP_LOG_OUTPUT_TIMER 60
-+#define PCAP_LOG_RECORD_LENGTH 50000
-+
-+unsigned char pcap_log_data[PCAP_LOG_RECORD_LENGTH];
-+
-+u8* pcap_log_now_address = pcap_log_data;
-+#define PCAP_LOG_START_ADDRESS pcap_log_data
-+#define PCAP_LOG_END_ADDRESS pcap_log_data + PCAP_LOG_RECORD_LENGTH
-+u32 pcap_log_len = 0;
-+
-+void pcap_log_add_pure_data(u8* pData,u32 len)
-+{
-+ u32 i;
-+ if ((pData ==NULL)|| len == 0)
-+ return;
-+ for(i = 0;i<len;i++)
-+ {
-+ *pcap_log_now_address ++ = pData[i];
-+ if( PCAP_LOG_END_ADDRESS == pcap_log_now_address )
-+ pcap_log_now_address = PCAP_LOG_START_ADDRESS;
-+ pcap_log_len++;
-+ if(pcap_log_len >= PCAP_LOG_RECORD_LENGTH)
-+ pcap_log_len = PCAP_LOG_RECORD_LENGTH;
-+ }
-+ return;
-+}
-+
-+void pcap_log_add_data(u8* pData,u32 len)
-+{
-+ u32 i;
-+ u8 temp[20];
-+ if ((pData ==NULL)|| len == 0)
-+ return;
-+ sprintf(temp,"\n <%d MS>",(int)(OSCR/3686));
-+ for(i = 0;i<(u32)strlen(temp);i++)
-+ {
-+ *pcap_log_now_address ++ = temp[i];
-+ if( PCAP_LOG_END_ADDRESS == pcap_log_now_address )
-+ pcap_log_now_address = PCAP_LOG_START_ADDRESS;
-+ pcap_log_len++;
-+ if(pcap_log_len >= PCAP_LOG_RECORD_LENGTH)
-+ pcap_log_len = PCAP_LOG_RECORD_LENGTH;
-+ }
-+
-+ for(i = 0;i<len;i++)
-+ {
-+ *pcap_log_now_address ++ = pData[i];
-+ if( PCAP_LOG_END_ADDRESS == pcap_log_now_address )
-+ pcap_log_now_address = PCAP_LOG_START_ADDRESS;
-+ pcap_log_len++;
-+ if(pcap_log_len >= PCAP_LOG_RECORD_LENGTH)
-+ pcap_log_len = PCAP_LOG_RECORD_LENGTH;
-+ }
-+ return;
-+}
-+
-+static void pcap_log_output_from_ffuart(void)
-+{
-+ u32 i;
-+ u32 ssp_ffuart_dll,ssp_ffuart_dlh;
-+ u8 ssp_ffuart_cken = 1,ssp_ffuart_en = 1;
-+ if(0 == pcap_log_len)
-+ return;
-+
-+ /* if cable in NOT UART cable, should return */
-+ printk("\n *********log out ************* \n <%d jiffies>log:",(int)jiffies);
-+ local_irq_disable();
-+ if(!(CKEN&CKEN6_FFUART))
-+ {
-+ ssp_ffuart_cken = 0;
-+ CKEN |= CKEN6_FFUART;
-+ pcap_log_add_data("FFUART CLK not ENABLE!",strlen("FFUART CLK not ENABLE!"));
-+ }
-+
-+ FFLCR = (FFLCR&0xff)|0x80;
-+ ssp_ffuart_dll = FFDLL&0xff;
-+ ssp_ffuart_dlh = FFDLH&0xff;
-+ FFLCR = FFLCR&0x7f;
-+
-+ if((0x08 !=ssp_ffuart_dll)||(0x00 != ssp_ffuart_dlh))
-+ {
-+ FFLCR = 0x83;
-+ FFDLL = 0x08;
-+ FFDLH = 0;
-+ FFLCR = 0x03;
-+ }
-+
-+ if(!(FFIER&0x00000040))
-+ {
-+ ssp_ffuart_en = 0;
-+ FFIER |= 0x00000040;
-+ pcap_log_add_data("FFUART model not ENABLE!",strlen("FFUART model not ENABLE!"));
-+ }
-+
-+ for(i=0;i<pcap_log_len;i++)
-+ {
-+ while((FFLSR &0x40) == 0);
-+ FFTHR = pcap_log_data[i];
-+ }
-+ if(!ssp_ffuart_cken)
-+ {
-+ CKEN &= ~CKEN6_FFUART;
-+ }
-+
-+
-+ if((0x08 !=ssp_ffuart_dll)||(0x00 != ssp_ffuart_dlh))
-+ {
-+ FFLCR = 0x83;
-+ FFDLL = ssp_ffuart_dll;
-+ FFDLH = ssp_ffuart_dlh;
-+ FFLCR = 0x03;
-+ }
-+
-+ if(!ssp_ffuart_en)
-+ {
-+ CKEN &= ~CKEN6_FFUART;
-+ }
-+ local_irq_enable();
-+
-+ printk("\n ********* log end ************ \n");
-+}
-+
-+static void pcap_log_output_from_stuart(void)
-+{
-+ u32 i;
-+ u32 ssp_stuart_dll,ssp_stuart_dlh;
-+ u8 ssp_stuart_cken = 1,ssp_stuart_en = 1;
-+ if(0 == pcap_log_len)
-+ return;
-+
-+ /* if cable in NOT UART cable, should return */
-+ printk("\n *********log out ************* \n <%d jiffies>log:",(int)jiffies);
-+ local_irq_disable();
-+ if(!(CKEN&CKEN5_STUART))
-+ {
-+ ssp_stuart_cken = 0;
-+ CKEN |= CKEN5_STUART;
-+ pcap_log_add_data("STUART CLK not ENABLE!",strlen("STUART CLK not ENABLE!"));
-+ }
-+
-+ STLCR = (STLCR&0xff)|0x80;
-+ ssp_stuart_dll = STDLL&0xff;
-+ ssp_stuart_dlh = STDLH&0xff;
-+ STLCR &= 0x7f;
-+
-+ if((0x08 !=ssp_stuart_dll)||(0x00 != ssp_stuart_dlh))
-+ {
-+ STLCR = 0x83;
-+ STDLL = 0x08;
-+ STDLH = 0;
-+ STLCR = 0x03;
-+ }
-+
-+ if(!(STIER&0x00000040))
-+ {
-+ ssp_stuart_en = 0;
-+ STIER |= 0x00000040;
-+ pcap_log_add_data("STUART model not ENABLE!",strlen("STUART model not ENABLE!"));
-+ }ACCESSORY_DEVICE_STATUS
-+
-+ for(i=0;i<pcap_log_len;i++)
-+ {
-+ while((STLSR &0x40) == 0);
-+ STTHR = pcap_log_data[i];
-+ }
-+ if(!ssp_stuart_cken)
-+ {
-+ CKEN &= ~CKEN5_STUART;
-+ }
-+
-+
-+ if((0x08 !=ssp_stuart_dll)||(0x00 != ssp_stuart_dlh))
-+ {
-+ STLCR = 0x83;
-+ STDLL = ssp_stuart_dll;
-+ STDLH = ssp_stuart_dlh;
-+ STLCR = 0x03;
-+ }
-+
-+ if(!ssp_stuart_en)
-+ {
-+ CKEN &= ~CKEN5_STUART;
-+ }
-+ local_irq_enable();
-+
-+ printk("\n ********* log end ************ \n");
-+}
-+
-+
-+static void pcap_output_log_handler( u32 data)
-+{
-+ pcap_log_output_from_stuart();
-+
-+ pcap_outlog_timer.function = pcap_output_log_handler;
-+ pcap_outlog_timer.expires = (jiffies + PCAP_LOG_OUTPUT_TIMER * HZ);
-+ add_timer(&pcap_outlog_timer);
-+}
-+
-+static void pcap_output_log_init(void)
-+{
-+ init_timer(&pcap_outlog_timer);
-+ pcap_outlog_timer.function = pcap_output_log_handler;
-+ pcap_outlog_timer.expires = (jiffies + 2*PCAP_LOG_OUTPUT_TIMER * HZ);
-+ add_timer(&pcap_outlog_timer);
-+}
-+/* record log end */
-+#else
-+void pcap_log_add_pure_data(u8* pData,u32 len)
-+{
-+ return;
-+}
-+
-+void pcap_log_add_data(u8* pData,u32 len)
-+{
-+ return;
-+}
-+#endif
-+
-+void ssp_pcap_screenlock_lock(u32 data)
-+{
-+ u32 flags;
-+ save_flags(flags);
-+ local_irq_disable();
-+ del_timer(&ssp_tsi_timer);
-+ ssp_pcap_clear_int();
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ ssp_pcap_screenlock_status = 1 ;
-+ restore_flags(flags);
-+}
-+
-+void ssp_pcap_screenlock_unlock(u32 data)
-+{
-+ u32 flags;
-+ save_flags(flags);
-+ local_irq_disable();
-+ del_timer(&ssp_pcap_screenlock_timer);
-+ ssp_pcap_clear_int();
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ ssp_pcap_screenlock_status = 0 ;
-+ restore_flags(flags);
-+}
-+
-+static void ssp_pcap_screenlock_lockhandler(u32 data)
-+{
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("lockscreen timer arrived!",strlen("lockscreen timer arrived!"));
-+#endif
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ISR_TSI);
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ return;
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION: GPIO init for operating PCAP via GPIO mode.
-+
-+ INPUTS: none.
-+
-+
-+ OUTPUTS: none.
-+
-+
-+ IMPORTANT NOTES: auto-recognized pcap's CE signal. init PCAP's register.
-+
-+
-+---------------------------------------------------------------------------*/
-+#ifndef SSP_PCAP_OPERATE_WITH_SPI
-+
-+static u32 test_pcap_cs_rxd(void)
-+{
-+ u32 ret = FALSE;
-+ u32 temp;
-+ /* write a data 0x0003ffff to IMR */
-+ SSP_PCAP_write_data_to_PCAP(1, 0x0003ffff);
-+ SSP_PCAP_read_data_from_PCAP(1, &temp);
-+ if( 0x0003ffff == temp)
-+ ret = TRUE;
-+ return ret;
-+}
-+
-+static void ssp_pcap_gpioInit(void)
-+{
-+ u32 i;
-+ u32 tempValue;
-+ u32 ret;
-+ /* stop SPI port work mode disable SPI clock */
-+ SSCR0 = 0x00000000;
-+ CKEN &= ~CKEN23_SSP1;
-+
-+ /* the four PIN as GPIO mode */
-+ pxa_gpio_mode(GPIO_SPI_CLK|GPIO_OUT);
-+ pxa_gpio_mode(GPIO_SPI_CE|GPIO_OUT);
-+ pxa_gpio_mode(GPIO_SPI_MOSI|GPIO_OUT);
-+ pxa_gpio_mode(GPIO_SPI_MISO|GPIO_IN);
-+
-+ /* test pcap's CE with inverter??? */
-+ ssp_pcap_operate_pin_with_inverter = 0;
-+ ssp_pcap_rxd_pin_with_inverter = 0;
-+
-+ /* deassert SEC_CE */
-+ GPCR(GPIO_SPI_CE) = GPIO_bit(GPIO_SPI_CE);
-+ for(i=0;i<500;i++);
-+ ret = test_pcap_cs_rxd();
-+
-+ if (FALSE == ret)
-+ {
-+ ssp_pcap_operate_pin_with_inverter = 0;
-+ ssp_pcap_rxd_pin_with_inverter = 1;
-+ /* deassert SEC_CE */
-+ GPCR(GPIO_SPI_CE) = GPIO_bit(GPIO_SPI_CE);
-+ for(i=0;i<500;i++);
-+ ret = test_pcap_cs_rxd();
-+ }
-+
-+ if (FALSE == ret)
-+ {
-+ ssp_pcap_operate_pin_with_inverter = 1;
-+ ssp_pcap_rxd_pin_with_inverter = 0;
-+ /* deassert SEC_CE */
-+ GPSR(GPIO_SPI_CE) = GPIO_bit(GPIO_SPI_CE);
-+ for(i=0;i<500;i++);
-+ ret = test_pcap_cs_rxd();
-+ }
-+
-+
-+ if (FALSE == ret)
-+ {
-+ ssp_pcap_operate_pin_with_inverter = 1;
-+ ssp_pcap_rxd_pin_with_inverter = 1;
-+ /* deassert SEC_CE */
-+ GPSR(GPIO_SPI_CE) = GPIO_bit(GPIO_SPI_CE);
-+ for(i=0;i<500;i++);
-+ ret = test_pcap_cs_rxd();
-+ }
-+
-+ if (FALSE == ret )
-+ {
-+ printk("\n Bulverde can not communicate with PCAP!!!!");
-+ return;
-+ }
-+
-+ SSP_PCAP_write_data_to_PCAP(1, 0x0013ffff);
-+
-+ for(i=0; i<32 ;i++)
-+ {
-+ if(SSP_PCAP_SUCCESS == SSP_PCAP_read_data_from_PCAP(i,&tempValue))
-+ {
-+ ssp_pcap_registerValue[i] = tempValue;
-+ }
-+ else
-+ {
-+ ssp_pcap_registerValue[i] = 0;
-+ }
-+ }
-+ return;
-+}
-+
-+
-+static void ssp_pcap_gpioClkControl(u32 bitValue)
-+{
-+ if(bitValue)
-+ {
-+ GPSR(GPIO_SPI_CLK) = GPIO_bit(GPIO_SPI_CLK);
-+ }
-+ else
-+ {
-+ GPCR(GPIO_SPI_CLK) = GPIO_bit(GPIO_SPI_CLK);
-+ }
-+}
-+
-+static void ssp_pcap_gpioFrmControl(u32 bitValue)
-+{
-+ if( ssp_pcap_operate_pin_with_inverter )
-+ {
-+ if(bitValue)
-+ {
-+ GPCR(GPIO_SPI_CE) = GPIO_bit(GPIO_SPI_CE);
-+ }
-+ else
-+ {
-+ GPSR(GPIO_SPI_CE) = GPIO_bit(GPIO_SPI_CE);
-+ }
-+ }
-+ else
-+ {
-+ if(bitValue)
-+ {
-+ GPSR(GPIO_SPI_CE) = GPIO_bit(GPIO_SPI_CE);
-+ }
-+ else
-+ {
-+ GPCR(GPIO_SPI_CE) = GPIO_bit(GPIO_SPI_CE);
-+ }
-+ }
-+}
-+
-+static void ssp_pcap_gpioTxdControl(u32 bitValue)
-+{
-+ if(bitValue)
-+ {
-+ GPSR(GPIO_SPI_MOSI) = GPIO_bit(GPIO_SPI_MOSI);
-+ }
-+ else
-+ {
-+ GPCR(GPIO_SPI_MOSI) = GPIO_bit(GPIO_SPI_MOSI);
-+ }
-+}
-+
-+static u32 ssp_pcap_gpioRxdGetStatus(void)
-+{
-+ if(ssp_pcap_rxd_pin_with_inverter)
-+ {
-+ if( GPLR(GPIO_SPI_MISO)&GPIO_bit(GPIO_SPI_MISO) )
-+ {
-+ return SSP_PCAP_BIT_ZERO;
-+ }
-+ else
-+ {
-+ return SSP_PCAP_BIT_ONE;
-+ }
-+ }
-+ else
-+ {
-+ if( GPLR(GPIO_SPI_MISO)&GPIO_bit(GPIO_SPI_MISO) )
-+ {
-+ return SSP_PCAP_BIT_ONE;
-+ }
-+ else
-+ {
-+ return SSP_PCAP_BIT_ZERO;
-+ }
-+ }
-+}
-+
-+static void ssp_pcap_gpioWrite(u32 pcapValue)
-+{
-+ u32 tempValue;
-+ u32 loopValue = 0x80000000;
-+ int i;
-+ /* prepare for starting the frame */
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ZERO);
-+ ssp_pcap_gpioFrmControl(SSP_PCAP_BIT_ZERO);
-+ ssp_pcap_gpioTxdControl(SSP_PCAP_BIT_ZERO);
-+
-+ /* start the data transfering frame */
-+ ssp_pcap_gpioFrmControl(SSP_PCAP_BIT_ONE);
-+ for(i=0;i<32;i++)
-+ {
-+ tempValue = pcapValue&loopValue;
-+ /* setup data bit to TXD line */
-+ ssp_pcap_gpioTxdControl(tempValue);
-+ /* create clock */
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ONE);
-+ loopValue = loopValue/2;
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ZERO);
-+ }
-+ /* end the frame */
-+ ssp_pcap_gpioFrmControl(SSP_PCAP_BIT_ZERO);
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( " \n Write END \n " );
-+#endif
-+ return;
-+}
-+
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+
-+static void ssp_pcap_gpioRead( u32 registerNumber,u32* pPcapValue)
-+{
-+ int i;
-+ u32 tempValue;
-+ u32 loopValue = 0x80000000;
-+
-+ /* prepare for starting the frame */
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ZERO);
-+ ssp_pcap_gpioFrmControl(SSP_PCAP_BIT_ZERO);
-+ ssp_pcap_gpioTxdControl(SSP_PCAP_BIT_ZERO);
-+
-+ /* start the data transfering frame */
-+ ssp_pcap_gpioFrmControl(SSP_PCAP_BIT_ONE);
-+ /* indictaor it's a read data command */
-+ ssp_pcap_gpioTxdControl(SSP_PCAP_BIT_ZERO);
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ONE);
-+ loopValue = loopValue/2;
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ZERO);
-+
-+ for(i=0; i<5;i++)
-+ {
-+ /* here maybe can be optimized */
-+ tempValue = registerNumber&(loopValue/0x04000000);
-+ ssp_pcap_gpioTxdControl(tempValue);
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ONE);
-+ loopValue = loopValue/2;
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ZERO);
-+ }
-+
-+ /* the dead bit */
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ONE);
-+ loopValue = loopValue/2;
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ZERO);
-+
-+ tempValue = 0;
-+ for(i=0;i<25;i++)
-+ {
-+ tempValue |= loopValue*ssp_pcap_gpioRxdGetStatus();
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ONE);
-+ loopValue = loopValue/2;
-+ ssp_pcap_gpioClkControl(SSP_PCAP_BIT_ZERO);
-+ }
-+ /* end the data frame */
-+ ssp_pcap_gpioFrmControl(SSP_PCAP_BIT_ZERO);
-+ if(pPcapValue)
-+ {
-+ *pPcapValue = tempValue;
-+ }
-+
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk(" \n Read Data end \n");
-+#endif
-+ return ;
-+}
-+
-+#endif
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+
-+void SSPTest(void)
-+{
-+ char string[80];
-+ u32 i,j,k;
-+ u16 x,y;
-+ u32 tempValue;
-+ // ssp_pcap_init();
-+// ssp_pcap_open();
-+ printk(" \n ****************************** \n SSP TEST \n *****************\n ");
-+// SSP_vibrate_start_command();
-+// for(i=0; i<100000000; i++);
-+// SSP_vibrate_stop_command();
-+ SSP_PCAP_write_data_to_PCAP(3,0x0fffffff);
-+
-+ SSP_PCAP_read_data_from_PCAP(0,&k);
-+ SSP_PCAP_write_data_to_PCAP(0,k);
-+
-+ for(i =0;i<32;i++)
-+ {
-+ SSP_PCAP_read_data_from_PCAP(i,&k);
-+ sprintf(string,"pcap register %d = 0x%x! \n",i,k);
-+ printk(string);
-+ }
-+
-+ SSP_PCAP_read_data_from_PCAP(0,&k);
-+ SSP_PCAP_write_data_to_PCAP(0,k);
-+
-+
-+// SSP_PCAP_write_data_to_PCAP(9,0x000a0000);
-+ printk( "\n ************* \n test TS position start \n ");
-+
-+ for(i=0;i<10000;i++)
-+ {
-+ tempValue = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_ISR_TSI);
-+ if(tempValue)
-+ {
-+
-+ sprintf(string, "GEDR0 = %x ICPR = %x ICMR= %x \n ",GEDR0,ICPR,ICMR );
-+ printk(string);
-+ GEDR0 = GEDR0;
-+ ICPR = ICPR;
-+
-+
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_ADCDONE2M);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_PRESSURE_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ tempValue = 0 ;
-+ while(!tempValue)
-+ {
-+ tempValue = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+ }
-+ SSP_PCAP_TSI_get_XY_value(&x,&y);
-+
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_TSI);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+
-+ sprintf(string,"\n TS xy pressure X=%d y=%d \n",x,y);
-+ printk(string);
-+
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_ADCDONE2M);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_PRESSURE_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ tempValue = 0 ;
-+ while(!tempValue)
-+ {
-+ tempValue = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+ }
-+ SSP_PCAP_TSI_get_XY_value(&x,&y);
-+
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_TSI);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+
-+ sprintf(string,"\n TS xy pressure X=%d y=%d \n",x,y);
-+ printk(string);
-+
-+
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_POSITION_XY_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ tempValue = 0 ;
-+ while(!tempValue)
-+ {
-+ tempValue = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+ }
-+ SSP_PCAP_TSI_get_XY_value(&x,&y);
-+
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_TSI);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+
-+ sprintf(string,"\n TS xy possition X=%d y=%d \n",x,y);
-+ printk(string);
-+
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_PRESSURE_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ tempValue = 0 ;
-+ while(!tempValue)
-+ {
-+ tempValue = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+ }
-+ SSP_PCAP_TSI_get_XY_value(&x,&y);
-+
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_TSI);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+
-+ sprintf(string,"\n TS xy pressure X=%d y=%d \n",x,y);
-+ printk(string);
-+
-+ i = 0;
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_MSR_ADCDONE2M);
-+ // SSP_PCAP_write_data_to_PCAP(9,0x000a0000);
-+
-+ }
-+ for(j=0;j<60000;j++);
-+ }
-+ printk(" TS pressure test start \n ");
-+
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_PRESSURE_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ tempValue = 0 ;
-+ while(!tempValue)
-+ {
-+ tempValue = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_ISR_ADCDONEI);
-+ }
-+ SSP_PCAP_TSI_get_XY_value(&x,&y);
-+
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_TSI);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_ADCDONEI);
-+
-+ sprintf(string,"\n TS xy pressure X=%d y=%d \n",x,y);
-+ printk(string);
-+
-+ SSP_PCAP_read_data_from_PCAP(0,&tempValue);
-+
-+ sprintf(string," before clean ISR = %x \n ", tempValue );
-+ printk(string);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_TSI);
-+ SSP_PCAP_read_data_from_PCAP(0,&tempValue);
-+ sprintf(string," after clean ISR = %x \n ", tempValue );
-+ printk(string);
-+ GEDR0 = GEDR0;
-+ ICPR = ICPR;
-+
-+ tempValue = 0;
-+ while(!tempValue)
-+ {
-+ tempValue = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_ISR_TSI);
-+ tempValue &= 0x00000001;
-+ }
-+ SSP_PCAP_read_data_from_PCAP(0,&tempValue);
-+ SSP_PCAP_read_data_from_PCAP(1,&k);
-+ sprintf(string, " MSR = %8x ISR= %8x, GEDR0 = %8x ICPR = %8x \n",k,tempValue,GEDR0,ICPR);
-+ printk(string);
-+ GEDR0 = GEDR0;
-+ ICPR = ICPR;
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_PRESSURE_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ tempValue = 0;
-+ while(!tempValue)
-+ {
-+ tempValue = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+ tempValue &= 0x00000001;
-+ }
-+ for(i=0;i<60000;i++);
-+ SSP_PCAP_read_data_from_PCAP(0,&tempValue);
-+ sprintf(string," ISR =%8x GEDR0 =%8x ICPR = %8x \n",tempValue,GEDR0,ICPR);
-+ printk(string);
-+ SSP_PCAP_TSI_get_XY_value(&x,&y);
-+ sprintf(string," TS pressure x = %d y= %d \n" ,x,y );
-+ printk(string);
-+ return;
-+}
-+#endif
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+static int pcap_pm_callback(struct pm_dev *pm_dev, pm_request_t req, void *data)
-+{
-+ switch(req)
-+ {
-+ case PM_SUSPEND:
-+ ssp_pcap_intoSleepCallBack();
-+ break;
-+ case PM_RESUME:
-+ ssp_pcap_wakeUpCallBack();
-+ break;
-+ }
-+ return 0;
-+}
-+static int ssp_pcap_init_is_ok = 0;
-+void ssp_pcap_init(void)
-+{
-+#ifdef SSP_PCAP_DEBUG_BOARD
-+ U32 tempValue;
-+#endif
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ char debugStr[100];
-+ sprintf(debugStr,"\n ***************** \n SSP init start \n");
-+ printk(debugStr);
-+#endif
-+
-+#ifdef SSP_PCAP_OPERATE_WITH_SPI
-+ CKEN |= CKEN3_SSP;
-+ pxa_gpio_mode(GPIO_SPI_CLK|(GPIO_SPI_CLK == GPIO23_SCLK? GPIO_ALT_FN_2_OUT:GPIO_ALT_FN_3_OUT);
-+ pxa_gpio_mode(GPIO_SPI_CE|GPIO_ALT_FN_2_OUT);
-+ pxa_gpio_mode(GPIO_SPI_MOSI|GPIO_ALT_FN_2_OUT);
-+ pxa_gpio_mode(GPIO_SPI_MISO|GPIO_ALT_FN_1_IN);
-+
-+ SSCR1 = 0x00000401;
-+ SSCR0 = 0x00000000;
-+ SSCR0 = 0x0000008f;
-+ init_waitqueue_head(&ssp_pcap_send_wait);
-+ request_irq(IRQ_SSP,ssp_interrupt_routine,0,"SSP received the data irq ",NULL);
-+#else
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk(" \n ********************* \n SSP GPIO mode init \n");
-+#endif
-+ if(!ssp_pcap_init_is_ok)
-+ {
-+ ssp_pcap_gpioInit();
-+ ssp_pcap_init_is_ok = 1;
-+ }
-+#endif
-+
-+#ifdef SSP_PCAP_DEBUG_BOARD
-+ printk("\n ********************* \n SSP DEBUG BOARD init \n ");
-+ tempValue = GPDR2;
-+ tempValue = tempValue&0x0001ffff;
-+ tempValue |= 0x00010000;
-+ GPDR2 = tempValue;
-+ GAFR2_U = 0x00000002;
-+#endif
-+ pxa_gpio_mode(GPIO_PCAP_SEC_INT | GPIO_IN);
-+ set_GPIO_IRQ_edge(GPIO_PCAP_SEC_INT,GPIO_RISING_EDGE);
-+
-+ request_irq(IRQ_GPIO1,ssp_pcap_interrupt_routine,0,"PCAP request irq ",NULL);
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_output_log_init();
-+#endif
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk(" \n *********************** \n SSP init END \n ");
-+#endif
-+ init_timer(&ssp_tsi_timer);
-+ ssp_tsi_timer.function = ssp_tsi_keeper;
-+
-+ init_timer(&ssp_usb_accessory_debounce_timer);
-+ ssp_usb_accessory_debounce_timer.function = ssp_usb_accessory_debounce_handler;
-+
-+ ssp_pcap_screenlock_status = 0 ;
-+ init_timer(&ssp_pcap_screenlock_timer);
-+ ssp_pcap_screenlock_timer.function = ssp_pcap_screenlock_lockhandler;
-+
-+ /* since in GPIO init, we have gotten the register's value. */
-+// SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_MSR_USB4VM );
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_ISR_USB4VI);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_USB4VM);
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_ISR_USB1VI);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_USB1VM);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_A1CTRL);
-+ SSP_PCAP_V_VIB_level_set(PCAP_VIBRATOR_VOLTAGE_LEVEL3);
-+ SSP_PCAP_V_VIB_level_set(PCAP_VIBRATOR_VOLTAGE_LEVEL3);
-+
-+ /* set SW1 sleep to keep SW1 1.3v in sync mode */
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW1_MODE10 );
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW1_MODE11 );
-+ /* SW1 active in sync mode */
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW1_MODE00 );
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW1_MODE01);
-+ /* at SW1 -core voltage to 1.30V */
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW10_DVS);
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW11_DVS);
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW12_DVS);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_SW13_DVS);
-+
-+ /* when STANDY2 PIN ACTIVE (high) set V3-- sram V8 -- pll off */
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_VREG2_V3_STBY);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_VREG2_V3_LOWPWR);
-+
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_VREG2_V8_STBY);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_VREG2_V8_LOWPWR);
-+
-+ /* when STANDY2 PIN ACTIVE (high) set V4-- lcd only for e680 V6 --- camera for e680 */
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_VREG2_V4_STBY);
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_VREG2_V4_LOWPWR);
-+
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_VREG2_V6_STBY);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_VREG2_V6_LOWPWR);
-+
-+ /* set Vc to low power mode when AP sleep */
-+ //SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VC_STBY);
-+
-+ /* set VAUX2 to voltage 2.775V and low power mode when AP sleep */
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX2_1);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX2_0);
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VAUX2_STBY);
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_LOWPWR_CTRL_VAUX2_LOWPWR);
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_AUX_VREG_VAUX2_EN );
-+
-+ PGSR(GPIO34_TXENB) |= GPIO_bit(GPIO34_TXENB);
-+ if(SSP_PCAP_BIT_ONE == SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_PSTAT_USBDET_4V ))
-+ {
-+ accessory_bus_detect_handler(ACCESSORY_DEVICE_USB_PORT,ACCESSORY_DEVICE_STATUS_ATTACHED,NULL);
-+ }
-+ else
-+ {
-+ accessory_bus_detect_handler(ACCESSORY_DEVICE_USB_PORT,ACCESSORY_DEVICE_STATUS_DETACHED,NULL);
-+ }
-+ /* register pm callback function */
-+ /* only for temp solution 2004-05-10 */
-+#ifdef PCAP2_V1.4_AND_BEFORE
-+ pxa_gpio_mode(GPIO_TC_MM_EN | GPIO_OUT );
-+ GPCR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ PGSR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+#endif
-+ /* the PM callback will move to apm.c */
-+// pcap_pm_dev = pm_register(PM_SYS_DEV,0,pcap_pm_callback);
-+ return;
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+void pcap_switch_off_usb(void)
-+{
-+ if(!ssp_pcap_init_is_ok)
-+ {
-+ ssp_pcap_gpioInit();
-+ ssp_pcap_init_is_ok = 1;
-+ }
-+ /* only for PST tool recognize the USB cable */
-+ if(SSP_PCAP_BIT_ONE == SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_PSTAT_USBDET_4V ))
-+ {
-+ SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PU);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PU);
-+ }
-+ return;
-+}
-+
-+void pcap_switch_on_usb(void)
-+{
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PU);
-+ if(SSP_PCAP_BIT_ONE == SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_PSTAT_USBDET_4V ))
-+ {
-+// stop_ffuart();
-+// usb_gpio_init();
-+ }
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+void ssp_pcap_release(void)
-+{
-+/* the PM callback will move to apm.c */
-+// pm_unregister(pcap_pm_dev);
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+void ssp_pcap_open(SSP_PCAP_INIT_DRIVER_TYPE portType)
-+{
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ u32 i;
-+ u32 tempValue;
-+#endif
-+#ifdef SSP_PCAP_DEBUG_BOARD
-+ /* select the primary SPI of PCAP */
-+ *SSP_SELECT_BUFFER = 0x00000094;
-+ SSP_PCAP_write_data_to_PCAP(3, 0x00100002);
-+ SSP_PCAP_write_data_to_PCAP(20,0x010000a4);
-+ SSP_PCAP_bit_set(0x58080000 );
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_STANDBY_MODE);
-+ *SSP_SELECT_BUFFER = 0x00000070;
-+#endif
-+ switch(portType)
-+ {
-+ case SSP_PCAP_TS_OPEN:
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk(" \n SSP TS open!!! ");
-+#endif
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ADC1_TS_REFENB );
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I);
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_ISR_TSI);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_ADCDONE2M);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ADC2_ADINC1);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ADC2_ADINC2);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ADC1_ATO0);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ADC1_ATO1);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ADC1_ATO2);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ADC1_ATO3);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ADC1_ATOX);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ADC1_MTR1);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ADC1_MTR2);
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_STANDBY_MODE);
-+ /* send the usb accessory infomation to PM */
-+ if((ACCESSORY_TYPE) sspUsbAccessoryInfo.type == ACCESSORY_DEVICE_USB_PORT)
-+ {
-+ if( (ACCESSORY_DEVICE_STATUS )sspUsbAccessoryInfo.status == ACCESSORY_DEVICE_STATUS_ATTACHED )
-+ apm_queue_event(KRNL_ACCS_ATTACH);
-+ else
-+ apm_queue_event(KRNL_ACCS_DETACH);
-+ }
-+ break;
-+ case SSP_PCAP_AUDIO_OPEN:
-+ break;
-+ default:
-+ break;
-+ }
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ for(i=0;i<32;i++)
-+ {
-+ SSP_PCAP_read_data_from_PCAP(i, &tempValue);
-+ printk("\n PCAP register %d = 0x%x!",i,tempValue);
-+ }
-+#endif
-+ return;
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+void ssp_pcap_close(void)
-+{
-+ SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_MSR_REGISTER,PCAP_MASK_ALL_INTERRUPT);
-+ return;
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+void ssp_pcap_intoSleepCallBack(void)
-+{
-+ /* set TS_REF to low power mode */
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ADC1_TS_REF_LOWPWR);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_MSR_MB2M);
-+ /* set SPI_CLK as input PIN */;
-+ GPDR(GPIO_SPI_CLK) &= ~GPIO_bit(GPIO_SPI_CLK);
-+ /* set SPI_MOSI as input PIN */
-+ GPDR(GPIO_SPI_MOSI) &= ~GPIO_bit(GPIO_SPI_MOSI);
-+ /* set PCAP's CE pin to dessert signal SPI_CE must be in range of 0~31 PIN */
-+ if(ssp_pcap_operate_pin_with_inverter)
-+ {
-+ PGSR0 |= GPIO_bit(GPIO_SPI_CE);
-+ }
-+ else
-+ {
-+ PGSR0 &= ~GPIO_bit(GPIO_SPI_CE);
-+ }
-+}
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+void ssp_pcap_wakeUpCallBack(void)
-+{
-+#ifdef PCAP2_V1.4_AND_BEFORE
-+ GPCR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+#endif
-+ /* set SPI_CLK to output PIN */;
-+ GPDR(GPIO_SPI_CLK) |= GPIO_bit(GPIO_SPI_CLK) ;
-+ /* set SPI_MOSI to output PIN */
-+ GPDR(GPIO_SPI_MOSI) |= GPIO_bit(GPIO_SPI_MOSI);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_ADC1_TS_REF_LOWPWR);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_MSR_MB2M);
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_configure_USB_UART_transeiver(SSP_PCAP_PORT_TYPE portType)
-+{
-+ SSP_PCAP_STATUS ret = SSP_PCAP_SUCCESS;
-+ switch(portType)
-+ {
-+ case SSP_PCAP_SERIAL_PORT:
-+ /* according to HW requirement, do not clear VUSB_EN 2004-05-11 */
-+ //ret = SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ if(SSP_PCAP_SUCCESS == ret)
-+ {
-+ ret = SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB);
-+ }
-+ break;
-+ case SSP_PCAP_LOW_USB_PORT:
-+ ret = SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB);
-+ if(SSP_PCAP_SUCCESS == ret)
-+ {
-+ ret = SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_FSENB);
-+ }
-+ if(SSP_PCAP_SUCCESS == ret)
-+ {
-+ ret = SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ }
-+ break;
-+ case SSP_PCAP_HIGH_USB_PORT:
-+ ret = SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB);
-+ if(SSP_PCAP_SUCCESS == ret)
-+ {
-+ ret = SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_FSENB);
-+ }
-+ if(SSP_PCAP_SUCCESS == ret)
-+ {
-+ ret = SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ }
-+ break;
-+ default:
-+ ret = SSP_PCAP_NOT_RUN ;
-+ break;
-+ }
-+ return ret;
-+}
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+
-+SSP_PCAP_STATUS SSP_PCAP_TSI_mode_set(TOUCH_SCREEN_DETECT_TYPE mode_Type )
-+{
-+ U32 tempValue;
-+ tempValue = ssp_pcap_registerValue[SSP_PCAP_ADJ_ADC1_REGISTER]&(~SSP_PCAP_TOUCH_PANEL_POSITION_DETECT_MODE_MASK);
-+ tempValue = tempValue|mode_Type;
-+ return SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_ADC1_REGISTER,tempValue);
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_TSI_start_XY_read(void)
-+{
-+ SSP_PCAP_STATUS ret = SSP_PCAP_SUCCESS;
-+ U32 tempValue;
-+#ifdef PCAP2_V1.4_AND_BEFORE
-+ /* invert the TC_MM_EN pin to alert BP */
-+ u32 i;
-+ if(GPLR(GPIO_TC_MM_EN)&GPIO_bit(GPIO_TC_MM_EN))
-+ {
-+ GPCR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ }
-+ else
-+ {
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ }
-+ for(i=0;i<0x00002000;i++);
-+ if(GPLR(GPIO_TC_MM_EN)&GPIO_bit(GPIO_TC_MM_EN))
-+ {
-+ GPCR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ }
-+ else
-+ {
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ }
-+#endif
-+ tempValue = ssp_pcap_registerValue[SSP_PCAP_ADJ_ADC1_REGISTER]&SSP_PCAP_ADC_START_VALUE_SET_MASK;
-+ tempValue |= SSP_PCAP_ADC_START_VALUE;
-+ SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_ADC1_REGISTER,tempValue);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ADC2_ASC);
-+ return ret;
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES: y reads TSX1's ADC value in ADD2 register, x reads TSY1's ADC value in ADD1 register.
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_TSI_get_XY_value(P_U16 p_x,P_U16 p_y)
-+{
-+ U32 tempValue;
-+ SSP_PCAP_STATUS ret = SSP_PCAP_read_data_from_PCAP(SSP_PCAP_ADJ_ADC2_REGISTER,&tempValue);
-+ if( SSP_PCAP_SUCCESS != ret)
-+ return ret;
-+ if(ssp_pcap_screenlock_status)
-+ {
-+ *p_x = 0;
-+ *p_y = 0;
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_STANDBY_MODE);
-+ mod_timer(&ssp_pcap_screenlock_timer,jiffies + SSP_PCAP_TS_KEEPER_TIMER);
-+ return ret;
-+ }
-+ if(tempValue&0x00400000)
-+ return SSP_PCAP_ERROR_VALUE;
-+ if(p_x)
-+ {
-+ *p_x = (U16)(tempValue&SSP_PCAP_ADD1_VALUE_MASK);
-+ }
-+ if(p_y)
-+ {
-+ *p_y = (U16)((tempValue&SSP_PCAP_ADD2_VALUE_MASK)>>SSP_PCAP_ADD2_VALUE_SHIFT);
-+ }
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_STANDBY_MODE);
-+ return ret;
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+
-+SSP_PCAP_STATUS SSP_PCAP_CDC_CLK_set(PHONE_CDC_CLOCK_TYPE clkType)
-+{
-+ U32 tempValue;
-+ tempValue = ssp_pcap_registerValue[SSP_PCAP_ADJ_AUD_CODEC_REGISTER]&(~SSP_PCAP_PHONE_CDC_CLOCK_MASK);
-+ tempValue = tempValue|clkType;
-+ return SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_AUD_CODEC_REGISTER,tempValue);
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_V_VIB_level_set(VibratorVoltageLevel_TYPE VIBLevelType)
-+{
-+ U32 tempValue;
-+ tempValue = ssp_pcap_registerValue[SSP_PCAP_ADJ_AUX_VREG_REGISTER]&(~SSP_PCAP_VIBRATOR_VOLTAGE_LEVEL_MASK);
-+ tempValue = tempValue|VIBLevelType;
-+ return SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_AUX_VREG_REGISTER,tempValue);
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_CDC_SR_set(ST_SAMPLE_RATE_TYPE srType)
-+{
-+ U32 tempValue;
-+ tempValue = ssp_pcap_registerValue[SSP_PCAP_ADJ_ST_DAC_REGISTER]&(~SSP_PCAP_STEREO_SAMPLE_RATE_MASK);
-+ tempValue = tempValue|srType;
-+ return SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_ST_DAC_REGISTER,tempValue);
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_BCLK_set(ST_BCLK_TIME_SLOT_TYPE bclkType)
-+{
-+ U32 tempValue;
-+ tempValue = ssp_pcap_registerValue[SSP_PCAP_ADJ_ST_DAC_REGISTER]&(~SSP_PCAP_STEREO_BCLK_TIME_SLOT_MASK);
-+ tempValue = tempValue|bclkType;
-+ return SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_ST_DAC_REGISTER,tempValue);
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_STCLK_set(ST_CLK_TYPE stClkType)
-+{
-+ U32 tempValue;
-+ tempValue = ssp_pcap_registerValue[SSP_PCAP_ADJ_ST_DAC_REGISTER]&(~SSP_PCAP_STEREO_CLOCK_MASK);
-+ tempValue = tempValue|stClkType;
-+ return SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_ST_DAC_REGISTER,tempValue);
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_DIG_AUD_FS_set(DIG_AUD_MODE_TYPE fsType)
-+{
-+ U32 tempValue;
-+ tempValue = ssp_pcap_registerValue[SSP_PCAP_ADJ_ST_DAC_REGISTER]&(~SSP_PCAP_DIGITAL_AUDIO_MODE_MASK);
-+ tempValue = tempValue|fsType;
-+ return SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_ST_DAC_REGISTER,tempValue);
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_AUDIG_set(U32 audioInGain)
-+{
-+ U32 tempValue;
-+ if (audioInGain > PCAP_AUDIO_IN_GAIN_MAX_VALUE)
-+ return SSP_PCAP_ERROR_VALUE;
-+ tempValue = ssp_pcap_registerValue[SSP_PCAP_ADJ_TX_AUD_AMPS_REGISTER]&(~SSP_PCAP_AUDIO_IN_GAIN_MASK);
-+
-+ /* shoulb be better like this tempValue |= audioInGain <<SSP_PCAP_AUDIO_IN_GAIN_SHIFT; */
-+ tempValue = tempValue|audioInGain;
-+ return SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_TX_AUD_AMPS_REGISTER,tempValue);
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_MONO_set(MONO_TYPE monoType)
-+{
-+ U32 tempValue;
-+ tempValue = ssp_pcap_registerValue[SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER]&(~SSP_PCAP_MONO_PGA_MASK);
-+ tempValue = tempValue|monoType;
-+ return SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER,tempValue);
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_AUDOG_set(U32 audioOutGain)
-+{
-+ U32 tempValue;
-+ if (audioOutGain > PCAP_AUDIO_OUT_GAIN_MAX_VALUE)
-+ return SSP_PCAP_ERROR_VALUE;
-+ tempValue = ssp_pcap_registerValue[SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER]&(~SSP_PCAP_AUDIO_OUT_GAIN_MASK);
-+ tempValue |= audioOutGain <<SSP_PCAP_AUDIO_OUT_GAIN_SHIFT;
-+ return SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER,tempValue);
-+}
-+
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+#ifdef SSP_PCAP_OPERATE_WITH_SPI
-+/* ssp has received 2 bytes, the function will be invoked. */
-+static void ssp_interrupt_routine(int irq, void *dev_id, struct pt_regs *regs )
-+{
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk("\n SSP INTERRUPT WAS CALLED \n ");
-+#endif
-+ if(SSSR&SSP_SR_RNE)
-+ {
-+ ssp_pcap_readValue = (SSDR&SSP_PCAP_REGISTER_VALUE_DOWN_WORD_MASK)<<16;
-+ if(SSSR&SSP_SR_RNE)
-+ {
-+ ssp_pcap_readValue += (SSDR&SSP_PCAP_REGISTER_VALUE_DOWN_WORD_MASK);
-+ if(SSSR&SSP_SR_RNE)
-+ {
-+ while(SSSR&SSP_SR_RNE)
-+ {
-+ ssp_pcap_readValue = (SSDR&SSP_PCAP_REGISTER_VALUE_DOWN_WORD_MASK);
-+ }
-+ ssp_pcap_readValue = 0;
-+ }
-+ }
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk("\n SSP INTERRUPT send wakeup info \n ");
-+#endif
-+ wake_up(&ssp_pcap_send_wait);
-+ }
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk("\n SSP INTERRUPT EXIT \n ");
-+#endif
-+ return;
-+}
-+
-+#endif
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+
-+static void ssp_tsi_keeper(u32 data)
-+{
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("TS timer arrived!",strlen("TS timer arrived!"));
-+#endif
-+ if(SSP_PCAP_BIT_ONE == SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_MSR_TSM))
-+ {
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_ISR_TSI);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ }
-+ return;
-+}
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+void ssp_pcap_clear_int(void)
-+{
-+ U32 tempValue;
-+ U32 tempClearInterrupt;
-+
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n ************************ \n SSP interrupt by GPIO from sleep. ");
-+#endif
-+ /* should care the return value */
-+ SSP_PCAP_read_data_from_PCAP( SSP_PCAP_ADJ_ISR_REGISTER,&tempValue);
-+ tempClearInterrupt = tempValue&(SSP_PCAP_ADJ_BIT_ISR_MB2I|SSP_PCAP_ADJ_BIT_ISR_STI|SSP_PCAP_ADJ_BIT_ISR_A1I|SSP_PCAP_ADJ_BIT_ISR_USB1VI|SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I|SSP_PCAP_ADJ_BIT_ISR_TSI|SSP_PCAP_ADJ_BIT_ISR_USB4VI);
-+
-+ /* send the data to ISR register to clear the interrupt flag */
-+ SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_ISR_REGISTER,tempClearInterrupt);
-+
-+ if(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I&tempValue)
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n SSP ADC interrupt should be discarded." );
-+#endif
-+ }
-+
-+ if(SSP_PCAP_ADJ_BIT_ISR_TSI&tempValue)
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n SSP TSI should be discarded. ");
-+#endif
-+ }
-+
-+
-+ if(SSP_PCAP_ADJ_BIT_ISR_USB4VI&tempValue)
-+ {
-+ if(SSP_PCAP_BIT_ZERO == SSP_PCAP_get_bit_from_buffer(SSP_PCAP_ADJ_BIT_MSR_USB4VM))
-+ {
-+ if(SSP_PCAP_BIT_ONE == SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_PSTAT_USBDET_4V))
-+ {
-+ /* maybe we can support low speed USB how to do??? */
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n SSP USB4VI need handle. ");
-+#endif
-+ accessory_bus_detect_handler(ACCESSORY_DEVICE_USB_PORT,ACCESSORY_DEVICE_STATUS_ATTACHED,NULL);
-+ }
-+ }
-+ }
-+
-+ if(SSP_PCAP_ADJ_BIT_ISR_USB1VI&tempValue)
-+ {
-+ if(SSP_PCAP_BIT_ZERO == SSP_PCAP_get_bit_from_buffer(SSP_PCAP_ADJ_BIT_MSR_USB1VM))
-+ {
-+ if(SSP_PCAP_BIT_ONE != SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_PSTAT_USBDET_1V))
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n SSP USB_VBUS less than 1V! need handle.");
-+#endif
-+ accessory_bus_detect_handler(ACCESSORY_DEVICE_USB_PORT,ACCESSORY_DEVICE_STATUS_DETACHED,NULL);
-+ }
-+ }
-+ }
-+
-+
-+ if(SSP_PCAP_ADJ_BIT_ISR_A1I&tempValue)
-+ {
-+ if(SSP_PCAP_BIT_ZERO == SSP_PCAP_get_bit_from_buffer(SSP_PCAP_ADJ_BIT_MSR_A1M))
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n A1_INT insert/remove case, need to handle. ISR =%x ",tempValue );
-+#endif
-+ /* earpiece insert/remove need handler */
-+ if (headjack_change_interrupt_routine)
-+ (*headjack_change_interrupt_routine)(0,NULL,NULL);
-+ }
-+ }
-+
-+ if(SSP_PCAP_ADJ_BIT_ISR_MB2I&tempValue)
-+ {
-+ if(SSP_PCAP_BIT_ZERO == SSP_PCAP_get_bit_from_buffer(SSP_PCAP_ADJ_BIT_MSR_MB2M))
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n MIC insert/remove case, need to handle! ISR =%x ",tempValue );
-+#endif
-+ //queue_apm_event(KRNL_KEYPAD,NULL);
-+ /* mic insert/remove or answer/end call handler */
-+ if(mic_change_interrupt_routine)
-+ (*mic_change_interrupt_routine)(0,NULL,NULL);
-+ }
-+ }
-+ return;
-+}
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+static u32 ssp_pcap_last_jiffies = 0;
-+
-+static void ssp_pcap_ts_send_pMmessage(void)
-+{
-+ u32 temp = jiffies - ssp_pcap_last_jiffies;
-+
-+ if( temp >SSP_SEND_PM_ALART_INTERVAL)
-+ {
-+ ssp_pcap_last_jiffies = (u32) jiffies;
-+ apm_queue_event(KRNL_TOUCHSCREEN);
-+ }
-+ return;
-+}
-+
-+static void ssp_pcap_interrupt_routine(int irq, void *dev_id, struct pt_regs *regs )
-+{
-+ u32 pcap_repeat_num;
-+ U32 tempValue;
-+ u32 tempClearInterrupt;
-+#ifdef PCAP_LOG_FFUART_OUT
-+ u8 temp[100];
-+ pcap_log_add_data("SSP interrupt by GPIO.",strlen("\n SSP interrupt by GPIO."));
-+#endif
-+
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n ************************ \n SSP interrupt by GPIO. ");
-+#endif
-+ /* should care the return value */
-+ pcap_repeat_num = 0;
-+intRepeat:
-+ SSP_PCAP_read_data_from_PCAP( SSP_PCAP_ADJ_ISR_REGISTER,&tempValue);
-+ tempClearInterrupt = tempValue&(SSP_PCAP_ADJ_BIT_ISR_MB2I|SSP_PCAP_ADJ_BIT_ISR_STI|SSP_PCAP_ADJ_BIT_ISR_A1I|SSP_PCAP_ADJ_BIT_ISR_USB1VI|SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I|SSP_PCAP_ADJ_BIT_ISR_TSI|SSP_PCAP_ADJ_BIT_ISR_USB4VI);
-+
-+ /* send the data to ISR register to clear the interrupt flag */
-+ SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_ISR_REGISTER,tempClearInterrupt);
-+
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk("\n w17202 TSI = 0x%x ",tempClearInterrupt);
-+#endif
-+ if(SSP_PCAP_ADJ_BIT_ISR_ADCDONE2I&tempValue)
-+ {
-+ if(SSP_PCAP_BIT_ZERO == SSP_PCAP_get_bit_from_buffer(SSP_PCAP_ADJ_BIT_MSR_ADCDONE2M))
-+ {
-+ /* call read XY callback function */
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("SSP ADC interrupt need handle.",strlen("SSP ADC interrupt need handle."));
-+#endif
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n ************************** \n SSP ADC interrupt need handle." );
-+#endif
-+ ssp_pcap_ts_send_pMmessage();
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_ADC1_ADEN);
-+ /* 2 seconds protect timer */
-+ /* better used it after linux 2.4.17 */
-+ mod_timer(&ssp_tsi_timer,jiffies + SSP_PCAP_TS_KEEPER_TIMER);
-+ ezx_ts_dataReadok_interrupt(0,NULL,NULL);
-+ }
-+ else
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n ************************** \n SSP ADC interrupt should be discarded." );
-+#endif
-+ }
-+ }
-+
-+ if(SSP_PCAP_ADJ_BIT_ISR_TSI&tempValue)
-+ {
-+ if(SSP_PCAP_BIT_ZERO == SSP_PCAP_get_bit_from_buffer(SSP_PCAP_ADJ_BIT_MSR_TSM))
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n ************************* \n SSP TSI need handle.");
-+#endif
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("SSP TSI need handle.",strlen("SSP TSI need handle."));
-+#endif
-+ ssp_pcap_ts_send_pMmessage();
-+ //if ( pxafb_ezx_getLCD_status() )
-+ if (1)
-+ {
-+ /* call touch panel callbcak function */
-+ SSP_PCAP_bit_set( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ /* 2 seconds protect timer */
-+ /* better used it after linux 2.4.17 */
-+ mod_timer(&ssp_tsi_timer,jiffies + SSP_PCAP_TS_KEEPER_TIMER);;
-+ ezx_ts_touch_interrupt(0,NULL,NULL);
-+ }
-+ }
-+ else
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n************************* \n SSP TSI should be discarded.");
-+#endif
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("SSP TSI need not handle.",strlen("SSP TSI need not handle."));
-+#endif
-+ }
-+ }
-+
-+
-+ if(SSP_PCAP_ADJ_BIT_ISR_USB4VI&tempValue)
-+ {
-+ if(SSP_PCAP_BIT_ZERO == SSP_PCAP_get_bit_from_buffer(SSP_PCAP_ADJ_BIT_MSR_USB4VM))
-+ {
-+ if(SSP_PCAP_BIT_ONE == SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_PSTAT_USBDET_4V))
-+ {
-+ /* maybe we can support low speed USB how to do??? */
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n************************* \n SSP USB4VI need handle.");
-+#endif
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("SSP USB4VI need handle.",strlen("SSP USB4VI need handle."));
-+#endif
-+ accessory_bus_detect_handler(ACCESSORY_DEVICE_USB_PORT,ACCESSORY_DEVICE_STATUS_ATTACHED,NULL);
-+ }
-+ else
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n ************************* \n SSP USB4VI low need NOT handle same as USB1VI low.");
-+#endif
-+ }
-+ }
-+ else
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n************************* \n SSP USB4VI should be discarded.");
-+#endif
-+ }
-+ }
-+
-+ if(SSP_PCAP_ADJ_BIT_ISR_USB1VI&tempValue)
-+ {
-+ if(SSP_PCAP_BIT_ZERO == SSP_PCAP_get_bit_from_buffer(SSP_PCAP_ADJ_BIT_MSR_USB1VM))
-+ {
-+ if(SSP_PCAP_BIT_ONE == SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_PSTAT_USBDET_1V))
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n************************* \n SSP USB_VBUS greater than 1V!");
-+#endif
-+ }
-+ else
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n************************* \n SSP USB_VBUS less than 1V! need handle.");
-+#endif
-+ accessory_bus_detect_handler(ACCESSORY_DEVICE_USB_PORT,ACCESSORY_DEVICE_STATUS_DETACHED,NULL);
-+ }
-+ }
-+ else
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n************************* \n SSP USB1VI should be discarded.");
-+#endif
-+ }
-+ }
-+
-+
-+ if(SSP_PCAP_ADJ_BIT_ISR_A1I&tempValue)
-+ {
-+ if(SSP_PCAP_BIT_ZERO == SSP_PCAP_get_bit_from_buffer(SSP_PCAP_ADJ_BIT_MSR_A1M))
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n A1_INT insert/remove case, need to handle. ISR =%x ",tempValue );
-+#endif
-+#ifdef PCAP_LOG_FFUART_OUT
-+ sprintf(temp,"A1_INT insert/remove case, need to handle. ISR =%x ",tempValue );
-+ pcap_log_add_data(temp,strlen(temp));
-+#endif
-+ /* earpiece insert/remove need handler */
-+ if (headjack_change_interrupt_routine)
-+ (*headjack_change_interrupt_routine)(0,NULL,NULL);
-+ }
-+ else
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n A1_INT should be discarded." );
-+#endif
-+ }
-+ }
-+
-+ if(SSP_PCAP_ADJ_BIT_ISR_MB2I&tempValue)
-+ {
-+ if(SSP_PCAP_BIT_ZERO == SSP_PCAP_get_bit_from_buffer(SSP_PCAP_ADJ_BIT_MSR_MB2M))
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n MIC insert/remove case, need to handle! ISR =%x ",tempValue );
-+#endif
-+#ifdef PCAP_LOG_FFUART_OUT
-+ sprintf(temp,"MIC insert/remove case, need to handle! ISR =%x ",tempValue );
-+ pcap_log_add_data(temp,strlen(temp));
-+#endif
-+ //queue_apm_event(KRNL_KEYPAD,NULL);
-+ /* mic insert/remove or answer/end call handler */
-+ if (mic_change_interrupt_routine)
-+ (*mic_change_interrupt_routine)(0,NULL,NULL);
-+ }
-+ else
-+ {
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk( "\n************************* \n SSP MB2I should be discarded.");
-+#endif
-+ }
-+ }
-+ if(GPLR0&0x00000002)
-+ {
-+ /* this case is a very critical case. */
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("repeat pcap int!",strlen("repeat pcap int!"));
-+#endif
-+ if(pcap_repeat_num<10)
-+ {
-+ pcap_repeat_num++;
-+ goto intRepeat;
-+ }
-+ else
-+ {
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("repeat pcap exceed 10 times!",strlen("repeat pcap exceed 10 times!"));
-+#endif
-+ }
-+ }
-+ return;
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+
-+#ifdef SSP_PCAP_OPERATE_WITH_SPI
-+
-+void ssp_put_intoData(U32 pcapValue)
-+{
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ char string[100];
-+#endif
-+ U32 tempFirstByte;
-+ U32 tempSecondByte;
-+ tempFirstByte = (pcapValue&SSP_PCAP_REGISTER_VALUE_UP_WORD_MASK)>>SSP_PCAP_REGISTER_VALUE_LENGTH;
-+ tempSecondByte = (pcapValue&SSP_PCAP_REGISTER_VALUE_DOWN_WORD_MASK);
-+ /* disable all interrupt or disable the SSP (zero to SSE) */
-+ local_irq_disable();
-+ SSDR = tempFirstByte ;
-+ SSDR = tempSecondByte ;
-+ local_irq_enable();
-+#ifdef SSP_PCAP_OPERATE_DEBUG_INFORNMATION
-+ printk("\n ssp put dat \n");
-+ sprintf( string,"\n fisrt part =%8x second part =%8x \n",tempFirstByte,tempSecondByte);
-+ printk(string);
-+#endif
-+ return;
-+}
-+
-+#endif
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_write_data_to_PCAP(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER sspPcapRegister,U32 registerValue)
-+{
-+ u32 pcapTempValue ;
-+ unsigned long flags;
-+ /* prevent the process schedule out and mask the PCAP's interrupt handler */
-+ //ICMR &= ~(1<<(GPIO1_RST+PXA_IRQ_SKIP));
-+ save_flags(flags);
-+ local_irq_disable();
-+ spin_lock(&pcapoperation_lock);
-+
-+ if(!test_and_set_bit(0,&ssp_pcap_status))
-+ {
-+ switch(sspPcapRegister)
-+ {
-+#ifdef SSP_PCAP_DEBUG_BOARD
-+ case 3:
-+ case 22:
-+#endif
-+ case SSP_PCAP_ADJ_ISR_REGISTER:
-+ case SSP_PCAP_ADJ_MSR_REGISTER:
-+ case SSP_PCAP_ADJ_PSTAT_REGISTER:
-+ case SSP_PCAP_ADJ_VREG2_REGISTER:
-+ case SSP_PCAP_ADJ_AUX_VREG_REGISTER:
-+ case SSP_PCAP_ADJ_BATT_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_ADC1_REGISTER:
-+ case SSP_PCAP_ADJ_ADC2_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_CODEC_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_ST_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_BUSCTRL_REGISTER:
-+ case SSP_PCAP_ADJ_PERIPH_REGISTER:
-+ case SSP_PCAP_ADJ_LOWPWR_CTRL_REGISTER:
-+ case SSP_PCAP_ADJ_TX_AUD_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_GP_REG_REGISTER:
-+ ssp_pcap_registerValue[sspPcapRegister] = registerValue&SSP_PCAP_REGISTER_VALUE_MASK;
-+ pcapTempValue = SSP_PCAP_REGISTER_WRITE_OP_BIT|(sspPcapRegister<<SSP_PCAP_REGISTER_ADDRESS_SHIFT )|(ssp_pcap_registerValue[sspPcapRegister]);
-+
-+#ifdef SSP_PCAP_OPERATE_WITH_SPI
-+ ssp_put_intoData(pcapTempValue);
-+ interruptible_sleep_on(&ssp_pcap_send_wait);
-+ /* here need to judge the wakeup reason and handle it */
-+#else
-+ ssp_pcap_gpioWrite(pcapTempValue);
-+#endif
-+ clear_bit(0,&ssp_pcap_status);
-+
-+ /* Now it's OK */
-+ spin_unlock(&pcapoperation_lock);
-+ restore_flags(flags);
-+ //ICMR |= (1<<(GPIO1_RST+PXA_IRQ_SKIP));
-+/*
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("write pcap end!",strlen("write pcap end!"));
-+#endif
-+*/
-+ return SSP_PCAP_SUCCESS;
-+ /* maybe here should NOT be a break */
-+ break;
-+ default:
-+ clear_bit(0,&ssp_pcap_status);
-+
-+ /* Now it's OK */
-+ spin_unlock(&pcapoperation_lock);
-+ restore_flags(flags);
-+ //ICMR |= (1<<(GPIO1_RST+PXA_IRQ_SKIP));
-+/*
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("write pcap error register!",strlen("write pcap error register!"));
-+#endif
-+*/
-+ return SSP_PCAP_ERROR_REGISTER;
-+ /* maybe here should NOT be a break */
-+ break;
-+ }
-+ }
-+ else
-+ {
-+
-+ /* Now it's OK */
-+ spin_unlock(&pcapoperation_lock);
-+ restore_flags(flags);
-+ //ICMR |= (1<<(GPIO1_RST+PXA_IRQ_SKIP));
-+/*
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("write pcap not run!",strlen("write pcap not run!"));
-+#endif
-+*/
-+ return SSP_PCAP_NOT_RUN;
-+ }
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_read_data_from_PCAP(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER sspPcapRegister,P_U32 pSspPcapRegisterValue)
-+{
-+#ifdef SSP_PCAP_OPERATE_WITH_SPI
-+ U32 pcapTempValue;
-+#endif
-+ unsigned long flags;
-+/*
-+#ifdef PCAP_LOG_FFUART_OUT
-+ pcap_log_add_data("read pcap start!",strlen("read pcap start!"));
-+#endif
-+*/
-+ /* prevent the process schedule out and mask the PCAP's interrupt handler */
-+ //ICMR &= ~(1<<(GPIO1_RST+PXA_IRQ_SKIP));
-+ save_flags(flags);
-+ local_irq_disable();
-+ spin_lock(&pcapoperation_lock);
-+
-+ if(!test_and_set_bit(0,&ssp_pcap_status))
-+ {
-+ switch(sspPcapRegister)
-+ {
-+#ifdef SSP_PCAP_DEBUG_BOARD
-+ case 3:
-+ case 22:
-+#endif
-+ case SSP_PCAP_ADJ_ISR_REGISTER:
-+ case SSP_PCAP_ADJ_MSR_REGISTER:
-+ case SSP_PCAP_ADJ_PSTAT_REGISTER:
-+ case SSP_PCAP_ADJ_VREG2_REGISTER:
-+ case SSP_PCAP_ADJ_AUX_VREG_REGISTER:
-+ case SSP_PCAP_ADJ_BATT_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_ADC1_REGISTER:
-+ case SSP_PCAP_ADJ_ADC2_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_CODEC_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_ST_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_BUSCTRL_REGISTER:
-+ case SSP_PCAP_ADJ_PERIPH_REGISTER:
-+ case SSP_PCAP_ADJ_LOWPWR_CTRL_REGISTER:
-+ case SSP_PCAP_ADJ_TX_AUD_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_GP_REG_REGISTER:
-+#ifdef SSP_PCAP_OPERATE_WITH_SPI
-+ pcapTempValue = SSP_PCAP_REGISTER_READ_OP_BIT|(sspPcapRegister<<SSP_PCAP_REGISTER_ADDRESS_SHIFT );
-+ ssp_put_intoData(pcapTempValue);
-+ /* sleep with timeout */
-+ interruptible_sleep_on(&ssp_pcap_send_wait);
-+
-+ /* here need to judge the wakeup reason and handle it */
-+// if (signal_pending(current)) {
-+// ret = -ERESTARTSYS;
-+// break;
-+// }
-+ *pSspPcapRegisterValue = ssp_pcap_readValue;
-+#else
-+ ssp_pcap_gpioRead(sspPcapRegister,pSspPcapRegisterValue);
-+#endif
-+ ssp_pcap_registerValue[sspPcapRegister] = *pSspPcapRegisterValue&SSP_PCAP_REGISTER_VALUE_MASK;
-+ clear_bit(0,&ssp_pcap_status);
-+
-+ /* Now it's OK */
-+ spin_unlock(&pcapoperation_lock);
-+ restore_flags(flags);
-+ //ICMR |= (1<<(GPIO1_RST+PXA_IRQ_SKIP));
-+ return SSP_PCAP_SUCCESS;
-+ /* maybe here should NOT be a break */
-+ break;
-+ default:
-+ clear_bit(0,&ssp_pcap_status);
-+
-+ /* Now it's OK */
-+ spin_unlock(&pcapoperation_lock);
-+ restore_flags(flags);
-+ //ICMR |= (1<<(GPIO1_RST+PXA_IRQ_SKIP));
-+ return SSP_PCAP_ERROR_REGISTER;
-+ /* maybe here should NOT be a break */
-+ break;
-+ }
-+ }
-+ else
-+ {
-+ /* Now it's OK */
-+ spin_unlock(&pcapoperation_lock);
-+ restore_flags(flags);
-+ //ICMR |= (1<<(GPIO1_RST+PXA_IRQ_SKIP));
-+ return SSP_PCAP_NOT_RUN;
-+ }
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_bit_set(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE sspPcapBit )
-+{
-+ U32 sspPcapRegisterBitValue;
-+ SSP_PCAP_STATUS ret;
-+ U8 sspPcapRegister = (sspPcapBit&SSP_PCAP_REGISTER_ADDRESS_MASK)>>SSP_PCAP_REGISTER_ADDRESS_SHIFT;
-+
-+ switch(sspPcapRegister)
-+ {
-+ case SSP_PCAP_ADJ_ISR_REGISTER:
-+ ssp_pcap_registerValue[sspPcapRegister] = 0;
-+#ifdef SSP_PCAP_DEBUG_BOARD
-+ case 22:
-+#endif
-+ case SSP_PCAP_ADJ_MSR_REGISTER:
-+ case SSP_PCAP_ADJ_PSTAT_REGISTER:
-+ case SSP_PCAP_ADJ_VREG2_REGISTER:
-+ case SSP_PCAP_ADJ_AUX_VREG_REGISTER:
-+ case SSP_PCAP_ADJ_BATT_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_ADC1_REGISTER:
-+ case SSP_PCAP_ADJ_ADC2_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_CODEC_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_ST_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_BUSCTRL_REGISTER:
-+ case SSP_PCAP_ADJ_PERIPH_REGISTER:
-+ case SSP_PCAP_ADJ_LOWPWR_CTRL_REGISTER:
-+ case SSP_PCAP_ADJ_TX_AUD_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_GP_REG_REGISTER:
-+
-+ sspPcapRegisterBitValue = (sspPcapBit&SSP_PCAP_REGISTER_VALUE_MASK);
-+ ssp_pcap_registerValue[sspPcapRegister] |= sspPcapRegisterBitValue;
-+ /* should care the return value */
-+ ret =SSP_PCAP_write_data_to_PCAP(sspPcapRegister,ssp_pcap_registerValue[sspPcapRegister]);
-+ return SSP_PCAP_SUCCESS;
-+ break;
-+ default:
-+ return SSP_PCAP_ERROR_REGISTER;
-+ break;
-+ }
-+ return SSP_PCAP_SUCCESS;
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_STATUS SSP_PCAP_bit_clean(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE sspPcapBit )
-+{
-+ U32 sspPcapRegisterBitValue;
-+ SSP_PCAP_STATUS ret;
-+ U8 sspPcapRegister = (sspPcapBit&SSP_PCAP_REGISTER_ADDRESS_MASK)>>SSP_PCAP_REGISTER_ADDRESS_SHIFT;
-+
-+ switch(sspPcapRegister)
-+ {
-+ case SSP_PCAP_ADJ_ISR_REGISTER:
-+ ssp_pcap_registerValue[sspPcapRegister] = 0;
-+ case SSP_PCAP_ADJ_MSR_REGISTER:
-+ case SSP_PCAP_ADJ_PSTAT_REGISTER:
-+ case SSP_PCAP_ADJ_VREG2_REGISTER:
-+ case SSP_PCAP_ADJ_AUX_VREG_REGISTER:
-+ case SSP_PCAP_ADJ_BATT_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_ADC1_REGISTER:
-+ case SSP_PCAP_ADJ_ADC2_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_CODEC_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_ST_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_BUSCTRL_REGISTER:
-+ case SSP_PCAP_ADJ_PERIPH_REGISTER:
-+ case SSP_PCAP_ADJ_LOWPWR_CTRL_REGISTER:
-+ case SSP_PCAP_ADJ_TX_AUD_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_GP_REG_REGISTER:
-+ sspPcapRegisterBitValue = (sspPcapBit&SSP_PCAP_REGISTER_VALUE_MASK);
-+ ssp_pcap_registerValue[sspPcapRegister] &= ~sspPcapRegisterBitValue;
-+ /* should care the return value */
-+ ret =SSP_PCAP_write_data_to_PCAP(sspPcapRegister,ssp_pcap_registerValue[sspPcapRegister]);
-+ return SSP_PCAP_SUCCESS;
-+ break;
-+ default:
-+ return SSP_PCAP_ERROR_REGISTER;
-+ break;
-+ }
-+ return SSP_PCAP_SUCCESS;
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_BIT_STATUS SSP_PCAP_get_bit_from_buffer(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE sspPcapBit )
-+{
-+ U32 sspPcapRegisterBitValue;
-+ U8 sspPcapRegister = (sspPcapBit&SSP_PCAP_REGISTER_ADDRESS_MASK)>>SSP_PCAP_REGISTER_ADDRESS_SHIFT;
-+ switch(sspPcapRegister)
-+ {
-+ case SSP_PCAP_ADJ_ISR_REGISTER:
-+ case SSP_PCAP_ADJ_MSR_REGISTER:
-+ case SSP_PCAP_ADJ_PSTAT_REGISTER:
-+ case SSP_PCAP_ADJ_VREG2_REGISTER:
-+ case SSP_PCAP_ADJ_AUX_VREG_REGISTER:
-+ case SSP_PCAP_ADJ_BATT_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_ADC1_REGISTER:
-+ case SSP_PCAP_ADJ_ADC2_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_CODEC_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_ST_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_BUSCTRL_REGISTER:
-+ case SSP_PCAP_ADJ_PERIPH_REGISTER:
-+ case SSP_PCAP_ADJ_LOWPWR_CTRL_REGISTER:
-+ case SSP_PCAP_ADJ_TX_AUD_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_GP_REG_REGISTER:
-+ sspPcapRegisterBitValue = (sspPcapBit&SSP_PCAP_REGISTER_VALUE_MASK);
-+ sspPcapRegisterBitValue &= ssp_pcap_registerValue[sspPcapRegister];
-+ if(sspPcapRegisterBitValue)
-+ {
-+ return SSP_PCAP_BIT_ONE;
-+ }
-+ else
-+ {
-+ return SSP_PCAP_BIT_ZERO;
-+ }
-+ break;
-+ default:
-+ return SSP_PCAP_BIT_ERROR;
-+ break;
-+ }
-+ return SSP_PCAP_BIT_ERROR;
-+}
-+
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+SSP_PCAP_BIT_STATUS SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER_BIT_TYPE sspPcapBit )
-+{
-+ U32 sspPcapTempRegisterValue;
-+ U32 sspPcapRegisterBitValue;
-+ SSP_PCAP_STATUS ret;
-+ U8 sspPcapRegister = (sspPcapBit&SSP_PCAP_REGISTER_ADDRESS_MASK)>>SSP_PCAP_REGISTER_ADDRESS_SHIFT;
-+
-+ switch(sspPcapRegister)
-+ {
-+ case SSP_PCAP_ADJ_ISR_REGISTER:
-+ case SSP_PCAP_ADJ_MSR_REGISTER:
-+ case SSP_PCAP_ADJ_PSTAT_REGISTER:
-+ case SSP_PCAP_ADJ_VREG2_REGISTER:
-+ case SSP_PCAP_ADJ_AUX_VREG_REGISTER:
-+ case SSP_PCAP_ADJ_BATT_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_ADC1_REGISTER:
-+ case SSP_PCAP_ADJ_ADC2_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_CODEC_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_ST_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_BUSCTRL_REGISTER:
-+ case SSP_PCAP_ADJ_PERIPH_REGISTER:
-+ case SSP_PCAP_ADJ_LOWPWR_CTRL_REGISTER:
-+ case SSP_PCAP_ADJ_TX_AUD_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_GP_REG_REGISTER:
-+ sspPcapRegisterBitValue = (sspPcapBit&SSP_PCAP_REGISTER_VALUE_MASK);
-+ /* should care the return value */
-+ ret = SSP_PCAP_read_data_from_PCAP(sspPcapRegister,&sspPcapTempRegisterValue);
-+ sspPcapRegisterBitValue &= sspPcapTempRegisterValue;
-+ if(sspPcapRegisterBitValue)
-+ {
-+ return SSP_PCAP_BIT_ONE;
-+ }
-+ else
-+ {
-+ return SSP_PCAP_BIT_ZERO;
-+ }
-+ break;
-+ default:
-+ return SSP_PCAP_BIT_ERROR;
-+ break;
-+ }
-+ return SSP_PCAP_BIT_ERROR;
-+}
-+/*---------------------------------------------------------------------------
-+ DESCRIPTION:
-+
-+ INPUTS:
-+
-+
-+ OUTPUTS:
-+
-+
-+ IMPORTANT NOTES:
-+
-+
-+---------------------------------------------------------------------------*/
-+U32 SSP_PCAP_get_register_value_from_buffer(SSP_PCAP_SECONDARY_PROCESSOR_REGISTER sspPcapRegister )
-+{
-+ switch(sspPcapRegister)
-+ {
-+ case SSP_PCAP_ADJ_ISR_REGISTER:
-+ case SSP_PCAP_ADJ_MSR_REGISTER:
-+ case SSP_PCAP_ADJ_PSTAT_REGISTER:
-+ case SSP_PCAP_ADJ_VREG2_REGISTER:
-+ case SSP_PCAP_ADJ_AUX_VREG_REGISTER:
-+ case SSP_PCAP_ADJ_BATT_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_ADC1_REGISTER:
-+ case SSP_PCAP_ADJ_ADC2_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_CODEC_REGISTER:
-+ case SSP_PCAP_ADJ_AUD_RX_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_ST_DAC_REGISTER:
-+ case SSP_PCAP_ADJ_BUSCTRL_REGISTER:
-+ case SSP_PCAP_ADJ_PERIPH_REGISTER:
-+ case SSP_PCAP_ADJ_LOWPWR_CTRL_REGISTER:
-+ case SSP_PCAP_ADJ_TX_AUD_AMPS_REGISTER:
-+ case SSP_PCAP_ADJ_GP_REG_REGISTER:
-+ return ssp_pcap_registerValue[sspPcapRegister];
-+ break;
-+ default:
-+ return SSP_PCAP_ERROR_REGISTER;
-+ break;
-+ }
-+}
-+#ifdef __cplusplus
-+}
-+#endif
-Index: linux-2.6.16.5-a/drivers/char/Kconfig
-===================================================================
---- linux-2.6.16.5-a.orig/drivers/char/Kconfig 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/drivers/char/Kconfig 2006-05-04 17:07:04.000000000 +0200
-@@ -1007,6 +1007,16 @@
- The mmtimer device allows direct userspace access to the
- Altix system timer.
-
-+config LINUX_LED
-+ tristate "LED support"
-+
-+config PXA_E680_LED
-+ tristate "E680 LED suppory"
-+ depends on LINUX_LED
-+
-+config BULVERDE_SRAM_DEV
-+ tristate "BULVERDE Internal SRAM char device"
-+
- source "drivers/char/tpm/Kconfig"
-
- config TELCLOCK
-Index: linux-2.6.16.5-a/drivers/char/Makefile
-===================================================================
---- linux-2.6.16.5-a.orig/drivers/char/Makefile 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/drivers/char/Makefile 2006-05-04 17:07:04.000000000 +0200
-@@ -95,6 +95,14 @@
-
- obj-$(CONFIG_HANGCHECK_TIMER) += hangcheck-timer.o
- obj-$(CONFIG_TCG_TPM) += tpm/
-+
-+obj-$(CONFIG_LINUX_LED) += led.o
-+obj-$(CONFIG_PXA_E680_LED) += led_pxa_e680.o
-+
-+obj-$(CONFIG_MAINSTONE_KEYPAD) += mstone_keypad.o
-+obj-$(CONFIG_BULVERDE_SRAM_DEV) += sram.o
-+
-+
- # Files generated that shall be removed upon make clean
- clean-files := consolemap_deftbl.c defkeymap.c qtronixmap.c
-
-Index: linux-2.6.16.5-a/drivers/char/gpio_test.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/char/gpio_test.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,216 @@
-+/*
-+ * linux/drivers/char/gpio_test.c
-+ *
-+ * Support for the Motorola Ezx A780 Development Platform.
-+ *
-+ * Author: Jay Jia
-+ * Created: April 25, 2004
-+ * Copyright: Motorola Inc.
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ *
-+ */
-+#include <linux/module.h>
-+#include <linux/kernel.h>
-+#include <linux/delay.h>
-+#include <linux/init.h>
-+#include <linux/kdev_t.h>
-+#include <linux/fs.h>
-+#include <linux/wrapper.h>
-+#include <asm/hardware.h>
-+#include <asm/irq.h>
-+#include <linux/init.h>
-+#include <linux/interrupt.h>
-+#include <asm/arch/ezx.h>
-+#include "../misc/ssp_pcap.h"
-+
-+
-+#define SUCCESS 0
-+#define DEVICE_NAME "gpio_test"
-+#define GPIO_TEST_IOCTL_CMD_OPS_MASK 0x000F
-+#define GPIO_TEST_IOCTL_CMD_VAL_MASK 0x0080
-+#define GPIO_TEST_IOCTL_CMD_NUM_MASK 0xFF00
-+#define GPIO_TEST_IOCTL_CMD_VAL_SHIFT 7
-+#define GPIO_TEST_IOCTL_CMD_NUM_SHIFT 8
-+
-+static int Major=127;
-+static unsigned char pcap_usb_ps = 0;
-+static unsigned char pcap_vusb_en = 0;
-+static unsigned char pcap_ov_test_on = 0;
-+
-+static int gpio_test_open(struct inode *inode,struct file *file)
-+{
-+ MOD_INC_USE_COUNT;
-+ return SUCCESS;
-+}
-+
-+static int gpio_test_release(struct inode *inode,struct file *file)
-+
-+{
-+ MOD_DEC_USE_COUNT;
-+ return SUCCESS;
-+}
-+
-+
-+/*******************************************************************************
-+Function Name: gpio_test_ioctl
-+
-+Parameter:
-+ The ioctl() accept a 2-byte command : cmd
-+ Use this param as follows:
-+
-+ bit 0 - 3: operation type.
-+ 0x01, gpio read
-+ 0x02, gpio write
-+ 0x03, gpio config
-+ 0x04, PCAP test
-+ bit 4 -6:
-+ reserved. keep ZERO
-+ bit 7:
-+ For gpio, write/config value.
-+ For Over voltage test,
-+ 0, ON
-+ 1, OFF
-+ bit 8 - 15:
-+ For gpio, it is gpio pin number
-+ For PCAP test,
-+ 0x01, Over voltage test.
-+ others, reserved.
-+
-+Return Value:
-+ For Over voltage test,
-+ return 0 for success.
-+ return 1 for error.
-+*******************************************************************************/
-+static int gpio_test_ioctl(struct inode *inode,struct file *file,unsigned short cmd,unsigned long arg)
-+{
-+ int num, val, ops, ret;
-+
-+ ret = 0;
-+ num = (cmd & GPIO_TEST_IOCTL_CMD_NUM_MASK) >> GPIO_TEST_IOCTL_CMD_NUM_SHIFT;
-+ val = cmd & GPIO_TEST_IOCTL_CMD_VAL_MASK;
-+ ops = cmd & GPIO_TEST_IOCTL_CMD_OPS_MASK;
-+
-+ if(ops == 1)/*read gpio*/
-+ {
-+// set_GPIO_mode(num);
-+// GPDR(num) &= ~GPIO_bit(num);
-+ ret = GPLR(num) & GPIO_bit(num);
-+// printk("in GPIO kernel read function, num = %d and ret = %d\n",num,ret);
-+ return (ret == 0) ? 0:1;
-+ }
-+
-+ if(ops == 2)/*write gpio*/
-+ {
-+// set_GPIO_mode(num);
-+// GPDR(num) |= GPIO_bit(num);
-+ if( val )
-+ GPSR(num) = GPIO_bit(num);
-+ else
-+ GPCR(num) = GPIO_bit(num);
-+ return 2;
-+ }
-+
-+ if(ops == 3)/*set gpio*/
-+ {
-+ set_GPIO_mode(num);
-+ if( val )
-+ GPDR(num) |= GPIO_bit(num);
-+ else
-+ GPDR(num) &= ~GPIO_bit(num);
-+ return 3;
-+ }
-+
-+ if(ops == 4)/* PCAP test */
-+ {
-+ printk("PCAP test, cmd = 0x%x.\n", cmd);
-+ val = val >> GPIO_TEST_IOCTL_CMD_VAL_SHIFT;
-+ switch(num)
-+ {
-+ case 1: /* Over Voltage test */
-+ if(val == 0) /* ON */
-+ {
-+ printk("Over Voltage test ON.\n");
-+ /* backup USB_PS and VUSB_EN */
-+ pcap_ov_test_on = 1;
-+ pcap_usb_ps = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PS);
-+ pcap_vusb_en = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ /* USB_PS = 0, PCAP USB powered by VUSB_IN */
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PS);
-+ /* VUSB_EN = 1, USB tranceiver enabled */
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ /* USB 1V INT mask */
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_MSR_USB1VM);
-+ /* USB 4V INT mask */
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_MSR_USB4VM);
-+ ret = 0;
-+ }
-+ else if(val == 1) /* OFF */
-+ {
-+ printk("Over Voltage test OFF.\n");
-+ if(pcap_ov_test_on != 1)
-+ {
-+ ret = 1; /* return error */
-+ break;
-+ }
-+ /* restore USB_PS and VUSB_EN */
-+ if(pcap_usb_ps)
-+ {
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PS);
-+ }
-+ else
-+ {
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PS);
-+ }
-+ if(pcap_vusb_en)
-+ {
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ }
-+ else
-+ {
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ }
-+ pcap_ov_test_on = 0;
-+ /* USB 1V INT unmask */
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_USB1VI); /* clear 1V INT status */
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_MSR_USB1VM);
-+ /* USB 4V INT unmask */
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_USB4VI); /* clear 4V INT status */
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_MSR_USB4VM);
-+ ret = 0;
-+ }
-+ else /* Unrecongized command */
-+ {
-+ ret = 1;
-+ }
-+ break;
-+ default:
-+ ret = 1;
-+ }
-+ return ret;
-+ } /* end of PCAP test */
-+}
-+
-+static struct file_operations gpio_test_fops={
-+ ioctl: gpio_test_ioctl,
-+ open: gpio_test_open,
-+ release:gpio_test_release,
-+};
-+
-+int gpio_test_init_module()
-+{
-+ register_chrdev(Major, DEVICE_NAME, &gpio_test_fops);
-+ return 0;
-+}
-+
-+void gpio_test_cleanup_module()
-+{
-+ unregister_chrdev(Major,DEVICE_NAME);
-+}
-+
-+module_init(gpio_test_init_module);
-+module_exit(gpio_test_cleanup_module);
-+MODULE_AUTHOR("Jay Jia");
-+MODULE_LICENSE("GPL");
-Index: linux-2.6.16.5-a/drivers/char/led.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/char/led.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,318 @@
-+/*
-+ * Device driver for controlling LEDs. See linux/led.h for info on
-+ * how to use this.
-+ *
-+ * This currently only supports mono and bicolor LEDs, but support for
-+ * fancier LEDs (scrolling text or numeric LEDs, for instance) could
-+ * easily be added.
-+ *
-+ * Corey Minyard <minyard@mvista.com>
-+ */
-+
-+#include <linux/config.h>
-+#include <linux/module.h>
-+#include <linux/version.h>
-+#include <linux/types.h>
-+#include <linux/errno.h>
-+#include <linux/miscdevice.h>
-+#include <asm/io.h>
-+#include <asm/uaccess.h>
-+#include <asm/system.h>
-+#include <linux/init.h>
-+#include <linux/led.h>
-+#include <linux/string.h>
-+#include <linux/spinlock.h>
-+
-+#define VERSION "1.0"
-+
-+/* A lock that is held when manipulating LED info. */
-+static spinlock_t led_lock = SPIN_LOCK_UNLOCKED;
-+
-+/* A linked list of all the LEDs registered. */
-+static struct led_reg_info *leds;
-+
-+/* Register a new LED with the driver. */
-+int register_led_info(struct led_reg_info *info)
-+{
-+ struct led_reg_info *led;
-+ int rv = 0;
-+
-+ spin_lock(&led_lock);
-+ info->next = NULL;
-+ led = leds;
-+ if (led == NULL)
-+ {
-+ leds = info;
-+ }
-+ else
-+ {
-+ while (led->next != NULL)
-+ {
-+ if (strcmp(led->info->name, info->info->name) == 0)
-+ {
-+ /* Registering a duplicate. */
-+ rv = -1;
-+ goto out;
-+ }
-+ led = led->next;
-+ }
-+ led->next = info;
-+ }
-+ MOD_INC_USE_COUNT;
-+
-+out:
-+ spin_unlock(&led_lock);
-+
-+ return rv;
-+}
-+
-+/* Unregister an LED from the driver. */
-+int unregister_led_info(struct led_reg_info *info)
-+{
-+ int rv = -1;
-+ struct led_reg_info *led;
-+
-+ if (info == NULL)
-+ {
-+ return -1;
-+ }
-+
-+ spin_lock(&led_lock);
-+ led = leds;
-+ if (led == info)
-+ {
-+ MOD_DEC_USE_COUNT;
-+ leds = leds->next;
-+ }
-+ else
-+ {
-+ while (led->next != NULL)
-+ {
-+ if (led->next == info)
-+ {
-+ MOD_DEC_USE_COUNT;
-+ led->next = info->next;
-+ rv = 0;
-+ goto out;
-+ }
-+ led = led->next;
-+ }
-+ }
-+out:
-+ spin_unlock(&led_lock);
-+ return rv;
-+}
-+
-+/* Return the number of LEDs registered. */
-+static int count_leds(void)
-+{
-+ struct led_reg_info *led;
-+ int count = 0;
-+
-+ spin_lock(&led_lock);
-+ led = leds;
-+ while (led != NULL)
-+ {
-+ count = count + 1;
-+ led = led->next;
-+ }
-+ spin_unlock(&led_lock);
-+
-+ return count;
-+}
-+
-+/* Find an LED by its number. Must be called with the led spin lock
-+ held. */
-+static struct led_reg_info *get_led_by_num(int num)
-+{
-+ struct led_reg_info *led;
-+ int count = num;
-+
-+ led = leds;
-+ while (led != NULL)
-+ {
-+ if (count == 0)
-+ {
-+ led->info->led_num = num;
-+ return led;
-+ }
-+ count = count - 1;
-+ led = led->next;
-+ }
-+
-+ return NULL;
-+}
-+
-+/* Find an LED by its name. Must be called with the led spin lock
-+ held. */
-+static struct led_reg_info *get_led_by_name(char *name)
-+{
-+ struct led_reg_info *led;
-+ int count = 0;
-+
-+ led = leds;
-+ while (led != NULL)
-+ {
-+ if (strcmp(name, led->info->name) == 0)
-+ {
-+ led->info->led_num = count;
-+ return led;
-+ }
-+ count++;
-+ led = led->next;
-+ }
-+
-+ return NULL;
-+}
-+
-+/* The IOCTL handler for the LED driver. */
-+static int led_ioctl(struct inode *inode,
-+ struct file *file,
-+ unsigned int cmd,
-+ unsigned long arg)
-+{
-+ int i;
-+ struct led_reg_info *led;
-+ struct led_info info;
-+ struct led_op op;
-+
-+ switch(cmd)
-+ {
-+ case LEDIOC_GETCOUNT:
-+ return count_leds();
-+
-+ case LEDIOC_GETINFO_BY_NUM:
-+ case LEDIOC_GETINFO_BY_NAME:
-+ i = copy_from_user(&info, (void*)arg, sizeof(info));
-+ if (i)
-+ {
-+ return -EFAULT;
-+ }
-+
-+ spin_lock(&led_lock);
-+ if (cmd == LEDIOC_GETINFO_BY_NUM)
-+ led = get_led_by_num(info.led_num);
-+ else
-+ led = get_led_by_name(info.name);
-+ if (led == NULL)
-+ {
-+ spin_unlock(&led_lock);
-+ return -EINVAL;
-+ }
-+
-+ info.type = led->info->type;
-+ info.led_num = led->info->led_num;
-+ strcpy(info.name, led->info->name);
-+ info.info = led->info->info;
-+ i = copy_to_user((void *)arg, &info, sizeof(info));
-+
-+ spin_unlock(&led_lock);
-+
-+ if (i)
-+ {
-+ return -EFAULT;
-+ }
-+ return 0;
-+
-+ case LEDIOC_OP:
-+ i = copy_from_user(&op, (void*)arg, sizeof(op));
-+ if (i)
-+ {
-+ return -EFAULT;
-+ }
-+
-+ spin_lock(&led_lock);
-+ led = get_led_by_name(op.name);
-+ if (led == NULL)
-+ {
-+ spin_unlock(&led_lock);
-+ return -EINVAL;
-+ }
-+
-+ i = led->handle_led_op(led, &op);
-+ if (!i)
-+ {
-+ i = copy_to_user((void *)arg, &op, sizeof(op));
-+ if (i)
-+ {
-+ i = -EFAULT;
-+ }
-+ }
-+ spin_unlock(&led_lock);
-+
-+ return i;
-+
-+ default:
-+ return -ENOIOCTLCMD;
-+ }
-+}
-+
-+/* Not much to do for opening. */
-+static int led_open(struct inode *inode, struct file *file)
-+{
-+ switch(MINOR(inode->i_rdev))
-+ {
-+ case LED_MINOR:
-+ return 0;
-+
-+ default:
-+ return -ENODEV;
-+ }
-+}
-+
-+/* Closing is really easy. */
-+static int led_close(struct inode *inode, struct file *file)
-+{
-+ return 0;
-+}
-+
-+
-+static struct file_operations led_fops = {
-+ owner: THIS_MODULE,
-+ llseek: NULL,
-+ read: NULL,
-+ write: NULL,
-+ ioctl: led_ioctl,
-+ open: led_open,
-+ release: led_close,
-+};
-+
-+static struct miscdevice led_miscdev=
-+{
-+ LED_MINOR,
-+ "led",
-+ &led_fops
-+};
-+
-+
-+/* Remove the LED driver. */
-+static void __exit led_exit(void)
-+{
-+ misc_deregister(&led_miscdev);
-+}
-+
-+/* Set up the LED device driver. */
-+static int __init led_init(void)
-+{
-+ int ret;
-+
-+ printk("generic LED driver: v%s Corey Minyard (minyard@mvista.com)\n",
-+ VERSION);
-+
-+ leds = NULL;
-+ ret = misc_register(&led_miscdev);
-+ if (ret) {
-+ printk(KERN_ERR "led: can't misc_register on minor=%d\n",
-+ LED_MINOR);
-+ return -1;
-+ }
-+ return 0;
-+}
-+
-+module_init(led_init);
-+module_exit(led_exit);
-+
-+EXPORT_SYMBOL(register_led_info);
-+EXPORT_SYMBOL(unregister_led_info);
-+
-+MODULE_LICENSE("GPL");
-Index: linux-2.6.16.5-a/drivers/char/led_pxa_e680.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/char/led_pxa_e680.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,596 @@
-+/*--------------------------------------------------------------------------------------------
-+// Module Name: led_pxa_e680.c
-+//
-+// General Description: This is the driver for E680 LED.
-+//---------------------------------------------------------------------------------------------
-+// Motorola Confidential Proprietary
-+// (c) Copyright Motorola 2003-2004, All Rights Reserved
-+//
-+//
-+// Revision History:
-+// Modification Tracking
-+// Author (core ID) Date Number Description of Changes
-+// ------------------------- ------------ ---------- ----------------------------
-+// Liu weijie (A19553) 11/01/2003 LIBdd43835 Init create
-+// Wang Jamshid(a5036c) 04/29/2004 LIBee01180 fix bug,register pm call back
-+*/
-+#include <linux/config.h>
-+#include <linux/module.h>
-+#include <linux/version.h>
-+#include <linux/string.h>
-+#include <linux/kernel.h>
-+#include <asm/io.h>
-+#include <asm/errno.h>
-+#include <linux/init.h>
-+#include <linux/led_pxa_e680.h>
-+#include <linux/pm.h>
-+#include "../misc/ssp_pcap.h"
-+
-+#ifdef CONFIG_E680_P4A
-+#define IND_CNTL_R_BUL 79
-+#define IND_CNTL_G_BUL 18
-+#else
-+#define IND_CNTL_R_BUL 46
-+#define IND_CNTL_G_BUL 47
-+#endif
-+
-+#define SSP_PCAP_LED_MASK 0x000fffe0
-+#define SSP_PCAP_LED_SHIFT 5
-+
-+#define VERSION "1.0"
-+
-+//#define DEBUG_LED_DRIVER
-+
-+#ifdef DEBUG_LED_DRIVER
-+#define PRINTK(s...) printk(s)
-+#else
-+#define PRINTK(s...)
-+#endif
-+typedef struct
-+{
-+ unsigned char ind_GPIO_red; /*Indicator Red control GPIO 79: 0 active, 1 disactive*/
-+ unsigned char ind_GPIO_green; /*Indicator Green control GPIO 18: 0 active, 1 disactive*/
-+ unsigned char pcap_LEDR_en; /*pcap LEDR_EN bit value: 1 =Red LED(&Green)
-+ sink circuit enabled*/
-+ unsigned char pcap_LEDG_en; /*pcap LEDG_EN bit value:1 =Green(->Blue)LED
-+ sink circuit enabled*/
-+ unsigned char pcap_LEDR_CTRL; /* 4bits Sets the timing for the red(&Green) LED
-+ sink circuit*/
-+ unsigned char pcap_LEDG_CTRL; /* 4bits Sets the timing for the GREEN (->Blue) LED
-+ sink circuit*/
-+ unsigned char pcap_LEDR_I; /* 2 bits 00 3mA,01 4mA, 10 5mA, 11 9mA */
-+ /* sets the pulsed current level for LEDR*/
-+ unsigned char pcap_LEDG_I;
-+ unsigned char pcap_SKIP_on; /*1=The ON timing sequence defined by LEDx_CTRL
-+ is executed on every other cycle*/
-+}PCAP2_LED_REGISTER_VALUE;
-+
-+const PCAP2_LED_REGISTER_VALUE led_register_value [LED_BOTTOM_STATE +1 ]=
-+{
-+ {0x1,0x1, 0x0,0x0, 0x0,0x0, 0x0,0x0,0x0}, /*LED_OFF*/
-+
-+ /*Always On*/
-+ {0x0,0x1, 0x1,0x0, 0xc,0x0, 0x1,0x0,0x0}, /*LED_RED_ALWAYS_ON,skip off*/
-+ {0x1,0x0, 0x1,0x0, 0xc,0x0, 0x1,0x0,0x0}, /*LED_GREEN_ALWAYS_ON*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0xc, 0x0,0x0,0x0}, /*LED_BLUE_ALWAYS_ON*/
-+ {0x0,0x1, 0x1,0x1, 0xc,0xc, 0x1,0x0,0x0}, /*LED_LIGHT_RED_ALWAYS_ON*/
-+ {0x0,0x0, 0x1,0x0, 0xc,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_ALWAYS_ON*/
-+ {0x1,0x0, 0x1,0x1, 0xc,0xc, 0x1,0x0,0x0}, /*LED_LIGHT_BLUE_ALWAYS_ON*/
-+ {0x0,0x0, 0x1,0x1, 0xc,0xc, 0x1,0x0,0x0}, /*LED_WHITE_ALWAYS_ON*/
-+
-+ /* RED 5 mA current Skip OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x1,0x0, 0x1,0x0,0x0}, /*LED_RED_01_ON_19_OFF,skip off*/
-+ {0x0,0x1, 0x1,0x0, 0x2,0x0, 0x1,0x0,0x0}, /*LED_RED_02_ON_18_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x3,0x0, 0x1,0x0,0x0}, /*LED_RED_05_ON_15_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x4,0x0, 0x1,0x0,0x0}, /*LED_RED_025_ON_075_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x5,0x0, 0x1,0x0,0x0}, /*LED_RED_025_ON_175_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x6,0x0, 0x1,0x0,0x0}, /*LED_RED_005_ON_195_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x7,0x0, 0x1,0x0,0x0}, /*LED_RED_05_ON_05_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x8,0x0, 0x1,0x0,0x0}, /*LED_RED_05_OFF_05_ON*/
-+ {0x0,0x1, 0x1,0x0, 0x9,0x0, 0x1,0x0,0x0}, /*LED_RED_0125_ON_05_OFF_0075_ON_15_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0xa,0x0, 0x1,0x0,0x0}, /*LED_RED_0125_ON_2075_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0xb,0x0, 0x1,0x0,0x0}, /*LED_RED_0625_OFF_0075_ON_15_OFF*/
-+
-+ /* RED Skip ON*/
-+ {0x0,0x1, 0x1,0x0, 0x1,0x0, 0x1,0x0,0x1}, /*LED_RED_01_ON_19_OFF,skip On*/
-+ {0x0,0x1, 0x1,0x0, 0x2,0x0, 0x1,0x0,0x1}, /*LED_RED_02_ON_18_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x3,0x0, 0x1,0x0,0x1}, /*LED_RED_05_ON_15_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x4,0x0, 0x1,0x0,0x1}, /*LED_RED_025_ON_075_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x5,0x0, 0x1,0x0,0x1}, /*LED_RED_025_ON_175_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x6,0x0, 0x1,0x0,0x1}, /*LED_RED_005_ON_195_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x7,0x0, 0x1,0x0,0x1}, /*LED_RED_05_ON_05_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0x8,0x0, 0x1,0x0,0x1}, /*LED_RED_05_OFF_05_ON*/
-+ {0x0,0x1, 0x1,0x0, 0x9,0x0, 0x1,0x0,0x1}, /*LED_RED_0125_ON_05_OFF_0075_ON_15_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0xa,0x0, 0x1,0x0,0x1}, /*LED_RED_0125_ON_2075_OFF*/
-+ {0x0,0x1, 0x1,0x0, 0xb,0x0, 0x1,0x0,0x1}, /*LED_RED_0625_OFF_0075_ON_15_OFF*/
-+
-+ /*GREEN Skip OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x1,0x0, 0x1,0x0,0x0}, /*LED_GREEN_01_ON_19_OFF,skip off*/
-+ {0x1,0x0, 0x1,0x0, 0x2,0x0, 0x1,0x0,0x0}, /*LED_GREEN_02_ON_18_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x3,0x0, 0x1,0x0,0x0}, /*LED_GREEN_05_ON_15_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x4,0x0, 0x1,0x0,0x0}, /*LED_GREEN_025_ON_075_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x5,0x0, 0x1,0x0,0x0}, /*LED_GREEN_025_ON_175_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x6,0x0, 0x1,0x0,0x0}, /*LED_GREEN_005_ON_195_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x7,0x0, 0x1,0x0,0x0}, /*LED_GREEN_05_ON_05_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x8,0x0, 0x1,0x0,0x0}, /*LED_GREEN_05_OFF_05_ON*/
-+ {0x1,0x0, 0x1,0x0, 0x9,0x0, 0x1,0x0,0x0}, /*LED_GREEN_0125_ON_05_OFF_0075_ON_15_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0xa,0x0, 0x1,0x0,0x0}, /*LED_GREEN_0125_ON_2075_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0xb,0x0, 0x1,0x0,0x0}, /*LED_GREEN_0625_OFF_0075_ON_15_OFF*/
-+
-+ /*GREEN Skip ON*/
-+ {0x1,0x0, 0x1,0x0, 0x1,0x0, 0x1,0x0,0x1}, /*LED_GREEN_01_ON_19_OFF,skip On*/
-+ {0x1,0x0, 0x1,0x0, 0x2,0x0, 0x1,0x0,0x1}, /*LED_GREEN_02_ON_18_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x3,0x0, 0x1,0x0,0x1}, /*LED_GREEN_05_ON_15_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x4,0x0, 0x1,0x0,0x1}, /*LED_GREEN_025_ON_075_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x5,0x0, 0x1,0x0,0x1}, /*LED_GREEN_025_ON_175_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x6,0x0, 0x1,0x0,0x1}, /*LED_GREEN_005_ON_195_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x7,0x0, 0x1,0x0,0x1}, /*LED_GREEN_05_ON_05_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0x8,0x0, 0x1,0x0,0x1}, /*LED_GREEN_05_OFF_05_ON*/
-+ {0x1,0x0, 0x1,0x0, 0x9,0x0, 0x1,0x0,0x1}, /*LED_GREEN_0125_ON_05_OFF_0075_ON_15_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0xa,0x0, 0x1,0x0,0x1}, /*LED_GREEN_0125_ON_2075_OFF*/
-+ {0x1,0x0, 0x1,0x0, 0xb,0x0, 0x1,0x0,0x1}, /*LED_GREEN_0625_OFF_0075_ON_15_OFF*/
-+
-+ /*BLUE 5 mA Current Skip OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x1, 0x0,0x0,0x0}, /*LED_BLUE_01_ON_19_OFF,skip off*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x2, 0x0,0x0,0x0}, /*LED_BLUE_02_ON_18_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x3, 0x0,0x0,0x0}, /*LED_BLUE_05_ON_15_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x4, 0x0,0x0,0x0}, /*LED_BLUE_025_ON_075_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x5, 0x0,0x0,0x0}, /*LED_BLUE_025_ON_175_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x6, 0x0,0x0,0x0}, /*LED_BLUE_005_ON_195_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x7, 0x0,0x0,0x0}, /*LED_BLUE_05_ON_05_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x8, 0x0,0x0,0x0}, /*LED_BLUE_05_OFF_05_ON*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x9, 0x0,0x0,0x0}, /*LED_BLUE_0125_ON_05_OFF_0075_ON_15_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0xa, 0x0,0x0,0x0}, /*LED_BLUE_0125_ON_2075_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0xb, 0x0,0x0,0x0}, /*LED_BLUE_0625_OFF_0075_ON_15_OFF*/
-+
-+ /*BLUE 5 mA Current Skip On*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x1, 0x0,0x0,0x1}, /*LED_BLUE_01_ON_19_OFF,skip On*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x2, 0x0,0x0,0x1}, /*LED_BLUE_02_ON_18_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x3, 0x0,0x0,0x1}, /*LED_BLUE_05_ON_15_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x4, 0x0,0x0,0x1}, /*LED_BLUE_025_ON_075_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x5, 0x0,0x0,0x1}, /*LED_BLUE_025_ON_175_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x6, 0x0,0x0,0x1}, /*LED_BLUE_005_ON_195_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x7, 0x0,0x0,0x1}, /*LED_BLUE_05_ON_05_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x8, 0x0,0x0,0x1}, /*LED_BLUE_05_OFF_05_ON*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0x9, 0x0,0x0,0x1}, /*LED_BLUE_0125_ON_05_OFF_0075_ON_15_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0xa, 0x0,0x0,0x1}, /*LED_BLUE_0125_ON_2075_OFF*/
-+ {0x1,0x1, 0x0,0x1, 0x0,0xb, 0x0,0x0,0x1}, /*LED_BLUE_0625_OFF_0075_ON_15_OFF*/
-+
-+ /*ORANGE 5 mA Current Skip OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x1,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_01_ON_19_OFF,skip off*/
-+ {0x0,0x0, 0x1,0x0, 0x2,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_02_ON_18_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x3,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_05_ON_15_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x4,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_025_ON_075_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x5,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_025_ON_175_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x6,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_005_ON_195_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x7,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_05_ON_05_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x8,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_05_OFF_05_ON*/
-+ {0x0,0x0, 0x1,0x0, 0x9,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_0125_ON_05_OFF_0075_ON_15_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0xa,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_0125_ON_2075_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0xb,0x0, 0x1,0x0,0x0}, /*LED_ORANGE_0625_OFF_0075_ON_15_OFF*/
-+
-+ /*ORANGE 5 mA current Skip On*/
-+ {0x0,0x0, 0x1,0x0, 0x1,0x0, 0x1,0x0,0x1}, /*LED_ORANGE_01_ON_19_OFF,skip On*/
-+ {0x0,0x0, 0x1,0x0, 0x2,0x0, 0x1,0x0,0x1}, /*LED_ORANGE_02_ON_18_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x3,0x0, 0x1,0x0,0x1}, /*LED_ORANGE_05_ON_15_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x4,0x0, 0x1,0x0,0x1}, /*LED_ORANGE_025_ON_075_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x5,0x0, 0x1,0x0,0x1}, /*LED_ORANGE_025_ON_175_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x6,0x0, 0x1,0x0,0x1}, /*LED_ORANGE_005_ON_195_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x7,0x0, 0x1,0x0,0x1}, /*LED_ORANGE_05_ON_05_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0x8,0x0, 0x1,0x0,0x1}, /*LED_ORANGE_05_OFF_05_ON*/
-+ {0x0,0x0, 0x1,0x0, 0x9,0x0, 0x1,0x0,0x1}, /*LED_ORANGE_0125_ON_05_OFF_0075_ON_15_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0xa,0x0, 0x1,0x0,0x1}, /*LED_ORANGE_0125_ON_2075_OFF*/
-+ {0x0,0x0, 0x1,0x0, 0xb,0x0, 0x1,0x0,0x1}, /*LED_ORANGE_0625_OFF_0075_ON_15_OFF*/
-+
-+ /*LED_RED_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF*/
-+ {0x0,0x1, 0x1,0x1, 0xa,0xb, 0x1,0x0,0x0},
-+ /*LED_GREEN_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF*/
-+ {0x1,0x0, 0x1,0x1, 0xa,0xb, 0x1,0x0,0x0},
-+ /*LED_ORANGE_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF*/
-+ {0x0,0x0, 0x1,0x1, 0xa,0xb, 0x1,0x0,0x0},
-+
-+ /*LED_RED_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF_SKIP*/
-+ {0x0,0x1, 0x1,0x1, 0xa,0xb, 0x1,0x0,0x1},
-+ /*LED_GREEN_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF_SKIP*/
-+ {0x1,0x0, 0x1,0x1, 0xa,0xb, 0x1,0x0,0x1},
-+ /*LED_ORANGE_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF_SKIP*/
-+ {0x0,0x0, 0x1,0x1, 0xa,0xb, 0x1,0x0,0x1},
-+
-+ {0, 0, 0, 0, 0, 0, 0, 0, 0}
-+};
-+
-+#ifdef DEBUG_LED_DRIVER
-+char LED_Name[LED_BOTTOM_STATE +1][100]=
-+{
-+ "LED_OFF",
-+
-+ "LED_RED_ALWAYS_ON",
-+ "LED_GREEN_ALWAYS_ON",
-+ "LED_BLUE_ALWAYS_ON",
-+ "LED_LIGHT_RED_ALWAYS_ON",
-+ "LED_ORANGE_ALWAYS_ON",
-+ "LED_LIGHT_BLUE_ALWAYS_ON",
-+ "LED_WHITE_ALWAYS_ON",
-+
-+ "LED_RED_01_ON_19_OFF",
-+ "LED_RED_02_ON_18_OFF",
-+ "LED_RED_05_ON_15_OFF",
-+ "LED_RED_025_ON_075_OFF",
-+ "LED_RED_025_ON_175_OFF",
-+ "LED_RED_005_ON_195_OFF",
-+ "LED_RED_05_ON_05_OFF",
-+ "LED_RED_05_OFF_05_ON",
-+ "LED_RED_0125_ON_05_OFF_0075_ON_15_OFF",
-+ "LED_RED_0125_ON_2075_OFF",
-+ "LED_RED_0625_OFF_0075_ON_15_OFF",
-+
-+ "LED_RED_01_ON_19_OFF_SKIP",
-+ "LED_RED_02_ON_18_OFF_SKIP",
-+ "LED_RED_05_ON_15_OFF_SKIP",
-+ "LED_RED_025_ON_075_OFF_SKIP",
-+ "LED_RED_025_ON_175_OFF_SKIP",
-+ "LED_RED_005_ON_195_OFF_SKIP",
-+ "LED_RED_05_ON_05_OFF_SKIP",
-+ "LED_RED_05_OFF_05_ON_SKIP",
-+ "LED_RED_0125_ON_05_OFF_0075_ON_15_OFF_SKIP",
-+ "LED_RED_0125_ON_2075_OFF_SKIP",
-+ "LED_RED_0625_OFF_0075_ON_15_OFF_SKIP",
-+
-+ "LED_GREEN_01_ON_19_OFF",
-+ "LED_GREEN_02_ON_18_OFF",
-+ "LED_GREEN_05_ON_15_OFF",
-+ "LED_GREEN_025_ON_075_OFF",
-+ "LED_GREEN_025_ON_175_OFF",
-+ "LED_GREEN_005_ON_195_OFF",
-+ "LED_GREEN_05_ON_05_OFF",
-+ "LED_GREEN_05_OFF_05_ON",
-+ "LED_GREEN_0125_ON_05_OFF_0075_ON_15_OFF",
-+ "LED_GREEN_0125_ON_2075_OFF",
-+ "LED_GREEN_0625_OFF_0075_ON_15_OFF",
-+
-+ "LED_GREEN_01_ON_19_OFF_SKIP",
-+ "LED_GREEN_02_ON_18_OFF_SKIP",
-+ "LED_GREEN_05_ON_15_OFF_SKIP",
-+ "LED_GREEN_025_ON_075_OFF_SKIP",
-+ "LED_GREEN_025_ON_175_OFF_SKIP",
-+ "LED_GREEN_005_ON_195_OFF_SKIP",
-+ "LED_GREEN_05_ON_05_OFF_SKIP",
-+ "LED_GREEN_05_OFF_05_ON_SKIP",
-+ "LED_GREEN_0125_ON_05_OFF_0075_ON_15_OFF_SKIP",
-+ "LED_GREEN_0125_ON_2075_OFF_SKIP",
-+ "LED_GREEN_0625_OFF_0075_ON_15_OFF_SKIP",
-+
-+ "LED_BLUE_01_ON_19_OFF",
-+ "LED_BLUE_02_ON_18_OFF",
-+ "LED_BLUE_05_ON_15_OFF",
-+ "LED_BLUE_025_ON_075_OFF",
-+ "LED_BLUE_025_ON_175_OFF",
-+ "LED_BLUE_005_ON_195_OFF",
-+ "LED_BLUE_05_ON_05_OFF",
-+ "LED_BLUE_05_OFF_05_ON",
-+ "LED_BLUE_0125_ON_05_OFF_0075_ON_15_OFF",
-+ "LED_BLUE_0125_ON_2075_OFF",
-+ "LED_BLUE_0625_OFF_0075_ON_15_OFF",
-+
-+ "LED_BLUE_01_ON_19_OFF_SKIP",
-+ "LED_BLUE_02_ON_18_OFF_SKIP",
-+ "LED_BLUE_05_ON_15_OFF_SKIP",
-+ "LED_BLUE_025_ON_075_OFF_SKIP",
-+ "LED_BLUE_025_ON_175_OFF_SKIP",
-+ "LED_BLUE_005_ON_195_OFF_SKIP",
-+ "LED_BLUE_05_ON_05_OFF_SKIP",
-+ "LED_BLUE_05_OFF_05_ON_SKIP",
-+ "LED_BLUE_0125_ON_05_OFF_0075_ON_15_OFF_SKIP",
-+ "LED_BLUE_0125_ON_2075_OFF_SKIP",
-+ "LED_BLUE_0625_OFF_0075_ON_15_OFF_SKIP",
-+
-+ "LED_ORANGE_01_ON_19_OFF",
-+ "LED_ORANGE_02_ON_18_OFF",
-+ "LED_ORANGE_05_ON_15_OFF",
-+ "LED_ORANGE_025_ON_075_OFF",
-+ "LED_ORANGE_025_ON_175_OFF",
-+ "LED_ORANGE_005_ON_195_OFF",
-+ "LED_ORANGE_05_ON_05_OFF",
-+ "LED_ORANGE_05_OFF_05_ON",
-+ "LED_ORANGE_0125_ON_05_OFF_0075_ON_15_OFF",
-+ "LED_ORANGE_0125_ON_2075_OFF",
-+ "LED_ORANGE_0625_OFF_0075_ON_15_OFF",
-+
-+ "LED_ORANGE_01_ON_19_OFF_SKIP",
-+ "LED_ORANGE_02_ON_18_OFF_SKIP",
-+ "LED_ORANGE_05_ON_15_OFF_SKIP",
-+ "LED_ORANGE_025_ON_075_OFF_SKIP",
-+ "LED_ORANGE_025_ON_175_OFF_SKIP",
-+ "LED_ORANGE_005_ON_195_OFF_SKIP",
-+ "LED_ORANGE_05_ON_05_OFF_SKIP",
-+ "LED_ORANGE_05_OFF_05_ON_SKIP",
-+ "LED_ORANGE_0125_ON_05_OFF_0075_ON_15_OFF_SKIP",
-+ "LED_ORANGE_0125_ON_2075_OFF_SKIP",
-+ "LED_ORANGE_0625_OFF_0075_ON_15_OFF_SKIP",
-+
-+ "LED_RED_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF",
-+ "LED_GREEN_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF",
-+ "LED_ORANGE_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF",
-+
-+
-+ "LED_RED_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF_SKIP",
-+ "LED_GREEN_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF_SKIP",
-+ "LED_ORANGE_0125_ON_2075_OFF_BLUE_0625_OFF_0075_ON_15_OFF_SKIP",
-+ ""
-+}; /* LED Name*/
-+#endif
-+/* These are the control structures for the LEDs. */
-+static struct led_info info1;
-+static struct led_reg_info led1;
-+static int old_state ;
-+static unsigned int old_tempValue;
-+static struct pm_dev *led_pxa_pm_dev;
-+/*---------------------------------------------------------------------------
-+DESCRIPTION: Set LED state.
-+INPUTS: int state LED light mode.
-+OUTPUTS: int 0, succesee else return error no.
-+IMPORTANT NOTES:
-+To prevent RED to GREEN phase timing issues, the RED and Green LED bit codes should be written
-+simultaneously. Additionally, changing the timing of one or both drivers should be accomplished by first writing a
-+zero to each bit location, followed by a write to both locations with the desired bits.
-+
-+---------------------------------------------------------------------------*/
-+int PXA_E680_LED_set(int state)
-+{
-+ unsigned char ledr_en,ledg_en,ledr_ctrl,ledg_ctrl,ledr_i,ledg_i,skip;
-+ unsigned int tempValue, value =0;
-+
-+ if ( state >= LED_BOTTOM_STATE)
-+ {
-+ PRINTK("Driver:LED The State is invalid.\n");
-+ return 1;
-+ }
-+ else if ( old_state == state)
-+ {
-+ PRINTK("Driver:LED Same to previous State %s.\n",LED_Name[state]);
-+ return 0; /*Donn't need change the LED state.*/
-+ }
-+ /*First Disable LED.*/
-+ if(SSP_PCAP_read_data_from_PCAP(SSP_PCAP_ADJ_PERIPH_REGISTER,&tempValue)!=
-+ SSP_PCAP_SUCCESS)
-+ {
-+ PRINTK("Driver:LED PCAP Read Failed.\n");
-+ return 1;
-+ }
-+ tempValue &= (~SSP_PCAP_LED_MASK);
-+ if(SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_PERIPH_REGISTER,tempValue)!=SSP_PCAP_SUCCESS)
-+ {
-+ PRINTK("Driver:LED PCAP Write Failed (Clear Data).\n");
-+ return 1;
-+ }
-+
-+ /*Set GPIO as general I/O and as output*/
-+ set_GPIO_mode(IND_CNTL_R_BUL | GPIO_OUT);
-+ set_GPIO_mode(IND_CNTL_G_BUL | GPIO_OUT);
-+
-+ if (led_register_value[state].ind_GPIO_red && led_register_value[state].ind_GPIO_green)
-+ {
-+ /*Disable Red & Green signal*/
-+ set_GPIO(IND_CNTL_R_BUL); /*IND_CNTL_R_BUL Low active*/
-+ PGSR(IND_CNTL_R_BUL) = PGSR(IND_CNTL_R_BUL) | GPIO_bit(IND_CNTL_R_BUL);
-+
-+ clr_GPIO(IND_CNTL_G_BUL); /*IND_CNTL_G_BUL High active*/
-+ PGSR(IND_CNTL_G_BUL) = PGSR(IND_CNTL_G_BUL) & (~GPIO_bit(IND_CNTL_G_BUL));
-+
-+ PRINTK("GPIO Green Disable, Red Disable!\n");
-+ }else if ( (!led_register_value[state].ind_GPIO_red) &&
-+ led_register_value[state].ind_GPIO_green)
-+ {
-+ /*Green Disable, Red Enable*/
-+ clr_GPIO(IND_CNTL_R_BUL);
-+ PGSR(IND_CNTL_R_BUL) = PGSR(IND_CNTL_R_BUL) & (~GPIO_bit(IND_CNTL_R_BUL));
-+
-+ clr_GPIO(IND_CNTL_G_BUL);
-+ PGSR(IND_CNTL_G_BUL) = PGSR(IND_CNTL_G_BUL) & (~GPIO_bit(IND_CNTL_G_BUL));
-+
-+ PRINTK("GPIO Green Disable, Red Enable!\n");
-+ }else if ( led_register_value[state].ind_GPIO_red &&
-+ !led_register_value[state].ind_GPIO_green)
-+ {
-+ /*Red Disable, Green Enable*/
-+ set_GPIO(IND_CNTL_R_BUL);
-+ PGSR(IND_CNTL_R_BUL) = PGSR(IND_CNTL_R_BUL) | GPIO_bit(IND_CNTL_R_BUL);
-+
-+ set_GPIO(IND_CNTL_G_BUL);
-+ PGSR(IND_CNTL_G_BUL) = PGSR(IND_CNTL_G_BUL) | GPIO_bit(IND_CNTL_G_BUL);
-+ PRINTK("GPIO Red Disable, Green Enable");
-+ }else
-+ {
-+ /*Red & Green enable*/
-+ clr_GPIO(IND_CNTL_R_BUL);
-+ PGSR(IND_CNTL_R_BUL) = PGSR(IND_CNTL_R_BUL) & (~GPIO_bit(IND_CNTL_R_BUL));
-+
-+ set_GPIO(IND_CNTL_G_BUL);
-+ PGSR(IND_CNTL_G_BUL) = PGSR(IND_CNTL_G_BUL) | GPIO_bit(IND_CNTL_G_BUL);
-+ PRINTK("GPIO Red & Green enable!\n");
-+ }
-+ PRINTK("Driver:--IND_CNTL_G_BUL:%x IND_CNTL_R_BUL:%x\n",GPIO_is_high(IND_CNTL_G_BUL),
-+ GPIO_is_high(IND_CNTL_R_BUL));
-+ /* Write PCAP Peripheral Control Register*/
-+ ledr_en = led_register_value[state].pcap_LEDR_en & 0x1;
-+ ledg_en = led_register_value[state].pcap_LEDG_en & 0x1;
-+ ledr_ctrl = led_register_value[state].pcap_LEDR_CTRL & 0xf;
-+ ledg_ctrl = led_register_value[state].pcap_LEDG_CTRL & 0xf;
-+ ledr_i = led_register_value[state].pcap_LEDR_I & 0x3;
-+ ledg_i = led_register_value[state].pcap_LEDG_I & 0x3;
-+ skip = led_register_value[state].pcap_SKIP_on & 0x1;
-+
-+ value = ( ledr_en | (ledg_en <<1) | (ledr_ctrl <<2) | (ledg_ctrl <<6) |
-+ (ledr_i << 10) | (ledg_i <<12) | (skip <<14) ) & 0x7fff;
-+ tempValue |= (value <<SSP_PCAP_LED_SHIFT);
-+ if(SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_PERIPH_REGISTER,tempValue)==SSP_PCAP_SUCCESS)
-+ {
-+ PRINTK("Driver:LED write Value to PCAP:0x%x :0x%x\n",tempValue,value);
-+ PRINTK("Driver:LED State To: %s\n",LED_Name[state]);
-+ old_tempValue = tempValue;
-+ old_state = state;
-+ return 0;
-+ }else
-+ {
-+ PRINTK("Driver:LED: Changed to State %s Failed.\n",LED_Name[state]);
-+ return 1;
-+ }
-+}
-+
-+
-+/*---------------------------------------------------------------------------
-+DESCRIPTION: reptore PGSR.
-+INPUTS: old_state.
-+OUTPUTS: int 0, succesee else return error no.
-+IMPORTANT NOTES:
-+
-+---------------------------------------------------------------------------*/
-+int PXA_E680_LED_retore_PGSR(struct pm_dev *dev, pm_request_t rqst, void *data)
-+{
-+ unsigned int tempValue;
-+
-+
-+ switch (rqst)
-+ {
-+ case PM_RESUME:
-+ {
-+ /*First Disable LED.*/
-+ if(SSP_PCAP_read_data_from_PCAP(SSP_PCAP_ADJ_PERIPH_REGISTER,&tempValue)!=
-+ SSP_PCAP_SUCCESS)
-+ {
-+ PRINTK("Driver:LED PCAP Read Failed.\n");
-+ return 1;
-+ }
-+ tempValue &= (~SSP_PCAP_LED_MASK);
-+ if(SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_PERIPH_REGISTER,tempValue)!=SSP_PCAP_SUCCESS)
-+ {
-+ PRINTK("Driver:LED PCAP Write Failed (Clear Data).\n");
-+ return 1;
-+ }
-+
-+ if (led_register_value[old_state].ind_GPIO_red && led_register_value[old_state].ind_GPIO_green)
-+ {
-+ /*Disable Red & Green signal*/
-+ set_GPIO(IND_CNTL_R_BUL); /*IND_CNTL_R_BUL Low active*/
-+ PGSR(IND_CNTL_R_BUL) = PGSR(IND_CNTL_R_BUL) | GPIO_bit(IND_CNTL_R_BUL);
-+
-+ clr_GPIO(IND_CNTL_G_BUL); /*IND_CNTL_G_BUL High active*/
-+ PGSR(IND_CNTL_G_BUL) = PGSR(IND_CNTL_G_BUL) & (~GPIO_bit(IND_CNTL_G_BUL));
-+
-+ PRINTK("RESTORE____GPIO Green Disable, Red Disable!\n");
-+ }else if ( (!led_register_value[old_state].ind_GPIO_red) &&
-+ led_register_value[old_state].ind_GPIO_green)
-+ {
-+ /*Green Disable, Red Enable*/
-+ clr_GPIO(IND_CNTL_R_BUL);
-+ PGSR(IND_CNTL_R_BUL) = PGSR(IND_CNTL_R_BUL) & (~GPIO_bit(IND_CNTL_R_BUL));
-+
-+ clr_GPIO(IND_CNTL_G_BUL);
-+ PGSR(IND_CNTL_G_BUL) = PGSR(IND_CNTL_G_BUL) & (~GPIO_bit(IND_CNTL_G_BUL));
-+
-+ PRINTK("RESTORE____GPIO Green Disable, Red Enable!\n");
-+ }else if ( led_register_value[old_state].ind_GPIO_red &&
-+ !led_register_value[old_state].ind_GPIO_green)
-+ {
-+ /*Red Disable, Green Enable*/
-+ set_GPIO(IND_CNTL_R_BUL);
-+ PGSR(IND_CNTL_R_BUL) = PGSR(IND_CNTL_R_BUL) | GPIO_bit(IND_CNTL_R_BUL);
-+
-+ set_GPIO(IND_CNTL_G_BUL);
-+ PGSR(IND_CNTL_G_BUL) = PGSR(IND_CNTL_G_BUL) | GPIO_bit(IND_CNTL_G_BUL);
-+ PRINTK("RESTORE____GPIO Red Disable, Green Enable");
-+ }else
-+ {
-+ /*Red & Green enable*/
-+ clr_GPIO(IND_CNTL_R_BUL);
-+ PGSR(IND_CNTL_R_BUL) = PGSR(IND_CNTL_R_BUL) & (~GPIO_bit(IND_CNTL_R_BUL));
-+
-+ set_GPIO(IND_CNTL_G_BUL);
-+ PGSR(IND_CNTL_G_BUL) = PGSR(IND_CNTL_G_BUL) | GPIO_bit(IND_CNTL_G_BUL);
-+ PRINTK("RESTORE____GPIO Red & Green enable!\n");
-+ }
-+ PRINTK("Driver:--IND_CNTL_G_BUL:%x IND_CNTL_R_BUL:%x\n",GPIO_is_high(IND_CNTL_G_BUL),
-+ GPIO_is_high(IND_CNTL_R_BUL));
-+
-+ if(SSP_PCAP_write_data_to_PCAP(SSP_PCAP_ADJ_PERIPH_REGISTER,old_tempValue)==SSP_PCAP_SUCCESS)
-+ {
-+ PRINTK("Driver:LED write Value to PCAP:0x%x\n",old_tempValue);
-+ PRINTK("Driver:LED State To: %s\n",LED_Name[old_state]);
-+ return 0;
-+ }else
-+ {
-+ PRINTK("Driver:LED: Changed to State %s Failed.\n",LED_Name[old_state]);
-+ return 1;
-+ }
-+
-+ break;
-+ }//end of case RESUME
-+ }//end of switch
-+ return 0;
-+}//end of function
-+
-+
-+/* Handle an actual LED set*/
-+int handle_led_op(struct led_reg_info *info,
-+ struct led_op *op)
-+{
-+ switch (op->op)
-+ {
-+ case SET_LED:
-+ if ( PXA_E680_LED_set(op->op_info.bicolor.color) == 0)
-+ return 0;
-+ else
-+ return -EINVAL;
-+ default:
-+ PRINTK("LED:Error CMD.\n");
-+ return -EINVAL;
-+ }
-+}
-+
-+/**
-+ * PXA_E680_LED_exit:
-+ *
-+ * Remove the LEDs from the LED driver
-+ */
-+
-+static void __exit PXA_E680_LED_exit(void)
-+{
-+ pm_unregister(led_pxa_pm_dev);
-+ unregister_led_info(&led1);
-+}
-+
-+/**
-+ * PXA_E680_LED_init
-+ *
-+ * Register the LEDs with the LED driver.
-+ */
-+
-+static int __init PXA_E680_LED_init(void)
-+{
-+ info1.type = LED_TYPE_BICOLOR;
-+ strcpy(info1.name, LED_E680_NAME);
-+ led1.info = &info1;
-+ led1.data = (void *) 0;
-+ led1.handle_led_op = handle_led_op;
-+ register_led_info(&led1);
-+
-+ old_state = LED_OFF;
-+ old_tempValue = 0;
-+ led_pxa_pm_dev = pm_register(PM_UNKNOWN_DEV, PM_SYS_UNKNOWN, PXA_E680_LED_retore_PGSR);
-+
-+ /*Set GPIO as general IO and as Output*/
-+ set_GPIO_mode(IND_CNTL_R_BUL | GPIO_OUT);
-+ set_GPIO_mode(IND_CNTL_G_BUL | GPIO_OUT);
-+
-+ set_GPIO(IND_CNTL_R_BUL);
-+ PGSR(IND_CNTL_R_BUL) = PGSR(IND_CNTL_R_BUL) | GPIO_bit(IND_CNTL_R_BUL);
-+
-+ clr_GPIO(IND_CNTL_G_BUL);
-+ PGSR(IND_CNTL_G_BUL) = PGSR(IND_CNTL_G_BUL) & (~GPIO_bit(IND_CNTL_G_BUL));
-+ PRINTK("PCAP2 LED driver: v%s E680\n", VERSION);
-+ return 0;
-+}
-+
-+module_init(PXA_E680_LED_init);
-+module_exit(PXA_E680_LED_exit);
-+MODULE_LICENSE("GPL");
-Index: linux-2.6.16.5-a/drivers/char/mstone_keypad.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/char/mstone_keypad.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,581 @@
-+/*
-+ * linux/driver/char/mstone_keypad.c
-+ * Keypad driver for Intel Mainstone development board
-+ *
-+ * Copyright (C) 2003, Intel Corporation (yu.tang@intel.com)
-+ * Copyright 2003 MontaVista Software Inc.
-+ * Author: MontaVista Software, Inc.
-+ * source@mvista.com
-+ *
-+ * This program is free software; you can redistribute it and/or modify it
-+ * under the terms of the GNU General Public License as published by the
-+ * Free Software Foundation; either version 2 of the License, or (at your
-+ * option) any later version.
-+ *
-+ * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED
-+ * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
-+ * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN
-+ * NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
-+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
-+ * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
-+ * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
-+ * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
-+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-+ *
-+ * You should have received a copy of the GNU General Public License along
-+ * with this program; if not, write to the Free Software Foundation, Inc.,
-+ * 675 Mass Ave, Cambridge, MA 02139, USA.
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/init.h>
-+#include <linux/kernel.h>
-+#include <linux/sched.h>
-+#include <linux/errno.h>
-+#include <linux/delay.h>
-+#include <linux/poll.h>
-+#include <linux/spinlock.h>
-+#include <linux/sem.h>
-+#include <linux/miscdevice.h>
-+#include <asm/system.h>
-+#include <asm/irq.h>
-+#include <asm/hardware.h>
-+#include <asm/hardirq.h>
-+#include <asm/uaccess.h>
-+#include <asm/ioctl.h>
-+
-+#include <asm/arch/keypad.h>
-+
-+/* Direct-KEY scan-code for Mainstone-I Board */
-+#define ROTARY_DEFAULT 0x7F
-+#define NO_KEY 0xFF
-+#define SCAN_CODE_SCROLL_UP 0xA
-+#define SCAN_CODE_SCROLL_DOWN 0xB
-+#define SCAN_CODE_ACTION 0xC
-+
-+DECLARE_MUTEX(kpdrv_mutex);
-+static struct kpe_queue kpe_queue;
-+static int kpdrv_refcount = 0;
-+
-+//#define DEBUG 1
-+#if DEBUG
-+static unsigned int mstone_keypad_dbg = 1;
-+#else
-+#define mstone_keypad_dbg 0
-+#endif
-+
-+#ifdef CONFIG_DPM
-+#include <linux/device.h>
-+
-+static int pxakpd_suspend(struct device *dev, u32 state, u32 level);
-+static int pxakpd_resume(struct device *dev, u32 level);
-+static int pxakpd_scale(struct bus_op_point *op, u32 level);
-+
-+static struct device_driver pxakpd_driver_ldm = {
-+ name: "pxa-kpd",
-+ devclass: NULL,
-+ probe: NULL,
-+ suspend: pxakpd_suspend,
-+ resume: pxakpd_resume,
-+ scale: pxakpd_scale,
-+ remove: NULL,
-+ constraints: NULL,
-+};
-+
-+static struct device pxakpd_device_ldm = {
-+ name: "PXA Keypad",
-+ bus_id: "pxakpd",
-+ driver: NULL,
-+ power_state: DPM_POWER_ON,
-+};
-+
-+static void
-+pxakpd_ldm_register(void)
-+{
-+ extern void pxaopb_driver_register(struct device_driver *driver);
-+ extern void pxaopb_device_register(struct device *device);
-+
-+ pxaopb_driver_register(&pxakpd_driver_ldm);
-+ pxaopb_device_register(&pxakpd_device_ldm);
-+}
-+
-+static void
-+pxakpd_ldm_unregister(void)
-+{
-+ extern void pxaopb_driver_unregister(struct device_driver *driver);
-+ extern void pxaopb_device_unregister(struct device *device);
-+
-+ pxaopb_device_unregister(&pxakpd_device_ldm);
-+ pxaopb_driver_unregister(&pxakpd_driver_ldm);
-+}
-+
-+static int
-+pxakpd_resume(struct device *dev, u32 level)
-+{
-+ if (mstone_keypad_dbg)
-+ printk("+++: in pxakpd_resume()\n");
-+
-+ switch (level) {
-+ case RESUME_POWER_ON:
-+ /* enable direct and matrix interrupts */
-+ KPC |= (KPC_DIE | KPC_MIE);
-+
-+ /* enable clock to keypad */
-+ CKEN |= CKEN19_KEYPAD;
-+ {
-+ struct kp_event kpe;
-+ unsigned char c;
-+
-+ kpe.flags |= (KP_DIRECT | KP_MATRIX );
-+ c = get_scancode(&kpe);
-+ if (c != NO_KEY) {
-+ /* Insert it into key event list. */
-+ kpq_put(&kpe);
-+ }
-+ else {
-+ /* We are not woke by key press. */
-+ }
-+ }
-+ break;
-+ }
-+
-+ return 0;
-+}
-+
-+static int
-+pxakpd_suspend(struct device *dev, u32 state, u32 level)
-+{
-+ if (mstone_keypad_dbg)
-+ printk("+++: in pxakpd_suspend()\n");
-+
-+ switch (level) {
-+ case SUSPEND_POWER_DOWN:
-+ /* disable clock to keypad */
-+ CKEN &= ~CKEN19_KEYPAD;
-+
-+ /* disable direct and matrix interrupts */
-+ KPC &= ~(KPC_DIE | KPC_MIE);
-+ break;
-+ }
-+
-+ return 0;
-+}
-+
-+static int
-+pxakpd_scale(struct bus_op_point *op, u32 level)
-+{
-+ printk("+++: in pxakpd_scale()\n");
-+
-+ return 0;
-+}
-+#endif /* CONFIG_DPM */
-+
-+/* Init kpe queue */
-+static void kpq_init(void)
-+{
-+ kpe_queue.head = kpe_queue.tail = kpe_queue.len = 0;
-+ kpe_queue.spinlock = SPIN_LOCK_UNLOCKED;
-+ init_waitqueue_head(&kpe_queue.waitq);
-+}
-+
-+static int kpq_empty(void)
-+{
-+ int flags, empty;
-+
-+ spin_lock_irqsave(&kpe_queue.spinlock,flags);
-+ empty = kpe_queue.len ? 0 : 1;
-+ spin_unlock_irqrestore(&kpe_queue.spinlock, flags);
-+
-+ return empty;
-+}
-+
-+static int kpq_get(struct kp_event *kpe)
-+{
-+ int flags, err = 0;
-+
-+ spin_lock_irqsave(&kpe_queue.spinlock, flags);
-+ if (kpe_queue.head == kpe_queue.tail) {
-+ printk(KERN_ERR "keypad: empty event queue, looks bad\n");
-+ err = -EAGAIN;
-+ goto out;
-+ }
-+ memcpy(kpe, kpe_queue.kpes + kpe_queue.tail, sizeof(struct kp_event));
-+ kpe_queue.len--;
-+ kpe_queue.tail = (kpe_queue.tail + 1) % MAX_KPES;
-+ out:
-+ spin_unlock_irqrestore(&kpe_queue.spinlock, flags);
-+ return err;
-+}
-+
-+static void kpq_put(struct kp_event *kpe)
-+{
-+ int flags;
-+
-+ spin_lock_irqsave(&kpe_queue.spinlock, flags);
-+ memcpy(kpe_queue.kpes + kpe_queue.head, kpe, sizeof(struct kp_event));
-+ kpe_queue.len++;
-+ if (kpe_queue.len == MAX_KPES) {
-+ printk(KERN_ERR "keypad: events are comes too fast, will discard next\n");
-+ kpe_queue.len--;
-+ goto out;
-+ }
-+ kpe_queue.head = (kpe_queue.head + 1) % MAX_KPES;
-+ out:
-+ spin_unlock_irqrestore(&kpe_queue.spinlock, flags);
-+ /* Wake up the waiting processes */
-+ wake_up_interruptible(&kpe_queue.waitq);
-+}
-+
-+static int kp_direct_scan(struct kp_event *kpe)
-+{
-+ kpe->flags |= KP_DIRECT;
-+ kpe->direct = KPDK;
-+ kpe->rotary = KPREC;
-+ return 0;
-+}
-+
-+static int kp_matrix_scan(struct kp_event *kpe)
-+{
-+ KPC |= KPC_AS;
-+ while (KPAS &KPAS_SO);
-+
-+ kpe->flags |= KP_MATRIX;
-+ kpe->matrix[0] = KPAS;
-+ kpe->matrix[1] = KPASMKP0;
-+ kpe->matrix[2] = KPASMKP1;
-+ kpe->matrix[3] = KPASMKP2;
-+ kpe->matrix[4] = KPASMKP3;
-+
-+ KPC &= ~KPC_AS;
-+
-+ return 0;
-+}
-+
-+/* Interrupt kandler for keypad */
-+static void kp_interrupt(int irq, void *ptr, struct pt_regs *regs)
-+{
-+ struct kp_event kpe = {0};
-+ int flags;
-+ unsigned long kpc_val;
-+
-+ printk("+++: kp_interrupt()\n");
-+
-+ spin_lock_irqsave(&kpe_queue.spinlock,flags);
-+
-+ /* ACK interrupt */
-+ kpc_val = KPC;
-+ kpe.jiffies = jiffies;
-+
-+ /* Direct interrupt */
-+ if (kpc_val & KPC_DI)
-+ kp_direct_scan(&kpe);
-+
-+ /* Matrix interrupt */
-+ if (kpc_val & KPC_MI)
-+ kp_matrix_scan(&kpe);
-+
-+ spin_unlock_irqrestore(&kpe_queue.spinlock, flags);
-+
-+ if (((kpe.flags & KP_DIRECT) || (kpe.flags & KP_MATRIX)) && kpdrv_refcount)
-+ kpq_put(&kpe);
-+}
-+
-+/* Wait for keypad event, must be in task-context */
-+int kp_wait(struct kp_event *kpe, signed int timeout)
-+{
-+ int n, err = 0;
-+
-+ while(1) {
-+ if (!kpq_empty()) {
-+ n = kpq_get(kpe);
-+ if (n < 0)
-+ continue;
-+ break;
-+ }
-+
-+ /* No event available ? */
-+ if (!timeout) {
-+ err = -EAGAIN;
-+ break;
-+ }
-+
-+ if (timeout > 0) {
-+ /* Wait for timeout */
-+ timeout = interruptible_sleep_on_timeout(&kpe_queue.waitq, timeout);
-+ continue;
-+ }
-+ else{
-+ /* Wait for kpevent/signal */
-+ while(1) {
-+ interruptible_sleep_on(&kpe_queue.waitq);
-+ if (kpq_empty() && !signal_pending(current))
-+ continue;
-+ break;
-+ }
-+
-+ if (signal_pending(current)) {
-+ err = -EINTR;
-+ break;
-+ }
-+ }
-+ }
-+ return err;
-+}
-+
-+/* Poll for keypad event */
-+unsigned int kp_poll(struct file *file, poll_table *wait)
-+{
-+ poll_wait(file, &kpe_queue.waitq, wait);
-+ return kpq_empty() ? 0 : POLLIN | POLLRDNORM;
-+}
-+
-+static unsigned char get_scancode(struct kp_event *kpe)
-+{
-+ static unsigned int curr, prev = ROTARY_DEFAULT;
-+ unsigned int c;
-+
-+ c = NO_KEY;
-+
-+ if (kpe->flags & KP_DIRECT) {
-+
-+ curr = kpe->rotary & 0xFF;
-+
-+ if (kpe->rotary & KPREC_OF0) {
-+ KPREC &= ~KPREC_OF0;
-+ KPREC |= ROTARY_DEFAULT;
-+ prev = ROTARY_DEFAULT;
-+ c = SCAN_CODE_SCROLL_UP;
-+ }
-+ else if (kpe->rotary & KPREC_UF0) {
-+ KPREC &= ~KPREC_UF0;
-+ KPREC |= ROTARY_DEFAULT;
-+ prev = ROTARY_DEFAULT;
-+ c = SCAN_CODE_SCROLL_DOWN;
-+ }
-+ else if (curr > prev) {
-+ c = SCAN_CODE_SCROLL_UP;
-+ prev = curr;
-+ }
-+ else if (curr < prev) {
-+ c = SCAN_CODE_SCROLL_DOWN;
-+ prev = curr;
-+ }
-+ else if (kpe->direct & KPDK_DK2) {
-+ c = SCAN_CODE_ACTION;
-+ prev = curr;
-+ }
-+ }
-+
-+ if (kpe->flags & KP_MATRIX) {
-+ unsigned int count = (kpe->matrix[0] >> 26) & 0x1f;
-+
-+ c = kpe->matrix[0] & 0xff;
-+
-+ /* Key up */
-+ if (!count) c |= 0x80;
-+ }
-+
-+ return c;
-+}
-+
-+static ssize_t kpdrv_read(struct file * filp, char * buf,
-+ size_t count, loff_t *ppos)
-+{
-+ struct kp_event kpe;
-+ int err,left,timeout;
-+ unsigned char c;
-+
-+ timeout = 0;
-+ left = count;
-+ do {
-+ err = kp_wait(&kpe, timeout);
-+ if (err) {
-+ if ( left != count ) return (count-left);
-+
-+ if (filp->f_flags & O_NONBLOCK) return err;
-+
-+ if (timeout) return err;
-+
-+ timeout = -1;
-+ continue;
-+ }
-+ /* Parse if direct/matrix flags are set*/
-+ if ( (kpe.flags & KP_DIRECT) || (kpe.flags & KP_MATRIX) ) {
-+ c = get_scancode(&kpe);
-+ if (c != NO_KEY) {
-+ put_user(c, buf++);
-+ left --;
-+ }
-+ }
-+ } while (left);
-+ return (count-left);
-+}
-+
-+static int kpdrv_ioctl(struct inode *ip, struct file *fp,
-+ unsigned int cmd, unsigned long arg)
-+{
-+ int interval = KPKDI & 0xffff;
-+ int ign = (KPC & KPC_IMKP);
-+
-+ switch(cmd) {
-+ case KPIOGET_INTERVAL:
-+ if (copy_to_user((void*)arg, &interval, sizeof(int)))
-+ return -EFAULT;
-+ break;
-+ case KPIOGET_IGNMULTI:
-+ if (copy_to_user((void*)arg, &ign, sizeof(int)))
-+ return -EFAULT;
-+ break;
-+ case KPIOSET_INTERVAL:
-+ if (copy_from_user(&interval, (void*)arg, sizeof(int)))
-+ return -EFAULT;
-+
-+ /* FIXME : sighting #34833, Matrix Key interval should be >10ms */
-+ if ( (interval & 0xff) < 10) return -EINVAL;
-+
-+ KPKDI &= ~0xffff;
-+ KPKDI |= (interval & 0xffff);
-+ break;
-+ case KPIOSET_IGNMULTI:
-+ if (copy_from_user(&ign, (void*)arg, sizeof(int)))
-+ return -EFAULT;
-+
-+ if (ign)
-+ KPC |= KPC_IMKP;
-+ else
-+ KPC &= ~KPC_IMKP;
-+
-+ break;
-+
-+ default:
-+ /* Unknown command */
-+ return -EINVAL;
-+ }
-+ return 0;
-+}
-+
-+static unsigned int kpdrv_poll(struct file *filp, poll_table * wait) {
-+ return kp_poll(filp, wait);
-+}
-+
-+static int kpdrv_open(struct inode *inode, struct file *filp)
-+{
-+ down(&kpdrv_mutex);
-+ if (!kpdrv_refcount)
-+ kpq_init();
-+ kpdrv_refcount++;
-+ up(&kpdrv_mutex);
-+ return 0;
-+}
-+
-+static int kpdrv_close(struct inode *inode, struct file *filp)
-+{
-+ down(&kpdrv_mutex);
-+ kpdrv_refcount--;
-+ up(&kpdrv_mutex);
-+
-+ return 0;
-+}
-+
-+static struct file_operations kpdrv_fops = {
-+ owner: THIS_MODULE,
-+ open: kpdrv_open,
-+ release: kpdrv_close,
-+ read: kpdrv_read,
-+ ioctl: kpdrv_ioctl,
-+ poll: kpdrv_poll,
-+};
-+
-+
-+static struct miscdevice keypad_miscdevice = {
-+ minor: MISC_DYNAMIC_MINOR,
-+ name: "keypad",
-+ fops: &kpdrv_fops
-+};
-+
-+static int __init kpdrv_init(void)
-+{
-+ int err;
-+
-+ /* Setup gpio */
-+ set_GPIO_mode(93 | GPIO_ALT_FN_1_IN);
-+ set_GPIO_mode(94 | GPIO_ALT_FN_1_IN);
-+ set_GPIO_mode(95 | GPIO_ALT_FN_1_IN);
-+ set_GPIO_mode(96 | GPIO_ALT_FN_1_IN);
-+ set_GPIO_mode(97 | GPIO_ALT_FN_1_IN);
-+ set_GPIO_mode(98 | GPIO_ALT_FN_1_IN);
-+ set_GPIO_mode(99 | GPIO_ALT_FN_1_IN);
-+
-+ set_GPIO_mode(100 | GPIO_ALT_FN_1_IN);
-+ set_GPIO_mode(101 | GPIO_ALT_FN_1_IN);
-+ set_GPIO_mode(102 | GPIO_ALT_FN_1_IN);
-+
-+ set_GPIO_mode(103 | GPIO_ALT_FN_2_OUT);
-+ set_GPIO_mode(104 | GPIO_ALT_FN_2_OUT);
-+ set_GPIO_mode(105 | GPIO_ALT_FN_2_OUT);
-+ set_GPIO_mode(106 | GPIO_ALT_FN_2_OUT);
-+ set_GPIO_mode(107 | GPIO_ALT_FN_2_OUT);
-+ set_GPIO_mode(108 | GPIO_ALT_FN_2_OUT);
-+
-+ /* Set keypad control register */
-+ KPC = (KPC_ASACT | (3<<26) | (4<<23)|
-+ KPC_ME | (2<<6) | KPC_DEE0 | KPC_DE |
-+ KPC_MS_ALL | KPC_MIE | KPC_DIE | KPC_IMKP);
-+
-+ /* Set debouce time seperately for Matrix/Direct. */
-+ KPKDI= 0x010A;
-+
-+ /* Set scroll wheel value to mid-point value */
-+ KPREC= 0x7F;
-+
-+ /* Enable unit clock */
-+ CKEN |= CKEN19_KEYPAD;
-+
-+ /* Request keypad IRQ */
-+ err = request_irq(IRQ_KEYPAD, kp_interrupt, 0, "keypad", NULL);
-+ if (err) {
-+ printk (KERN_CRIT "can't register IRQ%d for keypad, error %d\n",
-+ IRQ_KEYPAD, err);
-+ /* Disable clock unit */
-+ CKEN &= ~CKEN19_KEYPAD;
-+ return -ENODEV;
-+ }
-+
-+ /* Register driver as miscdev */
-+ err = misc_register(&keypad_miscdevice);
-+ if (err)
-+ printk(KERN_ERR "can't register keypad misc device, error %d\n", err);
-+ else
-+ printk(KERN_INFO "Intel Mainstone Keypad driver registered with minor %d\n",
-+ keypad_miscdevice.minor);
-+
-+#ifdef CONFIG_DPM
-+ pxakpd_ldm_register();
-+#endif /* CONFIG_DPM */
-+
-+ return err;
-+}
-+
-+static void __exit kpdrv_exit(void)
-+{
-+#ifdef CONFIG_DPM
-+ pxakpd_ldm_unregister();
-+#endif /* CONFIG_DPM */
-+
-+ /* Disable clock unit */
-+ CKEN &= ~CKEN19_KEYPAD;
-+
-+ /* Free keypad IRQ */
-+ free_irq(IRQ_KEYPAD, NULL);
-+
-+ /* Unregister keypad device */
-+ misc_deregister(&keypad_miscdevice);
-+}
-+
-+module_init(kpdrv_init);
-+module_exit(kpdrv_exit);
-+
-+MODULE_AUTHOR("Yu Tang <yu.tang@intel.com>, source@mvista.com");
-+MODULE_DESCRIPTION("Intel Mainstone KEYPAD driver");
-+MODULE_LICENSE("GPL");
-Index: linux-2.6.16.5-a/drivers/char/n_tty.c
-===================================================================
---- linux-2.6.16.5-a.orig/drivers/char/n_tty.c 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/drivers/char/n_tty.c 2006-05-04 17:07:04.000000000 +0200
-@@ -60,6 +60,12 @@
- #define TTY_THRESHOLD_THROTTLE 128 /* now based on remaining room */
- #define TTY_THRESHOLD_UNTHROTTLE 128
-
-+#if defined(CONFIG_ARCH_EZX) && 0
-+extern int btuart_flip_flow_ctl;
-+extern void rs_flip_unthrottle(struct tty_struct *tty);
-+#endif
-+
-+
- static inline unsigned char *alloc_buf(void)
- {
- gfp_t prio = in_interrupt() ? GFP_ATOMIC : GFP_KERNEL;
-@@ -957,6 +963,11 @@
-
- n_tty_set_room(tty);
-
-+#if defined (CONFIG_ARCH_EZX) && 0
-+ if (tty && tth->driver.btuart)
-+ rs_flip_unthrottle(tty);
-+#endif
-+
- if (!tty->icanon && (tty->read_cnt >= tty->minimum_to_wake)) {
- kill_fasync(&tty->fasync, SIGIO, POLL_IN);
- if (waitqueue_active(&tty->read_wait))
-Index: linux-2.6.16.5-a/drivers/char/sram.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/char/sram.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,194 @@
-+/*
-+ * linux/drivers/char/sram.c
-+ *
-+ * Bulverde Internal Memory character device driver
-+ *
-+ * Created: Sep 05, 2003
-+ * Copyright: MontaVista Software Inc.
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License as published by
-+ * the Free Software Foundation; either version 2 of the License, or
-+ * (at your option) any later version.
-+ *
-+ * This program is distributed in the hope that it will be useful,
-+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
-+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-+ * GNU General Public License for more details.
-+ *
-+ * You should have received a copy of the GNU General Public License
-+ * along with this program; if not, write to the Free Software
-+ * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
-+ *
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/init.h>
-+#include <linux/kernel.h>
-+#include <linux/sched.h>
-+#include <linux/config.h>
-+#include <linux/mm.h>
-+#include <linux/major.h>
-+#include <linux/miscdevice.h>
-+#include <linux/vmalloc.h>
-+#include <linux/mman.h>
-+#include <linux/init.h>
-+#include <linux/rwsem.h>
-+
-+#include <asm/uaccess.h>
-+#include <asm/io.h>
-+#include <asm/pgalloc.h>
-+
-+#include <linux/devfs_fs_kernel.h>
-+
-+static unsigned long sram_base = 0;
-+static unsigned long sram_size = 0;
-+
-+extern int sram_access_obtain(unsigned long *pmem, unsigned long *psize);
-+extern int sram_access_release(unsigned long *pmem, unsigned long *psize);
-+
-+/*
-+ * This funcion reads the SRAM memory.
-+ * The f_pos points to the SRAM memory location.
-+ */
-+static ssize_t sram_read(struct file * file, char * buf,
-+ size_t count, loff_t *ppos) {
-+ unsigned long p = *ppos;
-+ ssize_t read;
-+
-+ if (p >= sram_size)
-+ return 0;
-+
-+ if (count > sram_size - p)
-+ count = sram_size - p;
-+
-+ read = 0;
-+
-+ if (copy_to_user(buf, (char *)(sram_base + p), count))
-+ return -EFAULT;
-+
-+ read += count;
-+ *ppos += read;
-+
-+ return read;
-+}
-+
-+static ssize_t sram_write(struct file * file, const char * buf,
-+ size_t count, loff_t *ppos) {
-+ unsigned long p = *ppos;
-+ ssize_t written;
-+
-+ if (p >= sram_size)
-+ return 0;
-+
-+ if (count > sram_size - p)
-+ count = sram_size - p;
-+
-+ written = 0;
-+
-+ if (copy_from_user((char *)(sram_base + p), buf, count))
-+ return -EFAULT;
-+
-+ written += count;
-+ *ppos += written;
-+
-+ return written;
-+}
-+
-+static int sram_mmap(struct file * file, struct vm_area_struct * vma) {
-+
-+ unsigned long offset = vma->vm_pgoff << PAGE_SHIFT;
-+
-+ if (((file->f_flags & O_WRONLY) != 0) ||
-+ ((file->f_flags & O_RDWR) != 0)) {
-+ vma->vm_page_prot = (pgprot_t)PAGE_SHARED;
-+ } else {
-+ vma->vm_page_prot = (pgprot_t)PAGE_READONLY;
-+ }
-+
-+ /* Do not cache SRAM memory if O_SYNC flag is set */
-+ if ((file->f_flags & O_SYNC) != 0) {
-+ pgprot_val(vma->vm_page_prot) &= ~L_PTE_CACHEABLE;
-+ }
-+
-+ /* Don't try to swap out physical pages.. */
-+ vma->vm_flags |= VM_RESERVED | VM_LOCKED;
-+
-+ if (remap_page_range(vma->vm_start, SRAM_MEM_PHYS + offset,
-+ vma->vm_end - vma->vm_start, vma->vm_page_prot)) {
-+ return -EAGAIN;
-+ }
-+
-+ return 0;
-+}
-+
-+
-+static loff_t sram_lseek(struct file * file, loff_t offset, int orig) {
-+
-+ switch (orig) {
-+ case 0:
-+ file->f_pos = offset;
-+ break;
-+ case 1:
-+ file->f_pos += offset;
-+ break;
-+ case 2:
-+ file->f_pos = SRAM_SIZE + offset;
-+ break;
-+ default:
-+ return -EINVAL;
-+ }
-+
-+ if (file->f_pos < 0) {
-+ file->f_pos = 0;
-+ } else if (file->f_pos > SRAM_SIZE) {
-+ file->f_pos = SRAM_SIZE;
-+ }
-+
-+ return file->f_pos;
-+}
-+
-+static int sram_open(struct inode * inode, struct file * filp) {
-+ return sram_access_obtain(&sram_base, &sram_size);
-+}
-+
-+static int sram_release(struct inode * inode, struct file * filp) {
-+ return sram_access_release(&sram_base, &sram_size);
-+}
-+
-+
-+static struct file_operations sram_fops = {
-+ llseek: sram_lseek,
-+ read: sram_read,
-+ write: sram_write,
-+ mmap: sram_mmap,
-+ open: sram_open,
-+ release: sram_release,
-+};
-+
-+static struct miscdevice sram_misc = {
-+ minor : MISC_DYNAMIC_MINOR,
-+ name : "misc/sram",
-+ fops : &sram_fops,
-+};
-+
-+static int __init sram_chr_init(void) {
-+ if (misc_register(&sram_misc) != 0)
-+ {
-+ printk(KERN_ERR "Cannot register device /dev/%s\n",
-+ sram_misc.name);
-+ return -EFAULT;
-+ }
-+
-+ return 0;
-+}
-+
-+static void __exit sram_chr_exit(void) {
-+ misc_deregister(&sram_misc);
-+}
-+
-+module_init(sram_chr_init)
-+module_exit(sram_chr_exit)
-+
-+MODULE_LICENSE("GPL");
-+MODULE_AUTHOR("MontaVista Software Inc.");
-Index: linux-2.6.16.5-a/drivers/char/tty_io.c
-===================================================================
---- linux-2.6.16.5-a.orig/drivers/char/tty_io.c 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/drivers/char/tty_io.c 2006-05-04 17:07:04.000000000 +0200
-@@ -2772,6 +2772,14 @@
- goto out;
- }
- spin_lock_irqsave(&tty->buf.lock, flags);
-+#if defined(CONFIG_EZX_A780) || defined(CONFIG_ARCH_EZX_E680)
-+ if (tty && tty->driver.btuart &&
-+ ((N_TTY_BUF_SIZE - tty->read_cnt - 2) < (512 + 128))) {
-+ schedule_delayed_work(&tty->flip.work, 1);
-+ return;
-+ }
-+#endif
-+
- while((tbuf = tty->buf.head) != NULL) {
- while ((count = tbuf->commit - tbuf->read) != 0) {
- char_buf = tbuf->char_buf_ptr + tbuf->read;
-Index: linux-2.6.16.5-a/drivers/misc/Kconfig
-===================================================================
---- linux-2.6.16.5-a.orig/drivers/misc/Kconfig 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/drivers/misc/Kconfig 2006-05-04 17:07:04.000000000 +0200
-@@ -30,3 +30,4 @@
-
- endmenu
-
-+source "drivers/misc/ezx/Kconfig"
-Index: linux-2.6.16.5-a/drivers/misc/Makefile
-===================================================================
---- linux-2.6.16.5-a.orig/drivers/misc/Makefile 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/drivers/misc/Makefile 2006-05-04 17:07:04.000000000 +0200
-@@ -5,3 +5,4 @@
-
- obj-$(CONFIG_IBM_ASM) += ibmasm/
- obj-$(CONFIG_HDPU_FEATURES) += hdpuftrs/
-+obj-$(CONFIG_PXA_EZX) += ezx/
-Index: linux-2.6.16.5-a/drivers/misc/ezx/Kconfig
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/Kconfig 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,20 @@
-+#
-+# Misc strange devices
-+#
-+
-+menu "Motorola EZX devices"
-+
-+config KEYPAD_A780
-+ tristate "Device driver for Motorola A780 keypad"
-+
-+config KEYPAD_E680
-+ tristate "Device driver for Motorola E680 keypad"
-+
-+config KEYLIGHT_A780
-+ tristate "Device driver for Motorola A780 keylight"
-+
-+config FMRADIO_E680
-+ tristate "Device driver for Motorola E680 FM Radio"
-+
-+endmenu
-+
-Index: linux-2.6.16.5-a/drivers/misc/ezx/Makefile
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/Makefile 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,13 @@
-+
-+obj-$(CONFIG_PXA_EZX) += ssp_pcap_main.o ezx-ts.o ezx-button.o ezx-emu.o
-+
-+# obj-$(CONFIG_EZX) += keypad.o keypad-panasonic.o keypad-e398.o
-+
-+obj-$(CONFIG_KEYPAD_A780) += keypad.o
-+obj-$(CONFIG_KEYPAD_E680) += keypad.o
-+obj-$(CONFIG_KEYLIGHT_A780) += keylight.o
-+obj-$(CONFIG_FMRADIO_E680) += fmradio.o
-+
-+obj-$(CONFIG_PANIC_LOG) += log.o
-+obj-$(CONFIG_ARCH_EZX) += ezx_log.o
-+
-Index: linux-2.6.16.5-a/drivers/misc/ezx/ezx-button.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/ezx-button.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,476 @@
-+/*
-+ * linux/drivers/char/ezx-button.c --- button driver on ezx
-+ *
-+ * Support for the Motorola Ezx A780 Development Platform.
-+ *
-+ * Author: Zhou Qiong, Jay Jia
-+ * Created: Dec 16, 2003
-+ * Copyright: Motorola Inc.
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ *
-+ * Jin Lihong(w20076) Mar.15,2004,LIBdd86574 headset judgement condition reverse
-+ * Jin Lihong(w20076) Apr.13,2004,LIBdd96876 reorganise file header
-+ *
-+ */
-+
-+#include <linux/init.h>
-+#include <linux/config.h>
-+#include <linux/module.h>
-+#include <linux/kernel.h>
-+#include <linux/sched.h>
-+#include <linux/interrupt.h>
-+#include <linux/time.h>
-+#include <linux/timer.h>
-+#include <linux/fs.h>
-+#include <linux/miscdevice.h>
-+#include <linux/string.h>
-+#include <linux/errno.h>
-+#include <linux/poll.h>
-+#include <linux/pm.h>
-+#include <linux/delay.h>
-+#include <linux/apm_bios.h>
-+
-+#include <asm/hardware.h>
-+#include <asm/uaccess.h>
-+#include <asm/irq.h>
-+#include <asm/semaphore.h>
-+#include <asm/mach-types.h>
-+#include <asm/arch/pxa-regs.h>
-+#include <asm/arch/ezx.h>
-+
-+#include "ssp_pcap.h"
-+#include "ezx-button.h"
-+
-+#define DEBUG
-+#ifdef CONFIG_PM
-+static struct pm_dev *pm_dev;
-+#endif
-+
-+#define FULL(queue) ((queue.head+1==queue.tail)||(queue.head+1-NR_BUTTONS==queue.tail))
-+
-+struct button_queue{
-+ unsigned short button_buffer[NR_BUTTONS];
-+ unsigned int head;
-+ unsigned int tail;
-+};
-+
-+static struct timer_list lockscreen_timer;
-+static struct timer_list answer_timer;
-+
-+static DECLARE_WAIT_QUEUE_HEAD(button_wait_queue); /* Used for blocking read */
-+static struct button_queue buttonevent;
-+
-+static int answer_flag=0;
-+int lockscreen_flag=0;
-+
-+static int first_open=0;
-+static int before_emu=0;
-+static int before_charge_500mA=0;
-+static int before_charge_0mA=0;
-+
-+void usb_cable_event_handler(unsigned short cable_event)
-+{
-+ if(!FULL(buttonevent))
-+ {
-+ buttonevent.button_buffer[buttonevent.head] = cable_event;
-+ buttonevent.head = (buttonevent.head+1)%(NR_BUTTONS);
-+ wake_up_interruptible(&button_wait_queue);
-+ printk("usb cable event = %d\n", cable_event);
-+ }
-+}
-+
-+static int button_ioctl(struct inode *inode, struct file *file, uint cmd, ulong arg)
-+{
-+ int data, ret;
-+
-+ switch(cmd){
-+/*
-+*/
-+ case BUTTON_GET_HEADSETSTATUS:
-+ data = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_PSTAT_A1SNS);
-+ if(data)
-+ ret = HEADSET_IN;
-+ else
-+ ret = HEADSET_OUT;
-+ return put_user(ret, (int *)arg);
-+/*
-+*/
-+ case BUTTON_GET_FLIPSTATUS:
-+ data = GPLR(GPIO_FLIP_PIN) & GPIO_bit(GPIO_FLIP_PIN);
-+ if(!data)
-+ ret = FLIP_OFF;
-+ else
-+ ret = FLIP_ON;
-+ lockscreen_flag = ret;
-+ return put_user(ret, (int *)arg);
-+ default:
-+ return -EINVAL;
-+ }
-+ return 0;
-+}
-+
-+static unsigned int button_poll(struct file *file, poll_table *wait)
-+{
-+ poll_wait(file, &button_wait_queue, wait);
-+ if(buttonevent.head != buttonevent.tail)
-+ return POLLIN | POLLRDNORM;
-+ return 0;
-+}
-+/*
-+ * This function is called when a user space program attempts to read
-+ * /dev/button. It puts the device to sleep on the wait queue until
-+ * irq handler writes some data to the buffer and flushes
-+ * the queue, at which point it writes the data out to the device and
-+ * returns the number of characters it has written. This function is
-+ * reentrant, so that many processes can be attempting to read from the
-+ * device at any one time.
-+ */
-+
-+static int button_read (struct file *file, char *buffer, size_t count, loff_t *ppos)
-+{
-+ DECLARE_WAITQUEUE(wait, current);
-+ int retval = 0;
-+
-+ if (buttonevent.head == buttonevent.tail)
-+ {
-+ add_wait_queue(&button_wait_queue, &wait);
-+ current->state = TASK_INTERRUPTIBLE;
-+
-+ while (buttonevent.head == buttonevent.tail)
-+ {
-+ if (file->f_flags & O_NONBLOCK)
-+ {
-+ retval = -EAGAIN;
-+ break;
-+ }
-+ if (signal_pending(current))
-+ {
-+ retval = -ERESTARTSYS;
-+ break;
-+ }
-+ schedule();
-+ }
-+ current->state = TASK_RUNNING;
-+ remove_wait_queue(&button_wait_queue, &wait);
-+ }
-+
-+ if (retval)
-+ return retval;
-+
-+ while ((buttonevent.head != buttonevent.tail) && (retval + sizeof(unsigned short)) <= count)
-+ {
-+ if (copy_to_user(buffer+retval, buttonevent.button_buffer+buttonevent.tail, sizeof(unsigned short)))
-+ return -EFAULT;
-+ buttonevent.tail = (buttonevent.tail+1)%(NR_BUTTONS);
-+ retval += sizeof(unsigned short);
-+ }
-+
-+ return retval;
-+}
-+
-+static void scan_lockscreen_button(unsigned long parameters)
-+{
-+ unsigned long data;
-+ int bdelay = BUTTON_INTERVAL;
-+
-+#ifdef DEBUG
-+ printk("enter scan_lockscreen_button\n");
-+#endif
-+ data = GPLR(GPIO_FLIP_PIN);
-+ if(!(data & GPIO_bit(GPIO_FLIP_PIN))) // lockscreen - 0
-+ {
-+ lockscreen_flag = 0;
-+ if(!FULL(buttonevent))
-+ {
-+ buttonevent.button_buffer[buttonevent.head] = FLIP | KEYDOWN;
-+ buttonevent.head = (buttonevent.head+1)%(NR_BUTTONS);
-+#ifdef CONFIG_KEYPAD_E680
-+ ssp_pcap_screenlock_lock(0);
-+#endif
-+ wake_up_interruptible(&button_wait_queue);
-+#ifdef CONFIG_APM
-+ apm_queue_event(KRNL_FLIP_OFF);
-+#endif
-+
-+#ifdef DEBUG
-+ printk("LockScreen keydown\n");
-+#endif
-+ }
-+ }
-+ else // lockscreen - 1
-+ {
-+ lockscreen_flag = 1;
-+ if(!FULL(buttonevent))
-+ {
-+ buttonevent.button_buffer[buttonevent.head] = FLIP | KEYUP;
-+ buttonevent.head = (buttonevent.head+1)%(NR_BUTTONS);
-+#ifdef CONFIG_KEYPAD_E680
-+ ssp_pcap_screenlock_unlock(0);
-+#endif
-+ wake_up_interruptible(&button_wait_queue);
-+#ifdef CONFIG_APM
-+ apm_queue_event(KRNL_FLIP_ON);
-+#endif
-+
-+#ifdef DEBUG
-+ printk("LockScreen keyup\n");
-+#endif
-+ }
-+ }
-+}
-+
-+static void scan_answer_button(unsigned long parameters)
-+{
-+ int ssp_pcap_bit_status;
-+ int bdelay = BUTTON_INTERVAL;
-+
-+#ifdef DEBUG
-+ printk("enter scan_answer_button\n");
-+#endif
-+ /* read pcap register to check if headjack is in */
-+// ssp_pcap_bit_status = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_PSTAT_A1SNS);
-+// if( ssp_pcap_bit_status != 0 ) /* headjack is in */
-+ {
-+ ssp_pcap_bit_status = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_PSTAT_MB2SNS);
-+ if(ssp_pcap_bit_status == 0) // keydown
-+ {
-+ answer_flag ++;
-+ if((!FULL(buttonevent))&&((answer_flag==1)||((answer_flag%NR_REPEAT)==0)))
-+ {
-+ buttonevent.button_buffer[buttonevent.head] = ANSWER | KEYDOWN;
-+ buttonevent.head = (buttonevent.head+1)%(NR_BUTTONS);
-+ wake_up_interruptible(&button_wait_queue);
-+#ifdef DEBUG
-+ printk("answer keydown\n");
-+#endif
-+ }
-+ answer_timer.expires = (jiffies + bdelay);
-+ add_timer (&answer_timer);
-+ }
-+ else if(answer_flag) // keyup
-+ {
-+ del_timer(&answer_timer);
-+ answer_flag = 0;
-+ if(!FULL(buttonevent))
-+ {
-+ buttonevent.button_buffer[buttonevent.head] = ANSWER | KEYUP;
-+ buttonevent.head = (buttonevent.head+1)%(NR_BUTTONS);
-+ wake_up_interruptible(&button_wait_queue);
-+#ifdef DEBUG
-+ printk("answer keyup\n");
-+#endif
-+ }
-+ }
-+ }
-+}
-+
-+static void lockscreen_handler(int irq, void *dev_id, struct pt_regs *regs)
-+{
-+ int bdelay = 10; /* The delay, in jiffies */
-+
-+ del_timer (&lockscreen_timer);
-+ lockscreen_timer.expires = (jiffies + bdelay);
-+ add_timer (&lockscreen_timer);
-+}
-+
-+void answer_button_handler(int irq, void *dev_id, struct pt_regs *regs)
-+{
-+#if 0
-+ int bdelay = BUTTON_DELAY; /* The delay, in jiffies */
-+
-+ del_timer (&answer_timer);
-+ answer_timer.expires = (jiffies + bdelay);
-+ add_timer (&answer_timer);
-+ printk("answer_button_handler\n");
-+#endif
-+ scan_answer_button(0);
-+}
-+
-+void headset_in_handler(int irq, void *dev_id, struct pt_regs *regs)
-+{
-+ if(!FULL(buttonevent))
-+ {
-+ buttonevent.button_buffer[buttonevent.head] = HEADSET_INT | KEYDOWN;
-+ buttonevent.head = (buttonevent.head+1)%(NR_BUTTONS);
-+ wake_up_interruptible(&button_wait_queue);
-+ printk("headset button insert\n");
-+ answer_flag = 0;
-+ }
-+}
-+
-+
-+void headset_out_handler(int irq, void *dev_id, struct pt_regs *regs)
-+{
-+ if(!FULL(buttonevent))
-+ {
-+ buttonevent.button_buffer[buttonevent.head] = HEADSET_INT | KEYUP;
-+ buttonevent.head = (buttonevent.head+1)%(NR_BUTTONS);
-+ wake_up_interruptible(&button_wait_queue);
-+ printk("headset button remove\n");
-+ answer_flag = 0;
-+ }
-+}
-+
-+#ifdef CONFIG_PM
-+static int button_pm_callback(struct pm_dev *pm_dev, pm_request_t req, void *data)
-+{
-+ switch(req)
-+ {
-+ case PM_SUSPEND:
-+ break;
-+
-+ case PM_RESUME:
-+ break;
-+ }
-+ return 0;
-+}
-+#endif
-+
-+static int count=0;
-+static int button_release(struct inode * inode, struct file * file)
-+{
-+ int i;
-+
-+ count --;
-+ if(count)
-+ {
-+ return -EBUSY;
-+ }
-+
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_MB2I); /* clear interrupt */
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_MSR_MB2M); /* mask interrupt */
-+
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_A1I); /* clear interrupt */
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_MSR_A1M); /* mask interrupt */
-+
-+ // init gpio12 input,
-+// GPDR(GPIO_LOCK_SCREEN_PIN) &= 0xFFFFEFFF;
-+ GPDR(GPIO_FLIP_PIN) &= ~(GPIO_bit(GPIO_FLIP_PIN));
-+ del_timer (&lockscreen_timer);
-+ del_timer (&answer_timer);
-+ free_irq(IRQ_GPIO(GPIO_FLIP_PIN), NULL);
-+
-+ for(i=0; i<NR_BUTTONS; i++)
-+ buttonevent.button_buffer[i] = 0;
-+ buttonevent.head = 0;
-+ buttonevent.tail = 0;
-+
-+#ifdef CONFIG_PM
-+ pm_unregister(pm_dev);
-+#endif
-+#ifdef DEBUG
-+ printk("button device released\n");
-+#endif
-+
-+ return 0;
-+}
-+
-+static int button_open(struct inode * inode, struct file * file)
-+{
-+ int i, data;
-+
-+ if(count)
-+ {
-+ return -EBUSY;
-+ }
-+
-+ count ++;
-+ for(i=0; i<NR_BUTTONS; i++)
-+ buttonevent.button_buffer[i] = 0;
-+ buttonevent.head = 0;
-+ buttonevent.tail = 0;
-+
-+ init_timer (&lockscreen_timer);
-+ lockscreen_timer.function = scan_lockscreen_button;
-+ init_timer (&answer_timer);
-+ answer_timer.function = scan_answer_button;
-+ GAFR(GPIO_FLIP_PIN) &= ~(3<<(2*(GPIO_bit(GPIO_FLIP_PIN) & 0xf)));
-+ GPDR(GPIO_FLIP_PIN) |= GPIO_bit(GPIO_FLIP_PIN);
-+ udelay(10);
-+ set_GPIO_IRQ_edge(GPIO_FLIP_PIN, GPIO_FALLING_EDGE | GPIO_RISING_EDGE);
-+ if (request_irq (IRQ_GPIO(GPIO_FLIP_PIN), lockscreen_handler, SA_INTERRUPT, "flip", NULL))
-+ {
-+ printk (KERN_WARNING "flip irq is free.\n");
-+ return -EIO;
-+ }
-+
-+ ssp_pcap_open(SSP_PCAP_AUDIO_OPEN);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_A1I); /* clear interrupt */
-+ udelay(10);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_MSR_A1M); /* unmask interrupt */
-+ data = SSP_PCAP_get_bit_from_PCAP(SSP_PCAP_ADJ_BIT_PSTAT_A1SNS);
-+ if(data)
-+ {
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_TX_AUD_AMPS_MB_ON2);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_ISR_MB2I);
-+ udelay(10);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_MSR_MB2M);
-+ }
-+#ifdef CONFIG_PM
-+ pm_dev = pm_register(PM_SYS_DEV, 0, button_pm_callback);
-+#endif
-+
-+#ifdef DEBUG
-+ printk("button device opened\n");
-+#endif
-+
-+#ifdef CONFIG_KEYPAD_E680
-+ data = GPLR(GPIO_FLIP_PIN) & GPIO_bit(GPIO_FLIP_PIN);
-+ if(!data)
-+ ssp_pcap_screenlock_lock(0);
-+#endif
-+
-+ first_open = 1;
-+ return 0;
-+}
-+
-+/* add button_ioctl to check flip status */
-+static struct file_operations button_fops = {
-+ owner: THIS_MODULE,
-+ open: button_open,
-+ release: button_release,
-+ read: button_read,
-+ poll: button_poll,
-+ ioctl: button_ioctl,
-+};
-+
-+/*
-+ * This structure is the misc device structure, which specifies the minor
-+ * device number (158 in this case), the name of the device (for /proc/misc),
-+ * and the address of the above file operations structure.
-+ */
-+
-+static struct miscdevice button_misc_device = {
-+ BUTTON_MINOR,
-+ "button",
-+ &button_fops,
-+};
-+
-+/*
-+ * This function is called to initialise the driver, either from misc.c at
-+ * bootup if the driver is compiled into the kernel, or from init_module
-+ * below at module insert time. It attempts to register the device node
-+ * and the IRQ and fails with a warning message if either fails, though
-+ * neither ever should because the device number and IRQ are unique to
-+ * this driver.
-+ */
-+
-+static int __init button_init(void)
-+{
-+ if (misc_register (&button_misc_device)) {
-+ printk (KERN_WARNING "button: Couldn't register device 10, "
-+ "%d.\n", BUTTON_MINOR);
-+ return -EBUSY;
-+ }
-+}
-+
-+static void __exit button_exit (void)
-+{
-+ misc_deregister(&button_misc_device);
-+}
-+
-+module_init(button_init);
-+module_exit(button_exit);
-Index: linux-2.6.16.5-a/drivers/misc/ezx/ezx-button.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/ezx-button.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,84 @@
-+/*
-+ * linux/drivers/char/ezx-button.h
-+ * author: zhouqiong
-+ * company: Motorola BJDC
-+ * date: 11/6/2002
-+ */
-+/* modified by zq, Jan 15,2003
-+ * (1) add flip status ioctl definition
-+ */
-+#include <linux/ioctl.h>
-+
-+/* Various defines: */
-+#define BUTTON_DELAY 1 /* How many jiffies to wait */
-+#define BUTTON_INTERVAL 10 /* How many jiffies to interval */
-+#define VERSION "0.1" /* Driver version number */
-+#define BUTTON_MINOR 158 /* Major 10, Minor 158, /dev/button */
-+
-+/* single button */
-+#define FLIP 0x80
-+#define ANSWER 0x81
-+#define HEADSET_INT 0x82
-+#define EMU_CHARGER_500mA 0x83
-+#define EMU_USB 0x84
-+#define EMU_CHARGER_0 0x85
-+
-+#define NR_BUTTONS 256
-+
-+#define BUTTON_IOCTL_BASE 0xde
-+#define BUTTON_GET_FLIPSTATUS _IOR(BUTTON_IOCTL_BASE, 1,int)
-+#define BUTTON_GET_HEADSETSTATUS _IOR(BUTTON_IOCTL_BASE, 2,int)
-+#define BUTTON_GET_EMU_CABLE _IOR(BUTTON_IOCTL_BASE, 3,int)
-+#define BUTTON_GET_EMU_CHARGER _IOR(BUTTON_IOCTL_BASE, 4,int)
-+#define BUTTON_USB_CABLE_IN _IOR(BUTTON_IOCTL_BASE, 5,int)
-+#define BUTTON_USB_CABLE_OUT _IOR(BUTTON_IOCTL_BASE, 6,int)
-+#define BUTTON_CHARGER_CAP _IOR(BUTTON_IOCTL_BASE, 7,int)
-+#define BUTTON_USB_DEV_TYPE _IOR(BUTTON_IOCTL_BASE, 8,int)
-+#define NR_REPEAT 5
-+#define FLIP_ON 1
-+#define FLIP_OFF 0
-+#define HEADSET_IN 0
-+#define HEADSET_OUT 1
-+#define EMU_CABLE_BEFORE 1
-+#define EMU_CHARGE_500mA_BEFORE 1
-+#define EMU_CHARGE_0mA_BEFORE 2
-+
-+#define KEYDOWN 0x8000
-+#define KEYUP 0x0000
-+//#define LOCKSCREEN 0x84
-+#define LOCKSCREEN FLIP
-+//# define BUTTON_GET_LOCKSCREENSTATUS _IOR(BUTTON_IOCTL_BASE, 3,int)
-+# define BUTTON_GET_LOCKSCREENSTATUS BUTTON_GET_FLIPSTATUS
-+//#define LOCKSCREEN_ON 1
-+#define LOCKSCREEN_ON FLIP_OFF
-+//#define LOCKSCREEN_OFF 0
-+#define LOCKSCREEN_OFF FLIP_ON
-+
-+#ifndef u16
-+#define u16 unsigned short
-+#endif
-+/* usb cable event */
-+#define USB_CABLE_IN 0xa0
-+#define USB_CABLE_OUT 0xa1
-+#define USB_CABLE_500mA 0xa2
-+#define USB_CABLE_0mA 0xa3
-+#define NETMONITOR_CABLE 0xa4
-+#define MODEM_CABLE 0xa5
-+#define APLOG_CABLE 0xa6
-+#define CFG11_CABLE 0xa7
-+#define DSPLOG_CABLE 0xa8
-+#define USBNET_CABLE 0xa9
-+#define PST_CABLE 0xaa
-+#define MASSSTORAGE_CABLE 0xab
-+#define UNKNOWN_CABLE 0xff
-+/*add function*/
-+extern void answer_button_handler(int irq, void *dev_id, struct pt_regs *regs);
-+extern void headset_in_handler(int irq, void *dev_id, struct pt_regs *regs);
-+extern void headset_out_handler(int irq, void *dev_id, struct pt_regs *regs);
-+/*
-+extern void emu_charger_500mA_handler(void);
-+extern void emu_usb_in_handler(void);
-+extern void emu_usb_out_handler(void);
-+extern void emu_charger_0(void);
-+*/
-+extern void usb_cable_event_handler(unsigned short cable_event);
-Index: linux-2.6.16.5-a/drivers/misc/ezx/ezx-emu.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/ezx-emu.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,1185 @@
-+#ifdef EMU_PIHF_FEATURE
-+/*
-+ * linux/drivers/misc/ezx-emu.c --- EMU driver on ezx
-+ *
-+ * Support for the Motorola Ezx A780 Development Platform.
-+ *
-+ * Author: Cheng Xuefeng
-+ * Created: April 30, 2004
-+ * Copyright: Motorola Inc.
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ *
-+ */
-+
-+#include <linux/init.h>
-+#include <linux/config.h>
-+#include <linux/module.h>
-+#include <linux/kernel.h>
-+#include <linux/sched.h>
-+#include <linux/interrupt.h>
-+#include <linux/time.h>
-+#include <linux/timer.h>
-+#include <linux/fs.h>
-+#include <linux/miscdevice.h>
-+#include <linux/string.h>
-+#include <linux/errno.h>
-+#include <linux/poll.h>
-+#include <linux/pm.h>
-+#include <linux/delay.h>
-+#include <linux/apm_bios.h>
-+
-+#include <asm/hardware.h>
-+#include <asm/uaccess.h>
-+#include <asm/irq.h>
-+#include <asm/semaphore.h>
-+#include <asm/mach-types.h>
-+#include "ssp_pcap.h"
-+#include "ezx-emu.h"
-+
-+#include <asm/arch/pxa-regs.h>
-+#include <asm/arch/ezx.h>
-+
-+#define DEBUG
-+#ifdef CONFIG_PM
-+static struct pm_dev *pm_dev;
-+#endif
-+
-+#ifdef EMU_INTERFACE_DEBUG
-+#define EMU_DBG(fmt,args...) printk("EMU:"fmt,##args);
-+#else
-+#define EMU_DBG(fmt,args...)
-+#endif
-+
-+EXPORT_SYMBOL(emu_switch_to);
-+
-+extern void emu_switch_to(T_EMU_SWITCH_TO to);
-+
-+#define EMU_YES (1)
-+#define EMU_NO (0)
-+
-+/* 1ms */
-+#define EMU_PIHF_DPLUS_INIT_INTERVAL (1)
-+
-+static int emu_is_int = EMU_NO;
-+static int emu_is_wait = EMU_NO;
-+
-+typedef enum{
-+ EMU_USB = 0,
-+ EMU_SPD,
-+ EMU_PIHF, /*EMU_PIHF is a subset of EMU_SPD*/
-+ EMU_EIHF
-+} T_EMU_CURRENT_DEVICE;
-+
-+typedef enum{
-+ EMU_MODE_UART =0,
-+ EMU_MODE_USB,
-+ EMU_MODE_AUDIO_MONO,
-+ EMU_MODE_AUDIO_STEREO
-+} T_EMU_MODE;
-+
-+static T_EMU_CURRENT_DEVICE emu_current_device = EMU_USB;
-+static T_EMU_MODE emu_current_mode = EMU_MODE_USB;
-+
-+static DECLARE_WAIT_QUEUE_HEAD(emu_wait_queue); /* Used for blocking read */
-+
-+static int emucount=0;
-+
-+
-+static void emu_handle_int(int irq,void *dev,struct pt_regs *regs);
-+
-+/* This will be export to other modules. For other feature, developer should
-+ * add related T_EMU_SWITCH_TO type as requriement.
-+ */
-+void emu_switch_to(T_EMU_SWITCH_TO to)
-+{
-+ switch(to)
-+ {
-+ case EMU_SWITCH_TO_NO_DEV:
-+ EMU_DBG("emu_switch_to:EMU_SWITCH_TO_NO_DEV\n");
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PU);
-+
-+ /* Disable the PCAP transceiver both for USB and RS232 */
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB);
-+
-+ /* Set the Bulverde GPIO */
-+ pxa_gpio_mode(GPIO34_USB_P2_2_MD);
-+ set_GPIO(GPIO34_TXENB);
-+ pxa_gpio_mode(GPIO35_USB_P2_1_MD);
-+ pxa_gpio_mode(GPIO36_USB_P2_4_MD);
-+ pxa_gpio_mode(GPIO39_USB_P2_6_MD); //pxa_gpio_mode(GPIO39_VPOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO40_USB_P2_5_MD);
-+ pxa_gpio_mode(GPIO53_USB_P2_3_MD);
-+ break;
-+ case EMU_SWITCH_TO_UART:
-+
-+ /* set the PCAP as UART mode */
-+ /*SSP_PCAP_configure_USB_UART_transeiver(SSP_PCAP_SERIAL_PORT);*/
-+ if(SSP_PCAP_SUCCESS == SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN))
-+ {
-+ EMU_DBG("Before SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB clean\n");
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB);
-+ }
-+ else
-+ {
-+ return;
-+ }
-+
-+ /* This must be set. */
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232_DIR);
-+ EMU_DBG("emu_switch_to:EMU_SWITCH_TO_UART:set txd high\n");
-+ set_GPIO(GPIO39_FFTXD);
-+
-+ /* set other USB related GPIO direcction to IN first */
-+ pxa_gpio_mode(GPIO34_USB_P2_2_MD);
-+ set_GPIO(GPIO34_TXENB);
-+ pxa_gpio_mode(GPIO35_XRXD | GPIO_IN);
-+ pxa_gpio_mode(GPIO36_VMOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO40_VPIN | GPIO_IN);
-+
-+ /* Init UART related GPIO */
-+ pxa_gpio_mode(GPIO39_FFTXD_MD);
-+ pxa_gpio_mode(GPIO53_FFRXD_MD);
-+ CKEN |= CKEN6_FFUART;
-+
-+ /* set the MUX1/2 to data mode */
-+ clr_GPIO(GPIO_EMU_MUX1);
-+ clr_GPIO(GPIO_EMU_MUX2);
-+
-+ emu_current_mode = EMU_MODE_UART;
-+ break;
-+ case EMU_SWITCH_TO_USB:
-+ EMU_DBG("emu_switch_to:EMU_SWITCH_TO_USB\n");
-+ /* set the 6 USB related GPIOs as USB function*/
-+ pxa_gpio_mode(GPIO34_USB_P2_2_MD);
-+ pxa_gpio_mode(GPIO35_USB_P2_1_MD);
-+ pxa_gpio_mode(GPIO36_USB_P2_4_MD);
-+ pxa_gpio_mode(GPIO39_USB_P2_6_MD);
-+ pxa_gpio_mode(GPIO40_USB_P2_5_MD);
-+ pxa_gpio_mode(GPIO53_USB_P2_3_MD);
-+ UP2OCR = 0x02000000;
-+
-+ /* set the PCAP as UART mode */
-+ /*SSP_PCAP_configure_USB_UART_transeiver(SSP_PCAP_HIGH_USB_PORT);*/
-+ if(SSP_PCAP_SUCCESS == SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB))
-+ {
-+ if(SSP_PCAP_SUCCESS == SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_FSENB))
-+ {
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ }
-+ }
-+
-+ /* set the MUX1/2 to data mode */
-+ clr_GPIO(GPIO_EMU_MUX1);
-+ clr_GPIO(GPIO_EMU_MUX2);
-+
-+ emu_current_mode = EMU_MODE_USB;
-+ break;
-+ case EMU_SWITCH_TO_AUDIO_MONO:
-+ /* This will not change the PCAP audio related
-+ * register. Just change the MUX1/2. Switching
-+ * the audio path is controlled by other driver.
-+ */
-+ EMU_DBG("emu_switch_to:EMU_SWITCH_TO_AUDIO_MONO\n");
-+
-+ clr_GPIO(GPIO39_VPOUT);
-+ mdelay(1);
-+ pxa_gpio_mode(GPIO34_TXENB | GPIO_OUT);
-+ set_GPIO(GPIO34_TXENB);
-+ pxa_gpio_mode(GPIO35_XRXD | GPIO_IN);
-+ pxa_gpio_mode(GPIO36_VMOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO39_VPOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO40_VPIN | GPIO_IN);
-+ pxa_gpio_mode(GPIO53_VMIN | GPIO_IN);
-+
-+ /* set the MUX1/2 to mono mode */
-+ set_GPIO(GPIO_EMU_MUX1);
-+ clr_GPIO(GPIO_EMU_MUX2);
-+
-+ emu_current_mode = EMU_MODE_AUDIO_MONO;
-+ break;
-+ case EMU_SWITCH_TO_AUDIO_STEREO:
-+ /* This will not change the PCAP audio related
-+ * register. Just change the MUX1/2. Switching
-+ * the audio path is controlled by other driver.
-+ */
-+ EMU_DBG("emu_switch_to:EMU_SWITCH_TO_AUDIO_STEREO\n");
-+ clr_GPIO(GPIO39_VPOUT);
-+ pxa_gpio_mode(GPIO34_USB_P2_@ | GPIO_IN);
-+ pxa_gpio_mode(GPIO35_XRXD | GPIO_IN);
-+ pxa_gpio_mode(GPIO36_VMOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO39_VPOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO40_VPIN | GPIO_IN);
-+ pxa_gpio_mode(GPIO53_VMIN | GPIO_IN);
-+
-+ /* set the MUX1/2 to stereo mode */
-+ set_GPIO(GPIO_EMU_MUX1);
-+ set_GPIO(GPIO_EMU_MUX2);
-+ emu_current_mode = EMU_MODE_AUDIO_STEREO;
-+ break;
-+ default:
-+ break;
-+ }
-+ return;
-+}
-+
-+
-+static int emu_ioctl(struct inode *inode, struct file *file, uint cmd, ulong arg)
-+{
-+ int ret;
-+ long val;
-+
-+ switch(cmd){
-+
-+ /* Switch the MUX1/2 and set the GPIOs */
-+ case EMU_SW_TO_UART:
-+ EMU_DBG("emu_ioctl:EMU_SW_TO_UART:before change\n");
-+ emu_switch_to(EMU_SWITCH_TO_UART);
-+ break;
-+
-+ case EMU_SW_TO_USB:
-+ EMU_DBG("emu_ioctl:EMU_SW_TO_USB:before change\n");
-+ emu_switch_to(EMU_SWITCH_TO_USB);
-+ break;
-+
-+ case EMU_SW_TO_AUDIO_MONO:
-+ EMU_DBG("emu_ioctl:EMU_SW_TO_AUDIO_MONO:before change\n");
-+ emu_switch_to(EMU_SWITCH_TO_AUDIO_MONO);
-+ break;
-+
-+ case EMU_SW_TO_AUDIO_STEREO:
-+ EMU_DBG("emu_ioctl:EMU_SW_TO_AUDIO_STEREO: not support...\n");
-+ emu_switch_to(EMU_SWITCH_TO_AUDIO_STEREO);
-+ break;
-+
-+ case EMU_SMART_SPD_INIT:
-+
-+ EMU_DBG("emu_ioctl:EMU_SPD_INIT\n");
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PU);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PD);
-+ mdelay(EMU_PIHF_DPLUS_INIT_INTERVAL);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PD);
-+
-+ /* init to UART mode */
-+ emu_switch_to(EMU_SWITCH_TO_UART);
-+
-+ EMU_DBG("emu_ioctl:set GPIO 86\n");
-+ /* For SNP_INT_CTL, the inactive state is low.
-+ * That means the ID line is high.
-+ */
-+ pxa_gpio_mode(GPIO_SNP_INT_CTL|GPIO_OUT);
-+ clr_GPIO(GPIO_SNP_INT_CTL);
-+
-+ EMU_DBG("emu_ioctl:before request_irq()\n");
-+
-+ udelay(10);
-+
-+ set_GPIO_IRQ_edge(GPIO_SNP_INT_IN,GPIO_FALLING_EDGE|GPIO_RISING_EDGE);
-+
-+ if (request_irq(IRQ_GPIO(GPIO_SNP_INT_IN),emu_handle_int,
-+ SA_INTERRUPT|SA_SAMPLE_RANDOM,
-+ "EMU SNP interrupt",(void*)1)
-+ )
-+ {
-+ printk(KERN_WARNING"can't get EMU snp_int irq\n");
-+ return -EIO;
-+ }
-+
-+ emu_current_device = EMU_SPD;
-+ break;
-+
-+ /* EMU PIHF */
-+ case EMU_PIHF_INIT:
-+ EMU_DBG("%s,%s:EMU_PIHF_INIT",__FILE__,__FUNCTION__);
-+
-+ /* init to UART mode */
-+ emu_switch_to(EMU_SWITCH_TO_UART);
-+
-+ emu_current_device = EMU_PIHF;
-+ break;
-+ case EMU_PIHF_SNP_INT_CTL:
-+ EMU_DBG("emu_ioctl:got the SNP_INT_CTL...\n");
-+ /* For SNP_INT_CTL, the inactive state is low.
-+ * That means the ID line is high.
-+ */
-+ ret = get_user(val,(long *)arg);
-+ if (ret)
-+ return ret;
-+ disable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ set_GPIO(GPIO_SNP_INT_CTL);
-+ mdelay(val);
-+ clr_GPIO(GPIO_SNP_INT_CTL);
-+ enable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ break;
-+
-+ case EMU_PIHF_ID_LOW:
-+ EMU_DBG("emu_ioctl:EMU_PIHF_ID_LOW\n");
-+ disable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ set_GPIO(GPIO_SNP_INT_CTL);
-+ enable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ break;
-+
-+ case EMU_PIHF_ID_HIGH:
-+ EMU_DBG("emu_ioctl:EMU_PIHF_ID_HIGH\n");
-+ disable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ clr_GPIO(GPIO_SNP_INT_CTL);
-+ enable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ break;
-+
-+ /* EMU EIHF */
-+ case EMU_EIHF_INIT:
-+ emu_current_device = EMU_EIHF;
-+ break;
-+
-+ case EMU_EIHF_MUTE:
-+ clr_GPIO(GPIO_SNP_INT_CTL);
-+ break;
-+
-+ case EMU_EIHF_UNMUTE:
-+ set_GPIO(GPIO_SNP_INT_CTL);
-+ break;
-+
-+ default:
-+ return -EINVAL;
-+ }
-+ return 0;
-+}
-+
-+static unsigned int emu_poll(struct file *file, poll_table *wait)
-+{
-+ if (emu_is_int == EMU_NO)
-+ {
-+ EMU_DBG("%s,%s:emu_is_int is NO\n",__FILE__,__FUNCTION__);
-+ emu_is_wait = EMU_YES;
-+ poll_wait(file, &emu_wait_queue, wait);
-+ }
-+ else
-+ {
-+ EMU_DBG("%s,%s:emu_is_int is YES\n",__FILE__,__FUNCTION__);
-+ emu_is_int = EMU_NO;
-+ }
-+ return POLLIN | POLLRDNORM;
-+}
-+/*
-+ * This function is called when a user space program attempts to read
-+ * /dev/emu. It puts the device to sleep on the wait queue until
-+ * irq handler writes some data to the buffer and flushes
-+ * the queue, at which point it writes the data out to the device and
-+ * returns the number of characters it has written. This function is
-+ * reentrant, so that many processes can be attempting to read from the
-+ * device at any one time.
-+ */
-+
-+static int emu_read (struct file *file, char *buffer, size_t count, loff_t *ppos)
-+{
-+ DECLARE_WAITQUEUE(wait, current);
-+ int retval = 0;
-+
-+ EMU_DBG("%s,%s:enter ...\n",__FILE__,__FUNCTION__);
-+ if (EMU_NO == emu_is_int)
-+ {
-+ EMU_DBG("%s,%s:emu_is_int is NO\n",__FILE__,__FUNCTION__);
-+ add_wait_queue(&emu_wait_queue, &wait);
-+ current->state = TASK_INTERRUPTIBLE;
-+
-+ while (EMU_NO == emu_is_int)
-+ {
-+ if (file->f_flags & O_NONBLOCK)
-+ {
-+ retval = -EAGAIN;
-+ break;
-+ }
-+ if (signal_pending(current))
-+ {
-+ retval = -ERESTARTSYS;
-+ break;
-+ }
-+ emu_is_wait = EMU_YES;
-+ EMU_DBG("%s,%s:before schedule()\n",__FILE__,__FUNCTION__);
-+ schedule();
-+ }
-+ current->state = TASK_RUNNING;
-+ EMU_DBG("%s,%s:after wake up\n",__FILE__,__FUNCTION__);
-+ remove_wait_queue(&emu_wait_queue, &wait);
-+ }
-+
-+ return retval;
-+}
-+
-+#ifdef CONFIG_PM
-+static int emu_pm_callback(struct pm_dev *pm_dev, pm_request_t req, void *data)
-+{
-+ EMU_DBG("emu_pm_callback\n");
-+ switch(req)
-+ {
-+ case PM_SUSPEND:
-+ EMU_DBG("emu_pm_callback:PM_SUSPEND\n");
-+ /* Disable the PCAP transceiver both for USB and RS232 */
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB);
-+
-+ /* Set the Bulverde GPIO */
-+ pxa_gpio_mode(GPIO34_TXENB | GPIO_OUT);
-+ set_GPIO(GPIO34_TXENB);
-+ PGSR(GPIO34_TXENB)|=GPIO_bit(GPIO34_TXENB);
-+ pxa_gpio_mode(GPIO35_XRXD | GPIO_IN);
-+ pxa_gpio_mode(GPIO36_VMOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO39_VPOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO40_VPIN | GPIO_IN);
-+ pxa_gpio_mode(GPIO53_VMIN | GPIO_IN);
-+ break;
-+
-+ case PM_RESUME:
-+
-+ if ( emucount != 0)
-+ {
-+ switch ( emu_current_device)
-+ {
-+ case EMU_PIHF:
-+
-+ EMU_DBG("emu_pm_callback:EMU_PIHF\n");
-+ disable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ clr_GPIO(GPIO_SNP_INT_CTL);
-+ enable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+
-+ switch(emu_current_mode)
-+ {
-+ case EMU_MODE_UART:
-+ emu_switch_to(EMU_SWITCH_TO_UART);
-+ break;
-+ case EMU_MODE_USB:
-+ emu_switch_to(EMU_SWITCH_TO_USB);
-+ break;
-+ case EMU_MODE_AUDIO_MONO:
-+ emu_switch_to(EMU_SWITCH_TO_AUDIO_MONO);
-+ break;
-+ case EMU_MODE_AUDIO_STEREO:
-+ emu_switch_to(EMU_SWITCH_TO_AUDIO_STEREO);
-+ break;
-+ default:
-+ break;
-+ }
-+ break;
-+ case EMU_EIHF:
-+ /* Should not come here since the EIHF must have the charger. */
-+ break;
-+ case EMU_USB:
-+ emu_switch_to(EMU_SWITCH_TO_USB);
-+ break;
-+ default:
-+ break;
-+ }
-+ }
-+ break;
-+ }
-+ return 0;
-+}
-+#endif
-+
-+static int emu_release(struct inode * inode, struct file * file)
-+{
-+ int i;
-+
-+ if ( emucount > 0)
-+ emucount --;
-+
-+ if(emucount)
-+ {
-+ return -EBUSY;
-+ }
-+
-+ if ( EMU_PIHF == emu_current_device)
-+ free_irq(IRQ_GPIO(GPIO_SNP_INT_IN),NULL);
-+
-+ EMU_DBG("emu_release:freed irq...%d\n",IRQ_GPIO(87));
-+
-+#ifdef CONFIG_PM
-+ pm_unregister(pm_dev);
-+#endif
-+#ifdef DEBUG
-+ EMU_DBG("emu_release:emu device released\n");
-+#endif
-+
-+ return 0;
-+}
-+
-+static void emu_handle_int(int irq,void *dev,struct pt_regs *regs)
-+{
-+ EMU_DBG("%s,%s:got the interrupt...\n",__FILE__,__FUNCTION__);
-+ if ( EMU_YES == emu_is_wait )
-+ {
-+ EMU_DBG("%s,%s:emu_is_wait is YES...\n",__FILE__,__FUNCTION__);
-+ wake_up_interruptible(&emu_wait_queue);
-+ emu_is_wait = EMU_NO;
-+ }
-+ else
-+ {
-+ EMU_DBG("%s,%s:emu_is_wait is NO...\n",__FILE__,__FUNCTION__);
-+ emu_is_int = EMU_YES;
-+ }
-+ EMU_DBG("emu_handle_int:after wake up...\n");
-+}
-+
-+static int emu_open(struct inode * inode, struct file * file)
-+{
-+ int i, data;
-+ int ret;
-+
-+ /* emucount could only be 1 or 0 */
-+ if(emucount)
-+ {
-+ return -EBUSY;
-+ }
-+ emucount ++;
-+
-+#ifdef CONFIG_PM
-+ pm_dev = pm_register(PM_SYS_DEV, 0, emu_pm_callback);
-+#endif
-+ EMU_DBG("emu_open:emu device opened\n");
-+ return 0;
-+}
-+
-+/* add emu_ioctl to check flip status */
-+static struct file_operations emu_fops = {
-+ owner: THIS_MODULE,
-+ open: emu_open,
-+ release: emu_release,
-+ read: emu_read,
-+ poll: emu_poll,
-+ ioctl: emu_ioctl,
-+};
-+
-+/*
-+ * This structure is the misc device structure, which specifies the minor
-+ * device number (165 in this case), the name of the device (for /proc/misc),
-+ * and the address of the above file operations structure.
-+ */
-+
-+static struct miscdevice emu_misc_device = {
-+ EMU_MINOR,
-+ "emu",
-+ &emu_fops,
-+};
-+
-+/*
-+ * This function is called to initialise the driver, either from misc.c at
-+ * bootup if the driver is compiled into the kernel, or from init_module
-+ * below at module insert time. It attempts to register the device node
-+ * and the IRQ and fails with a warning message if either fails, though
-+ * neither ever should because the device number and IRQ are unique to
-+ * this driver.
-+ */
-+
-+static int __init emu_init(void)
-+{
-+ pxa_gpio_mode(GPIO_SNP_INT_IN | GPIO_IN);
-+ pxa_gpio_mode(GPIO_EMU_MUX1 | GPIO_OUT);
-+ pxa_gpio_mode(GPIO_EMU_MUX2 | GPIO_OUT);
-+
-+ if (misc_register (&emu_misc_device)) {
-+ EMU_DBG (KERN_WARNING "emu: Couldn't register device 10, "
-+ "%d.\n", EMU_MINOR);
-+ return -EBUSY;
-+ }
-+}
-+
-+static void __exit emu_exit (void)
-+{
-+ misc_deregister(&emu_misc_device);
-+}
-+
-+
-+module_init(emu_init);
-+module_exit(emu_exit);
-+#else /* EMU_PIHF_FEATURE */
-+
-+/*
-+ * linux/drivers/misc/ezx-emu.c --- EMU driver on ezx
-+ *
-+ * Support for the Motorola Ezx A780 Development Platform.
-+ *
-+ * Author: Cheng Xuefeng
-+ * Created: April 30, 2004
-+ * Copyright: Motorola Inc.
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ *
-+ */
-+
-+#include <linux/init.h>
-+#include <linux/config.h>
-+#include <linux/module.h>
-+#include <linux/kernel.h>
-+#include <linux/sched.h>
-+#include <linux/interrupt.h>
-+#include <linux/time.h>
-+#include <linux/timer.h>
-+#include <linux/fs.h>
-+#include <linux/miscdevice.h>
-+#include <linux/string.h>
-+#include <linux/errno.h>
-+#include <linux/poll.h>
-+#include <linux/pm.h>
-+#include <linux/delay.h>
-+#include <linux/apm_bios.h>
-+
-+#include <asm/hardware.h>
-+#include <asm/uaccess.h>
-+#include <asm/irq.h>
-+#include <asm/semaphore.h>
-+#include <asm/mach-types.h>
-+#include "ssp_pcap.h"
-+#include "ezx-emu.h"
-+
-+#include <asm/arch/pxa-regs.h>
-+#include <asm/arch/ezx.h>
-+
-+#define DEBUG
-+#ifdef CONFIG_PM
-+static struct pm_dev *pm_dev;
-+#endif
-+
-+#ifdef EMU_INTERFACE_DEBUG
-+#define EMU_DBG(fmt,args...) printk("EMU:"fmt,##args);
-+#else
-+#define EMU_DBG(fmt,args...)
-+#endif
-+
-+EXPORT_SYMBOL(emu_switch_to);
-+
-+extern void emu_switch_to(T_EMU_SWITCH_TO to);
-+
-+#define EMU_YES (0)
-+#define EMU_NO (1)
-+
-+/* 1ms */
-+#define EMU_PIHF_DPLUS_INIT_INTERVAL (1)
-+
-+static int emu_is_int = EMU_NO;
-+static int emu_is_wait = EMU_NO;
-+
-+typedef enum{
-+ EMU_USB = 0,
-+ EMU_PIHF,
-+ EMU_EIHF
-+} T_EMU_CURRENT_DEVICE;
-+
-+typedef enum{
-+ EMU_MODE_UART =0,
-+ EMU_MODE_USB,
-+ EMU_MODE_AUDIO_MONO,
-+ EMU_MODE_AUDIO_STEREO
-+} T_EMU_MODE;
-+
-+static T_EMU_CURRENT_DEVICE emu_current_device = EMU_USB;
-+static T_EMU_MODE emu_current_mode = EMU_MODE_USB;
-+
-+static DECLARE_WAIT_QUEUE_HEAD(emu_wait_queue); /* Used for blocking read */
-+
-+static int emucount=0;
-+
-+
-+static void emu_handle_int(int irq,void *dev,struct pt_regs *regs);
-+
-+/* This will be export to other modules. For other feature, developer should
-+ * add related T_EMU_SWITCH_TO type as requriement.
-+ */
-+void emu_switch_to(T_EMU_SWITCH_TO to)
-+{
-+ switch(to)
-+ {
-+ case EMU_SWITCH_TO_NO_DEV:
-+ EMU_DBG("emu_switch_to:EMU_SWITCH_TO_NO_DEV\n");
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PU);
-+
-+ /* Disable the PCAP transceiver both for USB and RS232 */
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB);
-+
-+ /* Set the Bulverde GPIO */
-+ pxa_gpio_mode(GPIO34_TXENB | GPIO_OUT);
-+ set_GPIO(GPIO34_TXENB);
-+ pxa_gpio_mode(GPIO35_XRXD | GPIO_IN);
-+ pxa_gpio_mode(GPIO36_VMOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO39_VPOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO40_VPIN | GPIO_IN);
-+ pxa_gpio_mode(GPIO53_VMIN | GPIO_IN);
-+ break;
-+ case EMU_SWITCH_TO_UART:
-+ EMU_DBG("emu_switch_to:EMU_SWITCH_TO_UART\n");
-+ /* set other USB related GPIO direcction to IN first */
-+ set_GPIO(GPIO39_VPOUT);
-+
-+ pxa_gpio_mode(GPIO34_TXENB | GPIO_IN);
-+ pxa_gpio_mode(GPIO35_XRXD | GPIO_IN);
-+ pxa_gpio_mode(GPIO36_VMOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO40_VPIN | GPIO_IN);
-+
-+ /* Init UART related GPIO */
-+ pxa_gpio_mode(GPIO39_FFTXD_MD);
-+ pxa_gpio_mode(GPIO53_FFRXD_MD);
-+ CKEN |= CKEN6_FFUART;
-+ EMU_DBG("emu_switch_to:EMU_SWITCH_TO_UART:set txd high\n");
-+
-+ /* set the PCAP as UART mode */
-+ /*SSP_PCAP_configure_USB_UART_transeiver(SSP_PCAP_SERIAL_PORT);*/
-+ if(SSP_PCAP_SUCCESS == SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN))
-+ {
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB);
-+ }
-+ else
-+ {
-+ return;
-+ }
-+
-+ /* set the MUX1/2 to data mode */
-+ clr_GPIO(GPIO_EMU_MUX1);
-+ clr_GPIO(GPIO_EMU_MUX2);
-+
-+ emu_current_mode = EMU_MODE_UART;
-+ break;
-+ case EMU_SWITCH_TO_USB:
-+ EMU_DBG("emu_switch_to:EMU_SWITCH_TO_USB\n");
-+ /* set the 6 USB related GPIOs as USB function*/
-+ pxa_gpio_mode(GPIO34_USB_P2_2_MD);
-+ pxa_gpio_mode(GPIO35_XRXD_MD);
-+ pxa_gpio_mode(GPIO36_VMOUT_MD);
-+ pxa_gpio_mode(GPIO39_VPOUT_MD);
-+ pxa_gpio_mode(GPIO40_VPIN_MD);
-+ pxa_gpio_mode(GPIO53_VMIN_MD);
-+ UP2OCR = 0x02000000;
-+
-+ /* set the PCAP as UART mode */
-+ /*SSP_PCAP_configure_USB_UART_transeiver(SSP_PCAP_HIGH_USB_PORT);*/
-+ if(SSP_PCAP_SUCCESS == SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB))
-+ {
-+ if(SSP_PCAP_SUCCESS == SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_FSENB))
-+ {
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ }
-+ }
-+
-+ /* set the MUX1/2 to data mode */
-+ clr_GPIO(GPIO_EMU_MUX1);
-+ clr_GPIO(GPIO_EMU_MUX2);
-+
-+ emu_current_mode = EMU_MODE_USB;
-+ break;
-+ case EMU_SWITCH_TO_AUDIO_MONO:
-+ /* This will not change the PCAP audio related
-+ * register. Just change the MUX1/2. Switching
-+ * the audio path is controlled by other driver.
-+ */
-+ EMU_DBG("emu_switch_to:EMU_SWITCH_TO_AUDIO_MONO\n");
-+
-+ clr_GPIO(GPIO39_VPOUT);
-+ mdelay(1);
-+ pxa_gpio_mode(GPIO34_TXENB | GPIO_OUT);
-+ set_GPIO(GPIO34_TXENB);
-+ pxa_gpio_mode(GPIO35_XRXD | GPIO_IN);
-+ pxa_gpio_mode(GPIO36_VMOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO39_VPOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO40_VPIN | GPIO_IN);
-+ pxa_gpio_mode(GPIO53_VMIN | GPIO_IN);
-+
-+ /* set the MUX1/2 to mono mode */
-+ set_GPIO(GPIO_EMU_MUX1);
-+ clr_GPIO(GPIO_EMU_MUX2);
-+
-+ emu_current_mode = EMU_MODE_AUDIO_MONO;
-+ break;
-+ case EMU_SWITCH_TO_AUDIO_STEREO:
-+ /* This will not change the PCAP audio related
-+ * register. Just change the MUX1/2. Switching
-+ * the audio path is controlled by other driver.
-+ */
-+ EMU_DBG("emu_switch_to:EMU_SWITCH_TO_AUDIO_STEREO\n");
-+ clr_GPIO(GPIO39_VPOUT);
-+ pxa_gpio_mode(GPIO34_TXENB | GPIO_OUT);
-+ set_GPIO(GPIO34_TXENB);
-+ pxa_gpio_mode(GPIO35_XRXD | GPIO_IN);
-+ pxa_gpio_mode(GPIO36_VMOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO39_VPOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO40_VPIN | GPIO_IN);
-+ pxa_gpio_mode(GPIO53_VMIN | GPIO_IN);
-+
-+ /* set the MUX1/2 to stereo mode */
-+ set_GPIO(GPIO_EMU_MUX1);
-+ set_GPIO(GPIO_EMU_MUX2);
-+ emu_current_mode = EMU_MODE_AUDIO_STEREO;
-+ break;
-+ default:
-+ break;
-+ }
-+ return;
-+}
-+
-+
-+static int emu_ioctl(struct inode *inode, struct file *file, uint cmd, ulong arg)
-+{
-+ int ret;
-+ long val;
-+
-+ switch(cmd){
-+
-+ /* Switch the MUX1/2 and set the GPIOs */
-+ case EMU_SW_TO_UART:
-+ EMU_DBG("emu_ioctl:EMU_SW_TO_UART:before change\n");
-+ emu_switch_to(EMU_SWITCH_TO_UART);
-+ break;
-+
-+ case EMU_SW_TO_USB:
-+ EMU_DBG("emu_ioctl:EMU_SW_TO_USB:before change\n");
-+ emu_switch_to(EMU_SWITCH_TO_USB);
-+ break;
-+
-+ case EMU_SW_TO_AUDIO_MONO:
-+ EMU_DBG("emu_ioctl:EMU_SW_TO_AUDIO_MONO:before change\n");
-+ emu_switch_to(EMU_SWITCH_TO_AUDIO_MONO);
-+ break;
-+
-+ case EMU_SW_TO_AUDIO_STEREO:
-+ EMU_DBG("emu_ioctl:EMU_SW_TO_AUDIO_STEREO: not support...\n");
-+ emu_switch_to(EMU_SWITCH_TO_AUDIO_STEREO);
-+ break;
-+
-+ /* EMU PIHF */
-+ case EMU_PIHF_INIT:
-+ EMU_DBG("%s,%s:EMU_PIHF_INIT",__FILE__,__FUNCTION__);
-+
-+ /* init to UART mode */
-+ emu_switch_to(EMU_SWITCH_TO_UART);
-+
-+ EMU_DBG("emu_ioctl:set GPIO 86\n");
-+ /* For SNP_INT_CTL, the inactive state is low.
-+ * That means the ID line is high.
-+ */
-+ pxa_gpio_mode(GPIO_SNP_INT_CTL|GPIO_OUT);
-+ clr_GPIO(GPIO_SNP_INT_CTL);
-+
-+ EMU_DBG("emu_ioctl:before request_irq()\n");
-+
-+ udelay(10);
-+
-+ set_GPIO_IRQ_edge(GPIO_SNP_INT_IN,GPIO_FALLING_EDGE|GPIO_RISING_EDGE);
-+
-+#if 0
-+ if(GPLR(GPIO_SNP_INT_IN) & GPIO_bit(GPIO_SNP_INT_IN))
-+ {
-+ EMU_DBG("emu_ioctl:87 is high\n");
-+ }
-+ else
-+ {
-+ EMU_DBG("emu_ioctl:87 is low\n");
-+ }
-+#endif
-+
-+ if (request_irq(IRQ_GPIO(GPIO_SNP_INT_IN),emu_handle_int,
-+ SA_INTERRUPT|SA_SAMPLE_RANDOM,
-+ "EMU SNP interrupt",(void*)1)
-+ )
-+ {
-+ printk(KERN_WARNING"can't get EMU snp_int irq\n");
-+ return -EIO;
-+ }
-+
-+ emu_current_device = EMU_PIHF;
-+ break;
-+ case EMU_PIHF_SNP_INT_CTL:
-+ EMU_DBG("emu_ioctl:got the SNP_INT_CTL...\n");
-+ /* For SNP_INT_CTL, the inactive state is low.
-+ * That means the ID line is high.
-+ */
-+ ret = get_user(val,(long *)arg);
-+ if (ret)
-+ return ret;
-+ disable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ set_GPIO(GPIO_SNP_INT_CTL);
-+ mdelay(val);
-+ clr_GPIO(GPIO_SNP_INT_CTL);
-+ enable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ break;
-+
-+ case EMU_PIHF_ID_LOW:
-+ EMU_DBG("emu_ioctl:EMU_PIHF_ID_LOW\n");
-+ disable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ set_GPIO(GPIO_SNP_INT_CTL);
-+ enable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ break;
-+
-+ case EMU_PIHF_ID_HIGH:
-+ EMU_DBG("emu_ioctl:EMU_PIHF_ID_HIGH\n");
-+ disable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ clr_GPIO(GPIO_SNP_INT_CTL);
-+ enable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ break;
-+
-+ case EMU_PIHF_INIT_DPLUS_CTL:
-+ EMU_DBG("emu_ioctl:EMU_PIHF_INIT_DPLUS_CTL\n");
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PU);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PD);
-+ mdelay(EMU_PIHF_DPLUS_INIT_INTERVAL);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_USB_PD);
-+ break;
-+
-+ /* EMU EIHF */
-+ case EMU_EIHF_INIT:
-+ emu_current_device = EMU_EIHF;
-+ break;
-+
-+ case EMU_EIHF_MUTE:
-+ clr_GPIO(GPIO_SNP_INT_CTL);
-+ break;
-+
-+ case EMU_EIHF_UNMUTE:
-+ set_GPIO(GPIO_SNP_INT_CTL);
-+ break;
-+
-+ default:
-+ return -EINVAL;
-+ }
-+ return 0;
-+}
-+
-+static unsigned int emu_poll(struct file *file, poll_table *wait)
-+{
-+ if (emu_is_int == EMU_NO)
-+ {
-+ emu_is_wait = EMU_YES;
-+ poll_wait(file, &emu_wait_queue, wait);
-+ }
-+ else
-+ {
-+ emu_is_int = EMU_NO;
-+ }
-+ return POLLIN | POLLRDNORM;
-+}
-+/*
-+ * This function is called when a user space program attempts to read
-+ * /dev/emu. It puts the device to sleep on the wait queue until
-+ * irq handler writes some data to the buffer and flushes
-+ * the queue, at which point it writes the data out to the device and
-+ * returns the number of characters it has written. This function is
-+ * reentrant, so that many processes can be attempting to read from the
-+ * device at any one time.
-+ */
-+
-+static int emu_read (struct file *file, char *buffer, size_t count, loff_t *ppos)
-+{
-+ DECLARE_WAITQUEUE(wait, current);
-+ int retval = 0;
-+
-+ if (EMU_NO == emu_is_int)
-+ {
-+ add_wait_queue(&emu_wait_queue, &wait);
-+ current->state = TASK_INTERRUPTIBLE;
-+
-+ while (EMU_NO == emu_is_int)
-+ {
-+ if (file->f_flags & O_NONBLOCK)
-+ {
-+ retval = -EAGAIN;
-+ break;
-+ }
-+ if (signal_pending(current))
-+ {
-+ retval = -ERESTARTSYS;
-+ break;
-+ }
-+ emu_is_wait = EMU_YES;
-+ schedule();
-+ }
-+ current->state = TASK_RUNNING;
-+ remove_wait_queue(&emu_wait_queue, &wait);
-+ }
-+
-+ return retval;
-+}
-+
-+#ifdef CONFIG_PM
-+static int emu_pm_callback(struct pm_dev *pm_dev, pm_request_t req, void *data)
-+{
-+ EMU_DBG("emu_pm_callback\n");
-+ switch(req)
-+ {
-+ case PM_SUSPEND:
-+ EMU_DBG("emu_pm_callback:PM_SUSPEND\n");
-+ /* Disable the PCAP transceiver both for USB and RS232 */
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_BUSCTRL_VUSB_EN);
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_BUSCTRL_RS232ENB);
-+
-+ /* Set the Bulverde GPIO */
-+ pxa_gpio_mode(GPIO34_TXENB | GPIO_OUT);
-+ set_GPIO(GPIO34_TXENB);
-+ PGSR(GPIO34_TXENB)|=GPIO_bit(GPIO34_TXENB);
-+ pxa_gpio_mode(GPIO35_XRXD | GPIO_IN);
-+ pxa_gpio_mode(GPIO36_VMOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO39_VPOUT | GPIO_IN);
-+ pxa_gpio_mode(GPIO40_VPIN | GPIO_IN);
-+ pxa_gpio_mode(GPIO53_VMIN | GPIO_IN);
-+ break;
-+
-+ case PM_RESUME:
-+
-+ if ( emucount != 0)
-+ {
-+ switch ( emu_current_device)
-+ {
-+ case EMU_PIHF:
-+
-+ EMU_DBG("emu_pm_callback:EMU_PIHF\n");
-+ disable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+ clr_GPIO(GPIO_SNP_INT_CTL);
-+ enable_irq(IRQ_GPIO(GPIO_SNP_INT_IN));
-+
-+ switch(emu_current_mode)
-+ {
-+ case EMU_MODE_UART:
-+ emu_switch_to(EMU_SWITCH_TO_UART);
-+ break;
-+ case EMU_MODE_USB:
-+ emu_switch_to(EMU_SWITCH_TO_USB);
-+ break;
-+ case EMU_MODE_AUDIO_MONO:
-+ emu_switch_to(EMU_SWITCH_TO_AUDIO_MONO);
-+ break;
-+ case EMU_MODE_AUDIO_STEREO:
-+ emu_switch_to(EMU_SWITCH_TO_AUDIO_STEREO);
-+ break;
-+ default:
-+ break;
-+ }
-+ break;
-+ case EMU_EIHF:
-+ /* Should not come here since the EIHF must have the charger. */
-+ break;
-+ case EMU_USB:
-+ emu_switch_to(EMU_SWITCH_TO_USB);
-+ break;
-+ default:
-+ break;
-+ }
-+ }
-+ break;
-+ }
-+ return 0;
-+}
-+#endif
-+
-+static int emu_release(struct inode * inode, struct file * file)
-+{
-+ int i;
-+
-+ if ( emucount > 0)
-+ emucount --;
-+
-+ if(emucount)
-+ {
-+ return -EBUSY;
-+ }
-+
-+ if ( EMU_PIHF == emu_current_device)
-+ free_irq(IRQ_GPIO(GPIO_SNP_INT_IN),NULL);
-+
-+ EMU_DBG("emu_release:freed irq...%d\n",IRQ_GPIO(87));
-+
-+#ifdef CONFIG_PM
-+ pm_unregister(pm_dev);
-+#endif
-+#ifdef DEBUG
-+ EMU_DBG("emu_release:emu device released\n");
-+#endif
-+
-+ return 0;
-+}
-+
-+static void emu_handle_int(int irq,void *dev,struct pt_regs *regs)
-+{
-+ EMU_DBG("emu_handle_int:got the interrupt...\n");
-+ if ( EMU_YES == emu_is_wait )
-+ {
-+ wake_up_interruptible(&emu_wait_queue);
-+ emu_is_wait = EMU_NO;
-+ }
-+ else
-+ {
-+ emu_is_int = EMU_YES;
-+ }
-+ EMU_DBG("emu_handle_int:after wake up...\n");
-+}
-+
-+static int emu_open(struct inode * inode, struct file * file)
-+{
-+ int i, data;
-+ int ret;
-+
-+ /* emucount could only be 1 or 0 */
-+ if(emucount)
-+ {
-+ return -EBUSY;
-+ }
-+ emucount ++;
-+
-+#ifdef CONFIG_PM
-+ pm_dev = pm_register(PM_SYS_DEV, 0, emu_pm_callback);
-+#endif
-+ EMU_DBG("emu_open:emu device opened\n");
-+ return 0;
-+}
-+
-+/* add emu_ioctl to check flip status */
-+static struct file_operations emu_fops = {
-+ owner: THIS_MODULE,
-+ open: emu_open,
-+ release: emu_release,
-+ read: emu_read,
-+ poll: emu_poll,
-+ ioctl: emu_ioctl,
-+};
-+
-+/*
-+ * This structure is the misc device structure, which specifies the minor
-+ * device number (165 in this case), the name of the device (for /proc/misc),
-+ * and the address of the above file operations structure.
-+ */
-+
-+static struct miscdevice emu_misc_device = {
-+ EMU_MINOR,
-+ "emu",
-+ &emu_fops,
-+};
-+
-+/*
-+ * This function is called to initialise the driver, either from misc.c at
-+ * bootup if the driver is compiled into the kernel, or from init_module
-+ * below at module insert time. It attempts to register the device node
-+ * and the IRQ and fails with a warning message if either fails, though
-+ * neither ever should because the device number and IRQ are unique to
-+ * this driver.
-+ */
-+
-+static int __init emu_init(void)
-+{
-+ pxa_gpio_mode(GPIO_SNP_INT_IN | GPIO_IN);
-+
-+ if (misc_register (&emu_misc_device)) {
-+ EMU_DBG (KERN_WARNING "emu: Couldn't register device 10, "
-+ "%d.\n", EMU_MINOR);
-+ return -EBUSY;
-+ }
-+}
-+
-+static void __exit emu_exit (void)
-+{
-+ misc_deregister(&emu_misc_device);
-+}
-+
-+
-+module_init(emu_init);
-+module_exit(emu_exit);
-+#endif /* EMU_PIHF_FEATURE */
-Index: linux-2.6.16.5-a/drivers/misc/ezx/ezx-emu.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/ezx-emu.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,93 @@
-+#ifdef EMU_PIHF_FEATURE
-+/*
-+ * linux/drivers/emu/ezx-emu.h
-+ * author: Cheng Xuefeng
-+ * company: Motorola Inc.
-+ * date: 30/4/2004
-+ */
-+#include <linux/ioctl.h>
-+
-+/* Various defines: */
-+#define VERSION "0.1" /* Driver version number */
-+#define EMU_MINOR 250 /* Major 10, Minor 250, /dev/emu */
-+
-+/* single button */
-+
-+#define EMU_IOCTL_BASE 0xdf
-+
-+/* Switch the Mux1/2 and set the GPIOs */
-+#define EMU_SW_TO_UART _IO(EMU_IOCTL_BASE, 1)
-+#define EMU_SW_TO_USB _IO(EMU_IOCTL_BASE, 2)
-+#define EMU_SW_TO_AUDIO_MONO _IO(EMU_IOCTL_BASE, 3)
-+#define EMU_SW_TO_AUDIO_STEREO _IO(EMU_IOCTL_BASE, 4)
-+#define EMU_SMART_SPD_INIT _IO(EMU_IOCTL_BASE, 5)
-+
-+/* EMU PIHF */
-+#define EMU_PIHF_INIT _IOW(EMU_IOCTL_BASE, 21,int)
-+/*#define EMU_PIHF_GET_STATUS _IOR(EMU_IOCTL_BASE, 12,int)*/
-+#define EMU_PIHF_SNP_INT_CTL _IOR(EMU_IOCTL_BASE, 23,int)
-+#define EMU_PIHF_ID_LOW _IO(EMU_IOCTL_BASE, 24)
-+#define EMU_PIHF_ID_HIGH _IO(EMU_IOCTL_BASE, 25)
-+
-+/* EMU EIHF */
-+#define EMU_EIHF_INIT _IOW(EMU_IOCTL_BASE, 31,int)
-+#define EMU_EIHF_MUTE _IO(EMU_IOCTL_BASE, 32)
-+#define EMU_EIHF_UNMUTE _IO(EMU_IOCTL_BASE, 33)
-+
-+typedef enum{
-+ EMU_SWITCH_TO_UART = 0,
-+ EMU_SWITCH_TO_USB,
-+ EMU_SWITCH_TO_AUDIO_MONO,
-+ EMU_SWITCH_TO_AUDIO_STEREO,
-+ EMU_SWITCH_TO_NO_DEV
-+} T_EMU_SWITCH_TO;
-+
-+void emu_switch_to(T_EMU_SWITCH_TO to);
-+
-+#else /* EMU_PIHF_FEATURE */
-+
-+/*
-+ * linux/drivers/emu/ezx-emu.h
-+ * author: Cheng Xuefeng
-+ * company: Motorola Inc.
-+ * date: 30/4/2004
-+ */
-+#include <linux/ioctl.h>
-+
-+/* Various defines: */
-+#define VERSION "0.1" /* Driver version number */
-+#define EMU_MINOR 250 /* Major 10, Minor 250, /dev/emu */
-+
-+/* single button */
-+
-+#define EMU_IOCTL_BASE 0xdf
-+
-+/* Switch the Mux1/2 and set the GPIOs */
-+#define EMU_SW_TO_UART _IO(EMU_IOCTL_BASE, 1)
-+#define EMU_SW_TO_USB _IO(EMU_IOCTL_BASE, 2)
-+#define EMU_SW_TO_AUDIO_MONO _IO(EMU_IOCTL_BASE, 3)
-+#define EMU_SW_TO_AUDIO_STEREO _IO(EMU_IOCTL_BASE, 4)
-+
-+/* EMU PIHF */
-+#define EMU_PIHF_INIT _IOW(EMU_IOCTL_BASE, 21,int)
-+/*#define EMU_PIHF_GET_STATUS _IOR(EMU_IOCTL_BASE, 12,int)*/
-+#define EMU_PIHF_SNP_INT_CTL _IOR(EMU_IOCTL_BASE, 23,int)
-+#define EMU_PIHF_ID_LOW _IO(EMU_IOCTL_BASE, 24)
-+#define EMU_PIHF_ID_HIGH _IO(EMU_IOCTL_BASE, 25)
-+#define EMU_PIHF_INIT_DPLUS_CTL _IO(EMU_IOCTL_BASE, 26)
-+
-+/* EMU EIHF */
-+#define EMU_EIHF_INIT _IOW(EMU_IOCTL_BASE, 31,int)
-+#define EMU_EIHF_MUTE _IO(EMU_IOCTL_BASE, 32)
-+#define EMU_EIHF_UNMUTE _IO(EMU_IOCTL_BASE, 33)
-+
-+typedef enum{
-+ EMU_SWITCH_TO_UART = 0,
-+ EMU_SWITCH_TO_USB,
-+ EMU_SWITCH_TO_AUDIO_MONO,
-+ EMU_SWITCH_TO_AUDIO_STEREO,
-+ EMU_SWITCH_TO_NO_DEV
-+} T_EMU_SWITCH_TO;
-+
-+void emu_switch_to(T_EMU_SWITCH_TO to);
-+#endif /* EMU_PIHF_FEATURE */
-Index: linux-2.6.16.5-a/drivers/misc/ezx/ezx-log.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/ezx-log.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,183 @@
-+/*
-+ * Kernel panic log interface for Linux on A760(XScale PXA262).
-+ *
-+ * Copyright (c) 2000 Motorola
-+ *
-+ * This program is free software; you can redistribute it and/or
-+ * modify it under the terms of the GNU General Public License
-+ * as published by the Free Software Foundation; either version
-+ * 2 of the License, or (at your option) any later version.
-+ *
-+ * 0.01 2003-07-01 zxf <w19962@motorola.com>
-+ * - initial release
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/init.h>
-+#include <linux/slab.h>
-+#include <linux/mtd/mtd.h>
-+
-+#include <asm/io.h>
-+#include <asm/uaccess.h>
-+
-+#include "log.h"
-+
-+#define A760_LOG_NAME "A760"
-+#define A760_LOG_START 0x01fc0000
-+#define A760_LOG_SIZE 0x00020000
-+
-+#define E680_LOG_NAME "E680"
-+#define E680_LOG_START 0x01fc0000
-+#define E680_LOG_SIZE 0x00020000
-+
-+#define A780_LOG_NAME "A780"
-+#define A780_LOG_START 0x01fc0000
-+#define A780_LOG_SIZE 0x00020000
-+
-+#ifdef CONFIG_ARCH_EZX_E680
-+#define LOG_NAME E680_LOG_NAME
-+#define LOG_START E680_LOG_START
-+#define LOG_SIZE E680_LOG_SIZE
-+#elif CONFIG_ARCH_EZX_A780
-+#define LOG_NAME A780_LOG_NAME
-+#define LOG_START A780_LOG_START
-+#define LOG_SIZE A780_LOG_SIZE
-+#else
-+#define LOG_NAME A760_LOG_NAME
-+#define LOG_START A760_LOG_START
-+#define LOG_SIZE A760_LOG_SIZE
-+#endif
-+
-+static ssize_t log_read(const char *buf, size_t count, loff_t *ppos);
-+static ssize_t log_write(const char *buf, size_t count);
-+
-+static struct log_area flash_log = {
-+ name: LOG_NAME, //"A760",
-+ start: LOG_START, // LOGO_ADDR is 0x01fc0000
-+ size: LOG_SIZE,
-+ write: log_write,
-+ read: log_read,
-+};
-+
-+/*
-+ * Here the read implementation should not impact mtd device.
-+ * Most part of the read function is coming from mtdchar.c
-+ */
-+#define MAX_KMALLOC_SIZE 0x20000
-+static ssize_t log_read(const char *buf, size_t count, loff_t *ppos)
-+{
-+ struct mtd_info *mtd;
-+ size_t retlen=0;
-+ size_t total_retlen=0;
-+ int ret=0;
-+ int len;
-+ char *kbuf;
-+
-+ mtd = get_mtd_device(NULL, 3);
-+ if (!mtd)
-+ return -ENODEV;
-+
-+ while (count) {
-+ if (count > MAX_KMALLOC_SIZE)
-+ len = MAX_KMALLOC_SIZE;
-+ else
-+ len = count;
-+
-+ kbuf=kmalloc(len,GFP_KERNEL);
-+ if (!kbuf)
-+ return -ENOMEM;
-+
-+ ret = MTD_READ(mtd, *ppos, len, &retlen, kbuf);
-+ if (!ret) {
-+ *ppos += retlen;
-+ if (copy_to_user(buf, kbuf, retlen)) {
-+ kfree(kbuf);
-+ return -EFAULT;
-+ }
-+ else
-+ total_retlen += retlen;
-+
-+ count -= retlen;
-+ buf += retlen;
-+ }
-+ else {
-+ kfree(kbuf);
-+ return ret;
-+ }
-+
-+ kfree(kbuf);
-+ }
-+
-+ return total_retlen;
-+}
-+
-+static ssize_t log_write(const char *buf, size_t count)
-+{
-+ int i;
-+ ssize_t ret;
-+ void *area;
-+ unsigned short *buffer;
-+ volatile unsigned short *ptr;
-+
-+ //printk(KERN_EMERG "****** panic time: %d ******\n", OSCR);
-+
-+ area = __ioremap(flash_log.start, flash_log.size, 0);
-+ if (!area)
-+ return -ENOMEM;
-+
-+ ptr = (unsigned short *)area;
-+ ret = count;
-+
-+#define EZX_A760
-+#ifdef EZX_A760
-+ /* wait state ready */
-+ *ptr = 0x70;
-+ while (!((*ptr) & 0x80));
-+
-+ /* unlock the block */
-+ *ptr = 0x60; *ptr = 0xd0;
-+ while (!((*ptr) & 0x80));
-+
-+ /* erase the block */
-+ *ptr = 0x20; *ptr = 0xd0;
-+ while (!((*ptr) & 0x80));
-+
-+#elif EZX_BVD
-+ // bvd platform
-+ // same as A760
-+#endif
-+
-+ /* program the block */
-+ if(count > flash_log.size)
-+ count = flash_log.size;
-+ count = count / sizeof(unsigned short); /* it doesn't matter to lose a little data */
-+ buffer = (unsigned short *)buf;
-+ for (i = 0; i < count; i++, ptr++) {
-+ *ptr = 0x40;
-+ *ptr = *buffer++;
-+ while (!((*ptr) & 0x80));
-+ }
-+
-+ //printk(KERN_EMERG "****** panic time: %d ******\n", OSCR);
-+ __iounmap(area);
-+ return ret;
-+}
-+
-+
-+static int __init ezxlog_init(void)
-+{
-+ return log_register(&flash_log);
-+}
-+
-+static void __exit ezxlog_exit(void)
-+{
-+ log_unregister(&flash_log);
-+}
-+
-+module_init(ezxlog_init);
-+module_exit(ezxlog_exit);
-+
-+MODULE_AUTHOR("zxf <w19962@motorola.com>");
-+MODULE_DESCRIPTION("A760 Kernel panic log interface");
-+MODULE_LICENSE("GPL");
-+EXPORT_NO_SYMBOLS;
-Index: linux-2.6.16.5-a/drivers/misc/ezx/ezx-ts.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/ezx-ts.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,910 @@
-+/*
-+ * linux/drivers/char/ezx-ts.c
-+ *
-+ * Copyright (C) 2002 Lili Jiang, All Rights Reserved.
-+ *
-+ *
-+ * June, 2002 Lili Jiang, create
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/init.h>
-+#include <linux/fs.h>
-+#include <linux/miscdevice.h>
-+#include <linux/poll.h>
-+#include <linux/smp.h>
-+#include <linux/smp_lock.h>
-+#include <linux/sched.h>
-+#include <linux/completion.h>
-+#include <linux/string.h>
-+#include <linux/pm.h>
-+#include <linux/config.h>
-+#include <linux/fb.h>
-+
-+#include <asm/semaphore.h>
-+#include <asm/hardware.h>
-+#include <asm/arch/irqs.h>
-+#include <linux/timex.h>
-+#include <linux/interrupt.h>
-+
-+#include <asm/arch/pxa-regs.h>
-+
-+#include "ezx-ts.h"
-+#include "ssp_pcap.h"
-+
-+#define DEBUG 0 /*change it when formal release*/
-+#if DEBUG
-+# define TS_DPRINTK(s...) printk(s)
-+#else
-+# define TS_DPRINTK(s...)
-+#endif
-+
-+/*
-+ * This structure is nonsense - millisecs is not very useful
-+ * since the field size is too small. Also, we SHOULD NOT
-+ * be exposing jiffies to user space directly.
-+ */
-+struct ts_event {
-+ u16 pressure;
-+ u16 x;
-+ u16 y;
-+ u16 pad;
-+// struct timeval stamp;
-+};
-+
-+static struct timer_list ezx_ts_penup_timer;
-+
-+static struct irqaction ezx_ts_custom_timer_irq = {
-+ name: "ezx_ts_custom_timer",
-+};
-+
-+static u8 bSetPenupTimer = 0;
-+static u8 bFirstPen = 0;
-+//static unsigned long penCurJiffies = 0;
-+static unsigned int penSampleCount = 0;
-+static u32 tspenSampleCount = 0;
-+static u32 tsDiscardDataCount = 0;
-+
-+typedef enum
-+{
-+ PRESSURE,
-+ COORDINATE
-+}EZX_TS_READ_STATE;
-+
-+EZX_TS_READ_STATE ezx_ts_read_state = PRESSURE;
-+
-+#define TS_NR_EVENTS 128
-+/*250 //pay attention to that haed and tail is defined as u8*/
-+
-+#define TS_EDGE_MIN_LIMIT (0) /* 10 */
-+#define TS_EDGE_MAX_LIMIT (1023)
-+
-+/* jiffies : 10ms, pen shake 50ms????? */
-+//#define EZX_TS_READ_MIN_SPACE 10 /*100//5*/
-+//#define EZX_TS_PENUP_TIMEOUT_MS 8
-+
-+#define EZX_TS_PENSAMPLE_TIMEOUT_MS 2
-+ //8,6
-+//#define EZX_TS_HWR_TIMEOUT_MS 2
-+
-+#define QT_ONEPEN_SAMPLES_NUM 1
-+ //3,5
-+//#define HWR_ONEPEN_SAMPLES_NUM 1
-+
-+#define CUSTOM_ONEPEN_SAMPLES_NUM 1
-+#define EZX_TS_CUSTOM_TIMEOUT_MS 12
-+ //15ms
-+#define X_DIFF 85
-+#define Y_DIFF 75
-+#define MIN_X_HOLD 5
-+#define MIN_Y_HOLD 4
-+#define SAMPLE_COUNT_NOT_JUMPER 20
-+
-+typedef enum
-+{
-+ EZX_PEN_NORMAL,
-+ EZX_PEN_CUSTOM
-+}EZX_TS_PEN_STYLE;
-+
-+static EZX_TS_PEN_STYLE gPenStyle = EZX_PEN_NORMAL;
-+static u8 gPenSamplesNum = QT_ONEPEN_SAMPLES_NUM;
-+//static u32 gHwrTimer = EZX_TS_HWR_TIMEOUT_MS;
-+static u32 gCustomTimer = EZX_TS_CUSTOM_TIMEOUT_MS;
-+static u8 getPenUp = 0;
-+
-+struct ezx_ts_info {
-+ /*struct ucb1x00 *ucb;*/
-+ struct fasync_struct *fasync;
-+ wait_queue_head_t read_wait;
-+
-+ /*
-+ struct semaphore irq_wait;
-+ struct semaphore sem;
-+ struct completion init_exit;
-+ struct task_struct *rtask;
-+ */
-+ u16 x_cur; /*store the current pen value read from ADC*/
-+ u16 y_cur; /*store the current pen value read from ADC */
-+ u16 cur_pressure;
-+ u16 x_pre;
-+ u16 y_pre;
-+ u8 evt_head;
-+ u8 evt_tail;
-+ struct ts_event events[TS_NR_EVENTS]; /* buffer for store pen data*/
-+/*
-+ int restart:1;
-+ int adcsync:1;
-+
-+#ifdef CONFIG_PM
-+ struct pm_dev *pmdev;
-+#endif
-+*/
-+};
-+
-+static struct ezx_ts_info ezxts;
-+
-+#define EZX_TS_SHAKE_SAMPLES 3
-+static u8 ezx_ts_shake_samples_count = 0;
-+static struct ts_event ezx_ts_shake_samples[EZX_TS_SHAKE_SAMPLES];
-+
-+static int ezx_ts_init(void);
-+static void ezx_ts_exit(void);
-+static int ezx_ts_open(struct inode *inode, struct file * filp);
-+static int ezx_ts_release(struct inode *inode, struct file *filp);
-+static ssize_t ezx_ts_read(struct file* filp, char* buffer, size_t count, loff_t *ppos);
-+static unsigned int ezx_ts_poll(struct file* filp, struct poll_table_struct * wait);
-+static int ezx_ts_fasync(int fd, struct file* filp, int mode);
-+
-+/* internal function */
-+static void ezx_ts_init_penEvent(void);
-+static void ezx_ts_pen_touch_handler(void);
-+static void ezx_ts_penup_timeout(unsigned long data);
-+static void ezx_ts_set_timer(struct timer_list *timer, void (*timer_timeout)(unsigned long), signed long timeout);
-+static void ezx_ts_check_pen_samples(void);
-+static void ezx_ts_evt_add(u16 pressure, u16 x, u16 y);
-+static struct ts_event ezx_ts_get_onedata(void);
-+
-+/* for setup ezx ts self timer,begin */
-+static void ezx_ts_custom_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
-+{
-+ TS_DPRINTK("ezx_ts_custom_timer_interrupt entered.jiffies: %d\n@@@\n", jiffies);
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_POSITION_XY_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+
-+ /* clear this timer */
-+ OIER &= ~OIER_E3;
-+ OSSR = OSSR_M3; /* Clear match on timer 2 */
-+}
-+
-+static void ezx_ts_custom_setup_timer()
-+{
-+ ezx_ts_custom_timer_irq.handler = ezx_ts_custom_timer_interrupt;
-+ setup_irq(IRQ_OST3, &ezx_ts_custom_timer_irq);
-+}
-+
-+
-+static void ezx_ts_custom_timer_start(void)
-+{
-+ OIER |= OIER_E3;
-+ //OSMR2 = OSCR + sleep_limit * LATCH; //OSCR: 0x40A00010
-+ OSMR3 = OSCR + (gCustomTimer * HZ * LATCH) /1000;
-+}
-+
-+static void ezx_ts_custom_timer_stop(void)
-+{
-+ OIER &= ~OIER_E3;
-+ OSSR = OSSR_M3; /* Clear match on timer 2 */
-+}
-+
-+/* for setup ezx ts self timer, end */
-+
-+
-+static void ezx_ts_init_penEvent(void)
-+{
-+ int i;
-+
-+ ezxts.x_cur = 0;
-+ ezxts.y_cur = 0;
-+ ezxts.x_pre = 0;
-+ ezxts.y_pre = 0;
-+ ezxts.cur_pressure = PEN_UP;
-+
-+ for (i = 0; i < TS_NR_EVENTS; i++)
-+ {
-+ ezxts.events[i].pressure=(u16)0;
-+ ezxts.events[i].x=(u16)0;
-+ ezxts.events[i].y=(u16)0;
-+ ezxts.events[i].pad=(u16)0;
-+ }
-+ ezxts.evt_head = 0;
-+ ezxts.evt_tail = 0;
-+
-+ gPenStyle = EZX_PEN_NORMAL;
-+ gPenSamplesNum = QT_ONEPEN_SAMPLES_NUM;
-+ //gHwrTimer = EZX_TS_HWR_TIMEOUT_MS;
-+ gCustomTimer = EZX_TS_CUSTOM_TIMEOUT_MS;
-+}
-+
-+
-+static void ezx_ts_pen_touch_handler(void)
-+{
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_PRESSURE_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ ezx_ts_read_state = PRESSURE;
-+ ezxts.x_pre = 0;
-+ ezxts.y_pre = 0;
-+
-+ TS_DPRINTK("ezx_ts pen touch handler done.\n");
-+}
-+
-+static void ezx_ts_penup_timeout(unsigned long data)
-+{
-+ TS_DPRINTK("@@@\nIn pen drag! jiffies: %d\n@@@\n", jiffies);
-+ bSetPenupTimer = 0;
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_POSITION_XY_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+}
-+
-+static void ezx_ts_check_pen_samples(void)
-+{
-+ if ( (ezx_ts_read_state == COORDINATE) && (penSampleCount != 0 ) )
-+ {
-+ int k;
-+ if (penSampleCount < gPenSamplesNum)
-+ {
-+ for ( k = 0; k < (gPenSamplesNum - penSampleCount); k++)
-+ {
-+ ezx_ts_evt_add(PEN_DOWN, ezxts.x_cur, ezxts.y_cur);
-+ TS_DPRINTK("ezx_ts_add_additional_samples: %d\n", k);
-+ }
-+ }
-+ TS_DPRINTK("ezx_ts_evt_add: PEN_UP\n");
-+ //ezx_ts_evt_add(PEN_UP, 0, 0);
-+ }
-+
-+ if (bSetPenupTimer)
-+ {
-+ del_timer(&ezx_ts_penup_timer);
-+ bSetPenupTimer = 0;
-+ TS_DPRINTK("^^^^Delete penup timer1.\n");
-+ }
-+ penSampleCount = 0;
-+}
-+
-+static void ezx_ts_set_timer(struct timer_list *timer, void (*timer_timeout)(unsigned long),
-+ signed long timeout)
-+{
-+ init_timer(timer);
-+ timer->expires = timeout + jiffies;
-+ timer->data = (unsigned long) current;
-+ timer->function = timer_timeout;
-+
-+ add_timer(timer);
-+ //TS_DPRINTK("ezx_ts set timer done.\n");
-+}
-+
-+static void ezx_ts_evt_add(u16 pressure, u16 x, u16 y)
-+{
-+ int next_head;
-+ int last_head;
-+ /* if pen_up, then copy pressure=0, last_evt.x y to current evt*/
-+
-+ next_head = ezxts.evt_head + 1;
-+ if (next_head == TS_NR_EVENTS)
-+ {
-+ next_head = 0;
-+ }
-+
-+ last_head = ezxts.evt_head - 1;
-+ if (last_head == -1)
-+ {
-+ last_head = TS_NR_EVENTS - 1;
-+ }
-+
-+/* if (next_head != ezxts.evt_tail)*/
-+ //{
-+ if ( pressure == PEN_DOWN)
-+ {
-+/* if ( (penSampleCount >1) && ((penCurJiffies + EZX_TS_READ_MIN_SPACE) < jiffies))
-+ {
-+ // see two ~ four data or just ignore the data except the first one????
-+ return;
-+ }
-+ else*/
-+ //{
-+ ezxts.events[ezxts.evt_head].pressure = pressure;
-+ ezxts.events[ezxts.evt_head].x = x;
-+ ezxts.events[ezxts.evt_head].y = y;
-+ TS_DPRINTK("ezx_store: x: %d, y :%d, pressure: 0x%x\n", x, y, pressure);
-+ //}
-+ }
-+ else
-+ {
-+ ezxts.events[ezxts.evt_head].pressure = pressure;
-+ ezxts.events[ezxts.evt_head].x = ezxts.events[last_head].x;
-+ ezxts.events[ezxts.evt_head].y = ezxts.events[last_head].y;
-+ TS_DPRINTK("ezx_store: PEN_UP\n");
-+ }
-+ //}
-+// do_gettimeofday(&(ezxts.events[ezxts.evt_head].stamp));
-+ ezxts.evt_head = next_head;
-+
-+ if (ezxts.evt_head == ezxts.evt_tail)
-+ {
-+ if ( ++ezxts.evt_tail == TS_NR_EVENTS )
-+ ezxts.evt_tail = 0;
-+ }
-+
-+ if (ezxts.fasync)
-+ kill_fasync(&ezxts.fasync, SIGIO, POLL_IN);
-+ wake_up_interruptible(&ezxts.read_wait);
-+}
-+
-+static struct ts_event ezx_ts_get_onedata(void)
-+{
-+ int cur = ezxts.evt_tail;
-+
-+ if (++ezxts.evt_tail == TS_NR_EVENTS)
-+ ezxts.evt_tail = 0;
-+
-+ return ezxts.events[cur];
-+}
-+
-+/*****************************************************************************
-+ * FUNCTION NAME : ezx_ts_open()
-+ *
-+ * INPUTS:
-+ *
-+ * OUTPUTS: pen info from ts event structure
-+ *
-+ * VALUE RETURNED: none
-+ *
-+ * DESCRIPTION:
-+ * i) Increase this device module used count.
-+ * ii) Initialize a buffer for store data read from touch screen interface.
-+ * iii) Initialize touch screen interface hardware.
-+ * iv) Setup touch screen wait queue.
-+*****************************************************************************
-+ */
-+static int ezx_ts_open(struct inode *inode, struct file * filp)
-+{
-+ struct ezx_ts_info *ts = &ezxts;
-+
-+/* ssp_pcap_init(); // change to _start_kernel
-+ ssp_pcap_open(); */
-+ ssp_pcap_open(SSP_PCAP_TS_OPEN);
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+
-+ ezx_ts_init_penEvent();
-+ filp->private_data = ts;
-+
-+
-+ TS_DPRINTK("ezx touch screen driver opened\n");
-+ return 0;
-+}
-+
-+/* Decrease this device module used count. */
-+static int ezx_ts_release(struct inode *inode, struct file *filp)
-+{
-+ ezx_ts_init_penEvent();
-+ ezx_ts_fasync(-1, filp, 0);
-+
-+ TS_DPRINTK("ezx touch screen driver closed\n");
-+ return 0;
-+}
-+
-+/*****************************************************************************
-+ * FUNCTION NAME : ezx_ts_read
-+ *
-+ * INPUTS:
-+ *
-+ * OUTPUTS: pen info from ts event structure
-+ *
-+ * VALUE RETURNED: none
-+ *
-+ * DESCRIPTION:
-+ * This is used for UI app to call.
-+ * If device is opened by nonblock mode then copy available data from the ts event buffer
-+ * to user buffer and return the actual read data count, if device is opened by block mode
-+ * and no data available then sleep until the required data count be read completed.
-+ *
-+ * CAUTIONS:
-+ *
-+ *
-+ *****************************************************************************
-+ */
-+static ssize_t ezx_ts_read(struct file* filp, char* buffer, size_t count, loff_t *ppos)
-+{
-+ DECLARE_WAITQUEUE(wait, current);
-+
-+ struct ezx_ts_info *ts = filp->private_data;
-+ char *ptr = buffer;
-+ int err = 0;
-+ struct ts_event evt;
-+
-+ add_wait_queue(&ts->read_wait, &wait);
-+ while (count >= sizeof(struct ts_event))
-+ {
-+ err = -ERESTARTSYS;
-+ if (signal_pending(current))
-+ break;
-+ if ((ts)->evt_head != (ts)->evt_tail)
-+ {
-+ evt = ezx_ts_get_onedata(); /*evt_tail pos changed in this func*/
-+ err = copy_to_user(ptr, &evt, sizeof(struct ts_event));
-+
-+ if (err)
-+ break;
-+ //printk("ezx_ts_read: x:%d, y:%d, pressure:0x%x\n", evt.x, evt.y, evt.pressure);
-+ ptr += sizeof(struct ts_event);
-+ count -= sizeof(struct ts_event);
-+ continue;
-+ }
-+
-+ set_current_state(TASK_INTERRUPTIBLE);
-+ err = -EAGAIN;
-+ if (filp->f_flags & O_NONBLOCK)
-+ break;
-+ schedule();
-+ }
-+ current->state = TASK_RUNNING;
-+ remove_wait_queue(&(ts->read_wait), &wait);
-+
-+ return ptr == buffer ? err : ptr - buffer;
-+
-+}
-+
-+/*
-+This function is used in nonblock mode to determine whether it can read data from touch screen
-+device without blocking.
-+Call poll_wait to wait until read operation status changed then return POLLIN (flag of device can be
-+read without blocking) | POLLRDNORM (flag of data is available) bit mask if there is readable data
-+now.
-+*/
-+
-+static unsigned int ezx_ts_poll(struct file* filp, struct poll_table_struct * wait)
-+{
-+ struct ezx_ts_info *ts = filp->private_data;
-+ int ret = 0;
-+
-+ if ( ts != NULL)
-+ {
-+ TS_DPRINTK("ezx_ts_poll.\n");
-+ poll_wait(filp, &ts->read_wait, wait);
-+ if (ts->evt_head != ts->evt_tail)
-+ {
-+ TS_DPRINTK("ezx_ts_poll: ts->evt_head != ts->evt_tail\n");
-+ ret = POLLIN | POLLRDNORM;
-+ }
-+ }
-+
-+ return ret;
-+}
-+
-+/* Setup fasync queue for touch screen device. */
-+
-+static int ezx_ts_fasync(int fd, struct file* filp, int mode)
-+{
-+ struct ezx_ts_info *ts = filp->private_data;
-+
-+ if ( ts != NULL)
-+ {
-+ TS_DPRINTK("ezx_ts_fasync.\n");
-+ return fasync_helper(fd, filp, mode, &ts->fasync);
-+ }
-+ else return 0;
-+}
-+
-+static int
-+ezx_ts_ioctl(struct inode *inode, struct file *file, uint cmd, ulong arg)
-+{
-+ int res = 0;
-+
-+ TS_DPRINTK("ezx_ts_ioctl: arg is %d\n", arg);
-+ switch (cmd) {
-+/*
-+ case SETTONORMAL:
-+ TS_DPRINTK("ezx_ts_ioctl_test: This is SETTONORMAL.\n");
-+ gPenStyle = EZX_PEN_NORMAL;
-+ gPenSamplesNum = QT_ONEPEN_SAMPLES_NUM;
-+ //gHwrTimer = EZX_TS_HWR_TIMEOUT_MS;
-+ gCustomTimer = EZX_TS_CUSTOM_TIMEOUT_MS;
-+ break;
-+
-+ case SETTOHWR:
-+ TS_DPRINTK("ezx_ts_ioctl_test: This is SETTOHWR.\n");
-+ gPenStyle = EZX_PEN_HWR;
-+ gPenSamplesNum = HWR_ONEPEN_SAMPLES_NUM;
-+ if ( (arg > 0 ) && (arg < 100) )
-+ {
-+ gHwrTimer = arg;
-+ TS_DPRINTK("ezx_ts_ioctl_test: gHwrTimer is %d.\n", gHwrTimer);
-+ }
-+ break;
-+
-+ case SETTOCUSTOM:
-+ TS_DPRINTK("ezx_ts_ioctl_test: This is SETTOCUSTOM.\n");
-+ gPenStyle = EZX_PEN_CUSTOM;
-+ gPenSamplesNum = CUSTOM_ONEPEN_SAMPLES_NUM;
-+ if ( (arg > 0 ) && (arg < 100) )
-+ {
-+ gCustomTimer = arg;
-+ TS_DPRINTK("ezx_ts_ioctl_test: gCustomTimer is %d.\n", gCustomTimer);
-+ }
-+ break;
-+ case GETPENSTYLE:
-+ TS_DPRINTK("ezx_ts_ioctl_test: This is GETPENSTYLE.\n");
-+ put_user(gPenStyle, (u32*)arg);
-+ break;
-+ default:
-+ res = -EINVAL;
-+*/
-+ }
-+
-+ return res;
-+}
-+
-+/*****************************************************************************
-+ * FUNCTION NAME : ezx_ts_touch_interrupt
-+ *
-+ * INPUTS:
-+ *
-+ *
-+ * OUTPUTS:
-+ *
-+ *
-+ * VALUE RETURNED:
-+ *
-+ *
-+ * DESCRIPTION:
-+ * This is touch screen touch interrupt service routine called by PCAP module when touch screen
-+ * interrupt happened. First eliminate shake signal to get stable touch screen press information.
-+ * Then write instruction to PCAP register to read ADC conversion value of pressed spot x,y coordinate
-+ * and return.
-+ *
-+ * CAUTIONS:
-+ *
-+ *
-+ *
-+ *****************************************************************************
-+ */
-+void ezx_ts_touch_interrupt(int irq, void* dev_id, struct pt_regs *regs)
-+{
-+ TS_DPRINTK("ezx_ts_touch_irq happened.\n");
-+ ezx_ts_shake_samples_count = 0;
-+ //TS_DPRINTK("ezx_ts_touch_irq excuted.\n");
-+ ezx_ts_check_pen_samples();
-+ ezx_ts_pen_touch_handler();
-+
-+}
-+
-+/*****************************************************************************
-+ * FUNCTION NAME : ezx_ts_dataReadok_interrupt
-+ *
-+ * INPUTS: call PCAP API to read x,y
-+ *
-+ * OUTPUTS: Store the pen info to ts event structure
-+ *
-+ * VALUE RETURNED: none
-+ *
-+ * DESCRIPTION:
-+ * This is called by PCAP module to deal with the touch screen press raw information read from ADC
-+ * when ADC data conversion finished. It performs write the data to ts event buffer for user to
-+ * read out.
-+ *
-+ * CAUTIONS: Consider pen shake
-+ *
-+ *
-+ *****************************************************************************
-+ */
-+void ezx_ts_dataReadok_interrupt(int irq, void* dev_id, struct pt_regs *regs)
-+{
-+ static u16 pressure;
-+ u16 x;
-+ u16 y;
-+ U16 tempx,tempy;
-+
-+ if (SSP_PCAP_TSI_get_XY_value(&x, &y) != SSP_PCAP_SUCCESS)
-+ {
-+ return;
-+ }
-+ /* convert x,y???? */
-+ // TS_DPRINTK( "ezx_ts_get_XY_value: x:%d, y:%d\n",x, y);
-+ /* TS_DPRINTK( "\nezx_ts before convert: x:%d, y:%d\n",x, y);*/
-+
-+ if ( ezx_ts_read_state == PRESSURE)
-+ {
-+ if (( y >= TS_EDGE_MAX_LIMIT ) || (y <= TS_EDGE_MIN_LIMIT))
-+ {
-+ TS_DPRINTK("ezx_ts_datareadok_irq: PEN_UP.\n");
-+ pressure = PEN_UP;
-+ ezxts.cur_pressure = PEN_UP;
-+
-+ /*ezx_ts_check_pen_samples();*/
-+ if ( getPenUp == 0 )
-+ {
-+ ezx_ts_evt_add( pressure, 0, 0);
-+ }
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ return;
-+ }
-+ else
-+ {
-+ TS_DPRINTK("ezx_ts_datareadok_irq: PEN_DOWN.\n");
-+ getPenUp = 0;
-+ pressure = PEN_DOWN;
-+ ezxts.cur_pressure = PEN_DOWN;
-+ tspenSampleCount = 0;
-+ ezxts.x_pre = 0;
-+ ezxts.y_pre = 0;
-+ bFirstPen = 1 ;
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_POSITION_XY_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ ezx_ts_read_state = COORDINATE;
-+
-+ //TS_DPRINTK("ezx_ts_datareadok_irq: Begin read XY.\n");
-+ return;
-+ }
-+ }
-+ else if ( ezx_ts_read_state == COORDINATE)
-+ {/*
-+ u8 count;
-+
-+ count = 0;
-+ while ( (( x <= TS_EDGE_MIN_LIMIT)||( x >= TS_EDGE_MAX_LIMIT) ||
-+ ( y <= TS_EDGE_MIN_LIMIT)||( y >= TS_EDGE_MAX_LIMIT))
-+ && (count++ < 15) )
-+ {
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_POSITION_XY_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ }
-+ */
-+ if ( ( x <= TS_EDGE_MIN_LIMIT)||( x >= TS_EDGE_MAX_LIMIT) ||
-+ ( y <= TS_EDGE_MIN_LIMIT)||( y >= TS_EDGE_MAX_LIMIT) )
-+ { /* regard it as PEN_UP */
-+ pressure = PEN_UP;
-+ ezxts.cur_pressure = PEN_UP;
-+ x = 0;
-+ y = 0;
-+ tspenSampleCount = 0;
-+ SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_TSM);
-+ /*del_timer(&ezx_ts_read_timer);*/
-+ ezx_ts_check_pen_samples();
-+ ezx_ts_evt_add( pressure, 0, 0);
-+ /* SSP_PCAP_bit_clean( SSP_PCAP_ADJ_BIT_MSR_TSM);*/
-+ ezx_ts_read_state = PRESSURE;
-+ getPenUp = 1;
-+ TS_DPRINTK( "ezx_ts Invalid x,y position: PEN_UP?\n");
-+ return;
-+ }
-+ getPenUp = 0;
-+ penSampleCount++;
-+ //TS_DPRINTK("ezx_ts_datareadok_irq: Begin store XY %d.\n", penSampleCount);
-+
-+ if ( gPenStyle == EZX_PEN_CUSTOM )
-+ {
-+ if ( ((ezxts.x_pre == 0) && (ezxts.y_pre == 0))
-+ || ( (ezxts.x_pre != 0) && (ezxts.y_pre != 0)
-+ &&(!((abs(ezxts.x_pre - x) > X_DIFF) || (abs(ezxts.y_pre - y) > Y_DIFF))) )
-+ )
-+ {
-+ //TS_DPRINTK("ezx_ts_datareadok_irq: diff <= XY_DIFF.\n");
-+
-+ ezxts.x_pre = x;
-+ ezxts.y_pre = y;
-+
-+ TS_DPRINTK("ezx_ts_datareadok_irq:x_pre=%d,y_pre=%d\n", ezxts.x_pre, ezxts.y_pre);
-+ ezxts.x_cur = x;
-+ ezxts.y_cur = y;
-+ ezx_ts_evt_add(pressure, ezxts.x_cur, ezxts.y_cur);
-+ //printk("ezx_ts_datareadok_irq_custom add pressure0x%x,x_cur%d,y_cur%d\n",pressure,ezxts.x_cur,ezxts.y_cur);
-+ ezx_ts_custom_timer_start();
-+ }
-+ else
-+ {
-+ //TS_DPRINTK("ezx_ts_datareadok_irq: DIFF > XY_DIFF\n");
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_POSITION_XY_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ TS_DPRINTK("ezx_ts_datareadok_irq:x_pre=%d,y_pre=%d, x=%d,y=%d\n", ezxts.x_pre, ezxts.y_pre,x,y);
-+ }
-+
-+
-+ /*
-+ if ( ezx_ts_shake_samples_count < EZX_TS_SHAKE_SAMPLES )
-+ {
-+ ezx_ts_shake_samples[ezx_ts_shake_samples_count].x = x;
-+ ezx_ts_shake_samples[ezx_ts_shake_samples_count].y = y;
-+ ezx_ts_shake_samples[ezx_ts_shake_samples_count++].pressure = PEN_DOWN;
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_POSITION_XY_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ TS_DPRINTK("ezx_ts_read_shake_samples%d:x=%d,y=%d\n", ezx_ts_shake_samples_count,x,y);
-+ }
-+ if (ezx_ts_shake_samples_count >= EZX_TS_SHAKE_SAMPLES)
-+ {
-+ if ( (abs(ezx_ts_shake_samples[0].x - ezx_ts_shake_samples[1].x) > X_DIFF) ||
-+ (abs(ezx_ts_shake_samples[0].y - ezx_ts_shake_samples[1].y) > Y_DIFF) ||
-+ (abs(ezx_ts_shake_samples[1].x - ezx_ts_shake_samples[2].x) > X_DIFF) ||
-+ (abs(ezx_ts_shake_samples[1].y - ezx_ts_shake_samples[2].y) > Y_DIFF)
-+ )
-+ {
-+ // throw these data and re-read
-+ ezx_ts_shake_samples_count = 0;
-+ }
-+ else //save to ts_event queue
-+ {
-+ ezxts.x_pre = ezxts.x_cur;
-+ ezxts.y_pre = ezxts.y_cur;
-+ TS_DPRINTK("ezx_ts_datareadok_irq:x_pre=%d,y_pre=%d\n", ezxts.x_pre, ezxts.y_pre);
-+ ezxts.x_cur = (ezx_ts_shake_samples[0].x + ezx_ts_shake_samples[1].x + ezx_ts_shake_samples[2].x) / 3;
-+ ezxts.y_cur = (ezx_ts_shake_samples[0].y + ezx_ts_shake_samples[1].y + ezx_ts_shake_samples[2].y) / 3;;
-+ ezx_ts_shake_samples_count = 0;
-+ ezx_ts_evt_add(pressure, ezxts.x_cur, ezxts.y_cur);
-+ }
-+ ezx_ts_custom_timer_start();
-+ }
-+ */
-+ }
-+ else
-+ {
-+ /* ezxts.x_pre and ezxts.y_pre store the last position */
-+ tspenSampleCount ++;
-+ if(1 == tspenSampleCount)
-+ {
-+ ezxts.x_cur = x;
-+ ezxts.y_cur = y;
-+ if( 0 == bSetPenupTimer )
-+ {
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_POSITION_XY_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ }
-+ }
-+ else if (2 == tspenSampleCount)
-+ {
-+ tspenSampleCount = 0;
-+
-+ tempx = (ezxts.x_cur > x? ezxts.x_cur - x:x - ezxts.x_cur);
-+ tempy = (ezxts.y_cur > y? ezxts.y_cur - y:y - ezxts.y_cur);
-+ if(tempx <= X_DIFF && tempy <= Y_DIFF )
-+ {
-+ x = (x+ezxts.x_cur)/2;
-+ y = (y+ezxts.y_cur)/2;
-+ if( 1 == bFirstPen)
-+ {
-+ bFirstPen = 0;
-+ ezxts.x_pre = x;
-+ ezxts.y_pre = y;
-+ }
-+ tempx = ( ezxts.x_pre > x? ezxts.x_pre -x:x - ezxts.x_pre);
-+ tempy = ( ezxts.y_pre > y? ezxts.y_pre -y:y - ezxts.y_pre);
-+ if(tempx <= X_DIFF && tempy <= Y_DIFF )
-+ {
-+ tsDiscardDataCount = 0;
-+ if(tempx > MIN_X_HOLD || tempy > MIN_Y_HOLD)
-+ {
-+ ezxts.x_pre = x;
-+ ezxts.y_pre = y;
-+ }
-+ ezx_ts_evt_add(pressure, ezxts.x_pre, ezxts.y_pre);
-+ if ( bSetPenupTimer == 0 )
-+ {
-+ ezx_ts_set_timer(&ezx_ts_penup_timer, ezx_ts_penup_timeout,
-+ EZX_TS_PENSAMPLE_TIMEOUT_MS);
-+ TS_DPRINTK("ezx_ts_datareadok_irq: set timer pen sample\n");
-+ bSetPenupTimer = 1;
-+ }
-+ }
-+ else
-+ {
-+
-+ tsDiscardDataCount ++;
-+ if(tsDiscardDataCount > SAMPLE_COUNT_NOT_JUMPER)
-+ {
-+ tsDiscardDataCount = 0;
-+ ezxts.x_pre = x;
-+ ezxts.y_pre = y;
-+ ezx_ts_evt_add(pressure, ezxts.x_pre, ezxts.y_pre);
-+ if ( bSetPenupTimer == 0 )
-+ {
-+ ezx_ts_set_timer(&ezx_ts_penup_timer, ezx_ts_penup_timeout,
-+ EZX_TS_PENSAMPLE_TIMEOUT_MS);
-+ TS_DPRINTK("ezx_ts_datareadok_irq: set timer pen sample\n");
-+ bSetPenupTimer = 1;
-+ }
-+ }
-+ else if( 0 == bSetPenupTimer )
-+ {
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_POSITION_XY_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ }
-+ }
-+ }
-+ else
-+ {
-+ if( 0 == bSetPenupTimer )
-+ {
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_POSITION_XY_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ }
-+ }
-+ }
-+ else /* discard the case */
-+ {
-+ tspenSampleCount = 0;
-+ if( 0 == bSetPenupTimer )
-+ {
-+ SSP_PCAP_TSI_mode_set(PCAP_TS_POSITION_XY_MEASUREMENT);
-+ SSP_PCAP_TSI_start_XY_read();
-+ }
-+ }
-+ }
-+ /*if (penSampleCount >= gPenSamplesNum)
-+ {
-+ penSampleCount = 0;
-+ }*/
-+ //TS_DPRINTK("ezx_ts_datareadok_irq: read XY finished.\n");
-+ }
-+
-+}
-+
-+
-+static struct file_operations ezx_ts_fops = {
-+ .owner = THIS_MODULE,
-+ .read = ezx_ts_read,
-+ .poll = ezx_ts_poll,
-+ .open = ezx_ts_open,
-+ .release = ezx_ts_release,
-+ .fasync = ezx_ts_fasync,
-+ .ioctl = ezx_ts_ioctl,
-+};
-+
-+/*
-+ * miscdevice structure for misc driver registration.
-+ */
-+static struct miscdevice ezx_ts_dev =
-+{
-+ .minor = EZX_TS_MINOR_ID,
-+ .name = "ezx_ts",
-+ .fops = &ezx_ts_fops,
-+};
-+
-+/*Register touch screen device in misc devices.*/
-+static int ezx_ts_init(void)
-+{
-+ int ret;
-+
-+ init_waitqueue_head(&ezxts.read_wait);
-+ ret = misc_register(&ezx_ts_dev);
-+
-+ if (ret<0)
-+ {
-+ printk("ezx_ts_dev: failed to registering the device\n");
-+ }
-+ ezx_ts_custom_setup_timer();
-+
-+ TS_DPRINTK("ezx_ts_init done.\n");
-+ return ret;
-+}
-+
-+/*Unregister touch screen device.*/
-+static void ezx_ts_exit(void)
-+{
-+
-+ if (bSetPenupTimer)
-+ {
-+ del_timer(&ezx_ts_penup_timer);
-+ bSetPenupTimer = 0;
-+ }
-+
-+ ezx_ts_custom_timer_stop();
-+
-+ misc_deregister(&ezx_ts_dev);
-+
-+ TS_DPRINTK("ezx touch screen driver removed\n");
-+}
-+
-+module_init(ezx_ts_init);
-+module_exit(ezx_ts_exit);
-+
-+MODULE_DESCRIPTION("ezx touchscreen driver");
-+MODULE_LICENSE("GPL");
-Index: linux-2.6.16.5-a/drivers/misc/ezx/ezx-ts.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/ezx-ts.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,22 @@
-+/*
-+ * linux/drivers/char/ezx-ts.c
-+ *
-+ * Copyright (C) 2002 Lili Jiang, All Rights Reserved.
-+ *
-+ *
-+ * June, 2002 Lili Jiang, create
-+ */
-+
-+#ifndef _EZXTS_H
-+#define _EZXTS_H
-+
-+#define EZX_TS_MINOR_ID 14
-+
-+#define PEN_UP 0
-+#define PEN_DOWN 0xffff
-+
-+/* extern functio nfor PCAP */
-+void ezx_ts_touch_interrupt(int irq, void* dev_id, struct pt_regs *regs);
-+void ezx_ts_dataReadok_interrupt(int irq, void* dev_id, struct pt_regs *regs);
-+
-+#endif //_EZXTS_H
-Index: linux-2.6.16.5-a/drivers/misc/ezx/fmradio.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/fmradio.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,249 @@
-+/*
-+ * linux/drivers/i2c/fmradio.c
-+ *
-+ * Support for the Motorola Ezx A780 Development Platform.
-+ *
-+ * Author: Jay Jia
-+ * Created: Nov 25, 2003
-+ * Copyright: Motorola Inc.
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ */
-+#include <linux/tty.h>
-+#include <linux/init.h>
-+#include <linux/module.h>
-+#include <linux/poll.h>
-+#include <linux/miscdevice.h>
-+#include <linux/bitops.h>
-+#include <linux/param.h>
-+
-+#include <asm/hardware.h>
-+#include <asm/io.h>
-+#include <asm/irq.h>
-+#include <linux/pm.h>
-+#include <linux/apm_bios.h>
-+#include <asm/arch-pxa/irqs.h>
-+#include <linux/kernel.h>
-+#include <linux/sched.h>
-+#include <linux/string.h>
-+#include <linux/timer.h>
-+#include <linux/delay.h>
-+#include <linux/errno.h>
-+#include <linux/slab.h>
-+#include <linux/i2c.h>
-+#include <linux/videodev.h>
-+#include <linux/kdev_t.h>
-+#include <asm/semaphore.h>
-+
-+#include <linux/sound.h>
-+#include <linux/soundcard.h>
-+#include <asm/uaccess.h>
-+#include <asm/irq.h>
-+
-+#include "../../../sound/oss/ezx-common.h"
-+#include "fmradio.h"
-+
-+#define I2C_FMRADIO 0x81
-+
-+static int fmradio_adapter_attach(struct i2c_adapter *adap);
-+static int fmradio_detach(struct i2c_client *client);
-+static int fmradio_client_register(struct i2c_client *client);
-+static int fmradio_client_unregister(struct i2c_client *client);
-+/* ----------------------------------------------------------------------- */
-+static struct i2c_driver driver = {
-+ .owner = THIS_MODULE,
-+ .name = "fmradio driver",
-+ .id = I2C_FMRADIO,
-+ //.flags = I2C_DF_DUMMY,
-+ .attach_adapter = fmradio_adapter_attach,
-+ .detach_client = fmradio_detach,
-+};
-+
-+static struct i2c_adapter fmradio_adapter = {
-+ .owner = THIS_MODULE,
-+ .name = "fmradio adapter",
-+ .id = I2C_FMRADIO,
-+ .client_register = fmradio_client_register,
-+ .client_unregister = fmradio_client_unregister,
-+};
-+
-+static struct i2c_client client_template = {
-+ .name = "(unset)",
-+ .adapter = &fmradio_adapter,
-+};
-+
-+struct i2c_client *fmradio_client;
-+
-+static int fmradio_open(struct inode *inode, struct file *file)
-+{
-+ if( audioonflag & (DSP16_DEVICE|PHONE_DEVICE) ){
-+#ifdef EZX_OSS_DEBUG
-+ printk(EZXOSS_DEBUG "E680 open FM EBUSY because 0x%X device is using the sound hardware.\n",audioonflag );
-+#endif
-+ return -EBUSY;
-+ }
-+
-+
-+ poweron_mixer(FM_DEVICE);
-+ //MOD_INC_USE_COUNT;
-+
-+ return 0;
-+}
-+
-+static int fmradio_close(struct inode * inode, struct file *file)
-+{
-+ unsigned int flags;
-+ unsigned char standby[5] = {0x2a, 0x48, 0xa1, 0xdf, 0x40};
-+
-+ //MOD_DEC_USE_COUNT;
-+ //e680_boomer_path_tmp_mono_lineout (); //mute boomer
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_AUD_RX_AMPS_PGA_IN_SW);
-+
-+ local_irq_save(flags);
-+ enable_irq(IRQ_I2C);
-+ //write standby command
-+ i2c_master_send (fmradio_client, standby, 5);
-+ local_irq_restore(flags);
-+ shutdown_mixer(FM_DEVICE);
-+
-+ return 0;
-+}
-+
-+
-+static int fmradio_ioctl (struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg)
-+{
-+ return mixer_ioctl(inode, file, cmd, arg);
-+}
-+
-+static ssize_t fmradio_read(struct file *file, char *buf, size_t count, loff_t *ptr)
-+{
-+ char *tmp;
-+ int ret;
-+ unsigned int flags;
-+
-+ /* copy user space data to kernel space. */
-+ tmp = kmalloc(count,GFP_KERNEL);
-+ if (tmp==NULL)
-+ return -ENOMEM;
-+ local_irq_save(flags);
-+ enable_irq(IRQ_I2C);
-+ ret = i2c_master_recv(fmradio_client,tmp,count);
-+ local_irq_restore(flags);
-+ if (ret >= 0)
-+ copy_to_user(buf,tmp,count);
-+ kfree(tmp);
-+ return ret;
-+}
-+static ssize_t fmradio_write(struct file *file, const char *buf, size_t count, loff_t *ptr)
-+{
-+ int ret;
-+ char *tmp;
-+// char data[4]={0x18,0x7d,0xbd,0xcd};
-+// char freq[5]={0x2e,0x56,0x41,0x11,0x40};
-+// unsigned char s[5]={0, 0, 0, 0, 0};
-+
-+// mixer_write(data,4);
-+// i2c_master_send(fmradio_client,freq,5);
-+// printk("fmradio test code\n");
-+// mdelay(300);
-+// i2c_master_recv(fmradio_client, s, 5);
-+// printk("s0=%02x s1=%02x s2=%02x s3=%02x s4=%02x \n",s[0],s[1],s[2],s[3],s[4]);
-+
-+ unsigned int flags;
-+ /* copy user space data to kernel space. */
-+ tmp = kmalloc(count,GFP_KERNEL);
-+ if (tmp==NULL)
-+ return -ENOMEM;
-+ if (copy_from_user(tmp,buf,count)) {
-+ kfree(tmp);
-+ return -EFAULT;
-+ }
-+ local_irq_save(flags);
-+ enable_irq(IRQ_I2C);
-+ ret = i2c_master_send(fmradio_client,tmp,count);
-+ local_irq_restore(flags);
-+ kfree(tmp);
-+ return ret;
-+}
-+
-+static int fmradio_client_register(struct i2c_client *client)
-+{
-+
-+ return 0;
-+}
-+
-+static int fmradio_client_unregister(struct i2c_client *client)
-+{
-+
-+ return 0;
-+}
-+/* ----------------------------------------------------------------------- */
-+static struct file_operations fmradio_fops = {
-+ read: fmradio_read,
-+ write: fmradio_write,
-+ ioctl: fmradio_ioctl,
-+ open: fmradio_open,
-+ release: fmradio_close,
-+};
-+
-+static struct miscdevice fmradio_misc_device = {
-+ FMRADIO_MINOR,
-+ FMRADIO_NAME,
-+ &fmradio_fops,
-+};
-+
-+/* ----------------------------------------------------------------------- */
-+
-+static int fmradio_adapter_attach(struct i2c_adapter *adap)
-+{
-+ if(! (fmradio_client = kmalloc(sizeof(struct i2c_client),GFP_KERNEL)))
-+ return -ENOMEM;
-+ memcpy(fmradio_client,&client_template,sizeof(struct i2c_client));
-+ fmradio_client->adapter = adap;
-+
-+ fmradio_client->addr = 0x60;
-+
-+ printk("adapter %s\n",adap->name);
-+ i2c_attach_client(fmradio_client);
-+
-+ return 0;
-+}
-+
-+static int fmradio_detach(struct i2c_client *client)
-+{
-+ i2c_detach_client(fmradio_client);
-+ return 0;
-+}
-+/* ----------------------------------------------------------------------- */
-+
-+static int fmradio_init_module(void)
-+{
-+ int res;
-+
-+ res = i2c_add_driver(&driver);
-+ if( res < 0 )
-+ {
-+ printk("error in add fmradio i2c driver\n");
-+ return res;
-+ }
-+
-+ if (misc_register (&fmradio_misc_device))
-+ {
-+ printk(KERN_ERR "Couldn't register fmradio driver\n");
-+ return -EIO;
-+ }
-+ return 0;
-+}
-+
-+static void fmradio_cleanup_module(void)
-+{
-+ i2c_del_driver(&driver);
-+ misc_deregister(&fmradio_misc_device);
-+}
-+
-+module_init(fmradio_init_module);
-+module_exit(fmradio_cleanup_module);
-+MODULE_AUTHOR("Jay Jia");
-+MODULE_LICENSE("GPL");
-Index: linux-2.6.16.5-a/drivers/misc/ezx/fmradio.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/fmradio.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,7 @@
-+#ifndef __FMRADIO_H
-+#define __FMRADIO_H
-+
-+#define FMRADIO_NAME "fmradio"
-+#define FMRADIO_MINOR 198
-+
-+#endif
-Index: linux-2.6.16.5-a/drivers/misc/ezx/keylight.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/keylight.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,236 @@
-+/*
-+ * linux/drivers/misc/keylight.c --- key backlight driver on ezx
-+ *
-+ * Support for the Motorola Ezx A780 Development Platform.
-+ *
-+ * Author: Jay Jia
-+ * Created: Feb 16, 2004
-+ * Copyright: Motorola Inc.
-+ *
-+ * This program is free software; you can redistribute it and/or modify
-+ * it under the terms of the GNU General Public License version 2 as
-+ * published by the Free Software Foundation.
-+ */
-+#include <linux/kernel.h>
-+#include <linux/module.h>
-+#include <linux/fs.h>
-+#include <asm/hardware.h>
-+#include <asm/irq.h>
-+#include <linux/init.h>
-+#include <linux/miscdevice.h>
-+#include <linux/interrupt.h>
-+#include <linux/pm.h>
-+#include "keylight.h"
-+#include "ssp_pcap.h"
-+#include <linux/delay.h>
-+
-+static int keylight_open_cnt = 0;
-+static int main_current_brightness = 0xf;
-+static int aux_current_brightness = 0x1f;
-+
-+MODULE_LICENSE("GPL");
-+
-+#ifdef CONFIG_PM
-+static struct pm_dev *pm_dev;
-+#endif
-+
-+static int keylight_open(struct inode *inode,struct file *file)
-+{
-+ keylight_open_cnt++;
-+
-+ return 0;
-+}
-+
-+static int keylight_close(struct inode *inode,struct file *file)
-+{
-+ keylight_open_cnt--;
-+
-+ if ( keylight_open_cnt == 0 )
-+ {
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL0);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL1);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL2);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL3);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL4);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL0);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL1);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL2);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL3);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL4);
-+ }
-+
-+ return 0;
-+}
-+
-+static void keylight_main_turn_off(void)
-+{
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL0);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL1);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL2);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL3);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL4);
-+}
-+
-+static void keylight_aux_turn_off(void)
-+{
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL0);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL1);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL2);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL3);
-+ SSP_PCAP_bit_clean(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL4);
-+}
-+
-+static void keylight_main_turn_on(void)
-+{
-+ int i,count;
-+
-+ for( i=0; i<5; i++)
-+ {
-+ count = 1<<i;
-+ switch ( main_current_brightness & count )
-+ {
-+ case 1:
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL0);
-+ break;
-+ case 2:
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL1);
-+ break;
-+ case 4:
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL2);
-+ break;
-+ case 8:
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL3);
-+ break;
-+ case 16:
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_PERIPH_BL_CTRL4);
-+ break;
-+ default:
-+ break;
-+ }
-+ }
-+}
-+
-+static void keylight_aux_turn_on(void)
-+{
-+ int i,count;
-+
-+ for( i=0; i<5; i++)
-+ {
-+ count = 1<<i;
-+ switch ( aux_current_brightness & count )
-+ {
-+ case 1:
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL0);
-+ break;
-+ case 2:
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL1);
-+ break;
-+ case 4:
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL2);
-+ break;
-+ case 8:
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL3);
-+ break;
-+ case 16:
-+ SSP_PCAP_bit_set(SSP_PCAP_ADJ_BIT_PERIPH_BL2_CTRL4);
-+ break;
-+ default:
-+ break;
-+ }
-+ }
-+}
-+
-+static int keylight_ioctl(struct inode *inode,struct file *file,unsigned int cmd,unsigned long arg)
-+{
-+ int ret = 0;
-+
-+ switch( cmd )
-+ {
-+ case KEYLIGHT_MAIN_ON:
-+ keylight_main_turn_on();
-+ break;
-+ case KEYLIGHT_MAIN_OFF:
-+ keylight_main_turn_off();
-+ break;
-+ case KEYLIGHT_MAIN_SETTING:
-+ main_current_brightness = arg & 0x1f;
-+ break;
-+ case KEYLIGHT_AUX_ON:
-+ keylight_aux_turn_on();
-+ break;
-+ case KEYLIGHT_AUX_OFF:
-+ keylight_aux_turn_off();
-+ break;
-+ case KEYLIGHT_AUX_SETTING:
-+ ret = -EINVAL;
-+ break;
-+ default:
-+ break;
-+ }
-+
-+ return ret;
-+}
-+
-+#ifdef CONFIG_PM
-+static int ezx_keylight_pm_callback(struct pm_dev *pm_dev, pm_request_t req, void *data)
-+{
-+ switch(req)
-+ {
-+ case PM_SUSPEND:
-+ break;
-+ case PM_RESUME:
-+ break;
-+ default:
-+ break;
-+ }
-+ return 0;
-+}
-+#endif
-+
-+static struct file_operations keylight_fops = {
-+ .owner = THIS_MODULE,
-+ .ioctl = keylight_ioctl,
-+ .open = keylight_open,
-+ .release = keylight_close,
-+};
-+
-+static struct miscdevice keylight_dev = {
-+ KEYLIGHT_MINOR,
-+ "keylight",
-+ &keylight_fops,
-+};
-+
-+int init_keylight(void)
-+{
-+ int ret;
-+
-+ ret = misc_register(&keylight_dev);
-+ if( ret < 0 ){
-+ printk("Sorry,registering the keylight device failed.\n");
-+ return ret;
-+ }
-+#ifdef CONFIG_PM
-+ pm_dev = pm_register(PM_SYS_DEV, 0, ezx_keylight_pm_callback);
-+#endif
-+#if 0
-+ for(ret=0;ret<32;ret++)
-+ {
-+ aux_current_brightness=ret;
-+ keylight_aux_turn_on();
-+ main_current_brightness=ret;
-+ keylight_main_turn_on();
-+ mdelay(2000);
-+ }
-+#endif
-+ return 0;
-+}
-+void clean_keylight(void)
-+{
-+ misc_deregister(&keylight_dev);
-+#ifdef CONFIG_PM
-+ pm_unregister(pm_dev);
-+#endif
-+}
-+
-+module_init(init_keylight);
-+module_exit(clean_keylight);
-Index: linux-2.6.16.5-a/drivers/misc/ezx/keylight.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/keylight.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,20 @@
-+#ifndef KEYLIGHT_H
-+#define KEYLIGHT_H
-+
-+#ifdef __cplusplus
-+extern "C" {
-+#endif
-+
-+#define KEYLIGHT_MINOR 168
-+#define KEYLIGHT_MAIN_ON 0xf0
-+#define KEYLIGHT_AUX_ON 0xf1
-+#define KEYLIGHT_MAIN_OFF 0xf2
-+#define KEYLIGHT_AUX_OFF 0xf3
-+#define KEYLIGHT_MAIN_SETTING 0xf4
-+#define KEYLIGHT_AUX_SETTING 0xf5
-+
-+#ifdef __cplusplus
-+}
-+#endif
-+#endif
-+
-Index: linux-2.6.16.5-a/drivers/misc/ezx/keypad-e398.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/keypad-e398.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,1497 @@
-+/*
-+ * linux/drivers/char/keypad.c
-+ *
-+ * (c) Copyright Motorola 2003, All rights reserved.
-+ */
-+
-+/*
-+ * This driver is for three devices: /dev/keypad, /dev/keypadB and
-+ * /dev/keypadI.
-+ * /dev/keypad would be used for reading the key event buffer.
-+ * It can be opened by one process at a time.
-+ * /dev/keypadB would be used for ioctl(KEYPAD_IOC_GETBITMAP).
-+ * It can be opened by one process at a time.
-+ * /dev/keypadI would be used for ioctl(KEYPAD_IOC_INSERT_EVENT).
-+ * It can be opened any number of times simultaneously.
-+ *
-+ * The bulverde specification is ambiguous about when interrupts happen
-+ * for released keys. We were told by Intel that we won't
-+ * get interrupts for released keys except in the case when multiple
-+ * keys were down and they've all been released. So we implemented
-+ * a timer to poll for changes in key states.
-+ *
-+ * The E680 P2 hardware gives us interrupts when any key is released,
-+ * whether it was the only key down or not, and whether it's the last
-+ * of multiple keys to be released or not. We don't know whether this
-+ * behavior will continue in future hardware releases, so the release
-+ * timer is still in the code, #ifdef'd with USE_RELEASE_TIMER. On the
-+ * P2 hardware, the code works with or without USE_RELEASE_TIMER defined.
-+ * If the release interrupts are always going to happen, we can remove
-+ * the #ifdef'd code.
-+ *
-+ * With the P2 hardware, the power key bit in the KPDK register is always
-+ * on. We don't know if this is correct behavior or not, but in any case
-+ * it certainly causes trouble to have that key autorepeating indefinitely,
-+ * or to be checking indefinitely for the key to be released (if we're doing
-+ * release polling).
-+ *
-+ * For now, any_keys_down() returns 0 if the power key is the only one down.
-+ * . At interrupt time, if the power key is the only one down we don't
-+ * set the autorepeat timer or release timer.
-+ * . When the release timer goes off, if the power key is the only one
-+ * still down we don't set the timer again.
-+ * . When the autorepeat timer goes off, if the power key is the only
-+ * one down we don't generate any events.
-+ * In autorepeat_timer_went_off, if there are non-power keys down, while we're
-+ * looking through the whole bitmap of keys down we ignore the power key.
-+ */
-+
-+#include <linux/tty.h>
-+#include <linux/init.h>
-+#include <linux/module.h>
-+#include <linux/poll.h>
-+#include <linux/miscdevice.h>
-+#include <linux/bitops.h>
-+#include <linux/param.h>
-+
-+#include <asm/hardware.h>
-+#include <asm/io.h>
-+#include <asm/irq.h>
-+#include <linux/pm.h>
-+#include <linux/apm_bios.h>
-+#include "keypad.h"
-+#include <asm/arch/irqs.h>
-+#include "asm/arch/ezx.h"
-+
-+#ifdef CONFIG_PM
-+static struct pm_dev *pm_dev;
-+static struct pm_dev *keypadI_pm_dev;
-+static int kpc_res,kpkdi_res;
-+static int GPIO_TC_MM_STATE = 1;
-+extern unsigned char pxafb_ezx_getLCD_status(void);
-+#endif
-+/*
-+ * This is the number of microseconds we wait before checking to see if any
-+ * keys have been released.
-+ */
-+#define RDELAY 200
-+
-+#define KEYBUF_EMPTY() (keybuf_start == keybuf_end)
-+#define KEYBUF_FULL() ( ((keybuf_end+1)%KEYBUF_SIZE) == keybuf_start)
-+#define KEYBUF_INC(x) ((x) = (((x)+1) % KEYBUF_SIZE))
-+
-+static int keypad_open (struct inode *, struct file *);
-+static int keypad_close (struct inode *, struct file *);
-+static int keypad_ioctl (struct inode *, struct file *,
-+ unsigned int, unsigned long);
-+static unsigned int keypad_poll (struct file *, poll_table *);
-+static ssize_t keypad_read (struct file *, char *, size_t, loff_t *);
-+
-+static int keypadB_open (struct inode *, struct file *);
-+static int keypadB_close (struct inode *, struct file *);
-+static int keypadB_ioctl (struct inode *, struct file *,
-+ unsigned int, unsigned long);
-+static unsigned int keypadB_poll (struct file *, poll_table *);
-+
-+static int keypadI_open(struct inode *, struct file *);
-+static int keypadI_close(struct inode *, struct file *);
-+static int keypadI_ioctl (struct inode *, struct file *,
-+ unsigned int, unsigned long);
-+
-+static void kp_interrupt (int, void *, struct pt_regs *);
-+#ifdef USE_RELEASE_TIMER
-+static void release_timer_went_off (unsigned long);
-+static void do_scan(void);
-+#endif
-+static void autorepeat_timer_went_off (unsigned long);
-+
-+static int add_to_keybuf (unsigned short);
-+static int add_events (unsigned long *, unsigned long *);
-+static int insert_event (unsigned short);
-+static unsigned short get_from_keybuf (void);
-+static void scan_to_bitmap
-+ (unsigned long, unsigned long, unsigned long, unsigned long *);
-+static inline void set_bitmap_to_zero(unsigned long b[]);
-+static inline void copy_bitmap(unsigned long dest[], unsigned long source[]);
-+static inline void turn_on_bit(unsigned long map[], int);
-+static inline void turn_off_bit(unsigned long map[], int);
-+static inline int any_keys_down (unsigned long *);
-+
-+/*
-+ * keybuf is a circular buffer to hold keypad events.
-+ * keybuf_start is the index of the first event.
-+ * keybuf_end is one more than the index of the last event.
-+ * The buffer is empty when keybuf_start == keybuf_end.
-+ * We only use KEYBUF_SIZE-1 entries in the buffer so we can tell
-+ * when it's full without needing another variable to tell us.
-+ * The buffer is full when (keybuf_end+1)%KEYBUF_SIZE == keybuf_start.
-+ */
-+static unsigned short keybuf[KEYBUF_SIZE];
-+static int keybuf_start = 0;
-+static int keybuf_end = 0;
-+
-+static DECLARE_WAIT_QUEUE_HEAD(keypad_wait);
-+static spinlock_t keypad_lock = SPIN_LOCK_UNLOCKED;
-+
-+static int reading_opens = 0;
-+static int bitmap_opens = 0;
-+
-+/* previous bitmap of keys down */
-+static unsigned long oldkeybitmap[NUM_WORDS_IN_BITMAP];
-+/* current bitmap of keys down */
-+static unsigned long keybitmap[NUM_WORDS_IN_BITMAP];
-+/* last bitmap read by ioctl */
-+static unsigned long lastioctlbitmap[NUM_WORDS_IN_BITMAP];
-+
-+static unsigned long kpas = 0; /* last value of kpas */
-+static unsigned long kpasmkp0 = 0; /* last value of kpasmkp0 */
-+static unsigned long kpasmkp1 = 0; /* last value of kpasmkp1 */
-+static unsigned long kpasmkp2 = 0; /* last value of kpasamkp2*/
-+static unsigned long kpdk = 0; /* last value of kpdk */
-+
-+#ifdef USE_RELEASE_TIMER
-+static struct timer_list key_release_timer;
-+static int key_release_interval = RDELAY * HZ/1000;
-+#endif
-+
-+static int do_autorepeat = 1;
-+static long jiffies_to_first_repeat = 30;
-+static long jiffies_to_next_repeat = 30;
-+static struct timer_list autorepeat_timer;
-+
-+extern int lockscreen_flag;
-+
-+static int
-+keypad_open(struct inode *inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG "keypad_open\n");
-+#endif
-+ spin_lock(keypad_lock);
-+ if (reading_opens > 0)
-+ {
-+ spin_unlock(keypad_lock);
-+ return -EBUSY;
-+ }
-+ reading_opens++;
-+ spin_unlock(keypad_lock);
-+
-+ return 0;
-+}
-+
-+static int
-+keypadB_open(struct inode *inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG "keypadB_open\n");
-+#endif
-+ spin_lock(keypad_lock);
-+ if (bitmap_opens > 0)
-+ {
-+ spin_unlock(keypad_lock);
-+ return -EBUSY;
-+ }
-+ bitmap_opens++;
-+ /*
-+ * poll returns when lastioctlbitmap is different from keybitmap.
-+ * we set lastioctlbitmap to keybitmap here so that a poll right
-+ * after an open returns when the bitmap is different from when
-+ * the open was done, not when the bitmap is different from the
-+ * last time some other process read it
-+ */
-+ copy_bitmap(lastioctlbitmap, keybitmap);
-+ spin_unlock(keypad_lock);
-+
-+ return 0;
-+}
-+
-+#if defined(CONFIG_KEYPAD_E680)
-+#ifdef CONFIG_PM
-+static int keypadI_pm_callback(struct pm_dev *pm_dev, pm_request_t req, void *data)
-+{
-+ switch(req)
-+ {
-+ case PM_SUSPEND:
-+ break;
-+ case PM_RESUME:
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ if(GPIO_TC_MM_STATE == 1)
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ else
-+ GPCR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ break;
-+ default:
-+ break;
-+ }
-+ return 0;
-+}
-+#endif
-+#endif
-+
-+static int
-+keypadI_open(struct inode *inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG "keypadI_open\n");
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ pxa_gpio_mode(GPIO_TC_MM_EN);
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+#endif
-+
-+ return 0;
-+}
-+
-+static int
-+keypad_close(struct inode * inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_close\n");
-+#endif
-+ /*
-+ * this decrement of reading_opens doesn't have to be protected because
-+ * it can only be executed to close the single open of /dev/keypad
-+ */
-+ reading_opens--;
-+ return 0;
-+}
-+
-+static int
-+keypadB_close(struct inode * inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypadB_close\n");
-+#endif
-+ /*
-+ * this decrement of bitmap_opens doesn't have to be protected because
-+ * it can only be executed to close the single open of /dev/keypadB
-+ */
-+ bitmap_opens--;
-+ return 0;
-+}
-+
-+static int
-+keypadI_close(struct inode * inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypadI_close\n");
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ pxa_gpio_mode(GPIO_TC_MM_EN);
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+#endif
-+
-+ return 0;
-+}
-+
-+/**
-+ * Add the specified event to the key buffer.
-+ * This should be called with keypad_lock locked.
-+ */
-+static int
-+add_to_keybuf (unsigned short event)
-+{
-+ if (KEYBUF_FULL())
-+ {
-+ return -ENOMEM;
-+ }
-+
-+ keybuf[keybuf_end] = event;
-+ KEYBUF_INC (keybuf_end);
-+
-+#if CONFIG_APM
-+ queue_apm_event(KRNL_KEYPAD, NULL);
-+#endif
-+ printk("add keypad event = %x\n", event);
-+ return 0;
-+}
-+
-+/*
-+ * code[c*8+r] is the key code for the key that's down when there's a 1
-+ * in column c, row r of the scan registers.
-+ */
-+
-+#if defined(CONFIG_KEYPAD_V700)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_UP, KEYPAD_DOWN, KEYPAD_LEFT, KEYPAD_RIGHT,
-+ KEYPAD_POUND, KEYPAD_0, KEYPAD_9, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_2, KEYPAD_4, KEYPAD_6, KEYPAD_8,
-+ KEYPAD_7, KEYPAD_SLEFT, KEYPAD_SRIGHT, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_MENU, KEYPAD_1, KEYPAD_3, KEYPAD_5,
-+ KEYPAD_STAR, KEYPAD_VOLUP, KEYPAD_VOLDOWN, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_CAMERA, KEYPAD_CLEAR, KEYPAD_CARRIER, KEYPAD_ACTIVATE,
-+ KEYPAD_SEND, KEYPAD_SMART, KEYPAD_VAVR, KEYPAD_NONE
-+};
-+
-+/* end CONFIG_KEYPAD_V700 */
-+#elif defined(CONFIG_E680_P4A)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_UP, KEYPAD_DOWN, KEYPAD_LEFT, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_RIGHT, KEYPAD_CENTER, KEYPAD_HOME, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_GAME_R, KEYPAD_NONE, KEYPAD_GAME_L, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_A, KEYPAD_B, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+};
-+
-+/* end CONFIG_E680_P4A */
-+#elif defined(CONFIG_KEYPAD_E680)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_UP, KEYPAD_DOWN, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_RIGHT, KEYPAD_LEFT, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_NONE, KEYPAD_GAME_R, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_HOME, KEYPAD_GAME_L, KEYPAD_CENTER, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+
-+};
-+/*end CONFIG_KEYPAD_E680 */
-+#elif defined(CONFIG_KEYPAD_A780)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_OK, KEYPAD_1, KEYPAD_4, KEYPAD_7,
-+ KEYPAD_STAR, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_MENU, KEYPAD_2, KEYPAD_5, KEYPAD_8,
-+ KEYPAD_0, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_CANCEL, KEYPAD_3, KEYPAD_6, KEYPAD_9,
-+ KEYPAD_POUND, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_JOG_UP, KEYPAD_JOG_MIDDLE, KEYPAD_PTT, KEYPAD_HOME,
-+ KEYPAD_JOG_DOWN, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 4 */
-+ KEYPAD_UP, KEYPAD_CENTER, KEYPAD_LEFT, KEYPAD_RIGHT,
-+ KEYPAD_DOWN, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+};
-+#endif
-+
-+/*
-+ * Decode the specified scan register values into the bitmap pointed
-+ * to by the last argument. The bitmap will contain a 1
-+ * for each key that's down.
-+ *
-+ * Only the 1st two of the four scan registers are used.
-+ */
-+static void
-+scan_to_bitmap(unsigned long kpas, unsigned long kpasmkp0,
-+ unsigned long kpasmkp1, unsigned long bitmap[])
-+{
-+ int row, col;
-+ int bitnum;
-+ unsigned long scanmap;
-+#if defined(CONFIG_KEYPAD_A780)
-+ int keep;
-+#endif
-+
-+ set_bitmap_to_zero (bitmap);
-+
-+ if ((kpas & KPAS_MUKP) == MUKP_NO_KEYS)
-+ {
-+ return;
-+ }
-+
-+ if ((kpas & KPAS_MUKP) == MUKP_ONE_KEY)
-+ {
-+ row = (kpas & KPAS_RP) >> 4;
-+ col = kpas & KPAS_CP;
-+ turn_on_bit (bitmap, scanbit_to_keycode[col*8 + row]);
-+ return;
-+ }
-+
-+ /* reach here if multiple keys */
-+ scanmap = (kpasmkp0 & 0x7f) | ((kpasmkp0 & 0x7f0000) >> 8) |
-+ ((kpasmkp1 & 0x7f) << 16) | ((kpasmkp1 & 0x7f0000) << 8);
-+ while ((bitnum = ffs(scanmap)) != 0)
-+ {
-+ /*
-+ * ffs returns bit numbers starting with 1, so subtract 1 to index
-+ * into scanbit_to_keycode[]
-+ */
-+ turn_on_bit (bitmap, scanbit_to_keycode[bitnum-1]);
-+ scanmap &= ~(1<<(bitnum-1));
-+ }
-+#if defined(CONFIG_KEYPAD_A780)
-+ kpasmkp2 = KPASMKP2;
-+ printk("kpasmkp0 = 0x\n", kpasmkp0);
-+ printk("kpasmkp1 = 0x\n", kpasmkp1);
-+ printk("kpasmkp2 = 0x\n", kpasmkp2);
-+ if( (kpasmkp2 != 1) || (kpasmkp2 != 2) | (kpasmkp2 != 4) | (kpasmkp2 != 8) | (kpasmkp2 != 16) )
-+ return;
-+ while ((bitnum = ffs(kpasmkp2)) !=0)
-+ {
-+ turn_on_bit (bitmap, scanbit_to_keycode[32+bitnum-1]);
-+ kpasmkp2 &= ~(1<<(bitnum-1));
-+ }
-+#endif
-+}
-+
-+/*
-+ * Add events indicated by the difference between the last scan (oldbitmap)
-+ * and this one (newbitmap) to the input buffer.
-+ * Return nonzero right away if any of the events can't be added.
-+ * A zero return means all the events were added.
-+ * This should be called with keypad_lock locked.
-+ */
-+static int
-+add_events (unsigned long *oldbitmap, unsigned long *newbitmap)
-+{
-+ unsigned long tmpmap, onebitmap;
-+ int bitnum, i, ret;
-+
-+ /* generate events for keys that were down before and are up now */
-+ for (i=NUM_WORDS_IN_BITMAP-1;i>=0;i--)
-+ {
-+ tmpmap = oldbitmap[i];
-+ while ((bitnum = ffs(tmpmap)) != 0)
-+ {
-+ onebitmap = 1<<(bitnum-1);
-+ if ((newbitmap[i] & onebitmap) == 0)
-+ {
-+ ret = add_to_keybuf(bitnum + (32*(NUM_WORDS_IN_BITMAP-1-i) | KEYUP));
-+ if (ret < 0)
-+ {
-+ return ret;
-+ }
-+ }
-+ tmpmap &= ~onebitmap;
-+ }
-+ }
-+ /* generate events for down keys that were up before */
-+ for (i=NUM_WORDS_IN_BITMAP-1;i>=0;i--)
-+ {
-+ tmpmap = newbitmap[i];
-+ while ((bitnum = ffs(tmpmap)) != 0)
-+ {
-+ onebitmap = 1<<(bitnum-1);
-+ if ((oldbitmap[i] & onebitmap) == 0)
-+ {
-+ ret = add_to_keybuf
-+ (bitnum + (32*(NUM_WORDS_IN_BITMAP-1-i) | KEYDOWN));
-+ if (ret < 0)
-+ {
-+ return ret;
-+ }
-+ }
-+ tmpmap &= ~onebitmap;
-+ }
-+ }
-+ return 0;
-+}
-+
-+/*
-+ * do the INSERT_EVENT ioctl
-+ */
-+static int
-+insert_event (unsigned short event)
-+{
-+ unsigned long flags;
-+ int ret;
-+
-+ if (KEYCODE(event) > KEYPAD_MAXCODE)
-+ {
-+ printk(KERN_WARNING " inserted key code %d too big\n",
-+ KEYCODE(event));
-+ return -EINVAL;
-+ }
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ if (KEY_IS_DOWN(event))
-+ {
-+ turn_on_bit(keybitmap, KEYCODE(event));
-+ }
-+ else
-+ {
-+ turn_off_bit (keybitmap, event);
-+ }
-+ if ((ret = add_to_keybuf(event)) < 0)
-+ {
-+ spin_unlock_irqrestore(&keypad_lock,flags);
-+ return ret;
-+ }
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ wake_up_interruptible (&keypad_wait);
-+ return 0;
-+}
-+
-+static int
-+keypad_ioctl (struct inode *inode, struct file *file,
-+ unsigned int cmd, unsigned long arg)
-+{
-+ int interval; /* debounce interval */
-+ int imkp; /* Ignore Multiple Key Press bit */
-+ struct autorepeatinfo ar; /* autorepeat information */
-+
-+#ifdef KDEBUG
-+ printk (KERN_DEBUG "keypad_ioctl: 0x%x\n", cmd);
-+#endif
-+ switch (cmd)
-+ {
-+ case KEYPAD_IOC_INSERT_EVENT:
-+ return insert_event ((unsigned short)arg);
-+ break;
-+ case KEYPAD_IOC_GET_DEBOUNCE_INTERVAL:
-+ interval = KPKDI & KPKDI_BITS;
-+ return put_user(interval, (unsigned long *)arg);
-+ break;
-+ case KEYPAD_IOC_SET_DEBOUNCE_INTERVAL:
-+ interval = (unsigned short)arg;
-+ if (interval > KPKDI_BITS)
-+ {
-+ return -EINVAL;
-+ }
-+ KPKDI &= ~KPKDI_BITS;
-+ KPKDI |= interval;
-+ break;
-+ case KEYPAD_IOC_GET_IMKP_SETTING:
-+ imkp = ((KPC & KPC_IMKP) == KPC_IMKP);
-+ return put_user(imkp, (unsigned char *)arg);
-+ break;
-+ case KEYPAD_IOC_SET_IMKP_SETTING:
-+ imkp = (unsigned char)arg;
-+ if (imkp)
-+ {
-+ KPC |= KPC_IMKP;
-+ }
-+ else
-+ {
-+ KPC &= ~KPC_IMKP;
-+ }
-+ break;
-+ case KEYPAD_IOC_SET_AUTOREPEAT:
-+ if (copy_from_user (&ar, (void *)arg,
-+ sizeof(struct autorepeatinfo)) != 0)
-+ {
-+ return -EFAULT;
-+ }
-+ do_autorepeat = ar.r_repeat;
-+ /* times are specified in milliseconds; convert to jiffies */
-+ jiffies_to_first_repeat = ar.r_time_to_first_repeat * HZ/1000;
-+ jiffies_to_next_repeat = ar.r_time_between_repeats * HZ/1000;
-+ break;
-+ default:
-+ return -ENOTTY;
-+ }
-+ return 0;
-+}
-+
-+static int
-+keypadB_ioctl (struct inode *inode, struct file *file,
-+ unsigned int cmd, unsigned long arg)
-+{
-+ unsigned long flags;
-+ int ret;
-+
-+#ifdef KDEBUG
-+ printk (KERN_DEBUG "keypadB_ioctl: 0x%x\n", cmd);
-+#endif
-+ if (cmd == KEYPAD_IOC_INSERT_EVENT)
-+ {
-+ return insert_event ((unsigned short)arg);
-+ }
-+ else if (cmd == KEYPAD_IOC_GETBITMAP)
-+ {
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ ret = copy_to_user ((void *)arg, keybitmap,
-+ NUM_WORDS_IN_BITMAP * sizeof(unsigned long));
-+ copy_bitmap (lastioctlbitmap, keybitmap);
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return (ret != 0) ? -EFAULT : 0;
-+ }
-+ else
-+ {
-+ return -ENOTTY;
-+ }
-+}
-+
-+static int
-+keypadI_ioctl (struct inode *inode, struct file *file,
-+ unsigned int cmd, unsigned long arg)
-+{
-+ unsigned long flags;
-+ int ret;
-+
-+#ifdef KDEBUG
-+ printk (KERN_DEBUG "keypadI_ioctl: 0x%x\n", cmd);
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ if( cmd == KEYPADI_TURN_ON_LED )
-+ {
-+ GPCR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ GPIO_TC_MM_STATE = 0;
-+ PGSR3 &= ~GPIO_bit(GPIO_TC_MM_EN);
-+ return 0;
-+ }
-+ if( cmd == KEYPADI_TURN_OFF_LED )
-+ {
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ GPIO_TC_MM_STATE = 1;
-+ PGSR3 |= GPIO_bit(GPIO_TC_MM_EN);
-+ return 0;
-+ }
-+#endif
-+
-+ if (cmd == KEYPAD_IOC_INSERT_EVENT)
-+ {
-+ return insert_event ((unsigned short)arg);
-+ }
-+ else if (cmd == KEYPAD_IOC_GETBITMAP)
-+ {
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ ret = copy_to_user ((void *)arg, keybitmap,
-+ NUM_WORDS_IN_BITMAP * sizeof(unsigned long));
-+ copy_bitmap (lastioctlbitmap, keybitmap);
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return (ret != 0) ? -EFAULT : 0;
-+ }
-+ else
-+ {
-+ return -ENOTTY;
-+ }
-+}
-+
-+static unsigned int
-+keypad_poll( struct file *file, poll_table * wait )
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_poll\n");
-+#endif
-+ poll_wait(file, &keypad_wait, wait);
-+
-+ if (!KEYBUF_EMPTY())
-+ {
-+ return (POLLIN | POLLRDNORM);
-+ }
-+ return 0;
-+}
-+
-+static unsigned int
-+keypadB_poll( struct file *file, poll_table * wait )
-+{
-+ int i;
-+
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypadB_poll\n");
-+#endif
-+ poll_wait(file, &keypad_wait, wait);
-+
-+ for (i=0; i < NUM_WORDS_IN_BITMAP; i++)
-+ {
-+ if (lastioctlbitmap[i] != keybitmap[i])
-+ {
-+ return (POLLIN | POLLRDNORM);
-+ }
-+ }
-+ return 0;
-+}
-+
-+static unsigned short
-+get_from_keybuf(void)
-+{
-+ unsigned short event;
-+ unsigned long flags;
-+
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ event = keybuf[keybuf_start];
-+ KEYBUF_INC (keybuf_start);
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return event;
-+}
-+
-+static ssize_t
-+keypad_read(struct file *file, char *buf, size_t count, loff_t *ptr)
-+{
-+ int i, ret;
-+ unsigned short event;
-+
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_read\n");
-+#endif
-+ /* Can't seek (pread) on this device */
-+ if (ptr != &file->f_pos)
-+ {
-+ return -ESPIPE;
-+ }
-+
-+ if (count == 0)
-+ {
-+ return 0;
-+ }
-+
-+ if (KEYBUF_EMPTY())
-+ {
-+ /* buffer is empty */
-+ /* if not blocking return */
-+ if (file->f_flags & O_NONBLOCK)
-+ {
-+ return -EAGAIN;
-+ }
-+ /* blocking, so wait for input */
-+ ret = wait_event_interruptible(keypad_wait, !KEYBUF_EMPTY());
-+ if (ret)
-+ {
-+ return ret;
-+ }
-+ }
-+
-+ i = 0;
-+ /* copy events until we have what the user asked for or we run out */
-+ while ((i+1 < count) && !KEYBUF_EMPTY())
-+ {
-+ event = get_from_keybuf();
-+ if ((ret = put_user(event, (unsigned short *)buf)) != 0)
-+ {
-+ return ret;
-+ }
-+ buf += EVENTSIZE;
-+ i += EVENTSIZE;
-+ }
-+ return i;
-+}
-+
-+#ifdef CONFIG_PM
-+static int button_pm_callback(struct pm_dev *pm_dev, pm_request_t req, void *data)
-+{
-+ int pksr;
-+
-+ pksr = PKSR;
-+ PKSR = 0xfffff;
-+ switch(req)
-+ {
-+ case PM_SUSPEND:
-+ kpc_res = KPC;
-+ kpkdi_res = KPKDI;
-+ set_bitmap_to_zero (oldkeybitmap);
-+ set_bitmap_to_zero (keybitmap);
-+ set_bitmap_to_zero (lastioctlbitmap);
-+ kpas = 0;
-+ kpasmkp0 = 0;
-+ kpasmkp1 = 0;
-+ kpasmkp2 = 0;
-+ kpdk = 0;
-+ break;
-+ case PM_RESUME:
-+ KPC = kpc_res;
-+ KPKDI = kpkdi_res;
-+#if CONFIG_APM
-+#if defined(CONFIG_E680_P4A)
-+ if (pksr & 0xe4400) /*93 97 100 101 102 key is pressed (switch on) */
-+ {
-+ queue_apm_event(KRNL_KEYPAD, NULL);
-+ if (pksr & 0x400)
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ if (pksr & 0xee400) /*93 96 97 98 190 101 102 key is pressed */
-+ {
-+ queue_apm_event(KRNL_KEYPAD, NULL);
-+ if (pksr & 0x400)
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ if (pksr & 0x2000)
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ if (pksr & 0x8000)
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+#endif
-+#if defined(CONFIG_KEYPAD_A780)
-+ printk("pksr = %x\n",pksr);
-+ if (pksr & 0xec400) /* 93 97 98 100 101 102 key is pressed */
-+ {
-+ queue_apm_event(KRNL_KEYPAD, NULL);
-+ if (pksr & 0x400)
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+#endif
-+
-+ break;
-+ }
-+ return 0;
-+}
-+#endif
-+
-+/* for /dev/keypad */
-+static struct file_operations
-+keypad_fops = {
-+ read: keypad_read,
-+ llseek: no_llseek,
-+ poll: keypad_poll,
-+ ioctl: keypad_ioctl,
-+ open: keypad_open,
-+ release: keypad_close,
-+};
-+
-+static struct miscdevice
-+keypad_misc_device = {
-+ KEYPAD_MINOR,
-+ KEYPAD_NAME,
-+ &keypad_fops,
-+};
-+
-+/*
-+ * for /dev/keypadB.
-+ * read() isn't defined here. calls to read() will return -1 with EINVAL.
-+ */
-+static struct file_operations
-+keypadB_fops = {
-+ llseek: no_llseek,
-+ poll: keypadB_poll,
-+ ioctl: keypadB_ioctl,
-+ open: keypadB_open,
-+ release: keypadB_close,
-+};
-+
-+static struct miscdevice
-+keypadB_misc_device = {
-+ KEYPAD_BITMAP_MINOR,
-+ KEYPAD_BITMAP_NAME,
-+ &keypadB_fops,
-+};
-+
-+/*
-+ * for /dev/keypadI.
-+ * read() isn't defined here. calls to read() will return -1 with EINVAL.
-+ */
-+static struct file_operations
-+keypadI_fops = {
-+ llseek: no_llseek,
-+ ioctl: keypadI_ioctl,
-+ open: keypadI_open,
-+ release: keypadI_close,
-+};
-+
-+static struct miscdevice
-+keypadI_misc_device = {
-+ KEYPAD_INSERT_MINOR,
-+ KEYPAD_INSERT_NAME,
-+ &keypadI_fops,
-+};
-+
-+#ifdef CONFIG_PANIC_LOG
-+static u32 panic_bug_used =0;
-+#endif
-+
-+/* Interrupt Handler for KEYPAD */
-+static void
-+kp_interrupt(int irq, void *ptr, struct pt_regs *regs)
-+{
-+ unsigned long flags;
-+ unsigned long kpc_val;
-+
-+#ifdef USE_RELEASE_TIMER
-+ del_timer (&key_release_timer);
-+#endif
-+ del_timer (&autorepeat_timer);
-+ spin_lock_irqsave(&keypad_lock,flags);
-+
-+ /* ack interrupt */
-+ kpc_val = KPC;
-+
-+ /* matrix interrupt */
-+ if (kpc_val & KPC_MI)
-+ {
-+/*
-+ * The Intel driver turned on KPC_AS here. It doesn't seem that we
-+ * would need to do that, because getting an interrupt means that
-+ * a scan was just done. For now, I've commented out the setting
-+ * and clearing of this bit.
-+ KPC |= KPC_AS;
-+ */
-+ while (KPAS & KPAS_SO)
-+ {
-+ /* Wait for the Scan On bit to go off before */
-+ /* reading the scan registers. */
-+ NULL;
-+ };
-+
-+ kpas = KPAS;
-+ kpasmkp0 = KPASMKP0;
-+ kpasmkp1 = KPASMKP1;
-+ kpasmkp2 = KPASMKP2;
-+
-+ }
-+
-+ /* direct interrupt */
-+ if (kpc_val & KPC_DI)
-+ {
-+ kpdk = KPDK;
-+ /*
-+ * reading the register turns off the "key pressed since last read"
-+ * bit if it was on, so we turn it off
-+ */
-+ kpdk &= ~KPDK_DKP;
-+ }
-+
-+ copy_bitmap (oldkeybitmap, keybitmap);
-+ scan_to_bitmap (kpas, kpasmkp0, kpasmkp1, keybitmap);
-+#if defined(CONFIG_E680_P4A)
-+ if (kpdk & KPDK_DK0) /* VR key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ if (kpdk & KPDK_DK0) /* VR key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+ if (kpdk & KPDK_DK3)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ }
-+ if (kpdk & KPDK_DK5)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+
-+#elif defined(CONFIG_KEYPAD_A780)
-+ if (kpdk & KPDK_DK0) /* voice/camera key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+
-+#ifdef CONFIG_PANIC_LOG
-+ if ((kpdk & KPDK_DK0)&&(kpasmkp1& 0x00020000))
-+ {
-+ if(0 == panic_bug_used)
-+ {
-+ panic_bug_used = 1;
-+ BUG();
-+ }
-+ }
-+#endif
-+
-+ (void) add_events (oldkeybitmap, keybitmap);
-+
-+ /* If any keys are down, set a timer to check for key release */
-+ /* and one for autorepeat if that's on. */
-+ if (any_keys_down (keybitmap))
-+ {
-+#ifdef USE_RELEASE_TIMER
-+ key_release_timer.expires = (jiffies + key_release_interval);
-+ add_timer (&key_release_timer);
-+#endif
-+ if (do_autorepeat)
-+ {
-+ autorepeat_timer.expires = (jiffies + jiffies_to_first_repeat);
-+ add_timer (&autorepeat_timer);
-+ }
-+ }
-+
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ wake_up_interruptible (&keypad_wait);
-+ printk("keypad interrupt occurred\n");
-+}
-+
-+#ifdef USE_RELEASE_TIMER
-+/*
-+ * This is called when the key release timer goes off. That's the
-+ * only time it should be called. Check for changes in what keys
-+ * are down.
-+ */
-+static void
-+release_timer_went_off(unsigned long unused)
-+{
-+ unsigned long flags;
-+
-+ spin_lock_irqsave(&keypad_lock,flags);
-+ do_scan();
-+ /* If any keys are still down, set the timer going again. */
-+ if (any_keys_down (keybitmap))
-+ {
-+ mod_timer (&key_release_timer, jiffies + key_release_interval);
-+ }
-+ else
-+ {
-+ del_timer (&autorepeat_timer);
-+ }
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+}
-+#endif
-+
-+/*
-+ * This is called when the autorepeat timer goes off.
-+ */
-+static void
-+autorepeat_timer_went_off(unsigned long unused)
-+{
-+ int i, bitnum;
-+ unsigned long tmp;
-+ unsigned long flags;
-+
-+ spin_lock_irqsave(&keypad_lock,flags);
-+ if (!any_keys_down (keybitmap))
-+ {
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return;
-+ }
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ tmp = keybitmap[NUM_WORDS_IN_BITMAP-i-1];
-+ while ((bitnum = ffs(tmp)) != 0)
-+ {
-+ tmp &= ~(1<<(bitnum-1));
-+ /* see explanation at top of file */
-+ if ( (bitnum + (32*i)) == KEYPAD_POWER )
-+ {
-+ continue;
-+ }
-+ (void) add_to_keybuf( (bitnum + (32*i)) | KEYDOWN );
-+ }
-+ }
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ wake_up_interruptible (&keypad_wait);
-+
-+ mod_timer (&autorepeat_timer, jiffies + jiffies_to_next_repeat);
-+}
-+
-+#ifdef USE_RELEASE_TIMER
-+/*
-+ * Do a scan and add key events for anything that's different from the
-+ * last scan. We assume keypad_lock is locked when this is called
-+ * (by release_timer_went_off).
-+ */
-+static void
-+do_scan(void)
-+{
-+ unsigned long kpas_new, kpasmkp0_new, kpasmkp1_new;
-+ unsigned long kpdk_new;
-+ int change;
-+
-+ /* Initiate an automatic scan */
-+ KPC |= KPC_AS;
-+ /* Wait for the Scan On bit to go off before */
-+ /* reading the scan registers. */
-+ while (KPAS & KPAS_SO)
-+ {
-+ NULL;
-+ };
-+ kpas_new = KPAS;
-+ kpasmkp0_new = KPASMKP0;
-+ kpasmkp1_new = KPASMKP1;
-+ kpdk_new = KPDK;
-+ /*
-+ * reading the register turns off the "key pressed since last read" bit
-+ * if it was on, so we turn it off
-+ */
-+ kpdk_new &= ~KPDK_DKP;
-+ KPC &= ~KPC_AS;
-+
-+ change = ((kpas_new != kpas) ||
-+ (kpasmkp0_new != kpasmkp0) ||
-+ (kpasmkp1_new != kpasmkp1) ||
-+ (kpdk_new != kpdk));
-+
-+ if (change)
-+ {
-+ kpas = kpas_new;
-+ kpasmkp0 = kpasmkp0_new;
-+ kpasmkp1 = kpasmkp1_new;
-+ kpdk = kpdk_new;
-+
-+ copy_bitmap (oldkeybitmap, keybitmap);
-+ scan_to_bitmap (kpas, kpasmkp0, kpasmkp1, keybitmap);
-+#if defined(CONFIG_E680_P4A)
-+ if (kpdk & KPDK_DK0) /* screen lock key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ if (kpdk & KPDK_DK0) /* screen lock key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+ if (kpdk & KPDK_DK3)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ }
-+ if (kpdk & KPDK_DK5)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+
-+#elif defined(CONFIG_KEYPAD_A780)
-+ if (kpdk & KPDK_DK0) /* voice/camera key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+ add_events (oldkeybitmap, keybitmap);
-+
-+ wake_up_interruptible (&keypad_wait);
-+ }
-+}
-+#endif
-+
-+/*
-+ * set all words in the specified bitmap to 0
-+ */
-+static inline void set_bitmap_to_zero(unsigned long b[]) {
-+ int i;
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ b[i]=0;
-+ }
-+}
-+
-+/*
-+ * copy source bitmap to destination bitmap
-+ */
-+static inline void copy_bitmap(unsigned long dest[], unsigned long source[]) {
-+ int i;
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ dest[i]=source[i];
-+ }
-+}
-+
-+/*
-+ * Turn on the bit position in map for the specified key code.
-+ * Bit numbers start with 1 (not 0) and increase moving left within
-+ * words and within the array.
-+ * Bit 1 is the rightmost bit in map[NUM_WORDS_IN_BITMAP-1].
-+ * Bit 33 is the rightmost bit in map[NUM_WORDS_IN_BITMAP-2].
-+ */
-+static inline void
-+turn_on_bit(unsigned long map[], int code)
-+{
-+ int word, pos, p;
-+
-+ /* if we have 2 words, bits 1-32 are in map[1], 33-64 in map[0] */
-+ word = (NUM_WORDS_IN_BITMAP - 1) - ((code-1) / 32);
-+ /*
-+ * bit 1 is 1<<0, bit 2 is 1<<1, ... bit 32 is 1 << 31, all in map[1]
-+ * bit 33 is 1<<0, bit 34 is 1<<1, ... in map[0]
-+ * we want this:
-+ * code pos
-+ * 1 0
-+ * 2 1
-+ * ...
-+ * 31 30
-+ * 32 31
-+ * 33 0
-+ * 34 1
-+ * ...
-+ */
-+ pos = (p = (code % 32)) == 0 ? 31 : p-1;
-+ map[word] |= (1<<pos);
-+}
-+
-+/*
-+ * Turn off the bit position in map for the specified key code.
-+ * Bit positions start with 1 (not 0).
-+ */
-+static inline void
-+turn_off_bit(unsigned long map[], int code)
-+{
-+ int word, pos, p;
-+
-+ word = (NUM_WORDS_IN_BITMAP - 1) - ((code-1) / 32);
-+ pos = (p = (code % 32)) == 0 ? 31 : p-1;
-+ map[word] &= ~(1<<pos);
-+}
-+
-+/*
-+ * Return 1 if any bits are down in map[]
-+ */
-+static inline int
-+any_keys_down (unsigned long *map)
-+{
-+ int i;
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ /* don't count the power key */
-+ if ((i == 0) && (*map == 0x10))
-+ {
-+ map++;
-+ continue;
-+ }
-+ if (*map++)
-+ {
-+ return 1;
-+ }
-+ }
-+ return 0;
-+}
-+static int
-+__init keypad_init(void)
-+{
-+ int err;
-+
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_init\n");
-+#endif
-+
-+ set_bitmap_to_zero (oldkeybitmap);
-+ set_bitmap_to_zero (keybitmap);
-+ set_bitmap_to_zero (lastioctlbitmap);
-+
-+ /* set up gpio */
-+#if defined (CONFIG_KEYPAD_V700)
-+ pxa_gpio_mode(95 | GPIO_ALT_FN_1_IN); /* KP_MKIN<6> */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_1_IN); /* KP_MKIN<3> */
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_1_IN); /* KP_MKIN<4> */
-+ pxa_gpio_mode(99 | GPIO_ALT_FN_1_IN); /* KP_MKIN<5> */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+#elif defined(CONFIG_E680_P4A)
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN); /* KP_DKIN<0>, VR Key */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_1_IN); /* KP_DKIN<4>, power key */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN); /* KP_DKIN<0>, VR Key */
-+ pxa_gpio_mode(96 | GPIO_ALT_FN_1_IN); /* KP_DKIN<3>, GAME_A */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_1_IN); /* KP_DKIN<4>, power key */
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_1_IN); /* KP_DKIN<5>, GAME_B */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+ pxa_gpio_mode(GPIO_TC_MM_EN);
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ PGSR3 |= GPIO_bit(GPIO_TC_MM_EN);
-+#elif defined (CONFIG_KEYPAD_A780)
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN); /* KP_DKIN<0>, voice_rec */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_3_IN); /* KP_MKIN<3> */
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_3_IN); /* KP_MKIN<4> */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+ pxa_gpio_mode(107 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<4> */
-+#elif defined(CONFIG_KEYPAD_MAINSTONE)
-+ /* from Intel driver */
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(94 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(95 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(99 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+#endif
-+
-+ /* set keypad control register */
-+ KPC = (KPC_ASACT | /* automatic scan on activity */
-+ KPC_ME | KPC_DE | /* matrix and direct keypad enabled */
-+#if defined (CONFIG_KEYPAD_V700)
-+ (3<<23) | /* 4 columns */
-+ (6<<26) | /* 7 rows */
-+#elif defined(CONFIG_E680_P4A)
-+ (3<<23) | /* 4 columns */
-+ (2<<26) | /* 3 rows */
-+ (4<<6) | /* 4# direct key */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ (5<<23) | /* 4 columns */
-+ (4<<26) | /* 3 rows */
-+ (5<<6) | /* 5# direct keys */
-+#elif defined(CONFIG_KEYPAD_A780)
-+ (4<<23) | /* 5 columns */
-+ (4<<26) | /* 5 rows */
-+ (0<<6) | /* 1# direct keys */
-+#endif
-+ KPC_MS7_0); /* scan all columns */
-+
-+ CKEN |= CKEN19_KEYPAD;
-+
-+ err = request_irq (IRQ_KEYPAD, kp_interrupt, 0, "Keypad", NULL);
-+ if (err)
-+ {
-+ printk (KERN_CRIT "can't register IRQ%d for keypad, error %d\n",
-+ IRQ_KEYPAD, err);
-+ CKEN &= ~CKEN19_KEYPAD;
-+ return -ENODEV;
-+ }
-+
-+ if (misc_register (&keypad_misc_device))
-+ {
-+ printk(KERN_ERR "Couldn't register keypad driver\n");
-+ return -EIO;
-+ }
-+ if (misc_register (&keypadB_misc_device))
-+ {
-+ printk(KERN_ERR "Couldn't register keypadB driver\n");
-+ misc_deregister(&keypad_misc_device);
-+ return -EIO;
-+ }
-+ if (misc_register (&keypadI_misc_device))
-+ {
-+ printk(KERN_ERR "Couldn't register keypadI driver\n");
-+ misc_deregister(&keypad_misc_device);
-+ misc_deregister(&keypadB_misc_device);
-+ return -EIO;
-+ }
-+
-+#ifdef USE_RELEASE_TIMER
-+ init_timer (&key_release_timer);
-+ key_release_timer.function = release_timer_went_off;
-+#endif
-+ init_timer (&autorepeat_timer);
-+ autorepeat_timer.function = autorepeat_timer_went_off;
-+
-+ /*
-+ * we want the phone to be able to tell the status of the screen
-+ * lock switch at power-up time
-+ */
-+ kpdk = KPDK; /* read direct key register */
-+ /*
-+ * reading the register turns off the "key pressed since last read" bit
-+ * if it was on, so we turn it off
-+ */
-+ kpdk &= ~KPDK_DKP;
-+#if defined(CONFIG_E680_P4A)
-+ if (kpdk & KPDK_DK0) /* VR key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4) /* Power key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+#elif defined(CONFIG_KEYPAD_E680)
-+ if (kpdk & KPDK_DK0) /* VR key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4) /* Power key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ if (kpdk & KPDK_DK3) /* GAME_A key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ }
-+ if (kpdk & KPDK_DK5) /* GAME_B key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+#elif defined(CONFIG_KEYPAD_A780)
-+ if (kpdk & KPDK_DK0) /* voice/camera key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+
-+#ifdef CONFIG_PM
-+ pm_dev = pm_register(PM_SYS_DEV, 0, button_pm_callback);
-+#if defined(CONFIG_E680_P4A)
-+/*93,97,100,101,102*/
-+ PKWR = 0xe4400;
-+/*103 104 105 106*/
-+ PGSR3 |= 0x780;
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+/*93,96,97,98,100,101,102*/
-+ PKWR = 0xee400;
-+/*103 104 105 106*/
-+ PGSR3 |= 0x780;
-+#endif
-+#if defined(CONFIG_KEYPAD_A780)
-+/*93,97,98,100,101,102*/
-+ PKWR = 0xec400;
-+/*103 104 105 106 107*/
-+ PGSR3 |= 0xf80;
-+#endif
-+#endif
-+
-+#if defined(CONFIG_KEYPAD_E680)
-+#ifdef CONFIG_PM
-+ keypadI_pm_dev = pm_register(PM_SYS_DEV, 0, keypadI_pm_callback);
-+ PGSR3 |= 0x8;
-+#endif
-+#endif
-+
-+ KPC |= (KPC_DIE | KPC_MIE);
-+ KPKDI = 0x40;
-+ return 0;
-+}
-+
-+static void
-+__exit keypad_exit(void)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_exit\n");
-+#endif
-+ misc_deregister(&keypad_misc_device);
-+ misc_deregister(&keypadB_misc_device);
-+ misc_deregister(&keypadI_misc_device);
-+
-+#ifdef CONFIG_PM
-+ pm_unregister(pm_dev);
-+#endif
-+
-+#if defined(CONFIG_KEYPAD_E680)
-+#ifdef CONFIG_PM
-+ pm_unregister(keypadI_pm_dev);
-+#endif
-+#endif
-+
-+ CKEN &= ~CKEN19_KEYPAD;
-+}
-+
-+module_init (keypad_init);
-+module_exit (keypad_exit);
-Index: linux-2.6.16.5-a/drivers/misc/ezx/keypad-panasonic.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/keypad-panasonic.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,1569 @@
-+/*
-+ * linux/drivers/char/keypad.c
-+ *
-+ * (c) Copyright Motorola 2003, All rights reserved.
-+ */
-+
-+/*
-+ * This driver is for three devices: /dev/keypad, /dev/keypadB and
-+ * /dev/keypadI.
-+ * /dev/keypad would be used for reading the key event buffer.
-+ * It can be opened by one process at a time.
-+ * /dev/keypadB would be used for ioctl(KEYPAD_IOC_GETBITMAP).
-+ * It can be opened by one process at a time.
-+ * /dev/keypadI would be used for ioctl(KEYPAD_IOC_INSERT_EVENT).
-+ * It can be opened any number of times simultaneously.
-+ *
-+ * The bulverde specification is ambiguous about when interrupts happen
-+ * for released keys. We were told by Intel that we won't
-+ * get interrupts for released keys except in the case when multiple
-+ * keys were down and they've all been released. So we implemented
-+ * a timer to poll for changes in key states.
-+ *
-+ * The E680 P2 hardware gives us interrupts when any key is released,
-+ * whether it was the only key down or not, and whether it's the last
-+ * of multiple keys to be released or not. We don't know whether this
-+ * behavior will continue in future hardware releases, so the release
-+ * timer is still in the code, #ifdef'd with USE_RELEASE_TIMER. On the
-+ * P2 hardware, the code works with or without USE_RELEASE_TIMER defined.
-+ * If the release interrupts are always going to happen, we can remove
-+ * the #ifdef'd code.
-+ *
-+ * With the P2 hardware, the power key bit in the KPDK register is always
-+ * on. We don't know if this is correct behavior or not, but in any case
-+ * it certainly causes trouble to have that key autorepeating indefinitely,
-+ * or to be checking indefinitely for the key to be released (if we're doing
-+ * release polling).
-+ *
-+ * For now, any_keys_down() returns 0 if the power key is the only one down.
-+ * . At interrupt time, if the power key is the only one down we don't
-+ * set the autorepeat timer or release timer.
-+ * . When the release timer goes off, if the power key is the only one
-+ * still down we don't set the timer again.
-+ * . When the autorepeat timer goes off, if the power key is the only
-+ * one down we don't generate any events.
-+ * In autorepeat_timer_went_off, if there are non-power keys down, while we're
-+ * looking through the whole bitmap of keys down we ignore the power key.
-+ */
-+
-+#include <linux/tty.h>
-+#include <linux/init.h>
-+#include <linux/module.h>
-+#include <linux/poll.h>
-+#include <linux/miscdevice.h>
-+#include <linux/bitops.h>
-+#include <linux/param.h>
-+
-+#include <asm/hardware.h>
-+#include <asm/io.h>
-+#include <asm/irq.h>
-+#include <linux/pm.h>
-+#include <linux/apm_bios.h>
-+#include "keypad.h"
-+#include <asm/arch/irqs.h>
-+#include "asm/arch/ezx.h"
-+#include <linux/delay.h>
-+
-+#ifdef CONFIG_PM
-+static struct pm_dev *pm_dev;
-+static struct pm_dev *keypadI_pm_dev;
-+static int kpc_res,kpkdi_res;
-+static int GPIO_TC_MM_STATE = 1;
-+extern unsigned char pxafb_ezx_getLCD_status(void);
-+#endif
-+/*
-+ * This is the number of microseconds we wait before checking to see if any
-+ * keys have been released.
-+ */
-+#define RDELAY 200
-+
-+#define KEYBUF_EMPTY() (keybuf_start == keybuf_end)
-+#define KEYBUF_FULL() ( ((keybuf_end+1)%KEYBUF_SIZE) == keybuf_start)
-+#define KEYBUF_INC(x) ((x) = (((x)+1) % KEYBUF_SIZE))
-+
-+static int keypad_open (struct inode *, struct file *);
-+static int keypad_close (struct inode *, struct file *);
-+static int keypad_ioctl (struct inode *, struct file *,
-+ unsigned int, unsigned long);
-+static unsigned int keypad_poll (struct file *, poll_table *);
-+static ssize_t keypad_read (struct file *, char *, size_t, loff_t *);
-+
-+static int keypadB_open (struct inode *, struct file *);
-+static int keypadB_close (struct inode *, struct file *);
-+static int keypadB_ioctl (struct inode *, struct file *,
-+ unsigned int, unsigned long);
-+static unsigned int keypadB_poll (struct file *, poll_table *);
-+
-+static int keypadI_open(struct inode *, struct file *);
-+static int keypadI_close(struct inode *, struct file *);
-+static int keypadI_ioctl (struct inode *, struct file *,
-+ unsigned int, unsigned long);
-+
-+static void kp_interrupt (int, void *, struct pt_regs *);
-+#ifdef USE_RELEASE_TIMER
-+static void release_timer_went_off (unsigned long);
-+static void do_scan(void);
-+#endif
-+static void autorepeat_timer_went_off (unsigned long);
-+
-+static int add_to_keybuf (unsigned short);
-+static int add_events (unsigned long *, unsigned long *);
-+static int insert_event (unsigned short);
-+static unsigned short get_from_keybuf (void);
-+static void scan_to_bitmap
-+ (unsigned long, unsigned long, unsigned long, unsigned long *);
-+static inline void set_bitmap_to_zero(unsigned long b[]);
-+static inline void copy_bitmap(unsigned long dest[], unsigned long source[]);
-+static inline void turn_on_bit(unsigned long map[], int);
-+static inline void turn_off_bit(unsigned long map[], int);
-+static inline int any_keys_down (unsigned long *);
-+
-+/*
-+ * keybuf is a circular buffer to hold keypad events.
-+ * keybuf_start is the index of the first event.
-+ * keybuf_end is one more than the index of the last event.
-+ * The buffer is empty when keybuf_start == keybuf_end.
-+ * We only use KEYBUF_SIZE-1 entries in the buffer so we can tell
-+ * when it's full without needing another variable to tell us.
-+ * The buffer is full when (keybuf_end+1)%KEYBUF_SIZE == keybuf_start.
-+ */
-+static unsigned short keybuf[KEYBUF_SIZE];
-+static int keybuf_start = 0;
-+static int keybuf_end = 0;
-+
-+static DECLARE_WAIT_QUEUE_HEAD(keypad_wait);
-+static spinlock_t keypad_lock = SPIN_LOCK_UNLOCKED;
-+
-+static int reading_opens = 0;
-+static int bitmap_opens = 0;
-+
-+/* previous bitmap of keys down */
-+static unsigned long oldkeybitmap[NUM_WORDS_IN_BITMAP];
-+/* current bitmap of keys down */
-+static unsigned long keybitmap[NUM_WORDS_IN_BITMAP];
-+/* last bitmap read by ioctl */
-+static unsigned long lastioctlbitmap[NUM_WORDS_IN_BITMAP];
-+
-+static unsigned long kpas = 0; /* last value of kpas */
-+static unsigned long kpasmkp0 = 0; /* last value of kpasmkp0 */
-+static unsigned long kpasmkp1 = 0; /* last value of kpasmkp1 */
-+static unsigned long kpasmkp2 = 0; /* last value of kpasmkp2 */
-+static unsigned long kpdk = 0; /* last value of kpdk */
-+
-+#ifdef USE_RELEASE_TIMER
-+static struct timer_list key_release_timer;
-+static int key_release_interval = RDELAY * HZ/1000;
-+#endif
-+
-+static int do_autorepeat = 1;
-+static long jiffies_to_first_repeat = 30;
-+static long jiffies_to_next_repeat = 30;
-+static struct timer_list autorepeat_timer;
-+
-+extern int lockscreen_flag;
-+
-+static int
-+keypad_open(struct inode *inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG "keypad_open\n");
-+#endif
-+ spin_lock(keypad_lock);
-+ if (reading_opens > 0)
-+ {
-+ spin_unlock(keypad_lock);
-+ return -EBUSY;
-+ }
-+ reading_opens++;
-+ spin_unlock(keypad_lock);
-+
-+ return 0;
-+}
-+
-+static int
-+keypadB_open(struct inode *inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG "keypadB_open\n");
-+#endif
-+ spin_lock(keypad_lock);
-+ if (bitmap_opens > 0)
-+ {
-+ spin_unlock(keypad_lock);
-+ return -EBUSY;
-+ }
-+ bitmap_opens++;
-+ /*
-+ * poll returns when lastioctlbitmap is different from keybitmap.
-+ * we set lastioctlbitmap to keybitmap here so that a poll right
-+ * after an open returns when the bitmap is different from when
-+ * the open was done, not when the bitmap is different from the
-+ * last time some other process read it
-+ */
-+ copy_bitmap(lastioctlbitmap, keybitmap);
-+ spin_unlock(keypad_lock);
-+
-+ return 0;
-+}
-+
-+#if defined(CONFIG_KEYPAD_E680)
-+#ifdef CONFIG_PM
-+static int keypadI_pm_callback(struct pm_dev *pm_dev, pm_request_t req, void *data)
-+{
-+ switch(req)
-+ {
-+ case PM_SUSPEND:
-+ break;
-+ case PM_RESUME:
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ if(GPIO_TC_MM_STATE == 1)
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ else
-+ GPCR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ break;
-+ default:
-+ break;
-+ }
-+ return 0;
-+}
-+#endif
-+#endif
-+
-+static int
-+keypadI_open(struct inode *inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG "keypadI_open\n");
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ pxa_gpio_mode(GPIO_TC_MM_EN);
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+#endif
-+
-+ return 0;
-+}
-+
-+static int
-+keypad_close(struct inode * inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_close\n");
-+#endif
-+ /*
-+ * this decrement of reading_opens doesn't have to be protected because
-+ * it can only be executed to close the single open of /dev/keypad
-+ */
-+ reading_opens--;
-+ return 0;
-+}
-+
-+static int
-+keypadB_close(struct inode * inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypadB_close\n");
-+#endif
-+ /*
-+ * this decrement of bitmap_opens doesn't have to be protected because
-+ * it can only be executed to close the single open of /dev/keypadB
-+ */
-+ bitmap_opens--;
-+ return 0;
-+}
-+
-+static int
-+keypadI_close(struct inode * inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypadI_close\n");
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ pxa_gpio_mode(GPIO_TC_MM_EN);
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+#endif
-+
-+ return 0;
-+}
-+
-+/**
-+ * Add the specified event to the key buffer.
-+ * This should be called with keypad_lock locked.
-+ */
-+static int
-+add_to_keybuf (unsigned short event)
-+{
-+ if (KEYBUF_FULL())
-+ {
-+ return -ENOMEM;
-+ }
-+ keybuf[keybuf_end] = event;
-+ KEYBUF_INC (keybuf_end);
-+
-+#if CONFIG_APM
-+ queue_apm_event(KRNL_KEYPAD, NULL);
-+#endif
-+ printk("add keypad event = %x\n", event);
-+ return 0;
-+}
-+
-+/*
-+ * code[c*8+r] is the key code for the key that's down when there's a 1
-+ * in column c, row r of the scan registers.
-+ */
-+
-+#if defined(CONFIG_KEYPAD_V700)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_UP, KEYPAD_DOWN, KEYPAD_LEFT, KEYPAD_RIGHT,
-+ KEYPAD_POUND, KEYPAD_0, KEYPAD_9, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_2, KEYPAD_4, KEYPAD_6, KEYPAD_8,
-+ KEYPAD_7, KEYPAD_SLEFT, KEYPAD_SRIGHT, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_MENU, KEYPAD_1, KEYPAD_3, KEYPAD_5,
-+ KEYPAD_STAR, KEYPAD_VOLUP, KEYPAD_VOLDOWN, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_CAMERA, KEYPAD_CLEAR, KEYPAD_CARRIER, KEYPAD_ACTIVATE,
-+ KEYPAD_SEND, KEYPAD_SMART, KEYPAD_VAVR, KEYPAD_NONE
-+};
-+
-+/* end CONFIG_KEYPAD_V700 */
-+#elif defined(CONFIG_E680_P4A)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_UP, KEYPAD_DOWN, KEYPAD_LEFT, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_RIGHT, KEYPAD_CENTER, KEYPAD_HOME, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_GAME_R, KEYPAD_NONE, KEYPAD_GAME_L, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_A, KEYPAD_B, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+};
-+
-+/* end CONFIG_E680_P4A */
-+#elif defined(CONFIG_KEYPAD_E680)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_UP, KEYPAD_DOWN, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_RIGHT, KEYPAD_LEFT, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_NONE, KEYPAD_GAME_R, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_HOME, KEYPAD_GAME_L, KEYPAD_CENTER, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+
-+};
-+/*end CONFIG_KEYPAD_E680 */
-+#elif defined(CONFIG_KEYPAD_A780)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_OK, KEYPAD_1, KEYPAD_4, KEYPAD_7,
-+ KEYPAD_STAR, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_MENU, KEYPAD_2, KEYPAD_5, KEYPAD_8,
-+ KEYPAD_0, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_CANCEL, KEYPAD_3, KEYPAD_6, KEYPAD_9,
-+ KEYPAD_POUND, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_JOG_UP, KEYPAD_JOG_MIDDLE, KEYPAD_PTT, KEYPAD_NONE,
-+ KEYPAD_JOG_DOWN, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 4 */
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_HOME,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+};
-+#endif
-+
-+/*
-+ * Decode the specified scan register values into the bitmap pointed
-+ * to by the last argument. The bitmap will contain a 1
-+ * for each key that's down.
-+ *
-+ * Only the 1st two of the four scan registers are used.
-+ */
-+static void
-+scan_to_bitmap(unsigned long kpas, unsigned long kpasmkp0,
-+ unsigned long kpasmkp1, unsigned long bitmap[])
-+{
-+ int row, col;
-+ int bitnum;
-+ unsigned long scanmap;
-+
-+ set_bitmap_to_zero (bitmap);
-+
-+ if ((kpas & KPAS_MUKP) == MUKP_NO_KEYS)
-+ {
-+ return;
-+ }
-+
-+ if ((kpas & KPAS_MUKP) == MUKP_ONE_KEY)
-+ {
-+ row = (kpas & KPAS_RP) >> 4;
-+ col = kpas & KPAS_CP;
-+#if defined(CONFIG_KEYPAD_A780)
-+ if( !((row == 3)&&(col == 3)) )
-+ {
-+#endif
-+ turn_on_bit (bitmap, scanbit_to_keycode[col*8 + row]);
-+#if defined(CONFIG_KEYPAD_A780)
-+ }
-+#endif
-+
-+ return;
-+ }
-+
-+ /* reach here if multiple keys */
-+ scanmap = (kpasmkp0 & 0x7f) | ((kpasmkp0 & 0x7f0000) >> 8) |
-+ ((kpasmkp1 & 0x7f) << 16) | ((kpasmkp1 & 0x7f0000) << 8);
-+ while ((bitnum = ffs(scanmap)) != 0)
-+ {
-+ /*
-+ * ffs returns bit numbers starting with 1, so subtract 1 to index
-+ * into scanbit_to_keycode[]
-+ */
-+ turn_on_bit (bitmap, scanbit_to_keycode[bitnum-1]);
-+ scanmap &= ~(1<<(bitnum-1));
-+ }
-+#if defined(CONFIG_KEYPAD_A780)
-+ kpasmkp2 = KPASMKP2;
-+ kpasmkp2 &= 0x8;
-+ while ((bitnum = ffs(kpasmkp2)) !=0)
-+ {
-+ turn_on_bit (bitmap, scanbit_to_keycode[32+bitnum-1]);
-+ kpasmkp2 &= ~(1<<(bitnum-1));
-+ }
-+#endif
-+}
-+
-+/*
-+ * Add events indicated by the difference between the last scan (oldbitmap)
-+ * and this one (newbitmap) to the input buffer.
-+ * Return nonzero right away if any of the events can't be added.
-+ * A zero return means all the events were added.
-+ * This should be called with keypad_lock locked.
-+ */
-+static int
-+add_events (unsigned long *oldbitmap, unsigned long *newbitmap)
-+{
-+ unsigned long tmpmap, onebitmap;
-+ int bitnum, i, ret;
-+
-+ /* generate events for keys that were down before and are up now */
-+ for (i=NUM_WORDS_IN_BITMAP-1;i>=0;i--)
-+ {
-+ tmpmap = oldbitmap[i];
-+ while ((bitnum = ffs(tmpmap)) != 0)
-+ {
-+ onebitmap = 1<<(bitnum-1);
-+ if ((newbitmap[i] & onebitmap) == 0)
-+ {
-+ ret = add_to_keybuf(bitnum + (32*(NUM_WORDS_IN_BITMAP-1-i) | KEYUP));
-+ if (ret < 0)
-+ {
-+ return ret;
-+ }
-+ }
-+ tmpmap &= ~onebitmap;
-+ }
-+ }
-+ /* generate events for down keys that were up before */
-+ for (i=NUM_WORDS_IN_BITMAP-1;i>=0;i--)
-+ {
-+ tmpmap = newbitmap[i];
-+ while ((bitnum = ffs(tmpmap)) != 0)
-+ {
-+ onebitmap = 1<<(bitnum-1);
-+ if ((oldbitmap[i] & onebitmap) == 0)
-+ {
-+ ret = add_to_keybuf
-+ (bitnum + (32*(NUM_WORDS_IN_BITMAP-1-i) | KEYDOWN));
-+ if (ret < 0)
-+ {
-+ return ret;
-+ }
-+ }
-+ tmpmap &= ~onebitmap;
-+ }
-+ }
-+ return 0;
-+}
-+
-+/*
-+ * do the INSERT_EVENT ioctl
-+ */
-+static int
-+insert_event (unsigned short event)
-+{
-+ unsigned long flags;
-+ int ret;
-+
-+ if (KEYCODE(event) > KEYPAD_MAXCODE)
-+ {
-+ printk(KERN_WARNING " inserted key code %d too big\n",
-+ KEYCODE(event));
-+ return -EINVAL;
-+ }
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ if (KEY_IS_DOWN(event))
-+ {
-+ turn_on_bit(keybitmap, KEYCODE(event));
-+ }
-+ else
-+ {
-+ turn_off_bit (keybitmap, event);
-+ }
-+ if ((ret = add_to_keybuf(event)) < 0)
-+ {
-+ spin_unlock_irqrestore(&keypad_lock,flags);
-+ return ret;
-+ }
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ wake_up_interruptible (&keypad_wait);
-+ return 0;
-+}
-+
-+static int
-+keypad_ioctl (struct inode *inode, struct file *file,
-+ unsigned int cmd, unsigned long arg)
-+{
-+ int interval; /* debounce interval */
-+ int imkp; /* Ignore Multiple Key Press bit */
-+ struct autorepeatinfo ar; /* autorepeat information */
-+
-+#ifdef KDEBUG
-+ printk (KERN_DEBUG "keypad_ioctl: 0x%x\n", cmd);
-+#endif
-+ switch (cmd)
-+ {
-+ case KEYPAD_IOC_INSERT_EVENT:
-+ return insert_event ((unsigned short)arg);
-+ break;
-+ case KEYPAD_IOC_GET_DEBOUNCE_INTERVAL:
-+ interval = KPKDI & KPKDI_BITS;
-+ return put_user(interval, (unsigned long *)arg);
-+ break;
-+ case KEYPAD_IOC_SET_DEBOUNCE_INTERVAL:
-+ interval = (unsigned short)arg;
-+ if (interval > KPKDI_BITS)
-+ {
-+ return -EINVAL;
-+ }
-+ KPKDI &= ~KPKDI_BITS;
-+ KPKDI |= interval;
-+ break;
-+ case KEYPAD_IOC_GET_IMKP_SETTING:
-+ imkp = ((KPC & KPC_IMKP) == KPC_IMKP);
-+ return put_user(imkp, (unsigned char *)arg);
-+ break;
-+ case KEYPAD_IOC_SET_IMKP_SETTING:
-+ imkp = (unsigned char)arg;
-+ if (imkp)
-+ {
-+ KPC |= KPC_IMKP;
-+ }
-+ else
-+ {
-+ KPC &= ~KPC_IMKP;
-+ }
-+ break;
-+ case KEYPAD_IOC_SET_AUTOREPEAT:
-+ if (copy_from_user (&ar, (void *)arg,
-+ sizeof(struct autorepeatinfo)) != 0)
-+ {
-+ return -EFAULT;
-+ }
-+ do_autorepeat = ar.r_repeat;
-+ /* times are specified in milliseconds; convert to jiffies */
-+ jiffies_to_first_repeat = ar.r_time_to_first_repeat * HZ/1000;
-+ jiffies_to_next_repeat = ar.r_time_between_repeats * HZ/1000;
-+ break;
-+ default:
-+ return -ENOTTY;
-+ }
-+ return 0;
-+}
-+
-+static int
-+keypadB_ioctl (struct inode *inode, struct file *file,
-+ unsigned int cmd, unsigned long arg)
-+{
-+ unsigned long flags;
-+ int ret;
-+
-+#ifdef KDEBUG
-+ printk (KERN_DEBUG "keypadB_ioctl: 0x%x\n", cmd);
-+#endif
-+ if (cmd == KEYPAD_IOC_INSERT_EVENT)
-+ {
-+ return insert_event ((unsigned short)arg);
-+ }
-+ else if (cmd == KEYPAD_IOC_GETBITMAP)
-+ {
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ ret = copy_to_user ((void *)arg, keybitmap,
-+ NUM_WORDS_IN_BITMAP * sizeof(unsigned long));
-+ copy_bitmap (lastioctlbitmap, keybitmap);
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return (ret != 0) ? -EFAULT : 0;
-+ }
-+ else
-+ {
-+ return -ENOTTY;
-+ }
-+}
-+
-+static int
-+keypadI_ioctl (struct inode *inode, struct file *file,
-+ unsigned int cmd, unsigned long arg)
-+{
-+ unsigned long flags;
-+ int ret;
-+
-+#ifdef KDEBUG
-+ printk (KERN_DEBUG "keypadI_ioctl: 0x%x\n", cmd);
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ if( cmd == KEYPADI_TURN_ON_LED )
-+ {
-+ GPCR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ GPIO_TC_MM_STATE = 0;
-+ PGSR3 &= ~GPIO_bit(GPIO_TC_MM_EN);
-+ return 0;
-+ }
-+ if( cmd == KEYPADI_TURN_OFF_LED )
-+ {
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ GPIO_TC_MM_STATE = 1;
-+ PGSR3 |= GPIO_bit(GPIO_TC_MM_EN);
-+ return 0;
-+ }
-+#endif
-+
-+ if (cmd == KEYPAD_IOC_INSERT_EVENT)
-+ {
-+ return insert_event ((unsigned short)arg);
-+ }
-+ else if (cmd == KEYPAD_IOC_GETBITMAP)
-+ {
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ ret = copy_to_user ((void *)arg, keybitmap,
-+ NUM_WORDS_IN_BITMAP * sizeof(unsigned long));
-+ copy_bitmap (lastioctlbitmap, keybitmap);
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return (ret != 0) ? -EFAULT : 0;
-+ }
-+ else
-+ {
-+ return -ENOTTY;
-+ }
-+}
-+
-+static unsigned int
-+keypad_poll( struct file *file, poll_table * wait )
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_poll\n");
-+#endif
-+ poll_wait(file, &keypad_wait, wait);
-+
-+ if (!KEYBUF_EMPTY())
-+ {
-+ return (POLLIN | POLLRDNORM);
-+ }
-+ return 0;
-+}
-+
-+static unsigned int
-+keypadB_poll( struct file *file, poll_table * wait )
-+{
-+ int i;
-+
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypadB_poll\n");
-+#endif
-+ poll_wait(file, &keypad_wait, wait);
-+
-+ for (i=0; i < NUM_WORDS_IN_BITMAP; i++)
-+ {
-+ if (lastioctlbitmap[i] != keybitmap[i])
-+ {
-+ return (POLLIN | POLLRDNORM);
-+ }
-+ }
-+ return 0;
-+}
-+
-+static unsigned short
-+get_from_keybuf(void)
-+{
-+ unsigned short event;
-+ unsigned long flags;
-+
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ event = keybuf[keybuf_start];
-+ KEYBUF_INC (keybuf_start);
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return event;
-+}
-+
-+static ssize_t
-+keypad_read(struct file *file, char *buf, size_t count, loff_t *ptr)
-+{
-+ int i, ret;
-+ unsigned short event;
-+
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_read\n");
-+#endif
-+ /* Can't seek (pread) on this device */
-+ if (ptr != &file->f_pos)
-+ {
-+ return -ESPIPE;
-+ }
-+
-+ if (count == 0)
-+ {
-+ return 0;
-+ }
-+
-+ if (KEYBUF_EMPTY())
-+ {
-+ /* buffer is empty */
-+ /* if not blocking return */
-+ if (file->f_flags & O_NONBLOCK)
-+ {
-+ return -EAGAIN;
-+ }
-+ /* blocking, so wait for input */
-+ ret = wait_event_interruptible(keypad_wait, !KEYBUF_EMPTY());
-+ if (ret)
-+ {
-+ return ret;
-+ }
-+ }
-+
-+ i = 0;
-+ /* copy events until we have what the user asked for or we run out */
-+ while ((i+1 < count) && !KEYBUF_EMPTY())
-+ {
-+ event = get_from_keybuf();
-+ if ((ret = put_user(event, (unsigned short *)buf)) != 0)
-+ {
-+ return ret;
-+ }
-+ buf += EVENTSIZE;
-+ i += EVENTSIZE;
-+ }
-+ return i;
-+}
-+
-+#ifdef CONFIG_PM
-+static int button_pm_callback(struct pm_dev *pm_dev, pm_request_t req, void *data)
-+{
-+ int pksr;
-+
-+ pksr = PKSR;
-+ PKSR = 0xfffff;
-+ switch(req)
-+ {
-+ case PM_SUSPEND:
-+ kpc_res = KPC;
-+ kpkdi_res = KPKDI;
-+ set_bitmap_to_zero (oldkeybitmap);
-+ set_bitmap_to_zero (keybitmap);
-+ set_bitmap_to_zero (lastioctlbitmap);
-+ kpas = 0;
-+ kpasmkp0 = 0;
-+ kpasmkp1 = 0;
-+ kpasmkp2 = 0;
-+ kpdk = 0;
-+ break;
-+ case PM_RESUME:
-+ KPC = kpc_res;
-+ KPKDI = kpkdi_res;
-+#if CONFIG_APM
-+#if defined(CONFIG_E680_P4A)
-+ if (pksr & 0xe4400) /*93 97 100 101 102 key is pressed (switch on) */
-+ {
-+ queue_apm_event(KRNL_KEYPAD, NULL);
-+ if (pksr & 0x400)
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ if (pksr & 0xee400) /*93 96 97 98 190 101 102 key is pressed */
-+ {
-+ queue_apm_event(KRNL_KEYPAD, NULL);
-+ if (pksr & 0x400)
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ if (pksr & 0x2000)
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ if (pksr & 0x8000)
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+#endif
-+#if defined(CONFIG_KEYPAD_A780)
-+ printk("pksr = %x\n",pksr);
-+ if (pksr & 0xec400) /* 93 97 98 100 101 102 key is pressed */
-+ {
-+ queue_apm_event(KRNL_KEYPAD, NULL);
-+ if (pksr & 0x400)
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+#endif
-+
-+ break;
-+ }
-+ return 0;
-+}
-+#endif
-+
-+/* for /dev/keypad */
-+static struct file_operations
-+keypad_fops = {
-+ read: keypad_read,
-+ llseek: no_llseek,
-+ poll: keypad_poll,
-+ ioctl: keypad_ioctl,
-+ open: keypad_open,
-+ release: keypad_close,
-+};
-+
-+static struct miscdevice
-+keypad_misc_device = {
-+ KEYPAD_MINOR,
-+ KEYPAD_NAME,
-+ &keypad_fops,
-+};
-+
-+/*
-+ * for /dev/keypadB.
-+ * read() isn't defined here. calls to read() will return -1 with EINVAL.
-+ */
-+static struct file_operations
-+keypadB_fops = {
-+ llseek: no_llseek,
-+ poll: keypadB_poll,
-+ ioctl: keypadB_ioctl,
-+ open: keypadB_open,
-+ release: keypadB_close,
-+};
-+
-+static struct miscdevice
-+keypadB_misc_device = {
-+ KEYPAD_BITMAP_MINOR,
-+ KEYPAD_BITMAP_NAME,
-+ &keypadB_fops,
-+};
-+
-+/*
-+ * for /dev/keypadI.
-+ * read() isn't defined here. calls to read() will return -1 with EINVAL.
-+ */
-+static struct file_operations
-+keypadI_fops = {
-+ llseek: no_llseek,
-+ ioctl: keypadI_ioctl,
-+ open: keypadI_open,
-+ release: keypadI_close,
-+};
-+
-+static struct miscdevice
-+keypadI_misc_device = {
-+ KEYPAD_INSERT_MINOR,
-+ KEYPAD_INSERT_NAME,
-+ &keypadI_fops,
-+};
-+
-+#ifdef CONFIG_PANIC_LOG
-+static u32 panic_bug_used =0;
-+static int panic_key = 0;
-+#endif
-+
-+/* Interrupt Handler for KEYPAD */
-+static void
-+kp_interrupt(int irq, void *ptr, struct pt_regs *regs)
-+{
-+ unsigned long flags;
-+ unsigned long kpc_val;
-+
-+#ifdef USE_RELEASE_TIMER
-+ del_timer (&key_release_timer);
-+#endif
-+ del_timer (&autorepeat_timer);
-+ spin_lock_irqsave(&keypad_lock,flags);
-+
-+ /* ack interrupt */
-+ kpc_val = KPC;
-+
-+ /* matrix interrupt */
-+ if (kpc_val & KPC_MI)
-+ {
-+/*
-+ * The Intel driver turned on KPC_AS here. It doesn't seem that we
-+ * would need to do that, because getting an interrupt means that
-+ * a scan was just done. For now, I've commented out the setting
-+ * and clearing of this bit.
-+ KPC |= KPC_AS;
-+ */
-+ while (KPAS & KPAS_SO)
-+ {
-+ /* Wait for the Scan On bit to go off before */
-+ /* reading the scan registers. */
-+ NULL;
-+ };
-+
-+ kpas = KPAS;
-+ kpasmkp0 = KPASMKP0;
-+ kpasmkp1 = KPASMKP1;
-+ kpasmkp2 = KPASMKP2;
-+
-+ }
-+
-+ /* direct interrupt */
-+ if (kpc_val & KPC_DI)
-+ {
-+ kpdk = KPDK;
-+ /*
-+ * reading the register turns off the "key pressed since last read"
-+ * bit if it was on, so we turn it off
-+ */
-+ kpdk &= ~KPDK_DKP;
-+ }
-+
-+ copy_bitmap (oldkeybitmap, keybitmap);
-+#if defined(CONFIG_E680_P4A)
-+ if (kpdk & KPDK_DK0) /* VR key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ scan_to_bitmap (kpas, kpasmkp0, kpasmkp1, keybitmap);
-+ if (kpdk & KPDK_DK0) /* VR key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+ if (kpdk & KPDK_DK3)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ }
-+ if (kpdk & KPDK_DK5)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+
-+#elif defined(CONFIG_KEYPAD_A780)
-+#ifdef CONFIG_PANIC_LOG
-+ panic_key = 0;
-+#endif
-+ scan_to_bitmap (kpas, kpasmkp0, kpasmkp1 & 0xfff7ffff, keybitmap);
-+ if (kpdk & KPDK_DK0) /* voice/camera key is pressed */
-+ {
-+#ifdef CONFIG_PANIC_LOG
-+ panic_key = 1;
-+#endif
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+#if defined(CONFIG_KEYPAD_A780)
-+ kpasmkp2 = KPASMKP2;
-+ if ( (kpasmkp2 & 0x17) || (kpasmkp1 & 0x80000) )
-+ {
-+ if( kpasmkp2 == 0x5 && kpasmkp1 == 0x80000 )
-+ {
-+ printk("Jay Up key pressed\n");
-+ turn_on_bit(keybitmap, KEYPAD_UP);
-+ }
-+ else
-+ {
-+ if( kpasmkp2 == 0x14 && kpasmkp1 == 0x80000)
-+ {
-+ printk("Jay Right key pressed\n");
-+ turn_on_bit(keybitmap, KEYPAD_RIGHT);
-+ }
-+ else
-+ {
-+ if( kpasmkp2 == 0x12 && kpasmkp1 == 0x80000)
-+ {
-+ printk("Jay Down key pressed\n");
-+ turn_on_bit(keybitmap, KEYPAD_DOWN);
-+ }
-+ else
-+ {
-+ if( kpasmkp2 == 0x3 && kpasmkp1 == 0x80000)
-+ {
-+ printk("Jay Left key pressed\n");
-+ turn_on_bit(keybitmap, KEYPAD_LEFT);
-+ }
-+ else
-+ {
-+ if( kpasmkp1 == 0x80000 && (kpasmkp2 & 0x17) == 0)
-+
-+ {
-+ printk("Jay Center key pressed\n");
-+ turn_on_bit(keybitmap, KEYPAD_CENTER);
-+ }
-+ }
-+ }
-+ }
-+ }
-+ }
-+#endif
-+
-+
-+ (void) add_events (oldkeybitmap, keybitmap);
-+
-+ /* If any keys are down, set a timer to check for key release */
-+ /* and one for autorepeat if that's on. */
-+ if (any_keys_down (keybitmap))
-+ {
-+#ifdef USE_RELEASE_TIMER
-+ key_release_timer.expires = (jiffies + key_release_interval);
-+ add_timer (&key_release_timer);
-+#endif
-+ if (do_autorepeat)
-+ {
-+ autorepeat_timer.expires = (jiffies + jiffies_to_first_repeat);
-+ add_timer (&autorepeat_timer);
-+ }
-+ }
-+
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ wake_up_interruptible (&keypad_wait);
-+ printk("keypad interrupt occurred\n");
-+}
-+
-+#ifdef USE_RELEASE_TIMER
-+/*
-+ * This is called when the key release timer goes off. That's the
-+ * only time it should be called. Check for changes in what keys
-+ * are down.
-+ */
-+static void
-+release_timer_went_off(unsigned long unused)
-+{
-+ unsigned long flags;
-+
-+ spin_lock_irqsave(&keypad_lock,flags);
-+ do_scan();
-+ /* If any keys are still down, set the timer going again. */
-+ if (any_keys_down (keybitmap))
-+ {
-+ mod_timer (&key_release_timer, jiffies + key_release_interval);
-+ }
-+ else
-+ {
-+ del_timer (&autorepeat_timer);
-+ }
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+}
-+#endif
-+
-+/*
-+ * This is called when the autorepeat timer goes off.
-+ */
-+static void
-+autorepeat_timer_went_off(unsigned long unused)
-+{
-+ int i, bitnum;
-+ unsigned long tmp;
-+ unsigned long flags;
-+
-+#ifdef CONFIG_PANIC_LOG
-+ int temp_key;
-+ if( panic_key == 1 )
-+ {
-+ kpc_res = KPC;
-+ /* Initiate a manual scan */
-+ KPC &= ~(KPC_AS | KPC_ASACT | KPC_MIE | KPC_MS0 | KPC_MS1 | KPC_MS2 | KPC_MS3 | KPC_MS4 | KPC_MS5 | KPC_MS6 | KPC_MS7);
-+ /* reading the scan registers. */
-+ KPC |= 0x10000;
-+ mdelay(0x64);
-+ temp_key = KPMK & 0xff;
-+// KPC |= (KPC_ASACT | KPC_MS0 | KPC_MS1 | KPC_MS2 | KPC_MS3 | KPC_MS4 | KPC_MS5 | KPC_MS6 | KPC_MS7);
-+ KPC = kpc_res;
-+
-+ printk("temp_key = %x\n", temp_key);
-+
-+ if ( temp_key == 0x2 )
-+ {
-+ if(0 == panic_bug_used)
-+ {
-+ panic_bug_used = 1;
-+ BUG();
-+ }
-+ }
-+ }
-+#endif
-+
-+ spin_lock_irqsave(&keypad_lock,flags);
-+ if (!any_keys_down (keybitmap))
-+ {
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return;
-+ }
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ tmp = keybitmap[NUM_WORDS_IN_BITMAP-i-1];
-+ while ((bitnum = ffs(tmp)) != 0)
-+ {
-+ tmp &= ~(1<<(bitnum-1));
-+ /* see explanation at top of file */
-+ if ( (bitnum + (32*i)) == KEYPAD_POWER )
-+ {
-+ continue;
-+ }
-+ (void) add_to_keybuf( (bitnum + (32*i)) | KEYDOWN );
-+ }
-+ }
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ wake_up_interruptible (&keypad_wait);
-+
-+ mod_timer (&autorepeat_timer, jiffies + jiffies_to_next_repeat);
-+}
-+
-+#ifdef USE_RELEASE_TIMER
-+/*
-+ * Do a scan and add key events for anything that's different from the
-+ * last scan. We assume keypad_lock is locked when this is called
-+ * (by release_timer_went_off).
-+ */
-+static void
-+do_scan(void)
-+{
-+ unsigned long kpas_new, kpasmkp0_new, kpasmkp1_new;
-+ unsigned long kpdk_new;
-+ int change;
-+
-+ /* Initiate an automatic scan */
-+ KPC |= KPC_AS;
-+ /* Wait for the Scan On bit to go off before */
-+ /* reading the scan registers. */
-+ while (KPAS & KPAS_SO)
-+ {
-+ NULL;
-+ };
-+ kpas_new = KPAS;
-+ kpasmkp0_new = KPASMKP0;
-+ kpasmkp1_new = KPASMKP1;
-+ kpdk_new = KPDK;
-+ /*
-+ * reading the register turns off the "key pressed since last read" bit
-+ * if it was on, so we turn it off
-+ */
-+ kpdk_new &= ~KPDK_DKP;
-+ KPC &= ~KPC_AS;
-+
-+ change = ((kpas_new != kpas) ||
-+ (kpasmkp0_new != kpasmkp0) ||
-+ (kpasmkp1_new != kpasmkp1) ||
-+ (kpdk_new != kpdk));
-+
-+ if (change)
-+ {
-+ kpas = kpas_new;
-+ kpasmkp0 = kpasmkp0_new;
-+ kpasmkp1 = kpasmkp1_new;
-+ kpdk = kpdk_new;
-+
-+ copy_bitmap (oldkeybitmap, keybitmap);
-+ scan_to_bitmap (kpas, kpasmkp0, kpasmkp1, keybitmap);
-+#if defined(CONFIG_E680_P4A)
-+ if (kpdk & KPDK_DK0) /* screen lock key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ if (kpdk & KPDK_DK0) /* screen lock key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+ if (kpdk & KPDK_DK3)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ }
-+ if (kpdk & KPDK_DK5)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+
-+#elif defined(CONFIG_KEYPAD_A780)
-+ if (kpdk & KPDK_DK0) /* voice/camera key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+ add_events (oldkeybitmap, keybitmap);
-+
-+ wake_up_interruptible (&keypad_wait);
-+ }
-+}
-+#endif
-+
-+/*
-+ * set all words in the specified bitmap to 0
-+ */
-+static inline void set_bitmap_to_zero(unsigned long b[]) {
-+ int i;
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ b[i]=0;
-+ }
-+}
-+
-+/*
-+ * copy source bitmap to destination bitmap
-+ */
-+static inline void copy_bitmap(unsigned long dest[], unsigned long source[]) {
-+ int i;
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ dest[i]=source[i];
-+ }
-+}
-+
-+/*
-+ * Turn on the bit position in map for the specified key code.
-+ * Bit numbers start with 1 (not 0) and increase moving left within
-+ * words and within the array.
-+ * Bit 1 is the rightmost bit in map[NUM_WORDS_IN_BITMAP-1].
-+ * Bit 33 is the rightmost bit in map[NUM_WORDS_IN_BITMAP-2].
-+ */
-+static inline void
-+turn_on_bit(unsigned long map[], int code)
-+{
-+ int word, pos, p;
-+
-+ /* if we have 2 words, bits 1-32 are in map[1], 33-64 in map[0] */
-+ word = (NUM_WORDS_IN_BITMAP - 1) - ((code-1) / 32);
-+ /*
-+ * bit 1 is 1<<0, bit 2 is 1<<1, ... bit 32 is 1 << 31, all in map[1]
-+ * bit 33 is 1<<0, bit 34 is 1<<1, ... in map[0]
-+ * we want this:
-+ * code pos
-+ * 1 0
-+ * 2 1
-+ * ...
-+ * 31 30
-+ * 32 31
-+ * 33 0
-+ * 34 1
-+ * ...
-+ */
-+ pos = (p = (code % 32)) == 0 ? 31 : p-1;
-+ map[word] |= (1<<pos);
-+}
-+
-+/*
-+ * Turn off the bit position in map for the specified key code.
-+ * Bit positions start with 1 (not 0).
-+ */
-+static inline void
-+turn_off_bit(unsigned long map[], int code)
-+{
-+ int word, pos, p;
-+
-+ word = (NUM_WORDS_IN_BITMAP - 1) - ((code-1) / 32);
-+ pos = (p = (code % 32)) == 0 ? 31 : p-1;
-+ map[word] &= ~(1<<pos);
-+}
-+
-+/*
-+ * Return 1 if any bits are down in map[]
-+ */
-+static inline int
-+any_keys_down (unsigned long *map)
-+{
-+ int i;
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ /* don't count the power key */
-+ if ((i == 0) && (*map == 0x10))
-+ {
-+ map++;
-+ continue;
-+ }
-+ if (*map++)
-+ {
-+ return 1;
-+ }
-+ }
-+ return 0;
-+}
-+static int
-+__init keypad_init(void)
-+{
-+ int err;
-+
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_init\n");
-+#endif
-+
-+ set_bitmap_to_zero (oldkeybitmap);
-+ set_bitmap_to_zero (keybitmap);
-+ set_bitmap_to_zero (lastioctlbitmap);
-+
-+ /* set up gpio */
-+#if defined(CONFIG_KEYPAD_V700)
-+ pxa_gpio_mode(95 | GPIO_ALT_FN_1_IN); /* KP_MKIN<6> */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_1_IN); /* KP_MKIN<3> */
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_1_IN); /* KP_MKIN<4> */
-+ pxa_gpio_mode(99 | GPIO_ALT_FN_1_IN); /* KP_MKIN<5> */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+#elif defined(CONFIG_E680_P4A)
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN); /* KP_DKIN<0>, VR Key */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_1_IN); /* KP_DKIN<4>, power key */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN); /* KP_DKIN<0>, VR Key */
-+ pxa_gpio_mode(96 | GPIO_ALT_FN_1_IN); /* KP_DKIN<3>, GAME_A */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_1_IN); /* KP_DKIN<4>, power key */
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_1_IN); /* KP_DKIN<5>, GAME_B */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+ pxa_gpio_mode(GPIO_TC_MM_EN);
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ PGSR3 |= GPIO_bit(GPIO_TC_MM_EN);
-+#elif defined(CONFIG_KEYPAD_A780)
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN); /* KP_DKIN<0>, voice_rec */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_3_IN); /* KP_MKIN<3> */
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_3_IN); /* KP_MKIN<4> */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+ pxa_gpio_mode(107 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<4> */
-+#elif defined(CONFIG_KEYPAD_MAINSTONE)
-+ /* from Intel driver */
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(94 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(95 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(99 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+#endif
-+
-+ /* set keypad control register */
-+ KPC = (KPC_ASACT | /* automatic scan on activity */
-+ KPC_ME | KPC_DE | /* matrix and direct keypad enabled */
-+#if defined(CONFIG_KEYPAD_V700)
-+ (3<<23) | /* 4 columns */
-+ (6<<26) | /* 7 rows */
-+#elif defined(CONFIG_E680_P4A)
-+ (3<<23) | /* 4 columns */
-+ (2<<26) | /* 3 rows */
-+ (4<<6) | /* 4# direct key */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ (5<<23) | /* 4 columns */
-+ (4<<26) | /* 3 rows */
-+ (5<<6) | /* 5# direct keys */
-+#elif defined(CONFIG_KEYPAD_A780)
-+ KPC_IMKP |
-+ (4<<23) | /* 5 columns */
-+ (4<<26) | /* 5 rows */
-+ (0<<6) | /* 1# direct keys */
-+#endif
-+ KPC_MS7_0); /* scan all columns */
-+
-+ CKEN |= CKEN19_KEYPAD;
-+
-+ err = request_irq (IRQ_KEYPAD, kp_interrupt, 0, "Keypad", NULL);
-+ if (err)
-+ {
-+ printk (KERN_CRIT "can't register IRQ%d for keypad, error %d\n",
-+ IRQ_KEYPAD, err);
-+ CKEN &= ~CKEN19_KEYPAD;
-+ return -ENODEV;
-+ }
-+
-+ if (misc_register (&keypad_misc_device))
-+ {
-+ printk(KERN_ERR "Couldn't register keypad driver\n");
-+ return -EIO;
-+ }
-+ if (misc_register (&keypadB_misc_device))
-+ {
-+ printk(KERN_ERR "Couldn't register keypadB driver\n");
-+ misc_deregister(&keypad_misc_device);
-+ return -EIO;
-+ }
-+ if (misc_register (&keypadI_misc_device))
-+ {
-+ printk(KERN_ERR "Couldn't register keypadI driver\n");
-+ misc_deregister(&keypad_misc_device);
-+ misc_deregister(&keypadB_misc_device);
-+ return -EIO;
-+ }
-+
-+#ifdef USE_RELEASE_TIMER
-+ init_timer (&key_release_timer);
-+ key_release_timer.function = release_timer_went_off;
-+#endif
-+ init_timer (&autorepeat_timer);
-+ autorepeat_timer.function = autorepeat_timer_went_off;
-+
-+ /*
-+ * we want the phone to be able to tell the status of the screen
-+ * lock switch at power-up time
-+ */
-+ kpdk = KPDK; /* read direct key register */
-+ /*
-+ * reading the register turns off the "key pressed since last read" bit
-+ * if it was on, so we turn it off
-+ */
-+ kpdk &= ~KPDK_DKP;
-+#if defined(CONFIG_E680_P4A)
-+ if (kpdk & KPDK_DK0) /* VR key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4) /* Power key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+#elif defined(CONFIG_KEYPAD_E680)
-+ if (kpdk & KPDK_DK0) /* VR key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4) /* Power key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ if (kpdk & KPDK_DK3) /* GAME_A key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ }
-+ if (kpdk & KPDK_DK5) /* GAME_B key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+#elif defined(CONFIG_KEYPAD_A780)
-+ if (kpdk & KPDK_DK0) /* voice/camera key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+
-+#ifdef CONFIG_PM
-+ pm_dev = pm_register(PM_SYS_DEV, 0, button_pm_callback);
-+#if defined(CONFIG_E680_P4A)
-+/*93,97,100,101,102*/
-+ PKWR = 0xe4400;
-+/*103 104 105 106*/
-+ PGSR3 |= 0x780;
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+/*93,96,97,98,100,101,102*/
-+ PKWR = 0xee400;
-+/*103 104 105 106*/
-+ PGSR3 |= 0x780;
-+#endif
-+#if defined(CONFIG_KEYPAD_A780)
-+/*93,97,98,100,101,102*/
-+ PKWR = 0xec400;
-+/*103 104 105 106 107*/
-+ PGSR3 |= 0xf80;
-+#endif
-+#endif
-+
-+#if defined(CONFIG_KEYPAD_E680)
-+#ifdef CONFIG_PM
-+ keypadI_pm_dev = pm_register(PM_SYS_DEV, 0, keypadI_pm_callback);
-+ PGSR3 |= 0x8;
-+#endif
-+#endif
-+
-+ KPC |= (KPC_DIE | KPC_MIE);
-+ KPKDI = 0x40;
-+ return 0;
-+
-+}
-+
-+static void
-+__exit keypad_exit(void)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_exit\n");
-+#endif
-+ misc_deregister(&keypad_misc_device);
-+ misc_deregister(&keypadB_misc_device);
-+ misc_deregister(&keypadI_misc_device);
-+
-+#ifdef CONFIG_PM
-+ pm_unregister(pm_dev);
-+#endif
-+
-+#if defined(CONFIG_KEYPAD_E680)
-+#ifdef CONFIG_PM
-+ pm_unregister(keypadI_pm_dev);
-+#endif
-+#endif
-+
-+ CKEN &= ~CKEN19_KEYPAD;
-+}
-+
-+module_init (keypad_init);
-+module_exit (keypad_exit);
-Index: linux-2.6.16.5-a/drivers/misc/ezx/keypad.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/keypad.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,1499 @@
-+/*
-+ * linux/drivers/char/keypad.c
-+ *
-+ * (c) Copyright Motorola 2003, All rights reserved.
-+ */
-+
-+/*
-+ * This driver is for three devices: /dev/keypad, /dev/keypadB and
-+ * /dev/keypadI.
-+ * /dev/keypad would be used for reading the key event buffer.
-+ * It can be opened by one process at a time.
-+ * /dev/keypadB would be used for ioctl(KEYPAD_IOC_GETBITMAP).
-+ * It can be opened by one process at a time.
-+ * /dev/keypadI would be used for ioctl(KEYPAD_IOC_INSERT_EVENT).
-+ * It can be opened any number of times simultaneously.
-+ *
-+ * The bulverde specification is ambiguous about when interrupts happen
-+ * for released keys. We were told by Intel that we won't
-+ * get interrupts for released keys except in the case when multiple
-+ * keys were down and they've all been released. So we implemented
-+ * a timer to poll for changes in key states.
-+ *
-+ * The E680 P2 hardware gives us interrupts when any key is released,
-+ * whether it was the only key down or not, and whether it's the last
-+ * of multiple keys to be released or not. We don't know whether this
-+ * behavior will continue in future hardware releases, so the release
-+ * timer is still in the code, #ifdef'd with USE_RELEASE_TIMER. On the
-+ * P2 hardware, the code works with or without USE_RELEASE_TIMER defined.
-+ * If the release interrupts are always going to happen, we can remove
-+ * the #ifdef'd code.
-+ *
-+ * With the P2 hardware, the power key bit in the KPDK register is always
-+ * on. We don't know if this is correct behavior or not, but in any case
-+ * it certainly causes trouble to have that key autorepeating indefinitely,
-+ * or to be checking indefinitely for the key to be released (if we're doing
-+ * release polling).
-+ *
-+ * For now, any_keys_down() returns 0 if the power key is the only one down.
-+ * . At interrupt time, if the power key is the only one down we don't
-+ * set the autorepeat timer or release timer.
-+ * . When the release timer goes off, if the power key is the only one
-+ * still down we don't set the timer again.
-+ * . When the autorepeat timer goes off, if the power key is the only
-+ * one down we don't generate any events.
-+ * In autorepeat_timer_went_off, if there are non-power keys down, while we're
-+ * looking through the whole bitmap of keys down we ignore the power key.
-+ */
-+
-+#include <linux/tty.h>
-+#include <linux/init.h>
-+#include <linux/interrupt.h>
-+#include <linux/module.h>
-+#include <linux/poll.h>
-+#include <linux/miscdevice.h>
-+#include <linux/bitops.h>
-+#include <linux/param.h>
-+
-+#include <asm/hardware.h>
-+#include <asm/io.h>
-+#include <asm/irq.h>
-+#include <linux/pm.h>
-+#include <linux/apm_bios.h>
-+#include "keypad.h"
-+#include <asm/arch/irqs.h>
-+#include <asm/arch/pxa-regs.h>
-+
-+#include <asm/arch/ezx.h>
-+
-+#ifdef CONFIG_PM
-+static struct pm_dev *pm_dev;
-+static struct pm_dev *keypadI_pm_dev;
-+static int kpc_res,kpkdi_res;
-+#endif
-+static int GPIO_TC_MM_STATE = 1;
-+/*
-+ * This is the number of microseconds we wait before checking to see if any
-+ * keys have been released.
-+ */
-+#define RDELAY 200
-+
-+#define KEYBUF_EMPTY() (keybuf_start == keybuf_end)
-+#define KEYBUF_FULL() ( ((keybuf_end+1)%KEYBUF_SIZE) == keybuf_start)
-+#define KEYBUF_INC(x) ((x) = (((x)+1) % KEYBUF_SIZE))
-+
-+static int keypad_open (struct inode *, struct file *);
-+static int keypad_close (struct inode *, struct file *);
-+static int keypad_ioctl (struct inode *, struct file *,
-+ unsigned int, unsigned long);
-+static unsigned int keypad_poll (struct file *, poll_table *);
-+static ssize_t keypad_read (struct file *, char *, size_t, loff_t *);
-+
-+static int keypadB_open (struct inode *, struct file *);
-+static int keypadB_close (struct inode *, struct file *);
-+static int keypadB_ioctl (struct inode *, struct file *,
-+ unsigned int, unsigned long);
-+static unsigned int keypadB_poll (struct file *, poll_table *);
-+
-+static int keypadI_open(struct inode *, struct file *);
-+static int keypadI_close(struct inode *, struct file *);
-+static int keypadI_ioctl (struct inode *, struct file *,
-+ unsigned int, unsigned long);
-+
-+static irqreturn_t kp_interrupt (int, void *, struct pt_regs *);
-+#ifdef USE_RELEASE_TIMER
-+static void release_timer_went_off (unsigned long);
-+static void do_scan(void);
-+#endif
-+static void autorepeat_timer_went_off (unsigned long);
-+
-+static int add_to_keybuf (unsigned short);
-+static int add_events (unsigned long *, unsigned long *);
-+static int insert_event (unsigned short);
-+static unsigned short get_from_keybuf (void);
-+static void scan_to_bitmap
-+ (unsigned long, unsigned long, unsigned long, unsigned long *);
-+static inline void set_bitmap_to_zero(unsigned long b[]);
-+static inline void copy_bitmap(unsigned long dest[], unsigned long source[]);
-+static inline void turn_on_bit(unsigned long map[], int);
-+static inline void turn_off_bit(unsigned long map[], int);
-+static inline int any_keys_down (unsigned long *);
-+
-+/*
-+ * keybuf is a circular buffer to hold keypad events.
-+ * keybuf_start is the index of the first event.
-+ * keybuf_end is one more than the index of the last event.
-+ * The buffer is empty when keybuf_start == keybuf_end.
-+ * We only use KEYBUF_SIZE-1 entries in the buffer so we can tell
-+ * when it's full without needing another variable to tell us.
-+ * The buffer is full when (keybuf_end+1)%KEYBUF_SIZE == keybuf_start.
-+ */
-+static unsigned short keybuf[KEYBUF_SIZE];
-+static int keybuf_start = 0;
-+static int keybuf_end = 0;
-+
-+static DECLARE_WAIT_QUEUE_HEAD(keypad_wait);
-+static spinlock_t keypad_lock = SPIN_LOCK_UNLOCKED;
-+
-+static int reading_opens = 0;
-+static int bitmap_opens = 0;
-+
-+/* previous bitmap of keys down */
-+static unsigned long oldkeybitmap[NUM_WORDS_IN_BITMAP];
-+/* current bitmap of keys down */
-+static unsigned long keybitmap[NUM_WORDS_IN_BITMAP];
-+/* last bitmap read by ioctl */
-+static unsigned long lastioctlbitmap[NUM_WORDS_IN_BITMAP];
-+
-+static unsigned long kpas = 0; /* last value of kpas */
-+static unsigned long kpasmkp0 = 0; /* last value of kpasmkp0 */
-+static unsigned long kpasmkp1 = 0; /* last value of kpasmkp1 */
-+static unsigned long kpasmkp2 = 0; /* last value of kpasamkp2*/
-+static unsigned long kpdk = 0; /* last value of kpdk */
-+
-+#ifdef USE_RELEASE_TIMER
-+static struct timer_list key_release_timer;
-+static int key_release_interval = RDELAY * HZ/1000;
-+#endif
-+
-+static int do_autorepeat = 1;
-+static long jiffies_to_first_repeat = 30;
-+static long jiffies_to_next_repeat = 30;
-+static struct timer_list autorepeat_timer;
-+
-+extern int lockscreen_flag;
-+
-+static int
-+keypad_open(struct inode *inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG "keypad_open\n");
-+#endif
-+ spin_lock(keypad_lock);
-+ if (reading_opens > 0)
-+ {
-+ spin_unlock(keypad_lock);
-+ return -EBUSY;
-+ }
-+ reading_opens++;
-+ spin_unlock(keypad_lock);
-+
-+ return 0;
-+}
-+
-+static int
-+keypadB_open(struct inode *inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG "keypadB_open\n");
-+#endif
-+ spin_lock(keypad_lock);
-+ if (bitmap_opens > 0)
-+ {
-+ spin_unlock(keypad_lock);
-+ return -EBUSY;
-+ }
-+ bitmap_opens++;
-+ /*
-+ * poll returns when lastioctlbitmap is different from keybitmap.
-+ * we set lastioctlbitmap to keybitmap here so that a poll right
-+ * after an open returns when the bitmap is different from when
-+ * the open was done, not when the bitmap is different from the
-+ * last time some other process read it
-+ */
-+ copy_bitmap(lastioctlbitmap, keybitmap);
-+ spin_unlock(keypad_lock);
-+
-+ return 0;
-+}
-+
-+#if defined(CONFIG_KEYPAD_E680)
-+#ifdef CONFIG_PM
-+static int keypadI_pm_callback(struct pm_dev *pm_dev, pm_request_t req, void *data)
-+{
-+ switch(req)
-+ {
-+ case PM_SUSPEND:
-+ break;
-+ case PM_RESUME:
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ if(GPIO_TC_MM_STATE == 1)
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ else
-+ GPCR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ break;
-+ default:
-+ break;
-+ }
-+ return 0;
-+}
-+#endif
-+#endif
-+
-+static int
-+keypadI_open(struct inode *inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG "keypadI_open\n");
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ pxa_gpio_mode(GPIO_TC_MM_EN);
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+#endif
-+
-+ return 0;
-+}
-+
-+static int
-+keypad_close(struct inode * inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_close\n");
-+#endif
-+ /*
-+ * this decrement of reading_opens doesn't have to be protected because
-+ * it can only be executed to close the single open of /dev/keypad
-+ */
-+ reading_opens--;
-+ return 0;
-+}
-+
-+static int
-+keypadB_close(struct inode * inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypadB_close\n");
-+#endif
-+ /*
-+ * this decrement of bitmap_opens doesn't have to be protected because
-+ * it can only be executed to close the single open of /dev/keypadB
-+ */
-+ bitmap_opens--;
-+ return 0;
-+}
-+
-+static int
-+keypadI_close(struct inode * inode, struct file *file)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypadI_close\n");
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ pxa_gpio_mode(GPIO_TC_MM_EN);
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+#endif
-+
-+ return 0;
-+}
-+
-+/**
-+ * Add the specified event to the key buffer.
-+ * This should be called with keypad_lock locked.
-+ */
-+static int
-+add_to_keybuf (unsigned short event)
-+{
-+ if (KEYBUF_FULL())
-+ {
-+ return -ENOMEM;
-+ }
-+
-+ keybuf[keybuf_end] = event;
-+ KEYBUF_INC (keybuf_end);
-+
-+#ifdef CONFIG_APM
-+ apm_queue_event(KRNL_KEYPAD, NULL);
-+#endif
-+ //printk("add keypad event = %x\n", event);
-+ return 0;
-+}
-+
-+/*
-+ * code[c*8+r] is the key code for the key that's down when there's a 1
-+ * in column c, row r of the scan registers.
-+ */
-+
-+#if defined(CONFIG_KEYPAD_V700)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_UP, KEYPAD_DOWN, KEYPAD_LEFT, KEYPAD_RIGHT,
-+ KEYPAD_POUND, KEYPAD_0, KEYPAD_9, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_2, KEYPAD_4, KEYPAD_6, KEYPAD_8,
-+ KEYPAD_7, KEYPAD_SLEFT, KEYPAD_SRIGHT, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_MENU, KEYPAD_1, KEYPAD_3, KEYPAD_5,
-+ KEYPAD_STAR, KEYPAD_VOLUP, KEYPAD_VOLDOWN, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_CAMERA, KEYPAD_CLEAR, KEYPAD_CARRIER, KEYPAD_ACTIVATE,
-+ KEYPAD_SEND, KEYPAD_SMART, KEYPAD_VAVR, KEYPAD_NONE
-+};
-+
-+/* end CONFIG_KEYPAD_V700 */
-+#elif defined(CONFIG_E680_P4A)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_UP, KEYPAD_DOWN, KEYPAD_LEFT, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_RIGHT, KEYPAD_CENTER, KEYPAD_HOME, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_GAME_R, KEYPAD_NONE, KEYPAD_GAME_L, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_A, KEYPAD_B, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+};
-+
-+/* end CONFIG_E680_P4A */
-+#elif defined(CONFIG_KEYPAD_E680)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_UP, KEYPAD_DOWN, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_RIGHT, KEYPAD_LEFT, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_NONE, KEYPAD_GAME_R, KEYPAD_NONE, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_HOME, KEYPAD_GAME_L, KEYPAD_CENTER, KEYPAD_NONE,
-+ KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+
-+};
-+/*end CONFIG_KEYPAD_E680 */
-+#elif defined(CONFIG_KEYPAD_A780)
-+int
-+scanbit_to_keycode[] = {
-+ /* col 0 */
-+ KEYPAD_OK, KEYPAD_1, KEYPAD_4, KEYPAD_7,
-+ KEYPAD_STAR, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 1 */
-+ KEYPAD_MENU, KEYPAD_2, KEYPAD_5, KEYPAD_8,
-+ KEYPAD_0, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 2 */
-+ KEYPAD_CANCEL, KEYPAD_3, KEYPAD_6, KEYPAD_9,
-+ KEYPAD_POUND, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 3 */
-+ KEYPAD_JOG_UP, KEYPAD_JOG_MIDDLE, KEYPAD_JOG_DOWN, KEYPAD_LEFT,
-+ KEYPAD_DOWN, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+ /* col 4 */
-+ KEYPAD_CENTER, KEYPAD_HOME, KEYPAD_PTT, KEYPAD_UP,
-+ KEYPAD_RIGHT, KEYPAD_NONE, KEYPAD_NONE, KEYPAD_NONE,
-+};
-+#endif
-+
-+/*
-+ * Decode the specified scan register values into the bitmap pointed
-+ * to by the last argument. The bitmap will contain a 1
-+ * for each key that's down.
-+ *
-+ * Only the 1st two of the four scan registers are used.
-+ */
-+static void
-+scan_to_bitmap(unsigned long kpas, unsigned long kpasmkp0,
-+ unsigned long kpasmkp1, unsigned long bitmap[])
-+{
-+ int row, col;
-+ int bitnum;
-+ unsigned long scanmap;
-+#if defined(CONFIG_KEYPAD_A780)
-+ int keep;
-+#endif
-+
-+ set_bitmap_to_zero (bitmap);
-+
-+ if ((kpas & KPAS_MUKP) == MUKP_NO_KEYS)
-+ {
-+ return;
-+ }
-+
-+ if ((kpas & KPAS_MUKP) == MUKP_ONE_KEY)
-+ {
-+ row = (kpas & KPAS_RP) >> 4;
-+ col = kpas & KPAS_CP;
-+ turn_on_bit (bitmap, scanbit_to_keycode[col*8 + row]);
-+ return;
-+ }
-+
-+ /* reach here if multiple keys */
-+ scanmap = (kpasmkp0 & 0x7f) | ((kpasmkp0 & 0x7f0000) >> 8) |
-+ ((kpasmkp1 & 0x7f) << 16) | ((kpasmkp1 & 0x7f0000) << 8);
-+ while ((bitnum = ffs(scanmap)) != 0)
-+ {
-+ /*
-+ * ffs returns bit numbers starting with 1, so subtract 1 to index
-+ * into scanbit_to_keycode[]
-+ */
-+ turn_on_bit (bitmap, scanbit_to_keycode[bitnum-1]);
-+ scanmap &= ~(1<<(bitnum-1));
-+ }
-+#if defined(CONFIG_KEYPAD_A780)
-+ kpasmkp2 = KPASMKP2;
-+ if ((kpasmkp1 & 0x180000) || (kpasmkp2 & 0x18))
-+ keep = 1;
-+ else
-+ keep = 0;
-+ if ( keep )
-+ kpasmkp2 &= 0xfffffffe;
-+ while ((bitnum = ffs(kpasmkp2)) !=0)
-+ {
-+ turn_on_bit (bitmap, scanbit_to_keycode[32+bitnum-1]);
-+ kpasmkp2 &= ~(1<<(bitnum-1));
-+ }
-+#endif
-+}
-+
-+/*
-+ * Add events indicated by the difference between the last scan (oldbitmap)
-+ * and this one (newbitmap) to the input buffer.
-+ * Return nonzero right away if any of the events can't be added.
-+ * A zero return means all the events were added.
-+ * This should be called with keypad_lock locked.
-+ */
-+static int
-+add_events (unsigned long *oldbitmap, unsigned long *newbitmap)
-+{
-+ unsigned long tmpmap, onebitmap;
-+ int bitnum, i, ret;
-+
-+ /* generate events for keys that were down before and are up now */
-+ for (i=NUM_WORDS_IN_BITMAP-1;i>=0;i--)
-+ {
-+ tmpmap = oldbitmap[i];
-+ while ((bitnum = ffs(tmpmap)) != 0)
-+ {
-+ onebitmap = 1<<(bitnum-1);
-+ if ((newbitmap[i] & onebitmap) == 0)
-+ {
-+ ret = add_to_keybuf(bitnum + (32*(NUM_WORDS_IN_BITMAP-1-i) | KEYUP));
-+ if (ret < 0)
-+ {
-+ return ret;
-+ }
-+ }
-+ tmpmap &= ~onebitmap;
-+ }
-+ }
-+ /* generate events for down keys that were up before */
-+ for (i=NUM_WORDS_IN_BITMAP-1;i>=0;i--)
-+ {
-+ tmpmap = newbitmap[i];
-+ while ((bitnum = ffs(tmpmap)) != 0)
-+ {
-+ onebitmap = 1<<(bitnum-1);
-+ if ((oldbitmap[i] & onebitmap) == 0)
-+ {
-+ ret = add_to_keybuf
-+ (bitnum + (32*(NUM_WORDS_IN_BITMAP-1-i) | KEYDOWN));
-+ if (ret < 0)
-+ {
-+ return ret;
-+ }
-+ }
-+ tmpmap &= ~onebitmap;
-+ }
-+ }
-+ return 0;
-+}
-+
-+/*
-+ * do the INSERT_EVENT ioctl
-+ */
-+static int
-+insert_event (unsigned short event)
-+{
-+ unsigned long flags;
-+ int ret;
-+
-+ if (KEYCODE(event) > KEYPAD_MAXCODE)
-+ {
-+ printk(KERN_WARNING " inserted key code %d too big\n",
-+ KEYCODE(event));
-+ return -EINVAL;
-+ }
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ if (KEY_IS_DOWN(event))
-+ {
-+ turn_on_bit(keybitmap, KEYCODE(event));
-+ }
-+ else
-+ {
-+ turn_off_bit (keybitmap, event);
-+ }
-+ if ((ret = add_to_keybuf(event)) < 0)
-+ {
-+ spin_unlock_irqrestore(&keypad_lock,flags);
-+ return ret;
-+ }
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ wake_up_interruptible (&keypad_wait);
-+ return 0;
-+}
-+
-+static int
-+keypad_ioctl (struct inode *inode, struct file *file,
-+ unsigned int cmd, unsigned long arg)
-+{
-+ int interval; /* debounce interval */
-+ int imkp; /* Ignore Multiple Key Press bit */
-+ struct autorepeatinfo ar; /* autorepeat information */
-+
-+#ifdef KDEBUG
-+ printk (KERN_DEBUG "keypad_ioctl: 0x%x\n", cmd);
-+#endif
-+ switch (cmd)
-+ {
-+ case KEYPAD_IOC_INSERT_EVENT:
-+ return insert_event ((unsigned short)arg);
-+ break;
-+ case KEYPAD_IOC_GET_DEBOUNCE_INTERVAL:
-+ interval = KPKDI & KPKDI_BITS;
-+ return put_user(interval, (unsigned long *)arg);
-+ break;
-+ case KEYPAD_IOC_SET_DEBOUNCE_INTERVAL:
-+ interval = (unsigned short)arg;
-+ if (interval > KPKDI_BITS)
-+ {
-+ return -EINVAL;
-+ }
-+ KPKDI &= ~KPKDI_BITS;
-+ KPKDI |= interval;
-+ break;
-+ case KEYPAD_IOC_GET_IMKP_SETTING:
-+ imkp = ((KPC & KPC_IMKP) == KPC_IMKP);
-+ return put_user(imkp, (unsigned char *)arg);
-+ break;
-+ case KEYPAD_IOC_SET_IMKP_SETTING:
-+ imkp = (unsigned char)arg;
-+ if (imkp)
-+ {
-+ KPC |= KPC_IMKP;
-+ }
-+ else
-+ {
-+ KPC &= ~KPC_IMKP;
-+ }
-+ break;
-+ case KEYPAD_IOC_SET_AUTOREPEAT:
-+ if (copy_from_user (&ar, (void *)arg,
-+ sizeof(struct autorepeatinfo)) != 0)
-+ {
-+ return -EFAULT;
-+ }
-+ do_autorepeat = ar.r_repeat;
-+ /* times are specified in milliseconds; convert to jiffies */
-+ jiffies_to_first_repeat = ar.r_time_to_first_repeat * HZ/1000;
-+ jiffies_to_next_repeat = ar.r_time_between_repeats * HZ/1000;
-+ break;
-+ default:
-+ return -ENOTTY;
-+ }
-+ return 0;
-+}
-+
-+static int
-+keypadB_ioctl (struct inode *inode, struct file *file,
-+ unsigned int cmd, unsigned long arg)
-+{
-+ unsigned long flags;
-+ int ret;
-+
-+#ifdef KDEBUG
-+ printk (KERN_DEBUG "keypadB_ioctl: 0x%x\n", cmd);
-+#endif
-+ if (cmd == KEYPAD_IOC_INSERT_EVENT)
-+ {
-+ return insert_event ((unsigned short)arg);
-+ }
-+ else if (cmd == KEYPAD_IOC_GETBITMAP)
-+ {
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ ret = copy_to_user ((void *)arg, keybitmap,
-+ NUM_WORDS_IN_BITMAP * sizeof(unsigned long));
-+ copy_bitmap (lastioctlbitmap, keybitmap);
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return (ret != 0) ? -EFAULT : 0;
-+ }
-+ else
-+ {
-+ return -ENOTTY;
-+ }
-+}
-+
-+static int
-+keypadI_ioctl (struct inode *inode, struct file *file,
-+ unsigned int cmd, unsigned long arg)
-+{
-+ unsigned long flags;
-+ int ret;
-+
-+#ifdef KDEBUG
-+ printk (KERN_DEBUG "keypadI_ioctl: 0x%x\n", cmd);
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ if( cmd == KEYPADI_TURN_ON_LED )
-+ {
-+ GPCR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ GPIO_TC_MM_STATE = 0;
-+ PGSR3 &= ~GPIO_bit(GPIO_TC_MM_EN);
-+ return 0;
-+ }
-+ if( cmd == KEYPADI_TURN_OFF_LED )
-+ {
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ GPIO_TC_MM_STATE = 1;
-+ PGSR3 |= GPIO_bit(GPIO_TC_MM_EN);
-+ return 0;
-+ }
-+#endif
-+
-+ if (cmd == KEYPAD_IOC_INSERT_EVENT)
-+ {
-+ return insert_event ((unsigned short)arg);
-+ }
-+ else if (cmd == KEYPAD_IOC_GETBITMAP)
-+ {
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ ret = copy_to_user ((void *)arg, keybitmap,
-+ NUM_WORDS_IN_BITMAP * sizeof(unsigned long));
-+ copy_bitmap (lastioctlbitmap, keybitmap);
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return (ret != 0) ? -EFAULT : 0;
-+ }
-+ else
-+ {
-+ return -ENOTTY;
-+ }
-+}
-+
-+static unsigned int
-+keypad_poll( struct file *file, poll_table * wait )
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_poll\n");
-+#endif
-+ poll_wait(file, &keypad_wait, wait);
-+
-+ if (!KEYBUF_EMPTY())
-+ {
-+ return (POLLIN | POLLRDNORM);
-+ }
-+ return 0;
-+}
-+
-+static unsigned int
-+keypadB_poll( struct file *file, poll_table * wait )
-+{
-+ int i;
-+
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypadB_poll\n");
-+#endif
-+ poll_wait(file, &keypad_wait, wait);
-+
-+ for (i=0; i < NUM_WORDS_IN_BITMAP; i++)
-+ {
-+ if (lastioctlbitmap[i] != keybitmap[i])
-+ {
-+ return (POLLIN | POLLRDNORM);
-+ }
-+ }
-+ return 0;
-+}
-+
-+static unsigned short
-+get_from_keybuf(void)
-+{
-+ unsigned short event;
-+ unsigned long flags;
-+
-+ spin_lock_irqsave(&keypad_lock, flags);
-+ event = keybuf[keybuf_start];
-+ KEYBUF_INC (keybuf_start);
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return event;
-+}
-+
-+static ssize_t
-+keypad_read(struct file *file, char *buf, size_t count, loff_t *ptr)
-+{
-+ int i, ret;
-+ unsigned short event;
-+
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_read\n");
-+#endif
-+ /* Can't seek (pread) on this device */
-+ if (ptr != &file->f_pos)
-+ {
-+ return -ESPIPE;
-+ }
-+
-+ if (count == 0)
-+ {
-+ return 0;
-+ }
-+
-+ if (KEYBUF_EMPTY())
-+ {
-+ /* buffer is empty */
-+ /* if not blocking return */
-+ if (file->f_flags & O_NONBLOCK)
-+ {
-+ return -EAGAIN;
-+ }
-+ /* blocking, so wait for input */
-+ ret = wait_event_interruptible(keypad_wait, !KEYBUF_EMPTY());
-+ if (ret)
-+ {
-+ return ret;
-+ }
-+ }
-+
-+ i = 0;
-+ /* copy events until we have what the user asked for or we run out */
-+ while ((i+1 < count) && !KEYBUF_EMPTY())
-+ {
-+ event = get_from_keybuf();
-+ if ((ret = put_user(event, (unsigned short *)buf)) != 0)
-+ {
-+ return ret;
-+ }
-+ buf += EVENTSIZE;
-+ i += EVENTSIZE;
-+ }
-+ return i;
-+}
-+
-+#ifdef CONFIG_PM
-+static int button_pm_callback(struct pm_dev *pm_dev, pm_request_t req, void *data)
-+{
-+ int pksr;
-+
-+ pksr = PKSR;
-+ PKSR = 0xfffff;
-+ switch(req)
-+ {
-+ case PM_SUSPEND:
-+ kpc_res = KPC;
-+ kpkdi_res = KPKDI;
-+ set_bitmap_to_zero (oldkeybitmap);
-+ set_bitmap_to_zero (keybitmap);
-+ set_bitmap_to_zero (lastioctlbitmap);
-+ kpas = 0;
-+ kpasmkp0 = 0;
-+ kpasmkp1 = 0;
-+ kpasmkp2 = 0;
-+ kpdk = 0;
-+ break;
-+ case PM_RESUME:
-+ KPC = kpc_res;
-+ KPKDI = kpkdi_res;
-+#ifdef CONFIG_APM
-+#if defined(CONFIG_E680_P4A)
-+ if (pksr & 0xe4400) /*93 97 100 101 102 key is pressed (switch on) */
-+ {
-+ apm_queue_event(KRNL_KEYPAD);
-+ if (pksr & 0x400)
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+ if (pksr & 0xee400) /*93 96 97 98 190 101 102 key is pressed */
-+ {
-+ apm_queue_event(KRNL_KEYPAD);
-+ if (pksr & 0x400)
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ if (pksr & 0x2000)
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ if (pksr & 0x8000)
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+#endif
-+#if defined(CONFIG_KEYPAD_A780)
-+ printk("pksr = %x\n",pksr);
-+ if (pksr & 0xec400) /* 93 97 98 100 101 102 key is pressed */
-+ {
-+ apm_queue_event(KRNL_KEYPAD);
-+ if (pksr & 0x400)
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+#endif
-+
-+ break;
-+ }
-+ return 0;
-+}
-+#endif
-+
-+/* for /dev/keypad */
-+static struct file_operations
-+keypad_fops = {
-+ read: keypad_read,
-+ llseek: no_llseek,
-+ poll: keypad_poll,
-+ ioctl: keypad_ioctl,
-+ open: keypad_open,
-+ release: keypad_close,
-+};
-+
-+static struct miscdevice
-+keypad_misc_device = {
-+ KEYPAD_MINOR,
-+ KEYPAD_NAME,
-+ &keypad_fops,
-+};
-+
-+/*
-+ * for /dev/keypadB.
-+ * read() isn't defined here. calls to read() will return -1 with EINVAL.
-+ */
-+static struct file_operations
-+keypadB_fops = {
-+ llseek: no_llseek,
-+ poll: keypadB_poll,
-+ ioctl: keypadB_ioctl,
-+ open: keypadB_open,
-+ release: keypadB_close,
-+};
-+
-+static struct miscdevice
-+keypadB_misc_device = {
-+ KEYPAD_BITMAP_MINOR,
-+ KEYPAD_BITMAP_NAME,
-+ &keypadB_fops,
-+};
-+
-+/*
-+ * for /dev/keypadI.
-+ * read() isn't defined here. calls to read() will return -1 with EINVAL.
-+ */
-+static struct file_operations
-+keypadI_fops = {
-+ llseek: no_llseek,
-+ ioctl: keypadI_ioctl,
-+ open: keypadI_open,
-+ release: keypadI_close,
-+};
-+
-+static struct miscdevice
-+keypadI_misc_device = {
-+ KEYPAD_INSERT_MINOR,
-+ KEYPAD_INSERT_NAME,
-+ &keypadI_fops,
-+};
-+
-+#ifdef CONFIG_PANIC_LOG
-+static u32 panic_bug_used =0;
-+#endif
-+
-+/* Interrupt Handler for KEYPAD */
-+static irqreturn_t
-+kp_interrupt(int irq, void *ptr, struct pt_regs *regs)
-+{
-+ unsigned long flags;
-+ unsigned long kpc_val;
-+
-+#ifdef USE_RELEASE_TIMER
-+ del_timer (&key_release_timer);
-+#endif
-+ del_timer (&autorepeat_timer);
-+ spin_lock_irqsave(&keypad_lock,flags);
-+
-+ /* ack interrupt */
-+ kpc_val = KPC;
-+
-+ /* matrix interrupt */
-+ if (kpc_val & KPC_MI)
-+ {
-+/*
-+ * The Intel driver turned on KPC_AS here. It doesn't seem that we
-+ * would need to do that, because getting an interrupt means that
-+ * a scan was just done. For now, I've commented out the setting
-+ * and clearing of this bit.
-+ KPC |= KPC_AS;
-+ */
-+ while (KPAS & KPAS_SO)
-+ {
-+ /* Wait for the Scan On bit to go off before */
-+ /* reading the scan registers. */
-+ NULL;
-+ };
-+
-+ kpas = KPAS;
-+ kpasmkp0 = KPASMKP0;
-+ kpasmkp1 = KPASMKP1;
-+ kpasmkp2 = KPASMKP2;
-+
-+ }
-+
-+ /* direct interrupt */
-+ if (kpc_val & KPC_DI)
-+ {
-+ kpdk = KPDK;
-+ /*
-+ * reading the register turns off the "key pressed since last read"
-+ * bit if it was on, so we turn it off
-+ */
-+ kpdk &= ~KPDK_DKP;
-+ }
-+#ifdef CONFIG_PANIC_LOG
-+ if ((kpdk & KPDK_DK0)&&(kpasmkp1& 0x00020000))
-+ {
-+ if(0 == panic_bug_used)
-+ {
-+ panic_bug_used = 1;
-+ BUG();
-+ }
-+ }
-+#endif
-+ copy_bitmap (oldkeybitmap, keybitmap);
-+ scan_to_bitmap (kpas, kpasmkp0, kpasmkp1, keybitmap);
-+#if defined(CONFIG_E680_P4A)
-+ if (kpdk & KPDK_DK0) /* VR key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ if (kpdk & KPDK_DK0) /* VR key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+ if (kpdk & KPDK_DK3)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ }
-+ if (kpdk & KPDK_DK5)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+
-+#elif defined(CONFIG_KEYPAD_A780)
-+ if (kpdk & KPDK_DK0) /* voice/camera key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+
-+ (void) add_events (oldkeybitmap, keybitmap);
-+
-+ /* If any keys are down, set a timer to check for key release */
-+ /* and one for autorepeat if that's on. */
-+ if (any_keys_down (keybitmap))
-+ {
-+#ifdef USE_RELEASE_TIMER
-+ key_release_timer.expires = (jiffies + key_release_interval);
-+ add_timer (&key_release_timer);
-+#endif
-+ if (do_autorepeat)
-+ {
-+ autorepeat_timer.expires = (jiffies + jiffies_to_first_repeat);
-+ add_timer (&autorepeat_timer);
-+ }
-+ }
-+
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ wake_up_interruptible (&keypad_wait);
-+ //printk("keypad interrupt occurred\n");
-+ return IRQ_HANDLED;
-+}
-+
-+#ifdef USE_RELEASE_TIMER
-+/*
-+ * This is called when the key release timer goes off. That's the
-+ * only time it should be called. Check for changes in what keys
-+ * are down.
-+ */
-+static void
-+release_timer_went_off(unsigned long unused)
-+{
-+ unsigned long flags;
-+
-+ spin_lock_irqsave(&keypad_lock,flags);
-+ do_scan();
-+ /* If any keys are still down, set the timer going again. */
-+ if (any_keys_down (keybitmap))
-+ {
-+ mod_timer (&key_release_timer, jiffies + key_release_interval);
-+ }
-+ else
-+ {
-+ del_timer (&autorepeat_timer);
-+ }
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+}
-+#endif
-+
-+/*
-+ * This is called when the autorepeat timer goes off.
-+ */
-+static void
-+autorepeat_timer_went_off(unsigned long unused)
-+{
-+ int i, bitnum;
-+ unsigned long tmp;
-+ unsigned long flags;
-+
-+ spin_lock_irqsave(&keypad_lock,flags);
-+ if (!any_keys_down (keybitmap))
-+ {
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ return;
-+ }
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ tmp = keybitmap[NUM_WORDS_IN_BITMAP-i-1];
-+ while ((bitnum = ffs(tmp)) != 0)
-+ {
-+ tmp &= ~(1<<(bitnum-1));
-+ /* see explanation at top of file */
-+ if ( (bitnum + (32*i)) == KEYPAD_POWER )
-+ {
-+ continue;
-+ }
-+ (void) add_to_keybuf( (bitnum + (32*i)) | KEYDOWN );
-+ }
-+ }
-+ spin_unlock_irqrestore(&keypad_lock, flags);
-+ wake_up_interruptible (&keypad_wait);
-+
-+ mod_timer (&autorepeat_timer, jiffies + jiffies_to_next_repeat);
-+}
-+
-+#ifdef USE_RELEASE_TIMER
-+/*
-+ * Do a scan and add key events for anything that's different from the
-+ * last scan. We assume keypad_lock is locked when this is called
-+ * (by release_timer_went_off).
-+ */
-+static void
-+do_scan(void)
-+{
-+ unsigned long kpas_new, kpasmkp0_new, kpasmkp1_new;
-+ unsigned long kpdk_new;
-+ int change;
-+
-+ /* Initiate an automatic scan */
-+ KPC |= KPC_AS;
-+ /* Wait for the Scan On bit to go off before */
-+ /* reading the scan registers. */
-+ while (KPAS & KPAS_SO)
-+ {
-+ NULL;
-+ };
-+ kpas_new = KPAS;
-+ kpasmkp0_new = KPASMKP0;
-+ kpasmkp1_new = KPASMKP1;
-+ kpdk_new = KPDK;
-+ /*
-+ * reading the register turns off the "key pressed since last read" bit
-+ * if it was on, so we turn it off
-+ */
-+ kpdk_new &= ~KPDK_DKP;
-+ KPC &= ~KPC_AS;
-+
-+ change = ((kpas_new != kpas) ||
-+ (kpasmkp0_new != kpasmkp0) ||
-+ (kpasmkp1_new != kpasmkp1) ||
-+ (kpdk_new != kpdk));
-+
-+ if (change)
-+ {
-+ kpas = kpas_new;
-+ kpasmkp0 = kpasmkp0_new;
-+ kpasmkp1 = kpasmkp1_new;
-+ kpdk = kpdk_new;
-+
-+ copy_bitmap (oldkeybitmap, keybitmap);
-+ scan_to_bitmap (kpas, kpasmkp0, kpasmkp1, keybitmap);
-+#if defined(CONFIG_E680_P4A)
-+ if (kpdk & KPDK_DK0) /* screen lock key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ if (kpdk & KPDK_DK0) /* screen lock key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ /* power key is connected to GPIO97 as GPIO input */
-+ if (kpdk & KPDK_DK3)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ }
-+ if (kpdk & KPDK_DK5)
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+
-+#elif defined(CONFIG_KEYPAD_A780)
-+ if (kpdk & KPDK_DK0) /* voice/camera key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+ add_events (oldkeybitmap, keybitmap);
-+
-+ wake_up_interruptible (&keypad_wait);
-+ }
-+}
-+#endif
-+
-+/*
-+ * set all words in the specified bitmap to 0
-+ */
-+static inline void set_bitmap_to_zero(unsigned long b[]) {
-+ int i;
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ b[i]=0;
-+ }
-+}
-+
-+/*
-+ * copy source bitmap to destination bitmap
-+ */
-+static inline void copy_bitmap(unsigned long dest[], unsigned long source[]) {
-+ int i;
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ dest[i]=source[i];
-+ }
-+}
-+
-+/*
-+ * Turn on the bit position in map for the specified key code.
-+ * Bit numbers start with 1 (not 0) and increase moving left within
-+ * words and within the array.
-+ * Bit 1 is the rightmost bit in map[NUM_WORDS_IN_BITMAP-1].
-+ * Bit 33 is the rightmost bit in map[NUM_WORDS_IN_BITMAP-2].
-+ */
-+static inline void
-+turn_on_bit(unsigned long map[], int code)
-+{
-+ int word, pos, p;
-+
-+ /* if we have 2 words, bits 1-32 are in map[1], 33-64 in map[0] */
-+ word = (NUM_WORDS_IN_BITMAP - 1) - ((code-1) / 32);
-+ /*
-+ * bit 1 is 1<<0, bit 2 is 1<<1, ... bit 32 is 1 << 31, all in map[1]
-+ * bit 33 is 1<<0, bit 34 is 1<<1, ... in map[0]
-+ * we want this:
-+ * code pos
-+ * 1 0
-+ * 2 1
-+ * ...
-+ * 31 30
-+ * 32 31
-+ * 33 0
-+ * 34 1
-+ * ...
-+ */
-+ pos = (p = (code % 32)) == 0 ? 31 : p-1;
-+ map[word] |= (1<<pos);
-+}
-+
-+/*
-+ * Turn off the bit position in map for the specified key code.
-+ * Bit positions start with 1 (not 0).
-+ */
-+static inline void
-+turn_off_bit(unsigned long map[], int code)
-+{
-+ int word, pos, p;
-+
-+ word = (NUM_WORDS_IN_BITMAP - 1) - ((code-1) / 32);
-+ pos = (p = (code % 32)) == 0 ? 31 : p-1;
-+ map[word] &= ~(1<<pos);
-+}
-+
-+/*
-+ * Return 1 if any bits are down in map[]
-+ */
-+static inline int
-+any_keys_down (unsigned long *map)
-+{
-+ int i;
-+ for (i=0;i<NUM_WORDS_IN_BITMAP;i++)
-+ {
-+ /* don't count the power key */
-+ if ((i == 0) && (*map == 0x10))
-+ {
-+ map++;
-+ continue;
-+ }
-+ if (*map++)
-+ {
-+ return 1;
-+ }
-+ }
-+ return 0;
-+}
-+static int
-+__init keypad_init(void)
-+{
-+ int err;
-+
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_init\n");
-+#endif
-+
-+ set_bitmap_to_zero (oldkeybitmap);
-+ set_bitmap_to_zero (keybitmap);
-+ set_bitmap_to_zero (lastioctlbitmap);
-+
-+ /* set up gpio */
-+#if defined (CONFIG_KEYPAD_V700)
-+ pxa_gpio_mode(95 | GPIO_ALT_FN_1_IN); /* KP_MKIN<6> */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_1_IN); /* KP_MKIN<3> */
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_1_IN); /* KP_MKIN<4> */
-+ pxa_gpio_mode(99 | GPIO_ALT_FN_1_IN); /* KP_MKIN<5> */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+#elif defined(CONFIG_E680_P4A)
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN); /* KP_DKIN<0>, VR Key */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_1_IN); /* KP_DKIN<4>, power key */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN); /* KP_DKIN<0>, VR Key */
-+ pxa_gpio_mode(96 | GPIO_ALT_FN_1_IN); /* KP_DKIN<3>, GAME_A */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_1_IN); /* KP_DKIN<4>, power key */
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_1_IN); /* KP_DKIN<5>, GAME_B */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+ pxa_gpio_mode(GPIO_TC_MM_EN);
-+ GPDR(GPIO_TC_MM_EN) |= GPIO_bit(GPIO_TC_MM_EN);
-+ GPSR(GPIO_TC_MM_EN) = GPIO_bit(GPIO_TC_MM_EN);
-+ PGSR3 |= GPIO_bit(GPIO_TC_MM_EN);
-+#elif defined (CONFIG_KEYPAD_A780)
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN); /* KP_DKIN<0>, voice_rec */
-+ pxa_gpio_mode(97 | GPIO_ALT_FN_3_IN); /* KP_MKIN<3> */
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_3_IN); /* KP_MKIN<4> */
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+ pxa_gpio_mode(107 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<4> */
-+#elif defined(CONFIG_KEYPAD_MAINSTONE)
-+ /* from Intel driver */
-+ pxa_gpio_mode(93 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(94 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(95 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(98 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(99 | GPIO_ALT_FN_1_IN);
-+ pxa_gpio_mode(100 | GPIO_ALT_FN_1_IN); /* KP_MKIN<0> */
-+ pxa_gpio_mode(101 | GPIO_ALT_FN_1_IN); /* KP_MKIN<1> */
-+ pxa_gpio_mode(102 | GPIO_ALT_FN_1_IN); /* KP_MKIN<2> */
-+ pxa_gpio_mode(103 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<0> */
-+ pxa_gpio_mode(104 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<1> */
-+ pxa_gpio_mode(105 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<2> */
-+ pxa_gpio_mode(106 | GPIO_ALT_FN_2_OUT); /* KP_MKOUT<3> */
-+#endif
-+
-+ /* set keypad control register */
-+ KPC = (KPC_ASACT | /* automatic scan on activity */
-+ KPC_ME | KPC_DE | /* matrix and direct keypad enabled */
-+#if defined (CONFIG_KEYPAD_V700)
-+ (3<<23) | /* 4 columns */
-+ (6<<26) | /* 7 rows */
-+#elif defined(CONFIG_E680_P4A)
-+ (3<<23) | /* 4 columns */
-+ (2<<26) | /* 3 rows */
-+ (4<<6) | /* 4# direct key */
-+#elif defined(CONFIG_KEYPAD_E680)
-+ (5<<23) | /* 4 columns */
-+ (4<<26) | /* 3 rows */
-+ (5<<6) | /* 5# direct keys */
-+#elif defined(CONFIG_KEYPAD_A780)
-+ (4<<23) | /* 5 columns */
-+ (4<<26) | /* 5 rows */
-+ (0<<6) | /* 1# direct keys */
-+#endif
-+ KPC_MS_ALL); /* scan all columns */
-+
-+ CKEN |= CKEN19_KEYPAD;
-+
-+ err = request_irq (IRQ_KEYPAD, kp_interrupt, 0, "Keypad", NULL);
-+ if (err)
-+ {
-+ printk (KERN_CRIT "can't register IRQ%d for keypad, error %d\n",
-+ IRQ_KEYPAD, err);
-+ CKEN &= ~CKEN19_KEYPAD;
-+ return -ENODEV;
-+ }
-+
-+ if (misc_register (&keypad_misc_device))
-+ {
-+ printk(KERN_ERR "Couldn't register keypad driver\n");
-+ return -EIO;
-+ }
-+ if (misc_register (&keypadB_misc_device))
-+ {
-+ printk(KERN_ERR "Couldn't register keypadB driver\n");
-+ misc_deregister(&keypad_misc_device);
-+ return -EIO;
-+ }
-+ if (misc_register (&keypadI_misc_device))
-+ {
-+ printk(KERN_ERR "Couldn't register keypadI driver\n");
-+ misc_deregister(&keypad_misc_device);
-+ misc_deregister(&keypadB_misc_device);
-+ return -EIO;
-+ }
-+
-+#ifdef USE_RELEASE_TIMER
-+ init_timer (&key_release_timer);
-+ key_release_timer.function = release_timer_went_off;
-+#endif
-+ init_timer (&autorepeat_timer);
-+ autorepeat_timer.function = autorepeat_timer_went_off;
-+
-+ /*
-+ * we want the phone to be able to tell the status of the screen
-+ * lock switch at power-up time
-+ */
-+ kpdk = KPDK; /* read direct key register */
-+ /*
-+ * reading the register turns off the "key pressed since last read" bit
-+ * if it was on, so we turn it off
-+ */
-+ kpdk &= ~KPDK_DKP;
-+#if defined(CONFIG_E680_P4A)
-+ if (kpdk & KPDK_DK0) /* VR key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4) /* Power key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+#elif defined(CONFIG_KEYPAD_E680)
-+ if (kpdk & KPDK_DK0) /* VR key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+ if (kpdk & KPDK_DK4) /* Power key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_POWER);
-+ }
-+ if (kpdk & KPDK_DK3) /* GAME_A key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_A);
-+ }
-+ if (kpdk & KPDK_DK5) /* GAME_B key is pressed (switch on) */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_B);
-+ }
-+#elif defined(CONFIG_KEYPAD_A780)
-+ if (kpdk & KPDK_DK0) /* voice/camera key is pressed */
-+ {
-+ turn_on_bit (keybitmap, KEYPAD_CAMERA_VOICE);
-+ }
-+#endif
-+
-+#ifdef CONFIG_PM
-+ pm_dev = pm_register(PM_SYS_DEV, 0, button_pm_callback);
-+#if defined(CONFIG_E680_P4A)
-+/*93,97,100,101,102*/
-+ PKWR = 0xe4400;
-+/*103 104 105 106*/
-+ PGSR3 |= 0x780;
-+#endif
-+#if defined(CONFIG_KEYPAD_E680)
-+/*93,96,97,98,100,101,102*/
-+ PKWR = 0xee400;
-+/*103 104 105 106*/
-+ PGSR3 |= 0x780;
-+#endif
-+#if defined(CONFIG_KEYPAD_A780)
-+/*93,97,98,100,101,102*/
-+ PKWR = 0xec400;
-+/*103 104 105 106 107*/
-+ PGSR3 |= 0xf80;
-+#endif
-+#endif
-+
-+#if defined(CONFIG_KEYPAD_E680)
-+#ifdef CONFIG_PM
-+ keypadI_pm_dev = pm_register(PM_SYS_DEV, 0, keypadI_pm_callback);
-+ PGSR3 |= 0x8;
-+#endif
-+#endif
-+
-+ KPC |= (KPC_DIE | KPC_MIE);
-+ KPKDI = 0x40;
-+ return 0;
-+}
-+
-+static void
-+__exit keypad_exit(void)
-+{
-+#ifdef KDEBUG
-+ printk(KERN_DEBUG " keypad_exit\n");
-+#endif
-+ misc_deregister(&keypad_misc_device);
-+ misc_deregister(&keypadB_misc_device);
-+ misc_deregister(&keypadI_misc_device);
-+
-+#ifdef CONFIG_PM
-+ pm_unregister(pm_dev);
-+#endif
-+
-+#if defined(CONFIG_KEYPAD_E680)
-+#ifdef CONFIG_PM
-+ pm_unregister(keypadI_pm_dev);
-+#endif
-+#endif
-+
-+ CKEN &= ~CKEN19_KEYPAD;
-+}
-+
-+module_init (keypad_init);
-+module_exit (keypad_exit);
-Index: linux-2.6.16.5-a/drivers/misc/ezx/keypad.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/keypad.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,104 @@
-+#ifndef __DRIVER_CHAR_KEYPAD_H
-+#define __DRIVER_CHAR_KEYPAD_H
-+
-+/*
-+ * linux/drivers/char/keypad.h
-+ *
-+ * (c) Copyright Motorola 2003, All rights reserved.
-+ */
-+
-+#include <asm/hardware.h>
-+#include <linux/keypad.h>
-+
-+/**
-+ * /dev/keypad is the main keypad device. Opening this device provides access
-+ * for read(), ioctl() and poll()/select(). Only one process at a time
-+ * can open this device.
-+ */
-+#define KEYPAD_NAME "keypad"
-+#define KEYPAD_MINOR 0xf0 /* 240 */
-+
-+/**
-+ * /dev/keypadB can be opened for ioctl() and poll()/select().
-+ * Only one process at a time can open this device.
-+ */
-+#define KEYPAD_BITMAP_NAME "keypadB"
-+#define KEYPAD_BITMAP_MINOR 0xf1 /* 241 */
-+
-+/**
-+ * /dev/keypadI can be opened for ioctl(INSERT_EVENT).
-+ * Any number of devices can open this simultaneously.
-+ */
-+#define KEYPAD_INSERT_NAME "keypadI"
-+#define KEYPAD_INSERT_MINOR 0xf2 /* 242 */
-+
-+/*
-+ * KEYBUF_SIZE must be a power of 2 to avoid performance-destroying
-+ * integer divisions in the compiled code.
-+ * Each keypad event is a short, so a buffer n bytes long can hold
-+ * n/2 keypad events.
-+ */
-+#define KEYBUF_SIZE 256
-+
-+#if 0
-+#define KPC __REG(0x41500000) /* control register */
-+#define KPDK __REG(0x41500008) /* direct key register */
-+#define KPAS __REG(0x41500020) /* automatic scan register */
-+#define KPASMKP0 __REG(0x41500028) /* auto scan multiple key press reg 0 */
-+#define KPASMKP1 __REG(0x41500030) /* auto scan multiple key press reg 1 */
-+#define KPKDI __REG(0x41500048) /* debounce interval register */
-+
-+#define KPC_RSRVD0 0x80000000 /* reserved */
-+#define KPC_AS 0x40000000 /* automatic scan */
-+#define KPC_ASACT 0x20000000 /* automatic scan on activity */
-+#define KPC_MKRN 0x1c000000 /* number of matrix keypad rows - 1 */
-+#define KPC_MKCN 0x03800000 /* number of matrix keypad columns - 1 */
-+#define KPC_MI 0x00400000 /* matrix interrupt, reset when read */
-+#define KPC_IMKP 0x00200000 /* ignore multiple key press */
-+#define KPC_MS7_0 0x001fe000 /* MS7-MS0 assert to scan columns */
-+#define KPC_MS7 0x00100000 /* MS7 assert to scan column */
-+#define KPC_MS6 0x00080000 /* MS6 assert to scan column */
-+#define KPC_MS5 0x00040000 /* MS5 assert to scan column */
-+#define KPC_MS4 0x00020000 /* MS4 assert to scan column */
-+#define KPC_MS3 0x00010000 /* MS3 assert to scan column */
-+#define KPC_MS2 0x00008000 /* MS2 assert to scan column */
-+#define KPC_MS1 0x00004000 /* MS1 assert to scan column */
-+#define KPC_MS0 0x00002000 /* MS0 assert to scan column */
-+#define KPC_ME 0x00001000 /* matrix keypad enable */
-+#define KPC_MIE 0x00000800 /* matrix interrupt enable */
-+#define KPC_RSRVD1 0x00000600 /* reserved */
-+#define KPC_DKN 0x000001c0 /* number of direct keys - 1 */
-+#define KPC_DI 0x00000020 /* direct interrupt bit, reset when read */
-+#define KPC_RSRVD2 0x00000010 /* reserved */
-+#define KPC_REE1 0x00000008 /* rotary encoder 1 enable */
-+#define KPC_REE0 0x00000004 /* rotary encoder 0 enable */
-+#define KPC_DE 0x00000002 /* direct keypad enable */
-+#define KPC_DIE 0x00000001 /* direct keypad interrupt enable */
-+
-+#define KPC_7rows 0x18000000 /* 6 in KPC_MKRN */
-+#define KPC_4cols 0x01800000 /* 3 in KPC_MKCN */
-+/*
-+ * bits in Direct Key register
-+ */
-+#define KPDK_DKP (0x1 << 31) /* on if direct key pressed since last read */
-+#define KPDK_DK7 (0x1 << 7)
-+#define KPDK_DK6 (0x1 << 6)
-+#define KPDK_DK5 (0x1 << 5)
-+#define KPDK_DK4 (0x1 << 4)
-+#define KPDK_DK3 (0x1 << 3)
-+#define KPDK_DK2 (0x1 << 2)
-+#define KPDK_DK1 (0x1 << 1)
-+#define KPDK_DK0 (0x1 << 0)
-+
-+
-+#endif
-+
-+#define KPKDI_BITS 0xff /* bits in KPKDI register for debounce interval */
-+#define KPAS_MUKP 0x7c000000 /* KPAS bits 30-26 */
-+#define MUKP_NO_KEYS 0x00000000 /* value of MUKP if no keys are down */
-+#define MUKP_ONE_KEY 0x04000000 /* value of MUKP if one key is down */
-+#define KPAS_SO 0x80000000 /* scan on bit */
-+#define KPAS_RP 0x000000f0 /* row of single key */
-+#define KPAS_CP 0x0000000f /* column of single key */
-+
-+#endif /* __DRIVER_CHAR_KEYPAD_H */
-Index: linux-2.6.16.5-a/drivers/misc/ezx/log.c
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/log.c 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,287 @@
-+/*
-+ * Kernel panic log interface for Linux.
-+ *
-+ * Copyright (c) 2000 Motorola
-+ *
-+ * This program is free software; you can redistribute it and/or
-+ * modify it under the terms of the GNU General Public License
-+ * as published by the Free Software Foundation; either version
-+ * 2 of the License, or (at your option) any later version.
-+ *
-+ * 0.01 2003-07-01 zxf <w19962@motorola.com>
-+ * - initial release
-+ */
-+
-+#include <linux/module.h>
-+#include <linux/fs.h>
-+#include <linux/miscdevice.h>
-+#include <linux/string.h>
-+#include <linux/init.h>
-+#include <linux/poll.h>
-+#include <linux/rtc.h>
-+#include <linux/notifier.h>
-+#include <asm/bitops.h>
-+#include <asm/hardware.h>
-+#include <asm/irq.h>
-+
-+#include "log.h"
-+
-+#include <linux/fb.h>
-+#include "../video/pxafb.h"
-+
-+#define LOGDRV_MINOR 188
-+
-+static struct log_area *log = NULL;
-+struct log_cmdline log_cmdline;
-+
-+static int __init log_setup(char *str)
-+{
-+ struct log_cmdline *c;
-+
-+ c = &log_cmdline;
-+ memcpy(c->name, str, sizeof(c->name));
-+
-+ return 1;
-+}
-+
-+__setup("paniclog=", log_setup);
-+
-+void panic_trig(const char *str, struct pt_regs *regs, int err)
-+{
-+ if (log)
-+ die(str, regs, err);
-+}
-+EXPORT_SYMBOL(panic_trig);
-+
-+int log_register(struct log_area *log_f)
-+{
-+ if (strcmp(log_cmdline.name, log_f->name) == 0)
-+ log = log_f;
-+ return 0;
-+}
-+
-+int log_unregister(struct log_area *log_f)
-+{
-+ log = NULL;
-+ return 0;
-+}
-+
-+static loff_t logdrv_lseek(struct file *file, loff_t offset, int orig)
-+{
-+ switch (orig) {
-+ case 0:
-+ /* SEEK_SET */
-+ file->f_pos = offset;
-+ break;
-+ case 1:
-+ /* SEEK_CUR */
-+ file->f_pos += offset;
-+ break;
-+ case 2:
-+ /* SEEK_END */
-+ file->f_pos = log->size + offset;
-+ break;
-+ default:
-+ return -EINVAL;
-+ }
-+
-+ if (file->f_pos < 0)
-+ file->f_pos = 0;
-+ else if (file->f_pos >= log->size)
-+ file->f_pos = log->size - 1;
-+
-+ return file->f_pos;
-+}
-+
-+static int logdrv_open(struct inode *inode, struct file *file)
-+{
-+ if (!log) {
-+ printk("Not register mechine specific log structure!\n");
-+ return -ENODEV;
-+ }
-+
-+ return 0;
-+}
-+
-+static int logdrv_close(struct inode *inode, struct file *file)
-+{
-+ return 0;
-+}
-+
-+static ssize_t logdrv_read(struct file *file, char *buf, size_t count, loff_t *ppos)
-+{
-+ unsigned long p = *ppos;
-+
-+ if (count < 0)
-+ return -EINVAL;
-+
-+ if (count > log->size - p)
-+ count = log->size - p;
-+ if (log->read)
-+ return log->read(buf, count, ppos);
-+
-+ if (copy_to_user((void *)buf, (void *)(log->start + *ppos), count))
-+ return -EFAULT;
-+
-+ *ppos += count;
-+ return count;
-+}
-+
-+static struct file_operations logdrv_fops = {
-+ owner: THIS_MODULE,
-+ llseek: logdrv_lseek,
-+ read: logdrv_read,
-+ open: logdrv_open,
-+ release: logdrv_close,
-+};
-+
-+static struct miscdevice logdrv_miscdev = {
-+ LOGDRV_MINOR,
-+ "log drv",
-+ &logdrv_fops
-+};
-+
-+extern void logbuf_info(char **st, unsigned long *cnt);
-+extern struct pxafb_info *pxafbi;
-+extern int get_irq_list(char *buf);
-+
-+extern atomic_t vm_committed_space;
-+void dump_proc_meminfo(void)
-+{
-+ struct sysinfo i;
-+ char buf[1024];
-+ int len;
-+ int pg_size, committed;
-+
-+#define K(x) ((x) << (PAGE_SHIFT - 10))
-+#define B(x) ((unsigned long long)(x) << PAGE_SHIFT)
-+
-+ si_meminfo(&i);
-+ si_swapinfo(&i);
-+
-+ pg_size = atomic_read(&page_cache_size) - i.bufferram ;
-+ committed = atomic_read(&vm_committed_space);
-+
-+ len = sprintf(buf, " total: used: free: shared: buffers: cached:\n"
-+ "Mem: %8Lu %8Lu %8Lu %8Lu %8Lu %8Lu\n"
-+ "Swap: %8Lu %8Lu %8Lu\n",
-+ B(i.totalram), B(i.totalram-i.freeram), B(i.freeram),
-+ B(i.sharedram), B(i.bufferram),
-+ B(pg_size), B(i.totalswap),
-+ B(i.totalswap-i.freeswap), B(i.freeswap));
-+
-+ len += sprintf(buf+len,
-+ "MemTotal: %8lu kB\n"
-+ "MemFree: %8lu kB\n"
-+ "MemShared: %8lu kB\n"
-+ "Buffers: %8lu kB\n"
-+ "Cached: %8lu kB\n"
-+ "SwapCached: %8lu kB\n"
-+ "Active: %8u kB\n"
-+ "Inactive: %8u kB\n"
-+ "HighTotal: %8lu kB\n"
-+ "HighFree: %8lu kB\n"
-+ "LowTotal: %8lu kB\n"
-+ "LowFree: %8lu kB\n"
-+ "SwapTotal: %8lu kB\n"
-+ "SwapFree: %8lu kB\n"
-+ "Committed_AS: %8u kB\n",
-+ K(i.totalram),
-+ K(i.freeram),
-+ K(i.sharedram),
-+ K(i.bufferram),
-+ K(pg_size - swapper_space.nrpages),
-+ K(swapper_space.nrpages),
-+ K(nr_active_pages),
-+ K(nr_inactive_pages),
-+ K(i.totalhigh),
-+ K(i.freehigh),
-+ K(i.totalram-i.totalhigh),
-+ K(i.freeram-i.freehigh),
-+ K(i.totalswap),
-+ K(i.freeswap),
-+ K(committed));
-+
-+ printk(KERN_EMERG " [meminfo] len 0x%x\n %s\n", len, buf);
-+}
-+
-+int panic_log_notify(struct notifier_block *self, unsigned long code, void *unused)
-+{
-+ unsigned long count;
-+ char *start;
-+
-+ printk(KERN_EMERG "****** panic time: %d ******\n", OSCR); //RCNR);
-+
-+ if(pxafbi)
-+ {
-+ int i;
-+ unsigned long *p;
-+ printk(KERN_EMERG " pxafbi->map_cpu: 0x%x, size 0x%x\n", pxafbi->map_cpu, pxafbi->map_size);
-+ p = (unsigned long)(pxafbi->map_cpu);
-+ for(i=0; i<(pxafbi->map_size/sizeof(unsigned long)); i++)
-+ *p++ = 0x0;
-+ printk(KERN_EMERG "****** panic time: %d ******\n", OSCR);
-+ }
-+
-+ if(1)
-+ {
-+ // cat /proc/interrupts
-+ char buf[1024];
-+ int len;
-+
-+ len = get_irq_list(buf);
-+ printk(KERN_EMERG " [interrupts] len 0x%x\n", len);
-+ printk(KERN_EMERG "%s\n", buf);
-+ }
-+
-+ if(1)
-+ {
-+ // cat /proc/meminfo
-+ dump_proc_meminfo();
-+ }
-+
-+ /* Below 2 lines will overwrite useful information if log_buf is not large enough */
-+ printk(KERN_EMERG "****** show task state when panic *******\n");
-+ show_state();
-+
-+ /* get syslog buf info: start position, number of chars */
-+ logbuf_info(&start, &count);
-+
-+ /* write information to log area */
-+ if (log && log->write)
-+ log->write(start, count);
-+
-+ printk(KERN_EMERG "OK, Now we exit panic log function!\n");
-+
-+ return NOTIFY_DONE;
-+}
-+
-+static struct notifier_block panic_log_nb = {
-+ panic_log_notify,
-+ NULL,
-+ 0
-+};
-+
-+extern struct notifier_block *panic_notifier_list;
-+static int __init log_init(void)
-+{
-+ misc_register(&logdrv_miscdev);
-+ return notifier_chain_register(&panic_notifier_list, &panic_log_nb);
-+}
-+
-+static void __exit log_exit(void)
-+{
-+ notifier_chain_unregister(&panic_notifier_list, &panic_log_nb);
-+ misc_deregister(&logdrv_miscdev);
-+}
-+
-+module_init(log_init);
-+module_exit(log_exit);
-+
-+EXPORT_SYMBOL(log_register);
-+EXPORT_SYMBOL(log_unregister);
-+
-+MODULE_AUTHOR("zxf <w19962@motorola.com>");
-+MODULE_DESCRIPTION("Kernel panic log interface");
-+MODULE_LICENSE("GPL");
-+
-Index: linux-2.6.16.5-a/drivers/misc/ezx/log.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/drivers/misc/ezx/log.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,35 @@
-+/*
-+ * Kernel panic log interface for Linux on A760(XScale PXA262).
-+ *
-+ * Copyright (c) 2000 Motorola
-+ *
-+ * This program is free software; you can redistribute it and/or
-+ * modify it under the terms of the GNU General Public License
-+ * as published by the Free Software Foundation; either version
-+ * 2 of the License, or (at your option) any later version.
-+ *
-+ * 0.01 2003-07-01 zxf <w19962@motorola.com>
-+ * - initial release
-+ */
-+
-+#ifndef _PANIC_LOG_H_
-+#define _PANIC_LOG_H_
-+
-+#include <linux/fs.h>
-+
-+struct log_area {
-+ char name[8];
-+ unsigned long start;
-+ unsigned long size;
-+ ssize_t (*write) (const char *buf, size_t count);
-+ ssize_t (*read) (const char *buf, size_t count, loff_t *ppos);
-+};
-+
-+struct log_cmdline {
-+ char name[8];
-+};
-+
-+extern int log_register(struct log_area *log_f);
-+extern int log_unregister(struct log_area *log_f);
-+
-+#endif /* _PANIC_LOG_H_ */
-Index: linux-2.6.16.5-a/include/linux/keypad.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/include/linux/keypad.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,137 @@
-+#ifndef __LINUX_KEYPAD_H
-+#define __LINUX_KEYPAD_H
-+
-+/*
-+ * include/linux/keypad.h
-+ *
-+ * (c) Copyright Motorola 2003, All rights reserved.
-+ */
-+
-+#include <linux/ioctl.h>
-+
-+#define KEYDOWN 0x8000
-+#define KEYUP 0x0000
-+
-+#define EVENTSIZE sizeof(short)
-+#define KEY_IS_DOWN(x) ((x) & KEYDOWN)
-+#define KEYCODE(x) ((x) & 0x7fff)
-+
-+struct autorepeatinfo {
-+ int r_repeat; /* 1 to do autorepeat, 0 to not do it */
-+ int r_time_to_first_repeat; /* time to first repeat in milliseconds */
-+ int r_time_between_repeats; /* time between repeats in milliseconds */
-+};
-+
-+#define KEYPAD_IOCTL_BASE 'k'
-+
-+/*
-+ * return the bitmap of keys currently down.
-+ * The bitmap is an array of NUM_WORDS_IN_BITMAP unsigned long words.
-+ * We count the bits starting with 1 in the rightmost position in
-+ * the rightmost (highest-indexed) word. If NUM_WORDS_IN_BITMAP is two,
-+ * the bitmap looks like this:
-+ * 0 1
-+ * ----------------------------------------------------
-+ * | 64 63 ........... 34 33 | 32 31 ............. 2 1 |
-+ * ----------------------------------------------------
-+ * Bit n corresponds to key code n.
-+ */
-+
-+#define KEYPAD_IOC_GETBITMAP _IOR(KEYPAD_IOCTL_BASE,1,unsigned long *)
-+#define NUM_WORDS_IN_BITMAP 2
-+
-+/**
-+ * put the specified event on the keypad's input queue and update the bitmap.
-+ * The exact event as specified will be returned by read() when it
-+ * reaches the front of the queue. A key press event consists of
-+ * the key code or'd with KEYDOWN. A key release event consists of
-+ * just the key code.
-+ */
-+#define KEYPAD_IOC_INSERT_EVENT _IOW(KEYPAD_IOCTL_BASE,2,unsigned short)
-+
-+/**
-+ * have the driver interpret the specified scan register values as
-+ * if it had gotten an interrupt. The passed-in argument is a pointer
-+ * to three consecutive 32-bit words in this order: KPAS, KPASMKP0, KPASMKP1.
-+ */
-+#define KEYPAD_IOC_INSERTKEYSCAN _IOW(KEYPAD_IOCTL_BASE,3,unsigned long *)
-+
-+/* get the hardware debounce interval (in milliseconds) */
-+#define KEYPAD_IOC_GET_DEBOUNCE_INTERVAL \
-+ _IOR(KEYPAD_IOCTL_BASE,4,unsigned short *)
-+
-+/* set the hardware debounce interval (in milliseconds) */
-+#define KEYPAD_IOC_SET_DEBOUNCE_INTERVAL \
-+ _IOW(KEYPAD_IOCTL_BASE,4,unsigned short)
-+
-+/* get "Ignore Multiple Key Press" bit; 1 means they are ignored */
-+#define KEYPAD_IOC_GET_IMKP_SETTING _IOR(KEYPAD_IOCTL_BASE,5,unsigned char *)
-+
-+/* set "Ignore Multiple Key Press" bit; 1 means they will be ignored */
-+#define KEYPAD_IOC_SET_IMKP_SETTING _IOW(KEYPAD_IOCTL_BASE,5,unsigned char)
-+
-+/*
-+ * specify what to do about autorepeat on held keys
-+ * the 3rd argument is a pointer to a struct autorepeat
-+ */
-+#define KEYPAD_IOC_SET_AUTOREPEAT _IOW(KEYPAD_IOCTL_BASE,6,unsigned long *)
-+
-+#define KEYPADI_TURN_ON_LED 1
-+#define KEYPADI_TURN_OFF_LED 0
-+/*
-+ * the constant KEY_k is both the code for key k in an event returned by
-+ * read() and the bit position for key k in the bitmap returned by
-+ * ioctl(KEYPAD_IOC_GETBITMAP).
-+ */
-+#define KEYPAD_NONE 0
-+
-+#define KEYPAD_0 1
-+#define KEYPAD_1 2
-+#define KEYPAD_2 3
-+#define KEYPAD_3 4
-+#define KEYPAD_4 5
-+#define KEYPAD_5 6
-+#define KEYPAD_6 7
-+#define KEYPAD_7 8
-+#define KEYPAD_8 9
-+#define KEYPAD_9 10
-+
-+#define KEYPAD_UP 11
-+#define KEYPAD_DOWN 12
-+#define KEYPAD_LEFT 13
-+#define KEYPAD_RIGHT 14
-+#define KEYPAD_POUND 15
-+#define KEYPAD_STAR 16
-+#define KEYPAD_MENU 17
-+#define KEYPAD_SLEFT 18
-+#define KEYPAD_SRIGHT 19
-+#define KEYPAD_VOLUP 20
-+#define KEYPAD_VOLDOWN 21
-+#define KEYPAD_CAMERA 22
-+#define KEYPAD_CLEAR 23
-+#define KEYPAD_CARRIER 24
-+#define KEYPAD_ACTIVATE 25
-+#define KEYPAD_SEND 26
-+#define KEYPAD_SMART 27
-+#define KEYPAD_VAVR 28
-+
-+#define KEYPAD_CENTER 29
-+#define KEYPAD_HOME 30
-+#define KEYPAD_A 31
-+#define KEYPAD_B 32
-+#define KEYPAD_GAME_R 33
-+#define KEYPAD_GAME_L 34
-+#define KEYPAD_CAMERA_VOICE 35
-+//#define KEYPAD_SCREEN_LOCK 36
-+#define KEYPAD_POWER 37
-+
-+#define KEYPAD_OK 38
-+#define KEYPAD_CANCEL 39
-+#define KEYPAD_PTT 40
-+#define KEYPAD_JOG_UP 41
-+#define KEYPAD_JOG_MIDDLE 42
-+#define KEYPAD_JOG_DOWN 43
-+
-+#define KEYPAD_MAXCODE 43
-+
-+#endif /* __LINUX_KEYPAD_H */
-Index: linux-2.6.16.5-a/include/linux/wrapper.h
-===================================================================
---- /dev/null 1970-01-01 00:00:00.000000000 +0000
-+++ linux-2.6.16.5-a/include/linux/wrapper.h 2006-05-04 17:07:04.000000000 +0200
-@@ -0,0 +1,7 @@
-+#ifndef _WRAPPER_H_
-+#define _WRAPPER_H_
-+
-+#define mem_map_reserve(p) set_bit(PG_reserved, &((p)->flags))
-+#define mem_map_unreserve(p) clear_bit(PG_reserved, &((p)->flags))
-+
-+#endif /* _WRAPPER_H_ */
-Index: linux-2.6.16.5-a/include/linux/apm_bios.h
-===================================================================
---- linux-2.6.16.5-a.orig/include/linux/apm_bios.h 2006-05-04 17:06:50.000000000 +0200
-+++ linux-2.6.16.5-a/include/linux/apm_bios.h 2006-05-04 17:07:04.000000000 +0200
-@@ -208,6 +208,31 @@
- #define APM_CAP_RESUME_SUSPEND_PCMCIA 0x0080 /* Resume on PCMCIA Ring */
-
- /*
-+ * kernel event definitions for our ezx platform
-+ */
-+enum
-+{
-+ KRNL_ACCS_ATTACH,
-+ KRNL_ACCS_DETACH,
-+ KRNL_BLUETOOTH,
-+ KRNL_TOUCHSCREEN,
-+ KRNL_KEYPAD,
-+ KRNL_RTC,
-+ KRNL_FLIP_ON,
-+ KRNL_FLIP_OFF,
-+ KRNL_VOICE_REC,
-+ KRNL_ICL,
-+ KRNL_BP,
-+ KRNL_BP_WDI,
-+ KRNL_PROC_INACT,
-+ KRNL_IDLE_TIMEOUT,
-+ KRNL_SCREEN_LOCK,
-+ KRNL_SCREEN_UNLOCK
-+};
-+
-+
-+
-+/*
- * ioctl operations
- */
- #include <linux/ioctl.h>