create firmware image for the Ubiquiti LS-SR71 board
[openwrt/openwrt.git] / target / linux / s3c24xx / patches-2.6.26 / 1014-s3c2410_touchscreen.patch.patch
1 From fc5d5366335469828d78898e2e74f8f80aa1d076 Mon Sep 17 00:00:00 2001
2 From: mokopatches <mokopatches@openmoko.org>
3 Date: Wed, 16 Jul 2008 14:44:49 +0100
4 Subject: [PATCH] s3c2410_touchscreen.patch
5
6 ---
7 arch/arm/mach-s3c2410/mach-h1940.c | 8 +
8 arch/arm/plat-s3c24xx/devs.c | 18 ++
9 arch/arm/plat-s3c24xx/s3c244x.c | 1 +
10 drivers/input/touchscreen/Kconfig | 18 ++
11 drivers/input/touchscreen/Makefile | 1 +
12 drivers/input/touchscreen/s3c2410_ts.c | 437 ++++++++++++++++++++++++++++++++
13 include/asm-arm/arch-s3c2410/ts.h | 28 ++
14 include/asm-arm/plat-s3c24xx/devs.h | 1 +
15 8 files changed, 512 insertions(+), 0 deletions(-)
16 create mode 100644 drivers/input/touchscreen/s3c2410_ts.c
17 create mode 100644 include/asm-arm/arch-s3c2410/ts.h
18
19 diff --git a/arch/arm/mach-s3c2410/mach-h1940.c b/arch/arm/mach-s3c2410/mach-h1940.c
20 index 7c1145e..93cd8c8 100644
21 --- a/arch/arm/mach-s3c2410/mach-h1940.c
22 +++ b/arch/arm/mach-s3c2410/mach-h1940.c
23 @@ -38,6 +38,7 @@
24 #include <asm/arch/h1940.h>
25 #include <asm/arch/h1940-latch.h>
26 #include <asm/arch/fb.h>
27 +#include <asm/arch/tc.h>
28 #include <asm/plat-s3c24xx/udc.h>
29
30 #include <asm/plat-s3c24xx/clock.h>
31 @@ -129,6 +130,11 @@ static struct s3c2410_udc_mach_info h1940_udc_cfg __initdata = {
32 .vbus_pin_inverted = 1,
33 };
34
35 +static struct s3c2410_ts_mach_info h1940_ts_cfg __initdata = {
36 + .delay = 10000,
37 + .presc = 49,
38 + .oversampling_shift = 2,
39 +};
40
41 /**
42 * Set lcd on or off
43 @@ -186,6 +192,7 @@ static struct platform_device *h1940_devices[] __initdata = {
44 &s3c_device_i2c,
45 &s3c_device_iis,
46 &s3c_device_usbgadget,
47 + &s3c_device_ts,
48 &s3c_device_leds,
49 &s3c_device_bluetooth,
50 };
51 @@ -214,6 +221,7 @@ static void __init h1940_init(void)
52 u32 tmp;
53
54 s3c24xx_fb_set_platdata(&h1940_fb_info);
55 + set_s3c2410ts_info(&h1940_ts_cfg);
56 s3c24xx_udc_set_platdata(&h1940_udc_cfg);
57
58 /* Turn off suspend on both USB ports, and switch the
59 diff --git a/arch/arm/plat-s3c24xx/devs.c b/arch/arm/plat-s3c24xx/devs.c
60 index e546e93..c1fbe2d 100644
61 --- a/arch/arm/plat-s3c24xx/devs.c
62 +++ b/arch/arm/plat-s3c24xx/devs.c
63 @@ -24,6 +24,7 @@
64 #include <asm/mach/map.h>
65 #include <asm/mach/irq.h>
66 #include <asm/arch/fb.h>
67 +#include <asm/arch/ts.h>
68 #include <asm/hardware.h>
69 #include <asm/io.h>
70 #include <asm/irq.h>
71 @@ -207,6 +208,23 @@ struct platform_device s3c_device_nand = {
72
73 EXPORT_SYMBOL(s3c_device_nand);
74
75 +/* Touchscreen */
76 +struct platform_device s3c_device_ts = {
77 + .name = "s3c2410-ts",
78 + .id = -1,
79 +};
80 +
81 +EXPORT_SYMBOL(s3c_device_ts);
82 +
83 +static struct s3c2410_ts_mach_info s3c2410ts_info;
84 +
85 +void set_s3c2410ts_info(struct s3c2410_ts_mach_info *hard_s3c2410ts_info)
86 +{
87 + memcpy(&s3c2410ts_info,hard_s3c2410ts_info,sizeof(struct s3c2410_ts_mach_info));
88 + s3c_device_ts.dev.platform_data = &s3c2410ts_info;
89 +}
90 +EXPORT_SYMBOL(set_s3c2410ts_info);
91 +
92 /* USB Device (Gadget)*/
93
94 static struct resource s3c_usbgadget_resource[] = {
95 diff --git a/arch/arm/plat-s3c24xx/s3c244x.c b/arch/arm/plat-s3c24xx/s3c244x.c
96 index 2f01af5..7a1a12d 100644
97 --- a/arch/arm/plat-s3c24xx/s3c244x.c
98 +++ b/arch/arm/plat-s3c24xx/s3c244x.c
99 @@ -68,6 +68,7 @@ void __init s3c244x_map_io(struct map_desc *mach_desc, int size)
100 s3c_device_sdi.name = "s3c2440-sdi";
101 s3c_device_i2c.name = "s3c2440-i2c";
102 s3c_device_nand.name = "s3c2440-nand";
103 + s3c_device_ts.name = "s3c2440-ts";
104 s3c_device_usbgadget.name = "s3c2440-usbgadget";
105 }
106
107 diff --git a/drivers/input/touchscreen/Kconfig b/drivers/input/touchscreen/Kconfig
108 index 565ec71..52de2b0 100644
109 --- a/drivers/input/touchscreen/Kconfig
110 +++ b/drivers/input/touchscreen/Kconfig
111 @@ -67,6 +67,24 @@ config TOUCHSCREEN_FUJITSU
112 To compile this driver as a module, choose M here: the
113 module will be called fujitsu-ts.
114
115 +config TOUCHSCREEN_S3C2410
116 + tristate "Samsung S3C2410 touchscreen input driver"
117 + depends on ARCH_S3C2410 && INPUT && INPUT_TOUCHSCREEN
118 + select SERIO
119 + help
120 + Say Y here if you have the s3c2410 touchscreen.
121 +
122 + If unsure, say N.
123 +
124 + To compile this driver as a module, choose M here: the
125 + module will be called s3c2410_ts.
126 +
127 +config TOUCHSCREEN_S3C2410_DEBUG
128 + boolean "Samsung S3C2410 touchscreen debug messages"
129 + depends on TOUCHSCREEN_S3C2410
130 + help
131 + Select this if you want debug messages
132 +
133 config TOUCHSCREEN_GUNZE
134 tristate "Gunze AHL-51S touchscreen"
135 select SERIO
136 diff --git a/drivers/input/touchscreen/Makefile b/drivers/input/touchscreen/Makefile
137 index 3c096d7..7c3bd1c 100644
138 --- a/drivers/input/touchscreen/Makefile
139 +++ b/drivers/input/touchscreen/Makefile
140 @@ -26,3 +26,4 @@ wm97xx-ts-$(CONFIG_TOUCHSCREEN_WM9705) += wm9705.o
141 wm97xx-ts-$(CONFIG_TOUCHSCREEN_WM9712) += wm9712.o
142 wm97xx-ts-$(CONFIG_TOUCHSCREEN_WM9713) += wm9713.o
143 obj-$(CONFIG_TOUCHSCREEN_WM97XX_MAINSTONE) += mainstone-wm97xx.o
144 +obj-$(CONFIG_TOUCHSCREEN_S3C2410) += s3c2410_ts.o
145 diff --git a/drivers/input/touchscreen/s3c2410_ts.c b/drivers/input/touchscreen/s3c2410_ts.c
146 new file mode 100644
147 index 0000000..68071c2
148 --- /dev/null
149 +++ b/drivers/input/touchscreen/s3c2410_ts.c
150 @@ -0,0 +1,437 @@
151 +/*
152 + * This program is free software; you can redistribute it and/or modify
153 + * it under the terms of the GNU General Public License as published by
154 + * the Free Software Foundation; either version 2 of the License, or
155 + * (at your option) any later version.
156 + *
157 + * This program is distributed in the hope that it will be useful,
158 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
159 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
160 + * GNU General Public License for more details.
161 + *
162 + * You should have received a copy of the GNU General Public License
163 + * along with this program; if not, write to the Free Software
164 + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
165 + *
166 + * Copyright (c) 2004 Arnaud Patard <arnaud.patard@rtp-net.org>
167 + * iPAQ H1940 touchscreen support
168 + *
169 + * ChangeLog
170 + *
171 + * 2004-09-05: Herbert Pƶtzl <herbert@13thfloor.at>
172 + * - added clock (de-)allocation code
173 + *
174 + * 2005-03-06: Arnaud Patard <arnaud.patard@rtp-net.org>
175 + * - h1940_ -> s3c2410 (this driver is now also used on the n30
176 + * machines :P)
177 + * - Debug messages are now enabled with the config option
178 + * TOUCHSCREEN_S3C2410_DEBUG
179 + * - Changed the way the value are read
180 + * - Input subsystem should now work
181 + * - Use ioremap and readl/writel
182 + *
183 + * 2005-03-23: Arnaud Patard <arnaud.patard@rtp-net.org>
184 + * - Make use of some undocumented features of the touchscreen
185 + * controller
186 + *
187 + * 2007-05-23: Harald Welte <laforge@openmoko.org>
188 + * - Add proper support for S32440
189 + */
190 +
191 +#include <linux/errno.h>
192 +#include <linux/kernel.h>
193 +#include <linux/module.h>
194 +#include <linux/slab.h>
195 +#include <linux/input.h>
196 +#include <linux/init.h>
197 +#include <linux/serio.h>
198 +#include <linux/delay.h>
199 +#include <linux/platform_device.h>
200 +#include <linux/clk.h>
201 +#include <asm/io.h>
202 +#include <asm/irq.h>
203 +
204 +#include <asm/arch/regs-gpio.h>
205 +#include <asm/arch/ts.h>
206 +
207 +#include <asm/plat-s3c/regs-adc.h>
208 +
209 +/* For ts.dev.id.version */
210 +#define S3C2410TSVERSION 0x0101
211 +
212 +#define TSC_SLEEP (S3C2410_ADCTSC_PULL_UP_DISABLE | S3C2410_ADCTSC_XY_PST(0))
213 +
214 +#define WAIT4INT(x) (((x)<<8) | \
215 + S3C2410_ADCTSC_YM_SEN | S3C2410_ADCTSC_YP_SEN | S3C2410_ADCTSC_XP_SEN | \
216 + S3C2410_ADCTSC_XY_PST(3))
217 +
218 +#define AUTOPST (S3C2410_ADCTSC_YM_SEN | S3C2410_ADCTSC_YP_SEN | S3C2410_ADCTSC_XP_SEN | \
219 + S3C2410_ADCTSC_AUTO_PST | S3C2410_ADCTSC_XY_PST(0))
220 +
221 +#define DEBUG_LVL KERN_DEBUG
222 +
223 +MODULE_AUTHOR("Arnaud Patard <arnaud.patard@rtp-net.org>");
224 +MODULE_DESCRIPTION("s3c2410 touchscreen driver");
225 +MODULE_LICENSE("GPL");
226 +
227 +/*
228 + * Definitions & global arrays.
229 + */
230 +
231 +
232 +static char *s3c2410ts_name = "s3c2410 TouchScreen";
233 +
234 +/*
235 + * Per-touchscreen data.
236 + */
237 +
238 +struct s3c2410ts {
239 + struct input_dev *dev;
240 + long xp;
241 + long yp;
242 + int count;
243 + int shift;
244 +};
245 +
246 +static struct s3c2410ts ts;
247 +static void __iomem *base_addr;
248 +
249 +static inline void s3c2410_ts_connect(void)
250 +{
251 + s3c2410_gpio_cfgpin(S3C2410_GPG12, S3C2410_GPG12_XMON);
252 + s3c2410_gpio_cfgpin(S3C2410_GPG13, S3C2410_GPG13_nXPON);
253 + s3c2410_gpio_cfgpin(S3C2410_GPG14, S3C2410_GPG14_YMON);
254 + s3c2410_gpio_cfgpin(S3C2410_GPG15, S3C2410_GPG15_nYPON);
255 +}
256 +
257 +static void touch_timer_fire(unsigned long data)
258 +{
259 + unsigned long data0;
260 + unsigned long data1;
261 + int updown;
262 +
263 + data0 = readl(base_addr+S3C2410_ADCDAT0);
264 + data1 = readl(base_addr+S3C2410_ADCDAT1);
265 +
266 + updown = (!(data0 & S3C2410_ADCDAT0_UPDOWN)) && (!(data1 & S3C2410_ADCDAT0_UPDOWN));
267 +
268 + if (updown) {
269 + if (ts.count != 0) {
270 + ts.xp >>= ts.shift;
271 + ts.yp >>= ts.shift;
272 +
273 +#ifdef CONFIG_TOUCHSCREEN_S3C2410_DEBUG
274 + {
275 + struct timeval tv;
276 + do_gettimeofday(&tv);
277 + printk(DEBUG_LVL "T: %06d, X: %03ld, Y: %03ld\n", (int)tv.tv_usec, ts.xp, ts.yp);
278 + }
279 +#endif
280 +
281 + input_report_abs(ts.dev, ABS_X, ts.xp);
282 + input_report_abs(ts.dev, ABS_Y, ts.yp);
283 +
284 + input_report_key(ts.dev, BTN_TOUCH, 1);
285 + input_report_abs(ts.dev, ABS_PRESSURE, 1);
286 + input_sync(ts.dev);
287 + }
288 +
289 + ts.xp = 0;
290 + ts.yp = 0;
291 + ts.count = 0;
292 +
293 + writel(S3C2410_ADCTSC_PULL_UP_DISABLE | AUTOPST, base_addr+S3C2410_ADCTSC);
294 + writel(readl(base_addr+S3C2410_ADCCON) | S3C2410_ADCCON_ENABLE_START, base_addr+S3C2410_ADCCON);
295 + } else {
296 + ts.count = 0;
297 +
298 + input_report_key(ts.dev, BTN_TOUCH, 0);
299 + input_report_abs(ts.dev, ABS_PRESSURE, 0);
300 + input_sync(ts.dev);
301 +
302 + writel(WAIT4INT(0), base_addr+S3C2410_ADCTSC);
303 + }
304 +}
305 +
306 +static struct timer_list touch_timer =
307 + TIMER_INITIALIZER(touch_timer_fire, 0, 0);
308 +
309 +static irqreturn_t stylus_updown(int irq, void *dev_id)
310 +{
311 + unsigned long data0;
312 + unsigned long data1;
313 + int updown;
314 +
315 + data0 = readl(base_addr+S3C2410_ADCDAT0);
316 + data1 = readl(base_addr+S3C2410_ADCDAT1);
317 +
318 + updown = (!(data0 & S3C2410_ADCDAT0_UPDOWN)) && (!(data1 & S3C2410_ADCDAT0_UPDOWN));
319 +
320 + /* TODO we should never get an interrupt with updown set while
321 + * the timer is running, but maybe we ought to verify that the
322 + * timer isn't running anyways. */
323 +
324 + if (updown)
325 + touch_timer_fire(0);
326 +
327 + return IRQ_HANDLED;
328 +}
329 +
330 +
331 +static irqreturn_t stylus_action(int irq, void *dev_id)
332 +{
333 + unsigned long data0;
334 + unsigned long data1;
335 +
336 + data0 = readl(base_addr+S3C2410_ADCDAT0);
337 + data1 = readl(base_addr+S3C2410_ADCDAT1);
338 +
339 + ts.xp += data0 & S3C2410_ADCDAT0_XPDATA_MASK;
340 + ts.yp += data1 & S3C2410_ADCDAT1_YPDATA_MASK;
341 + ts.count++;
342 +
343 + if (ts.count < (1<<ts.shift)) {
344 + writel(S3C2410_ADCTSC_PULL_UP_DISABLE | AUTOPST, base_addr+S3C2410_ADCTSC);
345 + writel(readl(base_addr+S3C2410_ADCCON) | S3C2410_ADCCON_ENABLE_START, base_addr+S3C2410_ADCCON);
346 + } else {
347 + mod_timer(&touch_timer, jiffies+1);
348 + writel(WAIT4INT(1), base_addr+S3C2410_ADCTSC);
349 + }
350 +
351 + return IRQ_HANDLED;
352 +}
353 +
354 +static struct clk *adc_clock;
355 +
356 +/*
357 + * The functions for inserting/removing us as a module.
358 + */
359 +
360 +static int __init s3c2410ts_probe(struct platform_device *pdev)
361 +{
362 + int rc;
363 + struct s3c2410_ts_mach_info *info;
364 + struct input_dev *input_dev;
365 +
366 + info = ( struct s3c2410_ts_mach_info *)pdev->dev.platform_data;
367 +
368 + if (!info)
369 + {
370 + printk(KERN_ERR "Hm... too bad : no platform data for ts\n");
371 + return -EINVAL;
372 + }
373 +
374 +#ifdef CONFIG_TOUCHSCREEN_S3C2410_DEBUG
375 + printk(DEBUG_LVL "Entering s3c2410ts_init\n");
376 +#endif
377 +
378 + adc_clock = clk_get(NULL, "adc");
379 + if (!adc_clock) {
380 + printk(KERN_ERR "failed to get adc clock source\n");
381 + return -ENOENT;
382 + }
383 + clk_enable(adc_clock);
384 +
385 +#ifdef CONFIG_TOUCHSCREEN_S3C2410_DEBUG
386 + printk(DEBUG_LVL "got and enabled clock\n");
387 +#endif
388 +
389 + base_addr = ioremap(S3C2410_PA_ADC,0x20);
390 + if (base_addr == NULL) {
391 + printk(KERN_ERR "Failed to remap register block\n");
392 + return -ENOMEM;
393 + }
394 +
395 +
396 + /* If we acutally are a S3C2410: Configure GPIOs */
397 + if (!strcmp(pdev->name, "s3c2410-ts"))
398 + s3c2410_ts_connect();
399 +
400 + if ((info->presc&0xff) > 0)
401 + writel(S3C2410_ADCCON_PRSCEN | S3C2410_ADCCON_PRSCVL(info->presc&0xFF),\
402 + base_addr+S3C2410_ADCCON);
403 + else
404 + writel(0,base_addr+S3C2410_ADCCON);
405 +
406 +
407 + /* Initialise registers */
408 + if ((info->delay&0xffff) > 0)
409 + writel(info->delay & 0xffff, base_addr+S3C2410_ADCDLY);
410 +
411 + writel(WAIT4INT(0), base_addr+S3C2410_ADCTSC);
412 +
413 + /* Initialise input stuff */
414 + memset(&ts, 0, sizeof(struct s3c2410ts));
415 + input_dev = input_allocate_device();
416 +
417 + if (!input_dev) {
418 + printk(KERN_ERR "Unable to allocate the input device !!\n");
419 + return -ENOMEM;
420 + }
421 +
422 + ts.dev = input_dev;
423 + ts.dev->evbit[0] = BIT_MASK(EV_SYN) | BIT_MASK(EV_KEY) |
424 + BIT_MASK(EV_ABS);
425 + ts.dev->keybit[BIT_WORD(BTN_TOUCH)] = BIT_MASK(BTN_TOUCH);
426 + input_set_abs_params(ts.dev, ABS_X, 0, 0x3FF, 0, 0);
427 + input_set_abs_params(ts.dev, ABS_Y, 0, 0x3FF, 0, 0);
428 + input_set_abs_params(ts.dev, ABS_PRESSURE, 0, 1, 0, 0);
429 +
430 + ts.dev->private = &ts;
431 + ts.dev->name = s3c2410ts_name;
432 + ts.dev->id.bustype = BUS_RS232;
433 + ts.dev->id.vendor = 0xDEAD;
434 + ts.dev->id.product = 0xBEEF;
435 + ts.dev->id.version = S3C2410TSVERSION;
436 +
437 + ts.shift = info->oversampling_shift;
438 +
439 + /* Get irqs */
440 + if (request_irq(IRQ_ADC, stylus_action, IRQF_SAMPLE_RANDOM,
441 + "s3c2410_action", ts.dev)) {
442 + printk(KERN_ERR "s3c2410_ts.c: Could not allocate ts IRQ_ADC !\n");
443 + iounmap(base_addr);
444 + return -EIO;
445 + }
446 + if (request_irq(IRQ_TC, stylus_updown, IRQF_SAMPLE_RANDOM,
447 + "s3c2410_action", ts.dev)) {
448 + printk(KERN_ERR "s3c2410_ts.c: Could not allocate ts IRQ_TC !\n");
449 + free_irq(IRQ_ADC, ts.dev);
450 + iounmap(base_addr);
451 + return -EIO;
452 + }
453 +
454 + printk(KERN_INFO "%s successfully loaded\n", s3c2410ts_name);
455 +
456 + /* All went ok, so register to the input system */
457 + rc = input_register_device(ts.dev);
458 + if (rc) {
459 + free_irq(IRQ_TC, ts.dev);
460 + free_irq(IRQ_ADC, ts.dev);
461 + clk_disable(adc_clock);
462 + iounmap(base_addr);
463 + return -EIO;
464 + }
465 +
466 + return 0;
467 +}
468 +
469 +static int s3c2410ts_remove(struct platform_device *pdev)
470 +{
471 + disable_irq(IRQ_ADC);
472 + disable_irq(IRQ_TC);
473 + free_irq(IRQ_TC,ts.dev);
474 + free_irq(IRQ_ADC,ts.dev);
475 +
476 + if (adc_clock) {
477 + clk_disable(adc_clock);
478 + clk_put(adc_clock);
479 + adc_clock = NULL;
480 + }
481 +
482 + input_unregister_device(ts.dev);
483 + iounmap(base_addr);
484 +
485 + return 0;
486 +}
487 +
488 +#ifdef CONFIG_PM
489 +static int s3c2410ts_suspend(struct platform_device *pdev, pm_message_t state)
490 +{
491 + writel(TSC_SLEEP, base_addr+S3C2410_ADCTSC);
492 + writel(readl(base_addr+S3C2410_ADCCON) | S3C2410_ADCCON_STDBM,
493 + base_addr+S3C2410_ADCCON);
494 +
495 + disable_irq(IRQ_ADC);
496 + disable_irq(IRQ_TC);
497 +
498 + clk_disable(adc_clock);
499 +
500 + return 0;
501 +}
502 +
503 +static int s3c2410ts_resume(struct platform_device *pdev)
504 +{
505 + struct s3c2410_ts_mach_info *info =
506 + ( struct s3c2410_ts_mach_info *)pdev->dev.platform_data;
507 +
508 + clk_enable(adc_clock);
509 + msleep(1);
510 +
511 + enable_irq(IRQ_ADC);
512 + enable_irq(IRQ_TC);
513 +
514 + if ((info->presc&0xff) > 0)
515 + writel(S3C2410_ADCCON_PRSCEN | S3C2410_ADCCON_PRSCVL(info->presc&0xFF),\
516 + base_addr+S3C2410_ADCCON);
517 + else
518 + writel(0,base_addr+S3C2410_ADCCON);
519 +
520 + /* Initialise registers */
521 + if ((info->delay&0xffff) > 0)
522 + writel(info->delay & 0xffff, base_addr+S3C2410_ADCDLY);
523 +
524 + writel(WAIT4INT(0), base_addr+S3C2410_ADCTSC);
525 +
526 + return 0;
527 +}
528 +
529 +#else
530 +#define s3c2410ts_suspend NULL
531 +#define s3c2410ts_resume NULL
532 +#endif
533 +
534 +static struct platform_driver s3c2410ts_driver = {
535 + .driver = {
536 + .name = "s3c2410-ts",
537 + .owner = THIS_MODULE,
538 + },
539 + .probe = s3c2410ts_probe,
540 + .remove = s3c2410ts_remove,
541 + .suspend = s3c2410ts_suspend,
542 + .resume = s3c2410ts_resume,
543 +
544 +};
545 +
546 +static struct platform_driver s3c2440ts_driver = {
547 + .driver = {
548 + .name = "s3c2440-ts",
549 + .owner = THIS_MODULE,
550 + },
551 + .probe = s3c2410ts_probe,
552 + .remove = s3c2410ts_remove,
553 + .suspend = s3c2410ts_suspend,
554 + .resume = s3c2410ts_resume,
555 +
556 +};
557 +
558 +static int __init s3c2410ts_init(void)
559 +{
560 + int rc;
561 +
562 + rc = platform_driver_register(&s3c2410ts_driver);
563 + if (rc < 0)
564 + return rc;
565 +
566 + rc = platform_driver_register(&s3c2440ts_driver);
567 + if (rc < 0)
568 + platform_driver_unregister(&s3c2410ts_driver);
569 +
570 + return rc;
571 +}
572 +
573 +static void __exit s3c2410ts_exit(void)
574 +{
575 + platform_driver_unregister(&s3c2440ts_driver);
576 + platform_driver_unregister(&s3c2410ts_driver);
577 +}
578 +
579 +module_init(s3c2410ts_init);
580 +module_exit(s3c2410ts_exit);
581 +
582 +/*
583 + Local variables:
584 + compile-command: "make ARCH=arm CROSS_COMPILE=/usr/local/arm/3.3.2/bin/arm-linux- -k -C ../../.."
585 + c-basic-offset: 8
586 + End:
587 +*/
588 diff --git a/include/asm-arm/arch-s3c2410/ts.h b/include/asm-arm/arch-s3c2410/ts.h
589 new file mode 100644
590 index 0000000..593632a
591 --- /dev/null
592 +++ b/include/asm-arm/arch-s3c2410/ts.h
593 @@ -0,0 +1,28 @@
594 +/* linux/include/asm/arch-s3c2410/ts.h
595 + *
596 + * Copyright (c) 2005 Arnaud Patard <arnaud.patard@rtp-net.org>
597 + *
598 + *
599 + * This program is free software; you can redistribute it and/or modify
600 + * it under the terms of the GNU General Public License version 2 as
601 + * published by the Free Software Foundation.
602 + *
603 + *
604 + * Changelog:
605 + * 24-Mar-2005 RTP Created file
606 + * 03-Aug-2005 RTP Renamed to ts.h
607 + */
608 +
609 +#ifndef __ASM_ARM_TS_H
610 +#define __ASM_ARM_TS_H
611 +
612 +struct s3c2410_ts_mach_info {
613 + int delay;
614 + int presc;
615 + int oversampling_shift;
616 +};
617 +
618 +void set_s3c2410ts_info(struct s3c2410_ts_mach_info *hard_s3c2410ts_info);
619 +
620 +#endif /* __ASM_ARM_TS_H */
621 +
622 diff --git a/include/asm-arm/plat-s3c24xx/devs.h b/include/asm-arm/plat-s3c24xx/devs.h
623 index f9d6f03..43de9cc 100644
624 --- a/include/asm-arm/plat-s3c24xx/devs.h
625 +++ b/include/asm-arm/plat-s3c24xx/devs.h
626 @@ -42,6 +42,7 @@ extern struct platform_device s3c_device_timer2;
627 extern struct platform_device s3c_device_timer3;
628
629 extern struct platform_device s3c_device_usbgadget;
630 +extern struct platform_device s3c_device_ts;
631
632 /* s3c2440 specific devices */
633
634 --
635 1.5.6.3
636