X-Git-Url: http://plrg.eecs.uci.edu/git/?a=blobdiff_plain;f=drivers%2Fmedia%2Fvideo%2Fsiv120b.c;h=6bc4b92ea13c1b2f90eb6064dc8c065513671f26;hb=e82146650ea5de8205f8890eaf4cb98615c51d9a;hp=ade9562072ac79684cf19747c9e8bbda8b0f2570;hpb=a01580d71e50e345388faabf6939673cd1bae7ed;p=firefly-linux-kernel-4.4.55.git diff --git a/drivers/media/video/siv120b.c b/drivers/media/video/siv120b.c index ade9562072ac..6bc4b92ea13c 100755 --- a/drivers/media/video/siv120b.c +++ b/drivers/media/video/siv120b.c @@ -20,7 +20,7 @@ o* Driver for MT9M001 CMOS Image Sensor from Micron #include #include #include -#include +#include static int debug; module_param(debug, int, S_IRUGO|S_IWUSR); @@ -30,7 +30,7 @@ module_param(debug, int, S_IRUGO|S_IWUSR); printk(KERN_WARNING fmt , ## arg); } while (0) #define SENSOR_TR(format, ...) printk(KERN_ERR format, ## __VA_ARGS__) -#define SENSOR_DG(format, ...) dprintk(0, format, ## __VA_ARGS__) +#define SENSOR_DG(format, ...) dprintk(1, format, ## __VA_ARGS__) #define _CONS(a,b) a##b @@ -54,7 +54,7 @@ module_param(debug, int, S_IRUGO|S_IWUSR); #define SENSOR_INIT_WIDTH 640 /* Sensor pixel size for sensor_init_data array */ #define SENSOR_INIT_HEIGHT 480 #define SENSOR_INIT_WINSEQADR sensor_vga -#define SENSOR_INIT_PIXFMT V4L2_PIX_FMT_YUYV +#define SENSOR_INIT_PIXFMT V4L2_MBUS_FMT_YUYV8_2X8 #define CONFIG_SENSOR_WhiteBalance 0 #define CONFIG_SENSOR_Brightness 0 @@ -65,7 +65,7 @@ module_param(debug, int, S_IRUGO|S_IWUSR); #define CONFIG_SENSOR_DigitalZoom 0 #define CONFIG_SENSOR_Focus 0 #define CONFIG_SENSOR_Exposure 0 -#define CONFIG_SENSOR_Flash 0 +#define CONFIG_SENSOR_Flash 1 #define CONFIG_SENSOR_Mirror 0 #define CONFIG_SENSOR_Flip 0 @@ -90,12 +90,28 @@ module_param(debug, int, S_IRUGO|S_IWUSR); #define SENSOR_NAME_STRING(a) STR(CONS(SENSOR_NAME, a)) #define SENSOR_NAME_VARFUN(a) CONS(SENSOR_NAME, a) +#define SENSOR_AF_IS_ERR (0x00<<0) +#define SENSOR_AF_IS_OK (0x01<<0) +#define SENSOR_INIT_IS_ERR (0x00<<28) +#define SENSOR_INIT_IS_OK (0x01<<28) struct reginfo { u8 reg; u8 val; }; +//flash off in fixed time to prevent from too hot , zyc +struct flash_timer{ + struct soc_camera_device *icd; + struct hrtimer timer; +}; +static enum hrtimer_restart flash_off_func(struct hrtimer *timer); + +static struct flash_timer flash_off_timer; +//for user defined if user want to customize the series , zyc +#ifdef CONFIG_SIV120B_USER_DEFINED_SERIES +#include "siv120b_user_series.c" +#else /* init 640X480 VGA */ static struct reginfo sensor_init_data[] = { @@ -391,14 +407,16 @@ static struct reginfo sensor_qcif[] = { {0x00,0x00} }; - +#endif static struct reginfo sensor_ClrFmt_YUYV[]= { + {0x00,0x00} }; static struct reginfo sensor_ClrFmt_UYVY[]= { + {0x00,0x00} }; @@ -787,6 +805,7 @@ static struct reginfo sensor_Effect_Negative[] = {0xb8,0x00}, }; +#if 0 static struct reginfo sensor_Effect_Bluish[] = { // Bluish -- aqua @@ -796,7 +815,7 @@ static struct reginfo sensor_Effect_Bluish[] = {0xb8,0x60}, }; - +#endif static struct reginfo sensor_Effect_Green[] = { // Greenish @@ -970,7 +989,7 @@ static struct reginfo sensor_Zoom3[] = }; static struct reginfo *sensor_ZoomSeqe[] = {sensor_Zoom0, sensor_Zoom1, sensor_Zoom2, sensor_Zoom3, NULL,}; #endif -static const struct v4l2_querymenu sensor_menus[] = +static struct v4l2_querymenu sensor_menus[] = { #if CONFIG_SENSOR_WhiteBalance { .id = V4L2_CID_DO_WHITE_BALANCE, .index = 0, .name = "auto", .reserved = 0, }, { .id = V4L2_CID_DO_WHITE_BALANCE, .index = 1, .name = "incandescent", .reserved = 0,}, @@ -994,7 +1013,7 @@ static const struct v4l2_querymenu sensor_menus[] = #endif }; -static const struct v4l2_queryctrl sensor_controls[] = +static struct v4l2_queryctrl sensor_controls[] = { #if CONFIG_SENSOR_WhiteBalance { @@ -1167,8 +1186,12 @@ static int sensor_suspend(struct soc_camera_device *icd, pm_message_t pm_msg); static int sensor_resume(struct soc_camera_device *icd); static int sensor_set_bus_param(struct soc_camera_device *icd,unsigned long flags); static unsigned long sensor_query_bus_param(struct soc_camera_device *icd); +#if CONFIG_SENSOR_Effect static int sensor_set_effect(struct soc_camera_device *icd, const struct v4l2_queryctrl *qctrl, int value); +#endif +#if CONFIG_SENSOR_WhiteBalance static int sensor_set_whiteBalance(struct soc_camera_device *icd, const struct v4l2_queryctrl *qctrl, int value); +#endif static int sensor_deactivate(struct i2c_client *client); static struct soc_camera_ops sensor_ops = @@ -1183,16 +1206,28 @@ static struct soc_camera_ops sensor_ops = .num_menus = ARRAY_SIZE(sensor_menus), }; -#define COL_FMT(_name, _depth, _fourcc, _colorspace) \ - { .name = _name, .depth = _depth, .fourcc = _fourcc, \ - .colorspace = _colorspace } +/* only one fixed colorspace per pixelcode */ +struct sensor_datafmt { + enum v4l2_mbus_pixelcode code; + enum v4l2_colorspace colorspace; +}; + +/* Find a data format by a pixel code in an array */ +static const struct sensor_datafmt *sensor_find_datafmt( + enum v4l2_mbus_pixelcode code, const struct sensor_datafmt *fmt, + int n) +{ + int i; + for (i = 0; i < n; i++) + if (fmt[i].code == code) + return fmt + i; -#define JPG_FMT(_name, _depth, _fourcc) \ - COL_FMT(_name, _depth, _fourcc, V4L2_COLORSPACE_JPEG) + return NULL; +} -static const struct soc_camera_data_format sensor_colour_formats[] = { - JPG_FMT(SENSOR_NAME_STRING(UYVY), 16, V4L2_PIX_FMT_UYVY), - JPG_FMT(SENSOR_NAME_STRING(YUYV), 16, V4L2_PIX_FMT_YUYV), +static const struct sensor_datafmt sensor_colour_fmts[] = { + {V4L2_MBUS_FMT_UYVY8_2X8, V4L2_COLORSPACE_JPEG}, + {V4L2_MBUS_FMT_YUYV8_2X8, V4L2_COLORSPACE_JPEG} }; typedef struct sensor_info_priv_s @@ -1212,7 +1247,8 @@ typedef struct sensor_info_priv_s unsigned char mirror; /* HFLIP */ unsigned char flip; /* VFLIP */ unsigned int winseqe_cur_addr; - unsigned int pixfmt; + struct sensor_datafmt fmt; + unsigned int funmodule_state; } sensor_info_priv_t; @@ -1421,6 +1457,11 @@ static int sensor_ioctrl(struct soc_camera_device *icd,enum rk29sensor_power_cmd if (sensor->sensor_io_request && sensor->sensor_io_request->sensor_ioctrl) { sensor->sensor_io_request->sensor_ioctrl(icd->pdev,Cam_Flash, on); + if(on){ + //flash off after 2 secs + hrtimer_cancel(&(flash_off_timer.timer)); + hrtimer_start(&(flash_off_timer.timer),ktime_set(0, 800*1000*1000),HRTIMER_MODE_REL); + } } break; } @@ -1434,12 +1475,20 @@ sensor_power_end: return ret; } +static enum hrtimer_restart flash_off_func(struct hrtimer *timer){ + struct flash_timer *fps_timer = container_of(timer, struct flash_timer, timer); + sensor_ioctrl(fps_timer->icd,Sensor_Flash,0); + SENSOR_DG("%s %s !!!!!!",SENSOR_NAME_STRING(),__FUNCTION__); + return 0; + +} static int sensor_init(struct v4l2_subdev *sd, u32 val) { - struct i2c_client *client = sd->priv; + struct i2c_client *client = v4l2_get_subdevdata(sd); struct soc_camera_device *icd = client->dev.platform_data; struct sensor *sensor = to_sensor(client); const struct v4l2_queryctrl *qctrl; + const struct sensor_datafmt *fmt; int ret, i; SENSOR_DG("\n%s..%s.. \n",SENSOR_NAME_STRING(),__FUNCTION__); @@ -1460,7 +1509,7 @@ static int sensor_init(struct v4l2_subdev *sd, u32 val) // goto sensor_INIT_ERR; // } - mdelay(5); //delay 5 microseconds +// mdelay(5); //delay 5 microseconds for(i = 0; i < sizeof(sensor_init_data)/2;i++){ @@ -1477,11 +1526,15 @@ static int sensor_init(struct v4l2_subdev *sd, u32 val) // printk("read from reg[0x%x] 0x%x\n",sensor_init_data[i].reg,tmp); } sensor_task_lock(client,0); - - icd->user_width = SENSOR_INIT_WIDTH; - icd->user_height = SENSOR_INIT_HEIGHT; + sensor->info_priv.winseqe_cur_addr = (int)SENSOR_INIT_WINSEQADR; - sensor->info_priv.pixfmt = SENSOR_INIT_PIXFMT; + fmt = sensor_find_datafmt(SENSOR_INIT_PIXFMT,sensor_colour_fmts, ARRAY_SIZE(sensor_colour_fmts)); + if (!fmt) { + SENSOR_TR("error: %s initial array colour fmts is not support!!",SENSOR_NAME_STRING()); + ret = -EINVAL; + goto sensor_INIT_ERR; + } + sensor->info_priv.fmt = *fmt; /* sensor sensor information for initialization */ qctrl = soc_camera_find_qctrl(&sensor_ops, V4L2_CID_DO_WHITE_BALANCE); @@ -1528,12 +1581,16 @@ static int sensor_init(struct v4l2_subdev *sd, u32 val) qctrl = soc_camera_find_qctrl(&sensor_ops, V4L2_CID_FLASH); if (qctrl) sensor->info_priv.flash = qctrl->default_value; + flash_off_timer.icd = icd; + flash_off_timer.timer.function = flash_off_func; #endif SENSOR_DG("\n%s..%s.. icd->width = %d.. icd->height %d\n",SENSOR_NAME_STRING(),((val == 0)?__FUNCTION__:"sensor_reinit"),icd->user_width,icd->user_height); - + sensor->info_priv.funmodule_state |= SENSOR_INIT_IS_OK; return 0; sensor_INIT_ERR: + sensor->info_priv.funmodule_state &= ~SENSOR_INIT_IS_OK; + sensor_task_lock(client,0); sensor_deactivate(client); return ret; } @@ -1541,6 +1598,7 @@ sensor_INIT_ERR: static int sensor_deactivate(struct i2c_client *client) { struct soc_camera_device *icd = client->dev.platform_data; + struct sensor *sensor = to_sensor(client); SENSOR_DG("\n%s..%s.. Enter\n",SENSOR_NAME_STRING(),__FUNCTION__); @@ -1551,6 +1609,7 @@ static int sensor_deactivate(struct i2c_client *client) icd->user_width = SENSOR_INIT_WIDTH; icd->user_height = SENSOR_INIT_HEIGHT; msleep(100); + sensor->info_priv.funmodule_state &= ~SENSOR_INIT_IS_OK; return 0; } static struct reginfo sensor_power_down_sequence[]= @@ -1614,80 +1673,88 @@ static unsigned long sensor_query_bus_param(struct soc_camera_device *icd) return soc_camera_apply_sensor_flags(icl, flags); } -static int sensor_g_fmt(struct v4l2_subdev *sd, struct v4l2_format *f) +static int sensor_g_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *mf) { - struct i2c_client *client = sd->priv; + struct i2c_client *client = v4l2_get_subdevdata(sd); struct soc_camera_device *icd = client->dev.platform_data; struct sensor *sensor = to_sensor(client); - struct v4l2_pix_format *pix = &f->fmt.pix; - pix->width = icd->user_width; - pix->height = icd->user_height; - pix->pixelformat = sensor->info_priv.pixfmt; - pix->field = V4L2_FIELD_NONE; - pix->colorspace = V4L2_COLORSPACE_JPEG; + mf->width = icd->user_width; + mf->height = icd->user_height; + mf->code = sensor->info_priv.fmt.code; + mf->colorspace = sensor->info_priv.fmt.colorspace; + mf->field = V4L2_FIELD_NONE; return 0; } -static bool sensor_fmt_capturechk(struct v4l2_subdev *sd, struct v4l2_format *f) +#if 0 +static bool sensor_fmt_capturechk(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *mf) { bool ret = false; - if ((f->fmt.pix.width == 1024) && (f->fmt.pix.height == 768)) { + if ((mf->width == 1024) && (mf->height == 768)) { ret = true; - } else if ((f->fmt.pix.width == 1280) && (f->fmt.pix.height == 1024)) { + } else if ((mf->width == 1280) && (mf->height == 1024)) { ret = true; - } else if ((f->fmt.pix.width == 1600) && (f->fmt.pix.height == 1200)) { + } else if ((mf->width == 1600) && (mf->height == 1200)) { ret = true; - } else if ((f->fmt.pix.width == 2048) && (f->fmt.pix.height == 1536)) { + } else if ((mf->width == 2048) && (mf->height == 1536)) { ret = true; - } else if ((f->fmt.pix.width == 2592) && (f->fmt.pix.height == 1944)) { + } else if ((mf->width == 2592) && (mf->height == 1944)) { ret = true; } if (ret == true) - SENSOR_DG("%s %dx%d is capture format\n", __FUNCTION__, f->fmt.pix.width, f->fmt.pix.height); + SENSOR_DG("%s %dx%d is capture format\n", __FUNCTION__, mf->width, mf->height); return ret; } -static bool sensor_fmt_videochk(struct v4l2_subdev *sd, struct v4l2_format *f) +static bool sensor_fmt_videochk(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *mf) { bool ret = false; - if ((f->fmt.pix.width == 1280) && (f->fmt.pix.height == 720)) { + if ((mf->width == 1280) && (mf->height == 720)) { ret = true; - } else if ((f->fmt.pix.width == 1920) && (f->fmt.pix.height == 1080)) { + } else if ((mf->width == 1920) && (mf->height == 1080)) { ret = true; } if (ret == true) - SENSOR_DG("%s %dx%d is video format\n", __FUNCTION__, f->fmt.pix.width, f->fmt.pix.height); + SENSOR_DG("%s %dx%d is video format\n", __FUNCTION__, mf->width, mf->height); return ret; } -static int sensor_s_fmt(struct v4l2_subdev *sd, struct v4l2_format *f) +#endif +static int sensor_s_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *mf) { - struct i2c_client *client = sd->priv; + struct i2c_client *client = v4l2_get_subdevdata(sd); struct sensor *sensor = to_sensor(client); - struct v4l2_pix_format *pix = &f->fmt.pix; + const struct sensor_datafmt *fmt; struct reginfo *winseqe_set_addr=NULL; char readval; int ret=0, set_w,set_h,i; - if (sensor->info_priv.pixfmt != pix->pixelformat) { - switch (pix->pixelformat) + fmt = sensor_find_datafmt(mf->code, sensor_colour_fmts, + ARRAY_SIZE(sensor_colour_fmts)); + if (!fmt) { + ret = -EINVAL; + goto sensor_s_fmt_end; + } + + if (sensor->info_priv.fmt.code != mf->code) { + switch (mf->code) { - case V4L2_PIX_FMT_YUYV: + case V4L2_MBUS_FMT_YUYV8_2X8: { - //winseqe_set_addr = sensor_ClrFmt_YUYV; + winseqe_set_addr = sensor_ClrFmt_YUYV; sensor_read(client, 0x3a, &readval); sensor_write(client,0x3a, readval&0xf7); sensor_read(client,0x3d,&readval); sensor_write(client,0x3d,readval&0xfe); break; } - case V4L2_PIX_FMT_UYVY: + case V4L2_MBUS_FMT_UYVY8_2X8: { - //winseqe_set_addr = sensor_ClrFmt_UYVY; + winseqe_set_addr = sensor_ClrFmt_UYVY; sensor_read(client, 0x3a, &readval); sensor_write(client,0x3a, readval|0x08); sensor_read(client,0x3d,&readval); @@ -1699,19 +1766,16 @@ static int sensor_s_fmt(struct v4l2_subdev *sd, struct v4l2_format *f) } if (winseqe_set_addr != NULL) { sensor_write_array(client, winseqe_set_addr); - sensor->info_priv.pixfmt = pix->pixelformat; - - SENSOR_DG("%s Pixelformat(0x%x) set success!\n", SENSOR_NAME_STRING(),pix->pixelformat); + sensor->info_priv.fmt.code = mf->code; + sensor->info_priv.fmt.colorspace= mf->colorspace; + SENSOR_DG("%s v4l2_mbus_code:%d set success!\n", SENSOR_NAME_STRING(),mf->code); } else { - SENSOR_TR("%s Pixelformat(0x%x) is invalidate!\n", SENSOR_NAME_STRING(),pix->pixelformat); - // sensor->info_priv.pixfmt = pix->pixelformat; - - // SENSOR_DG("%s Pixelformat(0x%x) set success!\n", SENSOR_NAME_STRING(),pix->pixelformat); + SENSOR_TR("%s v4l2_mbus_code:%d is invalidate!\n", SENSOR_NAME_STRING(),mf->code); } } - set_w = pix->width; - set_h = pix->height; + set_w = mf->width; + set_h = mf->height; if (((set_w <= 176) && (set_h <= 144)) && sensor_qcif[0].reg) { @@ -1742,7 +1806,7 @@ static int sensor_s_fmt(struct v4l2_subdev *sd, struct v4l2_format *f) winseqe_set_addr = SENSOR_INIT_WINSEQADR; /* ddl@rock-chips.com : Sensor output smallest size if isn't support app */ set_w = SENSOR_INIT_WIDTH; set_h = SENSOR_INIT_HEIGHT; - SENSOR_TR("\n %s..%s Format is Invalidate. pix->width = %d.. pix->height = %d\n",SENSOR_NAME_STRING(),__FUNCTION__,pix->width,pix->height); + SENSOR_TR("\n %s..%s Format is Invalidate. pix->width = %d.. pix->height = %d\n",SENSOR_NAME_STRING(),__FUNCTION__,mf->width,mf->height); } if ((int)winseqe_set_addr != sensor->info_priv.winseqe_cur_addr) @@ -1766,44 +1830,74 @@ static int sensor_s_fmt(struct v4l2_subdev *sd, struct v4l2_format *f) SENSOR_DG("\n %s .. Current Format is validate. icd->width = %d.. icd->height %d\n",SENSOR_NAME_STRING(),set_w,set_h); } - pix->width = set_w; - pix->height = set_h; + mf->width = set_w; + mf->height = set_h; sensor_s_fmt_end: return ret; } -static int sensor_try_fmt(struct v4l2_subdev *sd, struct v4l2_format *f) +static int sensor_try_fmt(struct v4l2_subdev *sd, struct v4l2_mbus_framefmt *mf) { - struct v4l2_pix_format *pix = &f->fmt.pix; - bool bayer = pix->pixelformat == V4L2_PIX_FMT_UYVY || - pix->pixelformat == V4L2_PIX_FMT_YUYV; - - /* - * With Bayer format enforce even side lengths, but let the user play - * with the starting pixel - */ - - if (pix->height > SENSOR_MAX_HEIGHT) - pix->height = SENSOR_MAX_HEIGHT; - else if (pix->height < SENSOR_MIN_HEIGHT) - pix->height = SENSOR_MIN_HEIGHT; - else if (bayer) - pix->height = ALIGN(pix->height, 2); - - if (pix->width > SENSOR_MAX_WIDTH) - pix->width = SENSOR_MAX_WIDTH; - else if (pix->width < SENSOR_MIN_WIDTH) - pix->width = SENSOR_MIN_WIDTH; - else if (bayer) - pix->width = ALIGN(pix->width, 2); + struct i2c_client *client = v4l2_get_subdevdata(sd); + struct sensor *sensor = to_sensor(client); + const struct sensor_datafmt *fmt; + int ret = 0,set_w,set_h; + + fmt = sensor_find_datafmt(mf->code, sensor_colour_fmts, + ARRAY_SIZE(sensor_colour_fmts)); + if (fmt == NULL) { + fmt = &sensor->info_priv.fmt; + mf->code = fmt->code; + } + + if (mf->height > SENSOR_MAX_HEIGHT) + mf->height = SENSOR_MAX_HEIGHT; + else if (mf->height < SENSOR_MIN_HEIGHT) + mf->height = SENSOR_MIN_HEIGHT; + + if (mf->width > SENSOR_MAX_WIDTH) + mf->width = SENSOR_MAX_WIDTH; + else if (mf->width < SENSOR_MIN_WIDTH) + mf->width = SENSOR_MIN_WIDTH; + + set_w = mf->width; + set_h = mf->height; - return 0; + if (((set_w <= 176) && (set_h <= 144)) && sensor_qcif[0].reg) + { + set_w = 176; + set_h = 144; + } + else if (((set_w <= 320) && (set_h <= 240)) && sensor_qvga[0].reg) + { + set_w = 320; + set_h = 240; + } + else if (((set_w <= 352) && (set_h<= 288)) && sensor_cif[0].reg) + { + set_w = 352; + set_h = 288; + } + else if (((set_w <= 640) && (set_h <= 480)) && sensor_vga[0].reg) + { + set_w = 640; + set_h = 480; + } + else + { + set_w = SENSOR_INIT_WIDTH; + set_h = SENSOR_INIT_HEIGHT; + } + mf->width = set_w; + mf->height = set_h; + mf->colorspace = fmt->colorspace; + + return ret; } - static int sensor_g_chip_ident(struct v4l2_subdev *sd, struct v4l2_dbg_chip_ident *id) { - struct i2c_client *client = sd->priv; + struct i2c_client *client = v4l2_get_subdevdata(sd); if (id->match.type != V4L2_CHIP_MATCH_I2C_ADDR) return -EINVAL; @@ -2028,7 +2122,7 @@ static int sensor_set_whiteBalance(struct soc_camera_device *icd, const struct v } #endif #if CONFIG_SENSOR_DigitalZoom -static int sensor_set_digitalzoom(struct soc_camera_device *icd, const struct v4l2_queryctrl *qctrl, int *value) +static int sensor_set_digitalzoom(struct soc_camera_device *icd, const struct v4l2_queryctrl *qctrl, int value) { struct i2c_client *client = to_i2c_client(to_soc_camera_control(icd)); struct sensor *sensor = to_sensor(client); @@ -2042,29 +2136,29 @@ static int sensor_set_digitalzoom(struct soc_camera_device *icd, const struct v4 digitalzoom_cur = sensor->info_priv.digitalzoom; digitalzoom_total = qctrl_info->maximum; - if ((*value > 0) && (digitalzoom_cur >= digitalzoom_total)) + if ((value > 0) && (digitalzoom_cur >= digitalzoom_total)) { SENSOR_TR("%s digitalzoom is maximum - %x\n", SENSOR_NAME_STRING(), digitalzoom_cur); return -EINVAL; } - if ((*value < 0) && (digitalzoom_cur <= qctrl_info->minimum)) + if ((value < 0) && (digitalzoom_cur <= qctrl_info->minimum)) { SENSOR_TR("%s digitalzoom is minimum - %x\n", SENSOR_NAME_STRING(), digitalzoom_cur); return -EINVAL; } - if ((*value > 0) && ((digitalzoom_cur + *value) > digitalzoom_total)) + if ((value > 0) && ((digitalzoom_cur + value) > digitalzoom_total)) { - *value = digitalzoom_total - digitalzoom_cur; + value = digitalzoom_total - digitalzoom_cur; } - if ((*value < 0) && ((digitalzoom_cur + *value) < 0)) + if ((value < 0) && ((digitalzoom_cur + value) < 0)) { - *value = 0 - digitalzoom_cur; + value = 0 - digitalzoom_cur; } - digitalzoom_cur += *value; + digitalzoom_cur += value; if (sensor_ZoomSeqe[digitalzoom_cur] != NULL) { @@ -2073,7 +2167,7 @@ static int sensor_set_digitalzoom(struct soc_camera_device *icd, const struct v4 SENSOR_TR("%s..%s WriteReg Fail.. \n",SENSOR_NAME_STRING(), __FUNCTION__); return -EINVAL; } - SENSOR_DG("%s..%s : %x\n",SENSOR_NAME_STRING(),__FUNCTION__, *value); + SENSOR_DG("%s..%s : %x\n",SENSOR_NAME_STRING(),__FUNCTION__, value); return 0; } @@ -2100,7 +2194,7 @@ static int sensor_set_flash(struct soc_camera_device *icd, const struct v4l2_que static int sensor_g_control(struct v4l2_subdev *sd, struct v4l2_control *ctrl) { - struct i2c_client *client = sd->priv; + struct i2c_client *client = v4l2_get_subdevdata(sd); struct sensor *sensor = to_sensor(client); const struct v4l2_queryctrl *qctrl; @@ -2159,9 +2253,9 @@ static int sensor_g_control(struct v4l2_subdev *sd, struct v4l2_control *ctrl) static int sensor_s_control(struct v4l2_subdev *sd, struct v4l2_control *ctrl) { - struct i2c_client *client = sd->priv; - struct sensor *sensor = to_sensor(client); - struct soc_camera_device *icd = client->dev.platform_data; + //ruct i2c_client *client = v4l2_get_subdevdata(sd); + //ruct sensor *sensor = to_sensor(client); + //ruct soc_camera_device *icd = client->dev.platform_data; const struct v4l2_queryctrl *qctrl; @@ -2449,7 +2543,7 @@ static int sensor_s_ext_control(struct soc_camera_device *icd, struct v4l2_ext_c static int sensor_g_ext_controls(struct v4l2_subdev *sd, struct v4l2_ext_controls *ext_ctrl) { - struct i2c_client *client = sd->priv; + struct i2c_client *client = v4l2_get_subdevdata(sd); struct soc_camera_device *icd = client->dev.platform_data; int i, error_cnt=0, error_idx=-1; @@ -2474,7 +2568,7 @@ static int sensor_g_ext_controls(struct v4l2_subdev *sd, struct v4l2_ext_control static int sensor_s_ext_controls(struct v4l2_subdev *sd, struct v4l2_ext_controls *ext_ctrl) { - struct i2c_client *client = sd->priv; + struct i2c_client *client = v4l2_get_subdevdata(sd); struct soc_camera_device *icd = client->dev.platform_data; int i, error_cnt=0, error_idx=-1; @@ -2543,9 +2637,6 @@ static int sensor_video_probe(struct soc_camera_device *icd, goto sensor_video_probe_err; } - icd->formats = sensor_colour_formats; - icd->num_formats = ARRAY_SIZE(sensor_colour_formats); - return 0; sensor_video_probe_err: @@ -2555,7 +2646,7 @@ sensor_video_probe_err: static long sensor_ioctl(struct v4l2_subdev *sd, unsigned int cmd, void *arg) { - struct i2c_client *client = sd->priv; + struct i2c_client *client = v4l2_get_subdevdata(sd); struct soc_camera_device *icd = client->dev.platform_data; struct sensor *sensor = to_sensor(client); int ret = 0; @@ -2576,12 +2667,17 @@ static long sensor_ioctl(struct v4l2_subdev *sd, unsigned int cmd, void *arg) { sensor->sensor_io_request = (struct rk29camera_platform_data*)arg; if (sensor->sensor_io_request != NULL) { - if (sensor->sensor_io_request->gpio_res[0].dev_name && - (strcmp(sensor->sensor_io_request->gpio_res[0].dev_name, dev_name(icd->pdev)) == 0)) { - sensor->sensor_gpio_res = (struct rk29camera_gpio_res*)&sensor->sensor_io_request->gpio_res[0]; - } else if (sensor->sensor_io_request->gpio_res[1].dev_name && - (strcmp(sensor->sensor_io_request->gpio_res[1].dev_name, dev_name(icd->pdev)) == 0)) { - sensor->sensor_gpio_res = (struct rk29camera_gpio_res*)&sensor->sensor_io_request->gpio_res[1]; + sensor->sensor_gpio_res = NULL; + for (i=0; isensor_io_request->gpio_res[i].dev_name && + (strcmp(sensor->sensor_io_request->gpio_res[i].dev_name, dev_name(icd->pdev)) == 0)) { + sensor->sensor_gpio_res = (struct rk29camera_gpio_res*)&sensor->sensor_io_request->gpio_res[i]; + } + } + if (sensor->sensor_gpio_res == NULL) { + SENSOR_TR("%s %s obtain gpio resource failed when RK29_CAM_SUBDEV_IOREQUEST \n",SENSOR_NAME_STRING(),__FUNCTION__); + ret = -EINVAL; + goto sensor_ioctl_end; } } else { SENSOR_TR("%s %s RK29_CAM_SUBDEV_IOREQUEST fail\n",SENSOR_NAME_STRING(),__FUNCTION__); @@ -2595,11 +2691,18 @@ static long sensor_ioctl(struct v4l2_subdev *sd, unsigned int cmd, void *arg) if (sensor->sensor_gpio_res->gpio_flash == INVALID_GPIO) { for (i = 0; i < icd->ops->num_controls; i++) { if (V4L2_CID_FLASH == icd->ops->controls[i].id) { - memset((char*)&icd->ops->controls[i],0x00,sizeof(struct v4l2_queryctrl)); + //memset((char*)&icd->ops->controls[i],0x00,sizeof(struct v4l2_queryctrl)); + sensor_controls[i].id=0xffff; } } sensor->info_priv.flash = 0xff; SENSOR_DG("%s flash gpio is invalidate!\n",SENSOR_NAME_STRING()); + }else{ //two cameras are the same,need to deal diffrently ,zyc + for (i = 0; i < icd->ops->num_controls; i++) { + if(0xffff == icd->ops->controls[i].id){ + sensor_controls[i].id=V4L2_CID_FLASH; + } + } } } #endif @@ -2615,6 +2718,15 @@ sensor_ioctl_end: return ret; } +static int sensor_enum_fmt(struct v4l2_subdev *sd, unsigned int index, + enum v4l2_mbus_pixelcode *code) +{ + if (index >= ARRAY_SIZE(sensor_colour_fmts)) + return -EINVAL; + + *code = sensor_colour_fmts[index].code; + return 0; +} static struct v4l2_subdev_core_ops sensor_subdev_core_ops = { .init = sensor_init, .g_ctrl = sensor_g_control, @@ -2626,9 +2738,10 @@ static struct v4l2_subdev_core_ops sensor_subdev_core_ops = { }; static struct v4l2_subdev_video_ops sensor_subdev_video_ops = { - .s_fmt = sensor_s_fmt, - .g_fmt = sensor_g_fmt, - .try_fmt = sensor_try_fmt, + .s_mbus_fmt = sensor_s_fmt, + .g_mbus_fmt = sensor_g_fmt, + .try_mbus_fmt = sensor_try_fmt, + .enum_mbus_fmt = sensor_enum_fmt, }; static struct v4l2_subdev_ops sensor_subdev_ops = { @@ -2671,7 +2784,7 @@ static int sensor_probe(struct i2c_client *client, /* Second stage probe - when a capture adapter is there */ icd->ops = &sensor_ops; - icd->y_skip_top = 0; + sensor->info_priv.fmt = sensor_colour_fmts[0]; #if CONFIG_SENSOR_I2C_NOSCHED atomic_set(&sensor->tasklock_cnt,0); #endif @@ -2683,6 +2796,7 @@ static int sensor_probe(struct i2c_client *client, kfree(sensor); sensor = NULL; } + hrtimer_init(&(flash_off_timer.timer), CLOCK_MONOTONIC, HRTIMER_MODE_REL); SENSOR_DG("\n%s..%s..%d ret = %x \n",__FUNCTION__,__FILE__,__LINE__,ret); return ret; }