Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
L
linux
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
nexedi
linux
Commits
92944c1c
Commit
92944c1c
authored
Sep 05, 2010
by
Dmitry Torokhov
Browse files
Options
Browse Files
Download
Plain Diff
Merge branch 'mrst-touchscreen' into next
Conflicts: drivers/input/touchscreen/Makefile
parents
77686517
d4f5f937
Changes
8
Show whitespace changes
Inline
Side-by-side
Showing
8 changed files
with
700 additions
and
15 deletions
+700
-15
drivers/input/touchscreen/Kconfig
drivers/input/touchscreen/Kconfig
+12
-0
drivers/input/touchscreen/Makefile
drivers/input/touchscreen/Makefile
+1
-0
drivers/input/touchscreen/intel-mid-touch.c
drivers/input/touchscreen/intel-mid-touch.c
+687
-0
drivers/staging/Kconfig
drivers/staging/Kconfig
+0
-2
drivers/staging/Makefile
drivers/staging/Makefile
+0
-1
drivers/staging/mrst-touchscreen/Kconfig
drivers/staging/mrst-touchscreen/Kconfig
+0
-7
drivers/staging/mrst-touchscreen/Makefile
drivers/staging/mrst-touchscreen/Makefile
+0
-3
drivers/staging/mrst-touchscreen/TODO
drivers/staging/mrst-touchscreen/TODO
+0
-2
No files found.
drivers/input/touchscreen/Kconfig
View file @
92944c1c
...
@@ -260,6 +260,18 @@ config TOUCHSCREEN_INEXIO
...
@@ -260,6 +260,18 @@ config TOUCHSCREEN_INEXIO
To compile this driver as a module, choose M here: the
To compile this driver as a module, choose M here: the
module will be called inexio.
module will be called inexio.
config TOUCHSCREEN_INTEL_MID
tristate "Intel MID platform resistive touchscreen"
depends on INTEL_SCU_IPC
help
Say Y here if you have a Intel MID based touchscreen in
your system.
If unsure, say N.
To compile this driver as a module, choose M here: the
module will be called intel_mid_touch.
config TOUCHSCREEN_MK712
config TOUCHSCREEN_MK712
tristate "ICS MicroClock MK712 touchscreen"
tristate "ICS MicroClock MK712 touchscreen"
help
help
...
...
drivers/input/touchscreen/Makefile
View file @
92944c1c
...
@@ -23,6 +23,7 @@ obj-$(CONFIG_TOUCHSCREEN_EETI) += eeti_ts.o
...
@@ -23,6 +23,7 @@ obj-$(CONFIG_TOUCHSCREEN_EETI) += eeti_ts.o
obj-$(CONFIG_TOUCHSCREEN_ELO)
+=
elo.o
obj-$(CONFIG_TOUCHSCREEN_ELO)
+=
elo.o
obj-$(CONFIG_TOUCHSCREEN_FUJITSU)
+=
fujitsu_ts.o
obj-$(CONFIG_TOUCHSCREEN_FUJITSU)
+=
fujitsu_ts.o
obj-$(CONFIG_TOUCHSCREEN_INEXIO)
+=
inexio.o
obj-$(CONFIG_TOUCHSCREEN_INEXIO)
+=
inexio.o
obj-$(CONFIG_TOUCHSCREEN_INTEL_MID)
+=
intel-mid-touch.o
obj-$(CONFIG_TOUCHSCREEN_LPC32XX)
+=
lpc32xx_ts.o
obj-$(CONFIG_TOUCHSCREEN_LPC32XX)
+=
lpc32xx_ts.o
obj-$(CONFIG_TOUCHSCREEN_MC13783)
+=
mc13783_ts.o
obj-$(CONFIG_TOUCHSCREEN_MC13783)
+=
mc13783_ts.o
obj-$(CONFIG_TOUCHSCREEN_MCS5000)
+=
mcs5000_ts.o
obj-$(CONFIG_TOUCHSCREEN_MCS5000)
+=
mcs5000_ts.o
...
...
drivers/
staging/mrst-
touchscreen/intel-mid-touch.c
→
drivers/
input/
touchscreen/intel-mid-touch.c
View file @
92944c1c
/*
/*
*
intel_mid_touch.c -
Intel MID Resistive Touch Screen Driver
* Intel MID Resistive Touch Screen Driver
*
*
* Copyright (C) 2008 Intel Corp
* Copyright (C) 2008 Intel Corp
*
*
...
@@ -15,7 +15,7 @@
...
@@ -15,7 +15,7 @@
* General Public License for more details.
* General Public License for more details.
*
*
* You should have received a copy of the GNU General Public License along
* You should have received a copy of the GNU General Public License along
* with this program; ifnot, write to the Free Software Foundation, Inc.,
* with this program; if
not, write to the Free Software Foundation, Inc.,
* 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
* 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
*
*
* Questions/Comments/Bug fixes to Sreedhara (sreedhara.ds@intel.com)
* Questions/Comments/Bug fixes to Sreedhara (sreedhara.ds@intel.com)
...
@@ -23,11 +23,7 @@
...
@@ -23,11 +23,7 @@
* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
* ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
*
*
* TODO:
* TODO:
* kill off mrstouch_debug eventually
* review conversion of r/m/w sequences
* review conversion of r/m/w sequences
* Replace interrupt mutex abuse
* Kill of mrstouchdevp pointer
*
*/
*/
#include <linux/module.h>
#include <linux/module.h>
...
@@ -36,36 +32,25 @@
...
@@ -36,36 +32,25 @@
#include <linux/interrupt.h>
#include <linux/interrupt.h>
#include <linux/err.h>
#include <linux/err.h>
#include <linux/param.h>
#include <linux/param.h>
#include <linux/spi/spi.h>
#include <linux/slab.h>
#include <linux/platform_device.h>
#include <linux/irq.h>
#include <linux/irq.h>
#include <linux/delay.h>
#include <linux/delay.h>
#include <linux/kthread.h>
#include <asm/intel_scu_ipc.h>
#include <asm/intel_scu_ipc.h>
#if defined(MRSTOUCH_DEBUG)
#define mrstouch_debug(fmt, args...)\
do { \
printk(KERN_DEBUG "\n[MRSTOUCH(%d)] - ", __LINE__); \
printk(KERN_DEBUG fmt, ##args); \
} while (0);
#else
#define mrstouch_debug(fmt, args...)
#endif
/* PMIC Interrupt registers */
/* PMIC Interrupt registers */
#define PMIC_REG_ID1
0x00
/*
PMIC ID1 register */
#define PMIC_REG_ID1
0x00
/*
PMIC ID1 register */
/* PMIC Interrupt registers */
/* PMIC Interrupt registers */
#define PMIC_REG_INT
0x04
/*
PMIC interrupt register */
#define PMIC_REG_INT
0x04
/*
PMIC interrupt register */
#define PMIC_REG_MINT
0x05
/*
PMIC interrupt mask register */
#define PMIC_REG_MINT
0x05
/*
PMIC interrupt mask register */
/* ADC Interrupt registers */
/* ADC Interrupt registers */
#define PMIC_REG_ADCINT
0x5F
/*
ADC interrupt register */
#define PMIC_REG_ADCINT
0x5F
/*
ADC interrupt register */
#define PMIC_REG_MADCINT
0x60
/*
ADC interrupt mask register */
#define PMIC_REG_MADCINT
0x60
/*
ADC interrupt mask register */
/* ADC Control registers */
/* ADC Control registers */
#define PMIC_REG_ADCCNTL1
0x61
/*
ADC control register */
#define PMIC_REG_ADCCNTL1
0x61
/*
ADC control register */
/* ADC Channel Selection registers */
/* ADC Channel Selection registers */
#define PMICADDR0 0xA4
#define PMICADDR0 0xA4
...
@@ -80,27 +65,23 @@
...
@@ -80,27 +65,23 @@
#define MRST_TS_CHAN12 0xC
/* Touch screen Y+ connection */
#define MRST_TS_CHAN12 0xC
/* Touch screen Y+ connection */
#define MRST_TS_CHAN13 0xD
/* Touch screen Y- connection */
#define MRST_TS_CHAN13 0xD
/* Touch screen Y- connection */
/* Touch screen coordinate constants */
#define TOUCH_PRESSURE 50
#define TOUCH_PRESSURE_FS 100
#define XMOVE_LIMIT 5
#define YMOVE_LIMIT 5
#define XYMOVE_CNT 3
#define MAX_10BIT ((1<<10)-1)
/* Touch screen channel BIAS constants */
/* Touch screen channel BIAS constants */
#define XBIAS 0x20
#define
MRST_
XBIAS 0x20
#define YBIAS 0x40
#define
MRST_
YBIAS 0x40
#define ZBIAS 0x80
#define
MRST_
ZBIAS 0x80
/* Touch screen coordinates */
/* Touch screen coordinates */
#define MIN_X 10
#define MRST_X_MIN 10
#define MAX_X 1024
#define MRST_X_MAX 1024
#define MIN_Y 10
#define MRST_X_FUZZ 5
#define MAX_Y 1024
#define MRST_Y_MIN 10
#define WAIT_ADC_COMPLETION 10
#define MRST_Y_MAX 1024
#define MRST_Y_FUZZ 5
#define MRST_PRESSURE_MIN 0
#define MRST_PRESSURE_NOMINAL 50
#define MRST_PRESSURE_MAX 100
#define WAIT_ADC_COMPLETION 10
/* msec */
/* PMIC ADC round robin delays */
/* PMIC ADC round robin delays */
#define ADC_LOOP_DELAY0 0x0
/* Continuous loop */
#define ADC_LOOP_DELAY0 0x0
/* Continuous loop */
...
@@ -114,140 +95,45 @@
...
@@ -114,140 +95,45 @@
/* Touch screen device structure */
/* Touch screen device structure */
struct
mrstouch_dev
{
struct
mrstouch_dev
{
struct
spi_device
*
spi
;
/* SPI device associated with touch screen */
struct
device
*
dev
;
/* device associated with touch screen */
struct
input_dev
*
input
;
/* input device for touchscreen*/
struct
input_dev
*
input
;
char
phys
[
32
];
/* Device name */
char
phys
[
32
];
struct
task_struct
*
pendet_thrd
;
/* PENDET interrupt handler */
struct
mutex
lock
;
/* Sync between interrupt and PENDET handler */
bool
busy
;
/* Busy flag */
u16
asr
;
/* Address selection register */
u16
asr
;
/* Address selection register */
int
irq
;
/* Touch screen IRQ # */
int
irq
;
uint
vendor
;
/* PMIC vendor */
unsigned
int
vendor
;
/* PMIC vendor */
uint
rev
;
/* PMIC revision */
unsigned
int
rev
;
/* PMIC revision */
bool
suspended
;
/* Device suspended status */
bool
disabled
;
/* Device disabled status */
u16
x
;
/* X coordinate */
u16
y
;
/* Y coordinate */
bool
pendown
;
/* PEN position */
}
;
/* Global Pointer to Touch screen device */
int
(
*
read_prepare
)(
struct
mrstouch_dev
*
tsdev
);
static
struct
mrstouch_dev
*
mrstouchdevp
;
int
(
*
read
)(
struct
mrstouch_dev
*
tsdev
,
u16
*
x
,
u16
*
y
,
u16
*
z
);
int
(
*
read_finish
)(
struct
mrstouch_dev
*
tsdev
);
/* Utility to read PMIC ID */
};
static
int
mrstouch_pmic_id
(
uint
*
vendor
,
uint
*
rev
)
{
int
err
;
u8
r
;
err
=
intel_scu_ipc_ioread8
(
PMIC_REG_ID1
,
&
r
);
if
(
err
)
return
err
;
*
vendor
=
r
&
0x7
;
/*************************** NEC and Maxim Interface ************************/
*
rev
=
(
r
>>
3
)
&
0x7
;
return
0
;
static
int
mrstouch_nec_adc_read_prepare
(
struct
mrstouch_dev
*
tsdev
)
{
return
intel_scu_ipc_update_register
(
PMIC_REG_MADCINT
,
0
,
0x20
);
}
}
/*
/*
* Parse ADC channels to find end of the channel configured by other ADC user
* Enables PENDET interrupt.
* NEC and MAXIM requires 4 channels and FreeScale needs 18 channels
*/
*/
static
int
mrstouch_chan_parse
(
struct
mrstouch_dev
*
tsdev
)
static
int
mrstouch_nec_adc_read_finish
(
struct
mrstouch_dev
*
tsdev
)
{
int
err
,
i
,
j
,
found
;
u32
r32
;
found
=
-
1
;
for
(
i
=
0
;
i
<
MRSTOUCH_MAX_CHANNELS
;
i
++
)
{
if
(
found
>=
0
)
break
;
err
=
intel_scu_ipc_ioread32
(
PMICADDR0
,
&
r32
);
if
(
err
)
return
err
;
for
(
j
=
0
;
j
<
32
;
j
+=
8
)
{
if
(((
r32
>>
j
)
&
0xFF
)
==
END_OF_CHANNEL
)
{
found
=
i
;
break
;
}
}
}
if
(
found
<
0
)
return
0
;
if
(
tsdev
->
vendor
==
PMIC_VENDOR_FS
)
{
if
(
found
&&
found
>
(
MRSTOUCH_MAX_CHANNELS
-
18
))
return
-
ENOSPC
;
}
else
{
if
(
found
&&
found
>
(
MRSTOUCH_MAX_CHANNELS
-
4
))
return
-
ENOSPC
;
}
return
found
;
}
/* Utility to enable/disable pendet.
* pendet set to true enables PENDET interrupt
* pendet set to false disables PENDET interrupt
* Also clears RND mask bit
*/
static
int
pendet_enable
(
struct
mrstouch_dev
*
tsdev
,
bool
pendet
)
{
{
u16
reg
;
u8
r
;
u8
pendet_enabled
=
0
;
int
retry
=
0
;
int
err
;
int
err
;
err
=
intel_scu_ipc_ioread16
(
PMIC_REG_MADCINT
,
&
reg
);
err
=
intel_scu_ipc_update_register
(
PMIC_REG_MADCINT
,
0x20
,
0x20
);
if
(
err
)
if
(
!
err
)
return
err
;
err
=
intel_scu_ipc_update_register
(
PMIC_REG_ADCCNTL1
,
0
,
0x05
);
if
(
pendet
)
{
reg
&=
~
0x0005
;
reg
|=
0x2000
;
/* Enable pendet */
}
else
reg
&=
0xDFFF
;
/* Disable pendet */
/* Set MADCINT and update ADCCNTL1 (next reg byte) */
err
=
intel_scu_ipc_iowrite16
(
PMIC_REG_MADCINT
,
reg
);
if
(
!
pendet
||
err
)
return
err
;
return
err
;
/*
* Sometimes even after the register write succeeds
* the PMIC register value is not updated. Retry few iterations
* to enable pendet.
*/
err
=
intel_scu_ipc_ioread8
(
PMIC_REG_ADCCNTL1
,
&
r
);
pendet_enabled
=
(
r
>>
5
)
&
0x01
;
retry
=
0
;
while
(
!
err
&&
!
pendet_enabled
)
{
retry
++
;
msleep
(
10
);
err
=
intel_scu_ipc_iowrite8
(
PMIC_REG_ADCCNTL1
,
reg
>>
8
);
if
(
err
)
break
;
err
=
intel_scu_ipc_ioread8
(
PMIC_REG_ADCCNTL1
,
&
r
);
if
(
err
==
0
)
pendet_enabled
=
(
r
>>
5
)
&
0x01
;
if
(
retry
>=
10
)
{
dev_err
(
&
tsdev
->
spi
->
dev
,
"Touch screen disabled.
\n
"
);
return
-
EIO
;
}
}
return
0
;
}
}
/* To read PMIC ADC touch screen result
/*
* Reads ADC storage registers for higher 7 and lower 3 bits
* Reads PMIC ADC touch screen result
* converts the two readings to single value and turns off gain bit
* Reads ADC storage registers for higher 7 and lower 3 bits and
* converts the two readings into a single value and turns off gain bit
*/
*/
static
int
mrstouch_ts_chan_read
(
u16
offset
,
u16
chan
,
u16
*
vp
,
u16
*
vm
)
static
int
mrstouch_ts_chan_read
(
u16
offset
,
u16
chan
,
u16
*
vp
,
u16
*
vm
)
{
{
...
@@ -279,202 +165,93 @@ static int mrstouch_ts_chan_read(u16 offset, u16 chan, u16 *vp, u16 *vm)
...
@@ -279,202 +165,93 @@ static int mrstouch_ts_chan_read(u16 offset, u16 chan, u16 *vp, u16 *vm)
return
0
;
return
0
;
}
}
/* To configure touch screen channels
/*
* Writes touch screen channels to ADC address selection registers
* Enables X, Y and Z bias values
* Enables YPYM for X channels and XPXM for Y channels
*/
*/
static
int
mrstouch_ts_
chan_set
(
uint
offset
)
static
int
mrstouch_ts_
bias_set
(
uint
offset
,
uint
bias
)
{
{
int
count
;
int
count
;
u16
chan
;
u16
chan
,
start
;
u16
reg
[
5
];
u16
reg
[
4
];
u8
data
[
5
];
u8
data
[
4
];
chan
=
PMICADDR0
+
offset
;
chan
=
PMICADDR0
+
offset
;
start
=
MRST_TS_CHAN10
;
for
(
count
=
0
;
count
<=
3
;
count
++
)
{
for
(
count
=
0
;
count
<=
3
;
count
++
)
{
reg
[
count
]
=
chan
++
;
reg
[
count
]
=
chan
++
;
data
[
count
]
=
MRST_TS_CHAN10
+
count
;
data
[
count
]
=
bias
|
(
start
+
count
);
}
reg
[
count
]
=
chan
;
data
[
count
]
=
END_OF_CHANNEL
;
return
intel_scu_ipc_writev
(
reg
,
data
,
5
);
}
/* Initialize ADC */
static
int
mrstouch_adc_init
(
struct
mrstouch_dev
*
tsdev
)
{
int
err
,
start
;
u8
ra
,
rm
;
err
=
mrstouch_pmic_id
(
&
tsdev
->
vendor
,
&
tsdev
->
rev
);
if
(
err
)
{
dev_err
(
&
tsdev
->
spi
->
dev
,
"Unable to read PMIC id
\n
"
);
return
err
;
}
start
=
mrstouch_chan_parse
(
tsdev
);
if
(
start
<
0
)
{
dev_err
(
&
tsdev
->
spi
->
dev
,
"Unable to parse channels
\n
"
);
return
start
;
}
tsdev
->
asr
=
start
;
mrstouch_debug
(
"Channel offset(%d): 0x%X
\n
"
,
tsdev
->
asr
,
tsdev
->
vendor
);
/* ADC power on, start, enable PENDET and set loop delay
* ADC loop delay is set to 4.5 ms approximately
* Loop delay more than this results in jitter in adc readings
* Setting loop delay to 0 (continous loop) in MAXIM stops PENDET
* interrupt generation sometimes.
*/
if
(
tsdev
->
vendor
==
PMIC_VENDOR_FS
)
{
ra
=
0xE0
|
ADC_LOOP_DELAY0
;
rm
=
0x5
;
}
else
{
/* NEC and MAXIm not consistent with loop delay 0 */
ra
=
0xE0
|
ADC_LOOP_DELAY1
;
rm
=
0x0
;
/* configure touch screen channels */
err
=
mrstouch_ts_chan_set
(
tsdev
->
asr
);
if
(
err
)
return
err
;
}
err
=
intel_scu_ipc_update_register
(
PMIC_REG_ADCCNTL1
,
ra
,
0xE7
);
if
(
err
==
0
)
err
=
intel_scu_ipc_update_register
(
PMIC_REG_MADCINT
,
rm
,
0x03
);
return
err
;
}
/* Reports x,y coordinates to event subsystem */
static
void
mrstouch_report_xy
(
struct
mrstouch_dev
*
tsdev
,
u16
x
,
u16
y
,
u16
z
)
{
int
xdiff
,
ydiff
;
if
(
tsdev
->
pendown
&&
z
<=
TOUCH_PRESSURE
)
{
/* Pen removed, report button release */
mrstouch_debug
(
"BTN REL(%d)"
,
z
);
input_report_key
(
tsdev
->
input
,
BTN_TOUCH
,
0
);
tsdev
->
pendown
=
false
;
}
xdiff
=
abs
(
x
-
tsdev
->
x
);
ydiff
=
abs
(
y
-
tsdev
->
y
);
/*
if x and y values changes for XYMOVE_CNT readings it is considered
as stylus is moving. This is required to differentiate between stylus
movement and jitter
*/
if
(
x
<
MIN_X
||
x
>
MAX_X
||
y
<
MIN_Y
||
y
>
MAX_Y
)
{
/* Spurious values, release button if touched and return */
if
(
tsdev
->
pendown
)
{
mrstouch_debug
(
"BTN REL(%d)"
,
z
);
input_report_key
(
tsdev
->
input
,
BTN_TOUCH
,
0
);
tsdev
->
pendown
=
false
;
}
return
;
}
else
if
(
xdiff
>=
XMOVE_LIMIT
||
ydiff
>=
YMOVE_LIMIT
)
{
tsdev
->
x
=
x
;
tsdev
->
y
=
y
;
input_report_abs
(
tsdev
->
input
,
ABS_X
,
x
);
input_report_abs
(
tsdev
->
input
,
ABS_Y
,
y
);
input_sync
(
tsdev
->
input
);
}
}
return
intel_scu_ipc_writev
(
reg
,
data
,
4
);
if
(
!
tsdev
->
pendown
&&
z
>
TOUCH_PRESSURE
)
{
/* Pen touched, report button touch */
mrstouch_debug
(
"BTN TCH(%d, %d, %d)"
,
x
,
y
,
z
);
input_report_key
(
tsdev
->
input
,
BTN_TOUCH
,
1
);
tsdev
->
pendown
=
true
;
}
}
/* Utility to start ADC, used by freescale handler */
static
int
pendet_mask
(
void
)
{
return
intel_scu_ipc_update_register
(
PMIC_REG_MADCINT
,
0x02
,
0x02
);
}
/* Utility to stop ADC, used by freescale handler */
static
int
pendet_umask
(
void
)
{
return
intel_scu_ipc_update_register
(
PMIC_REG_MADCINT
,
0x00
,
0x02
);
}
}
/* Utility to read ADC, used by freescale handler */
/* To read touch screen channel values */
static
int
mrstouch_pmic_fs_adc_read
(
struct
mrstouch_dev
*
tsdev
)
static
int
mrstouch_nec_adc_read
(
struct
mrstouch_dev
*
tsdev
,
u16
*
x
,
u16
*
y
,
u16
*
z
)
{
{
int
err
;
int
err
;
u16
x
,
y
,
z
,
result
;
u16
xm
,
ym
,
zm
;
u16
reg
[
4
];
u8
data
[
4
];
result
=
PMIC_REG_ADCSNS0H
+
tsdev
->
asr
;
/* configure Y bias for X channels */
err
=
mrstouch_ts_bias_set
(
tsdev
->
asr
,
MRST_YBIAS
);
if
(
err
)
goto
ipc_error
;
reg
[
0
]
=
result
+
4
;
msleep
(
WAIT_ADC_COMPLETION
);
reg
[
1
]
=
result
+
5
;
reg
[
2
]
=
result
+
16
;
reg
[
3
]
=
result
+
17
;
err
=
intel_scu_ipc_readv
(
reg
,
data
,
4
);
/* read x+ and x- channels */
err
=
mrstouch_ts_chan_read
(
tsdev
->
asr
,
MRST_TS_CHAN10
,
x
,
&
xm
);
if
(
err
)
if
(
err
)
goto
ipc_error
;
goto
ipc_error
;
x
=
data
[
0
]
<<
3
;
/* Higher 7 bits */
/* configure x bias for y channels */
x
|=
data
[
1
]
&
0x7
;
/* Lower 3 bits */
err
=
mrstouch_ts_bias_set
(
tsdev
->
asr
,
MRST_XBIAS
);
x
&=
0x3FF
;
if
(
err
)
goto
ipc_error
;
y
=
data
[
2
]
<<
3
;
/* Higher 7 bits */
y
|=
data
[
3
]
&
0x7
;
/* Lower 3 bits */
y
&=
0x3FF
;
/* Read Z value */
msleep
(
WAIT_ADC_COMPLETION
);
reg
[
0
]
=
result
+
28
;
reg
[
1
]
=
result
+
29
;
err
=
intel_scu_ipc_readv
(
reg
,
data
,
4
);
/* read y+ and y- channels */
err
=
mrstouch_ts_chan_read
(
tsdev
->
asr
,
MRST_TS_CHAN12
,
y
,
&
ym
);
if
(
err
)
if
(
err
)
goto
ipc_error
;
goto
ipc_error
;
z
=
data
[
0
]
<<
3
;
/* Higher 7 bits */
/* configure z bias for x and y channels */
z
|=
data
[
1
]
&
0x7
;
/* Lower 3 bits */
err
=
mrstouch_ts_bias_set
(
tsdev
->
asr
,
MRST_ZBIAS
);
z
&=
0x3FF
;
if
(
err
)
goto
ipc_error
;
#if defined(MRSTOUCH_PRINT_XYZP)
msleep
(
WAIT_ADC_COMPLETION
);
mrstouch_debug
(
"X: %d, Y: %d, Z: %d"
,
x
,
y
,
z
);
#endif
if
(
z
>=
TOUCH_PRESSURE_FS
)
{
/* read z+ and z- channels */
mrstouch_report_xy
(
tsdev
,
x
,
y
,
TOUCH_PRESSURE
-
1
);
/* Pen Removed */
err
=
mrstouch_ts_chan_read
(
tsdev
->
asr
,
MRST_TS_CHAN10
,
z
,
&
zm
);
return
TOUCH_PRESSURE
-
1
;
if
(
err
)
}
else
{
goto
ipc_error
;
mrstouch_report_xy
(
tsdev
,
x
,
y
,
TOUCH_PRESSURE
+
1
);
/* Pen Touched */
return
TOUCH_PRESSURE
+
1
;
}
return
0
;
return
0
;
ipc_error:
ipc_error:
dev_err
(
&
tsdev
->
spi
->
dev
,
"ipc error during fs_
adc read
\n
"
);
dev_err
(
tsdev
->
dev
,
"ipc error during
adc read
\n
"
);
return
err
;
return
err
;
}
}
/* To handle free scale pmic pendet interrupt */
static
int
pmic0_pendet
(
void
*
dev_id
)
/*************************** Freescale Interface ************************/
static
int
mrstouch_fs_adc_read_prepare
(
struct
mrstouch_dev
*
tsdev
)
{
{
int
err
,
count
;
int
err
,
count
;
u16
chan
;
u16
chan
;
unsigned
int
touched
;
struct
mrstouch_dev
*
tsdev
=
(
struct
mrstouch_dev
*
)
dev_id
;
u16
reg
[
5
];
u16
reg
[
5
];
u8
data
[
5
];
u8
data
[
5
];
/* Stop the ADC */
err
=
intel_scu_ipc_update_register
(
PMIC_REG_MADCINT
,
0x00
,
0x02
);
if
(
err
)
goto
ipc_error
;
chan
=
PMICADDR0
+
tsdev
->
asr
;
chan
=
PMICADDR0
+
tsdev
->
asr
;
/* Set X BIAS */
/* Set X BIAS */
...
@@ -512,16 +289,65 @@ static int pmic0_pendet(void *dev_id)
...
@@ -512,16 +289,65 @@ static int pmic0_pendet(void *dev_id)
msleep
(
WAIT_ADC_COMPLETION
);
msleep
(
WAIT_ADC_COMPLETION
);
/*Read touch screen channels till pen removed
return
0
;
* Freescale reports constant value of z for all points
* z is high when screen is not touched and low when touched
ipc_error:
* Map high z value to not touched and low z value to pen touched
dev_err
(
tsdev
->
dev
,
"ipc error during %s
\n
"
,
__func__
);
*/
return
err
;
touched
=
mrstouch_pmic_fs_adc_read
(
tsdev
);
}
while
(
touched
>
TOUCH_PRESSURE
)
{
touched
=
mrstouch_pmic_fs_adc_read
(
tsdev
);
static
int
mrstouch_fs_adc_read
(
struct
mrstouch_dev
*
tsdev
,
msleep
(
WAIT_ADC_COMPLETION
);
u16
*
x
,
u16
*
y
,
u16
*
z
)
}
{
int
err
;
u16
result
;
u16
reg
[
4
];
u8
data
[
4
];
result
=
PMIC_REG_ADCSNS0H
+
tsdev
->
asr
;
reg
[
0
]
=
result
+
4
;
reg
[
1
]
=
result
+
5
;
reg
[
2
]
=
result
+
16
;
reg
[
3
]
=
result
+
17
;
err
=
intel_scu_ipc_readv
(
reg
,
data
,
4
);
if
(
err
)
goto
ipc_error
;
*
x
=
data
[
0
]
<<
3
;
/* Higher 7 bits */
*
x
|=
data
[
1
]
&
0x7
;
/* Lower 3 bits */
*
x
&=
0x3FF
;
*
y
=
data
[
2
]
<<
3
;
/* Higher 7 bits */
*
y
|=
data
[
3
]
&
0x7
;
/* Lower 3 bits */
*
y
&=
0x3FF
;
/* Read Z value */
reg
[
0
]
=
result
+
28
;
reg
[
1
]
=
result
+
29
;
err
=
intel_scu_ipc_readv
(
reg
,
data
,
4
);
if
(
err
)
goto
ipc_error
;
*
z
=
data
[
0
]
<<
3
;
/* Higher 7 bits */
*
z
|=
data
[
1
]
&
0x7
;
/* Lower 3 bits */
*
z
&=
0x3FF
;
return
0
;
ipc_error:
dev_err
(
tsdev
->
dev
,
"ipc error during %s
\n
"
,
__func__
);
return
err
;
}
static
int
mrstouch_fs_adc_read_finish
(
struct
mrstouch_dev
*
tsdev
)
{
int
err
,
count
;
u16
chan
;
u16
reg
[
5
];
u8
data
[
5
];
/* Clear all TS channels */
/* Clear all TS channels */
chan
=
PMICADDR0
+
tsdev
->
asr
;
chan
=
PMICADDR0
+
tsdev
->
asr
;
...
@@ -545,319 +371,316 @@ static int pmic0_pendet(void *dev_id)
...
@@ -545,319 +371,316 @@ static int pmic0_pendet(void *dev_id)
if
(
err
)
if
(
err
)
goto
ipc_error
;
goto
ipc_error
;
/* Start ADC */
err
=
intel_scu_ipc_update_register
(
PMIC_REG_MADCINT
,
0x02
,
0x02
);
if
(
err
)
goto
ipc_error
;
return
0
;
return
0
;
ipc_error:
ipc_error:
dev_err
(
&
tsdev
->
spi
->
dev
,
"ipc error during pendet
\n
"
);
dev_err
(
tsdev
->
dev
,
"ipc error during %s
\n
"
,
__func__
);
return
err
;
return
err
;
}
}
static
void
mrstouch_report_event
(
struct
input_dev
*
input
,
/* To enable X, Y and Z bias values
unsigned
int
x
,
unsigned
int
y
,
unsigned
int
z
)
* Enables YPYM for X channels and XPXM for Y channels
*/
static
int
mrstouch_ts_bias_set
(
uint
offset
,
uint
bias
)
{
{
int
count
;
if
(
z
>
MRST_PRESSURE_NOMINAL
)
{
u16
chan
,
start
;
/* Pen touched, report button touch and coordinates */
u16
reg
[
4
];
input_report_key
(
input
,
BTN_TOUCH
,
1
);
u8
data
[
4
];
input_report_abs
(
input
,
ABS_X
,
x
);
input_report_abs
(
input
,
ABS_Y
,
y
);
chan
=
PMICADDR0
+
offset
;
}
else
{
start
=
MRST_TS_CHAN10
;
input_report_key
(
input
,
BTN_TOUCH
,
0
);
for
(
count
=
0
;
count
<=
3
;
count
++
)
{
reg
[
count
]
=
chan
++
;
data
[
count
]
=
bias
|
(
start
+
count
);
}
}
return
intel_scu_ipc_writev
(
reg
,
data
,
4
);
input_report_abs
(
input
,
ABS_PRESSURE
,
z
);
input_sync
(
input
);
}
}
/*
To read touch screen channel values
*/
/*
PENDET interrupt handler
*/
static
i
nt
mrstouch_adc_read
(
struct
mrstouch_dev
*
tsdev
)
static
i
rqreturn_t
mrstouch_pendet_irq
(
int
irq
,
void
*
dev_id
)
{
{
int
err
;
struct
mrstouch_dev
*
tsdev
=
dev_id
;
u16
x
p
,
xm
,
yp
,
ym
,
zp
,
zm
;
u16
x
,
y
,
z
;
/*
configure Y bias for X channels */
/*
err
=
mrstouch_ts_bias_set
(
tsdev
->
asr
,
YBIAS
);
* Should we lower thread priority? Probably not, since we are
if
(
err
)
* not spinning but sleeping...
goto
ipc_error
;
*/
msleep
(
WAIT_ADC_COMPLETION
);
if
(
tsdev
->
read_prepare
(
tsdev
))
goto
out
;
/* read x+ and x- channels */
do
{
err
=
mrstouch_ts_chan_read
(
tsdev
->
asr
,
MRST_TS_CHAN10
,
&
xp
,
&
xm
);
if
(
tsdev
->
read
(
tsdev
,
&
x
,
&
y
,
&
z
))
if
(
err
)
break
;
goto
ipc_error
;
/* configure x bias for y channels */
mrstouch_report_event
(
tsdev
->
input
,
x
,
y
,
z
);
err
=
mrstouch_ts_bias_set
(
tsdev
->
asr
,
XBIAS
);
}
while
(
z
>
MRST_PRESSURE_NOMINAL
);
if
(
err
)
goto
ipc_error
;
msleep
(
WAIT_ADC_COMPLETION
);
tsdev
->
read_finish
(
tsdev
);
/* read y+ and y- channels */
out:
err
=
mrstouch_ts_chan_read
(
tsdev
->
asr
,
MRST_TS_CHAN12
,
&
yp
,
&
ym
);
return
IRQ_HANDLED
;
if
(
err
)
}
goto
ipc_error
;
/* configure z bias for x and y channels */
err
=
mrstouch_ts_bias_set
(
tsdev
->
asr
,
ZBIAS
);
if
(
err
)
goto
ipc_error
;
msleep
(
WAIT_ADC_COMPLETION
);
/* Utility to read PMIC ID */
static
int
__devinit
mrstouch_read_pmic_id
(
uint
*
vendor
,
uint
*
rev
)
{
int
err
;
u8
r
;
/* read z+ and z- channels */
err
=
intel_scu_ipc_ioread8
(
PMIC_REG_ID1
,
&
r
);
err
=
mrstouch_ts_chan_read
(
tsdev
->
asr
,
MRST_TS_CHAN10
,
&
zp
,
&
zm
);
if
(
err
)
if
(
err
)
goto
ipc_error
;
#if defined(MRSTOUCH_PRINT_XYZP)
printk
(
KERN_INFO
"X+: %d, Y+: %d, Z+: %d
\n
"
,
xp
,
yp
,
zp
);
#endif
#if defined(MRSTOUCH_PRINT_XYZM)
printk
(
KERN_INFO
"X-: %d, Y-: %d, Z-: %d
\n
"
,
xm
,
ym
,
zm
);
#endif
mrstouch_report_xy
(
tsdev
,
xp
,
yp
,
zp
);
/* report x and y to eventX */
return
zp
;
ipc_error:
dev_err
(
&
tsdev
->
spi
->
dev
,
"ipc error during adc read
\n
"
);
return
err
;
return
err
;
}
/* PENDET interrupt handler function for NEC and MAXIM */
*
vendor
=
r
&
0x7
;
static
void
pmic12_pendet
(
void
*
data
)
*
rev
=
(
r
>>
3
)
&
0x7
;
{
unsigned
int
touched
;
struct
mrstouch_dev
*
tsdev
=
(
struct
mrstouch_dev
*
)
data
;
/* read touch screen channels till pen removed */
return
0
;
do
{
touched
=
mrstouch_adc_read
(
tsdev
);
}
while
(
touched
>
TOUCH_PRESSURE
);
}
}
/* Handler to process PENDET interrupt */
/*
int
mrstouch_pendet
(
void
*
data
)
* Parse ADC channels to find end of the channel configured by other ADC user
* NEC and MAXIM requires 4 channels and FreeScale needs 18 channels
*/
static
int
__devinit
mrstouch_chan_parse
(
struct
mrstouch_dev
*
tsdev
)
{
{
struct
mrstouch_dev
*
tsdev
=
(
struct
mrstouch_dev
*
)
data
;
int
err
,
i
,
found
;
while
(
1
)
{
u8
r8
;
/* Wait for PENDET interrupt */
if
(
mutex_lock_interruptible
(
&
tsdev
->
lock
))
{
msleep
(
WAIT_ADC_COMPLETION
);
continue
;
}
if
(
tsdev
->
busy
)
return
0
;
tsdev
->
busy
=
true
;
found
=
-
1
;
if
(
tsdev
->
vendor
==
PMIC_VENDOR_NEC
||
for
(
i
=
0
;
i
<
MRSTOUCH_MAX_CHANNELS
;
i
++
)
{
tsdev
->
vendor
==
PMIC_VENDOR_MAXIM
)
{
if
(
found
>=
0
)
/* PENDET must be disabled in NEC before reading ADC */
break
;
pendet_enable
(
tsdev
,
false
);
/* Disbale PENDET */
pmic12_pendet
(
tsdev
);
pendet_enable
(
tsdev
,
true
);
/*Enable PENDET */
}
else
if
(
tsdev
->
vendor
==
PMIC_VENDOR_FS
)
{
pendet_umask
();
/* Stop ADC */
pmic0_pendet
(
tsdev
);
pendet_mask
();
/* Stop ADC */
}
else
dev_err
(
&
tsdev
->
spi
->
dev
,
"Unsupported touchscreen: %d
\n
"
,
tsdev
->
vendor
);
tsdev
->
busy
=
false
;
err
=
intel_scu_ipc_ioread8
(
PMICADDR0
+
i
,
&
r8
);
if
(
err
)
return
err
;
if
(
r8
==
END_OF_CHANNEL
)
{
found
=
i
;
break
;
}
}
}
if
(
found
<
0
)
return
0
;
return
0
;
if
(
tsdev
->
vendor
==
PMIC_VENDOR_FS
)
{
if
(
found
&&
found
>
(
MRSTOUCH_MAX_CHANNELS
-
18
))
return
-
ENOSPC
;
}
else
{
if
(
found
&&
found
>
(
MRSTOUCH_MAX_CHANNELS
-
4
))
return
-
ENOSPC
;
}
return
found
;
}
}
/* PENDET interrupt handler */
static
irqreturn_t
pendet_intr_handler
(
int
irq
,
void
*
handle
)
/*
* Writes touch screen channels to ADC address selection registers
*/
static
int
__devinit
mrstouch_ts_chan_set
(
uint
offset
)
{
{
struct
mrstouch_dev
*
tsdev
=
(
struct
mrstouch_dev
*
)
handle
;
u16
chan
;
mutex_unlock
(
&
tsdev
->
lock
);
int
ret
,
count
;
return
IRQ_HANDLED
;
chan
=
PMICADDR0
+
offset
;
for
(
count
=
0
;
count
<=
3
;
count
++
)
{
ret
=
intel_scu_ipc_iowrite8
(
chan
++
,
MRST_TS_CHAN10
+
count
);
if
(
ret
)
return
ret
;
}
return
intel_scu_ipc_iowrite8
(
chan
++
,
END_OF_CHANNEL
);
}
}
/* In
tializes input device and registers with input subsystem
*/
/* In
itialize ADC
*/
static
int
ts_input_dev_init
(
struct
mrstouch_dev
*
tsdev
,
struct
spi_device
*
spi
)
static
int
__devinit
mrstouch_adc_init
(
struct
mrstouch_dev
*
tsdev
)
{
{
int
err
=
0
;
int
err
,
start
;
u8
ra
,
rm
;
mrstouch_debug
(
"%s"
,
__func__
);
err
=
mrstouch_read_pmic_id
(
&
tsdev
->
vendor
,
&
tsdev
->
rev
);
if
(
err
)
{
dev_err
(
tsdev
->
dev
,
"Unable to read PMIC id
\n
"
);
return
err
;
}
tsdev
->
input
=
input_allocate_device
();
switch
(
tsdev
->
vendor
)
{
if
(
!
tsdev
->
input
)
{
case
PMIC_VENDOR_NEC
:
dev_err
(
&
tsdev
->
spi
->
dev
,
"Unable to allocate input device.
\n
"
);
case
PMIC_VENDOR_MAXIM
:
return
-
EINVAL
;
tsdev
->
read_prepare
=
mrstouch_nec_adc_read_prepare
;
tsdev
->
read
=
mrstouch_nec_adc_read
;
tsdev
->
read_finish
=
mrstouch_nec_adc_read_finish
;
break
;
case
PMIC_VENDOR_FS
:
tsdev
->
read_prepare
=
mrstouch_fs_adc_read_prepare
;
tsdev
->
read
=
mrstouch_fs_adc_read
;
tsdev
->
read_finish
=
mrstouch_fs_adc_read_finish
;
break
;
default:
dev_err
(
tsdev
->
dev
,
"Unsupported touchscreen: %d
\n
"
,
tsdev
->
vendor
);
return
-
ENXIO
;
}
}
tsdev
->
input
->
name
=
"mrst_touchscreen"
;
start
=
mrstouch_chan_parse
(
tsdev
)
;
snprintf
(
tsdev
->
phys
,
sizeof
(
tsdev
->
phys
),
if
(
start
<
0
)
{
"%s/input0"
,
dev_name
(
&
spi
->
dev
)
);
dev_err
(
tsdev
->
dev
,
"Unable to parse channels
\n
"
);
tsdev
->
input
->
phys
=
tsdev
->
phys
;
return
start
;
tsdev
->
input
->
dev
.
parent
=
&
spi
->
dev
;
}
tsdev
->
input
->
id
.
vendor
=
tsdev
->
vendor
;
tsdev
->
asr
=
start
;
tsdev
->
input
->
id
.
version
=
tsdev
->
rev
;
tsdev
->
input
->
evbit
[
0
]
=
BIT_MASK
(
EV_KEY
)
|
BIT_MASK
(
EV_ABS
);
/*
tsdev
->
input
->
keybit
[
BIT_WORD
(
BTN_TOUCH
)]
=
BIT_MASK
(
BTN_TOUCH
);
* ADC power on, start, enable PENDET and set loop delay
* ADC loop delay is set to 4.5 ms approximately
* Loop delay more than this results in jitter in adc readings
* Setting loop delay to 0 (continous loop) in MAXIM stops PENDET
* interrupt generation sometimes.
*/
input_set_abs_params
(
tsdev
->
input
,
ABS_X
,
MIN_X
,
MIN_Y
,
0
,
0
);
if
(
tsdev
->
vendor
==
PMIC_VENDOR_FS
)
{
input_set_abs_params
(
tsdev
->
input
,
ABS_Y
,
MIN_X
,
MIN_Y
,
0
,
0
);
ra
=
0xE0
|
ADC_LOOP_DELAY0
;
rm
=
0x5
;
}
else
{
/* NEC and MAXIm not consistent with loop delay 0 */
ra
=
0xE0
|
ADC_LOOP_DELAY1
;
rm
=
0x0
;
err
=
input_register_device
(
tsdev
->
input
);
/* configure touch screen channels */
if
(
err
)
{
err
=
mrstouch_ts_chan_set
(
tsdev
->
asr
);
dev_err
(
&
tsdev
->
spi
->
dev
,
"unable to register input device
\n
"
);
if
(
err
)
input_free_device
(
tsdev
->
input
);
return
err
;
return
err
;
}
}
mrstouch_debug
(
"%s"
,
"mrstouch initialized"
);
err
=
intel_scu_ipc_update_register
(
PMIC_REG_ADCCNTL1
,
ra
,
0xE7
);
if
(
err
)
return
err
;
return
0
;
err
=
intel_scu_ipc_update_register
(
PMIC_REG_MADCINT
,
rm
,
0x03
);
if
(
err
)
return
err
;
return
0
;
}
}
/* Probe function for touch screen driver */
/* Probe function for touch screen driver */
static
int
__devinit
mrstouch_probe
(
struct
spi_device
*
mrstouch_spi
)
static
int
__devinit
mrstouch_probe
(
struct
platform_device
*
pdev
)
{
{
int
err
;
unsigned
int
myirq
;
struct
mrstouch_dev
*
tsdev
;
struct
mrstouch_dev
*
tsdev
;
struct
input_dev
*
input
;
int
err
;
int
irq
;
mrstouch_debug
(
"%s(%p)"
,
__func__
,
mrstouch_spi
);
irq
=
platform_get_irq
(
pdev
,
0
);
if
(
irq
<
0
)
{
mrstouchdevp
=
NULL
;
dev_err
(
&
pdev
->
dev
,
"no interrupt assigned
\n
"
);
myirq
=
mrstouch_spi
->
irq
;
if
(
!
mrstouch_spi
->
irq
)
{
dev_err
(
&
mrstouch_spi
->
dev
,
"no interrupt assigned
\n
"
);
return
-
EINVAL
;
return
-
EINVAL
;
}
}
tsdev
=
kzalloc
(
sizeof
(
struct
mrstouch_dev
),
GFP_KERNEL
);
tsdev
=
kzalloc
(
sizeof
(
struct
mrstouch_dev
),
GFP_KERNEL
);
if
(
!
tsdev
)
{
input
=
input_allocate_device
();
dev_err
(
&
mrstouch_spi
->
dev
,
"unable to allocate memory
\n
"
);
if
(
!
tsdev
||
!
input
)
{
return
-
ENOMEM
;
dev_err
(
&
pdev
->
dev
,
"unable to allocate memory
\n
"
);
err
=
-
ENOMEM
;
goto
err_free_mem
;
}
}
tsdev
->
irq
=
myirq
;
tsdev
->
dev
=
&
pdev
->
dev
;
mrstouchdevp
=
tsdev
;
tsdev
->
input
=
input
;
tsdev
->
irq
=
irq
;
snprintf
(
tsdev
->
phys
,
sizeof
(
tsdev
->
phys
),
"%s/input0"
,
dev_name
(
tsdev
->
dev
));
err
=
mrstouch_adc_init
(
tsdev
);
err
=
mrstouch_adc_init
(
tsdev
);
if
(
err
)
{
if
(
err
)
{
dev_err
(
&
mrstouch_spi
->
dev
,
"ADC init
failed
\n
"
);
dev_err
(
&
pdev
->
dev
,
"ADC initialization
failed
\n
"
);
goto
mrstouch_
err_free_mem
;
goto
err_free_mem
;
}
}
dev_set_drvdata
(
&
mrstouch_spi
->
dev
,
tsdev
);
input
->
name
=
"mrst_touchscreen"
;
tsdev
->
spi
=
mrstouch_spi
;
input
->
phys
=
tsdev
->
phys
;
input
->
dev
.
parent
=
tsdev
->
dev
;
err
=
ts_input_dev_init
(
tsdev
,
mrstouch_spi
)
;
input
->
id
.
vendor
=
tsdev
->
vendor
;
i
f
(
err
)
{
i
nput
->
id
.
version
=
tsdev
->
rev
;
dev_err
(
&
tsdev
->
spi
->
dev
,
"ts_input_dev_init failed"
);
goto
mrstouch_err_free_mem
;
input
->
evbit
[
0
]
=
BIT_MASK
(
EV_KEY
)
|
BIT_MASK
(
EV_ABS
)
;
}
input
->
keybit
[
BIT_WORD
(
BTN_TOUCH
)]
=
BIT_MASK
(
BTN_TOUCH
);
mutex_init
(
&
tsdev
->
lock
);
input_set_abs_params
(
tsdev
->
input
,
ABS_X
,
mutex_lock
(
&
tsdev
->
lock
)
MRST_X_MIN
,
MRST_X_MAX
,
MRST_X_FUZZ
,
0
);
input_set_abs_params
(
tsdev
->
input
,
ABS_Y
,
MRST_Y_MIN
,
MRST_Y_MAX
,
MRST_Y_FUZZ
,
0
);
input_set_abs_params
(
tsdev
->
input
,
ABS_PRESSURE
,
MRST_PRESSURE_MIN
,
MRST_PRESSURE_MAX
,
0
,
0
);
mrstouch_debug
(
"Requesting IRQ-%d"
,
myirq
);
err
=
request_threaded_irq
(
tsdev
->
irq
,
NULL
,
mrstouch_pendet_irq
,
err
=
request_irq
(
myirq
,
pendet_intr_handler
,
0
,
"mrstouch"
,
tsdev
);
0
,
"mrstouch"
,
tsdev
);
if
(
err
)
{
if
(
err
)
{
dev_err
(
&
tsdev
->
spi
->
dev
,
"unable to allocate irq
\n
"
);
dev_err
(
tsdev
->
dev
,
"unable to allocate irq
\n
"
);
goto
mrstouch_
err_free_mem
;
goto
err_free_mem
;
}
}
tsdev
->
pendet_thrd
=
kthread_run
(
mrstouch_pendet
,
err
=
input_register_device
(
tsdev
->
input
);
(
void
*
)
tsdev
,
"pendet handler"
);
if
(
err
)
{
if
(
IS_ERR
(
tsdev
->
pendet_thrd
))
{
dev_err
(
tsdev
->
dev
,
"unable to register input device
\n
"
);
dev_err
(
&
tsdev
->
spi
->
dev
,
"kthread_run failed
\n
"
);
goto
err_free_irq
;
err
=
PTR_ERR
(
tsdev
->
pendet_thrd
);
goto
mrstouch_err_free_mem
;
}
}
mrstouch_debug
(
"%s"
,
"Driver initialized"
);
platform_set_drvdata
(
pdev
,
tsdev
);
return
0
;
return
0
;
mrstouch_err_free_mem:
err_free_irq:
free_irq
(
tsdev
->
irq
,
tsdev
);
err_free_mem:
input_free_device
(
input
);
kfree
(
tsdev
);
kfree
(
tsdev
);
return
err
;
return
err
;
}
}
static
int
mrstouch_suspend
(
struct
spi_device
*
spi
,
pm_message_t
msg
)
static
int
__devexit
mrstouch_remove
(
struct
platform_device
*
pdev
)
{
{
mrstouch_debug
(
"%s"
,
__func__
);
struct
mrstouch_dev
*
tsdev
=
platform_get_drvdata
(
pdev
);
mrstouchdevp
->
suspended
=
1
;
return
0
;
}
static
int
mrstouch_resume
(
struct
spi_device
*
spi
)
free_irq
(
tsdev
->
irq
,
tsdev
);
{
input_unregister_device
(
tsdev
->
input
);
mrstouch_debug
(
"%s"
,
__func__
);
kfree
(
tsdev
);
mrstouchdevp
->
suspended
=
0
;
return
0
;
platform_set_drvdata
(
pdev
,
NULL
);
}
static
int
mrstouch_remove
(
struct
spi_device
*
spi
)
{
mrstouch_debug
(
"%s"
,
__func__
);
free_irq
(
mrstouchdevp
->
irq
,
mrstouchdevp
);
input_unregister_device
(
mrstouchdevp
->
input
);
input_free_device
(
mrstouchdevp
->
input
);
if
(
mrstouchdevp
->
pendet_thrd
)
kthread_stop
(
mrstouchdevp
->
pendet_thrd
);
kfree
(
mrstouchdevp
);
return
0
;
return
0
;
}
}
static
struct
spi
_driver
mrstouch_driver
=
{
static
struct
platform
_driver
mrstouch_driver
=
{
.
driver
=
{
.
driver
=
{
.
name
=
"pmic_touch"
,
.
name
=
"pmic_touch"
,
.
bus
=
&
spi_bus_type
,
.
owner
=
THIS_MODULE
,
.
owner
=
THIS_MODULE
,
},
},
.
probe
=
mrstouch_probe
,
.
probe
=
mrstouch_probe
,
.
suspend
=
mrstouch_suspend
,
.
remove
=
__devexit_p
(
mrstouch_remove
),
.
resume
=
mrstouch_resume
,
.
remove
=
mrstouch_remove
,
};
};
static
int
__init
mrstouch_
module_
init
(
void
)
static
int
__init
mrstouch_init
(
void
)
{
{
int
err
;
return
platform_driver_register
(
&
mrstouch_driver
);
mrstouch_debug
(
"%s"
,
__func__
);
err
=
spi_register_driver
(
&
mrstouch_driver
);
if
(
err
)
{
mrstouch_debug
(
"%s(%d)"
,
"SPI PENDET failed"
,
err
);
return
-
1
;
}
return
0
;
}
}
module_init
(
mrstouch_init
);
static
void
__exit
mrstouch_
module_
exit
(
void
)
static
void
__exit
mrstouch_exit
(
void
)
{
{
mrstouch_debug
(
"%s"
,
__func__
);
platform_driver_unregister
(
&
mrstouch_driver
);
spi_unregister_driver
(
&
mrstouch_driver
);
return
;
}
}
module_exit
(
mrstouch_exit
);
module_init
(
mrstouch_module_init
);
module_exit
(
mrstouch_module_exit
);
MODULE_AUTHOR
(
"Sreedhara Murthy. D.S, sreedhara.ds@intel.com"
);
MODULE_AUTHOR
(
"Sreedhara Murthy. D.S, sreedhara.ds@intel.com"
);
MODULE_DESCRIPTION
(
"Intel Moorestown Resistive Touch Screen Driver"
);
MODULE_DESCRIPTION
(
"Intel Moorestown Resistive Touch Screen Driver"
);
...
...
drivers/staging/Kconfig
View file @
92944c1c
...
@@ -141,8 +141,6 @@ source "drivers/staging/adis16255/Kconfig"
...
@@ -141,8 +141,6 @@ source "drivers/staging/adis16255/Kconfig"
source "drivers/staging/xgifb/Kconfig"
source "drivers/staging/xgifb/Kconfig"
source "drivers/staging/mrst-touchscreen/Kconfig"
source "drivers/staging/msm/Kconfig"
source "drivers/staging/msm/Kconfig"
source "drivers/staging/lirc/Kconfig"
source "drivers/staging/lirc/Kconfig"
...
...
drivers/staging/Makefile
View file @
92944c1c
...
@@ -52,7 +52,6 @@ obj-$(CONFIG_CXT1E1) += cxt1e1/
...
@@ -52,7 +52,6 @@ obj-$(CONFIG_CXT1E1) += cxt1e1/
obj-$(CONFIG_TI_ST)
+=
ti-st/
obj-$(CONFIG_TI_ST)
+=
ti-st/
obj-$(CONFIG_ADIS16255)
+=
adis16255/
obj-$(CONFIG_ADIS16255)
+=
adis16255/
obj-$(CONFIG_FB_XGI)
+=
xgifb/
obj-$(CONFIG_FB_XGI)
+=
xgifb/
obj-$(CONFIG_TOUCHSCREEN_MRSTOUCH)
+=
mrst-touchscreen/
obj-$(CONFIG_MSM_STAGING)
+=
msm/
obj-$(CONFIG_MSM_STAGING)
+=
msm/
obj-$(CONFIG_EASYCAP)
+=
easycap/
obj-$(CONFIG_EASYCAP)
+=
easycap/
obj-$(CONFIG_SOLO6X10)
+=
solo6x10/
obj-$(CONFIG_SOLO6X10)
+=
solo6x10/
...
...
drivers/staging/mrst-touchscreen/Kconfig
deleted
100644 → 0
View file @
77686517
config TOUCHSCREEN_INTEL_MID
tristate "Intel MID platform resistive touchscreen"
depends on INTEL_SCU_IPC
default y
help
Say Y here if you have a Intel MID based touchscreen
If unsure, say N.
drivers/staging/mrst-touchscreen/Makefile
deleted
100644 → 0
View file @
77686517
obj-$(CONFIG_TOUCHSCREEN_INTEL_MID)
:=
intel_mid_touch.o
drivers/staging/mrst-touchscreen/TODO
deleted
100644 → 0
View file @
77686517
- Move the driver to not think it is SPI (requires fixing some of the SFI
and firmware side)
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment