[Armadeus-commitlog] SF.net SVN: armadeus: [644] trunk/buildroot/target/device/armadeus/linux/ ker
Brought to you by:
sszy
|
From: <th...@us...> - 2007-09-19 13:45:20
|
Revision: 644
http://armadeus.svn.sourceforge.net/armadeus/?rev=644&view=rev
Author: thom25
Date: 2007-09-19 06:45:18 -0700 (Wed, 19 Sep 2007)
Log Message:
-----------
Fix dead lock
Fix scheduling while atomic problem
Change sequencer
Allow scan of inputs (BAT1, BAT2, AUX and TEMP)
Fix problem with HWMON flag
Modified Paths:
--------------
trunk/buildroot/target/device/armadeus/linux/kernel-patches/2.6.18.1/076-linux-2.6.18-tsc2102-armadeus-patch.diff
Modified: trunk/buildroot/target/device/armadeus/linux/kernel-patches/2.6.18.1/076-linux-2.6.18-tsc2102-armadeus-patch.diff
===================================================================
--- trunk/buildroot/target/device/armadeus/linux/kernel-patches/2.6.18.1/076-linux-2.6.18-tsc2102-armadeus-patch.diff 2007-09-18 09:22:07 UTC (rev 643)
+++ trunk/buildroot/target/device/armadeus/linux/kernel-patches/2.6.18.1/076-linux-2.6.18-tsc2102-armadeus-patch.diff 2007-09-19 13:45:18 UTC (rev 644)
@@ -11,28 +11,64 @@
}
static void tsc2102_coords(int x, int y, int z1, int z2)
---- linux-2.6.18.1/drivers/spi/tsc2102.c 2007-08-05 23:03:42.000000000 +0200
-+++ linux-2.6.18.1.mod/drivers/spi/tsc2102.c 2007-08-05 22:39:44.000000000 +0200
-@@ -51,7 +51,8 @@
+--- linux-2.6.18.1/drivers/spi/Kconfig 2007-09-16 07:52:11.000000000 +0200
++++ linux-2.6.18.1.mod/drivers/spi/Kconfig 2007-09-16 06:36:48.000000000 +0200
+@@ -133,6 +133,7 @@ comment "SPI Protocol Masters"
+ #
+ config SPI_TSC2102
+ depends on SPI_MASTER
++ depends on HWMON = n || HWMON
+ tristate "TSC2102 codec support"
+ ---help---
+ Say Y here if you want support for the TSC2102 chip. It
+--- linux-2.6.18.1/drivers/spi/tsc2102.c 2007-09-16 07:52:11.000000000 +0200
++++ linux-2.6.18.1.mod/drivers/spi/tsc2102.c 2007-09-16 07:09:23.000000000 +0200
+@@ -2,8 +2,10 @@
+ * drivers/spi/tsc2102.c
+ *
+ * TSC2102 interface driver.
+- *
+- * Copyright (c) 2005 Andrzej Zaborowski <ba...@za...>
++ * Copyright (C) 2007 Armadeus systems (nc)
++ * -> fix dead locks, reorganize state machine
++ * -> fix scheduling while atomic and hwmon support
++ * Copyright (c) 2005 Andrzej Zaborowski <ba...@za...>
+ *
+ * This package is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+@@ -51,7 +53,10 @@
#define TSC2102_ADC_T1_CONTROL 0x2bf4
#define TSC2102_ADC_T2_CONTROL 0x33f4
#define TSC2102_ADC_DAV 0x4000
-#define TSC2102_ADC_INT_REF 0x0016
-+#define TSC2102_ADC_INT_REF_125 0x0016
-+#define TSC2102_ADC_INT_REF_250 0x0017
++#define TSC2102_ADC_PEN 0x0000
++#define TSC2102_ADC_INT_REF_125 0x0016
++#define TSC2102_ADC_INT_REF_250 0x0017
++#define TSC2102_ADC_REF TSC2102_ADC_INT_REF_250 /*2.5V*/
#define TSC2102_ADC_EXT_REF 0x0002
#define TSC2102_CONFIG_TIMES 0x0008
#define TSC2102_RESET 0xbb00
-@@ -87,7 +88,7 @@
+@@ -86,14 +91,14 @@ struct tsc2102_spi_req {
+
struct tsc2102_dev {
struct tsc2102_config *pdata;
- spinlock_t lock, lock_sync;
+- spinlock_t lock, lock_sync;
- struct clk *bclk_ck;
++ spinlock_t lock;
++ struct mutex lock_sync;
+// struct clk *bclk_ck; TODO add clock mechanism to i.MX ???
- int state; /* 0: TS, 1: Portscan, 2-3: Temps */
+- int state; /* 0: TS, 1: Portscan, 2-3: Temps */
++ int state; /* Scan modes */
struct timer_list ts_timer; /* Busy-wait for PEN UP */
-@@ -307,7 +308,9 @@
+ struct timer_list mode_timer; /* Change .state every some time */
+- int pendown;
+- int data_pending;
++ int touch_in_progress;
+ uint16_t status, adc_status, adc_data[4];
+ tsc2102_touch_t touch_cb;
+ tsc2102_coords_t coords_cb;
+@@ -307,7 +312,9 @@ int tsc2102_ ## cb(cb_t handler) \
}
tsc2102_cb_register_func(touch_cb, tsc2102_touch_t)
@@ -42,97 +78,578 @@
tsc2102_cb_register_func(ports_cb, tsc2102_ports_t)
tsc2102_cb_register_func(temp1_cb, tsc2102_temp_t)
tsc2102_cb_register_func(temp2_cb, tsc2102_temp_t)
-@@ -411,22 +414,25 @@
- TSC2102_TS_ADC_CTRL, TSC2102_ADC_ADST,
+@@ -345,242 +352,153 @@ static void tsc2102_print_dav(void)
+ }
+ #endif
+
+-static void tsc2102_complete_dummy(struct tsc2102_dev *dev)
+-{
+-}
++static void tsc2102_complete_dummy(struct tsc2102_dev *dev){}
+
+ static inline void tsc2102_touchscreen_mode(struct tsc2102_dev *dev)
+ {
++ spin_lock_irq(&dev->lock);
++ dev->touch_in_progress = 1;
++
+ /* Scan X, Y, Z1, Z2, chip controlled, 12-bit, 16 samples, 500 usec */
+ tsc2102_write_async(&dev->req_mode,
+ TSC2102_TS_ADC_CTRL, TSC2102_ADC_TS_CONTROL,
tsc2102_complete_dummy);
++ spin_unlock_irq(&dev->lock);
+ }
+-static inline void tsc2102_portscan_mode(struct tsc2102_dev *dev)
+-{
+- /* Scan BAT1, BAT2, AUX, 12-bit, 16 samples, 500 usec */
+- tsc2102_write_async(&dev->req_mode,
+- TSC2102_TS_ADC_CTRL, TSC2102_ADC_SCAN_CONTROL,
+- tsc2102_complete_dummy);
+-}
+-
+-static inline void tsc2102_temp1_mode(struct tsc2102_dev *dev)
+-{
+- /* Scan TEMP1, 12-bit, 16 samples, 500 usec */
+- tsc2102_write_async(&dev->req_mode,
+- TSC2102_TS_ADC_CTRL, TSC2102_ADC_T1_CONTROL,
+- tsc2102_complete_dummy);
+-}
+-
+-static inline void tsc2102_temp2_mode(struct tsc2102_dev *dev)
+-{
+- /* Scan TEMP2, 12-bit, 16 samples, 500 usec */
+- tsc2102_write_async(&dev->req_mode,
+- TSC2102_TS_ADC_CTRL, TSC2102_ADC_T2_CONTROL,
+- tsc2102_complete_dummy);
+-}
+-
+-static void tsc2102_mode(struct tsc2102_dev *dev)
++static void tsc2102_end_current_conversion(struct tsc2102_dev *dev)
+ {
++ spin_lock_irq(&dev->lock);
++ dev->touch_in_progress = 0;
++ dev->state++;
+ switch (dev->state) {
+- case 0:
+- tsc2102_touchscreen_mode(dev);
+- break;
+- case 1:
+- tsc2102_portscan_mode(dev);
++ /* Scan BAT1, BAT2, AUX, 12-bit, 16 samples, 500 usec */
++ case 0: tsc2102_write_async(&dev->req_mode, TSC2102_TS_ADC_CTRL,
++ TSC2102_ADC_SCAN_CONTROL, tsc2102_complete_dummy);
+ break;
+- case 2:
+- tsc2102_temp1_mode(dev);
++ /* Scan TEMP1, 12-bit, 16 samples, 500 usec */
++ case 1: tsc2102_write_async(&dev->req_mode, TSC2102_TS_ADC_CTRL,
++ TSC2102_ADC_T1_CONTROL, tsc2102_complete_dummy);
+ break;
+- case 3:
+- tsc2102_temp2_mode(dev);
++ /* Scan TEMP2, 12-bit, 16 samples, 500 usec */
++ case 2: tsc2102_write_async(&dev->req_mode, TSC2102_TS_ADC_CTRL,
++ TSC2102_ADC_T2_CONTROL, tsc2102_complete_dummy);
+ break;
+- default:
++ default:
++ tsc2102_write_async(&dev->req_mode, TSC2102_TS_ADC_CTRL,
++ TSC2102_ADC_SCAN_CONTROL, tsc2102_complete_dummy);
+ dev->state = 0;
+- tsc2102_touchscreen_mode(dev);
+ break;
+ }
++ spin_unlock_irq(&dev->lock);
++ mod_timer(&dev->mode_timer, jiffies +
++ msecs_to_jiffies(dev->mode_msecs));
+ }
+
+-/* Lock is held when this is called. */
+-static void tsc2102_new_mode(struct tsc2102_dev *dev)
++static void tsc2102_mode(unsigned long data)
+ {
+- /* Abort current conversion if any */
++ struct tsc2102_dev *dev = (struct tsc2102_dev *) data;
++ spin_lock_irq(&dev->lock);
++
+ tsc2102_write_async(&dev->req_stopadc,
+ TSC2102_TS_ADC_CTRL, TSC2102_ADC_ADST,
+- tsc2102_complete_dummy);
++ tsc2102_end_current_conversion);
+
- dev->state ++;
-+ //dev->state ++;
- tsc2102_mode(dev);
+- tsc2102_mode(dev);
++ spin_unlock_irq(&dev->lock);
}
- static void tsc2102_check_status(struct tsc2102_dev *dev);
-
+-static void tsc2102_check_status(struct tsc2102_dev *dev);
+-
-/* TSC has new data for us availiable. */
-static irqreturn_t tsc2102_handler(int irq, void *dev_id)
-+/* TSC has new data for us available. */
-+static irqreturn_t tsc2102_handler(int irq, void *dev_id, struct pt_regs *regs)
++/* Read touch screen data */
++static void tsc2102_TS_data_report(struct tsc2102_dev *dev)
{
- struct tsc2102_dev *dev = (struct tsc2102_dev *) dev_id;
- spin_lock_irq(&dev->lock);
-
+- struct tsc2102_dev *dev = (struct tsc2102_dev *) dev_id;
+- spin_lock_irq(&dev->lock);
+-
- if (!dev->data_pending)
-+ if (!dev->data_pending)
-+ {
-+ dev->data_pending = 1;
- tsc2102_check_status(dev);
+- tsc2102_check_status(dev);
-
- dev->data_pending ++;
-+ }
-+
-+// dev->data_pending ++;
+-
+- spin_unlock_irq(&dev->lock);
+- return IRQ_HANDLED;
++ if (dev->coords_cb)
++ dev->coords_cb(
++ dev->adc_data[0], dev->adc_data[1],
++ dev->adc_data[2], dev->adc_data[3]);
+ }
- spin_unlock_irq(&dev->lock);
- return IRQ_HANDLED;
-@@ -464,7 +470,7 @@
-
+-static void tsc2102_data_report(struct tsc2102_dev *dev)
++static void tsc2102_pressure_report(struct tsc2102_dev *dev)
+ {
+- if (dev->status & TSC2102_TS_DAV) {
+- if (dev->coords_cb)
+- dev->coords_cb(
+- dev->adc_data[0], dev->adc_data[1],
+- dev->adc_data[2], dev->adc_data[3]);
+- }
+-
+- if (dev->status & TSC2102_PS_DAV) {
+- if (dev->ports_cb)
+- dev->ports_cb(dev->adc_data[0],
+- dev->adc_data[1], dev->adc_data[2]);
+- dev->bat[0] = dev->adc_data[0];
+- dev->bat[1] = dev->adc_data[1];
+- dev->aux[0] = dev->adc_data[2];
+- }
+-
+- if (dev->status & TSC2102_T1_DAV) {
+- if (dev->temp1_cb)
+- dev->temp1_cb(*dev->adc_data);
+- dev->temp[0] = *dev->adc_data;
+- }
+-
+- if (dev->status & TSC2102_T2_DAV) {
+- if (dev->temp2_cb)
+- dev->temp2_cb(*dev->adc_data);
+- dev->temp[1] = *dev->adc_data;
+- }
+-
spin_lock_irq(&dev->lock);
++ mod_timer(&dev->mode_timer, jiffies +
++ msecs_to_jiffies(dev->mode_msecs));
- dev->data_pending --;
-+ dev->data_pending=0; // --
-
- /*
- * This may happen if the registers were successfully read and a
-@@ -474,8 +480,8 @@
- if (dev->data_pending)
- tsc2102_check_status(dev);
-
+-
+- /*
+- * This may happen if the registers were successfully read and a
+- * new conversion was started and completed by the TSC before the
+- * completion for SPI read was called.
+- */
+- if (dev->data_pending)
+- tsc2102_check_status(dev);
+-
- if (dev->status & (TSC2102_PS_DAV | TSC2102_T1_DAV | TSC2102_T2_DAV))
- tsc2102_new_mode(dev);
-+// if (dev->status & (TSC2102_PS_DAV | TSC2102_T1_DAV | TSC2102_T2_DAV))
-+// tsc2102_new_mode(dev);
+-
+- spin_unlock_irq(&dev->lock);
+-}
++ tsc2102_reads_async(&dev->req_adc, TSC2102_TS_X,
++ dev->adc_data, 4, tsc2102_TS_data_report);
- spin_unlock_irq(&dev->lock);
+-static void tsc2102_status_report(struct tsc2102_dev *dev)
+-{
+- /*
+- * Read all converted data from corresponding registers
+- * so that the ADC can move on to a new conversion.
+- */
+- if (dev->status & TSC2102_TS_DAV) {
+- tsc2102_reads_async(&dev->req_adc, TSC2102_TS_X,
+- dev->adc_data, 4, tsc2102_data_report);
+- if (!dev->pendown) {
+- dev->pendown = 1;
+- if (dev->touch_cb)
+- dev->touch_cb(1);
+-
+- mod_timer(&dev->ts_timer, jiffies +
++ if ( dev->adc_status & TSC2102_ADC_PSTCM) {
++ mod_timer(&dev->ts_timer, jiffies +
+ msecs_to_jiffies(dev->ts_msecs));
+- }
+- }
+-
+- if (dev->status & TSC2102_PS_DAV) {
+- tsc2102_reads_async(&dev->req_adc, TSC2102_TS_BAT1,
+- dev->adc_data, 3, tsc2102_data_report);
+ }
+-
+- if (dev->status & TSC2102_T1_DAV) {
+- tsc2102_read_async(&dev->req_adc, TSC2102_TS_TEMP1,
+- dev->adc_data, tsc2102_data_report);
+- }
+-
+- if (dev->status & TSC2102_T2_DAV) {
+- tsc2102_read_async(&dev->req_adc, TSC2102_TS_TEMP2,
+- dev->adc_data, tsc2102_data_report);
+- }
+-
+- if (!(dev->status & (TSC2102_TS_DAV | TSC2102_PS_DAV |
+- TSC2102_T1_DAV | TSC2102_T2_DAV))) {
+- spin_lock_irq(&dev->lock);
+- dev->data_pending --;
+- spin_unlock_irq(&dev->lock);
+-
+- WARN_ON(!dev->state);
+- }
+-}
+-
+-static void tsc2102_check_status(struct tsc2102_dev *dev)
+-{
+- tsc2102_read_async(&dev->req_status, TSC2102_TS_STATUS_CTRL,
+- &dev->status, tsc2102_status_report);
++ spin_unlock_irq(&dev->lock);
}
-@@ -486,6 +492,7 @@
- * Read all converted data from corresponding registers
- * so that the ADC can move on to a new conversion.
- */
-+
- if (dev->status & TSC2102_TS_DAV) {
- tsc2102_reads_async(&dev->req_adc, TSC2102_TS_X,
- dev->adc_data, 4, tsc2102_data_report);
-@@ -517,7 +524,7 @@
- if (!(dev->status & (TSC2102_TS_DAV | TSC2102_PS_DAV |
- TSC2102_T1_DAV | TSC2102_T2_DAV))) {
- spin_lock_irq(&dev->lock);
-- dev->data_pending --;
-+ dev->data_pending=0; //--
- spin_unlock_irq(&dev->lock);
- WARN_ON(!dev->state);
-@@ -539,8 +546,8 @@
+-static void tsc2102_mode_timer(unsigned long data)
++static void tsc2102_scan_data_report(struct tsc2102_dev *dev)
+ {
+- struct tsc2102_dev *dev = (struct tsc2102_dev *) data;
++ mod_timer(&dev->mode_timer, jiffies +
++ msecs_to_jiffies(dev->mode_msecs));
+ spin_lock_irq(&dev->lock);
++ switch (dev->state)
++ {
++ case 0: if (dev->ports_cb)
++ dev->ports_cb(dev->adc_data[0],
++ dev->adc_data[1], dev->adc_data[2]);
++ dev->bat[0] = dev->adc_data[0];
++ dev->bat[1] = dev->adc_data[1];
++ dev->aux[0] = dev->adc_data[2];
++ break;
++
++ case 1: if (dev->temp1_cb)
++ dev->temp1_cb(*dev->adc_data);
++ dev->temp[0] = *dev->adc_data;
++ break;
- tsc2102_new_mode(dev);
-
+- BUG_ON(dev->state);
+-
+- tsc2102_new_mode(dev);
+-
- mod_timer(&dev->mode_timer, jiffies +
- msecs_to_jiffies(dev->mode_msecs));
-+/* mod_timer(&dev->mode_timer, jiffies +
-+ msecs_to_jiffies(dev->mode_msecs));*/
++ case 2: if (dev->temp2_cb)
++ dev->temp2_cb(*dev->adc_data);
++ dev->temp[1] = *dev->adc_data;
++ break;
++ default: break;
++ }
++ tsc2102_touchscreen_mode(dev);
spin_unlock_irq(&dev->lock);
}
-@@ -786,7 +793,7 @@
+-/*
+- * There are at least three ways to check for pen-up:
+- * - the PINT/DAV pin state,
+- * - reading PSTCM bit in ADC Control register (D15, offset 0x00),
+- * - reading ADST bit in ADC Control register (D14, offset 0x00),
+- * ADC idle would indicate no screen touch.
+- * Unfortunately none of them seems to be 100% accurate and you will
+- * find they are totally inconsistent, i.e. you get to see any arbitrary
+- * combination of values in these three bits. So we will busy-wait
+- * for a moment when all three indicate a pen-up, using a timer, before
+- * we report a pen-up.
+- */
+-static void tsc2102_pressure_report(struct tsc2102_dev *dev)
++/* TSC has new data for us available. */
++static irqreturn_t tsc2102_handler(int irq, void *dev_id, struct pt_regs *regs)
+ {
+- if (!dev->pendown)
+- return;
++ struct tsc2102_dev *dev = (struct tsc2102_dev *) dev_id;
- /* Reference mode, 100 usec delay, 1.25 V reference */
+- if (dev->state ||
+- (dev->adc_status & TSC2102_ADC_PSTCM) ||
+- !(dev->adc_status & TSC2102_ADC_ADST)) {
+- mod_timer(&dev->ts_timer, jiffies +
+- msecs_to_jiffies(dev->ts_msecs));
+- } else {
+- dev->pendown = 0;
+- if (dev->touch_cb)
+- dev->touch_cb(0);
++ mod_timer(&dev->mode_timer, jiffies +
++ msecs_to_jiffies(dev->mode_msecs));
++
++ spin_lock_irq(&dev->lock);
++ if( dev->touch_in_progress ){
++ tsc2102_read_async(&dev->req_pressure, TSC2102_TS_ADC_CTRL,
++ &dev->adc_status, tsc2102_pressure_report);
++ }
++ else{
++ switch(dev->state){
++ case 0: tsc2102_reads_async(&dev->req_adc, TSC2102_TS_BAT1,
++ dev->adc_data, 3, tsc2102_scan_data_report);
++ break;
++ case 1: tsc2102_read_async(&dev->req_adc, TSC2102_TS_TEMP1,
++ dev->adc_data, tsc2102_scan_data_report);
++ break;
++ case 2: tsc2102_read_async(&dev->req_adc, TSC2102_TS_TEMP2,
++ dev->adc_data, tsc2102_scan_data_report);
++ break;
++ default: break;
++ }
+ }
++ spin_unlock_irq(&dev->lock);
++ return IRQ_HANDLED;
+ }
+
+ static void tsc2102_pressure(unsigned long data)
+ {
+ struct tsc2102_dev *dev = (struct tsc2102_dev *) data;
+-
+- BUG_ON(!dev->pendown);
+-
+- tsc2102_read_async(&dev->req_pressure, TSC2102_TS_ADC_CTRL,
+- &dev->adc_status, tsc2102_pressure_report);
++ if (dev->touch_cb){
++ dev->touch_cb(0);
++ }
+ }
+
+ #ifdef CONFIG_SOUND
+@@ -596,22 +514,20 @@ void tsc2102_set_volume(uint8_t left_ch,
+ if (right_ch == 0x00 || right_ch == 0x7f)
+ right_ch ^= 0x7f;
+
+- spin_lock(&tsc.lock_sync);
+-
++ mutex_lock(&tsc.lock_sync);
+ val = tsc2102_read_sync(TSC2102_DAC_GAIN_CTRL);
+
+ val &= 0x8080; /* Preserve mute-bits */
+ val |= (left_ch << 8) | right_ch;
+
+ tsc2102_write_sync(TSC2102_DAC_GAIN_CTRL, val);
+-
+- spin_unlock(&tsc.lock_sync);
++ mutex_unlock(&tsc.lock_sync);
+ }
+
+ void tsc2102_set_mute(int left_ch, int right_ch)
+ {
+ u16 val;
+- spin_lock(&tsc.lock_sync);
++ mutex_lock(&tsc.lock_sync);
+
+ val = tsc2102_read_sync(TSC2102_DAC_GAIN_CTRL);
+
+@@ -620,17 +536,17 @@ void tsc2102_set_mute(int left_ch, int r
+
+ tsc2102_write_sync(TSC2102_DAC_GAIN_CTRL, val);
+
+- spin_unlock(&tsc.lock_sync);
++ mutex_unlock(&tsc.lock_sync);
+ }
+
+ void tsc2102_get_mute(int *left_ch, int *right_ch)
+ {
+ u16 val;
+- spin_lock(&tsc.lock_sync);
++ mutex_lock(&tsc.lock_sync);
+
+ val = tsc2102_read_sync(TSC2102_DAC_GAIN_CTRL);
+
+- spin_unlock(&tsc.lock_sync);
++ mutex_unlock(&tsc.lock_sync);
+
+ *left_ch = !!(val & (1 << 15));
+ *right_ch = !!(val & (1 << 7));
+@@ -639,7 +555,7 @@ void tsc2102_get_mute(int *left_ch, int
+ void tsc2102_set_deemphasis(int enable)
+ {
+ u16 val;
+- spin_lock(&tsc.lock_sync);
++ mutex_lock(&tsc.lock_sync);
+ val = tsc2102_read_sync(TSC2102_DAC_POWER_CTRL);
+
+ if (enable)
+@@ -648,13 +564,13 @@ void tsc2102_set_deemphasis(int enable)
+ val |= TSC2102_DEEMPF;
+
+ tsc2102_write_sync(TSC2102_DAC_POWER_CTRL, val);
+- spin_unlock(&tsc.lock_sync);
++ mutex_unlock(&tsc.lock_sync);
+ }
+
+ void tsc2102_set_bassboost(int enable)
+ {
+ u16 val;
+- spin_lock(&tsc.lock_sync);
++ mutex_lock(&tsc.lock_sync);
+ val = tsc2102_read_sync(TSC2102_DAC_POWER_CTRL);
+
+ if (enable)
+@@ -663,7 +579,7 @@ void tsc2102_set_bassboost(int enable)
+ val |= TSC2102_BASSBC;
+
+ tsc2102_write_sync(TSC2102_DAC_POWER_CTRL, val);
+- spin_unlock(&tsc.lock_sync);
++ mutex_unlock(&tsc.lock_sync);
+ }
+
+ /* {rate, dsor, fsref} */
+@@ -709,7 +625,7 @@ int tsc2102_set_rate(int rate)
+ return -EINVAL;
+ }
+
+- spin_lock(&tsc.lock_sync);
++ mutex_lock(&tsc.lock_sync);
+
+ tsc2102_write_sync(TSC2102_AUDIO1_CTRL, tsc2102_rates[i].divisor);
+
+@@ -727,7 +643,7 @@ int tsc2102_set_rate(int rate)
+ tsc2102_write_sync(TSC2102_PLL2_CTRL, TSC2102_PLL2_48K);
+ }
+
+- spin_unlock(&tsc.lock_sync);
++ mutex_unlock(&tsc.lock_sync);
+ return 0;
+ }
+
+@@ -736,7 +652,7 @@ int tsc2102_set_rate(int rate)
+ */
+ void tsc2102_dac_power(int state)
+ {
+- spin_lock(&tsc.lock_sync);
++ mutex_lock(&tsc.lock_sync);
+
+ if (state) {
+ /* 16-bit words, DSP mode, sample at Fsref */
+@@ -760,13 +676,13 @@ void tsc2102_dac_power(int state)
+ tsc2102_write_sync(TSC2102_PLL1_CTRL, TSC2102_PLL1_OFF);
+ }
+
+- spin_unlock(&tsc.lock_sync);
++ mutex_unlock(&tsc.lock_sync);
+ }
+
+ void tsc2102_set_i2s_master(int state)
+ {
+ uint16_t val;
+- spin_lock(&tsc.lock_sync);
++ mutex_lock(&tsc.lock_sync);
+
+ val = tsc2102_read_sync(TSC2102_AUDIO3_CTRL);
+
+@@ -775,7 +691,7 @@ void tsc2102_set_i2s_master(int state)
+ else
+ tsc2102_write_sync(TSC2102_AUDIO3_CTRL, val & ~TSC2102_SLVMS);
+
+- spin_unlock(&tsc.lock_sync);
++ mutex_unlock(&tsc.lock_sync);
+ }
+ #endif /* CONFIG_SOUND */
+
+@@ -784,9 +700,9 @@ static int tsc2102_configure(struct tsc2
+ /* Reset the chip */
+ tsc2102_write_sync(TSC2102_TS_RESET_CTRL, TSC2102_RESET);
+
+- /* Reference mode, 100 usec delay, 1.25 V reference */
++ /* Reference mode, 100 usec delay, 2.5V reference */
if (dev->pdata->use_internal)
- tsc2102_write_sync(TSC2102_TS_REF_CTRL, TSC2102_ADC_INT_REF);
-+ tsc2102_write_sync(TSC2102_TS_REF_CTRL, TSC2102_ADC_INT_REF_250);
++ tsc2102_write_sync(TSC2102_TS_REF_CTRL, TSC2102_ADC_REF);
else
tsc2102_write_sync(TSC2102_TS_REF_CTRL, TSC2102_ADC_EXT_REF);
-@@ -986,7 +993,7 @@
+@@ -796,7 +712,10 @@ static int tsc2102_configure(struct tsc2
+ /* PINT/DAV acts as DAV */
+ tsc2102_write_sync(TSC2102_TS_STATUS_CTRL, TSC2102_ADC_DAV);
+
+- tsc2102_mode(dev);
++ /* Init mode state machine */
++ dev->state = 0;
++ dev->touch_in_progress = 0;
++ /* Start mode timer */
+ mod_timer(&dev->mode_timer, jiffies +
+ msecs_to_jiffies(dev->mode_msecs));
+ return 0;
+@@ -824,7 +743,7 @@ int tsc2102_get_revision(void)
+ void tsc2102_keyclick(int amplitude, int freq, int length)
{
+ u16 val;
+- spin_lock(&tsc.lock_sync);
++ mutex_lock(&tsc.lock_sync);
+ val = tsc2102_read_sync(TSC2102_AUDIO2_CTRL);
+ val &= 0x800f;
+
+@@ -857,17 +776,17 @@ void tsc2102_keyclick(int amplitude, int
+ val |= 0x8000;
+
+ tsc2102_write_sync(TSC2102_AUDIO2_CTRL, val);
+- spin_unlock(&tsc.lock_sync);
++ mutex_unlock(&tsc.lock_sync);
+ }
+
+-#ifdef CONFIG_HWMON
++#if defined(CONFIG_HWMON) || defined(CONFIG_HWMON_MODULE)
+ #define TSC2102_INPUT(devname, field) \
+ static ssize_t show_ ## devname(struct device *dev, \
+ struct device_attribute *devattr, char *buf) \
+ { \
+ struct tsc2102_dev *devhwmon = dev_get_drvdata(dev); \
+ int value = devhwmon->field; \
+- return sprintf(buf, "%i\n", value); \
++ return sprintf(buf, "%i\n", value); \
+ } \
+ static DEVICE_ATTR(devname ## _input, S_IRUGO, show_ ## devname, NULL);
+
+@@ -927,20 +846,20 @@ tsc2102_suspend(struct spi_device *spi,
+ if (!dev)
+ return 0;
+
+- spin_lock(&dev->lock_sync);
++ mutex_lock(&dev->lock_sync);
+
+ del_timer(&dev->mode_timer);
+ del_timer(&dev->ts_timer);
+
+- if (dev->pendown && dev->touch_cb)
++ if (dev->touch_cb)
+ dev->touch_cb(0);
+
+ /* Abort current conversion and power down the ADC */
+ tsc2102_write_sync(TSC2102_TS_ADC_CTRL, TSC2102_ADC_ADST);
+
+ dev->spi->dev.power.power_state = state;
++ mutex_unlock(&dev->lock_sync);
+
+- spin_unlock(&dev->lock_sync);
+ return 0;
+ }
+
+@@ -955,16 +874,13 @@ static int tsc2102_resume(struct spi_dev
+ if (!dev)
+ return 0;
+
+- spin_lock(&dev->lock_sync);
++ mutex_lock(&dev->lock_sync);
+
+ dev->spi->dev.power.power_state = PMSG_ON;
+
+- dev->state = 0;
+- dev->pendown = 0;
+-
+ err = tsc2102_configure(dev);
+
+- spin_unlock(&dev->lock_sync);
++ mutex_unlock(&dev->lock_sync);
+ return err;
+ }
+ #else
+@@ -986,7 +902,7 @@ static int tsc2102_probe(struct spi_devi
+ {
struct tsc2102_config *pdata = spi->dev.platform_data;
struct spi_transfer *spi_buffer;
- int err = 0;
@@ -140,12 +657,27 @@
if (!pdata) {
printk(KERN_ERR "TSC2102: Platform data not supplied\n");
-@@ -1021,21 +1028,23 @@
+@@ -999,11 +915,8 @@ static int tsc2102_probe(struct spi_devi
+ }
+
+ tsc.pdata = pdata;
+- tsc.state = 0;
+- tsc.pendown = 0;
+- tsc.data_pending = 0;
+- tsc.ts_msecs = 20;
+- tsc.mode_msecs = 1000;
++ tsc.ts_msecs = 30;
++ tsc.mode_msecs = 500;
+ tsc.spi = spi;
+
+ /* Allocate enough struct spi_transfer's for all requests */
+@@ -1021,21 +934,23 @@ static int tsc2102_probe(struct spi_devi
tsc2102_request_alloc(&tsc, &tsc.req_mode, 1, 1, &spi_buffer);
spin_lock_init(&tsc.lock);
-+ spin_lock_init(&tsc.lock_sync); // If think its better no ?
- spin_lock(&tsc.lock_sync);
+- spin_lock(&tsc.lock_sync);
++ mutex_init(&tsc.lock_sync);
++ mutex_lock(&tsc.lock_sync);
/* Get the BCLK - assuming the rate is at 12000000 */
- tsc.bclk_ck = clk_get(0, "bclk");
@@ -169,8 +701,17 @@
err = -EINVAL;
goto err_clk;
}
-@@ -1056,7 +1065,7 @@
+@@ -1043,7 +958,7 @@ static int tsc2102_probe(struct spi_devi
+ setup_timer(&tsc.ts_timer,
+ tsc2102_pressure, (unsigned long) &tsc);
+ setup_timer(&tsc.mode_timer,
+- tsc2102_mode_timer, (unsigned long) &tsc);
++ tsc2102_mode, (unsigned long) &tsc);
+ /* Set up the communication bus */
+ dev_set_drvdata(&spi->dev, &tsc);
+@@ -1056,7 +971,7 @@ static int tsc2102_probe(struct spi_devi
+
/* Now try to detect the chip, make first contact */
if (tsc2102_get_revision() != 0x1) {
- printk(KERN_ERR "No TI TSC2102 chip found!\n");
@@ -178,7 +719,16 @@
goto err_timer;
}
-@@ -1120,10 +1129,11 @@
+@@ -1077,7 +992,7 @@ static int tsc2102_probe(struct spi_devi
+ if (err)
+ goto err_ts;
+
+-#ifdef CONFIG_HWMON
++#if defined(CONFIG_HWMON) || defined(CONFIG_HWMON_MODULE)
+ tsc.hwmondev = hwmon_device_register(&spi->dev);
+ if (IS_ERR(tsc.hwmondev)) {
+ printk(KERN_ERR "tsc2102_hwmon: Device registration failed\n");
+@@ -1120,18 +1035,18 @@ err_timer:
del_timer(&tsc.mode_timer);
dev_set_drvdata(&spi->dev, NULL);
err_clk:
@@ -187,12 +737,22 @@
+/* clk_disable(tsc.bclk_ck); TODO add clock mechanism to i.MX ???
+ clk_put(tsc.bclk_ck);*/
done:
- spin_unlock(&tsc.lock_sync);
+- spin_unlock(&tsc.lock_sync);
++ mutex_unlock(&tsc.lock_sync);
+
return err;
}
-@@ -1139,8 +1149,8 @@
+ static int tsc2102_remove(struct spi_device *spi)
+ {
+ struct tsc2102_dev *dev = dev_get_drvdata(&spi->dev);
+-
+- spin_lock(&dev->lock_sync);
++ mutex_lock(&dev->lock_sync);
+
+ platform_device_unregister(&tsc2102_ts_device);
+ platform_device_unregister(&tsc2102_alsa_device);
+@@ -1139,15 +1054,15 @@ static int tsc2102_remove(struct spi_dev
dev_set_drvdata(&spi->dev, NULL);
/* Release the BCLK */
@@ -203,3 +763,20 @@
del_timer(&tsc.mode_timer);
del_timer(&tsc.ts_timer);
+
+ kfree(tsc.transfers);
+
+-#ifdef CONFIG_HWMON
++#if defined(CONFIG_HWMON) || defined(CONFIG_HWMON_MODULE)
+ hwmon_device_unregister(dev->hwmondev);
+ #endif
+
+@@ -1155,7 +1070,7 @@ static int tsc2102_remove(struct spi_dev
+ apm_get_power_status = 0;
+ #endif
+
+- spin_unlock(&dev->lock_sync);
++ mutex_unlock(&dev->lock_sync);
+
+ return 0;
+ }
This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site.
|