summaryrefslogtreecommitdiff
path: root/linux
diff options
context:
space:
mode:
Diffstat (limited to 'linux')
-rw-r--r--linux/Documentation/video4linux/gspca.txt2
-rw-r--r--linux/drivers/media/video/cx18/cx18-cards.c2
-rw-r--r--linux/drivers/media/video/cx18/cx18-driver.h4
-rw-r--r--linux/drivers/media/video/cx18/cx18-ioctl.c6
-rw-r--r--linux/drivers/media/video/gspca/gspca.c21
-rw-r--r--linux/drivers/media/video/gspca/pac207.c1
-rw-r--r--linux/drivers/media/video/gspca/sonixj.c51
-rw-r--r--linux/drivers/media/video/gspca/zc3xx.c4
-rw-r--r--linux/drivers/media/video/ivtv/ivtv-cards.h2
-rw-r--r--linux/drivers/media/video/ivtv/ivtv-ioctl.c41
-rw-r--r--linux/drivers/media/video/saa7134/saa6752hs.c127
-rw-r--r--linux/drivers/media/video/saa7134/saa7134-empress.c25
-rw-r--r--linux/drivers/media/video/saa7134/saa7134-i2c.c10
-rw-r--r--linux/drivers/media/video/saa7134/saa7134-video.c42
-rw-r--r--linux/drivers/media/video/saa7134/saa7134.h3
15 files changed, 200 insertions, 141 deletions
diff --git a/linux/Documentation/video4linux/gspca.txt b/linux/Documentation/video4linux/gspca.txt
index 9a3e4d797..308ce4ee2 100644
--- a/linux/Documentation/video4linux/gspca.txt
+++ b/linux/Documentation/video4linux/gspca.txt
@@ -42,6 +42,7 @@ zc3xx 0458:7007 Genius VideoCam V2
zc3xx 0458:700c Genius VideoCam V3
zc3xx 0458:700f Genius VideoCam Web V2
sonixj 0458:7025 Genius Eye 311Q
+sonixj 0458:702e Genius Slim 310 NB
sonixj 045e:00f5 MicroSoft VX3000
sonixj 045e:00f7 MicroSoft VX1000
ov519 045e:028c Micro$oft xbox cam
@@ -181,6 +182,7 @@ pac207 093a:2468 PAC207
pac207 093a:2470 Genius GF112
pac207 093a:2471 Genius VideoCam ge111
pac207 093a:2472 Genius VideoCam ge110
+pac207 093a:2476 Genius e-Messenger 112
pac7311 093a:2600 PAC7311 Typhoon
pac7311 093a:2601 Philips SPC 610 NC
pac7311 093a:2603 PAC7312
diff --git a/linux/drivers/media/video/cx18/cx18-cards.c b/linux/drivers/media/video/cx18/cx18-cards.c
index 8fe5f38c4..3cb9734ec 100644
--- a/linux/drivers/media/video/cx18/cx18-cards.c
+++ b/linux/drivers/media/video/cx18/cx18-cards.c
@@ -163,7 +163,7 @@ static const struct cx18_card cx18_card_h900 = {
},
.audio_inputs = {
{ CX18_CARD_INPUT_AUD_TUNER,
- CX18_AV_AUDIO8, 0 },
+ CX18_AV_AUDIO5, 0 },
{ CX18_CARD_INPUT_LINE_IN1,
CX18_AV_AUDIO_SERIAL1, 0 },
},
diff --git a/linux/drivers/media/video/cx18/cx18-driver.h b/linux/drivers/media/video/cx18/cx18-driver.h
index cc6f288a6..66cb74887 100644
--- a/linux/drivers/media/video/cx18/cx18-driver.h
+++ b/linux/drivers/media/video/cx18/cx18-driver.h
@@ -63,8 +63,8 @@
# error "This driver requires kernel PCI support."
#endif
-/* Default delay to throttle mmio access to the CX23418 so it doesn't choke */
-#define CX18_DEFAULT_MMIO_NDELAY 31 /* 30.3 ns = 1 PCI clock(s) / 33 MHz */
+/* Default delay to throttle mmio access to the CX23418 */
+#define CX18_DEFAULT_MMIO_NDELAY 0 /* 0 ns = 0 PCI clock(s) / 33 MHz */
#define CX18_MEM_OFFSET 0x00000000
#define CX18_MEM_SIZE 0x04000000
diff --git a/linux/drivers/media/video/cx18/cx18-ioctl.c b/linux/drivers/media/video/cx18/cx18-ioctl.c
index 1ef2690d4..b909c78d3 100644
--- a/linux/drivers/media/video/cx18/cx18-ioctl.c
+++ b/linux/drivers/media/video/cx18/cx18-ioctl.c
@@ -201,7 +201,6 @@ static int cx18_try_fmt_vid_cap(struct file *file, void *fh,
{
struct cx18_open_id *id = fh;
struct cx18 *cx = id->cx;
-
int w = fmt->fmt.pix.width;
int h = fmt->fmt.pix.height;
@@ -249,8 +248,7 @@ static int cx18_s_fmt_vid_cap(struct file *file, void *fh,
struct cx18_open_id *id = fh;
struct cx18 *cx = id->cx;
int ret;
- int w = fmt->fmt.pix.width;
- int h = fmt->fmt.pix.height;
+ int w, h;
ret = v4l2_prio_check(&cx->prio, &id->prio);
if (ret)
@@ -259,6 +257,8 @@ static int cx18_s_fmt_vid_cap(struct file *file, void *fh,
ret = cx18_try_fmt_vid_cap(file, fh, fmt);
if (ret)
return ret;
+ w = fmt->fmt.pix.width;
+ h = fmt->fmt.pix.height;
if (cx->params.width == w && cx->params.height == h)
return 0;
diff --git a/linux/drivers/media/video/gspca/gspca.c b/linux/drivers/media/video/gspca/gspca.c
index 122644224..8c98c7a05 100644
--- a/linux/drivers/media/video/gspca/gspca.c
+++ b/linux/drivers/media/video/gspca/gspca.c
@@ -47,7 +47,7 @@ MODULE_AUTHOR("Jean-Francois Moine <http://moinejf.free.fr>");
MODULE_DESCRIPTION("GSPCA USB Camera Driver");
MODULE_LICENSE("GPL");
-#define DRIVER_VERSION_NUMBER KERNEL_VERSION(2, 2, 0)
+#define DRIVER_VERSION_NUMBER KERNEL_VERSION(2, 3, 0)
static int video_nr = -1;
@@ -195,7 +195,7 @@ static void bulk_irq(struct urb *urb
{
struct gspca_dev *gspca_dev = (struct gspca_dev *) urb->context;
struct gspca_frame *frame;
- int j, ret;
+ int j;
PDEBUG(D_PACK, "bulk irq");
if (!gspca_dev->streaming)
@@ -222,11 +222,6 @@ static void bulk_irq(struct urb *urb
urb->transfer_buffer,
urb->actual_length);
}
- /* resubmit the URB */
- urb->status = 0;
- ret = usb_submit_urb(urb, GFP_ATOMIC);
- if (ret < 0)
- PDEBUG(D_ERR|D_PACK, "usb_submit_urb() ret %d", ret);
}
/*
@@ -512,20 +507,20 @@ static int create_urbs(struct gspca_dev *gspca_dev,
PDEBUG(D_STREAM,
"isoc %d pkts size %d = bsize:%d",
npkt, psize, bsize);
+ nurbs = DEF_NURBS;
} else {
npkt = 0;
bsize = psize;
PDEBUG(D_STREAM, "bulk bsize:%d", bsize);
+ nurbs = 1;
}
- nurbs = DEF_NURBS;
gspca_dev->nurbs = nurbs;
for (n = 0; n < nurbs; n++) {
urb = usb_alloc_urb(npkt, GFP_KERNEL);
if (!urb) {
err("usb_alloc_urb failed");
- for (i = 0; i < n; i++)
- usb_free_urb(gspca_dev->urb[i]);
+ destroy_urbs(gspca_dev);
return -ENOMEM;
}
urb->transfer_buffer = usb_buffer_alloc(gspca_dev->dev,
@@ -535,8 +530,8 @@ static int create_urbs(struct gspca_dev *gspca_dev,
if (urb->transfer_buffer == NULL) {
usb_free_urb(urb);
- destroy_urbs(gspca_dev);
err("usb_buffer_urb failed");
+ destroy_urbs(gspca_dev);
return -ENOMEM;
}
gspca_dev->urb[n] = urb;
@@ -594,6 +589,10 @@ static int gspca_init_transfer(struct gspca_dev *gspca_dev)
gspca_dev->streaming = 1;
atomic_set(&gspca_dev->nevent, 0);
+ /* start the bulk transfer is done by the subdriver */
+ if (gspca_dev->bulk)
+ break;
+
/* submit the URBs */
for (n = 0; n < gspca_dev->nurbs; n++) {
ret = usb_submit_urb(gspca_dev->urb[n], GFP_KERNEL);
diff --git a/linux/drivers/media/video/gspca/pac207.c b/linux/drivers/media/video/gspca/pac207.c
index 83b5f740c..34e923d00 100644
--- a/linux/drivers/media/video/gspca/pac207.c
+++ b/linux/drivers/media/video/gspca/pac207.c
@@ -534,6 +534,7 @@ static const __devinitdata struct usb_device_id device_table[] = {
{USB_DEVICE(0x093a, 0x2470)},
{USB_DEVICE(0x093a, 0x2471)},
{USB_DEVICE(0x093a, 0x2472)},
+ {USB_DEVICE(0x093a, 0x2476)},
{USB_DEVICE(0x2001, 0xf115)},
{}
};
diff --git a/linux/drivers/media/video/gspca/sonixj.c b/linux/drivers/media/video/gspca/sonixj.c
index e95613b12..a77164581 100644
--- a/linux/drivers/media/video/gspca/sonixj.c
+++ b/linux/drivers/media/video/gspca/sonixj.c
@@ -39,6 +39,7 @@ struct sd {
unsigned char contrast;
unsigned char colors;
unsigned char autogain;
+ __u8 vflip; /* ov7630 only */
signed char ag_cnt;
#define AG_CNT_START 13
@@ -70,6 +71,8 @@ static int sd_setcolors(struct gspca_dev *gspca_dev, __s32 val);
static int sd_getcolors(struct gspca_dev *gspca_dev, __s32 *val);
static int sd_setautogain(struct gspca_dev *gspca_dev, __s32 val);
static int sd_getautogain(struct gspca_dev *gspca_dev, __s32 *val);
+static int sd_setvflip(struct gspca_dev *gspca_dev, __s32 val);
+static int sd_getvflip(struct gspca_dev *gspca_dev, __s32 *val);
static struct ctrl sd_ctrls[] = {
{
@@ -131,6 +134,22 @@ static struct ctrl sd_ctrls[] = {
.set = sd_setautogain,
.get = sd_getautogain,
},
+/* ov7630 only */
+#define VFLIP_IDX 4
+ {
+ {
+ .id = V4L2_CID_VFLIP,
+ .type = V4L2_CTRL_TYPE_BOOLEAN,
+ .name = "Vflip",
+ .minimum = 0,
+ .maximum = 1,
+ .step = 1,
+#define VFLIP_DEF 0
+ .default_value = VFLIP_DEF,
+ },
+ .set = sd_setvflip,
+ .get = sd_getvflip,
+ },
};
static struct v4l2_pix_format vga_mode[] = {
@@ -450,7 +469,8 @@ static const __u8 ov7630_sensor_init[][8] = {
{0xa1, 0x21, 0x12, 0x48, 0x00, 0x00, 0x00, 0x10},
{0xa1, 0x21, 0x12, 0x48, 0x00, 0x00, 0x00, 0x10},
/*fixme: + 0x12, 0x04*/
- {0xa1, 0x21, 0x75, 0x82, 0x00, 0x00, 0x00, 0x10},
+/* {0xa1, 0x21, 0x75, 0x82, 0x00, 0x00, 0x00, 0x10}, * COMN
+ * set by setvflip */
{0xa1, 0x21, 0x10, 0x32, 0x00, 0x00, 0x00, 0x10},
{0xa1, 0x21, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10},
{0xb1, 0x21, 0x01, 0x80, 0x80, 0x00, 0x00, 0x10},
@@ -972,6 +992,8 @@ static int sd_config(struct gspca_dev *gspca_dev,
gspca_dev->ctrl_dis = (1 << AUTOGAIN_IDX);
break;
}
+ if (sd->sensor != SENSOR_OV7630)
+ gspca_dev->ctrl_dis |= (1 << VFLIP_IDX);
return 0;
}
@@ -1200,6 +1222,14 @@ static void setautogain(struct gspca_dev *gspca_dev)
sd->ag_cnt = -1;
}
+static void setvflip(struct sd *sd)
+{
+ if (sd->sensor != SENSOR_OV7630)
+ return;
+ i2c_w1(&sd->gspca_dev, 0x75, /* COMN */
+ sd->vflip ? 0x82 : 0x02);
+}
+
/* -- start the camera -- */
static void sd_start(struct gspca_dev *gspca_dev)
{
@@ -1298,6 +1328,7 @@ static void sd_start(struct gspca_dev *gspca_dev)
break;
case SENSOR_OV7630:
ov7630_InitSensor(gspca_dev);
+ setvflip(sd);
reg17 = 0xe2;
reg1 = 0x44;
break;
@@ -1586,6 +1617,23 @@ static int sd_getautogain(struct gspca_dev *gspca_dev, __s32 *val)
return 0;
}
+static int sd_setvflip(struct gspca_dev *gspca_dev, __s32 val)
+{
+ struct sd *sd = (struct sd *) gspca_dev;
+
+ sd->vflip = val;
+ setvflip(sd);
+ return 0;
+}
+
+static int sd_getvflip(struct gspca_dev *gspca_dev, __s32 *val)
+{
+ struct sd *sd = (struct sd *) gspca_dev;
+
+ *val = sd->vflip;
+ return 0;
+}
+
/* sub-driver description */
static const struct sd_desc sd_desc = {
.name = MODULE_NAME,
@@ -1607,6 +1655,7 @@ static const struct sd_desc sd_desc = {
static const __devinitdata struct usb_device_id device_table[] = {
#if !defined CONFIG_USB_SN9C102 && !defined CONFIG_USB_SN9C102_MODULE
{USB_DEVICE(0x0458, 0x7025), BSI(SN9C120, MI0360, 0x5d)},
+ {USB_DEVICE(0x0458, 0x702e), BSI(SN9C120, OV7660, 0x21)},
{USB_DEVICE(0x045e, 0x00f5), BSI(SN9C105, OV7660, 0x21)},
{USB_DEVICE(0x045e, 0x00f7), BSI(SN9C105, OV7660, 0x21)},
{USB_DEVICE(0x0471, 0x0327), BSI(SN9C105, MI0360, 0x5d)},
diff --git a/linux/drivers/media/video/gspca/zc3xx.c b/linux/drivers/media/video/gspca/zc3xx.c
index 782952b7a..3153bd4cd 100644
--- a/linux/drivers/media/video/gspca/zc3xx.c
+++ b/linux/drivers/media/video/gspca/zc3xx.c
@@ -6581,8 +6581,8 @@ static int setlightfreq(struct gspca_dev *gspca_dev)
cs2102_60HZ, cs2102_60HZScale},
/* SENSOR_CS2102K 1 */
{cs2102_NoFliker, cs2102_NoFlikerScale,
- cs2102_50HZ, cs2102_50HZScale,
- cs2102_60HZ, cs2102_60HZScale},
+ NULL, NULL, /* currently disabled */
+ NULL, NULL},
/* SENSOR_GC0305 2 */
{gc0305_NoFliker, gc0305_NoFliker,
gc0305_50HZ, gc0305_50HZ,
diff --git a/linux/drivers/media/video/ivtv/ivtv-cards.h b/linux/drivers/media/video/ivtv/ivtv-cards.h
index 381af1bce..0b8fe85fb 100644
--- a/linux/drivers/media/video/ivtv/ivtv-cards.h
+++ b/linux/drivers/media/video/ivtv/ivtv-cards.h
@@ -154,7 +154,7 @@
#define IVTV_CAP_ENCODER (V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_TUNER | \
V4L2_CAP_AUDIO | V4L2_CAP_READWRITE | V4L2_CAP_VBI_CAPTURE | \
V4L2_CAP_SLICED_VBI_CAPTURE)
-#define IVTV_CAP_DECODER (V4L2_CAP_VBI_OUTPUT | V4L2_CAP_VIDEO_OUTPUT | \
+#define IVTV_CAP_DECODER (V4L2_CAP_VIDEO_OUTPUT | \
V4L2_CAP_SLICED_VBI_OUTPUT | V4L2_CAP_VIDEO_OUTPUT_OVERLAY)
struct ivtv_card_video_input {
diff --git a/linux/drivers/media/video/ivtv/ivtv-ioctl.c b/linux/drivers/media/video/ivtv/ivtv-ioctl.c
index 61030309d..f00854ad6 100644
--- a/linux/drivers/media/video/ivtv/ivtv-ioctl.c
+++ b/linux/drivers/media/video/ivtv/ivtv-ioctl.c
@@ -101,18 +101,15 @@ void ivtv_expand_service_set(struct v4l2_sliced_vbi_format *fmt, int is_pal)
}
}
-static int check_service_set(struct v4l2_sliced_vbi_format *fmt, int is_pal)
+static void check_service_set(struct v4l2_sliced_vbi_format *fmt, int is_pal)
{
int f, l;
- u16 set = 0;
for (f = 0; f < 2; f++) {
for (l = 0; l < 24; l++) {
fmt->service_lines[f][l] = select_service_from_set(f, l, fmt->service_lines[f][l], is_pal);
- set |= fmt->service_lines[f][l];
}
}
- return set != 0;
}
u16 ivtv_get_service_set(struct v4l2_sliced_vbi_format *fmt)
@@ -474,7 +471,7 @@ static int ivtv_try_fmt_vid_cap(struct file *file, void *fh, struct v4l2_format
int h = fmt->fmt.pix.height;
w = min(w, 720);
- w = max(w, 1);
+ w = max(w, 2);
h = min(h, itv->is_50hz ? 576 : 480);
h = max(h, 2);
ivtv_g_fmt_vid_cap(file, fh, fmt);
@@ -512,27 +509,20 @@ static int ivtv_try_fmt_sliced_vbi_cap(struct file *file, void *fh, struct v4l2_
static int ivtv_try_fmt_vid_out(struct file *file, void *fh, struct v4l2_format *fmt)
{
struct ivtv_open_id *id = fh;
- s32 w, h;
- int field;
- int ret;
+ struct ivtv *itv = id->itv;
+ s32 w = fmt->fmt.pix.width;
+ s32 h = fmt->fmt.pix.height;
+ int field = fmt->fmt.pix.field;
+ int ret = ivtv_g_fmt_vid_out(file, fh, fmt);
- w = fmt->fmt.pix.width;
- h = fmt->fmt.pix.height;
- field = fmt->fmt.pix.field;
- ret = ivtv_g_fmt_vid_out(file, fh, fmt);
+ w = min(w, 720);
+ w = max(w, 2);
+ h = min(h, itv->is_out_50hz ? 576 : 480);
+ h = max(h, 2);
+ if (id->type == IVTV_DEC_STREAM_TYPE_YUV)
+ fmt->fmt.pix.field = field;
fmt->fmt.pix.width = w;
fmt->fmt.pix.height = h;
- if (!ret && id->type == IVTV_DEC_STREAM_TYPE_YUV) {
- fmt->fmt.pix.field = field;
- if (fmt->fmt.pix.width < 2)
- fmt->fmt.pix.width = 2;
- if (fmt->fmt.pix.width > 720)
- fmt->fmt.pix.width = 720;
- if (fmt->fmt.pix.height < 2)
- fmt->fmt.pix.height = 2;
- if (fmt->fmt.pix.height > 576)
- fmt->fmt.pix.height = 576;
- }
return ret;
}
@@ -560,9 +550,9 @@ static int ivtv_s_fmt_vid_cap(struct file *file, void *fh, struct v4l2_format *f
struct ivtv_open_id *id = fh;
struct ivtv *itv = id->itv;
struct cx2341x_mpeg_params *p = &itv->params;
+ int ret = ivtv_try_fmt_vid_cap(file, fh, fmt);
int w = fmt->fmt.pix.width;
int h = fmt->fmt.pix.height;
- int ret = ivtv_try_fmt_vid_cap(file, fh, fmt);
if (ret)
return ret;
@@ -600,8 +590,7 @@ static int ivtv_s_fmt_sliced_vbi_cap(struct file *file, void *fh, struct v4l2_fo
if (ret || id->type == IVTV_DEC_STREAM_TYPE_VBI)
return ret;
- if (check_service_set(vbifmt, itv->is_50hz) == 0)
- return -EINVAL;
+ check_service_set(vbifmt, itv->is_50hz);
if (atomic_read(&itv->capturing) > 0)
return -EBUSY;
itv->video_dec_func(itv, VIDIOC_S_FMT, fmt);
diff --git a/linux/drivers/media/video/saa7134/saa6752hs.c b/linux/drivers/media/video/saa7134/saa6752hs.c
index 6c97d4ab4..8ccca4d56 100644
--- a/linux/drivers/media/video/saa7134/saa6752hs.c
+++ b/linux/drivers/media/video/saa7134/saa6752hs.c
@@ -225,7 +225,7 @@ static struct saa6752hs_mpeg_params param_defaults =
/* ---------------------------------------------------------------------- */
-static int saa6752hs_chip_command(struct i2c_client* client,
+static int saa6752hs_chip_command(struct i2c_client *client,
enum saa6752hs_command command)
{
unsigned char buf[3];
@@ -292,54 +292,61 @@ static int saa6752hs_chip_command(struct i2c_client* client,
}
-static int saa6752hs_set_bitrate(struct i2c_client* client,
+static inline void set_reg8(struct i2c_client *client, uint8_t reg, uint8_t val)
+{
+ u8 buf[2];
+
+ buf[0] = reg;
+ buf[1] = val;
+ i2c_master_send(client, buf, 2);
+}
+
+static inline void set_reg16(struct i2c_client *client, uint8_t reg, uint16_t val)
+{
+ u8 buf[3];
+
+ buf[0] = reg;
+ buf[1] = val >> 8;
+ buf[2] = val & 0xff;
+ i2c_master_send(client, buf, 3);
+}
+
+static int saa6752hs_set_bitrate(struct i2c_client *client,
struct saa6752hs_state *h)
{
struct saa6752hs_mpeg_params *params = &h->params;
- u8 buf[3];
int tot_bitrate;
+ int is_384k;
/* set the bitrate mode */
- buf[0] = 0x71;
- buf[1] = (params->vi_bitrate_mode == V4L2_MPEG_VIDEO_BITRATE_MODE_VBR) ? 0 : 1;
- i2c_master_send(client, buf, 2);
+ set_reg8(client, 0x71,
+ params->vi_bitrate_mode != V4L2_MPEG_VIDEO_BITRATE_MODE_VBR);
/* set the video bitrate */
if (params->vi_bitrate_mode == V4L2_MPEG_VIDEO_BITRATE_MODE_VBR) {
/* set the target bitrate */
- buf[0] = 0x80;
- buf[1] = params->vi_bitrate >> 8;
- buf[2] = params->vi_bitrate & 0xff;
- i2c_master_send(client, buf, 3);
+ set_reg16(client, 0x80, params->vi_bitrate);
/* set the max bitrate */
- buf[0] = 0x81;
- buf[1] = params->vi_bitrate_peak >> 8;
- buf[2] = params->vi_bitrate_peak & 0xff;
- i2c_master_send(client, buf, 3);
+ set_reg16(client, 0x81, params->vi_bitrate_peak);
tot_bitrate = params->vi_bitrate_peak;
} else {
/* set the target bitrate (no max bitrate for CBR) */
- buf[0] = 0x81;
- buf[1] = params->vi_bitrate >> 8;
- buf[2] = params->vi_bitrate & 0xff;
- i2c_master_send(client, buf, 3);
+ set_reg16(client, 0x81, params->vi_bitrate);
tot_bitrate = params->vi_bitrate;
}
/* set the audio encoding */
- buf[0] = 0x93;
- buf[1] = (params->au_encoding == V4L2_MPEG_AUDIO_ENCODING_AC3);
- i2c_master_send(client, buf, 2);
+ set_reg8(client, 0x93,
+ params->au_encoding == V4L2_MPEG_AUDIO_ENCODING_AC3);
/* set the audio bitrate */
- buf[0] = 0x94;
if (params->au_encoding == V4L2_MPEG_AUDIO_ENCODING_AC3)
- buf[1] = V4L2_MPEG_AUDIO_AC3_BITRATE_384K == params->au_ac3_bitrate;
+ is_384k = V4L2_MPEG_AUDIO_AC3_BITRATE_384K == params->au_ac3_bitrate;
else
- buf[1] = V4L2_MPEG_AUDIO_L2_BITRATE_384K == params->au_l2_bitrate;
- tot_bitrate += buf[1] ? 384 : 256;
- i2c_master_send(client, buf, 2);
+ is_384k = V4L2_MPEG_AUDIO_L2_BITRATE_384K == params->au_l2_bitrate;
+ set_reg8(client, 0x94, is_384k);
+ tot_bitrate += is_384k ? 384 : 256;
/* Note: the total max bitrate is determined by adding the video and audio
bitrates together and also adding an extra 768kbit/s to stay on the
@@ -350,16 +357,12 @@ static int saa6752hs_set_bitrate(struct i2c_client* client,
tot_bitrate = MPEG_TOTAL_TARGET_BITRATE_MAX;
/* set the total bitrate */
- buf[0] = 0xb1;
- buf[1] = tot_bitrate >> 8;
- buf[2] = tot_bitrate & 0xff;
- i2c_master_send(client, buf, 3);
-
+ set_reg16(client, 0xb1, tot_bitrate);
return 0;
}
-static void saa6752hs_set_subsampling(struct i2c_client* client,
- struct v4l2_format* f)
+static void saa6752hs_set_subsampling(struct i2c_client *client,
+ struct v4l2_format *f)
{
struct saa6752hs_state *h = i2c_get_clientdata(client);
int dist_352, dist_480, dist_720;
@@ -666,51 +669,31 @@ static int saa6752hs_init(struct i2c_client *client, u32 leading_null_bytes)
h = i2c_get_clientdata(client);
/* Set video format - must be done first as it resets other settings */
- buf[0] = 0x41;
- buf[1] = h->video_format;
- i2c_master_send(client, buf, 2);
+ set_reg8(client, 0x41, h->video_format);
/* Set number of lines in input signal */
- buf[0] = 0x40;
- buf[1] = 0x00;
- if (h->standard & V4L2_STD_525_60)
- buf[1] = 0x01;
- i2c_master_send(client, buf, 2);
+ set_reg8(client, 0x40, (h->standard & V4L2_STD_525_60) ? 1 : 0);
/* set bitrate */
saa6752hs_set_bitrate(client, h);
/* Set GOP structure {3, 13} */
- buf[0] = 0x72;
- buf[1] = 0x03;
- buf[2] = 0x0D;
- i2c_master_send(client,buf,3);
+ set_reg16(client, 0x72, 0x030d);
/* Set minimum Q-scale {4} */
- buf[0] = 0x82;
- buf[1] = 0x04;
- i2c_master_send(client,buf,2);
+ set_reg8(client, 0x82, 0x04);
/* Set maximum Q-scale {12} */
- buf[0] = 0x83;
- buf[1] = 0x0C;
- i2c_master_send(client,buf,2);
+ set_reg8(client, 0x83, 0x0c);
/* Set Output Protocol */
- buf[0] = 0xD0;
- buf[1] = 0x81;
- i2c_master_send(client,buf,2);
+ set_reg8(client, 0xd0, 0x81);
/* Set video output stream format {TS} */
- buf[0] = 0xB0;
- buf[1] = 0x05;
- i2c_master_send(client,buf,2);
+ set_reg8(client, 0xb0, 0x05);
/* Set leading null byte for TS */
- buf[0] = 0xF6;
- buf[1] = (leading_null_bytes >> 8) & 0xff;
- buf[2] = leading_null_bytes & 0xff;
- i2c_master_send(client, buf, 3);
+ set_reg16(client, 0xf6, leading_null_bytes);
/* compute PAT */
memcpy(localPAT, PAT, sizeof(PAT));
@@ -745,33 +728,21 @@ static int saa6752hs_init(struct i2c_client *client, u32 leading_null_bytes)
localPMT[size - 1] = crc & 0xFF;
/* Set Audio PID */
- buf[0] = 0xC1;
- buf[1] = (h->params.ts_pid_audio >> 8) & 0xFF;
- buf[2] = h->params.ts_pid_audio & 0xFF;
- i2c_master_send(client,buf,3);
+ set_reg16(client, 0xc1, h->params.ts_pid_audio);
/* Set Video PID */
- buf[0] = 0xC0;
- buf[1] = (h->params.ts_pid_video >> 8) & 0xFF;
- buf[2] = h->params.ts_pid_video & 0xFF;
- i2c_master_send(client,buf,3);
+ set_reg16(client, 0xc0, h->params.ts_pid_video);
/* Set PCR PID */
- buf[0] = 0xC4;
- buf[1] = (h->params.ts_pid_pcr >> 8) & 0xFF;
- buf[2] = h->params.ts_pid_pcr & 0xFF;
- i2c_master_send(client,buf,3);
+ set_reg16(client, 0xc4, h->params.ts_pid_pcr);
/* Send SI tables */
i2c_master_send(client, localPAT, sizeof(PAT));
i2c_master_send(client, localPMT, size);
/* mute then unmute audio. This removes buzzing artefacts */
- buf[0] = 0xa4;
- buf[1] = 1;
- i2c_master_send(client, buf, 2);
- buf[1] = 0;
- i2c_master_send(client, buf, 2);
+ set_reg8(client, 0xa4, 1);
+ set_reg8(client, 0xa4, 0);
/* start it going */
saa6752hs_chip_command(client, SAA6752HS_COMMAND_START);
diff --git a/linux/drivers/media/video/saa7134/saa7134-empress.c b/linux/drivers/media/video/saa7134/saa7134-empress.c
index 1451fdf99..9ebe166cc 100644
--- a/linux/drivers/media/video/saa7134/saa7134-empress.c
+++ b/linux/drivers/media/video/saa7134/saa7134-empress.c
@@ -303,15 +303,6 @@ static int empress_streamoff(struct file *file, void *priv,
return videobuf_streamoff(&dev->empress_tsq);
}
-static int saa7134_i2c_call_saa6752(struct saa7134_dev *dev,
- unsigned int cmd, void *arg)
-{
- if (dev->mpeg_i2c_client == NULL)
- return -EINVAL;
- return dev->mpeg_i2c_client->driver->command(dev->mpeg_i2c_client,
- cmd, arg);
-}
-
static int empress_s_ext_ctrls(struct file *file, void *priv,
struct v4l2_ext_controls *ctrls)
{
@@ -431,6 +422,20 @@ static int empress_g_chip_ident(struct file *file, void *fh,
return -EINVAL;
}
+static int empress_s_std(struct file *file, void *priv, v4l2_std_id *id)
+{
+ struct saa7134_dev *dev = file->private_data;
+
+ return saa7134_s_std_internal(dev, NULL, id);
+}
+
+static int empress_g_std(struct file *file, void *priv, v4l2_std_id *id)
+{
+ struct saa7134_dev *dev = file->private_data;
+
+ *id = dev->tvnorm->id;
+ return 0;
+}
static const struct file_operations ts_fops =
{
@@ -465,6 +470,8 @@ static const struct v4l2_ioctl_ops ts_ioctl_ops = {
.vidioc_g_ctrl = empress_g_ctrl,
.vidioc_s_ctrl = empress_s_ctrl,
.vidioc_g_chip_ident = empress_g_chip_ident,
+ .vidioc_s_std = empress_s_std,
+ .vidioc_g_std = empress_g_std,
};
/* ----------------------------------------------------------- */
diff --git a/linux/drivers/media/video/saa7134/saa7134-i2c.c b/linux/drivers/media/video/saa7134/saa7134-i2c.c
index bdec276e0..2ca03df8c 100644
--- a/linux/drivers/media/video/saa7134/saa7134-i2c.c
+++ b/linux/drivers/media/video/saa7134/saa7134-i2c.c
@@ -432,6 +432,16 @@ void saa7134_i2c_call_clients(struct saa7134_dev *dev,
i2c_clients_command(&dev->i2c_adap, cmd, arg);
}
+int saa7134_i2c_call_saa6752(struct saa7134_dev *dev,
+ unsigned int cmd, void *arg)
+{
+ if (dev->mpeg_i2c_client == NULL)
+ return -EINVAL;
+ return dev->mpeg_i2c_client->driver->command(dev->mpeg_i2c_client,
+ cmd, arg);
+}
+EXPORT_SYMBOL_GPL(saa7134_i2c_call_saa6752);
+
int saa7134_i2c_register(struct saa7134_dev *dev)
{
dev->i2c_adap = saa7134_adap_template;
diff --git a/linux/drivers/media/video/saa7134/saa7134-video.c b/linux/drivers/media/video/saa7134/saa7134-video.c
index 547c0401a..241b60e3f 100644
--- a/linux/drivers/media/video/saa7134/saa7134-video.c
+++ b/linux/drivers/media/video/saa7134/saa7134-video.c
@@ -628,6 +628,9 @@ void saa7134_set_tvnorm_hw(struct saa7134_dev *dev)
if (card_in(dev, dev->ctl_input).tv)
saa7134_i2c_call_clients(dev, VIDIOC_S_STD, &dev->tvnorm->id);
+ /* Set the correct norm for the saa6752hs. This function
+ does nothing if there is no saa6752hs. */
+ saa7134_i2c_call_saa6752(dev, VIDIOC_S_STD, &dev->tvnorm->id);
}
static void set_h_prescale(struct saa7134_dev *dev, int task, int prescale)
@@ -1803,18 +1806,25 @@ static int saa7134_querycap(struct file *file, void *priv,
return 0;
}
-static int saa7134_s_std(struct file *file, void *priv, v4l2_std_id *id)
+int saa7134_s_std_internal(struct saa7134_dev *dev, struct saa7134_fh *fh, v4l2_std_id *id)
{
- struct saa7134_fh *fh = priv;
- struct saa7134_dev *dev = fh->dev;
unsigned long flags;
unsigned int i;
v4l2_std_id fixup;
int err;
- err = v4l2_prio_check(&dev->prio, &fh->prio);
- if (0 != err)
- return err;
+ /* When called from the empress code fh == NULL.
+ That needs to be fixed somehow, but for now this is
+ good enough. */
+ if (fh) {
+ err = v4l2_prio_check(&dev->prio, &fh->prio);
+ if (0 != err)
+ return err;
+ } else if (res_locked(dev, RESOURCE_OVERLAY)) {
+ /* Don't change the std from the mpeg device
+ if overlay is active. */
+ return -EBUSY;
+ }
for (i = 0; i < TVNORMS; i++)
if (*id == tvnorms[i].id)
@@ -1847,7 +1857,7 @@ static int saa7134_s_std(struct file *file, void *priv, v4l2_std_id *id)
*id = tvnorms[i].id;
mutex_lock(&dev->lock);
- if (res_check(fh, RESOURCE_OVERLAY)) {
+ if (fh && res_check(fh, RESOURCE_OVERLAY)) {
spin_lock_irqsave(&dev->slock, flags);
stop_preview(dev, fh);
spin_unlock_irqrestore(&dev->slock, flags);
@@ -1864,6 +1874,23 @@ static int saa7134_s_std(struct file *file, void *priv, v4l2_std_id *id)
mutex_unlock(&dev->lock);
return 0;
}
+EXPORT_SYMBOL_GPL(saa7134_s_std_internal);
+
+static int saa7134_s_std(struct file *file, void *priv, v4l2_std_id *id)
+{
+ struct saa7134_fh *fh = priv;
+
+ return saa7134_s_std_internal(fh->dev, fh, id);
+}
+
+static int saa7134_g_std(struct file *file, void *priv, v4l2_std_id *id)
+{
+ struct saa7134_fh *fh = priv;
+ struct saa7134_dev *dev = fh->dev;
+
+ *id = dev->tvnorm->id;
+ return 0;
+}
static int saa7134_cropcap(struct file *file, void *priv,
struct v4l2_cropcap *cap)
@@ -2404,6 +2431,7 @@ static const struct v4l2_ioctl_ops video_ioctl_ops = {
.vidioc_qbuf = saa7134_qbuf,
.vidioc_dqbuf = saa7134_dqbuf,
.vidioc_s_std = saa7134_s_std,
+ .vidioc_g_std = saa7134_g_std,
.vidioc_enum_input = saa7134_enum_input,
.vidioc_g_input = saa7134_g_input,
.vidioc_s_input = saa7134_s_input,
diff --git a/linux/drivers/media/video/saa7134/saa7134.h b/linux/drivers/media/video/saa7134/saa7134.h
index 55aa60f52..50319493d 100644
--- a/linux/drivers/media/video/saa7134/saa7134.h
+++ b/linux/drivers/media/video/saa7134/saa7134.h
@@ -667,6 +667,8 @@ int saa7134_i2c_register(struct saa7134_dev *dev);
int saa7134_i2c_unregister(struct saa7134_dev *dev);
void saa7134_i2c_call_clients(struct saa7134_dev *dev,
unsigned int cmd, void *arg);
+int saa7134_i2c_call_saa6752(struct saa7134_dev *dev,
+ unsigned int cmd, void *arg);
/* ----------------------------------------------------------- */
@@ -679,6 +681,7 @@ extern struct video_device saa7134_radio_template;
int saa7134_s_ctrl_internal(struct saa7134_dev *dev, struct saa7134_fh *fh, struct v4l2_control *c);
int saa7134_g_ctrl_internal(struct saa7134_dev *dev, struct saa7134_fh *fh, struct v4l2_control *c);
int saa7134_queryctrl(struct file *file, void *priv, struct v4l2_queryctrl *c);
+int saa7134_s_std_internal(struct saa7134_dev *dev, struct saa7134_fh *fh, v4l2_std_id *id);
int saa7134_videoport_init(struct saa7134_dev *dev);
void saa7134_set_tvnorm_hw(struct saa7134_dev *dev);