1 /*
2 * A V4L2 driver for s5k4e6yx Raw cameras.
3 *
4 * Copyright (c) 2017 by Allwinnertech Co., Ltd. http://www.allwinnertech.com
5 *
6 * Authors: Zhao Wei <zhaowei@allwinnertech.com>
7 * Liang WeiJie <liangweijie@allwinnertech.com>
8 *
9 * This program is free software; you can redistribute it and/or modify
10 * it under the terms of the GNU General Public License version 2 as
11 * published by the Free Software Foundation.
12 */
13
14 #include <linux/init.h>
15 #include <linux/module.h>
16 #include <linux/slab.h>
17 #include <linux/i2c.h>
18 #include <linux/delay.h>
19 #include <linux/videodev2.h>
20 #include <linux/clk.h>
21 #include <media/v4l2-device.h>
22 #include <media/v4l2-mediabus.h>
23 #include <linux/io.h>
24
25 #include "camera.h"
26 #include "sensor_helper.h"
27
28 MODULE_AUTHOR("myf");
29 MODULE_DESCRIPTION("A low-level driver for s5k4e6yx sensors");
30 MODULE_LICENSE("GPL");
31
32 #define MCLK (24*1000*1000)
33 #define V4L2_IDENT_SENSOR 0x4e60
34
35 /*
36 * Our nominal (default) frame rate.
37 */
38
39 #define SENSOR_FRAME_RATE 30
40
41 /*
42 * The s5k3h5xa i2c address
43 */
44 #define I2C_ADDR 0x6A //s5k4e6_lib.h--231h
45
46 #define SENSOR_NUM 0x2 //
47 #define SENSOR_NAME "s5k4e6yx" //
48 #define SENSOR_NAME_2 "s5k4e6yx_2" //
49
50
51
52 /*default_regs: 2608 x 1960 30fps*/
53 static struct regval_list sensor_default_regs[] = {
54
55
56
57 };
58
59
60 /*default_regs: 2608 x 1960 30fps*/
61 static struct regval_list sensor_2608_1960_30fps_30fps_regs[] = {
62
63 {0xFCFC, 0x4000},
64 {0x6010, 0x0001},
65
66 {0xffff, 0x0100}, //REG_DLY
67
68 {0x535B, 0x00},
69 {0x5402, 0x15},
70 {0x5401, 0x1D},
71 {0x6102, 0xC000},
72 {0x614C, 0x25AA},
73 {0x614E, 0x25B8},
74 {0x618C, 0x08D4},
75 {0x618E, 0x08D6},
76 {0x6028, 0x2000},
77 {0x602A, 0x11A8},
78 {0x6F12, 0x3AF9},
79 {0x6F12, 0x1410},
80 {0x6F12, 0x39F9},
81 {0x6F12, 0x1410},
82 {0x6028, 0x2000},
83 {0x602A, 0x0668},
84 {0x6F12, 0x4010},
85 {0x602A, 0x12BC},
86 {0x6F12, 0x1020},
87 {0x602A, 0x12C2},
88 {0x6F12, 0x1020},
89 {0x6F12, 0x1020},
90 {0x602A, 0x12CA},
91 {0x6F12, 0x1020},
92 {0x6F12, 0x1010},
93 {0x602A, 0x12FC},
94 {0x6F12, 0x1020},
95 {0x602A, 0x1302},
96 {0x6F12, 0x1020},
97 {0x6F12, 0x1020},
98 {0x602A, 0x130A},
99 {0x6F12, 0x1020},
100 {0x6F12, 0x1010},
101 {0x602A, 0x14B8},
102 {0x6F12, 0x0001},
103 {0x602A, 0x14B9},
104 {0x6F12, 0x0001},
105 {0x602A, 0x14C0},
106 {0x6F12, 0x0000},
107 {0x6F12, 0xFFDA},
108 {0x6F12, 0xFFDA},
109 {0x6F12, 0x0000},
110 {0x6F12, 0x0000},
111 {0x6F12, 0xFFDA},
112 {0x6F12, 0xFFDA},
113 {0x6F12, 0x0000},
114 {0x602A, 0x1488},
115 {0x6F12, 0xFF80},
116 {0x6F12, 0xFF80},
117 {0x6F12, 0xFF80},
118 {0x6F12, 0xFF80},
119 {0x602A, 0x1496},
120 {0x6F12, 0xFF80},
121 {0x6F12, 0xFF80},
122 {0x6F12, 0xFF80},
123 {0x6F12, 0xFF80},
124 {0x602A, 0x14A4},
125 {0x6F12, 0xFFC0},
126 {0x6F12, 0xFFC0},
127 {0x6F12, 0xFFC0},
128 {0x6F12, 0xFFC0},
129 {0x602A, 0x147A},
130 {0x6F12, 0x0000},
131 {0x6F12, 0x0002},
132 {0x6F12, 0xFFFC},
133 {0x602A, 0x0512},
134 {0x6F12, 0x0111},
135 {0x602A, 0x14AC},
136 {0x6F12, 0x0000},
137 {0x602A, 0x0524},
138 {0x6F12, 0x0000},
139 {0x3285, 0x00},
140 {0x327A, 0x0001},
141 {0x3283, 0x0A},
142 {0x3297, 0x18},
143 {0x32E1, 0x00},
144 {0x3286, 0x9000},
145 {0x3298, 0x40},
146 {0x32AA, 0x00},
147 {0x327C, 0x0400},
148 {0x328A, 0x0800},
149 {0x3284, 0x37},
150 {0x32A1, 0x20},
151 {0x32A2, 0x10},
152 {0x32A4, 0x0C},
153 {0x3204, 0x000C},
154 {0x3206, 0x000B},
155 {0x3208, 0x0009},
156 {0x3210, 0x0007},
157 {0x3212, 0x0007},
158 {0x0200, 0x0408},
159 {0x3219, 0x1C},
160 {0x321A, 0x32},
161 {0x321B, 0x24},
162 {0x321C, 0x07},
163 {0x321E, 0x08},
164 {0x3220, 0x13},
165 {0x3226, 0x52},
166 {0x3227, 0x5C},
167 {0x3228, 0x03},
168 {0x0305, 0x06}, //pre_pll_clk_div
169 {0x0307, 0x64}, //PLL multiplier Value
170 {0x5363, 0x00},
171 {0x5364, 0x42},
172 {0x5365, 0xA0},
173 {0x534E, 0x49},
174 {0x534F, 0x10},
175 {0x0340, 0x07F8}, //frame length lines =2040=0x07f8
176 {0x0342, 0x0B68}, //line length pck =2920=0x0b68
177 {0x021E, 0x03FC}, //coarse_integration_time_long 0x03fc=1020
178 {0x0344, 0x0000}, //x_addr_start =0
179 {0x0346, 0x0000}, //y_addr_start =0
180 {0x0348, 0x0A2F}, //x_addr_end =0x0a2f=2607
181 {0x034A, 0x07A7}, //y_addr_end =0x07a7=1959
182 {0x034C, 0x0A30}, //x_output_size= 2608 =0x0a30
183 {0x034E, 0x07A8}, //y_output_szie= 1960 =0x07a8
184 {0x3500, 0x00},
185 {0x3089, 0x00},
186 {0x0216, 0x01},
187 {0x5333, 0xE0},
188 {0x5080, 0x01},
189 {0x0100, 0x01},
190
191 };
192
193
194
195 /*read the value of the register*/
sensor_read_byte(struct v4l2_subdev * sd,unsigned short reg,unsigned char * value)196 static int sensor_read_byte(struct v4l2_subdev *sd, unsigned short reg,
197 unsigned char *value)
198 {
199 int ret = 0, cnt = 0;
200
201 if (!sd || !sd->entity.use_count) {
202 sensor_print("%s error! sensor is not used!\n", __func__);
203 return -1;
204 }
205
206 ret = cci_read_a16_d8(sd, reg, value);
207 while ((ret != 0) && (cnt < 2)) {
208 ret = cci_read_a16_d8(sd, reg, value);
209 cnt++;
210 }
211 if (cnt > 0)
212 pr_info("%s sensor read retry = %d\n", sd->name, cnt);
213
214 return ret;
215 }
216
sensor_write_byte(struct v4l2_subdev * sd,unsigned short reg,unsigned char value)217 static int sensor_write_byte(struct v4l2_subdev *sd, unsigned short reg,
218 unsigned char value)
219 {
220 int ret = 0, cnt = 0;
221
222 if (!sd || !sd->entity.use_count) {
223 sensor_print("%s error! sensor is not used!\n", __func__);
224 return -1;
225 }
226
227 ret = cci_write_a16_d8(sd, reg, value);
228 while ((ret != 0) && (cnt < 2)) {
229 ret = cci_write_a16_d8(sd, reg, value);
230 cnt++;
231 }
232 if (cnt > 0)
233 pr_info("%s sensor write retry = %d\n", sd->name, cnt);
234
235 return ret;
236 }
237
238
s5k4e6yx_write_array(struct v4l2_subdev * sd,struct regval_list * regs,int array_size)239 static int s5k4e6yx_write_array(struct v4l2_subdev *sd,
240 struct regval_list *regs, int array_size)
241 {
242 int i = 0, ret = 0;
243
244 if (!regs)
245 return -EINVAL;
246
247 while (i < array_size) {
248 if (regs->addr == REG_DLY) {
249 usleep_range(regs->data * 1000,
250 regs->data * 1000 + 100);
251 } else {
252 data_type testvalue; //for test
253
254 if (regs->addr == 0x535B || regs->addr == 0x5402
255 || regs->addr == 0x5401 || regs->addr == 0x3285
256 || regs->addr == 0x3283 || regs->addr == 0x3297
257 || regs->addr == 0x32E1 || regs->addr == 0x3298
258 || regs->addr == 0x32AA || regs->addr == 0x3284
259 || regs->addr == 0x32A1 || regs->addr == 0x32A2
260 || regs->addr == 0x32A4 || regs->addr == 0x3219
261 || regs->addr == 0x321A || regs->addr == 0x321B
262 || regs->addr == 0x321C || regs->addr == 0x321E
263 || regs->addr == 0x3220 || regs->addr == 0x3226
264 || regs->addr == 0x3227 || regs->addr == 0x3228
265 || regs->addr == 0x0305 || regs->addr == 0x0307
266 || regs->addr == 0x5363 || regs->addr == 0x5364
267 || regs->addr == 0x5365 || regs->addr == 0x534E
268 || regs->addr == 0x534F || regs->addr == 0x3500
269 || regs->addr == 0x3089 || regs->addr == 0x0216
270 || regs->addr == 0x5333 || regs->addr == 0x5080
271 || regs->addr == 0x0100
272 /*
273 * regs->addr == 0x32BC ||
274 * regs->addr == 0x32BD ||
275 * regs->addr == 0x32BE ||
276 * regs->addr == 0x012C ||
277 * regs->addr == 0x012D ||
278 * regs->addr == 0x012E ||
279 * regs->addr == 0x012F ||
280 * regs->addr == 0x6F12
281 */
282 ) {
283 ret = sensor_write_byte(sd,
284 regs->addr, regs->data);
285
286 usleep_range(10000, 12000);
287 sensor_read(sd, regs->addr, &testvalue);
288 sensor_dbg("[0x%.2x] = 0x%.2x, read = 0x%.2x\n",
289 regs->addr, regs->data, testvalue);
290 } else {
291 ret = sensor_write(sd, regs->addr, regs->data);
292
293 usleep_range(10000, 12000);
294 sensor_read(sd, regs->addr, &testvalue);
295 sensor_dbg("[0x%.2x] = 0x%.2x, read = 0x%.2x\n", regs->addr, regs->data, testvalue);
296
297 }
298 if (ret < 0) {
299 sensor_print("%s sensor write array error,array_size %d!\n", sd->name, array_size);
300 return -1;
301 }
302 }
303 i++;
304 regs++;
305 }
306 return 0;
307 }
308
309
310 static struct regval_list sensor_fmt_raw[] = {
311
312 };
313
314 /*
315 * Code for dealing with controls.
316 * fill with different sensor module
317 * different sensor module has different settings here
318 * if not support the follow function ,retrun -EINVAL
319 */
sensor_g_exp(struct v4l2_subdev * sd,__s32 * value)320 static int sensor_g_exp(struct v4l2_subdev *sd, __s32 *value)
321 {
322 struct sensor_info *info = to_state(sd);
323 *value = info->exp;
324 sensor_dbg("sensor_get_exposure = %d\n", info->exp);
325 return 0;
326 }
327
328 static int s5k4e6yx_sensor_vts;
329 static int s5k4e6yx_sensor_hts;
330
sensor_s_exp(struct v4l2_subdev * sd,unsigned int exp_val)331 static int sensor_s_exp(struct v4l2_subdev *sd, unsigned int exp_val)
332 {
333 unsigned int exp_coarse;
334 unsigned short exp_fine;
335 struct sensor_info *info = to_state(sd);
336
337 if (exp_val > 0xffffff)
338 exp_val = 0xfffff0;
339 if (exp_val < 16)
340 exp_val = 16;
341
342 if (info->exp == exp_val)
343 return 0;
344
345 exp_coarse = exp_val >> 4;
346
347 exp_fine = (unsigned short) (((exp_val - exp_coarse * 16) *
348 s5k4e6yx_sensor_hts) / 16);
349
350 sensor_write(sd, 0x0200, exp_fine);
351
352 sensor_write(sd, 0x0202, (unsigned short)exp_coarse);
353 info->exp = exp_val;
354 return 0;
355 }
356
357
sensor_g_gain(struct v4l2_subdev * sd,__s32 * value)358 static int sensor_g_gain(struct v4l2_subdev *sd, __s32 *value)
359 {
360 struct sensor_info *info = to_state(sd);
361 *value = info->gain;
362 sensor_dbg("sensor_get_gain = %d\n", info->gain);
363 return 0;
364 }
365
sensor_s_gain(struct v4l2_subdev * sd,int gain_val)366 static int sensor_s_gain(struct v4l2_subdev *sd, int gain_val)
367 {
368 struct sensor_info *info = to_state(sd);
369
370 data_type ana_gain_min, ana_gain_max;
371
372 ana_gain_min = 0x0020;
373 ana_gain_max = 0x0200;
374
375 int ana_gain = 0;
376
377 if (info->gain == gain_val)
378 return 0;
379
380 if (gain_val <= ana_gain_min)
381 ana_gain = ana_gain_min;
382 else if (gain_val > ana_gain_min && gain_val <= (ana_gain_max))
383 ana_gain = gain_val;
384 else
385 ana_gain = ana_gain_max;
386
387
388 ana_gain *= 2;
389
390 sensor_write(sd, 0x0204, (unsigned short)ana_gain);
391 info->gain = gain_val;
392
393 return 0;
394 }
395
396
sensor_s_exp_gain(struct v4l2_subdev * sd,struct sensor_exp_gain * exp_gain)397 static int sensor_s_exp_gain(struct v4l2_subdev *sd,
398 struct sensor_exp_gain *exp_gain)
399 {
400 int exp_val, gain_val, shutter, frame_length;
401 struct sensor_info *info = to_state(sd);
402
403 exp_val = exp_gain->exp_val;
404 gain_val = exp_gain->gain_val;
405
406 shutter = exp_val >> 4;
407
408 if (shutter > s5k4e6yx_sensor_vts - 4)
409 frame_length = shutter + 4;
410 else
411 frame_length = s5k4e6yx_sensor_vts;
412
413 sensor_write_byte(sd, 0x0104, 0x01);
414 sensor_write(sd, 0x0340, frame_length);
415 sensor_s_gain(sd, gain_val);
416 sensor_s_exp(sd, exp_val);
417 sensor_write_byte(sd, 0x0104, 0x00);
418
419 info->exp = exp_val;
420 info->gain = gain_val;
421 return 0;
422 }
423
sensor_s_sw_stby(struct v4l2_subdev * sd,int on_off)424 static int sensor_s_sw_stby(struct v4l2_subdev *sd, int on_off)
425 {
426 int ret;
427 unsigned char rdval;
428
429 ret = sensor_read_byte(sd, 0x0100, &rdval);
430 if (ret != 0)
431 return ret;
432
433 if (on_off == STBY_ON)
434 ret = sensor_write_byte(sd, 0x0100, rdval & 0xfe);
435 else
436 ret = sensor_write_byte(sd, 0x0100, rdval | 0x01);
437 return ret;
438 }
439
440 /*
441 * Stuff that knows about the sensor.
442 */
sensor_power(struct v4l2_subdev * sd,int on)443 static int sensor_power(struct v4l2_subdev *sd, int on)
444 {
445 int ret = 0;
446
447 switch (on) {
448 case STBY_ON:
449 sensor_dbg("STBY_ON!\n");
450 cci_lock(sd);
451 ret = sensor_s_sw_stby(sd, STBY_ON);
452 if (ret < 0)
453 sensor_dbg("soft stby falied!\n");
454 usleep_range(10000, 12000);
455 cci_unlock(sd);
456 break;
457 case STBY_OFF:
458 sensor_dbg("STBY_OFF!\n");
459 cci_lock(sd);
460 usleep_range(10000, 12000);
461 ret = sensor_s_sw_stby(sd, STBY_OFF);
462 if (ret < 0)
463 sensor_dbg("soft stby off falied!\n");
464 cci_unlock(sd);
465 break;
466 case PWR_ON:
467 sensor_dbg("PWR_ON!\n");
468 cci_lock(sd);
469 vin_gpio_set_status(sd, PWDN, 1);
470 /* RESET port set to output mode and pull-up */
471 vin_gpio_set_status(sd, RESET, 1);
472 vin_gpio_set_status(sd, POWER_EN, 1);
473 vin_gpio_write(sd, RESET, CSI_GPIO_LOW);
474 vin_gpio_write(sd, PWDN, CSI_GPIO_LOW);
475 vin_gpio_write(sd, POWER_EN, CSI_GPIO_HIGH);
476 usleep_range(1000, 1200);
477 vin_set_pmu_channel(sd, IOVDD, ON);
478 usleep_range(1000, 1200);
479 vin_set_pmu_channel(sd, AVDD, ON);
480 vin_set_pmu_channel(sd, DVDD, ON);
481 usleep_range(10000, 12000);
482 vin_gpio_write(sd, RESET, CSI_GPIO_HIGH);
483 vin_gpio_write(sd, PWDN, CSI_GPIO_HIGH);
484 usleep_range(10000, 12000);
485 vin_set_mclk(sd, ON);
486 usleep_range(10000, 12000);
487 vin_set_mclk_freq(sd, MCLK);
488 usleep_range(30000, 32000);
489 cci_unlock(sd);
490 break;
491 case PWR_OFF:
492 sensor_dbg("PWR_OFF!\n");
493 cci_lock(sd);
494 vin_gpio_set_status(sd, PWDN, 1);
495 vin_gpio_set_status(sd, RESET, 1);
496 vin_gpio_write(sd, RESET, CSI_GPIO_LOW);
497 vin_gpio_write(sd, PWDN, CSI_GPIO_LOW);
498 vin_set_mclk(sd, OFF);
499 vin_set_pmu_channel(sd, AFVDD, OFF);
500 vin_set_pmu_channel(sd, AVDD, OFF);
501 vin_set_pmu_channel(sd, IOVDD, OFF);
502 vin_set_pmu_channel(sd, DVDD, OFF);
503 vin_gpio_write(sd, POWER_EN, CSI_GPIO_LOW);
504 vin_gpio_set_status(sd, RESET, 0);
505 vin_gpio_set_status(sd, PWDN, 0);
506 vin_gpio_set_status(sd, POWER_EN, 0);
507 cci_unlock(sd);
508 break;
509 default:
510 return -EINVAL;
511 }
512
513 return 0;
514 }
515
sensor_reset(struct v4l2_subdev * sd,u32 val)516 static int sensor_reset(struct v4l2_subdev *sd, u32 val)
517 {
518 switch (val) {
519 case 0:
520 vin_gpio_write(sd, RESET, CSI_GPIO_HIGH);
521 usleep_range(100, 120);
522 break;
523 case 1:
524 vin_gpio_write(sd, RESET, CSI_GPIO_LOW);
525 usleep_range(100, 120);
526 break;
527 default:
528 return -EINVAL;
529 }
530 return 0;
531 }
532
sensor_detect(struct v4l2_subdev * sd)533 static int sensor_detect(struct v4l2_subdev *sd)
534 {
535 unsigned short rdval = 0;
536
537 sensor_read(sd, 0x0000, &rdval);
538 if (rdval != 0x4E60) {
539 /*sensor ID*/
540 sensor_dbg("s5k4e6y read 0x0000: 0x%04x != 0x4E60\n", rdval);
541 return -ENODEV;
542 }
543 sensor_dbg("s5k4e6y sensor detect success ID = 0x%04x\n", rdval);
544 return 0;
545 }
546
sensor_init(struct v4l2_subdev * sd,u32 val)547 static int sensor_init(struct v4l2_subdev *sd, u32 val)
548 {
549 int ret;
550 struct sensor_info *info = to_state(sd);
551
552 sensor_dbg("sensor_init\n");
553
554 /*Make sure it is a target sensor */
555 ret = sensor_detect(sd);
556 if (ret) {
557 sensor_dbg("chip found is not an target chip.\n");
558 return ret;
559 }
560
561 info->focus_status = 0;
562 info->low_speed = 0;
563 info->width = 2608;
564 info->height = 1960;
565 info->hflip = 0;
566 info->vflip = 0;
567 info->gain = 0;
568 info->exp = 0;
569
570 info->tpf.numerator = 1;
571 info->tpf.denominator = 30; /* 30fps */
572
573 return 0;
574 }
575
sensor_ioctl(struct v4l2_subdev * sd,unsigned int cmd,void * arg)576 static long sensor_ioctl(struct v4l2_subdev *sd, unsigned int cmd, void *arg)
577 {
578 int ret = 0;
579 struct sensor_info *info = to_state(sd);
580
581 switch (cmd) {
582 case GET_CURRENT_WIN_CFG:
583 if (info->current_wins != NULL) {
584 memcpy(arg, info->current_wins,
585 sizeof(struct sensor_win_size));
586 ret = 0;
587 } else {
588 sensor_dbg("empty wins!\n");
589 ret = -1;
590 }
591 break;
592 case SET_FPS:
593 ret = 0;
594 break;
595 case VIDIOC_VIN_SENSOR_EXP_GAIN:
596 ret = sensor_s_exp_gain(sd, (struct sensor_exp_gain *)arg);
597 break;
598 case VIDIOC_VIN_SENSOR_SET_FPS:
599 ret = 0;
600 break;
601 case VIDIOC_VIN_SENSOR_CFG_REQ:
602 sensor_cfg_req(sd, (struct sensor_config *)arg);
603 break;
604 default:
605 return -EINVAL;
606 }
607 return ret;
608 }
609
610 /*
611 * Store information about the video data format.
612 */
613 static struct sensor_format_struct sensor_formats[] = {
614 {
615 .desc = "Raw RGB Bayer",
616 .mbus_code = MEDIA_BUS_FMT_SGRBG10_1X10,
617 .regs = sensor_fmt_raw,
618 .regs_size = ARRAY_SIZE(sensor_fmt_raw),
619 .bpp = 1
620 },
621 };
622 #define N_FMTS ARRAY_SIZE(sensor_formats)
623
624 /*
625 * Then there is the issue of window sizes. Try to capture the info here.
626 */
627
628 static struct sensor_win_size sensor_win_sizes[] = {
629
630 {
631 .width = 2608, ////
632 .height = 1960, ////
633 .hoffset = 0,
634 .voffset = 0,
635 .hts = 2040, ////2040*2920*30=178 704 00
636 .vts = 2920, ////
637 .pclk = 180*1000*1000, ////
638 .mipi_bps = 1008*1000*1000, ////
639 .fps_fixed = 30,
640 .bin_factor = 1,
641 .intg_min = 16,
642 .intg_max = (2920-4)<<4, ////
643 .gain_min = 16,
644 .gain_max = (32<<4),
645 .regs = sensor_2608_1960_30fps_30fps_regs,
646 .regs_size = ARRAY_SIZE(sensor_2608_1960_30fps_30fps_regs),
647 .set_size = NULL,
648 },
649
650 };
651
652 #define N_WIN_SIZES (ARRAY_SIZE(sensor_win_sizes))
653
sensor_g_mbus_config(struct v4l2_subdev * sd,struct v4l2_mbus_config * cfg)654 static int sensor_g_mbus_config(struct v4l2_subdev *sd,
655 struct v4l2_mbus_config *cfg)
656 {
657 cfg->type = V4L2_MBUS_CSI2_DPHY;
658
659 cfg->flags = 0 | V4L2_MBUS_CSI2_2_LANE | V4L2_MBUS_CSI2_CHANNEL_0;
660
661 return 0;
662 }
663
664
665
sensor_g_ctrl(struct v4l2_ctrl * ctrl)666 static int sensor_g_ctrl(struct v4l2_ctrl *ctrl)
667 {
668
669 struct sensor_info *info =
670 container_of(ctrl->handler,
671 struct sensor_info, handler);
672
673 struct v4l2_subdev *sd = &info->sd;
674
675 switch (ctrl->id) {
676 case V4L2_CID_GAIN:
677 return sensor_g_gain(sd, &ctrl->val);
678 case V4L2_CID_EXPOSURE:
679 return sensor_g_exp(sd, &ctrl->val);
680 }
681 return -EINVAL;
682 }
683
sensor_s_ctrl(struct v4l2_ctrl * ctrl)684 static int sensor_s_ctrl(struct v4l2_ctrl *ctrl)
685 {
686 struct sensor_info *info =
687 container_of(ctrl->handler,
688 struct sensor_info, handler);
689
690 struct v4l2_subdev *sd = &info->sd;
691
692 switch (ctrl->id) {
693 case V4L2_CID_GAIN:
694 return sensor_s_gain(sd, ctrl->val);
695 case V4L2_CID_EXPOSURE:
696 return sensor_s_exp(sd, ctrl->val);
697 }
698 return -EINVAL;
699 }
700
701
702
sensor_reg_init(struct sensor_info * info)703 static int sensor_reg_init(struct sensor_info *info)
704 {
705 int ret;
706 struct v4l2_subdev *sd = &info->sd;
707 struct sensor_format_struct *sensor_fmt = info->fmt;
708 struct sensor_win_size *wsize = info->current_wins;
709
710 ret = s5k4e6yx_write_array(sd, sensor_default_regs,
711 ARRAY_SIZE(sensor_default_regs));
712 if (ret < 0) {
713 sensor_dbg("write sensor_default_regs error\n");
714 return ret;
715 }
716
717 sensor_dbg("sensor_reg_init\n");
718
719 s5k4e6yx_write_array(sd, sensor_fmt->regs, sensor_fmt->regs_size);
720
721 if (wsize->regs) {
722 s5k4e6yx_write_array(sd, wsize->regs, wsize->regs_size);
723 sensor_dbg("sensor_reg_init: wsize->regs\n");
724 }
725 if (wsize->set_size) {
726 sensor_dbg("sensor_reg_init: wsize->set_size\n");
727 wsize->set_size(sd);
728 }
729 info->width = wsize->width;
730 info->height = wsize->height;
731 s5k4e6yx_sensor_vts = wsize->vts;
732 s5k4e6yx_sensor_hts = wsize->hts;
733 sensor_dbg("sensor_reg_init: end\n");
734
735 return 0;
736 }
737
sensor_s_stream(struct v4l2_subdev * sd,int enable)738 static int sensor_s_stream(struct v4l2_subdev *sd, int enable)
739 {
740
741 struct sensor_info *info = to_state(sd);
742
743 sensor_dbg("%s on = %d, %d*%d fps: %d code: %x\n", __func__, enable,
744 info->current_wins->width, info->current_wins->height,
745 info->current_wins->fps_fixed, info->fmt->mbus_code);
746
747 if (!enable)
748 return 0;
749
750 return sensor_reg_init(info);
751 }
752
753
754
755 /* ----------------------------------------------------------------------- */
756
757 static const struct v4l2_ctrl_ops sensor_ctrl_ops = {
758 .g_volatile_ctrl = sensor_g_ctrl,
759 .s_ctrl = sensor_s_ctrl,
760 };
761
762 static const struct v4l2_subdev_core_ops sensor_core_ops = {
763 .reset = sensor_reset,
764 .init = sensor_init,
765 .s_power = sensor_power,
766 .ioctl = sensor_ioctl,
767 #ifdef CONFIG_COMPAT
768 .compat_ioctl32 = sensor_compat_ioctl32,
769 #endif
770 };
771
772 static const struct v4l2_subdev_video_ops sensor_video_ops = {
773 .s_stream = sensor_s_stream,
774 .g_mbus_config = sensor_g_mbus_config,
775 };
776
777 static const struct v4l2_subdev_pad_ops sensor_pad_ops = {
778 .enum_mbus_code = sensor_enum_mbus_code,
779 .enum_frame_size = sensor_enum_frame_size,
780 .get_fmt = sensor_get_fmt,
781 .set_fmt = sensor_set_fmt,
782 };
783
784 static const struct v4l2_subdev_ops sensor_ops = {
785 .core = &sensor_core_ops,
786 .video = &sensor_video_ops,
787 .pad = &sensor_pad_ops,
788 };
789
790 /* ----------------------------------------------------------------------- */
791 static struct cci_driver cci_drv[] = {
792 {
793 .name = SENSOR_NAME,
794 .addr_width = CCI_BITS_16,
795 .data_width = CCI_BITS_16,
796 }, {
797 .name = SENSOR_NAME_2,
798 .addr_width = CCI_BITS_16,
799 .data_width = CCI_BITS_16,
800 }
801 };
802
803
sensor_init_controls(struct v4l2_subdev * sd,const struct v4l2_ctrl_ops * ops)804 static int sensor_init_controls(struct v4l2_subdev *sd,
805 const struct v4l2_ctrl_ops *ops)
806 {
807 struct sensor_info *info = to_state(sd);
808 struct v4l2_ctrl_handler *handler = &info->handler;
809 struct v4l2_ctrl *ctrl;
810 int ret = 0;
811
812 v4l2_ctrl_handler_init(handler, 2);
813
814 v4l2_ctrl_new_std(handler, ops, V4L2_CID_GAIN, 1 * 1600,
815 256 * 1600, 1, 1 * 1600);
816 ctrl = v4l2_ctrl_new_std(handler, ops, V4L2_CID_EXPOSURE, 0,
817 65536 * 16, 1, 0);
818 if (ctrl != NULL)
819 ctrl->flags |= V4L2_CTRL_FLAG_VOLATILE;
820
821 if (handler->error) {
822 ret = handler->error;
823 v4l2_ctrl_handler_free(handler);
824 }
825
826 sd->ctrl_handler = handler;
827
828 return ret;
829 }
830
831 static int sensor_dev_id;
832
sensor_probe(struct i2c_client * client,const struct i2c_device_id * id)833 static int sensor_probe(struct i2c_client *client,
834 const struct i2c_device_id *id)
835 {
836 struct v4l2_subdev *sd;
837 struct sensor_info *info;
838 int i;
839
840 info = kzalloc(sizeof(struct sensor_info), GFP_KERNEL);
841 if (info == NULL)
842 return -ENOMEM;
843 sd = &info->sd;
844
845 if (client) {
846 for (i = 0; i < SENSOR_NUM; i++) {
847 if (!strcmp(cci_drv[i].name, client->name))
848 break;
849 }
850 cci_dev_probe_helper(sd, client, &sensor_ops, &cci_drv[i]);
851 } else {
852 cci_dev_probe_helper(sd, client,
853 &sensor_ops, &cci_drv[sensor_dev_id++]);
854 }
855
856 sensor_init_controls(sd, &sensor_ctrl_ops);
857
858 mutex_init(&info->lock);
859
860 info->fmt = &sensor_formats[0];
861 info->fmt_pt = &sensor_formats[0];
862 info->win_pt = &sensor_win_sizes[0];
863 info->fmt_num = N_FMTS;
864 info->win_size_num = N_WIN_SIZES;
865 info->sensor_field = V4L2_FIELD_NONE;
866 info->stream_seq = MIPI_BEFORE_SENSOR;
867 info->combo_mode = CMB_PHYA_OFFSET1 | MIPI_NORMAL_MODE;
868 info->af_first_flag = 1;
869 info->exp = 0;
870 info->gain = 0;
871
872 return 0;
873 }
874
sensor_remove(struct i2c_client * client)875 static int sensor_remove(struct i2c_client *client)
876 {
877 struct v4l2_subdev *sd;
878 int i;
879
880 if (client) {
881 for (i = 0; i < SENSOR_NUM; i++) {
882 if (!strcmp(cci_drv[i].name, client->name))
883 break;
884 }
885 sd = cci_dev_remove_helper(client, &cci_drv[i]);
886 } else {
887 sd = cci_dev_remove_helper(client, &cci_drv[sensor_dev_id++]);
888 }
889
890 kfree(to_state(sd));
891 return 0;
892 }
893
894 static const struct i2c_device_id sensor_id[] = {
895 {SENSOR_NAME, 0},
896 {}
897 };
898
899 static const struct i2c_device_id sensor_id_2[] = {
900 {SENSOR_NAME_2, 0},
901 {}
902 };
903
904 MODULE_DEVICE_TABLE(i2c, sensor_id);
905 MODULE_DEVICE_TABLE(i2c, sensor_id_2);
906
907 static struct i2c_driver sensor_driver[] = {
908 {
909 .driver = {
910 .owner = THIS_MODULE,
911 .name = SENSOR_NAME,
912 },
913 .probe = sensor_probe,
914 .remove = sensor_remove,
915 .id_table = sensor_id,
916 }, {
917 .driver = {
918 .owner = THIS_MODULE,
919 .name = SENSOR_NAME_2,
920 },
921 .probe = sensor_probe,
922 .remove = sensor_remove,
923 .id_table = sensor_id_2,
924 },
925 };
init_sensor(void)926 static __init int init_sensor(void)
927 {
928 int i, ret = 0;
929
930 sensor_dev_id = 0;
931
932 for (i = 0; i < SENSOR_NUM; i++)
933 ret = cci_dev_init_helper(&sensor_driver[i]);
934
935 return ret;
936 }
937
exit_sensor(void)938 static __exit void exit_sensor(void)
939 {
940 int i;
941
942 sensor_dev_id = 0;
943
944 for (i = 0; i < SENSOR_NUM; i++)
945 cci_dev_exit_helper(&sensor_driver[i]);
946 }
947
948 module_init(init_sensor);
949 module_exit(exit_sensor);
950