]> www.pilppa.org Git - linux-2.6-omap-h63xx.git/blob - drivers/spi/tsc2301-core.c
Merge branch 'omap-fixes'
[linux-2.6-omap-h63xx.git] / drivers / spi / tsc2301-core.c
1 /*
2  * TSC2301 driver
3  *
4  * Copyright (C) 2005, 2006 Nokia Corporation
5  *
6  * This program is free software; you can redistribute it and/or modify
7  * it under the terms of the GNU General Public License as published by
8  * the Free Software Foundation; either version 2 of the License, or
9  * (at your option) any later version.
10  *
11  * This program is distributed in the hope that it will be useful,
12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14  * GNU General Public License for more details.
15  *
16  * You should have received a copy of the GNU General Public License
17  * along with this program; if not, write to the Free Software
18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19  *
20  */
21
22 #include <linux/module.h>
23 #include <linux/device.h>
24 #include <linux/delay.h>
25 #include <linux/gpio.h>
26 #include <linux/spi/spi.h>
27 #include <linux/spi/tsc2301.h>
28
29 u16 tsc2301_read_reg(struct tsc2301 *tsc, int reg)
30 {
31         struct spi_transfer t[2];
32         struct spi_message m;
33         u16 data = 0, cmd;
34
35         cmd = reg;
36         cmd |= 0x8000;
37
38         memset(t, 0, sizeof(t));
39         spi_message_init(&m);
40         m.spi = tsc->spi;
41
42         t[0].tx_buf = &cmd;
43         t[0].rx_buf = NULL;
44         t[0].len = 2;
45         spi_message_add_tail(&t[0], &m);
46
47         t[1].tx_buf = NULL;
48         t[1].rx_buf = &data;
49         t[1].len = 2;
50         spi_message_add_tail(&t[1], &m);
51
52         spi_sync(m.spi, &m);
53
54         return data;
55 }
56
57 void tsc2301_write_reg(struct tsc2301 *tsc, int reg, u16 val)
58 {
59         struct spi_transfer t;
60         struct spi_message m;
61         u16 data[2];
62
63         /* Now we prepare the command for transferring */
64         data[0] = reg;
65         data[1] = val;
66
67         spi_message_init(&m);
68         m.spi = tsc->spi;
69
70         memset(&t, 0, sizeof(t));
71         t.tx_buf = data;
72         t.rx_buf = NULL;
73         t.len = 4;
74         spi_message_add_tail(&t, &m);
75
76         spi_sync(m.spi, &m);
77 }
78
79 void tsc2301_write_kbc(struct tsc2301 *tsc, int val)
80 {
81         u16 w;
82
83         w = tsc->config2_shadow;
84         w &= ~(0x03 << 14);
85         w |= (val & 0x03) << 14;
86         tsc2301_write_reg(tsc, TSC2301_REG_CONFIG2, w);
87         tsc->config2_shadow = w;
88 }
89
90 void tsc2301_write_pll(struct tsc2301 *tsc,
91                        int pll_n, int pll_a, int pll_pdc, int pct_e, int pll_o)
92 {
93         u16 w;
94
95         w = tsc->config2_shadow;
96         w &= ~0x3fff;
97         w |= (pll_n & 0x0f) | ((pll_a & 0x0f) << 4) | ((pll_pdc & 0x0f) << 8);
98         w |= pct_e ? (1 << 12) : 0;
99         w |= pll_o ? (1 << 13) : 0;
100         tsc2301_write_reg(tsc, TSC2301_REG_CONFIG2, w);
101         tsc->config2_shadow = w;
102 }
103
104 void tsc2301_read_buf(struct tsc2301 *tsc, int reg, u16 *rx_buf, int len)
105 {
106         struct spi_transfer t[2];
107         struct spi_message m;
108         u16 cmd, i;
109
110         cmd = reg;
111         cmd |= 0x8000;
112
113         spi_message_init(&m);
114         m.spi = tsc->spi;
115
116         memset(t, 0, sizeof(t));
117         t[0].tx_buf = &cmd;
118         t[0].rx_buf = NULL;
119         t[0].len = 2;
120         spi_message_add_tail(&t[0], &m);
121
122         t[1].tx_buf = NULL;
123         t[1].rx_buf = rx_buf;
124         t[1].len = 2 * len;
125         spi_message_add_tail(&t[1], &m);
126
127         spi_sync(m.spi, &m);
128
129         for (i = 0; i < len; i++)
130                 printk(KERN_DEBUG "rx_buf[%d]: %04x\n", i, rx_buf[i]);
131 }
132
133 static int __devinit tsc2301_probe(struct spi_device *spi)
134 {
135         struct tsc2301                  *tsc;
136         struct tsc2301_platform_data    *pdata = spi->dev.platform_data;
137         int r;
138         u16 w;
139
140         if (!pdata) {
141                 dev_dbg(&spi->dev, "no platform data?\n");
142                 return -ENODEV;
143         }
144
145         tsc = kzalloc(sizeof(*tsc), GFP_KERNEL);
146         if (tsc == NULL)
147                 return -ENOMEM;
148
149         dev_set_drvdata(&spi->dev, tsc);
150         tsc->spi = spi;
151
152         tsc->enable_clock = pdata->enable_clock;
153         tsc->disable_clock = pdata->disable_clock;
154
155         if (pdata->reset_gpio >= 0) {
156                 tsc->reset_gpio = pdata->reset_gpio;
157                 r = gpio_request(tsc->reset_gpio, "TSC2301 reset");
158                 if (r < 0)
159                         goto err1;
160                 gpio_direction_output(tsc->reset_gpio, 1);
161                 mdelay(1);
162                 gpio_set_value(tsc->reset_gpio, 0);
163         } else
164                 tsc->reset_gpio = -1;
165
166         spi->mode = SPI_MODE_1;
167         spi->bits_per_word = 16;
168         /* The max speed might've been defined by the board-specific
169          * struct */
170         if (!spi->max_speed_hz)
171                 spi->max_speed_hz = TSC2301_HZ;
172         spi_setup(spi);
173
174         /* Soft reset */
175         tsc2301_write_reg(tsc, TSC2301_REG_RESET, 0xbb00);
176         msleep(1);
177
178         w = tsc2301_read_reg(tsc, TSC2301_REG_ADC);
179         if (!(w & (1 << 14))) {
180                 dev_err(&spi->dev, "invalid ADC reg value: %04x\n", w);
181                 r = -ENODEV;
182                 goto err1;
183         }
184
185         w = tsc2301_read_reg(tsc, TSC2301_REG_DAC);
186         if (!(w & (1 << 15))) {
187                 dev_err(&spi->dev, "invalid DAC reg value: %04x\n", w);
188                 r = -ENODEV;
189                 goto err1;
190         }
191
192         /* Stop keypad scanning */
193         tsc2301_write_reg(tsc, TSC2301_REG_KEY, 0x4000);
194
195         /* We have to cache this for read-modify-write, since we can't
196          * read back BIT15 */
197         w = tsc2301_read_reg(tsc, TSC2301_REG_CONFIG2);
198         /* By default BIT15 is set */
199         w |= 1 << 15;
200         tsc->config2_shadow = w;
201
202         r = tsc2301_kp_init(tsc, pdata);
203         if (r)
204                 goto err1;
205         r = tsc2301_ts_init(tsc, pdata);
206         if (r)
207                 goto err2;
208         return 0;
209
210         tsc2301_ts_exit(tsc);
211 err2:
212         tsc2301_kp_exit(tsc);
213 err1:
214         kfree(tsc);
215         return r;
216 }
217
218 static int __devexit tsc2301_remove(struct spi_device *spi)
219 {
220         struct tsc2301 *tsc = dev_get_drvdata(&spi->dev);
221
222         tsc2301_ts_exit(tsc);
223         tsc2301_kp_exit(tsc);
224         if (tsc->reset_gpio >= 0)
225                 gpio_free(tsc->reset_gpio);
226         kfree(tsc);
227
228         return 0;
229 }
230
231 #ifdef CONFIG_PM
232 static int tsc2301_suspend(struct spi_device *spi, pm_message_t mesg)
233 {
234         struct tsc2301 *tsc = dev_get_drvdata(&spi->dev);
235         int r;
236
237         if ((r = tsc2301_kp_suspend(tsc)) < 0)
238                 return r;
239         if ((r = tsc2301_ts_suspend(tsc)) < 0) {
240                 tsc2301_kp_resume(tsc);
241                 return r;
242         }
243
244         return 0;
245 }
246
247 static int tsc2301_resume(struct spi_device *spi)
248 {
249         struct tsc2301 *tsc = dev_get_drvdata(&spi->dev);
250
251         tsc2301_ts_resume(tsc);
252         tsc2301_kp_resume(tsc);
253
254         return 0;
255 }
256 #endif
257
258 static struct spi_driver tsc2301_driver = {
259         .driver = {
260                    .name = "tsc2301",
261                    .bus = &spi_bus_type,
262                    .owner = THIS_MODULE,
263         },
264 #ifdef CONFIG_PM
265         .suspend = tsc2301_suspend,
266         .resume = tsc2301_resume,
267 #endif
268         .probe = tsc2301_probe,
269         .remove = __devexit_p(tsc2301_remove),
270 };
271
272 static int __init tsc2301_init(void)
273 {
274         printk("TSC2301 driver initializing\n");
275
276         return spi_register_driver(&tsc2301_driver);
277 }
278 module_init(tsc2301_init);
279
280 static void __exit tsc2301_exit(void)
281 {
282         spi_unregister_driver(&tsc2301_driver);
283 }
284 module_exit(tsc2301_exit);
285
286 MODULE_AUTHOR("Juha Yrjölä <juha.yrjola@nokia.com>");
287 MODULE_LICENSE("GPL");