diff options
author | Mauro Carvalho Chehab <mchehab@infradead.org> | 2006-04-24 11:28:23 -0300 |
---|---|---|
committer | Mauro Carvalho Chehab <mchehab@infradead.org> | 2006-04-24 11:28:23 -0300 |
commit | dba498eafc72039f1c6f29001c830d23bd8fe193 (patch) | |
tree | b935b18ecced8e414a64e9d83645b36b51c02c9f /linux/drivers | |
parent | 795652e2cf756c5cfa9b4cecb3f066b8ea01eb08 (diff) | |
download | mediapointer-dvb-s2-dba498eafc72039f1c6f29001c830d23bd8fe193.tar.gz mediapointer-dvb-s2-dba498eafc72039f1c6f29001c830d23bd8fe193.tar.bz2 |
ZC0301 driver updates
From: Luca Risolia <luca.risolia@studio.unibo.it>
ZC0301 driver updates:
- Add support for PB-0330 image sensor
- Generic documentation cleanups and updates
Signed-off-by: Luca Risolia <luca.risolia@studio.unibo.it>
Signed-off-by: Mauro Carvalho Chehab <mchehab@infradead.org>
Diffstat (limited to 'linux/drivers')
-rw-r--r-- | linux/drivers/media/video/zc0301/Kconfig | 6 | ||||
-rw-r--r-- | linux/drivers/media/video/zc0301/Makefile | 2 | ||||
-rw-r--r-- | linux/drivers/media/video/zc0301/zc0301.h | 6 | ||||
-rw-r--r-- | linux/drivers/media/video/zc0301/zc0301_core.c | 166 | ||||
-rw-r--r-- | linux/drivers/media/video/zc0301/zc0301_pas202bcb.c | 20 | ||||
-rw-r--r-- | linux/drivers/media/video/zc0301/zc0301_pb0330.c | 187 | ||||
-rw-r--r-- | linux/drivers/media/video/zc0301/zc0301_sensor.h | 32 |
7 files changed, 311 insertions, 108 deletions
diff --git a/linux/drivers/media/video/zc0301/Kconfig b/linux/drivers/media/video/zc0301/Kconfig index 115833e4f..a859a6920 100644 --- a/linux/drivers/media/video/zc0301/Kconfig +++ b/linux/drivers/media/video/zc0301/Kconfig @@ -1,9 +1,9 @@ config USB_ZC0301 - tristate "USB ZC0301 Image Processor and Control Chip support" + tristate "USB ZC0301[P] Image Processor and Control Chip support" depends on USB && VIDEO_V4L1 ---help--- - Say Y here if you want support for cameras based on the ZC0301 - Image Processor and Control Chip. + Say Y here if you want support for cameras based on the ZC0301 or + ZC0301P Image Processors and Control Chips. See <file:Documentation/video4linux/zc0301.txt> for more info. diff --git a/linux/drivers/media/video/zc0301/Makefile b/linux/drivers/media/video/zc0301/Makefile index d749199d8..d9e6d97fa 100644 --- a/linux/drivers/media/video/zc0301/Makefile +++ b/linux/drivers/media/video/zc0301/Makefile @@ -1,3 +1,3 @@ -zc0301-objs := zc0301_core.o zc0301_pas202bcb.o +zc0301-objs := zc0301_core.o zc0301_pb0330.o zc0301_pas202bcb.o obj-$(CONFIG_USB_ZC0301) += zc0301.o diff --git a/linux/drivers/media/video/zc0301/zc0301.h b/linux/drivers/media/video/zc0301/zc0301.h index 6959c980a..aca383d39 100644 --- a/linux/drivers/media/video/zc0301/zc0301.h +++ b/linux/drivers/media/video/zc0301/zc0301.h @@ -158,7 +158,7 @@ do { \ dev_info(&cam->usbdev->dev, fmt "\n", ## args); \ else if ((level) >= 3) \ dev_info(&cam->usbdev->dev, "[%s:%d] " fmt "\n", \ - __FUNCTION__, __LINE__ , ## args); \ + __FUNCTION__, __LINE__ , ## args); \ } \ } while (0) # define KDBG(level, fmt, args...) \ @@ -168,7 +168,7 @@ do { \ pr_info("zc0301: " fmt "\n", ## args); \ else if ((level) == 3) \ pr_debug("zc0301: [%s:%d] " fmt "\n", __FUNCTION__, \ - __LINE__ , ## args); \ + __LINE__ , ## args); \ } \ } while (0) # define V4LDBG(level, name, cmd) \ @@ -185,7 +185,7 @@ do { \ #undef PDBG #define PDBG(fmt, args...) \ dev_info(&cam->usbdev->dev, "[%s:%d] " fmt "\n", \ - __FUNCTION__, __LINE__ , ## args) + __FUNCTION__, __LINE__ , ## args) #undef PDBGG #define PDBGG(fmt, args...) do {;} while(0) /* placeholder */ diff --git a/linux/drivers/media/video/zc0301/zc0301_core.c b/linux/drivers/media/video/zc0301/zc0301_core.c index 0fad39754..6e34f3d2f 100644 --- a/linux/drivers/media/video/zc0301/zc0301_core.c +++ b/linux/drivers/media/video/zc0301/zc0301_core.c @@ -48,12 +48,12 @@ /*****************************************************************************/ #define ZC0301_MODULE_NAME "V4L2 driver for ZC0301 " \ - "Image Processor and Control Chip" + "Image Processor and Control Chip" #define ZC0301_MODULE_AUTHOR "(C) 2006 Luca Risolia" #define ZC0301_AUTHOR_EMAIL "<luca.risolia@studio.unibo.it>" #define ZC0301_MODULE_LICENSE "GPL" -#define ZC0301_MODULE_VERSION "1:1.03" -#define ZC0301_MODULE_VERSION_CODE KERNEL_VERSION(1, 0, 3) +#define ZC0301_MODULE_VERSION "1:1.04" +#define ZC0301_MODULE_VERSION_CODE KERNEL_VERSION(1, 0, 4) /*****************************************************************************/ @@ -67,67 +67,67 @@ MODULE_LICENSE(ZC0301_MODULE_LICENSE); static short video_nr[] = {[0 ... ZC0301_MAX_DEVICES-1] = -1}; module_param_array(video_nr, short, NULL, 0444); MODULE_PARM_DESC(video_nr, - "\n<-1|n[,...]> Specify V4L2 minor mode number." - "\n -1 = use next available (default)" - "\n n = use minor number n (integer >= 0)" - "\nYou can specify up to " - __MODULE_STRING(ZC0301_MAX_DEVICES) " cameras this way." - "\nFor example:" - "\nvideo_nr=-1,2,-1 would assign minor number 2 to" - "\nthe second registered camera and use auto for the first" - "\none and for every other camera." - "\n"); - -static short force_munmap[] = {[0 ... ZC0301_MAX_DEVICES-1] = - ZC0301_FORCE_MUNMAP}; + "\n<-1|n[,...]> Specify V4L2 minor mode number." + "\n -1 = use next available (default)" + "\n n = use minor number n (integer >= 0)" + "\nYou can specify up to " + __MODULE_STRING(ZC0301_MAX_DEVICES) " cameras this way." + "\nFor example:" + "\nvideo_nr=-1,2,-1 would assign minor number 2 to" + "\nthe second registered camera and use auto for the first" + "\none and for every other camera." + "\n"); + +static short force_munmap[] = {[0 ... ZC0301_MAX_DEVICES-1] = + ZC0301_FORCE_MUNMAP}; module_param_array(force_munmap, bool, NULL, 0444); MODULE_PARM_DESC(force_munmap, - "\n<0|1[,...]> Force the application to unmap previously" - "\nmapped buffer memory before calling any VIDIOC_S_CROP or" - "\nVIDIOC_S_FMT ioctl's. Not all the applications support" - "\nthis feature. This parameter is specific for each" - "\ndetected camera." - "\n 0 = do not force memory unmapping" - "\n 1 = force memory unmapping (save memory)" - "\nDefault value is "__MODULE_STRING(SN9C102_FORCE_MUNMAP)"." - "\n"); - -static unsigned int frame_timeout[] = {[0 ... ZC0301_MAX_DEVICES-1] = - ZC0301_FRAME_TIMEOUT}; + "\n<0|1[,...]> Force the application to unmap previously" + "\nmapped buffer memory before calling any VIDIOC_S_CROP or" + "\nVIDIOC_S_FMT ioctl's. Not all the applications support" + "\nthis feature. This parameter is specific for each" + "\ndetected camera." + "\n 0 = do not force memory unmapping" + "\n 1 = force memory unmapping (save memory)" + "\nDefault value is "__MODULE_STRING(SN9C102_FORCE_MUNMAP)"." + "\n"); + +static unsigned int frame_timeout[] = {[0 ... ZC0301_MAX_DEVICES-1] = + ZC0301_FRAME_TIMEOUT}; module_param_array(frame_timeout, uint, NULL, 0644); MODULE_PARM_DESC(frame_timeout, - "\n<n[,...]> Timeout for a video frame in seconds." - "\nThis parameter is specific for each detected camera." - "\nDefault value is "__MODULE_STRING(ZC0301_FRAME_TIMEOUT)"." - "\n"); + "\n<n[,...]> Timeout for a video frame in seconds." + "\nThis parameter is specific for each detected camera." + "\nDefault value is "__MODULE_STRING(ZC0301_FRAME_TIMEOUT)"." + "\n"); #ifdef ZC0301_DEBUG static unsigned short debug = ZC0301_DEBUG_LEVEL; module_param(debug, ushort, 0644); MODULE_PARM_DESC(debug, - "\n<n> Debugging information level, from 0 to 3:" - "\n0 = none (use carefully)" - "\n1 = critical errors" - "\n2 = significant informations" - "\n3 = more verbose messages" - "\nLevel 3 is useful for testing only, when only " - "one device is used." - "\nDefault value is "__MODULE_STRING(ZC0301_DEBUG_LEVEL)"." - "\n"); + "\n<n> Debugging information level, from 0 to 3:" + "\n0 = none (use carefully)" + "\n1 = critical errors" + "\n2 = significant informations" + "\n3 = more verbose messages" + "\nLevel 3 is useful for testing only, when only " + "one device is used." + "\nDefault value is "__MODULE_STRING(ZC0301_DEBUG_LEVEL)"." + "\n"); #endif /*****************************************************************************/ static u32 zc0301_request_buffers(struct zc0301_device* cam, u32 count, - enum zc0301_io_method io) + enum zc0301_io_method io) { struct v4l2_pix_format* p = &(cam->sensor.pix_format); struct v4l2_rect* r = &(cam->sensor.cropcap.bounds); const size_t imagesize = cam->module_param.force_munmap || - io == IO_READ ? - (p->width * p->height * p->priv) / 8 : - (r->width * r->height * p->priv) / 8; + io == IO_READ ? + (p->width * p->height * p->priv) / 8 : + (r->width * r->height * p->priv) / 8; void* buff = NULL; u32 i; @@ -216,7 +216,7 @@ int zc0301_write_reg(struct zc0301_device* cam, u16 index, u16 value) int res; res = usb_control_msg(udev, usb_sndctrlpipe(udev, 0), 0xa0, 0x40, - value, index, NULL, 0, ZC0301_CTRL_TIMEOUT); + value, index, NULL, 0, ZC0301_CTRL_TIMEOUT); if (res < 0) { DBG(3, "Failed to write a register (index 0x%04X, " "value 0x%02X, error %d)",index, value, res); @@ -234,7 +234,7 @@ int zc0301_read_reg(struct zc0301_device* cam, u16 index) int res; res = usb_control_msg(udev, usb_rcvctrlpipe(udev, 0), 0xa1, 0xc0, - 0x0001, index, buff, 1, ZC0301_CTRL_TIMEOUT); + 0x0001, index, buff, 1, ZC0301_CTRL_TIMEOUT); if (res < 0) DBG(3, "Failed to read a register (index 0x%04X, error %d)", index, res); @@ -337,11 +337,11 @@ static void zc0301_urb_complete(struct urb *urb, struct pt_regs* regs) if (!(*f)) (*f) = list_entry(cam->inqueue.next, struct zc0301_frame_t, - frame); + frame); imagesize = (cam->sensor.pix_format.width * - cam->sensor.pix_format.height * - cam->sensor.pix_format.priv) / 8; + cam->sensor.pix_format.height * + cam->sensor.pix_format.priv) / 8; for (i = 0; i < urb->number_of_packets; i++) { unsigned int len, status; @@ -395,8 +395,8 @@ end_of_frame: list_move_tail(&(*f)->frame, &cam->outqueue); if (!list_empty(&cam->inqueue)) (*f) = list_entry(cam->inqueue.next, - struct zc0301_frame_t, - frame); + struct zc0301_frame_t, + frame); else (*f) = NULL; spin_unlock(&cam->queue_lock); @@ -429,14 +429,14 @@ static int zc0301_start_transfer(struct zc0301_device* cam) struct usb_device *udev = cam->usbdev; struct urb* urb; const unsigned int wMaxPacketSize[] = {0, 128, 192, 256, 384, - 512, 768, 1023}; + 512, 768, 1023}; const unsigned int psz = wMaxPacketSize[ZC0301_ALTERNATE_SETTING]; s8 i, j; int err = 0; for (i = 0; i < ZC0301_URBS; i++) { cam->transfer_buffer[i] = kzalloc(ZC0301_ISO_PACKETS * psz, - GFP_KERNEL); + GFP_KERNEL); if (!cam->transfer_buffer[i]) { err = -ENOMEM; DBG(1, "Not enough memory"); @@ -528,9 +528,9 @@ static int zc0301_stream_interrupt(struct zc0301_device* cam) cam->stream = STREAM_INTERRUPT; timeout = wait_event_timeout(cam->wait_stream, - (cam->stream == STREAM_OFF) || - (cam->state & DEV_DISCONNECTED), - ZC0301_URB_TIMEOUT); + (cam->stream == STREAM_OFF) || + (cam->state & DEV_DISCONNECTED), + ZC0301_URB_TIMEOUT); if (cam->state & DEV_DISCONNECTED) return -ENODEV; else if (cam->stream != STREAM_OFF) { @@ -548,7 +548,7 @@ static int zc0301_stream_interrupt(struct zc0301_device* cam) static int zc0301_set_compression(struct zc0301_device* cam, - struct v4l2_jpegcompression* compression) + struct v4l2_jpegcompression* compression) { int r, err = 0; @@ -600,7 +600,7 @@ static int zc0301_init(struct zc0301_device* cam) if (s->set_ctrl) { for (i = 0; i < ARRAY_SIZE(s->qctrl); i++) - if (s->qctrl[i].id != 0 && + if (s->qctrl[i].id != 0 && !(s->qctrl[i].flags & V4L2_CTRL_FLAG_DISABLED)) { ctrl.id = s->qctrl[i].id; ctrl.value = qctrl[i].default_value; @@ -622,7 +622,7 @@ static int zc0301_init(struct zc0301_device* cam) init_waitqueue_head(&cam->wait_stream); cam->nreadbuffers = 2; memcpy(s->_qctrl, s->qctrl, sizeof(s->qctrl)); - memcpy(&(s->_rect), &(s->cropcap.defrect), + memcpy(&(s->_rect), &(s->cropcap.defrect), sizeof(struct v4l2_rect)); cam->state |= DEV_INITIALIZED; } @@ -670,8 +670,8 @@ static int zc0301_open(struct inode* inode, struct file* filp) } mutex_unlock(&cam->dev_mutex); err = wait_event_interruptible_exclusive(cam->open, - cam->state & DEV_DISCONNECTED - || !cam->users); + cam->state & DEV_DISCONNECTED + || !cam->users); if (err) { up_read(&zc0301_disconnect); return err; @@ -802,12 +802,12 @@ zc0301_read(struct file* filp, char __user * buf, size_t count, loff_t* f_pos) return -EAGAIN; } timeout = wait_event_interruptible_timeout - ( cam->wait_frame, - (!list_empty(&cam->outqueue)) || - (cam->state & DEV_DISCONNECTED) || - (cam->state & DEV_MISCONFIGURED), - cam->module_param.frame_timeout * - 1000 * msecs_to_jiffies(1) ); + ( cam->wait_frame, + (!list_empty(&cam->outqueue)) || + (cam->state & DEV_DISCONNECTED) || + (cam->state & DEV_MISCONFIGURED), + cam->module_param.frame_timeout * + 1000 * msecs_to_jiffies(1) ); if (timeout < 0) { mutex_unlock(&cam->fileop_mutex); return timeout; @@ -930,7 +930,7 @@ static int zc0301_mmap(struct file* filp, struct vm_area_struct *vma) { struct zc0301_device* cam = video_get_drvdata(video_devdata(filp)); unsigned long size = vma->vm_end - vma->vm_start, - start = vma->vm_start; + start = vma->vm_start; void *pos; u32 i; @@ -998,13 +998,13 @@ zc0301_vidioc_querycap(struct zc0301_device* cam, void __user * arg) .driver = "zc0301", .version = ZC0301_MODULE_VERSION_CODE, .capabilities = V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_READWRITE | - V4L2_CAP_STREAMING, + V4L2_CAP_STREAMING, }; strlcpy(cap.card, cam->v4ldev->name, sizeof(cap.card)); if (usb_make_path(cam->usbdev, cap.bus_info, sizeof(cap.bus_info)) < 0) strlcpy(cap.bus_info, cam->usbdev->dev.bus_id, - sizeof(cap.bus_info)); + sizeof(cap.bus_info)); if (copy_to_user(arg, &cap, sizeof(cap))) return -EFAULT; @@ -1337,7 +1337,7 @@ zc0301_vidioc_g_fmt(struct zc0301_device* cam, void __user * arg) static int zc0301_vidioc_try_s_fmt(struct zc0301_device* cam, unsigned int cmd, - void __user * arg) + void __user * arg) { struct zc0301_sensor* s = &cam->sensor; struct v4l2_format format; @@ -1600,7 +1600,7 @@ zc0301_vidioc_qbuf(struct zc0301_device* cam, void __user * arg) static int zc0301_vidioc_dqbuf(struct zc0301_device* cam, struct file* filp, - void __user * arg) + void __user * arg) { struct v4l2_buffer b; struct zc0301_frame_t *f; @@ -1619,12 +1619,12 @@ zc0301_vidioc_dqbuf(struct zc0301_device* cam, struct file* filp, if (filp->f_flags & O_NONBLOCK) return -EAGAIN; timeout = wait_event_interruptible_timeout - ( cam->wait_frame, - (!list_empty(&cam->outqueue)) || - (cam->state & DEV_DISCONNECTED) || - (cam->state & DEV_MISCONFIGURED), - cam->module_param.frame_timeout * - 1000 * msecs_to_jiffies(1) ); + ( cam->wait_frame, + (!list_empty(&cam->outqueue)) || + (cam->state & DEV_DISCONNECTED) || + (cam->state & DEV_MISCONFIGURED), + cam->module_param.frame_timeout * + 1000 * msecs_to_jiffies(1) ); if (timeout < 0) return timeout; if (cam->state & DEV_DISCONNECTED) @@ -1748,7 +1748,7 @@ zc0301_vidioc_s_parm(struct zc0301_device* cam, void __user * arg) static int zc0301_ioctl_v4l2(struct inode* inode, struct file* filp, - unsigned int cmd, void __user * arg) + unsigned int cmd, void __user * arg) { struct zc0301_device* cam = video_get_drvdata(video_devdata(filp)); @@ -1842,7 +1842,7 @@ static int zc0301_ioctl_v4l2(struct inode* inode, struct file* filp, static int zc0301_ioctl(struct inode* inode, struct file* filp, - unsigned int cmd, unsigned long arg) + unsigned int cmd, unsigned long arg) { struct zc0301_device* cam = video_get_drvdata(video_devdata(filp)); int err = 0; @@ -1948,7 +1948,7 @@ zc0301_usb_probe(struct usb_interface* intf, const struct usb_device_id* id) mutex_lock(&cam->dev_mutex); err = video_register_device(cam->v4ldev, VFL_TYPE_GRABBER, - video_nr[dev_nr]); + video_nr[dev_nr]); if (err) { DBG(1, "V4L2 device registration failed"); if (err == -ENFILE && video_nr[dev_nr] == -1) @@ -1992,7 +1992,7 @@ static void zc0301_usb_disconnect(struct usb_interface* intf) down_write(&zc0301_disconnect); - mutex_lock(&cam->dev_mutex); + mutex_lock(&cam->dev_mutex); DBG(2, "Disconnecting %s...", cam->v4ldev->name); diff --git a/linux/drivers/media/video/zc0301/zc0301_pas202bcb.c b/linux/drivers/media/video/zc0301/zc0301_pas202bcb.c index eaadf0252..005ef2469 100644 --- a/linux/drivers/media/video/zc0301/zc0301_pas202bcb.c +++ b/linux/drivers/media/video/zc0301/zc0301_pas202bcb.c @@ -1,10 +1,10 @@ /*************************************************************************** - * Plug-in for PAS202BCB image sensor connected to the ZC030! Image * + * Plug-in for PAS202BCB image sensor connected to the ZC0301[P] Image * * Processor and Control Chip * * * * Copyright (C) 2006 by Luca Risolia <luca.risolia@studio.unibo.it> * * * - * Initialization values of the ZC0301 have been taken from the SPCA5XX * + * Initialization values of the ZC0301[P] have been taken from the SPCA5XX * * driver maintained by Michel Xhaard <mxhaard@magic.fr> * * * * This program is free software; you can redistribute it and/or modify * @@ -24,10 +24,10 @@ /* NOTE: Sensor controls are disabled for now, becouse changing them while - streaming sometimes results in out-of-sync video frames. We'll use - the default initialization, until we know how to stop and start video - in the chip. However, the image quality still looks good under various - light conditions. + streaming sometimes results in out-of-sync video frames. We'll use + the default initialization, until we know how to stop and start video + in the chip. However, the image quality still looks good under various + light conditions. */ #include <linux/delay.h> @@ -164,8 +164,8 @@ static int pas202bcb_init(struct zc0301_device* cam) } -static int pas202bcb_get_ctrl(struct zc0301_device* cam, - struct v4l2_control* ctrl) +static int pas202bcb_get_ctrl(struct zc0301_device* cam, + struct v4l2_control* ctrl) { switch (ctrl->id) { case V4L2_CID_EXPOSURE: @@ -207,8 +207,8 @@ static int pas202bcb_get_ctrl(struct zc0301_device* cam, } -static int pas202bcb_set_ctrl(struct zc0301_device* cam, - const struct v4l2_control* ctrl) +static int pas202bcb_set_ctrl(struct zc0301_device* cam, + const struct v4l2_control* ctrl) { int err = 0; diff --git a/linux/drivers/media/video/zc0301/zc0301_pb0330.c b/linux/drivers/media/video/zc0301/zc0301_pb0330.c new file mode 100644 index 000000000..ed8542e6c --- /dev/null +++ b/linux/drivers/media/video/zc0301/zc0301_pb0330.c @@ -0,0 +1,187 @@ +/*************************************************************************** + * Plug-in for PB-0330 image sensor connected to the ZC0301[P] Image * + * Processor and Control Chip * + * * + * Copyright (C) 2006 by Luca Risolia <luca.risolia@studio.unibo.it> * + * * + * Initialization values of the ZC0301[P] have been taken from the SPCA5XX * + * driver maintained by Michel Xhaard <mxhaard@magic.fr> * + * * + * This program is free software; you can redistribute it and/or modify * + * it under the terms of the GNU General Public License as published by * + * the Free Software Foundation; either version 2 of the License, or * + * (at your option) any later version. * + * * + * This program is distributed in the hope that it will be useful, * + * but WITHOUT ANY WARRANTY; without even the implied warranty of * + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * + * GNU General Public License for more details. * + * * + * You should have received a copy of the GNU General Public License * + * along with this program; if not, write to the Free Software * + * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. * + ***************************************************************************/ + +#include <linux/delay.h> +#include "zc0301_sensor.h" + + +static struct zc0301_sensor pb0330; + + +static int pb0330_init(struct zc0301_device* cam) +{ + int err = 0; + + err += zc0301_write_reg(cam, 0x0000, 0x01); + err += zc0301_write_reg(cam, 0x0008, 0x03); + err += zc0301_write_reg(cam, 0x0010, 0x0A); + err += zc0301_write_reg(cam, 0x0002, 0x00); + err += zc0301_write_reg(cam, 0x0003, 0x02); + err += zc0301_write_reg(cam, 0x0004, 0x80); + err += zc0301_write_reg(cam, 0x0005, 0x01); + err += zc0301_write_reg(cam, 0x0006, 0xE0); + err += zc0301_write_reg(cam, 0x0001, 0x01); + err += zc0301_write_reg(cam, 0x0012, 0x05); + err += zc0301_write_reg(cam, 0x0012, 0x07); + err += zc0301_write_reg(cam, 0x0098, 0x00); + err += zc0301_write_reg(cam, 0x009A, 0x00); + err += zc0301_write_reg(cam, 0x011A, 0x00); + err += zc0301_write_reg(cam, 0x011C, 0x00); + err += zc0301_write_reg(cam, 0x0012, 0x05); + + err += zc0301_i2c_write(cam, 0x01, 0x0006); + err += zc0301_i2c_write(cam, 0x02, 0x0011); + err += zc0301_i2c_write(cam, 0x03, 0x01E7); + err += zc0301_i2c_write(cam, 0x04, 0x0287); + err += zc0301_i2c_write(cam, 0x06, 0x0003); + err += zc0301_i2c_write(cam, 0x07, 0x3002); + err += zc0301_i2c_write(cam, 0x20, 0x1100); + err += zc0301_i2c_write(cam, 0x2F, 0xF7B0); + err += zc0301_i2c_write(cam, 0x30, 0x0005); + err += zc0301_i2c_write(cam, 0x31, 0x0000); + err += zc0301_i2c_write(cam, 0x34, 0x0100); + err += zc0301_i2c_write(cam, 0x35, 0x0060); + err += zc0301_i2c_write(cam, 0x3D, 0x068F); + err += zc0301_i2c_write(cam, 0x40, 0x01E0); + err += zc0301_i2c_write(cam, 0x58, 0x0078); + err += zc0301_i2c_write(cam, 0x62, 0x0411); + + err += zc0301_write_reg(cam, 0x0087, 0x10); + err += zc0301_write_reg(cam, 0x0101, 0x37); + err += zc0301_write_reg(cam, 0x0012, 0x05); + err += zc0301_write_reg(cam, 0x0100, 0x0D); + err += zc0301_write_reg(cam, 0x0189, 0x06); + err += zc0301_write_reg(cam, 0x01AD, 0x00); + err += zc0301_write_reg(cam, 0x01C5, 0x03); + err += zc0301_write_reg(cam, 0x01CB, 0x13); + err += zc0301_write_reg(cam, 0x0250, 0x08); + err += zc0301_write_reg(cam, 0x0301, 0x08); + err += zc0301_write_reg(cam, 0x01A8, 0x60); + err += zc0301_write_reg(cam, 0x018D, 0x6C); + err += zc0301_write_reg(cam, 0x01AD, 0x09); + err += zc0301_write_reg(cam, 0x01AE, 0x15); + err += zc0301_write_reg(cam, 0x010A, 0x50); + err += zc0301_write_reg(cam, 0x010B, 0xF8); + err += zc0301_write_reg(cam, 0x010C, 0xF8); + err += zc0301_write_reg(cam, 0x010D, 0xF8); + err += zc0301_write_reg(cam, 0x010E, 0x50); + err += zc0301_write_reg(cam, 0x010F, 0xF8); + err += zc0301_write_reg(cam, 0x0110, 0xF8); + err += zc0301_write_reg(cam, 0x0111, 0xF8); + err += zc0301_write_reg(cam, 0x0112, 0x50); + err += zc0301_write_reg(cam, 0x0008, 0x03); + err += zc0301_write_reg(cam, 0x01C6, 0x08); + err += zc0301_write_reg(cam, 0x01CB, 0x0F); + err += zc0301_write_reg(cam, 0x010A, 0x50); + err += zc0301_write_reg(cam, 0x010B, 0xF8); + err += zc0301_write_reg(cam, 0x010C, 0xF8); + err += zc0301_write_reg(cam, 0x010D, 0xF8); + err += zc0301_write_reg(cam, 0x010E, 0x50); + err += zc0301_write_reg(cam, 0x010F, 0xF8); + err += zc0301_write_reg(cam, 0x0110, 0xF8); + err += zc0301_write_reg(cam, 0x0111, 0xF8); + err += zc0301_write_reg(cam, 0x0112, 0x50); + err += zc0301_write_reg(cam, 0x0180, 0x00); + err += zc0301_write_reg(cam, 0x0019, 0x00); + + err += zc0301_i2c_write(cam, 0x05, 0x0066); + err += zc0301_i2c_write(cam, 0x09, 0x02B2); + err += zc0301_i2c_write(cam, 0x10, 0x0002); + + err += zc0301_write_reg(cam, 0x011D, 0x60); + err += zc0301_write_reg(cam, 0x0190, 0x00); + err += zc0301_write_reg(cam, 0x0191, 0x07); + err += zc0301_write_reg(cam, 0x0192, 0x8C); + err += zc0301_write_reg(cam, 0x0195, 0x00); + err += zc0301_write_reg(cam, 0x0196, 0x00); + err += zc0301_write_reg(cam, 0x0197, 0x8A); + err += zc0301_write_reg(cam, 0x018C, 0x10); + err += zc0301_write_reg(cam, 0x018F, 0x20); + err += zc0301_write_reg(cam, 0x01A9, 0x14); + err += zc0301_write_reg(cam, 0x01AA, 0x24); + err += zc0301_write_reg(cam, 0x001D, 0xD7); + err += zc0301_write_reg(cam, 0x001E, 0xF0); + err += zc0301_write_reg(cam, 0x001F, 0xF8); + err += zc0301_write_reg(cam, 0x0020, 0xFF); + err += zc0301_write_reg(cam, 0x01AD, 0x09); + err += zc0301_write_reg(cam, 0x01AE, 0x15); + err += zc0301_write_reg(cam, 0x0180, 0x40); + err += zc0301_write_reg(cam, 0x0180, 0x42); + + msleep(100); + + return err; +} + + +static struct zc0301_sensor pb0330 = { + .name = "PB-0330", + .init = &pb0330_init, + .cropcap = { + .bounds = { + .left = 0, + .top = 0, + .width = 640, + .height = 480, + }, + .defrect = { + .left = 0, + .top = 0, + .width = 640, + .height = 480, + }, + }, + .pix_format = { + .width = 640, + .height = 480, + .pixelformat = V4L2_PIX_FMT_JPEG, + .priv = 8, + }, +}; + + +int zc0301_probe_pb0330(struct zc0301_device* cam) +{ + int r0, err = 0; + + err += zc0301_write_reg(cam, 0x0000, 0x01); + err += zc0301_write_reg(cam, 0x0010, 0x0a); + err += zc0301_write_reg(cam, 0x0001, 0x01); + err += zc0301_write_reg(cam, 0x0012, 0x03); + err += zc0301_write_reg(cam, 0x0012, 0x01); + + msleep(10); + + r0 = zc0301_i2c_read(cam, 0x00, 2); + + if (r0 < 0 || err) + return -EIO; + + if (r0 != 0x8243) + return -ENODEV; + + zc0301_attach_sensor(cam, &pb0330); + + return 0; +} diff --git a/linux/drivers/media/video/zc0301/zc0301_sensor.h b/linux/drivers/media/video/zc0301/zc0301_sensor.h index 7f11465ce..7f005a940 100644 --- a/linux/drivers/media/video/zc0301/zc0301_sensor.h +++ b/linux/drivers/media/video/zc0301/zc0301_sensor.h @@ -1,5 +1,5 @@ /*************************************************************************** - * API for image sensors connected to the ZC030! Image Processor and * + * API for image sensors connected to the ZC0301 Image Processor and * * Control Chip * * * * Copyright (C) 2006 by Luca Risolia <luca.risolia@studio.unibo.it> * @@ -36,37 +36,53 @@ struct zc0301_sensor; /*****************************************************************************/ extern int zc0301_probe_pas202bcb(struct zc0301_device* cam); +extern int zc0301_probe_pb0330(struct zc0301_device* cam); #define ZC0301_SENSOR_TABLE \ /* Weak detections must go at the end of the list */ \ static int (*zc0301_sensor_table[])(struct zc0301_device*) = { \ &zc0301_probe_pas202bcb, \ + &zc0301_probe_pb0330, \ NULL, \ }; extern struct zc0301_device* zc0301_match_id(struct zc0301_device* cam, const struct usb_device_id *id); -extern void +extern void zc0301_attach_sensor(struct zc0301_device* cam, struct zc0301_sensor* sensor); #define ZC0301_USB_DEVICE(vend, prod, intclass) \ .match_flags = USB_DEVICE_ID_MATCH_DEVICE | \ - USB_DEVICE_ID_MATCH_INT_CLASS, \ + USB_DEVICE_ID_MATCH_INT_CLASS, \ .idVendor = (vend), \ .idProduct = (prod), \ .bInterfaceClass = (intclass) #define ZC0301_ID_TABLE \ static const struct usb_device_id zc0301_id_table[] = { \ - { ZC0301_USB_DEVICE(0x041e, 0x4017, 0xff), }, \ + { ZC0301_USB_DEVICE(0x041e, 0x4017, 0xff), }, /* ICM105 */ \ { ZC0301_USB_DEVICE(0x041e, 0x401c, 0xff), }, /* PAS106 */ \ - { ZC0301_USB_DEVICE(0x041e, 0x401e, 0xff), }, /* HV7131B */ \ + { ZC0301_USB_DEVICE(0x041e, 0x401e, 0xff), }, /* HV7131 */ \ + { ZC0301_USB_DEVICE(0x041e, 0x401f, 0xff), }, /* TAS5130 */ \ + { ZC0301_USB_DEVICE(0x041e, 0x4022, 0xff), }, \ { ZC0301_USB_DEVICE(0x041e, 0x4034, 0xff), }, /* PAS106 */ \ { ZC0301_USB_DEVICE(0x041e, 0x4035, 0xff), }, /* PAS106 */ \ - { ZC0301_USB_DEVICE(0x046d, 0x08ae, 0xff), }, /* PAS202BCB */ \ + { ZC0301_USB_DEVICE(0x041e, 0x4036, 0xff), }, /* HV7131 */ \ + { ZC0301_USB_DEVICE(0x041e, 0x403a, 0xff), }, /* HV7131 */ \ + { ZC0301_USB_DEVICE(0x0458, 0x7007, 0xff), }, /* TAS5130 */ \ + { ZC0301_USB_DEVICE(0x0458, 0x700C, 0xff), }, /* TAS5130 */ \ + { ZC0301_USB_DEVICE(0x0458, 0x700f, 0xff), }, /* TAS5130 */ \ + { ZC0301_USB_DEVICE(0x046d, 0x08ae, 0xff), }, /* PAS202 */ \ + { ZC0301_USB_DEVICE(0x055f, 0xd003, 0xff), }, /* TAS5130 */ \ + { ZC0301_USB_DEVICE(0x055f, 0xd004, 0xff), }, /* TAS5130 */ \ + { ZC0301_USB_DEVICE(0x046d, 0x08ae, 0xff), }, /* PAS202 */ \ { ZC0301_USB_DEVICE(0x0ac8, 0x0301, 0xff), }, \ - { ZC0301_USB_DEVICE(0x10fd, 0x8050, 0xff), }, /* TAS5130D */ \ + { ZC0301_USB_DEVICE(0x0ac8, 0x301b, 0xff), }, /* PB-0330/HV7131 */ \ + { ZC0301_USB_DEVICE(0x0ac8, 0x303b, 0xff), }, /* PB-0330 */ \ + { ZC0301_USB_DEVICE(0x10fd, 0x0128, 0xff), }, /* TAS5130 */ \ + { ZC0301_USB_DEVICE(0x10fd, 0x8050, 0xff), }, /* TAS5130 */ \ + { ZC0301_USB_DEVICE(0x10fd, 0x804e, 0xff), }, /* TAS5130 */ \ { } \ }; @@ -93,7 +109,7 @@ struct zc0301_sensor { int (*init)(struct zc0301_device*); int (*get_ctrl)(struct zc0301_device*, struct v4l2_control* ctrl); int (*set_ctrl)(struct zc0301_device*, - const struct v4l2_control* ctrl); + const struct v4l2_control* ctrl); int (*set_crop)(struct zc0301_device*, const struct v4l2_rect* rect); /* Private */ |