2 * driver for Fusitju M5MO LS 8MP camera
4 * Copyright (c) 2010, Samsung Electronics. All rights reserved
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License version 2 as
8 * published by the Free Software Foundation.
10 * This program is distributed in the hope that it will be useful, but
11 * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
12 * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 #include <linux/i2c.h>
17 #include <linux/init.h>
18 #include <media/v4l2-device.h>
19 #include <linux/delay.h>
20 #include <linux/interrupt.h>
21 #include <linux/irq.h>
22 #include <linux/vmalloc.h>
23 #include <linux/firmware.h>
24 #include <linux/videodev2.h>
26 #ifdef CONFIG_VIDEO_SAMSUNG_V4L2
27 #include <linux/videodev2_exynos_media.h>
28 #include <linux/videodev2_exynos_camera.h>
31 #include <linux/regulator/machine.h>
33 #include <media/m5mo_platform.h>
36 #define M5MO_DRIVER_NAME "M5MO"
39 #define M5MO_FW_PATH "/sdcard/RS_M5LS.bin"
40 #endif /* SDCARD_FW */
41 #define M5MOT_FW_REQUEST_PATH "m5mo/RS_M5LS_T.bin" /* Techwin */
42 #define M5MOO_FW_REQUEST_PATH "m5mo/RS_M5LS_O.bin" /* Optical communication */
43 #define M5MO_FW_DUMP_PATH "/data/RS_M5LS_dump.bin"
44 #define M5MO_FW_VER_LEN 22
45 #define M5MO_FW_VER_FILE_CUR 0x16FF00
47 #define M5MO_FLASH_BASE_ADDR 0x10000000
48 #define M5MO_INT_RAM_BASE_ADDR 0x68000000
50 #define M5MO_I2C_RETRY 5
51 #define M5MO_I2C_VERIFY 500
52 #define M5MO_TIMEOUT 5000
53 #define M5MO_AFB_TIMEOUT 15000 /* FIXME */
54 #define M5MO_ESD_TIMEOUT 1000
56 #define M5MO_POSTVIEW_SUPPORT
57 #define M5MO_JPEG_MAXSIZE 0x3A0000
58 #define M5MO_THUMB_MAXSIZE 0x10000
59 #define M5MO_POST_MAXSIZE 0xBB800
60 #define M5MO_POST_SIZE_VGA 0x70800
61 #define M5MO_POST_SIZE_WVGA 0x8CA00
63 #define M5MO_DEF_APEX_DEN 100
65 #define m5mo_readb(sd, g, b, v) m5mo_read(sd, 1, g, b, v)
66 #define m5mo_readw(sd, g, b, v) m5mo_read(sd, 2, g, b, v)
67 #define m5mo_readl(sd, g, b, v) m5mo_read(sd, 4, g, b, v)
69 #define m5mo_writeb(sd, g, b, v) m5mo_write(sd, 1, g, b, v)
70 #define m5mo_writew(sd, g, b, v) m5mo_write(sd, 2, g, b, v)
71 #define m5mo_writel(sd, g, b, v) m5mo_write(sd, 4, g, b, v)
73 static const struct m5mo_frmsizeenum preview_frmsizes[] = {
74 { M5MO_PREVIEW_QCIF, 176, 144, 0x05, 0 }, /* 176 x 144 */
75 { M5MO_PREVIEW_QCIF2, 528, 432, 0x2C, 0 }, /* 176 x 144 */
76 { M5MO_PREVIEW_QVGA, 320, 240, 0x09, 0 },
77 { M5MO_PREVIEW_VGA, 640, 480, 0x17, 0 },
78 { M5MO_PREVIEW_D1, 720, 480, 0x18, 0 },
79 { M5MO_PREVIEW_WVGA, 800, 480, 0x1A, 1 },
80 { M5MO_PREVIEW_720P, 1280, 720, 0x21, 1 },
81 { M5MO_PREVIEW_1080P, 1920, 1080, 0x28, 1 },
82 { M5MO_PREVIEW_HDR, 3264, 2448, 0x27, 0 },
85 static const struct m5mo_frmsizeenum capture_frmsizes[] = {
86 { M5MO_CAPTURE_VGA, 640, 480, 0x09, 0 },
87 { M5MO_CAPTURE_WVGA, 800, 480, 0x0A, 1 },
88 { M5MO_CAPTURE_HD, 1280, 720, 0x10, 1 },
89 { M5MO_CAPTURE_2MP, 1600, 1200, 0x17, 0 },
90 { M5MO_CAPTURE_FULLHD, 1920, 1080, 0x19, 1 },
91 { M5MO_CAPTURE_W2MP, 2048, 1232, 0x2C, 1 },
92 { M5MO_CAPTURE_3MP, 2048, 1536, 0x1B, 0 },
93 { M5MO_CAPTURE_W4MP, 2560, 1536, 0x1D, 1 },
94 { M5MO_CAPTURE_5MP, 2560, 1920, 0x1F, 0 },
95 { M5MO_CAPTURE_6MP, 3264, 1960, 0x22, 1 },
96 { M5MO_CAPTURE_W7MP, 3264, 1968, 0x2D, 1 },
97 { M5MO_CAPTURE_8MP, 3264, 2448, 0x25, 0 },
100 static struct m5mo_control m5mo_ctrls[] = {
103 .id = V4L2_CID_CAMERA_SENSOR_MODE,
104 .minimum = SENSOR_CAMERA,
105 .maximum = SENSOR_MOVIE,
107 .value = SENSOR_CAMERA,
108 .default_value = SENSOR_CAMERA,
110 .id = V4L2_CID_CAM_DR,
117 .id = V4L2_CID_CAMERA_HDR,
127 .id = V4L2_CID_CAMERA_FLASH_MODE,
128 .minimum = FLASH_MODE_OFF,
129 .maximum = FLASH_MODE_MAX - 1,
131 .value = FLASH_MODE_OFF,
132 .default_value = FLASH_MODE_OFF,
135 /* Exposure & Scenemode stuff(ISO, Metering, Saturation, etc) */
137 .id = V4L2_CID_CAMERA_ISO,
142 .default_value = ISO_AUTO,
144 .id = V4L2_CID_CAMERA_METERING,
145 .minimum = METERING_MATRIX,
146 .maximum = METERING_MAX - 1,
148 .value = METERING_MATRIX,
149 .default_value = METERING_MATRIX,
151 .id = V4L2_CID_EXPOSURE,
158 .id = V4L2_CID_SATURATION,
159 .minimum = 0, /* -2 */
160 .maximum = 4, /* +2 */
165 .id = V4L2_CID_SHARPNESS,
166 .minimum = 0, /* -2 */
167 .maximum = 4, /* +2 */
172 .id = V4L2_CID_WHITE_BALANCE_PRESET,
173 .minimum = WHITE_BALANCE_AUTO,
174 .maximum = WHITE_BALANCE_MAX - 1,
176 .value = WHITE_BALANCE_AUTO,
177 .default_value = WHITE_BALANCE_AUTO,
179 .id = V4L2_CID_COLORFX,
180 .minimum = V4L2_COLORFX_NONE,
181 .maximum = V4L2_COLORFX_VIVID,
183 .value = V4L2_COLORFX_NONE,
184 .default_value = V4L2_COLORFX_NONE,
186 .id = V4L2_CID_CAMERA_SCENE_MODE,
187 .minimum = SCENE_MODE_NONE,
188 .maximum = SCENE_MODE_MAX - 1,
190 .value = SCENE_MODE_NONE,
191 .default_value = SCENE_MODE_MAX,
196 .id = V4L2_CID_ZOOM_ABSOLUTE,
197 .minimum = ZOOM_LEVEL_0,
198 .maximum = ZOOM_LEVEL_MAX - 1,
200 .value = ZOOM_LEVEL_0,
201 .default_value = ZOOM_LEVEL_0,
206 .id = V4L2_CID_FOCUS_AUTO_RECTANGLE_LEFT,
208 .maximum = 4000, /* FIXME */
213 .id = V4L2_CID_FOCUS_AUTO_RECTANGLE_TOP,
215 .maximum = 3000, /* FIXME */
220 .id = V4L2_CID_FOCUS_AUTO_RECTANGLE_WIDTH,
222 .maximum = 4000, /* FIXME */
227 .id = V4L2_CID_FOCUS_AUTO_RECTANGLE_HEIGHT,
229 .maximum = 3000, /* FIXME */
234 .id = V4L2_CID_FOCUS_AUTO_MODE,
235 .minimum = V4L2_FOCUS_AUTO_NORMAL,
236 .maximum = V4L2_FOCUS_AUTO_RECTANGLE,
238 .value = V4L2_FOCUS_AUTO_NORMAL,
239 .default_value = V4L2_FOCUS_AUTO_NORMAL,
241 .id = V4L2_CID_CAMERA_SET_AUTO_FOCUS,
251 .id = V4L2_CID_CAMERA_CAPTURE,
258 .id = V4L2_CID_CAM_JPEG_QUALITY,
263 .default_value = 100,
266 /* <-- TODO: duplicated CID. will be removed. */
268 .id = V4L2_CID_CAMERA_WDR,
275 .id = V4L2_CID_CAMERA_ZOOM,
276 .minimum = ZOOM_LEVEL_0,
277 .maximum = ZOOM_LEVEL_MAX - 1,
279 .value = ZOOM_LEVEL_0,
280 .default_value = ZOOM_LEVEL_0,
285 static inline struct m5mo_state *to_state(struct v4l2_subdev *sd)
287 return container_of(sd, struct m5mo_state, sd);
290 #define M5MOLS_I2C_MAX_SIZE 4
291 #define M5MOLS_BYTE_READ 0x01
292 #define M5MOLS_BYTE_WRITE 0x02
294 static int m5mo_read(struct v4l2_subdev *sd,
295 u8 len, u8 category, u8 byte, u32 *val)
297 struct i2c_client *client = v4l2_get_subdevdata(sd);
298 struct device *cdev = &client->dev;
299 struct i2c_msg msg[2];
300 unsigned char data[5];
301 unsigned char recv_data[len + 1];
304 if (!client->adapter)
307 if (len != 0x01 && len != 0x02 && len != 0x04)
310 msg[0].addr = client->addr;
315 data[1] = M5MOLS_BYTE_READ;
320 msg[1].addr = client->addr;
321 msg[1].flags = I2C_M_RD;
322 msg[1].len = len + 1;
323 msg[1].buf = recv_data;
325 ret = i2c_transfer(client->adapter, msg, 2);
328 dev_err(cdev, "read failed: len:%d cat:%02x byte:%02x. %d\n",
329 len, category, byte, ret);
335 else if (len == 0x02)
336 *val = recv_data[1] << 8 | recv_data[2];
338 *val = recv_data[1] << 24 | recv_data[2] << 16 |
339 recv_data[3] << 8 | recv_data[4];
344 static int m5mo_write(struct v4l2_subdev *sd,
345 u8 len, u8 category, u8 byte, u32 val)
347 struct i2c_client *client = v4l2_get_subdevdata(sd);
348 struct device *cdev = &client->dev;
349 struct i2c_msg msg[1];
350 unsigned char data[len + 4];
354 if (!client->adapter)
357 if (len != 0x01 && len != 0x02 && len != 0x04)
360 msg->addr = client->addr;
362 msg->len = (u16)len + 4;
365 data[1] = M5MOLS_BYTE_WRITE;
370 data[4] = val & 0xFF;
371 } else if (len == 0x02) {
372 data[4] = (val >> 8) & 0xFF;
373 data[5] = val & 0xFF;
375 data[4] = (val >> 24) & 0xFF;
376 data[5] = (val >> 16) & 0xFF;
377 data[6] = (val >> 8) & 0xFF;
378 data[7] = val & 0xFF;
381 for (i = M5MO_I2C_RETRY; i; i--) {
382 ret = i2c_transfer(client->adapter, msg, 1);
385 usleep_range(10000, 10000);
388 dev_err(cdev, "write failed: len:%d cat:%02x byte:%02x "
390 len, category, byte, val, ret);
393 dev_dbg(cdev, "I2C write : len:%d cat:%02x byte:%02x val:%02x.\n",
394 len, category, byte, val);
399 static int m5mo_mem_read(struct v4l2_subdev *sd, u16 len, u32 addr, u8 *val)
401 struct i2c_client *client = v4l2_get_subdevdata(sd);
402 struct device *cdev = &client->dev;
404 unsigned char data[8];
405 unsigned char recv_data[len + 3];
408 if (!client->adapter)
414 msg.addr = client->addr;
416 msg.len = sizeof(data);
419 /* high byte goes out first */
422 data[2] = (addr >> 24) & 0xFF;
423 data[3] = (addr >> 16) & 0xFF;
424 data[4] = (addr >> 8) & 0xFF;
425 data[5] = addr & 0xFF;
426 data[6] = (len >> 8) & 0xFF;
427 data[7] = len & 0xFF;
429 for (i = M5MO_I2C_RETRY; i; i--) {
430 err = i2c_transfer(client->adapter, &msg, 1);
433 usleep_range(2000, 2000);
439 msg.flags = I2C_M_RD;
440 msg.len = sizeof(recv_data);
442 for (i = M5MO_I2C_RETRY; i; i--) {
443 err = i2c_transfer(client->adapter, &msg, 1);
446 usleep_range(2000, 2000);
452 if (len != (recv_data[1] << 8 | recv_data[2])){
453 dev_info(cdev, "expected length %d, but return length %d\n",
454 len, recv_data[1] << 8 | recv_data[2]);
457 memcpy(val, recv_data + 3, len);
459 dev_info(cdev, "address %#x, length %d\n", addr, len);
463 static int m5mo_mem_write(struct v4l2_subdev *sd,
464 u8 cmd, u16 len, u32 addr, u8 *val)
466 struct i2c_client *client = v4l2_get_subdevdata(sd);
467 struct device *cdev = &client->dev;
469 unsigned char data[len + 8];
472 if (!client->adapter)
475 msg.addr = client->addr;
477 msg.len = sizeof(data);
480 /* high byte goes out first */
483 data[2] = (addr >> 24) & 0xFF;
484 data[3] = (addr >> 16) & 0xFF;
485 data[4] = (addr >> 8) & 0xFF;
486 data[5] = addr & 0xFF;
487 data[6] = (len >> 8) & 0xFF;
488 data[7] = len & 0xFF;
489 memcpy(data + 2 + sizeof(addr) + sizeof(len), val, len);
491 dev_info(cdev, "address %#x, length %d\n", addr, len);
493 for (i = M5MO_I2C_RETRY; i; i--) {
494 err = i2c_transfer(client->adapter, &msg, 1);
497 usleep_range(2000, 2000);
503 static int m5mo_busy(struct v4l2_subdev *sd, u8 category, u8 byte, u32 mask)
505 struct i2c_client *client = v4l2_get_subdevdata(sd);
506 struct device *cdev = &client->dev;
510 for (i = 0; i < M5MO_I2C_VERIFY; i++) {
511 ret = m5mo_readb(sd, category, byte, &val);
514 if ((val & mask) == mask) {
515 dev_dbg(cdev, "busy: verified [c,b,v] "
516 "[%02x, %02x, %02x] (try = %d)\n",
517 category, byte, mask, i);
520 /* If camera mode is not changed, wait 10ms more at least. */
527 static irqreturn_t m5mo_isp_isr(int irq, void *dev_id)
529 struct v4l2_subdev *sd = (struct v4l2_subdev *)dev_id;
530 struct m5mo_state *state = to_state(sd);
532 state->isp.issued = 1;
533 wake_up_interruptible(&state->isp.wait);
538 static u32 m5mo_wait(struct v4l2_subdev *sd, int cond, u32 timeout)
540 struct m5mo_state *state = to_state(sd);
541 struct i2c_client *client = v4l2_get_subdevdata(sd);
542 struct device *cdev = &client->dev;
546 if (wait_event_interruptible_timeout(state->isp.wait,
548 msecs_to_jiffies(timeout)) == 0)
551 /* Disable Interrupt */
552 ret = m5mo_writeb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_INT_EN, M5MO_INT_NONE);
556 ret = m5mo_readb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_INT_FACTOR, ®);
560 if ((reg == 0xff) || (reg == 0xfa)) {
561 dev_info(cdev, "*** error issued: ret %d, reg %x\n", ret, reg);
565 state->isp.int_factor = reg;
566 if (!is_interrupted(cond))
569 state->isp.issued = 0;
571 dev_info(cdev, "*** issued: [%s - 0x%x]\n",
572 reg == M5MO_INT_MODE ? "INT_MODE" :
573 reg == M5MO_INT_AF ? "INT_AF" :
574 reg == M5MO_INT_CAPTURE ? "INT_CAPTURE" :
575 reg == M5MO_INT_SOUND ? "INT_SOUND" :
576 reg == M5MO_INT_ZOOM ? "INT_ZOOM" :
577 reg == M5MO_INT_FD ? "INT_FD" :
578 reg == M5MO_INT_LENS_INIT ? "INT_LENS_INIT" :
579 reg == (M5MO_INT_SOUND | M5MO_INT_CAPTURE) ? "INT_SOUND_CAPTURE" :
585 static int m5mo_reg_mode(struct v4l2_subdev *sd, u32 mode)
589 ret = m5mo_writeb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_MODE, mode);
591 ret = m5mo_busy(sd, M5MO_CATEGORY_SYS, M5MO_SYS_MODE, mode);
595 static int m5mo_set_mode(struct v4l2_subdev *sd, u32 mode)
597 struct m5mo_state *state = to_state(sd);
598 struct i2c_client *client = v4l2_get_subdevdata(sd);
599 struct device *cdev = &client->dev;
603 if (mode < M5MO_PARMSET_MODE && mode > M5MO_STILLCAP_MODE)
606 err = m5mo_readb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_MODE, &old_mode);
607 if (!err && old_mode == mode)
613 case M5MO_SYSINIT_MODE:
616 case M5MO_PARMSET_MODE:
617 err = m5mo_reg_mode(sd, M5MO_MONITOR_MODE);
618 if (mode == M5MO_STILLCAP_MODE)
619 err = m5mo_reg_mode(sd, M5MO_STILLCAP_MODE);
621 case M5MO_MONITOR_MODE:
622 err = m5mo_reg_mode(sd, mode);
624 case M5MO_STILLCAP_MODE:
625 err = m5mo_reg_mode(sd, M5MO_PARMSET_MODE);
626 if (mode == M5MO_MONITOR_MODE)
627 err = m5mo_reg_mode(sd, M5MO_MONITOR_MODE);
630 dev_info(cdev, "@@@@@ mode: unknown, %d\n", old_mode);
634 dev_info(cdev, "@@@@@ mode: Changed: %#x -> %#x, issued %d\n",
635 old_mode, mode, state->isp.issued);
640 * v4l2_subdev_core_ops
642 static int m5mo_queryctrl(struct v4l2_subdev *sd, struct v4l2_queryctrl *qc)
646 for (i = 0; i < ARRAY_SIZE(m5mo_ctrls); i++) {
647 if (qc->id == m5mo_ctrls[i].id) {
648 qc->maximum = m5mo_ctrls[i].maximum;
649 qc->minimum = m5mo_ctrls[i].minimum;
650 qc->step = m5mo_ctrls[i].step;
651 qc->default_value = m5mo_ctrls[i].default_value;
658 static int m5mo_g_ctrl(struct v4l2_subdev *sd, struct v4l2_control *ctrl)
660 struct m5mo_state *state = to_state(sd);
661 struct i2c_client *client = v4l2_get_subdevdata(sd);
662 struct device *cdev = &client->dev;
667 err = m5mo_queryctrl(sd, &qc);
669 dev_info(cdev, "g_ctrl: no CID[0x%08x] value[%d]. Just pass.\n",
670 ctrl->id, ctrl->value);
677 case V4L2_CID_CAM_SENSOR_FW_VER:
678 dev_info(cdev, "FW ver [%s]\n", state->exif.unique_id);
681 /* dependent on SENSOR itself */
682 case V4L2_CID_CAMERA_SENSOR_MODE:
685 case V4L2_CID_CAM_DR:
686 case V4L2_CID_CAMERA_WDR:
687 ctrl->value = state->wdr;
689 case V4L2_CID_CAMERA_HDR:
690 ctrl->value = state->hdr;
694 case V4L2_CID_CAMERA_FLASH_MODE:
695 ctrl->value = state->flash_mode;
698 /* Exposure & Scenemode stuff(ISO, Metering, Saturation, etc) */
699 case V4L2_CID_CAMERA_ISO:
700 ctrl->value = state->iso;
702 case V4L2_CID_CAMERA_METERING:
703 ctrl->value = state->metering;
705 case V4L2_CID_EXPOSURE:
706 ctrl->value = state->exposure;
708 case V4L2_CID_SATURATION:
709 ctrl->value = state->saturation;
711 case V4L2_CID_SHARPNESS:
712 ctrl->value = state->sharpness;
714 case V4L2_CID_WHITE_BALANCE_PRESET:
715 ctrl->value = state->wb_preset;
717 case V4L2_CID_COLORFX:
718 ctrl->value = state->colorfx;
720 case V4L2_CID_CAMERA_SCENE_MODE:
721 ctrl->value = state->scenemode;
725 case V4L2_CID_ZOOM_ABSOLUTE:
726 case V4L2_CID_CAMERA_ZOOM:
727 ctrl->value = state->zoom;
731 case V4L2_CID_FOCUS_AUTO_RECTANGLE_LEFT:
732 ctrl->value = state->focus.pos_x;
734 case V4L2_CID_FOCUS_AUTO_RECTANGLE_TOP:
735 ctrl->value = state->focus.pos_y;
737 case V4L2_CID_FOCUS_AUTO_RECTANGLE_WIDTH:
738 ctrl->value = state->focus.width;
740 case V4L2_CID_FOCUS_AUTO_RECTANGLE_HEIGHT:
741 ctrl->value = state->focus.height;
743 case V4L2_CID_FOCUS_AUTO_MODE:
744 if (state->focus.mode == V4L2_FOCUS_AUTO_MACRO)
745 ctrl->value = V4L2_FOCUS_AUTO_MACRO;
746 else if (state->focus.mode == V4L2_FOCUS_AUTO_CONTINUOUS)
747 ctrl->value = V4L2_FOCUS_AUTO_CONTINUOUS;
748 else if (state->focus.mode == V4L2_FOCUS_AUTO_FACE_DETECTION)
749 ctrl->value = V4L2_FOCUS_AUTO_FACE_DETECTION;
750 else if (state->focus.mode == V4L2_FOCUS_AUTO_RECTANGLE)
751 ctrl->value = V4L2_FOCUS_AUTO_RECTANGLE;
753 ctrl->value = V4L2_FOCUS_AUTO_NORMAL;
757 case V4L2_CID_CAM_JPEG_MAIN_SIZE:
758 ctrl->value = state->jpeg.main_size;
760 case V4L2_CID_CAM_JPEG_THUMB_SIZE:
761 ctrl->value = state->jpeg.thumb_size;
763 case V4L2_CID_CAM_JPEG_THUMB_OFFSET:
764 ctrl->value = state->jpeg.thumb_offset;
766 case V4L2_CID_CAM_JPEG_POSTVIEW_SIZE:
767 ctrl->value = (state->wide_res ? M5MO_POST_SIZE_WVGA : M5MO_POST_SIZE_VGA);
768 dev_info(cdev, "%s: Postview size : %d\n", __func__, ctrl->value);
770 case V4L2_CID_CAM_JPEG_POSTVIEW_OFFSET:
771 ctrl->value = state->jpeg.postview_offset;
773 case V4L2_CID_CAM_JPEG_MEMSIZE: /* Using on FIMC */
774 ctrl->value = M5MO_JPEG_MAXSIZE +
775 M5MO_THUMB_MAXSIZE + M5MO_POST_MAXSIZE;
779 case V4L2_CID_CAMERA_EXIF_EXPTIME:
780 ctrl->value = state->exif.exptime;
782 case V4L2_CID_CAMERA_EXIF_TV:
783 ctrl->value = state->exif.tv;
785 case V4L2_CID_CAMERA_EXIF_BV:
786 ctrl->value = state->exif.bv;
788 case V4L2_CID_CAMERA_EXIF_FLASH:
789 ctrl->value = state->exif.flash;
791 case V4L2_CID_CAMERA_EXIF_ISO:
792 ctrl->value = state->exif.iso;
794 case V4L2_CID_CAMERA_EXIF_EBV:
795 ctrl->value = state->exif.ebv;
799 dev_info(cdev, "g_ctrl: warnings!!! "
800 "no CID[%s][0x%08x] PRIVATE[%d] val[%d]\n",
801 v4l2_ctrl_get_name(ctrl->id), ctrl->id,
802 ctrl->id - V4L2_CID_PRIVATE_BASE,
807 dev_dbg(cdev, "g_ctrl: CID[%s][0x%08x] PRIVATE[%d] val[%d] ret[%d]\n",
808 v4l2_ctrl_get_name(ctrl->id), ctrl->id,
809 ctrl->id - V4L2_CID_PRIVATE_BASE,
815 static int m5mo_set_af_softlanding(struct v4l2_subdev *sd)
817 struct m5mo_state *state = to_state(sd);
818 struct i2c_client *client = v4l2_get_subdevdata(sd);
819 struct device *cdev = &client->dev;
823 if (unlikely(state->isp.bad_fw)) {
824 dev_info(cdev, "\"Unknown\" state, please update F/W");
828 err = m5mo_set_mode(sd, M5MO_MONITOR_MODE);
830 err = m5mo_writeb(sd, M5MO_CATEGORY_LENS, M5MO_LENS_AF_MODE, 0x07);
834 for (i = M5MO_I2C_VERIFY; i; i--) {
835 err = m5mo_readb(sd, M5MO_CATEGORY_LENS, M5MO_LENS_AF_STATUS,
839 if ((status & 0x01) == 0x00)
843 if ((status & 0x01) != 0x00)
850 static int m5mo_dump_fw(struct v4l2_subdev *sd)
852 struct i2c_client *client = v4l2_get_subdevdata(sd);
853 struct device *cdev = &client->dev;
857 u32 addr, unit, count, intram_unit = 0x1000;
863 fp = filp_open(M5MO_FW_DUMP_PATH,
864 O_WRONLY|O_CREAT|O_TRUNC, S_IRUGO|S_IWUGO|S_IXUSR);
866 dev_info(cdev, "failed to open %s, err %ld\n",
867 M5MO_FW_DUMP_PATH, PTR_ERR(fp));
872 buf = kmalloc(intram_unit, GFP_KERNEL);
874 dev_info(cdev, "failed to allocate memory\n");
881 err = m5mo_mem_write(sd, 0x04, sizeof(val), 0x50000308, &val);
885 addr = M5MO_FLASH_BASE_ADDR;
888 for (i = 0; i < count; i++) {
889 for (j = 0; j < unit; j += intram_unit) {
890 err = m5mo_mem_read(sd,
891 intram_unit, addr + (i * unit) + j, buf);
893 dev_info(cdev, "i2c falied, err %d\n", err);
896 vfs_write(fp, buf, intram_unit, &fp->f_pos);
900 addr = M5MO_FLASH_BASE_ADDR + SZ_64K * count;
903 for (i = 0; i < count; i++) {
904 for (j = 0; j < unit; j += intram_unit) {
905 err = m5mo_mem_read(sd,
906 intram_unit, addr + (i * unit) + j, buf);
908 dev_info(cdev, "i2c falied, err %d\n", err);
911 vfs_write(fp, buf, intram_unit, &fp->f_pos);
919 filp_close(fp, current->files);
925 static int m5mo_get_phone_fw_version(struct v4l2_subdev *sd,
928 struct i2c_client *client = v4l2_get_subdevdata(sd);
929 struct device *dev = &client->adapter->dev;
930 struct device *cdev = &client->dev;
931 u8 sensor_ver[M5MO_FW_VER_LEN] = {0, };
932 const struct firmware *fentry;
939 int fw_requested = 1;
944 fp = filp_open(M5MO_FW_PATH, O_RDONLY, 0);
946 dev_dbg(cdev, "failed to open %s, err %ld\n",
947 M5MO_FW_PATH, PTR_ERR(fp));
952 err = vfs_llseek(fp, M5MO_FW_VER_FILE_CUR, SEEK_SET);
954 dev_info(cdev, "failed to fseek, %d\n", err);
958 nread = vfs_read(fp, (char __user *)buf, M5MO_FW_VER_LEN, &fp->f_pos);
959 if (nread != M5MO_FW_VER_LEN) {
960 dev_info(cdev, "failed to read firmware file, %ld Bytes\n", nread);
968 #endif /* SDCARD_FW */
969 m5mo_get_sensor_fw_version(sd, sensor_ver);
971 if (sensor_ver[0] == 'T')
972 err = request_firmware(&fentry, M5MOT_FW_REQUEST_PATH, dev);
974 err = request_firmware(&fentry, M5MOO_FW_REQUEST_PATH, dev);
977 dev_info(cdev, "request_firmware falied\n");
982 memcpy(buf, (u8 *)&fentry->data[M5MO_FW_VER_FILE_CUR], M5MO_FW_VER_LEN);
985 #endif /* SDCARD_FW */
990 filp_close(fp, current->files);
993 #endif /* SDCARD_FW */
998 static int m5mo_check_fw(struct v4l2_subdev *sd)
1000 struct m5mo_state *state = to_state(sd);
1001 struct i2c_client *client = v4l2_get_subdevdata(sd);
1002 struct device *cdev = &client->dev;
1003 u8 sensor_ver[M5MO_FW_VER_LEN] = "FAILED Fujitsu M5MOLS";
1004 u8 phone_ver[M5MO_FW_VER_LEN] = "FAILED Fujitsu M5MOLS";
1005 int af_cal_h = 0, af_cal_l = 0;
1006 int rg_cal_h = 0, rg_cal_l = 0;
1007 int bg_cal_h = 0, bg_cal_l = 0;
1008 int update_count = 0;
1012 m5mo_get_phone_fw_version(sd, phone_ver);
1014 if (state->isp.bad_fw)
1017 m5mo_get_sensor_fw_version(sd, sensor_ver);
1019 err = m5mo_writeb(sd, M5MO_CATEGORY_FLASH, M5MO_FLASH_CAM_START, 0x01);
1021 err = m5mo_wait(sd, M5MO_INT_MODE, M5MO_TIMEOUT);
1023 err = m5mo_readb(sd, M5MO_CATEGORY_LENS, M5MO_LENS_AF_CAL,
1026 err = m5mo_readb(sd, M5MO_CATEGORY_ADJST, M5MO_ADJST_AWB_RG_H,
1029 err = m5mo_readb(sd, M5MO_CATEGORY_ADJST, M5MO_ADJST_AWB_RG_L,
1032 err = m5mo_readb(sd, M5MO_CATEGORY_ADJST, M5MO_ADJST_AWB_BG_H,
1035 err = m5mo_readb(sd, M5MO_CATEGORY_ADJST, M5MO_ADJST_AWB_BG_L,
1041 if (!state->fw_version) {
1042 state->fw_version = kzalloc(50, GFP_KERNEL);
1043 if (!state->fw_version) {
1044 dev_info(cdev, "no memory for F/W version\n");
1049 sprintf(state->fw_version, "%s %s %d %x %x %x %x %x %x",
1050 sensor_ver, phone_ver, update_count,
1051 af_cal_h, af_cal_l, rg_cal_h, rg_cal_l, bg_cal_h, bg_cal_l);
1057 static int m5mo_get_sensor_fw_version(struct v4l2_subdev *sd,
1065 err = m5mo_mem_write(sd, 0x04, sizeof(val), 0x50000308, &val);
1067 err = m5mo_mem_read(sd, M5MO_FW_VER_LEN,
1068 M5MO_FLASH_BASE_ADDR + M5MO_FW_VER_FILE_CUR, buf);
1073 /* Control functions */
1074 static int m5mo_set_wdr(struct v4l2_subdev *sd, int value)
1076 struct m5mo_state *state = to_state(sd);
1079 err = m5mo_writeb(sd, M5MO_CATEGORY_MON, M5MO_MON_TONE_CTRL,
1080 value == 1 ? 0x09 : 0x05);
1082 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPPARM, M5MO_CAPPARM_WDR_EN,
1083 value == 1 ? 0x01 : 0x00);
1090 static int m5mo_set_hdr(struct v4l2_subdev *sd, int value)
1092 struct m5mo_state *state = to_state(sd);
1095 if (value < 0 && value > 2)
1099 err = m5mo_set_mode(sd, M5MO_MONITOR_MODE);
1105 err = m5mo_writeb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_ROOT_EN, 0x01);
1112 static int m5mo_set_flash(struct v4l2_subdev *sd, int value)
1114 struct m5mo_state *state = to_state(sd);
1115 struct i2c_client *client = v4l2_get_subdevdata(sd);
1116 const struct m5mo_platform_data *pdata = client->dev.platform_data;
1117 struct device *dev = &client->dev;
1121 * In SLP Platform, the recording mode of M5MO itself is not used.
1122 * So, it is not needed not to set flash mode on recording.
1123 * Exactly, always LIGHT & FLASH register should be configured.
1125 if (pdata->flash_power)
1126 err = pdata->flash_power(value == FLASH_MODE_OFF ? 0 : 1, dev);
1128 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPPARM,
1129 M5MO_CAPPARM_LIGHT_CTRL,
1130 value == FLASH_MODE_AUTO ? 0x02 :
1131 value == FLASH_MODE_ON ? 0x01 :
1132 value == FLASH_MODE_TORCH ? 0x03 : 0x00);
1134 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPPARM,
1135 M5MO_CAPPARM_FLASH_CTRL,
1136 value == FLASH_MODE_AUTO ? 0x02 :
1137 value == FLASH_MODE_ON ? 0x01 : 0x00);
1139 state->flash_mode = value;
1144 static int m5mo_set_iso(struct v4l2_subdev *sd, int value)
1146 struct m5mo_state *state = to_state(sd);
1148 u32 iso[] = { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05 };
1150 if (value == state->iso)
1153 err = m5mo_writeb(sd, M5MO_CATEGORY_AE, M5MO_AE_ISOSEL, iso[value]);
1160 static int m5mo_set_metering(struct v4l2_subdev *sd, int value)
1162 struct m5mo_state *state = to_state(sd);
1165 err = m5mo_writeb(sd, M5MO_CATEGORY_AE, M5MO_AE_MODE,
1166 value == METERING_SPOT ? 0x06 :
1167 value == METERING_MATRIX ? 0x01 : 0x03);
1169 state->metering = value;
1174 static int m5mo_set_exposure(struct v4l2_subdev *sd, int value)
1176 struct m5mo_state *state = to_state(sd);
1178 u32 exposure[] = { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08 };
1180 if (value == state->exposure)
1183 /* FIXME: videodev2.h*/
1184 err = m5mo_writeb(sd, M5MO_CATEGORY_AE, M5MO_AE_INDEX,
1187 state->exposure = value;
1192 static int m5mo_set_saturation(struct v4l2_subdev *sd, int value)
1194 struct m5mo_state *state = to_state(sd);
1196 u32 saturation[] = { 0x01, 0x02, 0x03, 0x04, 0x05 };
1198 if (value == state->saturation)
1201 err = m5mo_writeb(sd, M5MO_CATEGORY_MON, M5MO_MON_CHROMA_LVL,
1204 state->saturation = value;
1209 static int m5mo_set_sharpness(struct v4l2_subdev *sd, int value)
1211 struct m5mo_state *state = to_state(sd);
1213 u32 sharpness[] = { 0x03, 0x04, 0x05, 0x06, 0x07 };
1215 if (value == state->sharpness)
1218 err = m5mo_writeb(sd, M5MO_CATEGORY_MON, M5MO_MON_EDGE_LVL,
1221 state->sharpness = value;
1226 static int m5mo_set_whitebalance(struct v4l2_subdev *sd, int value)
1228 struct m5mo_state *state = to_state(sd);
1231 if (value == state->wb_preset)
1234 err = m5mo_writeb(sd, M5MO_CATEGORY_WB, M5MO_WB_AWB_MODE,
1235 value == WHITE_BALANCE_AUTO ? 0x01 : 0x02);
1237 err = m5mo_writeb(sd, M5MO_CATEGORY_WB, M5MO_WB_AWB_MANUAL,
1238 value == WHITE_BALANCE_SUNNY ? 0x04 :
1239 value == WHITE_BALANCE_CLOUDY ? 0x05 :
1240 value == WHITE_BALANCE_FLUORESCENT ? 0x02 : 0x01);
1242 state->wb_preset = value;
1247 static int m5mo_set_effect(struct v4l2_subdev *sd, int value)
1249 struct m5mo_state *state = to_state(sd);
1256 case V4L2_COLORFX_NONE:
1257 case V4L2_COLORFX_BW:
1258 case V4L2_COLORFX_SEPIA:
1260 err = m5mo_readb(sd, M5MO_CATEGORY_PARM, M5MO_PARM_EFFECT, &on);
1262 err = m5mo_set_mode(sd, M5MO_PARMSET_MODE);
1264 err = m5mo_writeb(sd, M5MO_CATEGORY_PARM,
1265 M5MO_PARM_EFFECT, 0);
1267 err = m5mo_set_mode(sd, M5MO_MONITOR_MODE);
1270 err = m5mo_writeb(sd, M5MO_CATEGORY_MON,
1271 M5MO_MON_COLOR_EFFECT,
1272 value == V4L2_COLORFX_NONE ? 0x00 : 0x01);
1273 if (!err && value != V4L2_COLORFX_NONE)
1274 err = m5mo_writeb(sd, M5MO_CATEGORY_MON, M5MO_MON_CFIXB,
1275 value == V4L2_COLORFX_SEPIA ? 0xd8 : 0x00);
1276 if (!err && value != V4L2_COLORFX_NONE)
1277 err = m5mo_writeb(sd, M5MO_CATEGORY_MON, M5MO_MON_CFIXR,
1278 value == V4L2_COLORFX_SEPIA ? 0x18 : 0x00);
1280 case V4L2_COLORFX_NEGATIVE:
1282 err = m5mo_readb(sd, M5MO_CATEGORY_MON, M5MO_MON_COLOR_EFFECT, &on);
1284 err = m5mo_writeb(sd, M5MO_CATEGORY_MON,
1285 M5MO_MON_COLOR_EFFECT, 0);
1288 err = m5mo_set_mode(sd, M5MO_PARMSET_MODE);
1290 err = m5mo_writeb(sd, M5MO_CATEGORY_PARM, M5MO_PARM_EFFECT,
1291 value == V4L2_COLORFX_NEGATIVE ? 0x01 : 0x08);
1294 err = m5mo_set_mode(sd, M5MO_MONITOR_MODE);
1298 value = V4L2_COLORFX_NONE;
1305 state->colorfx = value;
1310 static int m5mo_set_scene_mode(struct v4l2_subdev *sd, int value)
1312 struct m5mo_state *state = to_state(sd);
1316 if (value == state->scenemode)
1320 evp = value == SCENE_MODE_PORTRAIT ? 0x01 :
1321 value == SCENE_MODE_LANDSCAPE ? 0x02 :
1322 value == SCENE_MODE_SPORTS ? 0x03 :
1323 value == SCENE_MODE_PARTY_INDOOR ? 0x04 :
1324 value == SCENE_MODE_BEACH_SNOW ? 0x05 :
1325 value == SCENE_MODE_SUNSET ? 0x06 :
1326 value == SCENE_MODE_DUSK_DAWN ? 0x07 :
1327 value == SCENE_MODE_FALL_COLOR ? 0x08 :
1328 value == SCENE_MODE_NIGHTSHOT ? 0x09 :
1329 value == SCENE_MODE_BACK_LIGHT ? 0x0a :
1330 value == SCENE_MODE_FIREWORKS ? 0x0b :
1331 value == SCENE_MODE_TEXT ? 0x0c :
1332 value == SCENE_MODE_CANDLE_LIGHT ? 0x0d : 0x0;
1334 err = m5mo_writeb(sd, M5MO_CATEGORY_AE, M5MO_AE_EP_MODE_MON, evp);
1336 err = m5mo_writeb(sd, M5MO_CATEGORY_AE, M5MO_AE_EP_MODE_CAP, evp);
1339 err = m5mo_set_iso(sd, ISO_AUTO);
1342 err = m5mo_set_exposure(sd,
1343 value == SCENE_MODE_BEACH_SNOW ? EV_PLUS_2 :
1347 u32 awb = value == SCENE_MODE_SUNSET ? WHITE_BALANCE_SUNNY :
1348 value == SCENE_MODE_DUSK_DAWN ? WHITE_BALANCE_FLUORESCENT :
1349 value == SCENE_MODE_CANDLE_LIGHT ? WHITE_BALANCE_SUNNY :
1351 err = m5mo_set_whitebalance(sd, awb);
1354 /* Chroma Saturation */
1355 err = m5mo_set_saturation(sd,
1356 value == SCENE_MODE_LANDSCAPE ||
1357 value == SCENE_MODE_PARTY_INDOOR ||
1358 value == SCENE_MODE_BEACH_SNOW ? SATURATION_PLUS_1 :
1359 value == SCENE_MODE_FALL_COLOR ? SATURATION_PLUS_2 :
1360 SATURATION_DEFAULT);
1363 err = m5mo_set_sharpness(sd,
1364 value == SCENE_MODE_PORTRAIT ? SHARPNESS_MINUS_1 :
1365 value == SCENE_MODE_LANDSCAPE ? SHARPNESS_PLUS_1 :
1366 value == SCENE_MODE_TEXT ? SHARPNESS_PLUS_2 :
1369 /* Emotional Color */
1370 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPPARM, M5MO_CAPPARM_MCC_MODE,
1371 value == SCENE_MODE_NONE ? 0x01 : 0x00);
1373 state->scenemode = value;
1378 static int m5mo_set_zoom(struct v4l2_subdev *sd, int value)
1380 struct m5mo_state *state = to_state(sd);
1382 int zoom[] = { 1, 2, 3, 5, 6, 7, 9, 10, 11, 13, 14, 15, 17, 18, 19,
1383 20, 21, 22, 24, 25, 26, 28, 29, 30, 31, 32, 34, 35, 36, 38, 39 };
1385 err = m5mo_writeb(sd, M5MO_CATEGORY_MON, M5MO_MON_ZOOM, zoom[value]);
1387 state->zoom = value;
1392 static int m5mo_set_lock(struct v4l2_subdev *sd, int value)
1394 struct m5mo_state *state = to_state(sd);
1397 if (value == state->focus.lock)
1400 ret = m5mo_writeb(sd, M5MO_CATEGORY_AE, M5MO_AE_LOCK, value);
1402 ret = m5mo_writeb(sd, M5MO_CATEGORY_WB, M5MO_AWB_LOCK, value);
1404 state->focus.lock = value;
1409 static u32 m5mo_get_af(struct v4l2_subdev *sd)
1411 struct m5mo_state *state = to_state(sd);
1412 struct i2c_client *client = v4l2_get_subdevdata(sd);
1413 struct device *cdev = &client->dev;
1417 ret = m5mo_readb(sd, M5MO_CATEGORY_LENS, M5MO_LENS_AF_STATUS, ®);
1418 if (!ret && reg != M5MO_AF_STATUS_FAILED &&
1419 reg != M5MO_AF_STATUS_MOVING &&
1420 reg != M5MO_AF_STATUS_SUCCESS &&
1421 reg != M5MO_AF_STATUS_IDLE &&
1422 reg != M5MO_AF_STATUS_BUSY)
1425 state->focus.status = reg;
1427 ret = reg == M5MO_AF_STATUS_MOVING ? -EBUSY :
1428 reg == M5MO_AF_STATUS_SUCCESS ? 0 :
1429 reg == M5MO_AF_STATUS_FAILED ? -EAGAIN :
1430 reg == M5MO_AF_STATUS_IDLE ? 0 : -EBUSY;
1432 if (reg == M5MO_AF_STATUS_SUCCESS){
1433 dev_info(cdev, "@@@ AF status %s\n", "Success");
1434 }else if (reg == M5MO_AF_STATUS_FAILED){
1435 dev_info(cdev, "@@@ AF status %s\n", "Failed");
1441 static int m5mo_set_af_start(struct v4l2_subdev *sd)
1443 struct m5mo_state *state = to_state(sd);
1444 struct i2c_client *client = v4l2_get_subdevdata(sd);
1445 struct device *cdev = &client->dev;
1448 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
1449 dev_notice(cdev, "PERFORM : AF start\n");
1451 dev_info(cdev, "@@@ AF start\n");
1453 if (!is_focus(V4L2_FOCUS_AUTO_CONTINUOUS)) {
1454 if(state->focus.lock == 0)
1455 err = m5mo_set_lock(sd, 1); /* lock AE/AWB */
1456 if (!err) /* Execute Lens */
1457 err = m5mo_writeb(sd, M5MO_CATEGORY_LENS,
1458 M5MO_LENS_AF_START, 1);
1460 err = m5mo_writeb(sd, M5MO_CATEGORY_LENS, M5MO_LENS_AF_START,
1465 state->focus.focusing = true;
1466 state->focus.status = M5MO_AF_START;
1471 static int m5mo_set_af_stop(struct v4l2_subdev *sd)
1473 struct m5mo_state *state = to_state(sd);
1474 struct i2c_client *client = v4l2_get_subdevdata(sd);
1475 struct device *cdev = &client->dev;
1479 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
1480 dev_notice(cdev, "PERFORM : AF stop\n");
1482 dev_info(cdev, "@@@ AF stop\n");
1484 if (!is_focus(V4L2_FOCUS_AUTO_CONTINUOUS)) {
1485 /* Read lens status, and figure out */
1486 err = m5mo_readb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_STATUS, ®);
1487 if (!err && reg == 0x03) {
1489 err = m5mo_writeb(sd, M5MO_CATEGORY_LENS,
1490 M5MO_LENS_AF_START, 0x00);
1491 /* Check FACE Detection or MONITOR mode */
1493 err = m5mo_busy(sd, M5MO_CATEGORY_SYS,
1495 is_focus(V4L2_FOCUS_AUTO_FACE_DETECTION) ?
1498 dev_info(cdev, "@@@ Failed to wait changing[%s]\n",
1499 is_focus(V4L2_FOCUS_AUTO_FACE_DETECTION) ?
1500 "FACE detect" : "MONITOR mode");
1504 if(state->focus.lock == 1)
1505 err = m5mo_set_lock(sd, 0);
1507 err = m5mo_writeb(sd, M5MO_CATEGORY_LENS, M5MO_LENS_AF_START, 0x00);
1509 state->focus.status = M5MO_AF_STOP;
1514 static int m5mo_set_af_mode(struct v4l2_subdev *sd, int val)
1516 struct m5mo_state *state = to_state(sd);
1517 struct i2c_client *client = v4l2_get_subdevdata(sd);
1518 struct device *cdev = &client->dev;
1522 dev_info(cdev, "@@@ AF mode %d\n", val);
1524 if (val == state->focus.mode)
1527 err = m5mo_readb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_MODE, &old_mode);
1528 if (!err && old_mode != M5MO_MONITOR_MODE) {
1529 state->focus.needed = true;
1533 err = m5mo_writeb(sd, M5MO_CATEGORY_LENS, M5MO_LENS_AF_MODE,
1534 val == V4L2_FOCUS_AUTO_NORMAL ? 0x00 :
1535 val == V4L2_FOCUS_AUTO_MACRO ? 0x01 :
1536 val == V4L2_FOCUS_AUTO_CONTINUOUS ? 0x02 :
1537 val == V4L2_FOCUS_AUTO_FACE_DETECTION ? 0x03 : 0x04);
1539 state->focus.mode = val;
1544 static int m5mo_read_exif_info(struct v4l2_subdev *sd,
1545 u32 addr_num, u32 addr_den, u32 times,
1550 int ret = m5mo_readl(sd, M5MO_CATEGORY_EXIF, addr_num, &num);
1552 ret = m5mo_readl(sd, M5MO_CATEGORY_EXIF, addr_den, &den);
1556 *value = den == 0 ? 0 : num * times / den;
1561 static int m5mo_get_exif(struct v4l2_subdev *sd)
1563 struct m5mo_state *state = to_state(sd);
1564 u16 iso_std_values[] = { /* standard values */
1565 10, 12, 16, 20, 25, 32, 40, 50, 64, 80,
1566 100, 125, 160, 200, 250, 320, 400, 500, 640, 800,
1567 1000, 1250, 1600, 2000, 2500, 3200, 4000, 5000, 6400, 8000 };
1568 u16 iso_qtable[] = { /* quantization table */
1569 11, 14, 17, 22, 28, 35, 44, 56, 71, 89,
1570 112, 141, 178, 224, 282, 356, 449, 565, 712, 890,
1571 1122, 1414, 1782, 2245, 2828, 3564, 4490, 5657, 7127, 8909 };
1572 int num_flash, num_iso, i, err;
1575 err = m5mo_read_exif_info(sd,
1576 M5MO_EXIF_EXPTIME_NUM, M5MO_EXIF_EXPTIME_DEN,
1577 1000, &state->exif.exptime);
1578 if (!err) /* shutter speed */
1579 err = m5mo_read_exif_info(sd,
1580 M5MO_EXIF_TV_NUM, M5MO_EXIF_TV_DEN,
1581 M5MO_DEF_APEX_DEN, &state->exif.tv);
1582 if (!err) /* brightness */
1583 err = m5mo_read_exif_info(sd,
1584 M5MO_EXIF_BV_NUM, M5MO_EXIF_BV_DEN,
1585 M5MO_DEF_APEX_DEN, &state->exif.bv);
1586 if (!err) /* exposure */
1587 err = m5mo_read_exif_info(sd,
1588 M5MO_EXIF_EBV_NUM, M5MO_EXIF_EBV_DEN,
1589 M5MO_DEF_APEX_DEN, &state->exif.ebv);
1590 if (!err) /* flash */
1591 err = m5mo_readw(sd, M5MO_CATEGORY_EXIF, M5MO_EXIF_FLASH,
1594 err = m5mo_readw(sd, M5MO_CATEGORY_EXIF, M5MO_EXIF_ISO,
1597 state->exif.flash = (u16)num_flash;
1598 for (i = 0; i < sizeof(iso_qtable); i++) {
1599 if (num_iso <= iso_qtable[i]) {
1600 state->exif.iso = iso_std_values[i];
1610 static int m5mo_start_capture(struct v4l2_subdev *sd, int value)
1612 struct m5mo_state *state = to_state(sd);
1613 struct i2c_client *client = v4l2_get_subdevdata(sd);
1614 struct device *cdev = &client->dev;
1618 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
1619 dev_notice(cdev, "PERFORM : Shutter release lag\n");
1620 dev_notice(cdev, "PERFORM : Capture start\n");
1622 /* Clear Interrupt */
1623 err = m5mo_readb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_INT_FACTOR, ®);
1626 /* Enable Necessary Interrupt only */
1627 err = m5mo_writeb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_INT_EN, M5MO_INT_CAPTURE);
1631 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPCTRL, M5MO_CAPCTRL_FRM_SEL,
1633 #ifdef M5MO_POSTVIEW_SUPPORT
1634 /* JPEG(with header) + ThumbnailJPEG */
1636 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPPARM,
1637 M5MO_CAPPARM_YUVOUT_MAIN, 0x21);
1639 /* JPEG(with header) + ThumbnailJPEG + PostviewYUV */
1641 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPPARM,
1642 M5MO_CAPPARM_YUVOUT_MAIN, 0x10);
1645 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPCTRL, M5MO_CAPCTRL_TRANSFER,
1648 err = m5mo_wait(sd, M5MO_INT_CAPTURE, M5MO_TIMEOUT);
1650 err = m5mo_readl(sd, M5MO_CATEGORY_CAPCTRL, M5MO_CAPCTRL_IMG_SIZE,
1651 &state->jpeg.main_size);
1652 dev_info(cdev, "%s: jpeg main size = %d\n", __func__, state->jpeg.main_size);
1654 err = m5mo_readl(sd, M5MO_CATEGORY_CAPCTRL, M5MO_CAPCTRL_THUMB_SIZE,
1655 &state->jpeg.thumb_size);
1656 dev_info(cdev, "%s: jpeg thumb size = %d\n", __func__, state->jpeg.thumb_size);
1658 err = m5mo_get_exif(sd);
1660 /* succeeded capture, and get information */
1661 state->jpeg.main_offset = 0;
1662 state->jpeg.thumb_offset = M5MO_JPEG_MAXSIZE;
1663 state->jpeg.postview_offset = M5MO_JPEG_MAXSIZE +
1666 /* clear issued & unlock AE/AWB */
1667 state->isp.issued = 0;
1670 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
1671 dev_notice(cdev, "PERFORM : Capture end\n");
1676 static int m5mo_set_jpeg_quality(struct v4l2_subdev *sd, int value)
1678 struct m5mo_state *state = to_state(sd);
1681 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPPARM, M5MO_CAPPARM_JPEG_RATIO, 0x62);
1683 /* Normal 0x0a, Fine 0x05, Superfine 0x0 */
1684 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPPARM,
1685 M5MO_CAPPARM_JPEG_RATIO_OFS,
1686 value <= 65 ? 0x0a :
1687 value > 65 && value <= 75 ? 0x05 : 0x0);
1689 state->jpeg.quality = value;
1694 #if 0 /* unused control functions */
1695 static int m5mo_set_antishake(struct v4l2_subdev *sd, int val)
1699 ahs = (val == 1 ? 0x0E : 0x00);
1701 err = m5mo_writeb(sd, M5MO_CATEGORY_AE, M5MO_AE_EP_MODE_MON, ahs);
1703 err = m5mo_writeb(sd, M5MO_CATEGORY_AE, M5MO_AE_EP_MODE_CAP, ahs);
1708 static int m5mo_set_face_beauty(struct v4l2_subdev *sd, int val)
1710 struct m5mo_state *state = to_state(sd);
1713 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPPARM, M5MO_CAPPARM_AFB_CAP_EN,
1716 state->beauty_mode = val;
1721 static int m5mo_set_touch_auto_focus(struct v4l2_subdev *sd, int val)
1723 struct m5mo_state *state = to_state(sd);
1724 struct i2c_client *client = v4l2_get_subdevdata(sd);
1725 struct device *cdev = &client->dev;
1728 dev_info(cdev, "@@@ AF(Touch) %s\n", val ? "on" : "off");
1731 err = m5mo_set_af_mode(sd, V4L2_FOCUS_AUTO_RECTANGLE);
1733 err = m5mo_writew(sd, M5MO_CATEGORY_LENS,
1734 M5MO_LENS_AF_TOUCH_POSX,
1735 state->focus.pos_x);
1737 err = m5mo_writew(sd, M5MO_CATEGORY_LENS,
1738 M5MO_LENS_AF_TOUCH_POSY,
1739 state->focus.pos_y);
1742 state->focus.touch = val;
1748 static int m5mo_check_esd(struct v4l2_subdev *sd)
1750 struct i2c_client *client = v4l2_get_subdevdata(sd);
1751 struct device *cdev = &client->dev;
1756 err = m5mo_readb(sd, M5MO_CATEGORY_TEST, M5MO_TEST_ISP_PROCESS, &val);
1763 err = m5mo_wait(sd, M5MO_INT_MODE, M5MO_ESD_TIMEOUT);
1765 err = m5mo_readb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_ESD_INT,
1767 if (!err && (val & M5MO_INT_ESD))
1771 dev_info(cdev, "ESD is not detected\n");
1776 dev_info(cdev, "ESD shock is detected\n");
1780 static int m5mo_s_ctrl(struct v4l2_subdev *sd, struct v4l2_control *ctrl)
1782 struct m5mo_state *state = to_state(sd);
1783 struct i2c_client *client = v4l2_get_subdevdata(sd);
1784 struct device *cdev = &client->dev;
1785 struct v4l2_queryctrl qc = { 0, };
1786 int value = ctrl->value;
1789 if (unlikely(state->isp.bad_fw && ctrl->id != V4L2_CID_CAM_UPDATE_FW)) {
1790 dev_err(cdev, "\"Unknown\" state, please update F/W");
1795 err = m5mo_queryctrl(sd, &qc);
1797 dev_info(cdev, "s_ctrl: no CID[0x%08x] value[%d]. Just pass.\n",
1798 ctrl->id, ctrl->value);
1800 * After optimizing CID from SLP Platform, alive return
1804 return -ENOIOCTLCMD;*/
1810 case V4L2_CID_CAM_UPDATE_FW:
1811 if (ctrl->value == FW_MODE_DUMP)
1812 err = m5mo_dump_fw(sd);
1814 err = m5mo_check_fw(sd);
1817 /* dependent on SENSOR itself */
1818 case V4L2_CID_CAMERA_SENSOR_MODE:
1819 err = 0; /* FIXME */
1821 case V4L2_CID_CAM_DR:
1822 case V4L2_CID_CAMERA_WDR:
1823 err = m5mo_set_wdr(sd, value);
1825 case V4L2_CID_CAMERA_HDR:
1826 err = m5mo_set_hdr(sd, value);
1830 case V4L2_CID_CAMERA_FLASH_MODE:
1831 err = m5mo_set_flash(sd, value);
1834 /* Exposure & Scenemode stuff(ISO, Metering, Saturation, etc) */
1835 case V4L2_CID_CAMERA_ISO:
1836 err = m5mo_set_iso(sd, value);
1838 case V4L2_CID_CAMERA_METERING:
1839 err = m5mo_set_metering(sd, value);
1841 case V4L2_CID_EXPOSURE:
1842 err = m5mo_set_exposure(sd, value);
1844 case V4L2_CID_SATURATION:
1845 err = m5mo_set_saturation(sd, value);
1847 case V4L2_CID_SHARPNESS:
1848 err = m5mo_set_sharpness(sd, value);
1850 case V4L2_CID_WHITE_BALANCE_PRESET:
1851 err = m5mo_set_whitebalance(sd, value);
1853 case V4L2_CID_COLORFX:
1854 err = m5mo_set_effect(sd, value);
1856 case V4L2_CID_CAMERA_SCENE_MODE:
1857 err = m5mo_set_scene_mode(sd, value);
1860 case V4L2_CID_ZOOM_ABSOLUTE:
1861 case V4L2_CID_CAMERA_ZOOM:
1862 if (state->support_zoom == true) {
1863 dev_info(cdev, "%s: zoom level %d\n", __func__, value);
1864 err = m5mo_set_zoom(sd, value);
1866 dev_info(cdev, "%s: This resulution is not support zoom\n", __func__);
1871 case V4L2_CID_FOCUS_AUTO_RECTANGLE_LEFT:
1872 state->focus.pos_x = value;
1874 case V4L2_CID_FOCUS_AUTO_RECTANGLE_TOP:
1875 state->focus.pos_y = value;
1877 case V4L2_CID_FOCUS_AUTO_RECTANGLE_WIDTH:
1878 state->focus.width = value;
1880 case V4L2_CID_FOCUS_AUTO_RECTANGLE_HEIGHT:
1881 state->focus.height = value;
1883 case V4L2_CID_FOCUS_AUTO_MODE:
1884 if (value == V4L2_FOCUS_AUTO_MACRO)
1885 err = m5mo_set_af_mode(sd, V4L2_FOCUS_AUTO_MACRO);
1886 else if (value == V4L2_FOCUS_AUTO_CONTINUOUS)
1887 err = m5mo_set_af_mode(sd, V4L2_FOCUS_AUTO_CONTINUOUS);
1888 else if (value == V4L2_FOCUS_AUTO_FACE_DETECTION)
1889 err = m5mo_set_af_mode(sd, V4L2_FOCUS_AUTO_FACE_DETECTION);
1890 else if (value == V4L2_FOCUS_AUTO_RECTANGLE)
1891 err = m5mo_set_af_mode(sd, V4L2_FOCUS_AUTO_RECTANGLE);
1892 else /* V4L2_FOCUS_AUTO_NORMAL */
1893 err = m5mo_set_af_mode(sd, V4L2_FOCUS_AUTO_NORMAL);
1895 case V4L2_CID_CAMERA_SET_AUTO_FOCUS:
1898 if (state->focus.focusing != true)
1901 err = m5mo_set_af_stop(sd);
1903 state->focus.focusing = false;
1908 if (state->focus.focusing == false) {
1909 err = m5mo_set_af_start(sd);
1910 if (!err && !(is_focus(V4L2_FOCUS_AUTO_CONTINUOUS)))
1913 err = m5mo_get_af(sd);
1920 case V4L2_CID_CAMERA_CAPTURE:
1921 err = m5mo_start_capture(sd, value);
1923 case V4L2_CID_CAM_JPEG_QUALITY:
1924 err = m5mo_set_jpeg_quality(sd, value);
1926 case V4L2_CID_CAMERA_CHECK_ESD:
1927 err = m5mo_check_esd(sd);
1934 dev_dbg(cdev, "s_ctrl: CID[%s][0x%08x] PRIVATE[%d] val[%d] ret[%d]\n",
1935 v4l2_ctrl_get_name(ctrl->id), ctrl->id,
1936 ctrl->id - V4L2_CID_PRIVATE_BASE,
1941 static int m5mo_check_manufacturer_id(struct v4l2_subdev *sd)
1943 struct i2c_client *client = v4l2_get_subdevdata(sd);
1944 struct device *cdev = &client->dev;
1946 u32 addr[] = {0x1000AAAA, 0x10005554, 0x1000AAAA};
1952 u8 reset[] = {0x00, 0xF0};
1955 /* set manufacturer's ID read-mode */
1956 for (i = 0; i < 3; i++) {
1957 err = m5mo_mem_write(sd, 0x06, 2, addr[i], val[i]);
1962 /* read manufacturer's ID */
1963 err = m5mo_mem_read(sd, sizeof(id), 0x10000001, &id);
1965 /* reset manufacturer's ID read-mode */
1966 err = m5mo_mem_write(sd, 0x06, sizeof(reset), 0x10000000, reset);
1970 dev_info(cdev, "%#x\n", id);
1975 static int m5mo_program_fw(struct v4l2_subdev *sd,
1976 u8 *buf, u32 addr, u32 unit, u32 count, u8 id)
1978 struct i2c_client *client = v4l2_get_subdevdata(sd);
1979 struct device *cdev = &client->dev;
1981 u32 intram_unit = SZ_4K;
1982 int i, j, retries, err = 0;
1984 if (unit == SZ_64K && id != 0x01)
1987 for (i = 0; i < unit*count; i += unit) {
1988 /* Set Flash ROM memory address */
1989 err = m5mo_writel(sd, M5MO_CATEGORY_FLASH,
1990 M5MO_FLASH_ADDR, addr + i);
1994 /* Erase FLASH ROM entire memory */
1995 err = m5mo_writeb(sd, M5MO_CATEGORY_FLASH,
1996 M5MO_FLASH_ERASE, erase);
2000 /* Response while sector-erase is operating */
2004 err = m5mo_readb(sd, M5MO_CATEGORY_FLASH,
2005 M5MO_FLASH_ERASE, &val);
2009 } while (val == erase && retries++ < M5MO_I2C_VERIFY);
2012 dev_info(cdev, "failed to erase sector\n");
2016 /* Set FLASH ROM programming size */
2017 err = m5mo_writew(sd, M5MO_CATEGORY_FLASH, M5MO_FLASH_BYTE,
2018 unit == SZ_64K ? 0 : unit);
2022 /* Clear M-5MoLS internal RAM */
2023 err = m5mo_writeb(sd, M5MO_CATEGORY_FLASH,
2024 M5MO_FLASH_RAM_CLEAR, 0x01);
2028 /* Set Flash ROM programming address */
2029 err = m5mo_writel(sd, M5MO_CATEGORY_FLASH,
2030 M5MO_FLASH_ADDR, addr + i);
2034 /* Send programmed firmware */
2035 for (j = 0; j < unit; j += intram_unit) {
2036 err = m5mo_mem_write(sd, 0x04, intram_unit,
2037 M5MO_INT_RAM_BASE_ADDR + j, buf + i + j);
2043 /* Start Programming */
2044 err = m5mo_writeb(sd, M5MO_CATEGORY_FLASH, M5MO_FLASH_WR, 0x01);
2048 /* Confirm programming has been completed */
2052 err = m5mo_readb(sd, M5MO_CATEGORY_FLASH,
2053 M5MO_FLASH_WR, &val);
2057 } while (val && retries++ < M5MO_I2C_VERIFY);
2060 dev_info(cdev, "failed to program\n");
2068 static int m5mo_load_fw(struct v4l2_subdev *sd)
2070 struct i2c_client *client = v4l2_get_subdevdata(sd);
2071 struct device *dev = &client->adapter->dev;
2072 struct device *cdev = &client->dev;
2073 const struct firmware *fentry;
2074 u8 sensor_ver[M5MO_FW_VER_LEN] = {0, };
2075 u8 *buf = NULL, val, id;
2080 mm_segment_t old_fs;
2082 int fw_requested = 1;
2087 fp = filp_open(M5MO_FW_PATH, O_RDONLY, 0);
2089 dev_err(cdev, "failed to open %s, err %ld\n",
2090 M5MO_FW_PATH, PTR_ERR(fp));
2095 fsize = fp->f_path.dentry->d_inode->i_size;
2097 dev_info(cdev, "start, file path %s, size %ld Bytes\n",
2098 M5MO_FW_PATH, fsize);
2100 buf = vmalloc(fsize);
2102 dev_info(cdev, "failed to allocate memory\n");
2107 nread = vfs_read(fp, (char __user *)buf, fsize, &fp->f_pos);
2108 if (nread != fsize) {
2109 dev_info(cdev, "failed to read firmware file, %ld Bytes\n", nread);
2117 #endif /* SDCARD_FW */
2118 m5mo_get_sensor_fw_version(sd, sensor_ver);
2120 if (sensor_ver[0] == 'T')
2121 err = request_firmware(&fentry, M5MOT_FW_REQUEST_PATH, dev);
2123 err = request_firmware(&fentry, M5MOO_FW_REQUEST_PATH, dev);
2126 dev_info(cdev, "request_firmware falied\n");
2131 dev_info(cdev, "start, size %d Bytes\n", fentry->size);
2132 buf = (u8 *)fentry->data;
2136 #endif /* SDCARD_FW */
2140 err = m5mo_mem_write(sd, 0x04, sizeof(val), 0x50000308, &val);
2142 dev_info(cdev, "i2c falied, err %d\n", err);
2146 id = m5mo_check_manufacturer_id(sd);
2148 dev_info(cdev, "i2c falied, err %d\n", id);
2152 /* select flash memory */
2153 err = m5mo_writeb(sd, M5MO_CATEGORY_FLASH,
2154 M5MO_FLASH_SEL, id == 0x01 ? 0x00 : 0x01);
2156 dev_info(cdev, "i2c falied, err %d\n", err);
2160 /* program FLSH ROM */
2161 err = m5mo_program_fw(sd, buf, M5MO_FLASH_BASE_ADDR, SZ_64K, 31, id);
2165 offset = SZ_64K * 31;
2167 err = m5mo_program_fw(sd,
2168 buf + offset, M5MO_FLASH_BASE_ADDR + offset, SZ_8K, 4, id);
2170 err = m5mo_program_fw(sd,
2171 buf + offset, M5MO_FLASH_BASE_ADDR + offset, SZ_4K, 8, id);
2174 dev_info(cdev, "end\n");
2178 if (!fw_requested) {
2180 filp_close(fp, current->files);
2183 #endif /* SDCARD_FW */
2188 * v4l2_subdev_video_ops
2190 static const struct m5mo_frmsizeenum *m5mo_get_frmsize
2191 (const struct m5mo_frmsizeenum *frmsizes, int num_entries, int index)
2195 for (i = 0; i < num_entries; i++) {
2196 if (frmsizes[i].index == index)
2197 return &frmsizes[i];
2203 static int m5mo_set_frmsize(struct v4l2_subdev *sd)
2205 struct m5mo_state *state = to_state(sd);
2206 struct i2c_client *client = v4l2_get_subdevdata(sd);
2207 struct device *cdev = &client->dev;
2211 if (!is_format(V4L2_PIX_FMT_MODE_CAPTURE)) {
2212 err = m5mo_set_mode(sd, M5MO_PARMSET_MODE);
2214 err = m5mo_readb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_MODE,
2217 err = m5mo_writeb(sd, M5MO_CATEGORY_PARM,
2218 M5MO_PARM_MON_SIZE, state->preview->reg_val);
2219 if (!err && state->zoom) {
2221 * Zoom position returns to 1 when the monitor size
2224 dev_info(cdev, "%s: zoom level %d\n", __func__, state->zoom);
2225 err = m5mo_set_zoom(sd, state->zoom);
2228 err = m5mo_writeb(sd, M5MO_CATEGORY_CAPPARM,
2229 M5MO_CAPPARM_MAIN_IMG_SIZE, state->capture->reg_val);
2231 dev_info(cdev, "s_fmt: set_framesize %s %dx%d\n",
2232 is_format(V4L2_PIX_FMT_MODE_CAPTURE) ?
2234 is_format(V4L2_PIX_FMT_MODE_CAPTURE) ?
2235 state->capture->width : state->preview->width,
2236 is_format(V4L2_PIX_FMT_MODE_CAPTURE) ?
2237 state->capture->height : state->preview->height);
2243 static int m5mo_s_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *ffmt)
2245 struct m5mo_state *state = to_state(sd);
2246 struct i2c_client *client = v4l2_get_subdevdata(sd);
2247 struct device *cdev = &client->dev;
2248 const struct m5mo_frmsizeenum **frmsize;
2249 u32 width = ffmt->width;
2250 u32 height = ffmt->height;
2256 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
2257 dev_notice(cdev, "PERFORM : S_FMT start\n");
2259 if (unlikely(state->isp.bad_fw)) {
2260 dev_info(cdev, "\"Unknown\" state, please update F/W");
2264 if (ffmt->width < ffmt->height) {
2265 tmp_width = ffmt->height;
2266 height = ffmt->width;
2270 if (ffmt->colorspace == V4L2_COLORSPACE_JPEG) {
2271 state->format_mode = V4L2_PIX_FMT_MODE_CAPTURE;
2272 frmsize = &state->capture;
2274 state->format_mode = V4L2_PIX_FMT_MODE_PREVIEW;
2275 frmsize = &state->preview;
2276 err = m5mo_set_mode(sd, M5MO_PARMSET_MODE);
2281 old_index = *frmsize ? (*frmsize)->index : -1;
2284 if (!is_format(V4L2_PIX_FMT_MODE_CAPTURE)) {
2285 num_entries = ARRAY_SIZE(preview_frmsizes);
2286 for (i = 0; i < num_entries; i++) {
2287 if (width == preview_frmsizes[i].width &&
2288 height == preview_frmsizes[i].height) {
2289 *frmsize = &preview_frmsizes[i];
2293 if (preview_frmsizes[i].index == M5MO_PREVIEW_1080P)
2294 state->support_zoom = false;
2296 state->support_zoom = true;
2298 num_entries = ARRAY_SIZE(capture_frmsizes);
2299 for (i = 0; i < num_entries; i++) {
2300 if (width == capture_frmsizes[i].width &&
2301 height == capture_frmsizes[i].height) {
2302 *frmsize = &capture_frmsizes[i];
2306 if (*frmsize != NULL) {
2307 state->wide_res = capture_frmsizes[i].wide_res;
2308 dev_info(cdev, "%s: capture size: width = %d, height = %d, wide_res = %d\n",
2309 __func__, width, height, state->wide_res);
2311 dev_info(cdev, "%s: Not supported resolution. Set default\n", __func__);
2312 state->wide_res = 0;
2316 if (*frmsize == NULL) {
2317 dev_info(cdev, "s_fmt: invalid size %dx%d\n", width, height);
2318 *frmsize = state->format_mode != V4L2_PIX_FMT_MODE_CAPTURE ?
2319 m5mo_get_frmsize(preview_frmsizes, num_entries,
2321 m5mo_get_frmsize(capture_frmsizes, num_entries,
2325 dev_info(cdev, "s_fmt: %dx%d\n", (*frmsize)->width, (*frmsize)->height);
2327 if (old_index != (*frmsize)->index)
2328 m5mo_set_frmsize(sd);
2330 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
2331 dev_notice(cdev, "PERFORM : S_FMT end\n");
2336 static int m5mo_g_parm(struct v4l2_subdev *sd, struct v4l2_streamparm *a)
2338 struct m5mo_state *state = to_state(sd);
2339 struct i2c_client *client = v4l2_get_subdevdata(sd);
2340 struct device *cdev = &client->dev;
2342 dev_info(cdev, "g_parm: FPS %d\n", state->fps);
2343 if(state->fps == 0){
2344 a->parm.capture.timeperframe.numerator = state->fps;
2345 a->parm.capture.timeperframe.denominator = 1;
2347 a->parm.capture.timeperframe.numerator = 1;
2348 a->parm.capture.timeperframe.denominator = state->fps;
2354 #define M5MO_PARM_MON_FPS 0x02
2356 static int m5mo_s_parm(struct v4l2_subdev *sd, struct v4l2_streamparm *a)
2358 struct m5mo_state *state = to_state(sd);
2359 struct i2c_client *client = v4l2_get_subdevdata(sd);
2360 struct device *cdev = &client->dev;
2361 u32 denom = a->parm.capture.timeperframe.denominator;
2362 u32 numer = a->parm.capture.timeperframe.numerator;
2365 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
2366 dev_notice(cdev, "PERFORM : S_PARM start\n");
2368 if (denom >= 1 && numer == 1) {
2369 fps = denom / numer;
2372 * supported fps : 8(7.5), 10, 12, 15, 20, 21, 22, 23, 24, 30
2374 if (fps > 0 && fps <= 9){ fps = 8; state->fps_reg = 0x06;}
2375 else if (fps > 9 && fps <= 11){ fps = 10; state->fps_reg = 0x05;}
2376 else if (fps > 10 && fps <= 14){ fps = 12; state->fps_reg = 0x04;}
2377 else if (fps > 14 && fps <= 18){ fps = 15; state->fps_reg = 0x03;}
2378 else if (fps > 18 && fps <= 20){ fps = 20; state->fps_reg = 0x08;}
2379 else if (fps > 20 && fps <= 21){ fps = 21; state->fps_reg = 0x09;}
2380 else if (fps > 21 && fps <= 22){ fps = 22; state->fps_reg = 0x0A;}
2381 else if (fps > 22 && fps <= 23){ fps = 23; state->fps_reg = 0x0B;}
2382 else if (fps > 23 && fps <= 27){ fps = 24; state->fps_reg = 0x07;}
2383 else{fps = 30; state->fps_reg = 0x02;}
2385 } else if (denom == 1 && numer == 0){
2388 return -EINVAL; /* Wrong fps */
2390 if (state->fps != fps) {
2392 state->need_setfps = true;
2395 dev_info(cdev, "s_parm: denom %d, numer %d, FPS idx %08x\n",
2398 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
2399 dev_notice(cdev, "PERFORM : S_PARM end\n");
2404 static int m5mo_enum_framesizes(struct v4l2_subdev *sd,
2405 struct v4l2_frmsizeenum *fsize)
2407 struct m5mo_state *state = to_state(sd);
2410 err = m5mo_readb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_MODE, &old_mode);
2415 * The camera interface should read this value, this is the resolution
2416 * at which the sensor would provide framedata to the camera i/f
2417 * In case of image capture,
2418 * this returns the default camera resolution (VGA)
2420 if (!is_format(V4L2_PIX_FMT_MODE_CAPTURE)) {
2421 if (state->preview == NULL || state->preview->index < 0)
2424 fsize->type = V4L2_FRMSIZE_TYPE_DISCRETE;
2425 fsize->discrete.width = state->preview->width;
2426 fsize->discrete.height = state->preview->height;
2428 if (state->capture == NULL || state->capture->index < 0)
2431 fsize->type = V4L2_FRMSIZE_TYPE_DISCRETE;
2432 fsize->discrete.width = state->capture->width;
2433 fsize->discrete.height = state->capture->height;
2439 static int m5mo_s_stream_preview(struct v4l2_subdev *sd, int enable)
2441 struct m5mo_state *state = to_state(sd);
2442 struct i2c_client *client = v4l2_get_subdevdata(sd);
2443 struct device *cdev = &client->dev;
2446 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
2447 dev_notice(cdev, "PERFORM : Preview enable start.\n");
2450 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
2451 dev_notice(cdev, "PERFORM : Preview disable\n");
2457 * Removed contents - no more needs.
2458 * VTmode : M5MO_CATEGORY_AE, M5MO_AE_EP_MODE_MON, 0x11
2459 * Dataline check mode : M5MO_CATEGORY_TEST,
2460 * M5MO_TEST_OUTPUT_YCO_TEST_DATA, 0x01
2462 if (state->need_setfps == true) {
2463 err = m5mo_set_mode(sd, M5MO_PARMSET_MODE);
2466 * Changing Frame Rate is able to be only for MONITOR mode.
2467 * Don't call for CAPTURE mode. The Capture outcome can be
2470 if (state->fps == 30) {
2471 err = m5mo_writeb(sd, M5MO_CATEGORY_PARM, M5MO_PARM_HDMOVIE, 0x01);
2473 err = m5mo_writeb(sd, M5MO_CATEGORY_PARM, M5MO_PARM_HDMOVIE, 0x00);
2474 err = m5mo_writeb(sd, M5MO_CATEGORY_PARM, M5MO_PARM_MON_FPS, state->fps_reg);
2477 state->need_setfps = false;
2480 if(state->focus.lock == 1)
2481 err = m5mo_set_lock(sd, 0);
2484 if (!err && state->focus.needed) {
2485 state->focus.needed = false;
2487 /* Set Normal AF Mode */
2488 if (!is_focus(V4L2_FOCUS_AUTO_MACRO) &&
2489 !is_focus(V4L2_FOCUS_AUTO_CONTINUOUS) &&
2490 !is_focus(V4L2_FOCUS_AUTO_NORMAL))
2492 err = m5mo_writeb(sd, M5MO_CATEGORY_LENS, M5MO_LENS_AF_MODE,
2493 is_focus(V4L2_FOCUS_AUTO_MACRO) ? 0x01 :
2494 is_focus(V4L2_FOCUS_AUTO_CONTINUOUS) ? 0x02 :
2495 0x04); /* default AUTO */
2497 is_focus(V4L2_FOCUS_AUTO_MACRO) ? V4L2_FOCUS_AUTO_MACRO :
2498 is_focus(V4L2_FOCUS_AUTO_CONTINUOUS) ?
2499 V4L2_FOCUS_AUTO_CONTINUOUS :
2500 V4L2_FOCUS_AUTO_RECTANGLE; /* default TOUCH(AUTO) */
2501 state->focus.status = M5MO_AF_STOP;
2504 err = m5mo_set_mode(sd, M5MO_MONITOR_MODE);
2508 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
2509 dev_notice(cdev, "PERFORM : Preview %s end\n", enable ? "enable" : "disable");
2514 static int m5mo_s_stream_capture(struct v4l2_subdev *sd, int enable)
2516 struct m5mo_state *state = to_state(sd);
2517 struct i2c_client *client = v4l2_get_subdevdata(sd);
2518 struct device *cdev = &client->dev;
2522 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
2523 dev_notice(cdev, "PERFORM : Capture %s. mode change start\n", enable ? "enable" : "disable");
2526 return m5mo_set_mode(sd, M5MO_PARMSET_MODE);
2529 * As support team, it must be changing to STILLCAP mode (streamon
2530 * subdev call) before MIPI setup in FIMC driver.
2532 state->isp.issued = 0; /* clear issued & lock AE/AWB */
2534 /* Clear Interrupt */
2535 err = m5mo_readb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_INT_FACTOR, ®);
2538 /* Enable Necessary Interrupt only */
2539 err = m5mo_writeb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_INT_EN, M5MO_INT_CAPTURE);
2543 err = m5mo_set_mode(sd, M5MO_STILLCAP_MODE);
2545 err = m5mo_wait(sd, M5MO_INT_CAPTURE, M5MO_TIMEOUT);
2547 #if defined(CONFIG_VIDEO_M5MO_DEBUG)
2548 dev_notice(cdev, "PERFORM : Capture %s. mode change end\n", enable ? "enable" : "disable");
2553 static int m5mo_s_stream(struct v4l2_subdev *sd, int enable)
2555 struct m5mo_state *state = to_state(sd);
2556 struct i2c_client *client = v4l2_get_subdevdata(sd);
2557 struct device *cdev = &client->dev;
2560 if (unlikely(state->isp.bad_fw)) {
2561 dev_info(cdev, "\"Unknown\" state, please update F/W");
2566 case STREAM_MODE_CAM_ON:
2567 case STREAM_MODE_CAM_OFF:
2568 switch (state->format_mode) {
2569 case V4L2_PIX_FMT_MODE_CAPTURE:
2570 dev_info(cdev, "s_stream: capture %s\n",
2571 enable == STREAM_MODE_CAM_ON ? "on" : "off");
2572 err = m5mo_s_stream_capture(sd,
2573 enable == STREAM_MODE_CAM_ON);
2576 dev_info(cdev, "s_stream: preview %s\n",
2577 enable == STREAM_MODE_CAM_ON ? "on" : "off");
2578 err = m5mo_s_stream_preview(sd,
2579 enable == STREAM_MODE_CAM_ON);
2585 dev_info(cdev, "invalid stream option, %d\n", enable);
2592 static int m5mo_check_version(struct v4l2_subdev *sd)
2594 struct m5mo_state *state = to_state(sd);
2595 struct i2c_client *client = v4l2_get_subdevdata(sd);
2596 struct device *cdev = &client->dev;
2600 for (i = 0; i < 6; i++) {
2601 ret = m5mo_readb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_USER_VER, &val);
2602 state->exif.unique_id[i] = (char)val;
2604 state->exif.unique_id[i] = '\0';
2606 dev_info(cdev, "*************************************\n");
2607 dev_info(cdev, "F/W Version: %s\n", state->exif.unique_id);
2608 dev_info(cdev, "Binary Released: %s %s\n", __DATE__, __TIME__);
2609 dev_info(cdev, "*************************************\n");
2614 static int m5mo_init_param(struct v4l2_subdev *sd)
2616 struct m5mo_state *state = to_state(sd);
2619 err = m5mo_writeb(sd, M5MO_CATEGORY_SYS, M5MO_SYS_INT_EN,
2620 M5MO_INT_CAPTURE | M5MO_INT_SOUND);
2622 err = m5mo_writeb(sd, M5MO_CATEGORY_PARM, M5MO_PARM_OUT_SEL, 0x02);
2624 err = m5mo_writeb(sd, M5MO_CATEGORY_PARM, M5MO_PARM_MON_FPS, 0x01);
2628 err = m5mo_writel(sd, M5MO_CATEGORY_CAPPARM,
2629 M5MO_CAPPARM_THUMB_JPEG_MAX, M5MO_THUMB_MAXSIZE);
2631 err = m5mo_writeb(sd, M5MO_CATEGORY_FD, M5MO_FD_CTL, 0x0);
2633 err = m5mo_writeb(sd, M5MO_CATEGORY_PARM, M5MO_PARM_HDMOVIE, 0x00);
2635 err = m5mo_writeb(sd, M5MO_CATEGORY_AE, M5MO_AE_FLICKER, 0x02);
2637 err = m5mo_writeb(sd, M5MO_CATEGORY_AE, M5MO_AE_EV_BIAS, 0x1e);
2641 static int m5mo_init(struct v4l2_subdev *sd, u32 val)
2643 struct m5mo_state *state = to_state(sd);
2646 /* Default state values */
2647 state->preview = NULL;
2648 state->capture = NULL;
2649 state->format_mode = V4L2_PIX_FMT_MODE_PREVIEW;
2650 state->isp.bad_fw = 0;
2651 state->fps = 0; /* auto */
2653 /* Set default controls */
2654 memset(&state->focus, 0, sizeof(state->focus));
2655 memset(&state->jpeg, 0, sizeof(state->jpeg));
2656 memset(&state->exif, 0, sizeof(state->exif));
2657 state->flash_mode = FLASH_MODE_OFF;
2658 state->colorfx = V4L2_COLORFX_NONE;
2659 state->wdr = WDR_OFF;
2661 state->iso = ISO_AUTO;
2662 state->metering = METERING_MATRIX;
2663 state->exposure = EV_DEFAULT + 4;
2664 state->saturation = SATURATION_DEFAULT;
2665 state->sharpness = SHARPNESS_DEFAULT;
2666 state->wb_preset = WHITE_BALANCE_AUTO;
2667 state->scenemode = SCENE_MODE_BASE;
2668 state->zoom = ZOOM_LEVEL_0;
2669 state->support_zoom = true;
2670 state->need_setfps = true;
2672 /* start camera program(parallel FLASH ROM) */
2673 err = m5mo_writeb(sd, M5MO_CATEGORY_FLASH, M5MO_FLASH_CAM_START, 0x01);
2675 err = m5mo_wait(sd, M5MO_INT_MODE, M5MO_TIMEOUT);
2677 err = m5mo_check_version(sd); /* check up F/W version */
2681 return m5mo_init_param(sd);
2684 static int m5mo_s_power(struct v4l2_subdev *sd, int on)
2686 struct i2c_client *client = v4l2_get_subdevdata(sd);
2687 const struct m5mo_platform_data *pdata = client->dev.platform_data;
2688 struct device *dev = &client->dev;
2689 struct m5mo_state *state = to_state(sd);
2695 /* Only when disable sensor */
2696 ret = m5mo_set_af_softlanding(sd);
2699 if (pdata->flash_power && state->flash_mode != FLASH_MODE_OFF)
2700 ret = pdata->flash_power(0, dev);
2707 static const struct v4l2_subdev_core_ops m5mo_core_ops = {
2708 .init = m5mo_init, /* initializing API */
2709 .load_fw = m5mo_load_fw,
2710 .queryctrl = m5mo_queryctrl,
2711 .g_ctrl = m5mo_g_ctrl,
2712 .s_ctrl = m5mo_s_ctrl,
2713 .s_power = m5mo_s_power, /* Used only when release subdev */
2716 static const struct v4l2_subdev_video_ops m5mo_video_ops = {
2717 .s_mbus_fmt = m5mo_s_fmt,
2718 .g_parm = m5mo_g_parm,
2719 .s_parm = m5mo_s_parm,
2720 .enum_framesizes = m5mo_enum_framesizes,
2721 .s_stream = m5mo_s_stream,
2724 static const struct v4l2_subdev_ops m5mo_ops = {
2725 .core = &m5mo_core_ops,
2726 .video = &m5mo_video_ops,
2729 static ssize_t m5mo_camera_type_show(struct device *dev,
2730 struct device_attribute *attr, char *buf)
2732 char type[] = "SONY_M5MO_NONE";
2734 return sprintf(buf, "%s\n", type);
2737 static ssize_t m5mo_camera_fw_show(struct device *dev,
2738 struct device_attribute *attr, char *buf)
2740 struct i2c_client *client = to_i2c_client(dev);
2741 struct v4l2_subdev *sd = i2c_get_clientdata(client);
2742 struct m5mo_state *state = to_state(sd);
2744 return sprintf(buf, "%s\n", state->fw_version);
2747 static DEVICE_ATTR(camera_type, S_IRUGO, m5mo_camera_type_show, NULL);
2748 static DEVICE_ATTR(camera_fw, S_IRUGO, m5mo_camera_fw_show, NULL);
2750 #ifdef CONFIG_VIDEO_M5MO_I2C_DEBUG
2751 static ssize_t m5mo_i2c_debug_r(struct device *dev,
2752 struct device_attribute *attr,
2755 struct i2c_client *client = to_i2c_client(dev);
2756 struct v4l2_subdev *sd = i2c_get_clientdata(client);
2757 struct m5mo_state *state = to_state(sd);
2761 ret = m5mo_read(sd, 1, (u8)state->dbg.category,
2762 (u8)state->dbg.command, &value);
2764 state->dbg.value = (u8)value;
2766 return snprintf(buf, PAGE_SIZE, "%02x\n", state->dbg.value);
2769 static ssize_t m5mo_i2c_debug_w(struct device *dev,
2770 struct device_attribute *attr,
2771 char *buf, size_t count)
2773 struct i2c_client *client = to_i2c_client(dev);
2774 struct v4l2_subdev *sd = i2c_get_clientdata(client);
2775 struct m5mo_state *state = to_state(sd);
2776 int category, command, value;
2778 sscanf(buf, "%02x %02x %02x", &category, &command, &value);
2779 state->dbg.category = (u8)category;
2780 state->dbg.command = (u8)command;
2781 state->dbg.value = (u8)value;
2783 m5mo_write(sd, 1, (u8)state->dbg.category,
2784 (u8)state->dbg.command, (u8)state->dbg.value);
2786 return strnlen(buf, PAGE_SIZE);
2789 static DEVICE_ATTR(i2c_debug, S_IRUGO | S_IWUGO,
2790 m5mo_i2c_debug_r, m5mo_i2c_debug_w);
2791 #endif /* CONFIG_VIDEO_M5MO_I2C_DEBUG */
2795 * Fetching platform data is being done with s_config subdev call.
2796 * In probe routine, we just register subdev device
2798 static int __devinit m5mo_probe(struct i2c_client *client,
2799 const struct i2c_device_id *id)
2801 struct m5mo_state *state;
2802 struct device *cdev = &client->dev;
2803 struct v4l2_subdev *sd;
2805 const struct m5mo_platform_data *pdata =
2806 client->dev.platform_data;
2809 state = kzalloc(sizeof(struct m5mo_state), GFP_KERNEL);
2814 strcpy(sd->name, M5MO_DRIVER_NAME);
2816 /* Registering subdev */
2817 v4l2_i2c_subdev_init(sd, client, &m5mo_ops);
2819 if (device_create_file(&client->dev, &dev_attr_camera_type) < 0) {
2820 dev_info(cdev, "Failed to create device file, %s\n",
2821 dev_attr_camera_type.attr.name);
2824 if (device_create_file(&client->dev, &dev_attr_camera_fw) < 0) {
2825 dev_info(cdev, "Failed to create device file, %s\n",
2826 dev_attr_camera_fw.attr.name);
2829 #ifdef CONFIG_VIDEO_M5MO_I2C_DEBUG
2830 if (device_create_file(&client->dev, &dev_attr_i2c_debug) < 0) {
2831 dev_info(cdev, "Failed to create device file, %s\n",
2832 dev_attr_i2c_debug.attr.name);
2836 /* wait queue initialize */
2837 init_waitqueue_head(&state->isp.wait);
2839 if (pdata->config_isp_irq)
2840 pdata->config_isp_irq();
2842 err = request_irq(pdata->irq,
2843 m5mo_isp_isr, IRQF_TRIGGER_RISING, "m5mo isp", sd);
2845 dev_info(cdev, "failed to request irq\n");
2848 state->isp.irq = pdata->irq;
2849 state->isp.issued = 0;
2854 static int __devexit m5mo_remove(struct i2c_client *client)
2856 struct v4l2_subdev *sd = i2c_get_clientdata(client);
2857 struct m5mo_state *state = to_state(sd);
2860 #ifdef CONFIG_VIDEO_M5MO_I2C_DEBUG
2861 device_remove_file(&client->dev, &dev_attr_i2c_debug);
2863 device_remove_file(&client->dev, &dev_attr_camera_type);
2864 device_remove_file(&client->dev, &dev_attr_camera_fw);
2866 if (state->isp.irq > 0)
2867 free_irq(state->isp.irq, sd);
2869 v4l2_device_unregister_subdev(sd);
2871 kfree(state->fw_version);
2877 static const struct i2c_device_id m5mo_id[] = {
2878 { M5MO_DRIVER_NAME, 0 },
2881 MODULE_DEVICE_TABLE(i2c, m5mo_id);
2883 static struct i2c_driver m5mo_i2c_driver = {
2885 .name = M5MO_DRIVER_NAME,
2887 .probe = m5mo_probe,
2888 .remove = __devexit_p(m5mo_remove),
2889 .id_table = m5mo_id,
2892 static int __init m5mo_mod_init(void)
2894 return i2c_add_driver(&m5mo_i2c_driver);
2897 static void __exit m5mo_mod_exit(void)
2899 i2c_del_driver(&m5mo_i2c_driver);
2901 module_init(m5mo_mod_init);
2902 module_exit(m5mo_mod_exit);
2905 MODULE_AUTHOR("Goeun Lee <ge.lee@samsung.com>");
2906 MODULE_DESCRIPTION("driver for Fusitju M5MO LS 8MP camera");
2907 MODULE_LICENSE("GPL");