V4L/DVB (10014): gspca - m5602: Remove all sensor specific write functions.
[pandora-kernel.git] / drivers / media / video / gspca / m5602 / m5602_s5k83a.c
1 /*
2  * Driver for the s5k83a sensor
3  *
4  * Copyright (C) 2008 Erik AndrĂ©n
5  * Copyright (C) 2007 Ilyes Gouta. Based on the m5603x Linux Driver Project.
6  * Copyright (C) 2005 m5603x Linux Driver Project <m5602@x3ng.com.br>
7  *
8  * Portions of code to USB interface and ALi driver software,
9  * Copyright (c) 2006 Willem Duinker
10  * v4l2 interface modeled after the V4L2 driver
11  * for SN9C10x PC Camera Controllers
12  *
13  * This program is free software; you can redistribute it and/or
14  * modify it under the terms of the GNU General Public License as
15  * published by the Free Software Foundation, version 2.
16  *
17  */
18
19 #include "m5602_s5k83a.h"
20
21 static void s5k83a_dump_registers(struct sd *sd);
22
23 int s5k83a_probe(struct sd *sd)
24 {
25         u8 prod_id = 0, ver_id = 0;
26         int i, err = 0;
27
28         if (force_sensor) {
29                 if (force_sensor == S5K83A_SENSOR) {
30                         info("Forcing a %s sensor", s5k83a.name);
31                         goto sensor_found;
32                 }
33                 /* If we want to force another sensor, don't try to probe this
34                  * one */
35                 return -ENODEV;
36         }
37
38         info("Probing for a s5k83a sensor");
39
40         /* Preinit the sensor */
41         for (i = 0; i < ARRAY_SIZE(preinit_s5k83a) && !err; i++) {
42                 u8 data[2] = {preinit_s5k83a[i][2], preinit_s5k83a[i][3]};
43                 if (preinit_s5k83a[i][0] == SENSOR)
44                         err = m5602_write_sensor(sd, preinit_s5k83a[i][1],
45                                 data, 2);
46                 else
47                         err = m5602_write_bridge(sd, preinit_s5k83a[i][1],
48                                 data[0]);
49         }
50
51         /* We don't know what register (if any) that contain the product id
52          * Just pick the first addresses that seem to produce the same results
53          * on multiple machines */
54         if (s5k83a_read_sensor(sd, 0x00, &prod_id, 1))
55                 return -ENODEV;
56
57         if (s5k83a_read_sensor(sd, 0x01, &ver_id, 1))
58                 return -ENODEV;
59
60         if ((prod_id == 0xff) || (ver_id == 0xff))
61                 return -ENODEV;
62         else
63                 info("Detected a s5k83a sensor");
64
65 sensor_found:
66         sd->gspca_dev.cam.cam_mode = s5k83a.modes;
67         sd->gspca_dev.cam.nmodes = s5k83a.nmodes;
68         sd->desc->ctrls = s5k83a.ctrls;
69         sd->desc->nctrls = s5k83a.nctrls;
70         return 0;
71 }
72
73 int s5k83a_read_sensor(struct sd *sd, const u8 address,
74                        u8 *i2c_data, const u8 len)
75 {
76         int err, i;
77
78         do {
79                 err = m5602_read_bridge(sd, M5602_XB_I2C_STATUS, i2c_data);
80         } while ((*i2c_data & I2C_BUSY) && !err);
81         if (err < 0)
82                 goto out;
83
84         err = m5602_write_bridge(sd, M5602_XB_I2C_DEV_ADDR,
85                                  sd->sensor->i2c_slave_id);
86         if (err < 0)
87                 goto out;
88
89         err = m5602_write_bridge(sd, M5602_XB_I2C_REG_ADDR, address);
90         if (err < 0)
91                 goto out;
92
93         err = m5602_write_bridge(sd, M5602_XB_I2C_CTRL, 0x18 + len);
94
95         do {
96                 err = m5602_read_bridge(sd, M5602_XB_I2C_STATUS, i2c_data);
97         } while ((*i2c_data & I2C_BUSY) && !err);
98
99         for (i = 0; i < len && !len; i++) {
100                 err = m5602_read_bridge(sd, M5602_XB_I2C_DATA, &(i2c_data[i]));
101
102                 PDEBUG(D_CONF, "Reading sensor register "
103                                   "0x%x containing 0x%x ", address, *i2c_data);
104         }
105
106 out:
107         return err;
108 }
109
110 int s5k83a_init(struct sd *sd)
111 {
112         int i, err = 0;
113
114         for (i = 0; i < ARRAY_SIZE(init_s5k83a) && !err; i++) {
115                 u8 data[2] = {0x00, 0x00};
116
117                 switch (init_s5k83a[i][0]) {
118                 case BRIDGE:
119                         err = m5602_write_bridge(sd,
120                                         init_s5k83a[i][1],
121                                         init_s5k83a[i][2]);
122                         break;
123
124                 case SENSOR:
125                         data[0] = init_s5k83a[i][2];
126                         err = m5602_write_sensor(sd,
127                                 init_s5k83a[i][1], data, 1);
128                         break;
129
130                 case SENSOR_LONG:
131                         data[0] = init_s5k83a[i][2];
132                         data[1] = init_s5k83a[i][3];
133                         err = m5602_write_sensor(sd,
134                                 init_s5k83a[i][1], data, 2);
135                         break;
136                 default:
137                         info("Invalid stream command, exiting init");
138                         return -EINVAL;
139                 }
140         }
141
142         if (dump_sensor)
143                 s5k83a_dump_registers(sd);
144
145         return (err < 0) ? err : 0;
146 }
147
148 int s5k83a_power_down(struct sd *sd)
149 {
150         return 0;
151 }
152
153 void s5k83a_dump_registers(struct sd *sd)
154 {
155         int address;
156         u8 page, old_page;
157         s5k83a_read_sensor(sd, S5K83A_PAGE_MAP, &old_page, 1);
158
159         for (page = 0; page < 16; page++) {
160                 m5602_write_sensor(sd, S5K83A_PAGE_MAP, &page, 1);
161                 info("Dumping the s5k83a register state for page 0x%x", page);
162                 for (address = 0; address <= 0xff; address++) {
163                         u8 val = 0;
164                         s5k83a_read_sensor(sd, address, &val, 1);
165                         info("register 0x%x contains 0x%x",
166                              address, val);
167                 }
168         }
169         info("s5k83a register state dump complete");
170
171         for (page = 0; page < 16; page++) {
172                 m5602_write_sensor(sd, S5K83A_PAGE_MAP, &page, 1);
173                 info("Probing for which registers that are read/write "
174                       "for page 0x%x", page);
175                 for (address = 0; address <= 0xff; address++) {
176                         u8 old_val, ctrl_val, test_val = 0xff;
177
178                         s5k83a_read_sensor(sd, address, &old_val, 1);
179                         m5602_write_sensor(sd, address, &test_val, 1);
180                         s5k83a_read_sensor(sd, address, &ctrl_val, 1);
181
182                         if (ctrl_val == test_val)
183                                 info("register 0x%x is writeable", address);
184                         else
185                                 info("register 0x%x is read only", address);
186
187                         /* Restore original val */
188                         m5602_write_sensor(sd, address, &old_val, 1);
189                 }
190         }
191         info("Read/write register probing complete");
192         m5602_write_sensor(sd, S5K83A_PAGE_MAP, &old_page, 1);
193 }
194
195 int s5k83a_get_brightness(struct gspca_dev *gspca_dev, __s32 *val)
196 {
197         int err;
198         u8 data[2];
199         struct sd *sd = (struct sd *) gspca_dev;
200
201         err = s5k83a_read_sensor(sd, S5K83A_BRIGHTNESS, data, 2);
202         if (err < 0)
203                 goto out;
204
205         data[1] = data[1] << 1;
206         *val = data[1];
207
208 out:
209         return err;
210 }
211
212 int s5k83a_set_brightness(struct gspca_dev *gspca_dev, __s32 val)
213 {
214         int err;
215         u8 data[2];
216         struct sd *sd = (struct sd *) gspca_dev;
217
218         data[0] = 0x00;
219         data[1] = 0x20;
220         err = m5602_write_sensor(sd, 0x14, data, 2);
221         if (err < 0)
222                 goto out;
223
224         data[0] = 0x01;
225         data[1] = 0x00;
226         err = m5602_write_sensor(sd, 0x0d, data, 2);
227         if (err < 0)
228                 goto out;
229
230         /* FIXME: This is not sane, we need to figure out the composition
231                   of these registers */
232         data[0] = val >> 3; /* brightness, high 5 bits */
233         data[1] = val >> 1; /* brightness, high 7 bits */
234         err = m5602_write_sensor(sd, S5K83A_BRIGHTNESS, data, 2);
235
236 out:
237         return err;
238 }
239
240 int s5k83a_get_whiteness(struct gspca_dev *gspca_dev, __s32 *val)
241 {
242         int err;
243         u8 data;
244         struct sd *sd = (struct sd *) gspca_dev;
245
246         err = s5k83a_read_sensor(sd, S5K83A_WHITENESS, &data, 1);
247         if (err < 0)
248                 goto out;
249
250         *val = data;
251
252 out:
253         return err;
254 }
255
256 int s5k83a_set_whiteness(struct gspca_dev *gspca_dev, __s32 val)
257 {
258         int err;
259         u8 data[1];
260         struct sd *sd = (struct sd *) gspca_dev;
261
262         data[0] = val;
263         err = m5602_write_sensor(sd, S5K83A_WHITENESS, data, 1);
264
265         return err;
266 }
267
268 int s5k83a_get_gain(struct gspca_dev *gspca_dev, __s32 *val)
269 {
270         int err;
271         u8 data[2];
272         struct sd *sd = (struct sd *) gspca_dev;
273
274         err = s5k83a_read_sensor(sd, S5K83A_GAIN, data, 2);
275         if (err < 0)
276                 goto out;
277
278         data[1] = data[1] & 0x3f;
279         if (data[1] > S5K83A_MAXIMUM_GAIN)
280                 data[1] = S5K83A_MAXIMUM_GAIN;
281
282         *val = data[1];
283
284 out:
285         return err;
286 }
287
288 int s5k83a_set_gain(struct gspca_dev *gspca_dev, __s32 val)
289 {
290         int err;
291         u8 data[2];
292         struct sd *sd = (struct sd *) gspca_dev;
293
294         data[0] = 0;
295         data[1] = val;
296         err = m5602_write_sensor(sd, S5K83A_GAIN, data, 2);
297         return err;
298 }
299
300 int s5k83a_get_vflip(struct gspca_dev *gspca_dev, __s32 *val)
301 {
302         int err;
303         u8 data[1];
304         struct sd *sd = (struct sd *) gspca_dev;
305
306         data[0] = 0x05;
307         err = m5602_write_sensor(sd, S5K83A_PAGE_MAP, data, 1);
308         if (err < 0)
309                 goto out;
310
311         err = s5k83a_read_sensor(sd, S5K83A_FLIP, data, 1);
312         *val = (data[0] | 0x40) ? 1 : 0;
313
314 out:
315         return err;
316 }
317
318 int s5k83a_set_vflip(struct gspca_dev *gspca_dev, __s32 val)
319 {
320         int err;
321         u8 data[1];
322         struct sd *sd = (struct sd *) gspca_dev;
323
324         data[0] = 0x05;
325         err = m5602_write_sensor(sd, S5K83A_PAGE_MAP, data, 1);
326         if (err < 0)
327                 goto out;
328
329         err = s5k83a_read_sensor(sd, S5K83A_FLIP, data, 1);
330         if (err < 0)
331                 goto out;
332
333         /* set or zero six bit, seven is hflip */
334         data[0] = (val) ? (data[0] & 0x80) | 0x40 | S5K83A_FLIP_MASK
335                         : (data[0] & 0x80) | S5K83A_FLIP_MASK;
336         err = m5602_write_sensor(sd, S5K83A_FLIP, data, 1);
337         if (err < 0)
338                 goto out;
339
340         data[0] = (val) ? 0x0b : 0x0a;
341         err = m5602_write_sensor(sd, S5K83A_VFLIP_TUNE, data, 1);
342
343 out:
344         return err;
345 }
346
347 int s5k83a_get_hflip(struct gspca_dev *gspca_dev, __s32 *val)
348 {
349         int err;
350         u8 data[1];
351         struct sd *sd = (struct sd *) gspca_dev;
352
353         data[0] = 0x05;
354         err = m5602_write_sensor(sd, S5K83A_PAGE_MAP, data, 1);
355         if (err < 0)
356                 goto out;
357
358         err = s5k83a_read_sensor(sd, S5K83A_FLIP, data, 1);
359         *val = (data[0] | 0x80) ? 1 : 0;
360
361 out:
362         return err;
363 }
364
365 int s5k83a_set_hflip(struct gspca_dev *gspca_dev, __s32 val)
366 {
367         int err;
368         u8 data[1];
369         struct sd *sd = (struct sd *) gspca_dev;
370
371         data[0] = 0x05;
372         err = m5602_write_sensor(sd, S5K83A_PAGE_MAP, data, 1);
373         if (err < 0)
374                 goto out;
375
376         err = s5k83a_read_sensor(sd, S5K83A_FLIP, data, 1);
377         if (err < 0)
378                 goto out;
379
380         /* set or zero seven bit, six is vflip */
381         data[0] = (val) ? (data[0] & 0x40) | 0x80 | S5K83A_FLIP_MASK
382                         : (data[0] & 0x40) | S5K83A_FLIP_MASK;
383         err = m5602_write_sensor(sd, S5K83A_FLIP, data, 1);
384         if (err < 0)
385                 goto out;
386
387         data[0] = (val) ? 0x0a : 0x0b;
388         err = m5602_write_sensor(sd, S5K83A_HFLIP_TUNE, data, 1);
389 out:
390         return err;
391 }