From 16a939841722e3fe680364600031cb0ad064400c Mon Sep 17 00:00:00 2001 From: Ricardo Cerqueira Date: Sun, 18 Jun 2006 04:17:35 +0100 Subject: Fix card cx88 #50 remote From: Ricardo Cerqueira There was an unmasked bit in the keycodes that was causing random behaviour (the code could be N or N+1). Masked that bit now. Signed-off-by: Ricardo Cerqueira --- linux/drivers/media/video/cx88/cx88-input.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/linux/drivers/media/video/cx88/cx88-input.c b/linux/drivers/media/video/cx88/cx88-input.c index 9283be42d..0a98940f3 100644 --- a/linux/drivers/media/video/cx88/cx88-input.c +++ b/linux/drivers/media/video/cx88/cx88-input.c @@ -90,7 +90,7 @@ static void cx88_ir_handle_key(struct cx88_IR *ir) auxgpio = cx_read(MO_GP1_IO); /* Take out the parity part */ - gpio+=(auxgpio & 0xef); + gpio+=(gpio & 0x7fd) + (auxgpio & 0xef); } else auxgpio = gpio; -- cgit v1.2.3 From b219a25490dd768061f3fa29dd0d13cab1a37740 Mon Sep 17 00:00:00 2001 From: Ricardo Cerqueira Date: Sun, 18 Jun 2006 04:19:22 +0100 Subject: Fix cx88-alsa vs IRQ remote conflict From: Ricardo Cerqueira cx88-alsa was resetting the card on load, causing the IRQ IR handler to go away (maybe others, too). There's no actual need to reset the card, though, so that line was removed Signed-off-by: Ricardo Cerqueira --- linux/drivers/media/video/cx88/cx88-alsa.c | 1 - 1 file changed, 1 deletion(-) diff --git a/linux/drivers/media/video/cx88/cx88-alsa.c b/linux/drivers/media/video/cx88/cx88-alsa.c index 69d3c3c8f..7085192bc 100644 --- a/linux/drivers/media/video/cx88/cx88-alsa.c +++ b/linux/drivers/media/video/cx88/cx88-alsa.c @@ -799,7 +799,6 @@ static int __devinit snd_cx88_create(struct snd_card *card, chip->irq = -1; spin_lock_init(&chip->reg_lock); - cx88_reset(core); chip->core = core; /* get irq */ -- cgit v1.2.3 From c1752e9f9cc41b972abd82c12984361036b740dd Mon Sep 17 00:00:00 2001 From: Ricardo Cerqueira Date: Sun, 18 Jun 2006 04:21:49 +0100 Subject: Don't kill cx88 DMA sound on channel change From: Ricardo Cerqueira There's a call at cx88-tvaudio to reset DMA sound on channel change; that call was killing cx88-alsa whenever the channel was changed, resulting in no sound. Remove those calls if cx88-alsa is selected to be compiled. Signed-off-by: Ricardo Cerqueira --- linux/drivers/media/video/cx88/cx88-tvaudio.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/linux/drivers/media/video/cx88/cx88-tvaudio.c b/linux/drivers/media/video/cx88/cx88-tvaudio.c index efd8d231c..7920e2d22 100644 --- a/linux/drivers/media/video/cx88/cx88-tvaudio.c +++ b/linux/drivers/media/video/cx88/cx88-tvaudio.c @@ -140,12 +140,12 @@ static void set_audio_finish(struct cx88_core *core, u32 ctl) { u32 volume; -#ifndef USING_CX88_ALSA +#ifndef CONFIG_VIDEO_CX88_ALSA /* restart dma; This avoids buzz in NICAM and is good in others */ cx88_stop_audio_dma(core); #endif cx_write(AUD_RATE_THRES_DMD, 0x000000C0); -#ifndef USING_CX88_ALSA +#ifndef CONFIG_VIDEO_CX88_ALSA cx88_start_audio_dma(core); #endif -- cgit v1.2.3 From 6faaa169cbda16eb4f8ac681d40439e0e9dee8d6 Mon Sep 17 00:00:00 2001 From: Ricardo Cerqueira Date: Sun, 18 Jun 2006 04:26:49 +0100 Subject: Use saner defaults for cx88 contrast From: Ricardo Cerqueira The default value for contrast in cx88 cards was 25%; this worked OK, except when applications enforced their own defaults (like MythTV), and it was different from other defaults (Hue/Brightness/Saturation) that used 50%. The value for contrast has been offset so the default is now 50% (as with other controls), giving the same result as the previous 25% setting. Signed-off-by: Ricardo Cerqueira --- linux/drivers/media/video/cx88/cx88-video.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/linux/drivers/media/video/cx88/cx88-video.c b/linux/drivers/media/video/cx88/cx88-video.c index 9c2f0dd39..59a7e096d 100644 --- a/linux/drivers/media/video/cx88/cx88-video.c +++ b/linux/drivers/media/video/cx88/cx88-video.c @@ -266,10 +266,10 @@ static struct cx88_ctrl cx8800_ctls[] = { .minimum = 0, .maximum = 0xff, .step = 1, - .default_value = 0x3f, + .default_value = 0x7f, .type = V4L2_CTRL_TYPE_INTEGER, }, - .off = 0, + .off = 64, .reg = MO_CONTR_BRIGHT, .mask = 0xff00, .shift = 8, -- cgit v1.2.3 From 6a8bf297dd5c299754ce555c1d786c666619d5fc Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Sun, 18 Jun 2006 18:27:19 +0200 Subject: Add the new MPEG control/ioctl definitions to the public videodev2.h header. From: Hans Verkuil The old, experimental, VIDIOC_S/G_CODEC API to pass MPEG parameters is now obsolete and is replaced by 'extended controls' which offer more flexibility and are hopefully more future proof. Signed-off-by: Hans Verkuil --- linux/include/linux/videodev2.h | 225 +++++++++++++++++++++++++++++++++++++++- 1 file changed, 222 insertions(+), 3 deletions(-) diff --git a/linux/include/linux/videodev2.h b/linux/include/linux/videodev2.h index 26dc9c62d..d095481c0 100644 --- a/linux/include/linux/videodev2.h +++ b/linux/include/linux/videodev2.h @@ -105,6 +105,8 @@ enum v4l2_ctrl_type { V4L2_CTRL_TYPE_BOOLEAN = 2, V4L2_CTRL_TYPE_MENU = 3, V4L2_CTRL_TYPE_BUTTON = 4, + V4L2_CTRL_TYPE_INTEGER64 = 5, + V4L2_CTRL_TYPE_CTRL_CLASS = 6, }; enum v4l2_tuner_type { @@ -251,7 +253,7 @@ struct v4l2_pix_format #define V4L2_PIX_FMT_MJPEG v4l2_fourcc('M','J','P','G') /* Motion-JPEG */ #define V4L2_PIX_FMT_JPEG v4l2_fourcc('J','P','E','G') /* JFIF JPEG */ #define V4L2_PIX_FMT_DV v4l2_fourcc('d','v','s','d') /* 1394 */ -#define V4L2_PIX_FMT_MPEG v4l2_fourcc('M','P','E','G') /* MPEG */ +#define V4L2_PIX_FMT_MPEG v4l2_fourcc('M','P','E','G') /* MPEG-1/2/4 */ /* Vendor-specific formats */ #define V4L2_PIX_FMT_WNVA v4l2_fourcc('W','N','V','A') /* Winnov hw compress */ @@ -703,6 +705,34 @@ struct v4l2_control __s32 value; }; +struct v4l2_ext_control +{ + __u32 id; + __u32 reserved2[2]; + union { + __s32 value; + __s64 value64; + void *reserved; + }; +}; + +struct v4l2_ext_controls +{ + __u32 ctrl_class; + __u32 count; + __u32 error_idx; + __u32 reserved[2]; + struct v4l2_ext_control *controls; +}; + +/* Values for ctrl_class field */ +#define V4L2_CTRL_CLASS_USER 0x00980000 /* Old-style 'user' controls */ +#define V4L2_CTRL_CLASS_MPEG 0x00990000 /* MPEG-compression controls */ + +#define V4L2_CTRL_ID_MASK (0x0fffffff) +#define V4L2_CTRL_ID2CLASS(id) ((id) & 0x0fff0000UL) +#define V4L2_CTRL_DRIVER_PRIV(id) (((id) & 0xffff) >= 0x1000) + /* Used in the VIDIOC_QUERYCTRL ioctl for querying controls */ struct v4l2_queryctrl { @@ -729,12 +759,21 @@ struct v4l2_querymenu /* Control flags */ #define V4L2_CTRL_FLAG_DISABLED 0x0001 #define V4L2_CTRL_FLAG_GRABBED 0x0002 +#define V4L2_CTRL_FLAG_READ_ONLY 0x0004 +#define V4L2_CTRL_FLAG_UPDATE 0x0008 +#define V4L2_CTRL_FLAG_INACTIVE 0x0010 +#define V4L2_CTRL_FLAG_SLIDER 0x0020 + +/* Query flag, to be ORed with the control ID */ +#define V4L2_CTRL_FLAG_NEXT_CTRL 0x80000000 -/* Control IDs defined by V4L2 */ -#define V4L2_CID_BASE 0x00980900 +/* User-class control IDs defined by V4L2 */ +#define V4L2_CID_BASE (V4L2_CTRL_CLASS_USER | 0x900) +#define V4L2_CID_USER_BASE V4L2_CID_BASE /* IDs reserved for driver specific controls */ #define V4L2_CID_PRIVATE_BASE 0x08000000 +#define V4L2_CID_USER_CLASS (V4L2_CTRL_CLASS_USER | 1) #define V4L2_CID_BRIGHTNESS (V4L2_CID_BASE+0) #define V4L2_CID_CONTRAST (V4L2_CID_BASE+1) #define V4L2_CID_SATURATION (V4L2_CID_BASE+2) @@ -761,6 +800,183 @@ struct v4l2_querymenu #define V4L2_CID_VCENTER (V4L2_CID_BASE+23) #define V4L2_CID_LASTP1 (V4L2_CID_BASE+24) /* last CID + 1 */ +/* MPEG-class control IDs defined by V4L2 */ +#define V4L2_CID_MPEG_BASE (V4L2_CTRL_CLASS_MPEG | 0x900) +#define V4L2_CID_MPEG_CLASS (V4L2_CTRL_CLASS_MPEG | 1) + +/* MPEG streams */ +#define V4L2_CID_MPEG_STREAM_TYPE (V4L2_CID_MPEG_BASE+0) +enum v4l2_mpeg_stream_type { + V4L2_MPEG_STREAM_TYPE_MPEG2_PS, /* MPEG-2 program stream */ + V4L2_MPEG_STREAM_TYPE_MPEG2_TS, /* MPEG-2 transport stream */ + V4L2_MPEG_STREAM_TYPE_MPEG1_SS, /* MPEG-1 system stream */ + V4L2_MPEG_STREAM_TYPE_MPEG2_DVD, /* MPEG-2 DVD-compatible stream */ + V4L2_MPEG_STREAM_TYPE_MPEG1_VCD, /* MPEG-1 VCD-compatible stream */ + V4L2_MPEG_STREAM_TYPE_MPEG2_SVCD, /* MPEG-2 SVCD-compatible stream */ +}; +#define V4L2_CID_MPEG_STREAM_PID_PMT (V4L2_CID_MPEG_BASE+1) +#define V4L2_CID_MPEG_STREAM_PID_AUDIO (V4L2_CID_MPEG_BASE+2) +#define V4L2_CID_MPEG_STREAM_PID_VIDEO (V4L2_CID_MPEG_BASE+3) +#define V4L2_CID_MPEG_STREAM_PID_PCR (V4L2_CID_MPEG_BASE+4) +#define V4L2_CID_MPEG_STREAM_PES_ID_AUDIO (V4L2_CID_MPEG_BASE+5) +#define V4L2_CID_MPEG_STREAM_PES_ID_VIDEO (V4L2_CID_MPEG_BASE+6) + +/* MPEG audio */ +#define V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ (V4L2_CID_MPEG_BASE+100) +enum v4l2_mpeg_audio_sampling_freq { + V4L2_MPEG_AUDIO_SAMPLING_FREQ_44100, + V4L2_MPEG_AUDIO_SAMPLING_FREQ_48000, + V4L2_MPEG_AUDIO_SAMPLING_FREQ_32000, +}; +#define V4L2_CID_MPEG_AUDIO_ENCODING (V4L2_CID_MPEG_BASE+101) +enum v4l2_mpeg_audio_encoding { + V4L2_MPEG_AUDIO_ENCODING_LAYER_1, + V4L2_MPEG_AUDIO_ENCODING_LAYER_2, + V4L2_MPEG_AUDIO_ENCODING_LAYER_3, +}; +#define V4L2_CID_MPEG_AUDIO_L1_BITRATE (V4L2_CID_MPEG_BASE+102) +enum v4l2_mpeg_audio_l1_bitrate { + V4L2_MPEG_AUDIO_L1_BITRATE_32K, + V4L2_MPEG_AUDIO_L1_BITRATE_64K, + V4L2_MPEG_AUDIO_L1_BITRATE_96K, + V4L2_MPEG_AUDIO_L1_BITRATE_128K, + V4L2_MPEG_AUDIO_L1_BITRATE_160K, + V4L2_MPEG_AUDIO_L1_BITRATE_192K, + V4L2_MPEG_AUDIO_L1_BITRATE_224K, + V4L2_MPEG_AUDIO_L1_BITRATE_256K, + V4L2_MPEG_AUDIO_L1_BITRATE_288K, + V4L2_MPEG_AUDIO_L1_BITRATE_320K, + V4L2_MPEG_AUDIO_L1_BITRATE_352K, + V4L2_MPEG_AUDIO_L1_BITRATE_384K, + V4L2_MPEG_AUDIO_L1_BITRATE_416K, + V4L2_MPEG_AUDIO_L1_BITRATE_448K, +}; +#define V4L2_CID_MPEG_AUDIO_L2_BITRATE (V4L2_CID_MPEG_BASE+103) +enum v4l2_mpeg_audio_l2_bitrate { + V4L2_MPEG_AUDIO_L2_BITRATE_32K, + V4L2_MPEG_AUDIO_L2_BITRATE_48K, + V4L2_MPEG_AUDIO_L2_BITRATE_56K, + V4L2_MPEG_AUDIO_L2_BITRATE_64K, + V4L2_MPEG_AUDIO_L2_BITRATE_80K, + V4L2_MPEG_AUDIO_L2_BITRATE_96K, + V4L2_MPEG_AUDIO_L2_BITRATE_112K, + V4L2_MPEG_AUDIO_L2_BITRATE_128K, + V4L2_MPEG_AUDIO_L2_BITRATE_160K, + V4L2_MPEG_AUDIO_L2_BITRATE_192K, + V4L2_MPEG_AUDIO_L2_BITRATE_224K, + V4L2_MPEG_AUDIO_L2_BITRATE_256K, + V4L2_MPEG_AUDIO_L2_BITRATE_320K, + V4L2_MPEG_AUDIO_L2_BITRATE_384K, +}; +#define V4L2_CID_MPEG_AUDIO_L3_BITRATE (V4L2_CID_MPEG_BASE+104) +enum v4l2_mpeg_audio_l3_bitrate { + V4L2_MPEG_AUDIO_L3_BITRATE_32K, + V4L2_MPEG_AUDIO_L3_BITRATE_40K, + V4L2_MPEG_AUDIO_L3_BITRATE_48K, + V4L2_MPEG_AUDIO_L3_BITRATE_56K, + V4L2_MPEG_AUDIO_L3_BITRATE_64K, + V4L2_MPEG_AUDIO_L3_BITRATE_80K, + V4L2_MPEG_AUDIO_L3_BITRATE_96K, + V4L2_MPEG_AUDIO_L3_BITRATE_112K, + V4L2_MPEG_AUDIO_L3_BITRATE_128K, + V4L2_MPEG_AUDIO_L3_BITRATE_160K, + V4L2_MPEG_AUDIO_L3_BITRATE_192K, + V4L2_MPEG_AUDIO_L3_BITRATE_224K, + V4L2_MPEG_AUDIO_L3_BITRATE_256K, + V4L2_MPEG_AUDIO_L3_BITRATE_320K, +}; +#define V4L2_CID_MPEG_AUDIO_MODE (V4L2_CID_MPEG_BASE+105) +enum v4l2_mpeg_audio_mode { + V4L2_MPEG_AUDIO_MODE_STEREO, + V4L2_MPEG_AUDIO_MODE_JOINT_STEREO, + V4L2_MPEG_AUDIO_MODE_DUAL, + V4L2_MPEG_AUDIO_MODE_MONO, +}; +#define V4L2_CID_MPEG_AUDIO_MODE_EXTENSION (V4L2_CID_MPEG_BASE+106) +enum v4l2_mpeg_audio_mode_extension { + V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_4, + V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_8, + V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_12, + V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_16, +}; +#define V4L2_CID_MPEG_AUDIO_EMPHASIS (V4L2_CID_MPEG_BASE+107) +enum v4l2_mpeg_audio_emphasis { + V4L2_MPEG_AUDIO_EMPHASIS_NONE, + V4L2_MPEG_AUDIO_EMPHASIS_50_DIV_15_uS, + V4L2_MPEG_AUDIO_EMPHASIS_CCITT_J17, +}; +#define V4L2_CID_MPEG_AUDIO_CRC (V4L2_CID_MPEG_BASE+108) +enum v4l2_mpeg_audio_crc { + V4L2_MPEG_AUDIO_CRC_NONE, + V4L2_MPEG_AUDIO_CRC_CRC16, +}; + +/* MPEG video */ +#define V4L2_CID_MPEG_VIDEO_ENCODING (V4L2_CID_MPEG_BASE+200) +enum v4l2_mpeg_video_encoding { + V4L2_MPEG_VIDEO_ENCODING_MPEG_1, + V4L2_MPEG_VIDEO_ENCODING_MPEG_2, +}; +#define V4L2_CID_MPEG_VIDEO_ASPECT (V4L2_CID_MPEG_BASE+201) +enum v4l2_mpeg_video_aspect { + V4L2_MPEG_VIDEO_ASPECT_1x1, + V4L2_MPEG_VIDEO_ASPECT_4x3, + V4L2_MPEG_VIDEO_ASPECT_16x9, + V4L2_MPEG_VIDEO_ASPECT_221x100, +}; +#define V4L2_CID_MPEG_VIDEO_B_FRAMES (V4L2_CID_MPEG_BASE+202) +#define V4L2_CID_MPEG_VIDEO_GOP_SIZE (V4L2_CID_MPEG_BASE+203) +#define V4L2_CID_MPEG_VIDEO_GOP_CLOSURE (V4L2_CID_MPEG_BASE+204) +#define V4L2_CID_MPEG_VIDEO_PULLDOWN (V4L2_CID_MPEG_BASE+205) +#define V4L2_CID_MPEG_VIDEO_BITRATE_MODE (V4L2_CID_MPEG_BASE+206) +enum v4l2_mpeg_video_bitrate_mode { + V4L2_MPEG_VIDEO_BITRATE_MODE_VBR, + V4L2_MPEG_VIDEO_BITRATE_MODE_CBR, +}; +#define V4L2_CID_MPEG_VIDEO_BITRATE (V4L2_CID_MPEG_BASE+207) +#define V4L2_CID_MPEG_VIDEO_BITRATE_PEAK (V4L2_CID_MPEG_BASE+208) +#define V4L2_CID_MPEG_VIDEO_TEMPORAL_DECIMATION (V4L2_CID_MPEG_BASE+209) + +/* MPEG-class control IDs specific to the CX2584x driver as defined by V4L2 */ +#define V4L2_CID_MPEG_CX2341X_BASE (V4L2_CTRL_CLASS_MPEG | 0x1000) +#define V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE (V4L2_CID_MPEG_CX2341X_BASE+0) +enum v4l2_mpeg_cx2341x_video_spatial_filter_mode { + V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_MANUAL, + V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_AUTO, +}; +#define V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER (V4L2_CID_MPEG_CX2341X_BASE+1) +#define V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE (V4L2_CID_MPEG_CX2341X_BASE+2) +enum v4l2_mpeg_cx2341x_video_luma_spatial_filter_type { + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_OFF, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_1D_HOR, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_1D_VERT, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_2D_HV_SEPARABLE, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_2D_SYM_NON_SEPARABLE, +}; +#define V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE (V4L2_CID_MPEG_CX2341X_BASE+3) +enum v4l2_mpeg_cx2341x_video_chroma_spatial_filter_type { + V4L2_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE_OFF, + V4L2_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE_1D_HOR, +}; +#define V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE (V4L2_CID_MPEG_CX2341X_BASE+4) +enum v4l2_mpeg_cx2341x_video_temporal_filter_mode { + V4L2_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE_MANUAL, + V4L2_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE_AUTO, +}; +#define V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER (V4L2_CID_MPEG_CX2341X_BASE+5) +#define V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE (V4L2_CID_MPEG_CX2341X_BASE+6) +enum v4l2_mpeg_cx2341x_video_median_filter_type { + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_OFF, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_HOR, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_VERT, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_HOR_VERT, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_DIAG, +}; +#define V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_BOTTOM (V4L2_CID_MPEG_CX2341X_BASE+7) +#define V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_TOP (V4L2_CID_MPEG_CX2341X_BASE+8) +#define V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_BOTTOM (V4L2_CID_MPEG_CX2341X_BASE+9) +#define V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_TOP (V4L2_CID_MPEG_CX2341X_BASE+10) + /* * T U N I N G */ @@ -1090,6 +1306,9 @@ struct v4l2_streamparm #define VIDIOC_G_SLICED_VBI_CAP _IOR ('V', 69, struct v4l2_sliced_vbi_cap) #endif #define VIDIOC_LOG_STATUS _IO ('V', 70) +#define VIDIOC_G_EXT_CTRLS _IOWR ('V', 71, struct v4l2_ext_controls) +#define VIDIOC_S_EXT_CTRLS _IOWR ('V', 72, struct v4l2_ext_controls) +#define VIDIOC_TRY_EXT_CTRLS _IOWR ('V', 73, struct v4l2_ext_controls) #ifdef __OLD_VIDIOC_ /* for compatibility, will go away some day */ -- cgit v1.2.3 From 13df997912f6bd6191afa971517b5dd138c2a013 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Sun, 18 Jun 2006 18:43:28 +0200 Subject: Add videodev support for VIDIOC_S/G/TRY_EXT_CTRLS. From: Hans Verkuil videodev.c copies the control list specified in struct v4l2_ext_controls to kernel space. Signed-off-by: Hans Verkuil --- linux/drivers/media/video/videodev.c | 105 ++++++++++++++++++++++++++++++++++- linux/include/media/v4l2-dev.h | 6 ++ 2 files changed, 109 insertions(+), 2 deletions(-) diff --git a/linux/drivers/media/video/videodev.c b/linux/drivers/media/video/videodev.c index 9241cf5be..8eaf1b8ca 100644 --- a/linux/drivers/media/video/videodev.c +++ b/linux/drivers/media/video/videodev.c @@ -209,10 +209,15 @@ video_usercopy(struct inode *inode, struct file *file, void *mbuf = NULL; void *parg = NULL; int err = -EINVAL; + int is_ext_ctrl; + size_t ctrls_size = 0; + void __user *user_ptr = NULL; #ifdef __OLD_VIDIOC_ cmd = video_fix_command(cmd); #endif + is_ext_ctrl = (cmd == VIDIOC_S_EXT_CTRLS || cmd == VIDIOC_G_EXT_CTRLS || + cmd == VIDIOC_TRY_EXT_CTRLS); /* Copy arguments into temp kernel buffer */ switch (_IOC_DIR(cmd)) { @@ -234,19 +239,47 @@ video_usercopy(struct inode *inode, struct file *file, err = -EFAULT; if (_IOC_DIR(cmd) & _IOC_WRITE) - if (copy_from_user(parg, (void __user *)arg, - _IOC_SIZE(cmd))) + if (copy_from_user(parg, (void __user *)arg, _IOC_SIZE(cmd))) goto out; break; } + if (is_ext_ctrl) { + struct v4l2_ext_controls *p = parg; + + /* In case of an error, tell the caller that it wasn't + a specific control that caused it. */ + p->error_idx = p->count; + user_ptr = (void __user *)p->controls; + if (p->count) { + ctrls_size = sizeof(struct v4l2_ext_control) * p->count; + /* Note: v4l2_ext_controls fits in sbuf[] so mbuf is still NULL. */ + mbuf = kmalloc(ctrls_size, GFP_KERNEL); + err = -ENOMEM; + if (NULL == mbuf) + goto out_ext_ctrl; + err = -EFAULT; + if (copy_from_user(mbuf, user_ptr, ctrls_size)) + goto out_ext_ctrl; + p->controls = mbuf; + } + } /* call driver */ err = func(inode, file, cmd, parg); if (err == -ENOIOCTLCMD) err = -EINVAL; + if (is_ext_ctrl) { + struct v4l2_ext_controls *p = parg; + + p->controls = (void *)user_ptr; + if (p->count && err == 0 && copy_to_user(user_ptr, mbuf, ctrls_size)) + err = -EFAULT; + goto out_ext_ctrl; + } if (err < 0) goto out; +out_ext_ctrl: /* Copy results into user buffer */ switch (_IOC_DIR(cmd)) { @@ -1012,6 +1045,39 @@ static int __video_do_ioctl(struct inode *inode, struct file *file, ret=vfd->vidioc_s_ctrl(file, fh, p); break; } + case VIDIOC_G_EXT_CTRLS: + { + struct v4l2_ext_controls *p = arg; + + if (vfd->vidioc_g_ext_ctrls) { + dbgarg(cmd, "count=%d\n", p->count); + + ret=vfd->vidioc_g_ext_ctrls(file, fh, p); + } + break; + } + case VIDIOC_S_EXT_CTRLS: + { + struct v4l2_ext_controls *p = arg; + + if (vfd->vidioc_s_ext_ctrls) { + dbgarg(cmd, "count=%d\n", p->count); + + ret=vfd->vidioc_s_ext_ctrls(file, fh, p); + } + break; + } + case VIDIOC_TRY_EXT_CTRLS: + { + struct v4l2_ext_controls *p = arg; + + if (vfd->vidioc_try_ext_ctrls) { + dbgarg(cmd, "count=%d\n", p->count); + + ret=vfd->vidioc_try_ext_ctrls(file, fh, p); + } + break; + } case VIDIOC_QUERYMENU: { struct v4l2_querymenu *p=arg; @@ -1345,10 +1411,15 @@ int video_ioctl2 (struct inode *inode, struct file *file, void *mbuf = NULL; void *parg = NULL; int err = -EINVAL; + int is_ext_ctrl; + size_t ctrls_size = 0; + void __user *user_ptr = NULL; #ifdef __OLD_VIDIOC_ cmd = video_fix_command(cmd); #endif + is_ext_ctrl = (cmd == VIDIOC_S_EXT_CTRLS || cmd == VIDIOC_G_EXT_CTRLS || + cmd == VIDIOC_TRY_EXT_CTRLS); /* Copy arguments into temp kernel buffer */ switch (_IOC_DIR(cmd)) { @@ -1375,13 +1446,43 @@ int video_ioctl2 (struct inode *inode, struct file *file, break; } + if (is_ext_ctrl) { + struct v4l2_ext_controls *p = parg; + + /* In case of an error, tell the caller that it wasn't + a specific control that caused it. */ + p->error_idx = p->count; + user_ptr = (void __user *)p->controls; + if (p->count) { + ctrls_size = sizeof(struct v4l2_ext_control) * p->count; + /* Note: v4l2_ext_controls fits in sbuf[] so mbuf is still NULL. */ + mbuf = kmalloc(ctrls_size, GFP_KERNEL); + err = -ENOMEM; + if (NULL == mbuf) + goto out_ext_ctrl; + err = -EFAULT; + if (copy_from_user(mbuf, user_ptr, ctrls_size)) + goto out_ext_ctrl; + p->controls = mbuf; + } + } + /* Handles IOCTL */ err = __video_do_ioctl(inode, file, cmd, parg); if (err == -ENOIOCTLCMD) err = -EINVAL; + if (is_ext_ctrl) { + struct v4l2_ext_controls *p = parg; + + p->controls = (void *)user_ptr; + if (p->count && err == 0 && copy_to_user(user_ptr, mbuf, ctrls_size)) + err = -EFAULT; + goto out_ext_ctrl; + } if (err < 0) goto out; +out_ext_ctrl: /* Copy results into user buffer */ switch (_IOC_DIR(cmd)) { diff --git a/linux/include/media/v4l2-dev.h b/linux/include/media/v4l2-dev.h index 18f1bd706..39f4b7c69 100644 --- a/linux/include/media/v4l2-dev.h +++ b/linux/include/media/v4l2-dev.h @@ -245,6 +245,12 @@ struct video_device struct v4l2_control *a); int (*vidioc_s_ctrl) (struct file *file, void *fh, struct v4l2_control *a); + int (*vidioc_g_ext_ctrls) (struct file *file, void *fh, + struct v4l2_ext_controls *a); + int (*vidioc_s_ext_ctrls) (struct file *file, void *fh, + struct v4l2_ext_controls *a); + int (*vidioc_try_ext_ctrls) (struct file *file, void *fh, + struct v4l2_ext_controls *a); int (*vidioc_querymenu) (struct file *file, void *fh, struct v4l2_querymenu *a); -- cgit v1.2.3 From 1a96c8458e3bc1a8fd44dd305323a254e7776443 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Sun, 18 Jun 2006 19:11:08 +0200 Subject: Add helper functions for control processing to v4l2-common. From: Hans Verkuil Control processing is often duplicated in the various drivers. Unfortunately, simple things like the names of controls are often different between drivers, even though it is the same controls. Adding in the new extended controls and the need for having control helper functions became apparent. Several functions have now been added to v4l2-common to do things like filling the v4l2_queryctrl and v4l2_querymenu structs, to check for valid control input and to move to the next control when enumerating over all controls. Signed-off-by: Hans Verkuil --- linux/drivers/media/video/v4l2-common.c | 507 +++++++++++++++++++++++++++++++- linux/include/media/v4l2-common.h | 13 + 2 files changed, 519 insertions(+), 1 deletion(-) diff --git a/linux/drivers/media/video/v4l2-common.c b/linux/drivers/media/video/v4l2-common.c index c1697f045..c04216147 100644 --- a/linux/drivers/media/video/v4l2-common.c +++ b/linux/drivers/media/video/v4l2-common.c @@ -314,7 +314,10 @@ static const char *v4l2_ioctls[] = { #if 1 /*KEEP*/ [_IOC_NR(VIDIOC_G_SLICED_VBI_CAP)] = "VIDIOC_G_SLICED_VBI_CAP", #endif - [_IOC_NR(VIDIOC_LOG_STATUS)] = "VIDIOC_LOG_STATUS" + [_IOC_NR(VIDIOC_LOG_STATUS)] = "VIDIOC_LOG_STATUS", + [_IOC_NR(VIDIOC_G_EXT_CTRLS)] = "VIDIOC_G_EXT_CTRLS", + [_IOC_NR(VIDIOC_S_EXT_CTRLS)] = "VIDIOC_S_EXT_CTRLS", + [_IOC_NR(VIDIOC_TRY_EXT_CTRLS)] = "VIDIOC_TRY_EXT_CTRLS" }; #define V4L2_IOCTLS ARRAY_SIZE(v4l2_ioctls) @@ -531,6 +534,23 @@ void v4l_printk_ioctl_arg(char *s,unsigned int cmd, void *arg) printk ("%s: id=%d, value=%d\n", s, p->id, p->value); break; } + case VIDIOC_G_EXT_CTRLS: + case VIDIOC_S_EXT_CTRLS: + case VIDIOC_TRY_EXT_CTRLS: + { + struct v4l2_ext_controls *p = arg; + int i; + + printk("%s: ctrl_class=%d, count=%d\n", s, p->ctrl_class, p->count); + for (i = 0; i < p->count; i++) { + struct v4l2_ext_control *c = &p->controls[i]; + if (cmd == VIDIOC_G_EXT_CTRLS) + printk("%s: id=%d\n", s, c->id); + else + printk("%s: id=%d, value=%d\n", s, c->id, c->value); + } + break; + } case VIDIOC_G_CROP: case VIDIOC_S_CROP: { @@ -966,6 +986,484 @@ void v4l_printk_ioctl_arg(char *s,unsigned int cmd, void *arg) /* ----------------------------------------------------------------- */ +/* Helper functions for control handling */ + +/* Check for correctness of the ctrl's value based on the data from + struct v4l2_queryctrl and the available menu items. Note that + menu_items may be NULL, in that case it is ignored. */ +int v4l2_ctrl_check(struct v4l2_ext_control *ctrl, struct v4l2_queryctrl *qctrl, + const char **menu_items) +{ + if (qctrl->flags & V4L2_CTRL_FLAG_DISABLED) + return -EINVAL; + if (qctrl->flags & V4L2_CTRL_FLAG_GRABBED) + return -EBUSY; + if (qctrl->type == V4L2_CTRL_TYPE_BUTTON || + qctrl->type == V4L2_CTRL_TYPE_INTEGER64 || + qctrl->type == V4L2_CTRL_TYPE_CTRL_CLASS) + return 0; + if (ctrl->value < qctrl->minimum || ctrl->value > qctrl->maximum) + return -ERANGE; + if (qctrl->type == V4L2_CTRL_TYPE_MENU && menu_items != NULL) { + if (menu_items[ctrl->value] == NULL || + menu_items[ctrl->value][0] == '\0') + return -EINVAL; + } + return 0; +} + +/* Returns NULL or a character pointer array containing the menu for + the given control ID. The pointer array ends with a NULL pointer. + An empty string signifies a menu entry that is invalid. This allows + drivers to disable certain options if it is not supported. */ +const char **v4l2_ctrl_get_menu(u32 id) +{ + static const char *mpeg_audio_sampling_freq[] = { + "44.1 kHz", + "48 kHz", + "32 kHz", + NULL + }; + static const char *mpeg_audio_encoding[] = { + "Layer I", + "Layer II", + "Layer III", + NULL + }; + static const char *mpeg_audio_l1_bitrate[] = { + "32 kbps", + "64 kbps", + "96 kbps", + "128 kbps", + "160 kbps", + "192 kbps", + "224 kbps", + "256 kbps", + "288 kbps", + "320 kbps", + "352 kbps", + "384 kbps", + "416 kbps", + "448 kbps", + NULL + }; + static const char *mpeg_audio_l2_bitrate[] = { + "32 kbps", + "48 kbps", + "56 kbps", + "64 kbps", + "80 kbps", + "96 kbps", + "112 kbps", + "128 kbps", + "160 kbps", + "192 kbps", + "224 kbps", + "256 kbps", + "320 kbps", + "384 kbps", + NULL + }; + static const char *mpeg_audio_l3_bitrate[] = { + "32 kbps", + "40 kbps", + "48 kbps", + "56 kbps", + "64 kbps", + "80 kbps", + "96 kbps", + "112 kbps", + "128 kbps", + "160 kbps", + "192 kbps", + "224 kbps", + "256 kbps", + "320 kbps", + NULL + }; + static const char *mpeg_audio_mode[] = { + "Stereo", + "Joint Stereo", + "Dual", + "Mono", + NULL + }; + static const char *mpeg_audio_mode_extension[] = { + "Bound 4", + "Bound 8", + "Bound 12", + "Bound 16", + NULL + }; + static const char *mpeg_audio_emphasis[] = { + "No Emphasis", + "50/15 us", + "CCITT J17", + NULL + }; + static const char *mpeg_audio_crc[] = { + "No CRC", + "16-bit CRC", + NULL + }; + static const char *mpeg_video_encoding[] = { + "MPEG-1", + "MPEG-2", + NULL + }; + static const char *mpeg_video_aspect[] = { + "1x1", + "4x3", + "16x9", + "2.21x1", + NULL + }; + static const char *mpeg_video_bitrate_mode[] = { + "Variable Bitrate", + "Constant Bitrate", + NULL + }; + static const char *mpeg_stream_type[] = { + "MPEG-2 Program Stream", + "MPEG-2 Transport Stream", + "MPEG-1 System Stream", + "MPEG-2 DVD-compatible Stream", + "MPEG-1 VCD-compatible Stream", + "MPEG-2 SVCD-compatible Stream", + NULL + }; + + switch (id) { + case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: + return mpeg_audio_sampling_freq; + case V4L2_CID_MPEG_AUDIO_ENCODING: + return mpeg_audio_encoding; + case V4L2_CID_MPEG_AUDIO_L1_BITRATE: + return mpeg_audio_l1_bitrate; + case V4L2_CID_MPEG_AUDIO_L2_BITRATE: + return mpeg_audio_l2_bitrate; + case V4L2_CID_MPEG_AUDIO_L3_BITRATE: + return mpeg_audio_l3_bitrate; + case V4L2_CID_MPEG_AUDIO_MODE: + return mpeg_audio_mode; + case V4L2_CID_MPEG_AUDIO_MODE_EXTENSION: + return mpeg_audio_mode_extension; + case V4L2_CID_MPEG_AUDIO_EMPHASIS: + return mpeg_audio_emphasis; + case V4L2_CID_MPEG_AUDIO_CRC: + return mpeg_audio_crc; + case V4L2_CID_MPEG_VIDEO_ENCODING: + return mpeg_video_encoding; + case V4L2_CID_MPEG_VIDEO_ASPECT: + return mpeg_video_aspect; + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE: + return mpeg_video_bitrate_mode; + case V4L2_CID_MPEG_STREAM_TYPE: + return mpeg_stream_type; + default: + return NULL; + } +} + +/* Fill in a struct v4l2_queryctrl */ +int v4l2_ctrl_query_fill(struct v4l2_queryctrl *qctrl, s32 min, s32 max, s32 step, s32 def) +{ + const char *name; + + qctrl->flags = 0; + switch (qctrl->id) { + /* USER controls */ + case V4L2_CID_USER_CLASS: name = "User Controls"; break; + case V4L2_CID_AUDIO_VOLUME: name = "Volume"; break; + case V4L2_CID_AUDIO_MUTE: name = "Mute"; break; + case V4L2_CID_AUDIO_BALANCE: name = "Balance"; break; + case V4L2_CID_AUDIO_BASS: name = "Bass"; break; + case V4L2_CID_AUDIO_TREBLE: name = "Treble"; break; + case V4L2_CID_AUDIO_LOUDNESS: name = "Loudness"; break; + case V4L2_CID_BRIGHTNESS: name = "Brightness"; break; + case V4L2_CID_CONTRAST: name = "Contrast"; break; + case V4L2_CID_SATURATION: name = "Saturation"; break; + case V4L2_CID_HUE: name = "Hue"; break; + + /* MPEG controls */ + case V4L2_CID_MPEG_CLASS: name = "MPEG Encoder Controls"; break; + case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: name = "Audio Sampling Frequency"; break; + case V4L2_CID_MPEG_AUDIO_ENCODING: name = "Audio Encoding Layer"; break; + case V4L2_CID_MPEG_AUDIO_L1_BITRATE: name = "Audio Layer I Bitrate"; break; + case V4L2_CID_MPEG_AUDIO_L2_BITRATE: name = "Audio Layer II Bitrate"; break; + case V4L2_CID_MPEG_AUDIO_L3_BITRATE: name = "Audio Layer III Bitrate"; break; + case V4L2_CID_MPEG_AUDIO_MODE: name = "Audio Stereo Mode"; break; + case V4L2_CID_MPEG_AUDIO_MODE_EXTENSION: name = "Audio Stereo Mode Extension"; break; + case V4L2_CID_MPEG_AUDIO_EMPHASIS: name = "Audio Emphasis"; break; + case V4L2_CID_MPEG_AUDIO_CRC: name = "Audio CRC"; break; + case V4L2_CID_MPEG_VIDEO_ENCODING: name = "Video Encoding"; break; + case V4L2_CID_MPEG_VIDEO_ASPECT: name = "Video Aspect"; break; + case V4L2_CID_MPEG_VIDEO_B_FRAMES: name = "Video B Frames"; break; + case V4L2_CID_MPEG_VIDEO_GOP_SIZE: name = "Video GOP Size"; break; + case V4L2_CID_MPEG_VIDEO_GOP_CLOSURE: name = "Video GOP Closure"; break; + case V4L2_CID_MPEG_VIDEO_PULLDOWN: name = "Video Pulldown"; break; + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE: name = "Video Bitrate Mode"; break; + case V4L2_CID_MPEG_VIDEO_BITRATE: name = "Video Bitrate"; break; + case V4L2_CID_MPEG_VIDEO_BITRATE_PEAK: name = "Video Peak Bitrate"; break; + case V4L2_CID_MPEG_VIDEO_TEMPORAL_DECIMATION: name = "Video Temporal Decimation"; break; + case V4L2_CID_MPEG_STREAM_TYPE: name = "Stream Type"; break; + case V4L2_CID_MPEG_STREAM_PID_PMT: name = "Stream PMT Program ID"; break; + case V4L2_CID_MPEG_STREAM_PID_AUDIO: name = "Stream Audio Program ID"; break; + case V4L2_CID_MPEG_STREAM_PID_VIDEO: name = "Stream Video Program ID"; break; + case V4L2_CID_MPEG_STREAM_PID_PCR: name = "Stream PCR Program ID"; break; + case V4L2_CID_MPEG_STREAM_PES_ID_AUDIO: name = "Stream PES Audio ID"; break; + case V4L2_CID_MPEG_STREAM_PES_ID_VIDEO: name = "Stream PES Video ID"; break; + + default: + return -EINVAL; + } + switch (qctrl->id) { + case V4L2_CID_AUDIO_MUTE: + case V4L2_CID_AUDIO_LOUDNESS: + case V4L2_CID_MPEG_VIDEO_GOP_CLOSURE: + case V4L2_CID_MPEG_VIDEO_PULLDOWN: + qctrl->type = V4L2_CTRL_TYPE_BOOLEAN; + min = 0; + max = step = 1; + break; + case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: + case V4L2_CID_MPEG_AUDIO_ENCODING: + case V4L2_CID_MPEG_AUDIO_L1_BITRATE: + case V4L2_CID_MPEG_AUDIO_L2_BITRATE: + case V4L2_CID_MPEG_AUDIO_L3_BITRATE: + case V4L2_CID_MPEG_AUDIO_MODE: + case V4L2_CID_MPEG_AUDIO_MODE_EXTENSION: + case V4L2_CID_MPEG_AUDIO_EMPHASIS: + case V4L2_CID_MPEG_AUDIO_CRC: + case V4L2_CID_MPEG_VIDEO_ENCODING: + case V4L2_CID_MPEG_VIDEO_ASPECT: + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE: + case V4L2_CID_MPEG_STREAM_TYPE: + qctrl->type = V4L2_CTRL_TYPE_MENU; + step = 1; + break; + case V4L2_CID_USER_CLASS: + case V4L2_CID_MPEG_CLASS: + qctrl->type = V4L2_CTRL_TYPE_CTRL_CLASS; + qctrl->flags |= V4L2_CTRL_FLAG_READ_ONLY; + min = max = step = def = 0; + break; + default: + qctrl->type = V4L2_CTRL_TYPE_INTEGER; + break; + } + switch (qctrl->id) { + case V4L2_CID_MPEG_AUDIO_ENCODING: + case V4L2_CID_MPEG_AUDIO_MODE: + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE: + case V4L2_CID_MPEG_VIDEO_B_FRAMES: + case V4L2_CID_MPEG_STREAM_TYPE: + qctrl->flags |= V4L2_CTRL_FLAG_UPDATE; + break; + case V4L2_CID_AUDIO_VOLUME: + case V4L2_CID_AUDIO_BALANCE: + case V4L2_CID_AUDIO_BASS: + case V4L2_CID_AUDIO_TREBLE: + case V4L2_CID_BRIGHTNESS: + case V4L2_CID_CONTRAST: + case V4L2_CID_SATURATION: + case V4L2_CID_HUE: + qctrl->flags |= V4L2_CTRL_FLAG_SLIDER; + break; + } + qctrl->minimum = min; + qctrl->maximum = max; + qctrl->step = step; + qctrl->default_value = def; + qctrl->reserved[0] = qctrl->reserved[1] = 0; + snprintf(qctrl->name, sizeof(qctrl->name), name); + return 0; +} + +/* Fill in a struct v4l2_queryctrl with standard values based on + the control ID. */ +int v4l2_ctrl_query_fill_std(struct v4l2_queryctrl *qctrl) +{ + switch (qctrl->id) { + /* USER controls */ + case V4L2_CID_USER_CLASS: + case V4L2_CID_MPEG_CLASS: + return v4l2_ctrl_query_fill(qctrl, 0, 0, 0, 0); + case V4L2_CID_AUDIO_VOLUME: + return v4l2_ctrl_query_fill(qctrl, 0, 65535, 65535 / 100, 58880); + case V4L2_CID_AUDIO_MUTE: + case V4L2_CID_AUDIO_LOUDNESS: + return v4l2_ctrl_query_fill(qctrl, 0, 1, 1, 0); + case V4L2_CID_AUDIO_BALANCE: + case V4L2_CID_AUDIO_BASS: + case V4L2_CID_AUDIO_TREBLE: + return v4l2_ctrl_query_fill(qctrl, 0, 65535, 65535 / 100, 32768); + case V4L2_CID_BRIGHTNESS: + return v4l2_ctrl_query_fill(qctrl, 0, 255, 1, 128); + case V4L2_CID_CONTRAST: + case V4L2_CID_SATURATION: + return v4l2_ctrl_query_fill(qctrl, 0, 127, 1, 64); + case V4L2_CID_HUE: + return v4l2_ctrl_query_fill(qctrl, -128, 127, 1, 0); + + /* MPEG controls */ + case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_AUDIO_SAMPLING_FREQ_44100, + V4L2_MPEG_AUDIO_SAMPLING_FREQ_32000, 1, + V4L2_MPEG_AUDIO_SAMPLING_FREQ_48000); + case V4L2_CID_MPEG_AUDIO_ENCODING: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_AUDIO_ENCODING_LAYER_1, + V4L2_MPEG_AUDIO_ENCODING_LAYER_3, 1, + V4L2_MPEG_AUDIO_ENCODING_LAYER_2); + case V4L2_CID_MPEG_AUDIO_L1_BITRATE: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_AUDIO_L1_BITRATE_32K, + V4L2_MPEG_AUDIO_L1_BITRATE_448K, 1, + V4L2_MPEG_AUDIO_L1_BITRATE_256K); + case V4L2_CID_MPEG_AUDIO_L2_BITRATE: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_AUDIO_L2_BITRATE_32K, + V4L2_MPEG_AUDIO_L2_BITRATE_384K, 1, + V4L2_MPEG_AUDIO_L2_BITRATE_224K); + case V4L2_CID_MPEG_AUDIO_L3_BITRATE: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_AUDIO_L3_BITRATE_32K, + V4L2_MPEG_AUDIO_L3_BITRATE_320K, 1, + V4L2_MPEG_AUDIO_L3_BITRATE_192K); + case V4L2_CID_MPEG_AUDIO_MODE: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_AUDIO_MODE_STEREO, + V4L2_MPEG_AUDIO_MODE_MONO, 1, + V4L2_MPEG_AUDIO_MODE_STEREO); + case V4L2_CID_MPEG_AUDIO_MODE_EXTENSION: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_4, + V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_16, 1, + V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_4); + case V4L2_CID_MPEG_AUDIO_EMPHASIS: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_AUDIO_EMPHASIS_NONE, + V4L2_MPEG_AUDIO_EMPHASIS_CCITT_J17, 1, + V4L2_MPEG_AUDIO_EMPHASIS_NONE); + case V4L2_CID_MPEG_AUDIO_CRC: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_AUDIO_CRC_NONE, + V4L2_MPEG_AUDIO_CRC_CRC16, 1, + V4L2_MPEG_AUDIO_CRC_NONE); + case V4L2_CID_MPEG_VIDEO_ENCODING: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_VIDEO_ENCODING_MPEG_1, + V4L2_MPEG_VIDEO_ENCODING_MPEG_2, 1, + V4L2_MPEG_VIDEO_ENCODING_MPEG_2); + case V4L2_CID_MPEG_VIDEO_ASPECT: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_VIDEO_ASPECT_1x1, + V4L2_MPEG_VIDEO_ASPECT_221x100, 1, + V4L2_MPEG_VIDEO_ASPECT_4x3); + case V4L2_CID_MPEG_VIDEO_B_FRAMES: + return v4l2_ctrl_query_fill(qctrl, 0, 33, 1, 2); + case V4L2_CID_MPEG_VIDEO_GOP_SIZE: + return v4l2_ctrl_query_fill(qctrl, 1, 34, 1, 12); + case V4L2_CID_MPEG_VIDEO_GOP_CLOSURE: + return v4l2_ctrl_query_fill(qctrl, 0, 1, 1, 1); + case V4L2_CID_MPEG_VIDEO_PULLDOWN: + return v4l2_ctrl_query_fill(qctrl, 0, 1, 1, 0); + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_VIDEO_BITRATE_MODE_VBR, + V4L2_MPEG_VIDEO_BITRATE_MODE_CBR, 1, + V4L2_MPEG_VIDEO_BITRATE_MODE_VBR); + case V4L2_CID_MPEG_VIDEO_BITRATE: + return v4l2_ctrl_query_fill(qctrl, 0, 27000000, 1, 6000000); + case V4L2_CID_MPEG_VIDEO_BITRATE_PEAK: + return v4l2_ctrl_query_fill(qctrl, 0, 27000000, 1, 8000000); + case V4L2_CID_MPEG_VIDEO_TEMPORAL_DECIMATION: + return v4l2_ctrl_query_fill(qctrl, 0, 255, 1, 0); + case V4L2_CID_MPEG_STREAM_TYPE: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_STREAM_TYPE_MPEG2_PS, + V4L2_MPEG_STREAM_TYPE_MPEG2_SVCD, 1, + V4L2_MPEG_STREAM_TYPE_MPEG2_PS); + case V4L2_CID_MPEG_STREAM_PID_PMT: + return v4l2_ctrl_query_fill(qctrl, 0, (1 << 14) - 1, 1, 16); + case V4L2_CID_MPEG_STREAM_PID_AUDIO: + return v4l2_ctrl_query_fill(qctrl, 0, (1 << 14) - 1, 1, 260); + case V4L2_CID_MPEG_STREAM_PID_VIDEO: + return v4l2_ctrl_query_fill(qctrl, 0, (1 << 14) - 1, 1, 256); + case V4L2_CID_MPEG_STREAM_PID_PCR: + return v4l2_ctrl_query_fill(qctrl, 0, (1 << 14) - 1, 1, 259); + case V4L2_CID_MPEG_STREAM_PES_ID_AUDIO: + return v4l2_ctrl_query_fill(qctrl, 0, 255, 1, 0); + case V4L2_CID_MPEG_STREAM_PES_ID_VIDEO: + return v4l2_ctrl_query_fill(qctrl, 0, 255, 1, 0); + default: + return -EINVAL; + } +} + +/* Fill in a struct v4l2_querymenu based on the struct v4l2_queryctrl and + the menu. The qctrl pointer may be NULL, in which case it is ignored. */ +int v4l2_ctrl_query_menu(struct v4l2_querymenu *qmenu, struct v4l2_queryctrl *qctrl, + const char **menu_items) +{ + int i; + + if (menu_items == NULL || + (qctrl && (qmenu->index < qctrl->minimum || qmenu->index > qctrl->maximum))) + return -EINVAL; + for (i = 0; i < qmenu->index && menu_items[i]; i++) ; + if (menu_items[i] == NULL || menu_items[i][0] == '\0') + return -EINVAL; + snprintf(qmenu->name, sizeof(qmenu->name), menu_items[qmenu->index]); + qmenu->reserved = 0; + return 0; +} + +/* ctrl_classes points to an array of u32 pointers, the last element is + a NULL pointer. Each u32 array is a 0-terminated array of control IDs. + Each array must be sorted low to high and belong to the same control + class. The array of u32 pointer must also be sorted, from low class IDs + to high class IDs. + + This function returns the first ID that follows after the given ID. + When no more controls are available 0 is returned. */ +u32 v4l2_ctrl_next(const u32 * const * ctrl_classes, u32 id) +{ + u32 ctrl_class; + const u32 *pctrl; + + /* if no query is desired, then just return the control ID */ + if ((id & V4L2_CTRL_FLAG_NEXT_CTRL) == 0) + return id; + if (ctrl_classes == NULL) + return 0; + id &= V4L2_CTRL_ID_MASK; + ctrl_class = V4L2_CTRL_ID2CLASS(id); + id++; /* select next control */ + /* find first class that matches (or is greater than) the class of + the ID */ + while (*ctrl_classes && V4L2_CTRL_ID2CLASS(**ctrl_classes) < ctrl_class) + ctrl_classes++; + /* no more classes */ + if (*ctrl_classes == NULL) + return 0; + pctrl = *ctrl_classes; + /* find first ctrl within the class that is >= ID */ + while (*pctrl && *pctrl < id) pctrl++; + if (*pctrl) + return *pctrl; + /* we are at the end of the controls of the current class. */ + /* continue with next class if available */ + ctrl_classes++; + if (*ctrl_classes == NULL) + return 0; + return **ctrl_classes; +} + +/* ----------------------------------------------------------------- */ + EXPORT_SYMBOL(v4l2_video_std_construct); EXPORT_SYMBOL(v4l2_prio_init); @@ -980,6 +1478,13 @@ EXPORT_SYMBOL(v4l2_type_names); EXPORT_SYMBOL(v4l_printk_ioctl); EXPORT_SYMBOL(v4l_printk_ioctl_arg); +EXPORT_SYMBOL(v4l2_ctrl_next); +EXPORT_SYMBOL(v4l2_ctrl_check); +EXPORT_SYMBOL(v4l2_ctrl_get_menu); +EXPORT_SYMBOL(v4l2_ctrl_query_menu); +EXPORT_SYMBOL(v4l2_ctrl_query_fill); +EXPORT_SYMBOL(v4l2_ctrl_query_fill_std); + /* * Local variables: * c-basic-offset: 8 diff --git a/linux/include/media/v4l2-common.h b/linux/include/media/v4l2-common.h index f1d7a063a..98976fd3b 100644 --- a/linux/include/media/v4l2-common.h +++ b/linux/include/media/v4l2-common.h @@ -90,6 +90,19 @@ extern void v4l_printk_ioctl_arg(char *s,unsigned int cmd, void *arg); /* ------------------------------------------------------------------------- */ +/* Control helper functions */ + +int v4l2_ctrl_check(struct v4l2_ext_control *ctrl, struct v4l2_queryctrl *qctrl, + const char **menu_items); +const char **v4l2_ctrl_get_menu(u32 id); +int v4l2_ctrl_query_fill(struct v4l2_queryctrl *qctrl, s32 min, s32 max, s32 step, s32 def); +int v4l2_ctrl_query_fill_std(struct v4l2_queryctrl *qctrl); +int v4l2_ctrl_query_menu(struct v4l2_querymenu *qmenu, + struct v4l2_queryctrl *qctrl, const char **menu_items); +u32 v4l2_ctrl_next(const u32 * const *ctrl_classes, u32 id); + +/* ------------------------------------------------------------------------- */ + /* Internal ioctls */ /* VIDIOC_INT_G_REGISTER and VIDIOC_INT_S_REGISTER */ -- cgit v1.2.3 From 22ca6fbfdb83215e3e763226f6f15c2e7aec7a16 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Sun, 18 Jun 2006 19:40:30 +0200 Subject: Add CX2341X MPEG encoder module. From: Hans Verkuil Adds the cx2341x.c module that handles the programming of the Conexant cx23415/6 MPEG encoder chip used by cx88-blackbird, pvrusb2 and ivtv. Signed-off-by: Hans Verkuil --- linux/drivers/media/Kconfig | 3 + linux/drivers/media/video/Makefile | 1 + linux/drivers/media/video/cx2341x.c | 877 +++++++++++++++++++++ linux/drivers/media/video/cx88/Kconfig | 1 + linux/drivers/media/video/pvrusb2/Kconfig | 1 + .../drivers/media/video/pvrusb2/pvrusb2-encoder.c | 2 + linux/drivers/media/video/pvrusb2/pvrusb2-hdw.c | 1 + linux/include/media/cx2341x.h | 60 ++ v4l/versions.txt | 1 + 9 files changed, 947 insertions(+) create mode 100644 linux/drivers/media/video/cx2341x.c diff --git a/linux/drivers/media/Kconfig b/linux/drivers/media/Kconfig index ef52e6da0..583d151b7 100644 --- a/linux/drivers/media/Kconfig +++ b/linux/drivers/media/Kconfig @@ -82,6 +82,9 @@ config VIDEO_IR config VIDEO_TVEEPROM tristate +config VIDEO_CX2341X + tristate + config USB_DABUSB tristate "DABUSB driver" depends on USB diff --git a/linux/drivers/media/video/Makefile b/linux/drivers/media/video/Makefile index 44f84166f..572e84835 100644 --- a/linux/drivers/media/video/Makefile +++ b/linux/drivers/media/video/Makefile @@ -74,6 +74,7 @@ obj-$(CONFIG_VIDEO_SAA711X) += saa7115.o obj-$(CONFIG_VIDEO_SAA7127) += saa7127.o obj-$(CONFIG_VIDEO_UPD64031A) += upd64031a.o obj-$(CONFIG_VIDEO_UPD64083) += upd64083.o +obj-$(CONFIG_VIDEO_CX2341X) += cx2341x.o obj-$(CONFIG_USB_DABUSB) += dabusb.o obj-$(CONFIG_USB_DSBR) += dsbr100.o diff --git a/linux/drivers/media/video/cx2341x.c b/linux/drivers/media/video/cx2341x.c new file mode 100644 index 000000000..3df06694d --- /dev/null +++ b/linux/drivers/media/video/cx2341x.c @@ -0,0 +1,877 @@ +/* + * cx2341x - generic code for cx23415/6 based devices + * + * Copyright (C) 2006 Hans Verkuil + * + * 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 "compat.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0) +#include +#endif + +#include +#include +#include + +MODULE_DESCRIPTION("cx23415/6 driver"); +MODULE_AUTHOR("Hans Verkuil"); +MODULE_LICENSE("GPL"); + +static int debug = 0; +module_param(debug, int, 0644); +MODULE_PARM_DESC(debug, "Debug level (0-1)"); + + +/* Map the control ID to the correct field in the cx2341x_mpeg_params + struct. Return -EINVAL if the ID is unknown, else return 0. */ +static int cx2341x_get_ctrl(struct cx2341x_mpeg_params *params, + struct v4l2_ext_control *ctrl) +{ + switch (ctrl->id) { + case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: + ctrl->value = params->audio_sampling_freq; + break; + case V4L2_CID_MPEG_AUDIO_ENCODING: + ctrl->value = params->audio_encoding; + break; + case V4L2_CID_MPEG_AUDIO_L2_BITRATE: + ctrl->value = params->audio_l2_bitrate; + break; + case V4L2_CID_MPEG_AUDIO_MODE: + ctrl->value = params->audio_mode; + break; + case V4L2_CID_MPEG_AUDIO_MODE_EXTENSION: + ctrl->value = params->audio_mode_extension; + break; + case V4L2_CID_MPEG_AUDIO_EMPHASIS: + ctrl->value = params->audio_emphasis; + break; + case V4L2_CID_MPEG_AUDIO_CRC: + ctrl->value = params->audio_crc; + break; + case V4L2_CID_MPEG_VIDEO_ENCODING: + ctrl->value = params->video_encoding; + break; + case V4L2_CID_MPEG_VIDEO_ASPECT: + ctrl->value = params->video_aspect; + break; + case V4L2_CID_MPEG_VIDEO_B_FRAMES: + ctrl->value = params->video_b_frames; + break; + case V4L2_CID_MPEG_VIDEO_GOP_SIZE: + ctrl->value = params->video_gop_size; + break; + case V4L2_CID_MPEG_VIDEO_GOP_CLOSURE: + ctrl->value = params->video_gop_closure; + break; + case V4L2_CID_MPEG_VIDEO_PULLDOWN: + ctrl->value = params->video_pulldown; + break; + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE: + ctrl->value = params->video_bitrate_mode; + break; + case V4L2_CID_MPEG_VIDEO_BITRATE: + ctrl->value = params->video_bitrate; + break; + case V4L2_CID_MPEG_VIDEO_BITRATE_PEAK: + ctrl->value = params->video_bitrate_peak; + break; + case V4L2_CID_MPEG_VIDEO_TEMPORAL_DECIMATION: + ctrl->value = params->video_temporal_decimation; + break; + case V4L2_CID_MPEG_STREAM_TYPE: + ctrl->value = params->stream_type; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE: + ctrl->value = params->video_spatial_filter_mode; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER: + ctrl->value = params->video_spatial_filter; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE: + ctrl->value = params->video_luma_spatial_filter_type; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE: + ctrl->value = params->video_chroma_spatial_filter_type; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE: + ctrl->value = params->video_temporal_filter_mode; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER: + ctrl->value = params->video_temporal_filter; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE: + ctrl->value = params->video_median_filter_type; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_TOP: + ctrl->value = params->video_luma_median_filter_top; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_BOTTOM: + ctrl->value = params->video_luma_median_filter_bottom; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_TOP: + ctrl->value = params->video_chroma_median_filter_top; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_BOTTOM: + ctrl->value = params->video_chroma_median_filter_bottom; + break; + default: + return -EINVAL; + } + return 0; +} + +/* Map the control ID to the correct field in the cx2341x_mpeg_params + struct. Return -EINVAL if the ID is unknown, else return 0. */ +static int cx2341x_set_ctrl(struct cx2341x_mpeg_params *params, + struct v4l2_ext_control *ctrl) +{ + switch (ctrl->id) { + case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: + params->audio_sampling_freq = ctrl->value; + break; + case V4L2_CID_MPEG_AUDIO_ENCODING: + params->audio_encoding = ctrl->value; + break; + case V4L2_CID_MPEG_AUDIO_L2_BITRATE: + params->audio_l2_bitrate = ctrl->value; + break; + case V4L2_CID_MPEG_AUDIO_MODE: + params->audio_mode = ctrl->value; + break; + case V4L2_CID_MPEG_AUDIO_MODE_EXTENSION: + params->audio_mode_extension = ctrl->value; + break; + case V4L2_CID_MPEG_AUDIO_EMPHASIS: + params->audio_emphasis = ctrl->value; + break; + case V4L2_CID_MPEG_AUDIO_CRC: + params->audio_crc = ctrl->value; + break; + case V4L2_CID_MPEG_VIDEO_ASPECT: + params->video_aspect = ctrl->value; + break; + case V4L2_CID_MPEG_VIDEO_B_FRAMES: { + int b = ctrl->value + 1; + int gop = params->video_gop_size; + params->video_b_frames = ctrl->value; + params->video_gop_size = b * ((gop + b - 1) / b); + /* Max GOP size = 34 */ + while (params->video_gop_size > 34) + params->video_gop_size -= b; + break; + } + case V4L2_CID_MPEG_VIDEO_GOP_SIZE: { + int b = params->video_b_frames + 1; + int gop = ctrl->value; + params->video_gop_size = b * ((gop + b - 1) / b); + /* Max GOP size = 34 */ + while (params->video_gop_size > 34) + params->video_gop_size -= b; + ctrl->value = params->video_gop_size; + break; + } + case V4L2_CID_MPEG_VIDEO_GOP_CLOSURE: + params->video_gop_closure = ctrl->value; + break; + case V4L2_CID_MPEG_VIDEO_PULLDOWN: + params->video_pulldown = ctrl->value; + break; + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE: + /* MPEG-1 only allows CBR */ + if (params->video_encoding == V4L2_MPEG_VIDEO_ENCODING_MPEG_1 && + ctrl->value != V4L2_MPEG_VIDEO_BITRATE_MODE_CBR) + return -EINVAL; + params->video_bitrate_mode = ctrl->value; + break; + case V4L2_CID_MPEG_VIDEO_BITRATE: + params->video_bitrate = ctrl->value; + break; + case V4L2_CID_MPEG_VIDEO_BITRATE_PEAK: + params->video_bitrate_peak = ctrl->value; + break; + case V4L2_CID_MPEG_VIDEO_TEMPORAL_DECIMATION: + params->video_temporal_decimation = ctrl->value; + break; + case V4L2_CID_MPEG_STREAM_TYPE: + params->stream_type = ctrl->value; + params->video_encoding = + (params->stream_type == V4L2_MPEG_STREAM_TYPE_MPEG1_SS || + params->stream_type == V4L2_MPEG_STREAM_TYPE_MPEG1_VCD) ? + V4L2_MPEG_VIDEO_ENCODING_MPEG_1 : V4L2_MPEG_VIDEO_ENCODING_MPEG_2; + if (params->video_encoding == V4L2_MPEG_VIDEO_ENCODING_MPEG_1) { + /* MPEG-1 implies CBR */ + params->video_bitrate_mode = V4L2_MPEG_VIDEO_BITRATE_MODE_CBR; + } + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE: + params->video_spatial_filter_mode = ctrl->value; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER: + params->video_spatial_filter = ctrl->value; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE: + params->video_luma_spatial_filter_type = ctrl->value; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE: + params->video_chroma_spatial_filter_type = ctrl->value; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE: + params->video_temporal_filter_mode = ctrl->value; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER: + params->video_temporal_filter = ctrl->value; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE: + params->video_median_filter_type = ctrl->value; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_TOP: + params->video_luma_median_filter_top = ctrl->value; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_BOTTOM: + params->video_luma_median_filter_bottom = ctrl->value; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_TOP: + params->video_chroma_median_filter_top = ctrl->value; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_BOTTOM: + params->video_chroma_median_filter_bottom = ctrl->value; + break; + default: + return -EINVAL; + } + return 0; +} + +static int cx2341x_ctrl_query_fill(struct v4l2_queryctrl *qctrl, s32 min, s32 max, s32 step, s32 def) +{ + const char *name; + + qctrl->flags = 0; + switch (qctrl->id) { + /* MPEG controls */ + case V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE: + name = "Spatial Filter Mode"; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER: + name = "Spatial Filter"; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE: + name = "Spatial Luma Filter Type"; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE: + name = "Spatial Chroma Filter Type"; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE: + name = "Temporal Filter Mode"; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER: + name = "Temporal Filter"; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE: + name = "Median Filter Type"; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_TOP: + name = "Median Luma Filter Maximum"; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_BOTTOM: + name = "Median Luma Filter Minimum"; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_TOP: + name = "Median Chroma Filter Maximum"; + break; + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_BOTTOM: + name = "Median Chroma Filter Minimum"; + break; + + default: + return v4l2_ctrl_query_fill(qctrl, min, max, step, def); + } + switch (qctrl->id) { + case V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE: + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE: + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE: + case V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE: + case V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE: + qctrl->type = V4L2_CTRL_TYPE_MENU; + min = 0; + step = 1; + break; + default: + qctrl->type = V4L2_CTRL_TYPE_INTEGER; + break; + } + switch (qctrl->id) { + case V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE: + case V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE: + case V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE: + qctrl->flags |= V4L2_CTRL_FLAG_UPDATE; + break; + } + qctrl->minimum = min; + qctrl->maximum = max; + qctrl->step = step; + qctrl->default_value = def; + qctrl->reserved[0] = qctrl->reserved[1] = 0; + snprintf(qctrl->name, sizeof(qctrl->name), name); + return 0; +} + +int cx2341x_ctrl_query(struct cx2341x_mpeg_params *params, struct v4l2_queryctrl *qctrl) +{ + int err; + + switch (qctrl->id) { + case V4L2_CID_MPEG_AUDIO_ENCODING: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_AUDIO_ENCODING_LAYER_2, + V4L2_MPEG_AUDIO_ENCODING_LAYER_2, 1, + V4L2_MPEG_AUDIO_ENCODING_LAYER_2); + + case V4L2_CID_MPEG_AUDIO_L2_BITRATE: + return v4l2_ctrl_query_fill(qctrl, + V4L2_MPEG_AUDIO_L2_BITRATE_192K, + V4L2_MPEG_AUDIO_L2_BITRATE_384K, 1, + V4L2_MPEG_AUDIO_L2_BITRATE_224K); + + case V4L2_CID_MPEG_AUDIO_L1_BITRATE: + case V4L2_CID_MPEG_AUDIO_L3_BITRATE: + return -EINVAL; + + case V4L2_CID_MPEG_AUDIO_MODE_EXTENSION: + err = v4l2_ctrl_query_fill_std(qctrl); + if (err == 0 && params->audio_mode != V4L2_MPEG_AUDIO_MODE_JOINT_STEREO) + qctrl->flags |= V4L2_CTRL_FLAG_INACTIVE; + return err; + + case V4L2_CID_MPEG_VIDEO_ENCODING: + /* this setting is read-only for the cx2341x since the + V4L2_CID_MPEG_STREAM_TYPE really determines the + MPEG-1/2 setting */ + err = v4l2_ctrl_query_fill_std(qctrl); + if (err == 0) + qctrl->flags |= V4L2_CTRL_FLAG_READ_ONLY; + return err; + + case V4L2_CID_MPEG_VIDEO_BITRATE_PEAK: + err = v4l2_ctrl_query_fill_std(qctrl); + if (err == 0 && params->video_bitrate_mode == V4L2_MPEG_VIDEO_BITRATE_MODE_CBR) + qctrl->flags |= V4L2_CTRL_FLAG_INACTIVE; + return err; + + /* CX23415/6 specific */ + case V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE: + return cx2341x_ctrl_query_fill(qctrl, + V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_MANUAL, + V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_AUTO, 1, + V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_MANUAL); + + case V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER: + cx2341x_ctrl_query_fill(qctrl, 0, 15, 1, 0); + qctrl->flags |= V4L2_CTRL_FLAG_SLIDER; + if (params->video_spatial_filter_mode == V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_AUTO) + qctrl->flags |= V4L2_CTRL_FLAG_INACTIVE; + return 0; + + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE: + cx2341x_ctrl_query_fill(qctrl, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_OFF, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_2D_SYM_NON_SEPARABLE, 1, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_OFF); + if (params->video_spatial_filter_mode == V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_AUTO) + qctrl->flags |= V4L2_CTRL_FLAG_INACTIVE; + return 0; + + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE: + cx2341x_ctrl_query_fill(qctrl, + V4L2_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE_OFF, + V4L2_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE_1D_HOR, 1, + V4L2_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE_OFF); + if (params->video_spatial_filter_mode == V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_AUTO) + qctrl->flags |= V4L2_CTRL_FLAG_INACTIVE; + return 0; + + case V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE: + return cx2341x_ctrl_query_fill(qctrl, + V4L2_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE_MANUAL, + V4L2_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE_AUTO, 1, + V4L2_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE_MANUAL); + + case V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER: + cx2341x_ctrl_query_fill(qctrl, 0, 31, 1, 0); + qctrl->flags |= V4L2_CTRL_FLAG_SLIDER; + if (params->video_temporal_filter_mode == V4L2_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE_AUTO) + qctrl->flags |= V4L2_CTRL_FLAG_INACTIVE; + return 0; + + case V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE: + return cx2341x_ctrl_query_fill(qctrl, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_OFF, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_DIAG, 1, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_OFF); + + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_TOP: + cx2341x_ctrl_query_fill(qctrl, 0, 255, 1, 255); + qctrl->flags |= V4L2_CTRL_FLAG_SLIDER; + if (params->video_median_filter_type == V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_OFF) + qctrl->flags |= V4L2_CTRL_FLAG_INACTIVE; + return 0; + + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_BOTTOM: + cx2341x_ctrl_query_fill(qctrl, 0, 255, 1, 0); + qctrl->flags |= V4L2_CTRL_FLAG_SLIDER; + if (params->video_median_filter_type == V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_OFF) + qctrl->flags |= V4L2_CTRL_FLAG_INACTIVE; + return 0; + + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_TOP: + cx2341x_ctrl_query_fill(qctrl, 0, 255, 1, 255); + qctrl->flags |= V4L2_CTRL_FLAG_SLIDER; + if (params->video_median_filter_type == V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_OFF) + qctrl->flags |= V4L2_CTRL_FLAG_INACTIVE; + return 0; + + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_BOTTOM: + cx2341x_ctrl_query_fill(qctrl, 0, 255, 1, 0); + qctrl->flags |= V4L2_CTRL_FLAG_SLIDER; + if (params->video_median_filter_type == V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_OFF) + qctrl->flags |= V4L2_CTRL_FLAG_INACTIVE; + return 0; + + default: + return v4l2_ctrl_query_fill_std(qctrl); + + } +} + +const char **cx2341x_ctrl_get_menu(u32 id) +{ + static const char *mpeg_stream_type[] = { + "MPEG-2 Program Stream", + "", + "MPEG-1 System Stream", + "MPEG-2 DVD-compatible Stream", + "MPEG-1 VCD-compatible Stream", + "MPEG-2 SVCD-compatible Stream", + NULL + }; + + static const char *cx2341x_video_spatial_filter_mode_menu[] = { + "Manual", + "Auto", + NULL + }; + + static const char *cx2341x_video_luma_spatial_filter_type_menu[] = { + "Off", + "1D Horizontal", + "1D Vertical", + "2D H/V Separable", + "2D Symmetric non-separable", + NULL + }; + + static const char *cx2341x_video_chroma_spatial_filter_type_menu[] = { + "Off", + "1D Horizontal", + NULL + }; + + static const char *cx2341x_video_temporal_filter_mode_menu[] = { + "Manual", + "Auto", + NULL + }; + + static const char *cx2341x_video_median_filter_type_menu[] = { + "Off", + "Horizontal", + "Vertical", + "Horizontal/Vertical", + "Diagonal", + NULL + }; + + switch (id) { + case V4L2_CID_MPEG_STREAM_TYPE: + return mpeg_stream_type; + case V4L2_CID_MPEG_AUDIO_L1_BITRATE: + case V4L2_CID_MPEG_AUDIO_L3_BITRATE: + return NULL; + case V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE: + return cx2341x_video_spatial_filter_mode_menu; + case V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE: + return cx2341x_video_luma_spatial_filter_type_menu; + case V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE: + return cx2341x_video_chroma_spatial_filter_type_menu; + case V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE: + return cx2341x_video_temporal_filter_mode_menu; + case V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE: + return cx2341x_video_median_filter_type_menu; + default: + return v4l2_ctrl_get_menu(id); + } +} + +static void cx2341x_calc_audio_properties(struct cx2341x_mpeg_params *params) +{ + params->audio_properties = (params->audio_sampling_freq << 0) | + ((3 - params->audio_encoding) << 2) | + ((1 + params->audio_l2_bitrate) << 4) | + (params->audio_mode << 8) | + (params->audio_mode_extension << 10) | + (((params->audio_emphasis == V4L2_MPEG_AUDIO_EMPHASIS_CCITT_J17) ? + 3 : + params->audio_emphasis) << 12) | + (params->audio_crc << 14); +} + +int cx2341x_ext_ctrls(struct cx2341x_mpeg_params *params, + struct v4l2_ext_controls *ctrls, int cmd) +{ + int err = 0; + int i; + + if (cmd == VIDIOC_G_EXT_CTRLS) { + for (i = 0; i < ctrls->count; i++) { + struct v4l2_ext_control *ctrl = ctrls->controls + i; + + err = cx2341x_get_ctrl(params, ctrl); + if (err) { + ctrls->error_idx = i; + break; + } + } + return err; + } + for (i = 0; i < ctrls->count; i++) { + struct v4l2_ext_control *ctrl = ctrls->controls + i; + struct v4l2_queryctrl qctrl; + const char **menu_items = NULL; + + qctrl.id = ctrl->id; + err = cx2341x_ctrl_query(params, &qctrl); + if (err) + break; + if (qctrl.type == V4L2_CTRL_TYPE_MENU) + menu_items = cx2341x_ctrl_get_menu(qctrl.id); + err = v4l2_ctrl_check(ctrl, &qctrl, menu_items); + if (err) + break; + err = cx2341x_set_ctrl(params, ctrl); + if (err) + break; + } + if (err == 0 && params->video_bitrate_mode == V4L2_MPEG_VIDEO_BITRATE_MODE_VBR && + params->video_bitrate_peak < params->video_bitrate) { + err = -ERANGE; + ctrls->error_idx = ctrls->count; + } + if (err) { + ctrls->error_idx = i; + } + else { + cx2341x_calc_audio_properties(params); + } + return err; +} + +void cx2341x_fill_defaults(struct cx2341x_mpeg_params *p) +{ + static struct cx2341x_mpeg_params default_params = { + /* misc */ + .width = 720, + .height = 480, + .is_50hz = 0, + + /* stream */ + .stream_type = V4L2_MPEG_STREAM_TYPE_MPEG2_PS, + + /* audio */ + .audio_sampling_freq = V4L2_MPEG_AUDIO_SAMPLING_FREQ_48000, + .audio_encoding = V4L2_MPEG_AUDIO_ENCODING_LAYER_2, + .audio_l2_bitrate = V4L2_MPEG_AUDIO_L2_BITRATE_224K, + .audio_mode = V4L2_MPEG_AUDIO_MODE_STEREO, + .audio_mode_extension = V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_4, + .audio_emphasis = V4L2_MPEG_AUDIO_EMPHASIS_NONE, + .audio_crc = V4L2_MPEG_AUDIO_CRC_NONE, + + /* video */ + .video_encoding = V4L2_MPEG_VIDEO_ENCODING_MPEG_2, + .video_aspect = V4L2_MPEG_VIDEO_ASPECT_4x3, + .video_b_frames = 2, + .video_gop_size = 12, + .video_gop_closure = 1, + .video_pulldown = 0, + .video_bitrate_mode = V4L2_MPEG_VIDEO_BITRATE_MODE_VBR, + .video_bitrate = 6000000, + .video_bitrate_peak = 8000000, + .video_temporal_decimation = 0, + + /* encoding filters */ + .video_spatial_filter_mode = V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_MANUAL, + .video_spatial_filter = 0, + .video_luma_spatial_filter_type = V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_1D_HOR, + .video_chroma_spatial_filter_type = V4L2_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE_1D_HOR, + .video_temporal_filter_mode = V4L2_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE_MANUAL, + .video_temporal_filter = 0, + .video_median_filter_type = V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_OFF, + .video_luma_median_filter_top = 255, + .video_luma_median_filter_bottom = 0, + .video_chroma_median_filter_top = 255, + .video_chroma_median_filter_bottom = 0, + }; + + *p = default_params; + cx2341x_calc_audio_properties(p); +} + +static int cx2341x_api(void *priv, cx2341x_mbox_func func, int cmd, int args, ...) +{ + u32 data[CX2341X_MBOX_MAX_DATA]; + va_list vargs; + int i; + + va_start(vargs, args); + + for (i = 0; i < args; i++) { + data[i] = va_arg(vargs, int); + } + va_end(vargs); + return func(priv, cmd, args, 0, data); +} + +int cx2341x_update(void *priv, cx2341x_mbox_func func, + const struct cx2341x_mpeg_params *old, const struct cx2341x_mpeg_params *new) +{ + static int mpeg_stream_type[] = { + 0, /* MPEG-2 PS */ + 1, /* MPEG-2 TS */ + 2, /* MPEG-1 SS */ + 14, /* DVD */ + 11, /* VCD */ + 12, /* SVCD */ + }; + + int err = 0; + + cx2341x_api(priv, func, CX2341X_ENC_SET_OUTPUT_PORT, 1, 0); /* 0 = Memory */ + + if (old == NULL || old->is_50hz != new->is_50hz) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_FRAME_RATE, 1, new->is_50hz); + if (err) return err; + } + + if (old == NULL || old->width != new->width || old->height != new->height || + old->video_encoding != new->video_encoding) { + u16 w = new->width; + u16 h = new->height; + + if (new->video_encoding == V4L2_MPEG_VIDEO_ENCODING_MPEG_1) { + w /= 2; + h /= 2; + } + err = cx2341x_api(priv, func, CX2341X_ENC_SET_FRAME_SIZE, 2, h, w); + if (err) return err; + } + + if (old == NULL || old->stream_type != new->stream_type) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_STREAM_TYPE, 1, mpeg_stream_type[new->stream_type]); + if (err) return err; + } + if (old == NULL || old->video_aspect != new->video_aspect) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_ASPECT_RATIO, 1, 1 + new->video_aspect); + if (err) return err; + } + if (old == NULL || old->video_b_frames != new->video_b_frames || + old->video_gop_size != new->video_gop_size) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_GOP_PROPERTIES, 2, + new->video_gop_size, new->video_b_frames + 1); + if (err) return err; + } + if (old == NULL || old->video_gop_closure != new->video_gop_closure) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_GOP_CLOSURE, 1, new->video_gop_closure); + if (err) return err; + } + if (old == NULL || old->video_pulldown != new->video_pulldown) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_3_2_PULLDOWN, 1, new->video_pulldown); + if (err) return err; + } + if (old == NULL || old->audio_properties != new->audio_properties) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_AUDIO_PROPERTIES, 1, new->audio_properties); + if (err) return err; + } + if (old == NULL || old->video_bitrate_mode != new->video_bitrate_mode || + old->video_bitrate != new->video_bitrate || + old->video_bitrate_peak != new->video_bitrate_peak) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_BIT_RATE, 5, + new->video_bitrate_mode, new->video_bitrate, + new->video_bitrate_peak / 400, 0, 0); + if (err) return err; + } + if (old == NULL || old->video_spatial_filter_mode != new->video_spatial_filter_mode || + old->video_temporal_filter_mode != new->video_temporal_filter_mode || + old->video_median_filter_type != new->video_median_filter_type) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_DNR_FILTER_MODE, 2, + new->video_spatial_filter_mode | (new->video_temporal_filter_mode << 1), + new->video_median_filter_type); + if (err) return err; + } + if (old == NULL || + old->video_luma_median_filter_bottom != new->video_luma_median_filter_bottom || + old->video_luma_median_filter_top != new->video_luma_median_filter_top || + old->video_chroma_median_filter_bottom != new->video_chroma_median_filter_bottom || + old->video_chroma_median_filter_top != new->video_chroma_median_filter_top) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_CORING_LEVELS, 4, + new->video_luma_median_filter_bottom, + new->video_luma_median_filter_top, + new->video_chroma_median_filter_bottom, + new->video_chroma_median_filter_top); + if (err) return err; + } + if (old == NULL || + old->video_luma_spatial_filter_type != new->video_luma_spatial_filter_type || + old->video_chroma_spatial_filter_type != new->video_chroma_spatial_filter_type) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_SPATIAL_FILTER_TYPE, 2, + new->video_luma_spatial_filter_type, new->video_chroma_spatial_filter_type); + if (err) return err; + } + if (old == NULL || + old->video_spatial_filter != new->video_spatial_filter || + old->video_temporal_filter != new->video_temporal_filter) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_DNR_FILTER_PROPS, 2, + new->video_spatial_filter, new->video_temporal_filter); + if (err) return err; + } + if (old == NULL || old->video_temporal_decimation != new->video_temporal_decimation) { + err = cx2341x_api(priv, func, CX2341X_ENC_SET_FRAME_DROP_RATE, 1, + new->video_temporal_decimation); + if (err) return err; + } + return 0; +} + +static const char *cx2341x_menu_item(struct cx2341x_mpeg_params *p, u32 id) +{ + const char **menu = cx2341x_ctrl_get_menu(id); + struct v4l2_ext_control ctrl; + + if (menu == NULL) + goto invalid; + ctrl.id = id; + if (cx2341x_get_ctrl(p, &ctrl)) + goto invalid; + while (ctrl.value-- && *menu) menu++; + if (*menu == NULL) + goto invalid; + return *menu; + +invalid: + return ""; +} + +void cx2341x_log_status(struct cx2341x_mpeg_params *p, int card_id) +{ + int is_mpeg1 = p->video_encoding == V4L2_MPEG_VIDEO_ENCODING_MPEG_1; + + /* Stream */ + printk(KERN_INFO "cx2341x-%d: Stream: %s\n", + card_id, + cx2341x_menu_item(p, V4L2_CID_MPEG_STREAM_TYPE)); + + /* Video */ + printk(KERN_INFO "cx2341x-%d: Video: %dx%d, %d fps\n", + card_id, + p->width / (is_mpeg1 ? 2 : 1), p->height / (is_mpeg1 ? 2 : 1), + p->is_50hz ? 25 : 30); + printk(KERN_INFO "cx2341x-%d: Video: %s, %s, %s, %d", + card_id, + cx2341x_menu_item(p, V4L2_CID_MPEG_VIDEO_ENCODING), + cx2341x_menu_item(p, V4L2_CID_MPEG_VIDEO_ASPECT), + cx2341x_menu_item(p, V4L2_CID_MPEG_VIDEO_BITRATE_MODE), + p->video_bitrate); + if (p->video_bitrate_mode == V4L2_MPEG_VIDEO_BITRATE_MODE_VBR) { + printk(", Peak %d", p->video_bitrate_peak); + } + printk("\n"); + printk(KERN_INFO "cx2341x-%d: Video: GOP Size %d, %d B-Frames, %sGOP Closure, %s3:2 Pulldown\n", + card_id, + p->video_gop_size, p->video_b_frames, + p->video_gop_closure ? "" : "No ", + p->video_pulldown ? "" : "No "); + if (p->video_temporal_decimation) { + printk(KERN_INFO "cx2341x-%d: Video: Temporal Decimation %d\n", + card_id, p->video_temporal_decimation); + } + + /* Audio */ + printk(KERN_INFO "cx2341x-%d: Audio: %s, %s, %s, %s", + card_id, + cx2341x_menu_item(p, V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ), + cx2341x_menu_item(p, V4L2_CID_MPEG_AUDIO_ENCODING), + cx2341x_menu_item(p, V4L2_CID_MPEG_AUDIO_L2_BITRATE), + cx2341x_menu_item(p, V4L2_CID_MPEG_AUDIO_MODE)); + if (p->audio_mode == V4L2_MPEG_AUDIO_MODE_JOINT_STEREO) { + printk(", %s", + cx2341x_menu_item(p, V4L2_CID_MPEG_AUDIO_MODE_EXTENSION)); + } + printk(", %s, %s\n", + cx2341x_menu_item(p, V4L2_CID_MPEG_AUDIO_EMPHASIS), + cx2341x_menu_item(p, V4L2_CID_MPEG_AUDIO_CRC)); + + /* Encoding filters */ + printk(KERN_INFO "cx2341x-%d: Spatial Filter: %s, Luma %s, Chroma %s, %d\n", + card_id, + cx2341x_menu_item(p, V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE), + cx2341x_menu_item(p, V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE), + cx2341x_menu_item(p, V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE), + p->video_spatial_filter); + printk(KERN_INFO "cx2341x-%d: Temporal Filter: %s, %d\n", + card_id, + cx2341x_menu_item(p, V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE), + p->video_temporal_filter); + printk(KERN_INFO "cx2341x-%d: Median Filter: %s, Luma [%d, %d], Chroma [%d, %d]\n", + card_id, + cx2341x_menu_item(p, V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE), + p->video_luma_median_filter_bottom, + p->video_luma_median_filter_top, + p->video_chroma_median_filter_bottom, + p->video_chroma_median_filter_top); +} + +EXPORT_SYMBOL(cx2341x_fill_defaults); +EXPORT_SYMBOL(cx2341x_ctrl_query); +EXPORT_SYMBOL(cx2341x_ctrl_get_menu); +EXPORT_SYMBOL(cx2341x_ext_ctrls); +EXPORT_SYMBOL(cx2341x_update); +EXPORT_SYMBOL(cx2341x_log_status); + +/* + * Local variables: + * c-basic-offset: 8 + * End: + */ + diff --git a/linux/drivers/media/video/cx88/Kconfig b/linux/drivers/media/video/cx88/Kconfig index c092d2219..91e1c481a 100644 --- a/linux/drivers/media/video/cx88/Kconfig +++ b/linux/drivers/media/video/cx88/Kconfig @@ -11,6 +11,7 @@ config VIDEO_CX88 select VIDEO_BUF select VIDEO_TUNER select VIDEO_TVEEPROM + select VIDEO_CX2341X select VIDEO_IR ---help--- This is a video4linux driver for Conexant 2388x based diff --git a/linux/drivers/media/video/pvrusb2/Kconfig b/linux/drivers/media/video/pvrusb2/Kconfig index 4a7f88484..298b1c71a 100644 --- a/linux/drivers/media/video/pvrusb2/Kconfig +++ b/linux/drivers/media/video/pvrusb2/Kconfig @@ -4,6 +4,7 @@ config VIDEO_PVRUSB2 select FW_LOADER select VIDEO_TUNER select VIDEO_TVEEPROM + select VIDEO_CX2341X select VIDEO_SAA711X select VIDEO_MSP3400 ---help--- diff --git a/linux/drivers/media/video/pvrusb2/pvrusb2-encoder.c b/linux/drivers/media/video/pvrusb2/pvrusb2-encoder.c index 6c66e258f..958500466 100644 --- a/linux/drivers/media/video/pvrusb2/pvrusb2-encoder.c +++ b/linux/drivers/media/video/pvrusb2/pvrusb2-encoder.c @@ -20,8 +20,10 @@ * */ +#include "compat.h" #include // for linux/firmware.h #include +#include #include #include "pvrusb2-util.h" #include "pvrusb2-encoder.h" diff --git a/linux/drivers/media/video/pvrusb2/pvrusb2-hdw.c b/linux/drivers/media/video/pvrusb2/pvrusb2-hdw.c index 333419d6f..409343097 100644 --- a/linux/drivers/media/video/pvrusb2/pvrusb2-hdw.c +++ b/linux/drivers/media/video/pvrusb2/pvrusb2-hdw.c @@ -25,6 +25,7 @@ #include #include #include +#include #include #include "pvrusb2.h" #include "pvrusb2-std.h" diff --git a/linux/include/media/cx2341x.h b/linux/include/media/cx2341x.h index 7e7dcc072..81ebead2d 100644 --- a/linux/include/media/cx2341x.h +++ b/linux/include/media/cx2341x.h @@ -19,6 +19,66 @@ #ifndef CX2341X_H #define CX2341X_H +struct cx2341x_mpeg_params { + /* misc */ + u16 width; + u16 height; + u16 is_50hz; + + /* stream */ + enum v4l2_mpeg_stream_type stream_type; + + /* audio */ + enum v4l2_mpeg_audio_sampling_freq audio_sampling_freq; + enum v4l2_mpeg_audio_encoding audio_encoding; + enum v4l2_mpeg_audio_l2_bitrate audio_l2_bitrate; + enum v4l2_mpeg_audio_mode audio_mode; + enum v4l2_mpeg_audio_mode_extension audio_mode_extension; + enum v4l2_mpeg_audio_emphasis audio_emphasis; + enum v4l2_mpeg_audio_crc audio_crc; + u8 audio_properties; + + /* video */ + enum v4l2_mpeg_video_encoding video_encoding; + enum v4l2_mpeg_video_aspect video_aspect; + u16 video_b_frames; + u16 video_gop_size; + u16 video_gop_closure; + u16 video_pulldown; + enum v4l2_mpeg_video_bitrate_mode video_bitrate_mode; + u32 video_bitrate; + u32 video_bitrate_peak; + u16 video_temporal_decimation; + + /* encoding filters */ + enum v4l2_mpeg_cx2341x_video_spatial_filter_mode video_spatial_filter_mode; + u16 video_spatial_filter; + enum v4l2_mpeg_cx2341x_video_luma_spatial_filter_type video_luma_spatial_filter_type; + enum v4l2_mpeg_cx2341x_video_chroma_spatial_filter_type video_chroma_spatial_filter_type; + enum v4l2_mpeg_cx2341x_video_temporal_filter_mode video_temporal_filter_mode; + u16 video_temporal_filter; + enum v4l2_mpeg_cx2341x_video_median_filter_type video_median_filter_type; + u16 video_luma_median_filter_top; + u16 video_luma_median_filter_bottom; + u16 video_chroma_median_filter_top; + u16 video_chroma_median_filter_bottom; +}; + +#define CX2341X_MBOX_MAX_DATA 16 + +typedef int (*cx2341x_mbox_func)(void *priv, int cmd, int in, int out, + u32 data[CX2341X_MBOX_MAX_DATA]); +int cx2341x_update(void *priv, cx2341x_mbox_func func, + const struct cx2341x_mpeg_params *old, + const struct cx2341x_mpeg_params *new); +int cx2341x_ctrl_query(struct cx2341x_mpeg_params *params, + struct v4l2_queryctrl *qctrl); +const char **cx2341x_ctrl_get_menu(u32 id); +int cx2341x_ext_ctrls(struct cx2341x_mpeg_params *params, + struct v4l2_ext_controls *ctrls, int cmd); +void cx2341x_fill_defaults(struct cx2341x_mpeg_params *p); +void cx2341x_log_status(struct cx2341x_mpeg_params *p, int cardid); + /* Firmware names */ #define CX2341X_FIRM_ENC_FILENAME "v4l-cx2341x-enc.fw" /* Decoder firmware for the cx23415 only */ diff --git a/v4l/versions.txt b/v4l/versions.txt index 35cb44fc6..e7339be5d 100644 --- a/v4l/versions.txt +++ b/v4l/versions.txt @@ -206,3 +206,4 @@ VIDEO_BUF_DVB VIDEO_BTCX VIDEO_IR VIDEO_TVEEPROM +VIDEO_CX2341X -- cgit v1.2.3 From 0c29a3df704c348859725c6d26f9c184c546e960 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Sun, 18 Jun 2006 19:49:52 +0200 Subject: Use control helpers for saa7115, cx25840, msp3400. From: Hans Verkuil Replace hardcoded control description by the standard ones supplied by v4l2-common. Signed-off-by: Hans Verkuil --- linux/drivers/media/video/cx25840/cx25840-core.c | 119 ++++------------------- linux/drivers/media/video/msp3400-driver.c | 89 +++-------------- linux/drivers/media/video/saa7115.c | 58 ++--------- 3 files changed, 44 insertions(+), 222 deletions(-) diff --git a/linux/drivers/media/video/cx25840/cx25840-core.c b/linux/drivers/media/video/cx25840/cx25840-core.c index 16c8f9366..6558e317a 100644 --- a/linux/drivers/media/video/cx25840/cx25840-core.c +++ b/linux/drivers/media/video/cx25840/cx25840-core.c @@ -628,95 +628,6 @@ static int set_v4lfmt(struct i2c_client *client, struct v4l2_format *fmt) /* ----------------------------------------------------------------------- */ -static struct v4l2_queryctrl cx25836_qctrl[] = { - { - .id = V4L2_CID_BRIGHTNESS, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Brightness", - .minimum = 0, - .maximum = 255, - .step = 1, - .default_value = 128, - .flags = 0, - }, { - .id = V4L2_CID_CONTRAST, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Contrast", - .minimum = 0, - .maximum = 127, - .step = 1, - .default_value = 64, - .flags = 0, - }, { - .id = V4L2_CID_SATURATION, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Saturation", - .minimum = 0, - .maximum = 127, - .step = 1, - .default_value = 64, - .flags = 0, - }, { - .id = V4L2_CID_HUE, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Hue", - .minimum = -128, - .maximum = 127, - .step = 1, - .default_value = 0, - .flags = 0, - }, -}; - -static struct v4l2_queryctrl cx25840_qctrl[] = { - { - .id = V4L2_CID_AUDIO_VOLUME, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Volume", - .minimum = 0, - .maximum = 65535, - .step = 65535/100, - .default_value = 58880, - .flags = 0, - }, { - .id = V4L2_CID_AUDIO_BALANCE, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Balance", - .minimum = 0, - .maximum = 65535, - .step = 65535/100, - .default_value = 32768, - .flags = 0, - }, { - .id = V4L2_CID_AUDIO_MUTE, - .type = V4L2_CTRL_TYPE_BOOLEAN, - .name = "Mute", - .minimum = 0, - .maximum = 1, - .step = 1, - .default_value = 1, - .flags = 0, - }, { - .id = V4L2_CID_AUDIO_BASS, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Bass", - .minimum = 0, - .maximum = 65535, - .step = 65535/100, - .default_value = 32768, - }, { - .id = V4L2_CID_AUDIO_TREBLE, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Treble", - .minimum = 0, - .maximum = 65535, - .step = 65535/100, - .default_value = 32768, - }, -}; - -/* ----------------------------------------------------------------------- */ - static int cx25840_command(struct i2c_client *client, unsigned int cmd, void *arg) { @@ -784,21 +695,29 @@ static int cx25840_command(struct i2c_client *client, unsigned int cmd, case VIDIOC_QUERYCTRL: { struct v4l2_queryctrl *qc = arg; - int i; - for (i = 0; i < ARRAY_SIZE(cx25836_qctrl); i++) - if (qc->id && qc->id == cx25836_qctrl[i].id) { - memcpy(qc, &cx25836_qctrl[i], sizeof(*qc)); - return 0; - } + switch (qc->id) { + case V4L2_CID_BRIGHTNESS: + case V4L2_CID_CONTRAST: + case V4L2_CID_SATURATION: + case V4L2_CID_HUE: + return v4l2_ctrl_query_fill_std(qc); + default: + break; + } if (state->is_cx25836) return -EINVAL; - for (i = 0; i < ARRAY_SIZE(cx25840_qctrl); i++) - if (qc->id && qc->id == cx25840_qctrl[i].id) { - memcpy(qc, &cx25840_qctrl[i], sizeof(*qc)); - return 0; - } + switch (qc->id) { + case V4L2_CID_AUDIO_VOLUME: + case V4L2_CID_AUDIO_MUTE: + case V4L2_CID_AUDIO_BALANCE: + case V4L2_CID_AUDIO_BASS: + case V4L2_CID_AUDIO_TREBLE: + return v4l2_ctrl_query_fill_std(qc); + default: + return -EINVAL; + } return -EINVAL; } diff --git a/linux/drivers/media/video/msp3400-driver.c b/linux/drivers/media/video/msp3400-driver.c index 837894adb..5e209a36b 100644 --- a/linux/drivers/media/video/msp3400-driver.c +++ b/linux/drivers/media/video/msp3400-driver.c @@ -437,67 +437,6 @@ static int msp_mode_v4l1_to_v4l2(int mode) return V4L2_TUNER_MODE_MONO; } -static struct v4l2_queryctrl msp_qctrl_std[] = { - { - .id = V4L2_CID_AUDIO_VOLUME, - .name = "Volume", - .minimum = 0, - .maximum = 65535, - .step = 65535/100, - .default_value = 58880, - .flags = 0, - .type = V4L2_CTRL_TYPE_INTEGER, - },{ - .id = V4L2_CID_AUDIO_MUTE, - .name = "Mute", - .minimum = 0, - .maximum = 1, - .step = 1, - .default_value = 1, - .flags = 0, - .type = V4L2_CTRL_TYPE_BOOLEAN, - }, -}; - -static struct v4l2_queryctrl msp_qctrl_sound_processing[] = { - { - .id = V4L2_CID_AUDIO_BALANCE, - .name = "Balance", - .minimum = 0, - .maximum = 65535, - .step = 65535/100, - .default_value = 32768, - .flags = 0, - .type = V4L2_CTRL_TYPE_INTEGER, - },{ - .id = V4L2_CID_AUDIO_BASS, - .name = "Bass", - .minimum = 0, - .maximum = 65535, - .step = 65535/100, - .default_value = 32768, - .type = V4L2_CTRL_TYPE_INTEGER, - },{ - .id = V4L2_CID_AUDIO_TREBLE, - .name = "Treble", - .minimum = 0, - .maximum = 65535, - .step = 65535/100, - .default_value = 32768, - .type = V4L2_CTRL_TYPE_INTEGER, - },{ - .id = V4L2_CID_AUDIO_LOUDNESS, - .name = "Loudness", - .minimum = 0, - .maximum = 1, - .step = 1, - .default_value = 1, - .flags = 0, - .type = V4L2_CTRL_TYPE_BOOLEAN, - }, -}; - - static int msp_get_ctrl(struct i2c_client *client, struct v4l2_control *ctrl) { struct msp_state *state = i2c_get_clientdata(client); @@ -805,21 +744,25 @@ static int msp_command(struct i2c_client *client, unsigned int cmd, void *arg) case VIDIOC_QUERYCTRL: { struct v4l2_queryctrl *qc = arg; - int i; - for (i = 0; i < ARRAY_SIZE(msp_qctrl_std); i++) - if (qc->id && qc->id == msp_qctrl_std[i].id) { - memcpy(qc, &msp_qctrl_std[i], sizeof(*qc)); - return 0; - } + switch (qc->id) { + case V4L2_CID_AUDIO_VOLUME: + case V4L2_CID_AUDIO_MUTE: + return v4l2_ctrl_query_fill_std(qc); + default: + break; + } if (!state->has_sound_processing) return -EINVAL; - for (i = 0; i < ARRAY_SIZE(msp_qctrl_sound_processing); i++) - if (qc->id && qc->id == msp_qctrl_sound_processing[i].id) { - memcpy(qc, &msp_qctrl_sound_processing[i], sizeof(*qc)); - return 0; - } - return -EINVAL; + switch (qc->id) { + case V4L2_CID_AUDIO_LOUDNESS: + case V4L2_CID_AUDIO_BALANCE: + case V4L2_CID_AUDIO_BASS: + case V4L2_CID_AUDIO_TREBLE: + return v4l2_ctrl_query_fill_std(qc); + default: + return -EINVAL; + } } case VIDIOC_G_CTRL: diff --git a/linux/drivers/media/video/saa7115.c b/linux/drivers/media/video/saa7115.c index ea7c7c65b..fdfea3f16 100644 --- a/linux/drivers/media/video/saa7115.c +++ b/linux/drivers/media/video/saa7115.c @@ -1103,48 +1103,6 @@ static void saa7115_decode_vbi_line(struct i2c_client *client, /* ============ SAA7115 AUDIO settings (end) ============= */ -static struct v4l2_queryctrl saa7115_qctrl[] = { - { - .id = V4L2_CID_BRIGHTNESS, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Brightness", - .minimum = 0, - .maximum = 255, - .step = 1, - .default_value = 128, - .flags = 0, - }, { - .id = V4L2_CID_CONTRAST, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Contrast", - .minimum = 0, - .maximum = 127, - .step = 1, - .default_value = 64, - .flags = 0, - }, { - .id = V4L2_CID_SATURATION, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Saturation", - .minimum = 0, - .maximum = 127, - .step = 1, - .default_value = 64, - .flags = 0, - }, { - .id = V4L2_CID_HUE, - .type = V4L2_CTRL_TYPE_INTEGER, - .name = "Hue", - .minimum = -128, - .maximum = 127, - .step = 1, - .default_value = 0, - .flags = 0, - }, -}; - -/* ----------------------------------------------------------------------- */ - static int saa7115_command(struct i2c_client *client, unsigned int cmd, void *arg) { struct saa7115_state *state = i2c_get_clientdata(client); @@ -1188,14 +1146,16 @@ static int saa7115_command(struct i2c_client *client, unsigned int cmd, void *ar case VIDIOC_QUERYCTRL: { struct v4l2_queryctrl *qc = arg; - int i; - for (i = 0; i < ARRAY_SIZE(saa7115_qctrl); i++) - if (qc->id && qc->id == saa7115_qctrl[i].id) { - memcpy(qc, &saa7115_qctrl[i], sizeof(*qc)); - return 0; - } - return -EINVAL; + switch (qc->id) { + case V4L2_CID_BRIGHTNESS: + case V4L2_CID_CONTRAST: + case V4L2_CID_SATURATION: + case V4L2_CID_HUE: + return v4l2_ctrl_query_fill_std(qc); + default: + return -EINVAL; + } } case VIDIOC_G_STD: -- cgit v1.2.3 From 3c52e7d852cc06e7ebfcb96ff703f116eefb26c9 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Sun, 18 Jun 2006 19:56:12 +0200 Subject: Update cx2341x fw encoding API doc. From: Hans Verkuil Based on recent tests it turned out that some features are not implemented. This has now been documented. Signed-off-by: Hans Verkuil --- .../video4linux/cx2341x/fw-encoder-api.txt | 20 ++++++++++++++++++-- 1 file changed, 18 insertions(+), 2 deletions(-) diff --git a/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt b/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt index 64cd11134..58c7243d0 100644 --- a/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt +++ b/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt @@ -100,13 +100,20 @@ Param[1] Name CX2341X_ENC_SET_BIT_RATE Enum 149/0x95 Description - Assign average video stream bitrate. + Assign average video stream bitrate. Note on the last three params: + Param[3] and [4] seem to be always 0, param [5] doesn't seem to be used. Param[0] 0=variable bitrate, 1=constant bitrate Param[1] bitrate in bits per second Param[2] peak bitrate in bits per second, divided by 400 +Param[3] + Mux bitrate in bits per second, divided by 400. May be 0 (default). +Param[4] + Rate Control VBR Padding +Param[5] + VBV Buffer used by encoder ------------------------------------------------------------------------------- @@ -115,10 +122,11 @@ Enum 151/0x97 Description Setup the GOP structure Param[0] - GOP size + GOP size (maximum is 34) Param[1] Number of B frames between the I and P frame, plus 1. For example: IBBPBBPBBPBB --> GOP size: 12, number of B frames: 2+1 = 3 + Note that GOP size must be a multiple of (B-frames + 1). ------------------------------------------------------------------------------- @@ -241,6 +249,9 @@ Name CX2341X_ENC_SET_STREAM_TYPE Enum 185/0xB9 Description Assign stream type + Note: Transport stream is not working in recent firmwares. + And in older firmwares the timestamps in the TS seem to be + unreliable. Param[0] 0=Program stream 1=Transport stream @@ -278,6 +289,8 @@ Description '01' Layer III '00' Undefined This discrepancy may indicate a possible error in the documentation. + Testing indicated that only Layer II is actually working, and that + the minimum bitrate should be 192 kbps. Param[0] Bitmask: 0:1 '00' 44.1Khz @@ -313,6 +326,9 @@ Param[0] '01'=JointStereo '10'=Dual '11'=Mono + Note: testing seems to indicate that Mono and possibly + JointStereo are not working (default to stereo). + Dual does work, though. 10:11 Mode Extension used in joint_stereo mode. In Layer I and II they indicate which subbands are in -- cgit v1.2.3 From c1c781e4584001dda2e11a7ad34aba4d77b3d0e3 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Sun, 18 Jun 2006 19:59:25 +0200 Subject: Add v4l2-ctl test tool. From: Hans Verkuil v4l2-ctl can be used to query and set most v4l2 ioctls. Very useful while testing. Signed-off-by: Hans Verkuil --- test/Makefile | 3 +- test/v4l2-ctl.cpp | 1249 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 1251 insertions(+), 1 deletion(-) create mode 100644 test/v4l2-ctl.cpp diff --git a/test/Makefile b/test/Makefile index 8623e4d98..79e90417b 100644 --- a/test/Makefile +++ b/test/Makefile @@ -1,7 +1,8 @@ -FILES = ioctl-test sliced-vbi-test sliced-vbi-detect vbi-test +FILES = ioctl-test sliced-vbi-test sliced-vbi-detect vbi-test v4l2-ctl CC = gcc LIBS = CFLAGS = -O3 -Wall -fomit-frame-pointer -funroll-loops -g -I ../linux/include +CXXFLAGS = $(CFLAGS) LDFLAGS = all: $(FILES) diff --git a/test/v4l2-ctl.cpp b/test/v4l2-ctl.cpp new file mode 100644 index 000000000..ade779546 --- /dev/null +++ b/test/v4l2-ctl.cpp @@ -0,0 +1,1249 @@ +/* + Copyright (C) 2003-2004 Kevin Thayer + + Cleanup and VBI and audio in/out options: + Copyright (C) 2004 Hans Verkuil + + 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., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#include +#include /* Uses _GNU_SOURCE to define getsubopt in stdlib.h */ +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define __user +#include + +#include +#include +#include +#include + +/* Short option list + + Please keep in alphabetical order. + That makes it easier to see which short options are still free. + + In general the lower case is used to set something and the upper + case is used to retrieve a setting. */ +enum Option { + OptGetAudioInput = 'A', + OptSetAudioInput = 'a', + OptGetAudioOutput = 'B', + OptSetAudioOutput = 'b', + OptGetCtrl = 'C', + OptSetCtrl = 'c', + OptSetDevice = 'd', + OptGetDriverInfo = 'D', + OptGetFreq = 'F', + OptSetFreq = 'f', + OptHelp = 'h', + OptGetInput = 'I', + OptSetInput = 'i', + OptListCtrls = 'l', + OptListCtrlsMenus = 'L', + OptListOutputs = 'N', + OptListInputs = 'n', + OptGetOutput = 'O', + OptSetOutput = 'o', + OptListAudioOutputs = 'Q', + OptListAudioInputs = 'q', + OptGetStandard = 'S', + OptSetStandard = 's', + OptGetTuner = 'T', + OptSetTuner = 't', + OptGetVideoFormat = 'V', + OptSetVideoFormat = 'v', + OptLast = 128 +}; + +static char options[OptLast]; +static int option_all = 0; +static int option_streamoff = 0; +static int option_streamon = 0; +static int option_list_stds = 0; +static int option_version = 0; +static int option_log_status = 0; +static int option_verbose = 0; + +typedef std::vector ctrl_list; +static ctrl_list user_ctrls; +static ctrl_list mpeg_ctrls; + +typedef std::map ctrl_strmap; +static ctrl_strmap ctrl_str2id; +typedef std::map ctrl_idmap; +static ctrl_idmap ctrl_id2str; + +typedef std::list ctrl_get_list; +static ctrl_get_list get_ctrls; + +typedef std::map ctrl_set_map; +static ctrl_set_map set_ctrls; + +/* fmts specified */ +#define FMTWidth (1L<<0) +#define FMTHeight (1L<<1) + +static struct option long_options[] = { + {"list-audio-inputs", no_argument, 0, OptListAudioInputs}, + {"list-audio-outputs", no_argument, 0, OptListAudioOutputs}, + {"all", no_argument, &option_all, 1}, + {"device", required_argument, 0, OptSetDevice}, + {"get-format", no_argument, 0, OptGetVideoFormat}, + {"set-format", required_argument, 0, OptSetVideoFormat}, + {"help", no_argument, 0, OptHelp}, + {"get-output", no_argument, 0, OptGetOutput}, + {"set-output", required_argument, 0, OptSetOutput}, + {"list-outputs", no_argument, 0, OptListOutputs}, + {"list-inputs", no_argument, 0, OptListInputs}, + {"get-input", no_argument, 0, OptGetInput}, + {"set-input", required_argument, 0, OptSetInput}, + {"get-audio-input", no_argument, 0, OptGetAudioInput}, + {"set-audio-input", required_argument, 0, OptSetAudioInput}, + {"get-audio-output", no_argument, 0, OptGetAudioOutput}, + {"set-audio-output", required_argument, 0, OptSetAudioOutput}, + {"get-freq", no_argument, 0, OptGetFreq}, + {"set-freq", required_argument, 0, OptSetFreq}, + {"streamoff", no_argument, &option_streamoff, 1}, + {"streamon", no_argument, &option_streamon, 1}, + {"list-standards", no_argument, &option_list_stds, 1}, + {"get-standard", no_argument, 0, OptGetStandard}, + {"set-standard", required_argument, 0, OptSetStandard}, + {"info", no_argument, 0, OptGetDriverInfo}, + {"list-ctrls", no_argument, 0, OptListCtrls}, + {"list-ctrls-menus", no_argument, 0, OptListCtrlsMenus}, + {"set-ctrl", required_argument, 0, OptSetCtrl}, + {"get-ctrl", required_argument, 0, OptGetCtrl}, + {"get-tuner", no_argument, 0, OptGetTuner}, + {"set-tuner", required_argument, 0, OptSetTuner}, + {"version", no_argument, &option_version, 1}, + {"verbose", no_argument, &option_verbose, 1}, + {"log-status", no_argument, &option_log_status, 1}, + {0, 0, 0, 0} +}; + +void usage(void) +{ + printf("Usage:\n"); + printf(" --all display all information available\n"); + printf(" -A, --get-audio-input\n"); + printf(" query the current audio input [VIDIOC_G_AUDIO]\n"); + printf(" -a, --set-audio-input=\n"); + printf(" set the current audio input to [VIDIOC_S_AUDIO]\n"); + printf(" -B, --get-audio-output\n"); + printf(" query the current audio output [VIDIOC_G_AUDOUT]\n"); + printf(" -b, --set-audio-output=\n"); + printf(" set the current audio output to [VIDIOC_S_AUDOUT]\n"); + printf(" -C, --get-ctrl=[,...]\n"); + printf(" get the value of the controls [VIDIOC_G_EXT_CTRLS]\n"); + printf(" -c, --set-ctrl==[,=...]\n"); + printf(" set the controls to the values specified [VIDIOC_S_EXT_CTRLS]\n"); + printf(" -D, --info show driver info [VIDIOC_QUERYCAP]\n"); + printf(" -d, --device= use device instead of /dev/video0 [VIDIOC_S_EXT_CTRLS]\n"); + printf(" if is a single digit, then /dev/video is used\n"); + printf(" -F, --get-freq query the current frequency [VIDIOC_G_FREQUENCY]\n"); + printf(" -f, --set-freq=\n"); + printf(" set the current frequency to MHz [VIDIOC_S_FREQUENCY]\n"); + printf(" -h, --help display this help message\n"); + printf(" -I, --get-input query the current video input [VIDIOC_G_INPUT]\n"); + printf(" -i, --set-input=\n"); + printf(" set the current video input to [VIDIOC_S_INPUT]\n"); + printf(" -l, --list-ctrls display all controls and their values [VIDIOC_QUERYCTRL]\n"); + printf(" -L, --list-ctrls-menus\n"); + printf(" display all controls, their values and the menus [VIDIOC_QUERYMENU]\n"); + printf(" -N, --list-outputs display video outputs [VIDIOC_ENUMOUTPUT]\n"); + printf(" -n, --list-inputs display video inputs [VIDIOC_ENUMINPUT]\n"); + printf(" -O, --get-output query the current video output [VIDIOC_G_OUTPUT]\n"); + printf(" -o, --set-output=\n"); + printf(" set the current video output to [VIDIOC_S_OUTPUT]\n"); + printf(" -Q, --list-audio-outputs\n"); + printf(" display audio outputs [VIDIOC_ENUMAUDOUT]\n"); + printf(" -q, --list-audio-inputs\n"); + printf(" display audio inputs [VIDIOC_ENUMAUDIO]\n"); + printf(" -S, --get-standard\n"); + printf(" query the current video standard [VIDIOC_G_STD]\n"); + printf(" -s, --set-standard=\n"); + printf(" set the current video standard to [VIDIOC_S_STD]\n"); + printf(" can be a numerical v4l2_std value, or it can be one of:\n"); + printf(" pal-X (X = B/G/H/N/Nc/I/D/K/M) or just 'pal' (V4L2_STD_PAL)\n"); + printf(" ntsc-X (X = M/J/K) or just 'ntsc' (V4L2_STD_NTSC)\n"); + printf(" secam-X (X = B/G/H/D/K/L/Lc) or just 'secam' (V4L2_STD_SECAM)\n"); + printf(" --list-standards display supported video standards [VIDIOC_ENUMSTD]\n"); + printf(" -T, --get-tuner query the current tuner settings [VIDIOC_G_TUNER]\n"); + printf(" -t, --set-tuner=\n"); + printf(" set the audio mode of the tuner [VIDIOC_S_TUNER]\n"); + printf(" -V, --get-format query the current data format [VIDIOC_G_FMT]\n"); + printf(" -v, --set-format=width=,height=\n"); + printf(" set the current data format [VIDIOC_S_FMT]\n"); + printf(" Possible values: 0 (mono), 1 (stereo), 2 (lang2), 3 (lang1), 4 (both)\n"); + printf(" --verbose turn on verbose ioctl error reporting.\n"); + printf(" --version shows the version number of this utility.\n"); + printf("\n"); + printf("Expert options:\n"); + printf(" --streamoff turn the stream off [VIDIOC_STREAMOFF]\n"); + printf(" --streamon turn the stream on [VIDIOC_STREAMOFF]\n"); + printf(" --log-status log the board status in the kernel log [VIDIOC_LOG_STATUS]\n"); + exit(0); +} + + +static std::string name2var(unsigned char *name) +{ + std::string s; + + while (*name) { + if (*name == ' ') s += "_"; + else s += std::string(1, tolower(*name)); + name++; + } + return s; +} + +static void print_qctrl(int fd, struct v4l2_queryctrl *queryctrl, + struct v4l2_ext_control *ctrl, int show_menus) +{ + struct v4l2_querymenu qmenu = { 0 }; + std::string s = name2var(queryctrl->name); + int i; + + qmenu.id = queryctrl->id; + switch (queryctrl->type) { + case V4L2_CTRL_TYPE_INTEGER: + printf("%31s (int) : min=%d max=%d step=%d default=%d value=%d", + s.c_str(), + queryctrl->minimum, queryctrl->maximum, + queryctrl->step, queryctrl->default_value, + ctrl->value); + break; + case V4L2_CTRL_TYPE_INTEGER64: + printf("%31s (int64): value=%lld", queryctrl->name, ctrl->value64); + break; + case V4L2_CTRL_TYPE_BOOLEAN: + printf("%31s (bool) : default=%d value=%d", + s.c_str(), + queryctrl->default_value, ctrl->value); + break; + case V4L2_CTRL_TYPE_MENU: + printf("%31s (menu) : min=%d max=%d default=%d value=%d", + s.c_str(), + queryctrl->minimum, queryctrl->maximum, + queryctrl->default_value, ctrl->value); + break; + case V4L2_CTRL_TYPE_BUTTON: + printf("%31s (button)\n", s.c_str()); + break; + default: break; + } + if (queryctrl->flags) { + printf(" flags="); + if (queryctrl->flags & V4L2_CTRL_FLAG_GRABBED) + printf("grabbed "); + if (queryctrl->flags & V4L2_CTRL_FLAG_READ_ONLY) + printf("readonly "); + if (queryctrl->flags & V4L2_CTRL_FLAG_UPDATE) + printf("update "); + if (queryctrl->flags & V4L2_CTRL_FLAG_INACTIVE) + printf("inactive "); + if (queryctrl->flags & V4L2_CTRL_FLAG_SLIDER) + printf("slider "); + } + printf("\n"); + if (queryctrl->type == V4L2_CTRL_TYPE_MENU && show_menus) { + for (i = 0; i <= queryctrl->maximum; i++) { + qmenu.index = i; + if (ioctl(fd, VIDIOC_QUERYMENU, &qmenu)) + continue; + printf("\t\t\t\t%d: %s\n", i, qmenu.name); + } + } +} + +static int print_control(int fd, struct v4l2_queryctrl &qctrl, int show_menus) +{ + struct v4l2_control ctrl = { 0 }; + struct v4l2_ext_control ext_ctrl = { 0 }; + struct v4l2_ext_controls ctrls = { 0 }; + + if (qctrl.flags & V4L2_CTRL_FLAG_DISABLED) + return 1; + if (qctrl.type == V4L2_CTRL_TYPE_CTRL_CLASS) { + printf("\n%s\n\n", qctrl.name); + return 1; + } + ext_ctrl.id = qctrl.id; + ctrls.ctrl_class = V4L2_CTRL_ID2CLASS(qctrl.id); + ctrls.count = 1; + ctrls.controls = &ext_ctrl; + if (V4L2_CTRL_ID2CLASS(qctrl.id) != V4L2_CTRL_CLASS_USER && + qctrl.id < V4L2_CID_PRIVATE_BASE) { + if (ioctl(fd, VIDIOC_G_EXT_CTRLS, &ctrls)) { + printf("error %d getting ext_ctrl %s\n", + errno, qctrl.name); + return 0; + } + } + else { + ctrl.id = qctrl.id; + if (ioctl(fd, VIDIOC_G_CTRL, &ctrl)) { + printf("error %d getting ctrl %s\n", + errno, qctrl.name); + return 0; + } + ext_ctrl.value = ctrl.value; + } + print_qctrl(fd, &qctrl, &ext_ctrl, show_menus); + return 1; +} + +static void list_controls(int fd, int show_menus) +{ + struct v4l2_queryctrl qctrl = { V4L2_CTRL_FLAG_NEXT_CTRL }; + int id; + + while (ioctl(fd, VIDIOC_QUERYCTRL, &qctrl) == 0) { + print_control(fd, qctrl, show_menus); + qctrl.id |= V4L2_CTRL_FLAG_NEXT_CTRL; + } + if (qctrl.id != V4L2_CTRL_FLAG_NEXT_CTRL) + return; + for (id = V4L2_CID_USER_BASE; id < V4L2_CID_LASTP1; id++) { + qctrl.id = id; + if (ioctl(fd, VIDIOC_QUERYCTRL, &qctrl) == 0) + print_control(fd, qctrl, show_menus); + } + for (qctrl.id = V4L2_CID_PRIVATE_BASE; + ioctl(fd, VIDIOC_QUERYCTRL, &qctrl) == 0; qctrl.id++) { + print_control(fd, qctrl, show_menus); + } +} + +static void find_controls(int fd) +{ + struct v4l2_queryctrl qctrl = { V4L2_CTRL_FLAG_NEXT_CTRL }; + int id; + + while (ioctl(fd, VIDIOC_QUERYCTRL, &qctrl) == 0) { + if (qctrl.type != V4L2_CTRL_TYPE_CTRL_CLASS) { + ctrl_str2id[name2var(qctrl.name)] = qctrl.id; + ctrl_id2str[qctrl.id] = name2var(qctrl.name); + } + qctrl.id |= V4L2_CTRL_FLAG_NEXT_CTRL; + } + if (qctrl.id != V4L2_CTRL_FLAG_NEXT_CTRL) + return; + for (id = V4L2_CID_USER_BASE; id < V4L2_CID_LASTP1; id++) { + qctrl.id = id; + if (ioctl(fd, VIDIOC_QUERYCTRL, &qctrl) == 0) + ctrl_str2id[name2var(qctrl.name)] = qctrl.id; + } + for (qctrl.id = V4L2_CID_PRIVATE_BASE; + ioctl(fd, VIDIOC_QUERYCTRL, &qctrl) == 0; qctrl.id++) { + ctrl_str2id[name2var(qctrl.name)] = qctrl.id; + } +} + +int printfmt(struct v4l2_format vfmt) +{ + printf("Format:\n"); + + switch (vfmt.type) { + case 1: + printf("\tType : Video Capture\n"); + printf("\tWidth : %d\n", vfmt.fmt.pix.width); + printf("\tHeight : %d\n", vfmt.fmt.pix.height); + break; + case 2: + printf("\tType : Video Output\n"); + break; + case 3: + printf("\tType : Video Overlay\n"); + break; + case 4: + printf("\tType : VBI Capture\n"); + break; + case 5: + printf("\tType : VBI Output\n"); + break; + case 0x80: + printf("\tType : Private\n"); + break; + default: + printf("\tType : Unknown: %d\n", vfmt.type); + return -1; + break; + } + return 0; +} + +char *pts_to_string(char *str, unsigned long pts) +{ + static char buf[256]; + int hours, minutes, seconds, fracsec; + float fps; + int frame; + char *p = (str) ? str : buf; + + static const int MPEG_CLOCK_FREQ = 90000; + seconds = pts / MPEG_CLOCK_FREQ; + fracsec = pts % MPEG_CLOCK_FREQ; + + minutes = seconds / 60; + seconds = seconds % 60; + + hours = minutes / 60; + minutes = minutes % 60; + + fps = 30; + frame = (int)ceilf(((float)fracsec / (float)MPEG_CLOCK_FREQ) * fps); + + snprintf(p, sizeof(buf), "%d:%02d:%02d:%d", hours, minutes, seconds, + frame); + return p; +} + +static const char *audmode2s(int audmode) +{ + switch (audmode) { + case V4L2_TUNER_MODE_STEREO: return "stereo"; + case V4L2_TUNER_MODE_LANG1: return "lang1"; + case V4L2_TUNER_MODE_LANG2: return "lang2"; + case V4L2_TUNER_MODE_LANG1_LANG2: return "bilingual"; + case V4L2_TUNER_MODE_MONO: return "mono"; + default: return "unknown"; + } +} + +static std::string rxsubchans2s(int rxsubchans) +{ + std::string s; + + if (rxsubchans & V4L2_TUNER_SUB_MONO) + s += "mono "; + if (rxsubchans & V4L2_TUNER_SUB_STEREO) + s += "stereo "; + if (rxsubchans & V4L2_TUNER_SUB_LANG1) + s += "lang1 "; + if (rxsubchans & V4L2_TUNER_SUB_LANG2) + s += "lang2 "; + return s; +} + +static std::string tcap2s(unsigned cap) +{ + std::string s; + + if (cap & V4L2_TUNER_CAP_LOW) + s += "62.5 Hz "; + else + s += "62.5 kHz "; + if (cap & V4L2_TUNER_CAP_NORM) + s += "multi-standard "; + if (cap & V4L2_TUNER_CAP_STEREO) + s += "stereo "; + if (cap & V4L2_TUNER_CAP_LANG1) + s += "lang1 "; + if (cap & V4L2_TUNER_CAP_LANG2) + s += "lang2 "; + return s; +} + +static std::string cap2s(unsigned cap) +{ + std::string s; + + if (cap & V4L2_CAP_VIDEO_CAPTURE) + s += "\t\tVideo Capture\n"; + if (cap & V4L2_CAP_VIDEO_OUTPUT) + s += "\t\tVideo Output\n"; + if (cap & V4L2_CAP_VIDEO_OVERLAY) + s += "\t\tVideo Overlay\n"; + if (cap & V4L2_CAP_VBI_CAPTURE) + s += "\t\tVBI Capture\n"; + if (cap & V4L2_CAP_VBI_OUTPUT) + s += "\t\tVBI Output\n"; + if (cap & V4L2_CAP_SLICED_VBI_CAPTURE) + s += "\t\tSliced VBI Capture\n"; + if (cap & V4L2_CAP_SLICED_VBI_OUTPUT) + s += "\t\tSliced VBI Output\n"; + if (cap & V4L2_CAP_RDS_CAPTURE) + s += "\t\tRDS Capture\n"; + if (cap & V4L2_CAP_TUNER) + s += "\t\tTuner\n"; + if (cap & V4L2_CAP_AUDIO) + s += "\t\tAudio\n"; + if (cap & V4L2_CAP_RADIO) + s += "\t\tRadio\n"; + if (cap & V4L2_CAP_READWRITE) + s += "\t\tRead/Write\n"; + if (cap & V4L2_CAP_ASYNCIO) + s += "\t\tAsync I/O\n"; + if (cap & V4L2_CAP_STREAMING) + s += "\t\tStreaming\n"; + return s; +} + +static v4l2_std_id parse_pal(const char *pal) +{ + if (pal[0] == '-') { + switch (pal[1]) { + case 'b': + case 'B': + case 'g': + case 'G': + return V4L2_STD_PAL_BG; + case 'h': + case 'H': + return V4L2_STD_PAL_H; + case 'n': + case 'N': + if (pal[2] == 'c' || pal[2] == 'C') + return V4L2_STD_PAL_Nc; + return V4L2_STD_PAL_N; + case 'i': + case 'I': + return V4L2_STD_PAL_I; + case 'd': + case 'D': + case 'k': + case 'K': + return V4L2_STD_PAL_DK; + case 'M': + case 'm': + return V4L2_STD_PAL_M; + case '-': + break; + } + } + fprintf(stderr, "pal specifier not recognised\n"); + return 0; +} + +static v4l2_std_id parse_secam(const char *secam) +{ + if (secam[0] == '-') { + switch (secam[1]) { + case 'b': + case 'B': + case 'g': + case 'G': + case 'h': + case 'H': + return V4L2_STD_SECAM_B | V4L2_STD_SECAM_G | V4L2_STD_SECAM_H; + case 'd': + case 'D': + case 'k': + case 'K': + return V4L2_STD_SECAM_DK; + case 'l': + case 'L': + if (secam[2] == 'C' || secam[2] == 'c') + return V4L2_STD_SECAM_LC; + return V4L2_STD_SECAM_L; + case '-': + break; + } + } + fprintf(stderr, "secam specifier not recognised\n"); + return 0; +} + +static v4l2_std_id parse_ntsc(const char *ntsc) +{ + if (ntsc[0] == '-') { + switch (ntsc[1]) { + case 'm': + case 'M': + return V4L2_STD_NTSC_M; + case 'j': + case 'J': + return V4L2_STD_NTSC_M_JP; + case 'k': + case 'K': + return V4L2_STD_NTSC_M_KR; + case '-': + break; + } + } + fprintf(stderr, "ntsc specifier not recognised\n"); + return 0; +} + +static int doioctl(int fd, int request, void *parm, const char *name) +{ + int retVal; + + if (!option_verbose) return ioctl(fd, request, parm); + retVal = ioctl(fd, request, parm); + if (retVal < 0) + printf("failed: %s\n", strerror(errno)); + else + printf("ok\n"); + + return retVal; +} + +static int parse_subopt(char **subs, char * const *subopts, char **value) +{ + int opt = getsubopt(subs, subopts, value); + + if (opt == -1) { + fprintf(stderr, "Invalid suboptions specified\n"); + usage(); + exit(1); + } + if (value == NULL) { + fprintf(stderr, "No value given to suboption <%s>\n", + subopts[opt]); + usage(); + exit(1); + } + return opt; +} + +static void parse_next_subopt(char **subs, char **value) +{ + static char *const subopts[] = { + NULL + }; + int opt = getsubopt(subs, subopts, value); + + if (value == NULL) { + fprintf(stderr, "No value given to suboption <%s>\n", + subopts[opt]); + usage(); + exit(1); + } +} + +int main(int argc, char **argv) +{ + char *value, *subs; + int i; + + int fd = -1; + + /* bitfield for fmts */ + unsigned int set_fmts = 0; + + int mode = V4L2_TUNER_MODE_STEREO; /* set audio mode */ + + /* command args */ + char ch, *device = strdup("/dev/video0"); /* -d device */ + struct v4l2_format vfmt; /* set_format/get_format */ + struct v4l2_tuner tuner; /* set_tuner/get_tuner */ + struct v4l2_capability vcap; /* list_cap */ + struct v4l2_input vin; /* list_inputs */ + struct v4l2_output vout; /* list_outputs */ + struct v4l2_audio vaudio; /* list audio inputs */ + struct v4l2_audioout vaudout = { 0 }; /* audio outputs */ + int input; /* set_input/get_input */ + int output; /* set_output/get_output */ + v4l2_std_id std; /* get_std/set_std */ + double freq = 0; /* get/set frequency */ + struct v4l2_frequency vf; /* get_freq/set_freq */ + struct v4l2_standard vs; /* list_std */ + char short_options[26 * 2 * 2 + 1]; + int idx = 0; + + if (argc == 1) { + usage(); + return 0; + } + for (i = 0; long_options[i].name; i++) { + if (!isalpha(long_options[i].val)) + continue; + short_options[idx++] = long_options[i].val; + if (long_options[i].has_arg == required_argument) + short_options[idx++] = ':'; + } + while (1) { + int option_index = 0; + + short_options[idx] = 0; + ch = getopt_long(argc, argv, short_options, + long_options, &option_index); + if (ch == -1) + break; + + options[(int)ch] = 1; + switch (ch) { + case OptHelp: + usage(); + return 0; + case OptSetDevice: + device = strdup(optarg); + if (device[0] >= '0' && device[0] <= '9' && device[1] == 0) { + char dev = device[0]; + + sprintf(device, "/dev/video%c", dev); + } + break; + case OptSetVideoFormat: + subs = optarg; + while (*subs != '\0') { + static char *const subopts[] = { + "width", + "height", + NULL + }; + + switch (parse_subopt(&subs, subopts, &value)) { + case 0: + vfmt.fmt.pix.width = strtol(value, 0L, 0); + set_fmts |= FMTWidth; + break; + case 1: + vfmt.fmt.pix.height = strtol(value, 0L, 0); + set_fmts |= FMTHeight; + break; + } + } + break; + case OptSetInput: + input = strtol(optarg, 0L, 0); + break; + case OptSetOutput: + output = strtol(optarg, 0L, 0); + break; + case OptSetAudioInput: + vaudio.index = strtol(optarg, 0L, 0); + break; + case OptSetAudioOutput: + vaudout.index = strtol(optarg, 0L, 0); + break; + case OptSetFreq: + freq = strtod(optarg, NULL); + break; + case OptSetStandard: + if (!strncmp(optarg, "pal", 3)) { + if (optarg[3]) + std = parse_pal(optarg + 3); + else + std = V4L2_STD_PAL; + } + else if (!strncmp(optarg, "ntsc", 4)) { + if (optarg[4]) + std = parse_ntsc(optarg + 4); + else + std = V4L2_STD_NTSC; + } + else if (!strncmp(optarg, "secam", 5)) { + if (optarg[5]) + std = parse_secam(optarg + 5); + else + std = V4L2_STD_SECAM; + } + else { + std = strtol(optarg, 0L, 0); + } + break; + case OptGetCtrl: + subs = optarg; + while (*subs != '\0') { + parse_next_subopt(&subs, &value); + if (strchr(value, '=')) { + usage(); + exit(1); + } + else { + get_ctrls.push_back(value); + } + } + break; + case OptSetCtrl: + subs = optarg; + while (*subs != '\0') { + parse_next_subopt(&subs, &value); + if (const char *equal = strchr(value, '=')) { + set_ctrls[std::string(value, (equal - value))] = equal + 1; + } + else { + fprintf(stderr, "control '%s' without '='\n", value); + exit(1); + } + } + break; + case OptSetTuner: + if (!strcmp(optarg, "stereo")) + mode = V4L2_TUNER_MODE_STEREO; + else if (!strcmp(optarg, "lang1")) + mode = V4L2_TUNER_MODE_LANG1; + else if (!strcmp(optarg, "lang2")) + mode = V4L2_TUNER_MODE_LANG2; + else if (!strcmp(optarg, "bilingual")) + mode = V4L2_TUNER_MODE_LANG1_LANG2; + else if (!strcmp(optarg, "mono")) + mode = V4L2_TUNER_MODE_MONO; + else { + fprintf(stderr, "Unknown audio mode\n"); + usage(); + return 1; + } + break; + case ':': + fprintf(stderr, "Option `%s' requires a value\n", + argv[optind]); + usage(); + return 1; + case '?': + fprintf(stderr, "Unknown argument `%s'\n", + argv[optind]); + usage(); + return 1; + } + } + if (optind < argc) { + printf("unknown arguments: "); + while (optind < argc) + printf("%s ", argv[optind++]); + printf("\n"); + usage(); + return 1; + } + + if ((fd = open(device, O_RDWR)) < 0) { + fprintf(stderr, "Failed to open %s: %s\n", device, + strerror(errno)); + exit(1); + } + free(device); + + find_controls(fd); + for (ctrl_get_list::iterator iter = get_ctrls.begin(); iter != get_ctrls.end(); ++iter) { + if (ctrl_str2id.find(*iter) == ctrl_str2id.end()) { + fprintf(stderr, "unknown control '%s'\n", (*iter).c_str()); + exit(1); + } + } + for (ctrl_set_map::iterator iter = set_ctrls.begin(); iter != set_ctrls.end(); ++iter) { + if (ctrl_str2id.find(iter->first) == ctrl_str2id.end()) { + fprintf(stderr, "unknown control '%s'\n", iter->first.c_str()); + exit(1); + } + } + + if (option_all) { + options[OptGetVideoFormat] = 1; + options[OptGetDriverInfo] = 1; + options[OptGetInput] = 1; + options[OptGetOutput] = 1; + options[OptGetAudioInput] = 1; + options[OptGetAudioOutput] = 1; + options[OptGetStandard] = 1; + options[OptGetFreq] = 1; + options[OptGetTuner] = 1; + } + + + /* Setting Opts */ + + if (options[OptSetVideoFormat]) { + struct v4l2_format in_vfmt; + printf("ioctl: VIDIOC_S_FMT\n"); + in_vfmt.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; + if (ioctl(fd, VIDIOC_G_FMT, &in_vfmt) < 0) + fprintf(stderr, "ioctl: VIDIOC_G_FMT failed\n"); + else { + printf("\tBefore:\n"); + if (printfmt(in_vfmt) != 0) + fprintf(stderr, "error printing result\n"); + if (set_fmts & FMTWidth) + in_vfmt.fmt.pix.width = vfmt.fmt.pix.width; + if (set_fmts & FMTHeight) + in_vfmt.fmt.pix.height = vfmt.fmt.pix.height; + if (ioctl(fd, VIDIOC_S_FMT, &in_vfmt) < 0) + fprintf(stderr, "ioctl: VIDIOC_S_FMT failed\n"); + vfmt.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; + if (ioctl(fd, VIDIOC_G_FMT, &vfmt) < 0) + fprintf(stderr, "ioctl: VIDIOC_G_FMT failed\n"); + else { + printf("\n\tAfter:\n"); + if (printfmt(vfmt) != 0) + fprintf(stderr, + "error printing result\n"); + } + } + } + + if (option_streamoff) { + int dummy = 0; + doioctl(fd, VIDIOC_STREAMOFF, &dummy, "VIDIOC_STREAMOFF"); + } + + if (options[OptSetFreq]) { + double fac = 16; + + if (doioctl(fd, VIDIOC_G_TUNER, &tuner, "VIDIOC_G_TUNER") == 0) { + fac = (tuner.capability & V4L2_TUNER_CAP_LOW) ? 16000 : 16; + } + vf.tuner = 0; + vf.type = (enum v4l2_tuner_type)0; + vf.frequency = __u32(freq * fac); + if (doioctl(fd, VIDIOC_S_FREQUENCY, &vf, + "VIDIOC_S_FREQUENCY") == 0) + printf("Frequency set to %d (%f MHz)\n", vf.frequency, + vf.frequency / fac); + } + + if (options[OptSetStandard]) { + if (std < 16) { + vs.index = std; + if (ioctl(fd, VIDIOC_ENUMSTD, &vs) >= 0) { + std = vs.id; + } + } + if (doioctl(fd, VIDIOC_S_STD, &std, "VIDIOC_S_STD") == 0) + printf("Standard set to %08llx\n", (unsigned long long)std); + } + + if (options[OptSetCtrl] && !set_ctrls.empty()) { + struct v4l2_ext_controls ctrls = { 0 }; + + for (ctrl_set_map::iterator iter = set_ctrls.begin(); + iter != set_ctrls.end(); ++iter) { + struct v4l2_ext_control ctrl = { 0 }; + + ctrl.id = ctrl_str2id[iter->first]; + ctrl.value = atol(iter->second.c_str()); + if (V4L2_CTRL_ID2CLASS(ctrl.id) == V4L2_CTRL_CLASS_MPEG) + mpeg_ctrls.push_back(ctrl); + else + user_ctrls.push_back(ctrl); + } + for (unsigned i = 0; i < user_ctrls.size(); i++) { + struct v4l2_control ctrl; + + ctrl.id = user_ctrls[i].id; + ctrl.value = user_ctrls[i].value; + if (ioctl(fd, VIDIOC_S_CTRL, &ctrl)) { + fprintf(stderr, "%s: %s\n", + ctrl_id2str[ctrl.id].c_str(), + strerror(errno)); + } + } + if (mpeg_ctrls.size()) { + ctrls.ctrl_class = V4L2_CTRL_CLASS_MPEG; + ctrls.count = mpeg_ctrls.size(); + ctrls.controls = &mpeg_ctrls[0]; + if (ioctl(fd, VIDIOC_S_EXT_CTRLS, &ctrls)) { + if (ctrls.error_idx >= ctrls.count) { + fprintf(stderr, "Error setting MPEG controls: %s\n", + strerror(errno)); + } + else { + fprintf(stderr, "%s: %s\n", + ctrl_id2str[mpeg_ctrls[ctrls.error_idx].id].c_str(), + strerror(errno)); + } + } + } + } + + /* informational opts */ + + if (options[OptGetDriverInfo]) { + if (doioctl(fd, VIDIOC_QUERYCAP, &vcap, "VIDIOC_QUERYCAP") == 0) { + printf("Driver info:\n"); + printf("\tDriver name : %s\n", vcap.driver); + printf("\tCard type : %s\n", vcap.card); + printf("\tBus info : %s\n", vcap.bus_info); + printf("\tDriver version: %d\n", vcap.version); + printf("\tCapabilities : 0x%08X\n", vcap.capabilities); + printf("%s", cap2s(vcap.capabilities).c_str()); + } + } + + if (options[OptGetVideoFormat]) { + vfmt.type = V4L2_BUF_TYPE_VIDEO_CAPTURE; + if (doioctl(fd, VIDIOC_G_FMT, &vfmt, "VIDIOC_G_FMT") == 0) + if (printfmt(vfmt) != 0) + fprintf(stderr, "error printing result\n"); + } + + if (options[OptListInputs]) { + vin.index = 0; + printf("ioctl: VIDIOC_ENUMINPUT\n"); + while (ioctl(fd, VIDIOC_ENUMINPUT, &vin) >= 0) { + if (vin.index) + printf("\n"); + printf("\tInput : %d\n", vin.index); + printf("\tName : %s\n", vin.name); + printf("\tType : 0x%08X\n", vin.type); + printf("\tAudioset: 0x%08X\n", vin.audioset); + printf("\tTuner : 0x%08X\n", vin.tuner); + printf("\tStandard: 0x%016llX ( ", (unsigned long long)vin.std); + if (vin.std & 0x000FFF) + printf("PAL "); // hack + if (vin.std & 0x00F000) + printf("NTSC "); // hack + if (vin.std & 0x7F0000) + printf("SECAM "); // hack + printf(")\n"); + printf("\tStatus : %d\n", vin.status); + vin.index++; + } + } + + if (options[OptSetInput]) { + if (doioctl(fd, VIDIOC_S_INPUT, &input, "VIDIOC_S_INPUT") == 0) { + printf("Video input set to %d", input); + vin.index = input; + if (ioctl(fd, VIDIOC_ENUMINPUT, &vin) >= 0) + printf(" (%s)", vin.name); + printf("\n"); + } + } + + if (options[OptGetInput]) { + if (doioctl(fd, VIDIOC_G_INPUT, &input, "VIDIOC_G_INPUT") == 0) { + printf("Video input : %d", input); + vin.index = input; + if (ioctl(fd, VIDIOC_ENUMINPUT, &vin) >= 0) + printf(" (%s)", vin.name); + printf("\n"); + } + } + + if (options[OptListOutputs]) { + vout.index = 0; + printf("ioctl: VIDIOC_ENUMOUTPUT\n"); + while (ioctl(fd, VIDIOC_ENUMOUTPUT, &vout) >= 0) { + if (vout.index) + printf("\n"); + printf("\tOutput : %d\n", vout.index); + printf("\tName : %s\n", vout.name); + printf("\tType : 0x%08X\n", vout.type); + printf("\tAudioset: 0x%08X\n", vout.audioset); + printf("\tStandard: 0x%016llX ( ", (unsigned long long)vout.std); + if (vout.std & 0x000FFF) + printf("PAL "); // hack + if (vout.std & 0x00F000) + printf("NTSC "); // hack + if (vout.std & 0x7F0000) + printf("SECAM "); // hack + printf(")\n"); + vout.index++; + } + } + + if (options[OptSetOutput]) { + if (doioctl(fd, VIDIOC_S_OUTPUT, &output, "VIDIOC_S_OUTPUT") == 0) + printf("Output set to %d\n", output); + } + + if (options[OptGetOutput]) { + if (doioctl(fd, VIDIOC_G_OUTPUT, &output, "VIDIOC_G_OUTPUT") == 0) { + printf("Video output: %d", output); + vout.index = output; + if (ioctl(fd, VIDIOC_ENUMOUTPUT, &vout) >= 0) { + printf(" (%s)", vout.name); + } + printf("\n"); + } + } + + if (options[OptListAudioInputs]) { + struct v4l2_audio vaudio; /* list audio inputs */ + vaudio.index = 0; + printf("ioctl: VIDIOC_ENUMAUDIO\n"); + while (ioctl(fd, VIDIOC_ENUMAUDIO, &vaudio) >= 0) { + if (vaudio.index) + printf("\n"); + printf("\tInput : %d\n", vaudio.index); + printf("\tName : %s\n", vaudio.name); + vaudio.index++; + } + } + + if (options[OptSetAudioInput]) { + if (doioctl(fd, VIDIOC_S_AUDIO, &vaudio, "VIDIOC_S_AUDIO") == 0) + printf("Audio input set to %d\n", vaudio.index); + } + + if (options[OptGetAudioInput]) { + if (doioctl(fd, VIDIOC_G_AUDIO, &vaudio, "VIDIOC_G_AUDIO") == 0) + printf("Audio input : %d (%s)\n", vaudio.index, vaudio.name); + } + + if (options[OptSetAudioOutput]) { + if (doioctl(fd, VIDIOC_S_AUDOUT, &vaudout, "VIDIOC_S_AUDOUT") == 0) + printf("Audio output set to %d\n", vaudout.index); + } + + if (options[OptGetAudioOutput]) { + if (doioctl(fd, VIDIOC_G_AUDOUT, &vaudout, "VIDIOC_G_AUDOUT") == 0) + printf("Audio output: %d (%s)\n", vaudout.index, vaudout.name); + } + + if (options[OptGetFreq]) { + double fac = 16; + + if (doioctl(fd, VIDIOC_G_TUNER, &tuner, "VIDIOC_G_TUNER") == 0) { + fac = (tuner.capability & V4L2_TUNER_CAP_LOW) ? 16000 : 16; + } + vf.tuner = 0; + if (doioctl(fd, VIDIOC_G_FREQUENCY, &vf, "VIDIOC_G_FREQUENCY") == 0) + printf("Frequency: %d (%f MHz)\n", vf.frequency, + vf.frequency / fac); + } + + if (option_list_stds) { + printf("ioctl: VIDIOC_ENUMSTD\n"); + vs.index = 0; + while (ioctl(fd, VIDIOC_ENUMSTD, &vs) >= 0) { + if (vs.index) + printf("\n"); + printf("\tindex : %d\n", vs.index); + printf("\tID : 0x%016llX\n", (unsigned long long)vs.id); + printf("\tName : %s\n", vs.name); + printf("\tFrame period: %d/%d\n", + vs.frameperiod.numerator, + vs.frameperiod.denominator); + printf("\tFrame lines : %d\n", vs.framelines); + vs.index++; + } + } + + if (options[OptGetStandard]) { + if (doioctl(fd, VIDIOC_G_STD, &std, "VIDIOC_G_STD") == 0) + printf("Video standard = 0x%08llx\n", (unsigned long long)std); + } + + if (options[OptListCtrlsMenus]) { + list_controls(fd, 1); + } + + if (options[OptGetCtrl] && !get_ctrls.empty()) { + struct v4l2_ext_controls ctrls = { 0 }; + + mpeg_ctrls.clear(); + user_ctrls.clear(); + for (ctrl_get_list::iterator iter = get_ctrls.begin(); + iter != get_ctrls.end(); ++iter) { + struct v4l2_ext_control ctrl = { 0 }; + + ctrl.id = ctrl_str2id[*iter]; + if (V4L2_CTRL_ID2CLASS(ctrl.id) == V4L2_CTRL_CLASS_MPEG) + mpeg_ctrls.push_back(ctrl); + else + user_ctrls.push_back(ctrl); + } + for (unsigned i = 0; i < user_ctrls.size(); i++) { + struct v4l2_control ctrl; + + ctrl.id = user_ctrls[i].id; + doioctl(fd, VIDIOC_G_CTRL, &ctrl, "VIDIOC_G_CTRL"); + printf("%s: %d\n", ctrl_id2str[ctrl.id].c_str(), ctrl.value); + } + if (mpeg_ctrls.size()) { + ctrls.ctrl_class = V4L2_CTRL_CLASS_MPEG; + ctrls.count = mpeg_ctrls.size(); + ctrls.controls = &mpeg_ctrls[0]; + doioctl(fd, VIDIOC_S_EXT_CTRLS, &ctrls, "VIDIOC_S_EXT_CTRLS"); + for (unsigned i = 0; i < mpeg_ctrls.size(); i++) { + struct v4l2_ext_control ctrl = mpeg_ctrls[i]; + + printf("%s: %d\n", ctrl_id2str[ctrl.id].c_str(), ctrl.value); + } + } + } + + if (options[OptGetTuner]) { + struct v4l2_tuner vt; + memset(&vt, 0, sizeof(struct v4l2_tuner)); + if (doioctl(fd, VIDIOC_G_TUNER, &vt, "VIDIOC_G_TUNER") == 0) { + printf("Tuner:\n"); + printf("\tCapabilities : %s\n", tcap2s(vt.capability).c_str()); + if (vt.capability & V4L2_TUNER_CAP_LOW) + printf("\tFrequency range : %.1f MHz - %.1f MHz\n", + vt.rangelow / 16000.0, vt.rangehigh / 16000.0); + else + printf("\tFrequency range : %.1f MHz - %.1f MHz\n", + vt.rangelow / 16.0, vt.rangehigh / 16.0); + printf("\tSignal strength : %d%%\n", (int)(vt.signal / 655.35)); + printf("\tCurrent audio mode : %s\n", audmode2s(vt.audmode)); + printf("\tAvailable subchannels: %s\n", + rxsubchans2s(vt.rxsubchans).c_str()); + } + } + if (options[OptSetTuner]) { + struct v4l2_tuner vt; + + memset(&vt, 0, sizeof(struct v4l2_tuner)); + if (ioctl(fd, VIDIOC_G_TUNER, &vt) < 0) { + fprintf(stderr, "ioctl: VIDIOC_G_TUNER failed\n"); + exit(1); + } + vt.audmode = mode; + doioctl(fd, VIDIOC_S_TUNER, &vt, "VIDIOC_S_TUNER"); + } + + if (option_version) { + //printf("ivtvctl version " IVTV_VERSION "\n"); + } + + if (options[OptListCtrls]) { + list_controls(fd, 0); + } + + if (option_log_status) { + static char buf[40960]; + int len; + + if (doioctl(fd, VIDIOC_LOG_STATUS, NULL, "VIDIOC_LOG_STATUS") == 0) { + printf("\nStatus Log:\n\n"); + len = klogctl(3, buf, sizeof(buf) - 1); + if (len >= 0) { + char *p = buf; + char *q; + + buf[len] = 0; + while ((q = strstr(p, "START STATUS CARD #"))) { + p = q + 1; + } + if (p) { + while (p > buf && *p != '<') p--; + q = p; + while ((q = strstr(q, "<6>"))) { + memcpy(q, " ", 3); + } + printf("%s", p); + } + } + } + } + + if (option_streamon) { + int dummy = 0; + doioctl(fd, VIDIOC_STREAMON, &dummy, "VIDIOC_STREAMON"); + } + + close(fd); + exit(0); +} -- cgit v1.2.3 From 898361db1d687bff759e11052a02cb57797223e8 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Sun, 18 Jun 2006 20:05:09 +0200 Subject: Added qv4l2, a Qt application to interactively set/get controls. From: Hans Verkuil Signed-off-by: Hans Verkuil --- test/Makefile | 9 +- test/qv4l2/fileopen.xpm | 22 ++ test/qv4l2/qv4l2.cpp | 649 ++++++++++++++++++++++++++++++++++++++++++++++++ test/qv4l2/qv4l2.h | 79 ++++++ test/qv4l2/qv4l2.pro | 10 + 5 files changed, 768 insertions(+), 1 deletion(-) create mode 100644 test/qv4l2/fileopen.xpm create mode 100644 test/qv4l2/qv4l2.cpp create mode 100644 test/qv4l2/qv4l2.h create mode 100644 test/qv4l2/qv4l2.pro diff --git a/test/Makefile b/test/Makefile index 79e90417b..f7cfc29f7 100644 --- a/test/Makefile +++ b/test/Makefile @@ -5,8 +5,15 @@ CFLAGS = -O3 -Wall -fomit-frame-pointer -funroll-loops -g -I ../linux/include CXXFLAGS = $(CFLAGS) LDFLAGS = -all: $(FILES) +all: $(FILES) qv4l2 clean: -rm -f core core.[0123456789]* *~ *.o $(FILES) + -if [ -f qv4l2/Makefile ]; then make -C qv4l2 $@; fi + -rm -f qv4l2/qv4l2 qv4l2/Makefile +qv4l2: + if [ ! -f qv4l2/Makefile ]; then (cd qv4l2; qmake); fi + make -C qv4l2 + +.PHONY: qv4l2 diff --git a/test/qv4l2/fileopen.xpm b/test/qv4l2/fileopen.xpm new file mode 100644 index 000000000..880417eee --- /dev/null +++ b/test/qv4l2/fileopen.xpm @@ -0,0 +1,22 @@ +/* XPM */ +static const char *fileopen[] = { +" 16 13 5 1", +". c #040404", +"# c #808304", +"a c None", +"b c #f3f704", +"c c #f3f7f3", +"aaaaaaaaa...aaaa", +"aaaaaaaa.aaa.a.a", +"aaaaaaaaaaaaa..a", +"a...aaaaaaaa...a", +".bcb.......aaaaa", +".cbcbcbcbc.aaaaa", +".bcbcbcbcb.aaaaa", +".cbcb...........", +".bcb.#########.a", +".cb.#########.aa", +".b.#########.aaa", +"..#########.aaaa", +"...........aaaaa" +}; diff --git a/test/qv4l2/qv4l2.cpp b/test/qv4l2/qv4l2.cpp new file mode 100644 index 000000000..69146defa --- /dev/null +++ b/test/qv4l2/qv4l2.cpp @@ -0,0 +1,649 @@ + +#include "qv4l2.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include + +#include "fileopen.xpm" + +ApplicationWindow::ApplicationWindow() + : QMainWindow( 0, "V4L2 main window", WDestructiveClose | WGroupLeader ) +{ + QPixmap openIcon, saveIcon; + + fd = -1; + + sigMapper = NULL; + QToolBar * fileTools = new QToolBar( this, "file operations" ); + fileTools->setLabel( "File Operations" ); + + openIcon = QPixmap( fileopen ); + QToolButton * fileOpen + = new QToolButton( openIcon, "Open File", QString::null, + this, SLOT(choose()), fileTools, "open file" ); + + (void)QWhatsThis::whatsThisButton( fileTools ); + + const char * fileOpenText = "

" + "Click this button to open a new v4l device.
" + "You can also select the Open command " + "from the File menu.

"; + + QWhatsThis::add( fileOpen, fileOpenText ); + + QMimeSourceFactory::defaultFactory()->setPixmap( "fileopen", openIcon ); + + QPopupMenu * file = new QPopupMenu( this ); + menuBar()->insertItem( "&File", file ); + + + int id; + id = file->insertItem( openIcon, "&Open...", + this, SLOT(choose()), CTRL+Key_O ); + file->setWhatsThis( id, fileOpenText ); + + file->insertSeparator(); + + file->insertItem( "&Close", this, SLOT(close()), CTRL+Key_W ); + + file->insertItem( "&Quit", qApp, SLOT( closeAllWindows() ), CTRL+Key_Q ); + + menuBar()->insertSeparator(); + + QPopupMenu * help = new QPopupMenu( this ); + menuBar()->insertItem( "&Help", help ); + + help->insertItem( "&About", this, SLOT(about()), Key_F1 ); + help->insertItem( "What's &This", this, SLOT(whatsThis()), SHIFT+Key_F1 ); + + statusBar()->message( "Ready", 2000 ); + + tabs = new QTabWidget(this); + tabs->setMargin(3); + + //resize( 450, 600 ); +} + + +ApplicationWindow::~ApplicationWindow() +{ + if (fd >= 0) ::close(fd); +} + + +void ApplicationWindow::setDevice(const QString &device) +{ + if (fd >= 0) ::close(fd); + while (QWidget *page = tabs->page(0)) { + tabs->removePage(page); + delete page; + } + delete tabs; + delete sigMapper; + tabs = new QTabWidget(this); + tabs->setMargin(3); + sigMapper = new QSignalMapper(this); + connect(sigMapper, SIGNAL(mapped(int)), this, SLOT(ctrlAction(int))); + ctrlMap.clear(); + widgetMap.clear(); + classMap.clear(); + + fd = ::open(device, O_RDONLY); + if (fd >= 0) { + addTabs(); + } + if (QWidget *current = tabs->currentPage()) { + current->show(); + } + tabs->show(); + tabs->setFocus(); + setCentralWidget(tabs); +} + +void ApplicationWindow::addTabs() +{ + struct v4l2_queryctrl qctrl; + unsigned ctrl_class; + unsigned i; + int id; + + memset(&qctrl, 0, sizeof(qctrl)); + qctrl.id = V4L2_CTRL_FLAG_NEXT_CTRL; + while (::ioctl(fd, VIDIOC_QUERYCTRL, &qctrl) == 0) { + if ((qctrl.flags & V4L2_CTRL_FLAG_DISABLED) == 0) { + ctrlMap[qctrl.id] = qctrl; + if (qctrl.type != V4L2_CTRL_TYPE_CTRL_CLASS) + classMap[V4L2_CTRL_ID2CLASS(qctrl.id)].push_back(qctrl.id); + } + qctrl.id |= V4L2_CTRL_FLAG_NEXT_CTRL; + } + if (qctrl.id == V4L2_CTRL_FLAG_NEXT_CTRL) { + strcpy((char *)qctrl.name, "User Controls"); + qctrl.id = V4L2_CTRL_CLASS_USER | 1; + qctrl.type = V4L2_CTRL_TYPE_CTRL_CLASS; + ctrlMap[qctrl.id] = qctrl; + for (id = V4L2_CID_USER_BASE; id < V4L2_CID_LASTP1; id++) { + qctrl.id = id; + if (::ioctl(fd, VIDIOC_QUERYCTRL, &qctrl)) + continue; + if (qctrl.flags & V4L2_CTRL_FLAG_DISABLED) + continue; + ctrlMap[qctrl.id] = qctrl; + classMap[V4L2_CTRL_CLASS_USER].push_back(qctrl.id); + } + for (qctrl.id = V4L2_CID_PRIVATE_BASE; + ::ioctl(fd, VIDIOC_QUERYCTRL, &qctrl) == 0; qctrl.id++) { + if (qctrl.flags & V4L2_CTRL_FLAG_DISABLED) + continue; + ctrlMap[qctrl.id] = qctrl; + classMap[V4L2_CTRL_CLASS_USER].push_back(qctrl.id); + } + } + + for (ClassMap::iterator iter = classMap.begin(); iter != classMap.end(); ++iter) { + ctrl_class = V4L2_CTRL_ID2CLASS(iter->second[0]); + id = ctrl_class | 1; + const struct v4l2_queryctrl &qctrl = ctrlMap[id]; + QVBox *vbox = new QVBox(tabs); + QGrid *grid = new QGrid(4, vbox); + grid->setSpacing(3); + tabs->addTab(vbox, (char *)qctrl.name); + for (i = 0; i < iter->second.size(); i++) { + if (i & 1) + id = iter->second[(1+iter->second.size()) / 2 + i / 2]; + else + id = iter->second[i / 2]; + addCtrl(grid, ctrlMap[id]); + } + finishGrid(vbox, grid, ctrl_class, i & 1); + } +} + +void ApplicationWindow::finishGrid(QWidget *vbox, QGrid *grid, unsigned ctrl_class, bool odd) +{ + if (odd) { + new QWidget(grid); + new QWidget(grid); + } + QWidget *stretch = new QWidget(grid); + stretch->setSizePolicy(QSizePolicy::Fixed, QSizePolicy::Ignored); + + QFrame *frame = new QFrame(vbox); + frame->setFrameShape(QFrame::HLine); + frame->setFrameShadow(QFrame::Sunken); + frame->setMargin(3); + + QHBox *hbox = new QHBox(vbox); + hbox->setSpacing(3); + + QCheckBox *cbox = new QCheckBox("Update on change", hbox); + widgetMap[ctrl_class | CTRL_UPDATE_ON_CHANGE] = cbox; + connect(cbox, SIGNAL(clicked()), sigMapper, SLOT(map())); + sigMapper->setMapping(cbox, ctrl_class | CTRL_UPDATE_ON_CHANGE); + + stretch = new QWidget(hbox); + stretch->setSizePolicy(QSizePolicy::Ignored, QSizePolicy::Fixed); + + QPushButton *defBut = new QPushButton("Set Defaults", hbox); + widgetMap[ctrl_class | CTRL_DEFAULTS] = defBut; + connect(defBut, SIGNAL(clicked()), sigMapper, SLOT(map())); + sigMapper->setMapping(defBut, ctrl_class | CTRL_DEFAULTS); + + QPushButton *refreshBut = new QPushButton("Refresh", hbox); + widgetMap[ctrl_class | CTRL_REFRESH] = refreshBut; + connect(refreshBut, SIGNAL(clicked()), sigMapper, SLOT(map())); + sigMapper->setMapping(refreshBut, ctrl_class | CTRL_REFRESH); + + QPushButton *button = new QPushButton("Update", hbox); + widgetMap[ctrl_class | CTRL_UPDATE] = button; + connect(button, SIGNAL(clicked()), sigMapper, SLOT(map())); + sigMapper->setMapping(button, ctrl_class | CTRL_UPDATE); + connect(cbox, SIGNAL(toggled(bool)), button, SLOT(setDisabled(bool))); + + cbox->setChecked(ctrl_class == V4L2_CTRL_CLASS_USER); + + refresh(ctrl_class); +} + +void ApplicationWindow::addCtrl(QGrid *grid, const struct v4l2_queryctrl &qctrl) +{ + QIntValidator *val; + QLineEdit *edit; + QString name((char *)qctrl.name); + QComboBox *combo; + struct v4l2_querymenu qmenu; + + QLabel *label = new QLabel(name, grid); + label->setAlignment(Qt::AlignRight); + + switch (qctrl.type) { + case V4L2_CTRL_TYPE_INTEGER: + if (qctrl.flags & V4L2_CTRL_FLAG_SLIDER) { + widgetMap[qctrl.id] = + new QSlider(qctrl.minimum, qctrl.maximum, + qctrl.step, qctrl.default_value, + Horizontal, grid); + connect(widgetMap[qctrl.id], SIGNAL(valueChanged(int)), + sigMapper, SLOT(map())); + break; + } + + if (qctrl.maximum - qctrl.minimum <= 255) { + widgetMap[qctrl.id] = + new QSpinBox(qctrl.minimum, qctrl.maximum, 1, grid); + connect(widgetMap[qctrl.id], SIGNAL(valueChanged(int)), + sigMapper, SLOT(map())); + break; + } + + val = new QIntValidator(qctrl.minimum, qctrl.maximum, grid); + edit = new QLineEdit(grid); + edit->setValidator(val); + widgetMap[qctrl.id] = edit; + connect(widgetMap[qctrl.id], SIGNAL(lostFocus()), + sigMapper, SLOT(map())); + connect(widgetMap[qctrl.id], SIGNAL(returnPressed()), + sigMapper, SLOT(map())); + break; + + case V4L2_CTRL_TYPE_INTEGER64: + widgetMap[qctrl.id] = new QLineEdit(grid); + connect(widgetMap[qctrl.id], SIGNAL(lostFocus()), + sigMapper, SLOT(map())); + connect(widgetMap[qctrl.id], SIGNAL(returnPressed()), + sigMapper, SLOT(map())); + break; + + case V4L2_CTRL_TYPE_BOOLEAN: + label->setText(""); + widgetMap[qctrl.id] = new QCheckBox(name, grid); + connect(widgetMap[qctrl.id], SIGNAL(clicked()), + sigMapper, SLOT(map())); + break; + + case V4L2_CTRL_TYPE_BUTTON: + label->setText(""); + widgetMap[qctrl.id] = new QPushButton((char *)qctrl.name, grid); + connect(widgetMap[qctrl.id], SIGNAL(clicked()), + sigMapper, SLOT(map())); + break; + + case V4L2_CTRL_TYPE_MENU: + combo = new QComboBox(grid); + widgetMap[qctrl.id] = combo; + for (int i = qctrl.minimum; i <= qctrl.maximum; i++) { + qmenu.id = qctrl.id; + qmenu.index = i; + if (::ioctl(fd, VIDIOC_QUERYMENU, &qmenu)) + continue; + combo->insertItem((char *)qmenu.name); + } + connect(widgetMap[qctrl.id], SIGNAL(activated(int)), + sigMapper, SLOT(map())); + break; + + default: + return; + } + sigMapper->setMapping(widgetMap[qctrl.id], qctrl.id); + if (qctrl.flags & (V4L2_CTRL_FLAG_READ_ONLY | V4L2_CTRL_FLAG_INACTIVE)) + widgetMap[qctrl.id]->setDisabled(true); +} + +void ApplicationWindow::ctrlAction(int id) +{ + unsigned ctrl_class = V4L2_CTRL_ID2CLASS(id); + if (ctrl_class == V4L2_CID_PRIVATE_BASE) + ctrl_class = V4L2_CTRL_CLASS_USER; + unsigned ctrl = id & 0xffff; + QCheckBox *cbox = static_cast(widgetMap[ctrl_class | CTRL_UPDATE_ON_CHANGE]); + bool update = cbox->isChecked(); + bool all = (ctrl == CTRL_UPDATE || (update && ctrl == CTRL_UPDATE_ON_CHANGE)); + + if (ctrl == CTRL_DEFAULTS) { + setDefaults(ctrl_class); + return; + } + if (ctrl == CTRL_REFRESH) { + refresh(ctrl_class); + return; + } + if (!update && !all && ctrlMap[id].type != V4L2_CTRL_TYPE_BUTTON) + return; + if (ctrl_class == V4L2_CTRL_CLASS_USER) { + if (!all) { + updateCtrl(id); + return; + } + for (unsigned i = 0; i < classMap[ctrl_class].size(); i++) { + updateCtrl(classMap[ctrl_class][i]); + } + return; + } + if (!all) { + updateCtrl(id); + return; + } + unsigned count = classMap[ctrl_class].size(); + struct v4l2_ext_control *c = new v4l2_ext_control[count]; + struct v4l2_ext_controls ctrls; + int idx = 0; + + for (unsigned i = 0; i < count; i++) { + unsigned id = classMap[ctrl_class][i]; + + if (ctrlMap[id].flags & (V4L2_CTRL_FLAG_READ_ONLY | V4L2_CTRL_FLAG_INACTIVE)) + continue; + c[idx].id = id; + if (ctrlMap[id].type == V4L2_CTRL_TYPE_INTEGER64) + c[idx].value64 = getVal64(id); + else + c[idx].value = getVal(id); + idx++; + } + memset(&ctrls, 0, sizeof(ctrls)); + ctrls.count = idx; + ctrls.ctrl_class = ctrl_class; + ctrls.controls = c; + if (::ioctl(fd, VIDIOC_S_EXT_CTRLS, &ctrls)) { + int err = errno; + + if (ctrls.error_idx >= ctrls.count) { + printf("error: %s\n", strerror(err)); + } + else { + id = c[ctrls.error_idx].id; + printf("error %08x (%s): %s\n", id, + ctrlMap[id].name, strerror(err)); + } + } + delete [] c; + refresh(ctrl_class); +} + +long long ApplicationWindow::getVal64(unsigned id) +{ + const v4l2_queryctrl &qctrl = ctrlMap[id]; + QWidget *w = widgetMap[qctrl.id]; + + switch (qctrl.type) { + case V4L2_CTRL_TYPE_INTEGER64: + return static_cast(w)->text().toLongLong(); + default: + return 0; + } +} + +int ApplicationWindow::getVal(unsigned id) +{ + const v4l2_queryctrl &qctrl = ctrlMap[id]; + QWidget *w = widgetMap[qctrl.id]; + v4l2_querymenu qmenu; + int i, idx; + + switch (qctrl.type) { + case V4L2_CTRL_TYPE_INTEGER: + if (qctrl.flags & V4L2_CTRL_FLAG_SLIDER) { + return static_cast(w)->value(); + } + + if (qctrl.maximum - qctrl.minimum <= 255) { + return static_cast(w)->value(); + } + return static_cast(w)->text().toInt(); + + case V4L2_CTRL_TYPE_BOOLEAN: + return static_cast(w)->isChecked(); + + case V4L2_CTRL_TYPE_MENU: + idx = static_cast(w)->currentItem(); + for (i = qctrl.minimum; i <= qctrl.maximum; i++) { + qmenu.id = qctrl.id; + qmenu.index = i; + if (::ioctl(fd, VIDIOC_QUERYMENU, &qmenu)) + continue; + if (idx-- == 0) + break; + } + return i; + + default: + break; + } + return 0; +} + +void ApplicationWindow::updateCtrl(unsigned id) +{ + unsigned ctrl_class = V4L2_CTRL_ID2CLASS(id); + if (ctrl_class == V4L2_CID_PRIVATE_BASE) + ctrl_class = V4L2_CTRL_CLASS_USER; + + if (ctrlMap[id].flags & (V4L2_CTRL_FLAG_READ_ONLY | V4L2_CTRL_FLAG_INACTIVE)) + return; + + if (ctrl_class == V4L2_CTRL_CLASS_USER) { + struct v4l2_control c; + + c.id = id; + c.value = getVal(id); + if (::ioctl(fd, VIDIOC_S_CTRL, &c)) { + int err = errno; + + printf("error %08x (%s): %s\n", id, + ctrlMap[id].name, strerror(err)); + } + return; + } + struct v4l2_ext_control c; + struct v4l2_ext_controls ctrls; + + memset(&c, 0, sizeof(c)); + memset(&ctrls, 0, sizeof(ctrls)); + c.id = id; + if (ctrlMap[id].type == V4L2_CTRL_TYPE_INTEGER64) + c.value64 = getVal64(id); + else + c.value = getVal(id); + ctrls.count = 1; + ctrls.ctrl_class = ctrl_class; + ctrls.controls = &c; + if (::ioctl(fd, VIDIOC_S_EXT_CTRLS, &ctrls)) { + int err = errno; + + printf("error %08x (%s): %s\n", id, + ctrlMap[id].name, strerror(err)); + } + else if (ctrlMap[id].flags & V4L2_CTRL_FLAG_UPDATE) + refresh(ctrl_class); + else { + if (ctrlMap[id].type == V4L2_CTRL_TYPE_INTEGER64) + setVal64(id, c.value64); + else + setVal(id, c.value); + } +} + +void ApplicationWindow::refresh(unsigned ctrl_class) +{ + if (ctrl_class == V4L2_CTRL_CLASS_USER) { + for (unsigned i = 0; i < classMap[ctrl_class].size(); i++) { + unsigned id = classMap[ctrl_class][i]; + + v4l2_control c; + + c.id = id; + if (::ioctl(fd, VIDIOC_G_CTRL, &c)) { + int err = errno; + + printf("error %08x (%s): %s\n", id, + ctrlMap[id].name, strerror(err)); + } + setVal(id, c.value); + } + return; + } + unsigned count = classMap[ctrl_class].size(); + struct v4l2_ext_control *c = new v4l2_ext_control[count]; + struct v4l2_ext_controls ctrls; + + for (unsigned i = 0; i < count; i++) { + c[i].id = classMap[ctrl_class][i]; + } + memset(&ctrls, 0, sizeof(ctrls)); + ctrls.count = count; + ctrls.ctrl_class = ctrl_class; + ctrls.controls = c; + if (::ioctl(fd, VIDIOC_G_EXT_CTRLS, &ctrls)) { + int err = errno; + + if (ctrls.error_idx >= ctrls.count) { + printf("error: %s\n", strerror(err)); + } + else { + unsigned id = c[ctrls.error_idx].id; + printf("error %08x (%s): %s\n", id, + ctrlMap[id].name, strerror(err)); + } + } + else { + for (unsigned i = 0; i < ctrls.count; i++) { + unsigned id = c[i].id; + if (ctrlMap[id].type == V4L2_CTRL_TYPE_INTEGER64) + setVal64(id, c[i].value64); + else + setVal(id, c[i].value); + ::ioctl(fd, VIDIOC_QUERYCTRL, &ctrlMap[id]); + widgetMap[id]->setDisabled(ctrlMap[id].flags & + (V4L2_CTRL_FLAG_READ_ONLY | V4L2_CTRL_FLAG_INACTIVE)); + } + } + delete [] c; +} + +void ApplicationWindow::setVal(unsigned id, int v) +{ + const v4l2_queryctrl &qctrl = ctrlMap[id]; + v4l2_querymenu qmenu; + QWidget *w = widgetMap[qctrl.id]; + int i, idx; + + switch (qctrl.type) { + case V4L2_CTRL_TYPE_INTEGER: + if (qctrl.flags & V4L2_CTRL_FLAG_SLIDER) + static_cast(w)->setValue(v); + else if (qctrl.maximum - qctrl.minimum <= 255) + static_cast(w)->setValue(v); + else + static_cast(w)->setText(QString::number(v)); + break; + + case V4L2_CTRL_TYPE_BOOLEAN: + static_cast(w)->setChecked(v); + break; + + case V4L2_CTRL_TYPE_MENU: + idx = 0; + for (i = qctrl.minimum; i <= v; i++) { + qmenu.id = id; + qmenu.index = i; + if (::ioctl(fd, VIDIOC_QUERYMENU, &qmenu)) + continue; + idx++; + } + static_cast(w)->setCurrentItem(idx - 1); + break; + default: + break; + } +} + +void ApplicationWindow::setVal64(unsigned id, long long v) +{ + const v4l2_queryctrl &qctrl = ctrlMap[id]; + QWidget *w = widgetMap[qctrl.id]; + + switch (qctrl.type) { + case V4L2_CTRL_TYPE_INTEGER64: + static_cast(w)->setText(QString::number(v)); + break; + default: + break; + } +} + +void ApplicationWindow::setDefaults(unsigned ctrl_class) +{ + for (unsigned i = 0; i < classMap[ctrl_class].size(); i++) { + unsigned id = classMap[ctrl_class][i]; + + if (ctrlMap[id].type != V4L2_CTRL_TYPE_INTEGER64 && + ctrlMap[id].type != V4L2_CTRL_TYPE_BUTTON) + setVal(id, ctrlMap[id].default_value); + } + ctrlAction(ctrl_class | CTRL_UPDATE); +} + +void ApplicationWindow::choose() +{ + QString fn = QFileDialog::getOpenFileName( "/dev/v4l", QString::null, + this); + if ( !fn.isEmpty() ) { + setDevice(fn); + } + else + statusBar()->message( "Loading aborted", 2000 ); +} + + +void ApplicationWindow::closeEvent( QCloseEvent* ce ) +{ + ce->accept(); +} + + +void ApplicationWindow::about() +{ + QMessageBox::about( this, "V4L2 Control Panel", + "This program allows easy experimenting with video4linux devices."); +} + + +int main(int argc, char **argv) +{ + QApplication a(argc, argv); + ApplicationWindow *mw = new ApplicationWindow(); + mw->setCaption( "V4L2 Control Panel" ); + mw->setDevice("/dev/video0"); + mw->show(); + a.connect( &a, SIGNAL(lastWindowClosed()), &a, SLOT(quit()) ); + return a.exec(); +} diff --git a/test/qv4l2/qv4l2.h b/test/qv4l2/qv4l2.h new file mode 100644 index 000000000..f3ecf7262 --- /dev/null +++ b/test/qv4l2/qv4l2.h @@ -0,0 +1,79 @@ +/**************************************************************************** +** $Id: qt/application.h 3.3.6 edited Aug 31 2005 $ +** +** Copyright (C) 1992-2005 Trolltech AS. All rights reserved. +** +** This file is part of an example program for Qt. This example +** program may be used, distributed and modified without limitation. +** +*****************************************************************************/ + +#ifndef APPLICATION_H +#define APPLICATION_H + +#include +#include +#include +#include +#include +#include + +#define __user +#include + +class QTextEdit; + +typedef std::vector ClassIDVec; +typedef std::map ClassMap; +typedef std::map CtrlMap; +typedef std::map WidgetMap; + +enum { + CTRL_UPDATE_ON_CHANGE = 0x10, + CTRL_DEFAULTS, + CTRL_REFRESH, + CTRL_UPDATE +}; + +class ApplicationWindow: public QMainWindow +{ + Q_OBJECT + +public: + ApplicationWindow(); + ~ApplicationWindow(); + + void setDevice(const QString &device); + +protected: + void closeEvent( QCloseEvent* ); + +private slots: + void choose(); + void ctrlAction(int); + + void about(); + +private: + void addTabs(); + void finishGrid(QWidget *vbox, QGrid *grid, unsigned ctrl_class, bool odd); + void addCtrl(QGrid *grid, const struct v4l2_queryctrl &qctrl); + void updateCtrl(unsigned id); + void refresh(unsigned ctrl_class); + void setDefaults(unsigned ctrl_class); + int getVal(unsigned id); + long long getVal64(unsigned id); + void setVal(unsigned id, int v); + void setVal64(unsigned id, long long v); + + QString filename; + QSignalMapper *sigMapper; + QTabWidget *tabs; + int fd; + CtrlMap ctrlMap; + WidgetMap widgetMap; + ClassMap classMap; +}; + + +#endif diff --git a/test/qv4l2/qv4l2.pro b/test/qv4l2/qv4l2.pro new file mode 100644 index 000000000..62eb56b07 --- /dev/null +++ b/test/qv4l2/qv4l2.pro @@ -0,0 +1,10 @@ +###################################################################### +# Automatically generated by qmake (1.07a) Sat Jun 17 12:35:16 2006 +###################################################################### + +TEMPLATE = app +INCLUDEPATH += . ../../linux/include + +# Input +HEADERS += qv4l2.h +SOURCES += qv4l2.cpp -- cgit v1.2.3 From 6e6b1365d84797ce24f670257d61225ed52c0205 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Sun, 18 Jun 2006 21:11:06 +0200 Subject: Port cx88-blackbird to the new MPEG API. From: Hans Verkuil Signed-off-by: Hans Verkuil --- linux/drivers/media/video/cx88/cx88-blackbird.c | 771 +++--------------------- linux/drivers/media/video/cx88/cx88.h | 16 +- 2 files changed, 74 insertions(+), 713 deletions(-) diff --git a/linux/drivers/media/video/cx88/cx88-blackbird.c b/linux/drivers/media/video/cx88/cx88-blackbird.c index 05904b655..cad6f4a92 100644 --- a/linux/drivers/media/video/cx88/cx88-blackbird.c +++ b/linux/drivers/media/video/cx88/cx88-blackbird.c @@ -90,163 +90,11 @@ enum blackbird_framerate { BLACKBIRD_FRAMERATE_NTSC_30, /* NTSC: 30fps */ BLACKBIRD_FRAMERATE_PAL_25 /* PAL: 25fps */ }; -enum blackbird_video_bitrate_type { - BLACKBIRD_VIDEO_VBR, - BLACKBIRD_VIDEO_CBR -}; -#define BLACKBIRD_PEAK_RATE_DIVISOR 400 -enum blackbird_mux_rate { - BLACKBIRD_MUX_RATE_DEFAULT, - /* dvd mux rate: multiply by 400 to get the actual rate */ - BLACKBIRD_MUX_RATE_DVD = 25200 -}; -enum blackbird_aspect_ratio { - BLACKBIRD_ASPECT_RATIO_FORBIDDEN, - BLACKBIRD_ASPECT_RATIO_1_1_SQUARE, - BLACKBIRD_ASPECT_RATIO_4_3, - BLACKBIRD_ASPECT_RATIO_16_9, - BLACKBIRD_ASPECT_RATIO_221_100, - BLACKBIRD_ASPECT_RATIO_RESERVED -}; -enum blackbird_dnr_bits { - BLACKBIRD_DNR_BITS_MANUAL, - BLACKBIRD_DNR_BITS_AUTO_SPATIAL, - BLACKBIRD_DNR_BITS_AUTO_TEMPORAL, - BLACKBIRD_DNR_BITS_AUTO -}; -enum blackbird_median_filter { - BLACKBIRD_MEDIAN_FILTER_DISABLED, - BLACKBIRD_MEDIAN_FILTER_HORIZONTAL, - BLACKBIRD_MEDIAN_FILTER_VERTICAL, - BLACKBIRD_MEDIAN_FILTER_HV, - BLACKBIRD_MEDIAN_FILTER_DIAGONAL -}; -enum blackbird_spatial_filter_luma { - BLACKBIRD_SPATIAL_FILTER_LUMA_DISABLED, - BLACKBIRD_SPATIAL_FILTER_LUMA_1D_HORIZ, - BLACKBIRD_SPATIAL_FILTER_LUMA_1D_VERT, - BLACKBIRD_SPATIAL_FILTER_LUMA_2D_HV, /* separable, default */ - BLACKBIRD_SPATIAL_FILTER_LUMA_2D_SYMM /* symmetric non-separable */ -}; -enum blackbird_spatial_filter_chroma { - BLACKBIRD_SPATIAL_FILTER_CHROMA_DISABLED, - BLACKBIRD_SPATIAL_FILTER_CHROMA_1D_HORIZ /* default */ -}; -enum blackbird_pulldown { - BLACKBIRD_3_2_PULLDOWN_DISABLED, - BLACKBIRD_3_2_PULLDOWN_ENABLED -}; -enum blackbird_vbi_line_bits { - BLACKBIRD_VBI_LINE_BITS_TOP_FIELD, - BLACKBIRD_VBI_LINE_BITS_BOT_FIELD = (1 << 31), - BLACKBIRD_VBI_LINE_BITS_ALL_LINES = 0xFFFFFFFF -}; -enum blackbird_vbi_line { - BLACKBIRD_VBI_LINE_DISABLED, - BLACKBIRD_VBI_LINE_ENABLED -}; -enum blackbird_vbi_slicing { - BLACKBIRD_VBI_SLICING_NONE, - BLACKBIRD_VBI_SLICING_CLOSED_CAPTION -}; -enum blackbird_stream_type { - BLACKBIRD_STREAM_PROGRAM, - BLACKBIRD_STREAM_TRANSPORT, - BLACKBIRD_STREAM_MPEG1, - BLACKBIRD_STREAM_PES_AV, - BLACKBIRD_STREAM_UNKNOWN4, - BLACKBIRD_STREAM_PES_VIDEO, - BLACKBIRD_STREAM_UNKNOWN6, - BLACKBIRD_STREAM_PES_AUDIO, - BLACKBIRD_STREAM_UNKNOWN8, - BLACKBIRD_STREAM_UNKNOWN9, /* audio/pcm ? */ - BLACKBIRD_STREAM_DVD, - BLACKBIRD_STREAM_VCD, - BLACKBIRD_STREAM_UNKNOWN12 /* svcd/xvcd ? */ -}; enum blackbird_stream_port { BLACKBIRD_OUTPUT_PORT_MEMORY, BLACKBIRD_OUTPUT_PORT_STREAMING, BLACKBIRD_OUTPUT_PORT_SERIAL }; -enum blackbird_audio_bits_sample_rate { - BLACKBIRD_AUDIO_BITS_44100HZ, - BLACKBIRD_AUDIO_BITS_48000HZ, - BLACKBIRD_AUDIO_BITS_32000HZ, - BLACKBIRD_AUDIO_BITS_RESERVED_HZ, -}; -enum blackbird_audio_bits_encoding { - BLACKBIRD_AUDIO_BITS_LAYER_1 = 0x1 << 2, - BLACKBIRD_AUDIO_BITS_LAYER_2 = 0x2 << 2, -}; -enum blackbird_audio_bits_bitrate_layer_1 { - BLACKBIRD_AUDIO_BITS_LAYER_1_FREE_FORMAT, - BLACKBIRD_AUDIO_BITS_LAYER_1_32 = 0x01 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_64 = 0x02 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_96 = 0x03 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_128 = 0x04 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_160 = 0x05 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_192 = 0x06 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_224 = 0x07 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_256 = 0x08 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_288 = 0x09 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_320 = 0x0A << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_352 = 0x0B << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_384 = 0x0C << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_416 = 0x0D << 4, - BLACKBIRD_AUDIO_BITS_LAYER_1_448 = 0x0E << 4, -}; -enum blackbird_audio_bits_bitrate_layer_2 { - BLACKBIRD_AUDIO_BITS_LAYER_2_FREE_FORMAT, - BLACKBIRD_AUDIO_BITS_LAYER_2_32 = 0x01 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_48 = 0x02 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_56 = 0x03 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_64 = 0x04 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_80 = 0x05 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_96 = 0x06 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_112 = 0x07 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_128 = 0x08 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_160 = 0x09 << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_192 = 0x0A << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_224 = 0x0B << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_256 = 0x0C << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_320 = 0x0D << 4, - BLACKBIRD_AUDIO_BITS_LAYER_2_384 = 0x0E << 4, -}; -enum blackbird_audio_bits_mode { - BLACKBIRD_AUDIO_BITS_STEREO, - BLACKBIRD_AUDIO_BITS_JOINT_STEREO = 0x1 << 8, - BLACKBIRD_AUDIO_BITS_DUAL = 0x2 << 8, - BLACKBIRD_AUDIO_BITS_MONO = 0x3 << 8, -}; -enum blackbird_audio_bits_mode_extension { - BLACKBIRD_AUDIO_BITS_BOUND_4, - BLACKBIRD_AUDIO_BITS_BOUND_8 = 0x1 << 10, - BLACKBIRD_AUDIO_BITS_BOUND_12 = 0x2 << 10, - BLACKBIRD_AUDIO_BITS_BOUND_16 = 0x3 << 10, -}; -enum blackbird_audio_bits_emphasis { - BLACKBIRD_AUDIO_BITS_EMPHASIS_NONE, - BLACKBIRD_AUDIO_BITS_EMPHASIS_50_15 = 0x1 << 12, - BLACKBIRD_AUDIO_BITS_EMPHASIS_RESERVED = 0x2 << 12, - BLACKBIRD_AUDIO_BITS_EMPHASIS_CCITT_J17 = 0x3 << 12, -}; -enum blackbird_audio_bits_crc { - BLACKBIRD_AUDIO_BITS_CRC_OFF, - BLACKBIRD_AUDIO_BITS_CRC_ON = 0x1 << 14, -}; -enum blackbird_audio_bits_copyright { - BLACKBIRD_AUDIO_BITS_COPYRIGHT_OFF, - BLACKBIRD_AUDIO_BITS_COPYRIGHT_ON = 0x1 << 15, -}; -enum blackbird_audio_bits_original { - BLACKBIRD_AUDIO_BITS_COPY, - BLACKBIRD_AUDIO_BITS_ORIGINAL = 0x1 << 16, -}; -enum blackbird_gop_closure { - BLACKBIRD_GOP_CLOSURE_OFF, - BLACKBIRD_GOP_CLOSURE_ON, -}; enum blackbird_data_xfer_status { BLACKBIRD_MORE_BUFFERS_FOLLOW, BLACKBIRD_LAST_BUFFER, @@ -464,15 +312,12 @@ static int register_read(struct cx88_core *core, u32 address, u32 *value) /* ------------------------------------------------------------------ */ -/* We don't need to call the API often, so using just one mailbox will probably suffice */ -static int blackbird_api_cmd(struct cx8802_dev *dev, u32 command, - u32 inputcnt, u32 outputcnt, ...) +static int blackbird_mbox_func(void *priv, int command, int in, int out, u32 data[CX2341X_MBOX_MAX_DATA]) { + struct cx8802_dev *dev = priv; unsigned long timeout; u32 value, flag, retval; int i; - va_list args; - va_start(args, outputcnt); dprintk(1,"%s: 0x%X\n", __FUNCTION__, command); @@ -496,12 +341,11 @@ static int blackbird_api_cmd(struct cx8802_dev *dev, u32 command, /* write command + args + fill remaining with zeros */ memory_write(dev->core, dev->mailbox + 1, command); /* command code */ memory_write(dev->core, dev->mailbox + 3, IVTV_API_STD_TIMEOUT); /* timeout */ - for (i = 0; i < inputcnt ; i++) { - value = va_arg(args, int); - memory_write(dev->core, dev->mailbox + 4 + i, value); - dprintk(1, "API Input %d = %d\n", i, value); + for (i = 0; i < in; i++) { + memory_write(dev->core, dev->mailbox + 4 + i, data[i]); + dprintk(1, "API Input %d = %d\n", i, data[i]); } - for (; i < 16 ; i++) + for (; i < CX2341X_MBOX_MAX_DATA; i++) memory_write(dev->core, dev->mailbox + 4 + i, 0); flag |= 3; /* tell 'em we're done writing */ @@ -521,12 +365,10 @@ static int blackbird_api_cmd(struct cx8802_dev *dev, u32 command, } /* read output values */ - for (i = 0; i < outputcnt ; i++) { - int *vptr = va_arg(args, int *); - memory_read(dev->core, dev->mailbox + 4 + i, vptr); - dprintk(1, "API Output %d = %d\n", i, *vptr); + for (i = 0; i < out; i++) { + memory_read(dev->core, dev->mailbox + 4 + i, data + i); + dprintk(1, "API Output %d = %d\n", i, data[i]); } - va_end(args); memory_read(dev->core, dev->mailbox + 2, &retval); dprintk(1, "API result = %d\n",retval); @@ -535,7 +377,29 @@ static int blackbird_api_cmd(struct cx8802_dev *dev, u32 command, memory_write(dev->core, dev->mailbox, flag); return retval; } +/* ------------------------------------------------------------------ */ + +/* We don't need to call the API often, so using just one mailbox will probably suffice */ +static int blackbird_api_cmd(struct cx8802_dev *dev, u32 command, + u32 inputcnt, u32 outputcnt, ...) +{ + u32 data[CX2341X_MBOX_MAX_DATA]; + va_list vargs; + int i, err; + va_start(vargs, outputcnt); + + for (i = 0; i < inputcnt; i++) { + data[i] = va_arg(vargs, int); + } + err = blackbird_mbox_func(dev, command, inputcnt, outputcnt, data); + for (i = 0; i < outputcnt; i++) { + int *vptr = va_arg(vargs, int *); + *vptr = data[i]; + } + va_end(vargs); + return err; +} static int blackbird_find_mailbox(struct cx8802_dev *dev) { @@ -657,12 +521,19 @@ DB* DVD | MPEG2 | 720x576PAL | CBR | 600 :Good | 6000 Kbps | 25fps | M *DB: "DirectBurn" */ -static struct blackbird_dnr default_dnr_params = { - .mode = BLACKBIRD_DNR_BITS_MANUAL, - .type = BLACKBIRD_MEDIAN_FILTER_DISABLED, - .spatial = 0, - .temporal = 0 -}; +static void blackbird_codec_settings(struct cx8802_dev *dev) +{ + /* assign frame size */ + blackbird_api_cmd(dev, CX2341X_ENC_SET_FRAME_SIZE, 2, 0, + dev->height, dev->width); + + dev->params.width = dev->width; + dev->params.height = dev->height; + dev->params.is_50hz = (dev->core->tvnorm->id & V4L2_STD_625_50) != 0; + + cx2341x_update(dev, blackbird_mbox_func, NULL, &dev->params); +} + static struct v4l2_mpeg_compression default_mpeg_params = { .st_type = V4L2_MPEG_PS_2, .st_bitrate = { @@ -683,7 +554,7 @@ static struct v4l2_mpeg_compression default_mpeg_params = { .target = 224, .max = 224 }, - .au_sample_rate = 44100, + .au_sample_rate = 48000, .au_pesid = 0, .vi_type = V4L2_MPEG_VI_2, .vi_aspect_ratio = V4L2_MPEG_ASPECT_4_3, @@ -694,524 +565,13 @@ static struct v4l2_mpeg_compression default_mpeg_params = { .max = 6000 }, .vi_frame_rate = 25, - .vi_frames_per_gop = 15, + .vi_frames_per_gop = 12, .vi_bframes_count = 2, .vi_pesid = 0, - .closed_gops = 0, + .closed_gops = 1, .pulldown = 0 }; -static enum blackbird_stream_type mpeg_stream_types[] = { - [V4L2_MPEG_SS_1] = BLACKBIRD_STREAM_MPEG1, - [V4L2_MPEG_PS_2] = BLACKBIRD_STREAM_PROGRAM, - [V4L2_MPEG_TS_2] = BLACKBIRD_STREAM_TRANSPORT, - [V4L2_MPEG_PS_DVD] = BLACKBIRD_STREAM_DVD, -}; -static enum blackbird_aspect_ratio mpeg_stream_ratios[] = { - [V4L2_MPEG_ASPECT_SQUARE] = BLACKBIRD_ASPECT_RATIO_1_1_SQUARE, - [V4L2_MPEG_ASPECT_4_3] = BLACKBIRD_ASPECT_RATIO_4_3, - [V4L2_MPEG_ASPECT_16_9] = BLACKBIRD_ASPECT_RATIO_16_9, - [V4L2_MPEG_ASPECT_1_221] = BLACKBIRD_ASPECT_RATIO_221_100, -}; -static enum blackbird_video_bitrate_type mpeg_video_bitrates[] = { - [V4L2_BITRATE_NONE] = BLACKBIRD_VIDEO_CBR, - [V4L2_BITRATE_CBR] = BLACKBIRD_VIDEO_CBR, - [V4L2_BITRATE_VBR] = BLACKBIRD_VIDEO_VBR, -}; -/* find the best layer I/II bitrate to fit a given numeric value */ -struct bitrate_bits { - u32 bits; /* layer bits for the best fit */ - u32 rate; /* actual numeric value for the layer best fit */ -}; -struct bitrate_approximation { - u32 target; /* numeric value of the rate we want */ - struct bitrate_bits layer[2]; -}; -static struct bitrate_approximation mpeg_audio_bitrates[] = { - /* target layer[0].bits layer[0].rate layer[1].bits layer[1].rate */ - { 0, { { 0, 0, }, { 0, 0, }, }, }, - { 32, { { BLACKBIRD_AUDIO_BITS_LAYER_1_32 , 32, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_32 , 32, }, }, }, - { 48, { { BLACKBIRD_AUDIO_BITS_LAYER_1_64 , 64, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_48 , 48, }, }, }, - { 56, { { BLACKBIRD_AUDIO_BITS_LAYER_1_64 , 64, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_56 , 56, }, }, }, - { 64, { { BLACKBIRD_AUDIO_BITS_LAYER_1_64 , 64, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_64 , 64, }, }, }, - { 80, { { BLACKBIRD_AUDIO_BITS_LAYER_1_96 , 96, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_80 , 80, }, }, }, - { 96, { { BLACKBIRD_AUDIO_BITS_LAYER_1_96 , 96, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_96 , 96, }, }, }, - { 112, { { BLACKBIRD_AUDIO_BITS_LAYER_1_128, 128, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_112, 112, }, }, }, - { 128, { { BLACKBIRD_AUDIO_BITS_LAYER_1_128, 128, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_128, 128, }, }, }, - { 160, { { BLACKBIRD_AUDIO_BITS_LAYER_1_160, 160, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_160, 160, }, }, }, - { 192, { { BLACKBIRD_AUDIO_BITS_LAYER_1_192, 192, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_192, 192, }, }, }, - { 224, { { BLACKBIRD_AUDIO_BITS_LAYER_1_224, 224, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_224, 224, }, }, }, - { 256, { { BLACKBIRD_AUDIO_BITS_LAYER_1_256, 256, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_256, 256, }, }, }, - { 288, { { BLACKBIRD_AUDIO_BITS_LAYER_1_288, 288, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_320, 320, }, }, }, - { 320, { { BLACKBIRD_AUDIO_BITS_LAYER_1_320, 320, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_320, 320, }, }, }, - { 352, { { BLACKBIRD_AUDIO_BITS_LAYER_1_352, 352, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_384, 384, }, }, }, - { 384, { { BLACKBIRD_AUDIO_BITS_LAYER_1_384, 384, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_384, 384, }, }, }, - { 416, { { BLACKBIRD_AUDIO_BITS_LAYER_1_416, 416, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_384, 384, }, }, }, - { 448, { { BLACKBIRD_AUDIO_BITS_LAYER_1_448, 448, }, { BLACKBIRD_AUDIO_BITS_LAYER_2_384, 384, }, }, }, -}; -static const int BITRATES_SIZE = ARRAY_SIZE(mpeg_audio_bitrates); - -static void blackbird_set_default_params(struct cx8802_dev *dev) -{ - struct v4l2_mpeg_compression *params = &dev->params; - u32 au_params; - - /* assign stream type */ - if( params->st_type >= ARRAY_SIZE(mpeg_stream_types) ) - params->st_type = V4L2_MPEG_PS_2; - if( params->st_type == V4L2_MPEG_SS_1 ) - params->vi_type = V4L2_MPEG_VI_1; - else - params->vi_type = V4L2_MPEG_VI_2; - blackbird_api_cmd(dev, CX2341X_ENC_SET_STREAM_TYPE, 1, 0, mpeg_stream_types[params->st_type]); - - /* assign framerate */ - if( params->vi_frame_rate <= 25 ) - { - params->vi_frame_rate = 25; - blackbird_api_cmd(dev, CX2341X_ENC_SET_FRAME_RATE, 1, 0, BLACKBIRD_FRAMERATE_PAL_25); - } - else - { - params->vi_frame_rate = 30; - blackbird_api_cmd(dev, CX2341X_ENC_SET_FRAME_RATE, 1, 0, BLACKBIRD_FRAMERATE_NTSC_30); - } - - /* assign aspect ratio */ - if( params->vi_aspect_ratio >= ARRAY_SIZE(mpeg_stream_ratios) ) - params->vi_aspect_ratio = V4L2_MPEG_ASPECT_4_3; - blackbird_api_cmd(dev, CX2341X_ENC_SET_ASPECT_RATIO, 1, 0, mpeg_stream_ratios[params->vi_aspect_ratio]); - - /* assign gop properties */ - blackbird_api_cmd(dev, CX2341X_ENC_SET_GOP_PROPERTIES, 2, 0, params->vi_frames_per_gop, params->vi_bframes_count+1); - - /* assign gop closure */ - blackbird_api_cmd(dev, CX2341X_ENC_SET_GOP_CLOSURE, 1, 0, params->closed_gops); - - /* assign 3 2 pulldown */ - blackbird_api_cmd(dev, CX2341X_ENC_SET_3_2_PULLDOWN, 1, 0, params->pulldown); - - /* make sure the params are within bounds */ - if( params->st_bitrate.mode >= ARRAY_SIZE(mpeg_video_bitrates) ) - params->vi_bitrate.mode = V4L2_BITRATE_NONE; - if( params->vi_bitrate.mode >= ARRAY_SIZE(mpeg_video_bitrates) ) - params->vi_bitrate.mode = V4L2_BITRATE_NONE; - if( params->au_bitrate.mode >= ARRAY_SIZE(mpeg_video_bitrates) ) - params->au_bitrate.mode = V4L2_BITRATE_NONE; - - /* assign audio properties */ - /* note: it's not necessary to set the samplerate, the mpeg encoder seems to autodetect/adjust */ - au_params = BLACKBIRD_AUDIO_BITS_STEREO | - /* BLACKBIRD_AUDIO_BITS_BOUND_4 | */ - BLACKBIRD_AUDIO_BITS_EMPHASIS_NONE | - BLACKBIRD_AUDIO_BITS_CRC_OFF | - BLACKBIRD_AUDIO_BITS_COPYRIGHT_OFF | - BLACKBIRD_AUDIO_BITS_COPY | - 0; - if( params->au_sample_rate <= 32000 ) - { - params->au_sample_rate = 32000; - au_params |= BLACKBIRD_AUDIO_BITS_32000HZ; - } - else if( params->au_sample_rate <= 44100 ) - { - params->au_sample_rate = 44100; - au_params |= BLACKBIRD_AUDIO_BITS_44100HZ; - } - else - { - params->au_sample_rate = 48000; - au_params |= BLACKBIRD_AUDIO_BITS_48000HZ; - } - if( params->au_type == V4L2_MPEG_AU_2_I ) - { - au_params |= BLACKBIRD_AUDIO_BITS_LAYER_1; - } - else - { - /* TODO: try to handle the other formats more gracefully */ - params->au_type = V4L2_MPEG_AU_2_II; - au_params |= BLACKBIRD_AUDIO_BITS_LAYER_2; - } - if( params->au_bitrate.mode ) - { - int layer; - - if( params->au_bitrate.mode == V4L2_BITRATE_CBR ) - params->au_bitrate.max = params->vi_bitrate.target; - else - params->au_bitrate.target = params->vi_bitrate.max; - - layer = params->au_type; - if( params->au_bitrate.target == 0 ) - { - /* TODO: use the minimum possible bitrate instead of 0 ? */ - au_params |= 0; - } - else if( params->au_bitrate.target >= - mpeg_audio_bitrates[BITRATES_SIZE-1].layer[layer].rate ) - { - /* clamp the bitrate to the max supported by the standard */ - params->au_bitrate.target = mpeg_audio_bitrates[BITRATES_SIZE-1].layer[layer].rate; - params->au_bitrate.max = params->au_bitrate.target; - au_params |= mpeg_audio_bitrates[BITRATES_SIZE-1].layer[layer].bits; - } - else - { - /* round up to the nearest supported bitrate */ - int i; - for(i = 1; i < BITRATES_SIZE; i++) - { - if( params->au_bitrate.target > mpeg_audio_bitrates[i-1].layer[layer].rate && - params->au_bitrate.target <= mpeg_audio_bitrates[i].layer[layer].rate ) - { - params->au_bitrate.target = mpeg_audio_bitrates[i].layer[layer].rate; - params->au_bitrate.max = params->au_bitrate.target; - au_params |= mpeg_audio_bitrates[i].layer[layer].bits; - break; - } - } - } - } - else - { - /* TODO: ??? */ - params->au_bitrate.target = params->au_bitrate.max = 0; - au_params |= 0; - } - blackbird_api_cmd(dev, CX2341X_ENC_SET_AUDIO_PROPERTIES, 1, 0, au_params ); - - /* assign bitrates */ - if( params->vi_bitrate.mode ) - { - /* bitrate is set, let's figure out the cbr/vbr mess */ - if( params->vi_bitrate.max < params->vi_bitrate.target ) - { - if( params->vi_bitrate.mode == V4L2_BITRATE_CBR ) - params->vi_bitrate.max = params->vi_bitrate.target; - else - params->vi_bitrate.target = params->vi_bitrate.max; - } - } - else - { - if( params->st_bitrate.max < params->st_bitrate.target ) - { - if( params->st_bitrate.mode == V4L2_BITRATE_VBR ) - params->st_bitrate.target = params->st_bitrate.max; - else - params->st_bitrate.max = params->st_bitrate.target; - } - /* calculate vi_bitrate = st_bitrate - au_bitrate */ - params->vi_bitrate.max = params->st_bitrate.max - params->au_bitrate.max; - params->vi_bitrate.target = params->st_bitrate.target - params->au_bitrate.target; - } - blackbird_api_cmd(dev, CX2341X_ENC_SET_BIT_RATE, 4, 0, - mpeg_video_bitrates[params->vi_bitrate.mode], - params->vi_bitrate.target * 1000, /* kbps -> bps */ - params->vi_bitrate.max * 1000 / BLACKBIRD_PEAK_RATE_DIVISOR, /* peak/400 */ - BLACKBIRD_MUX_RATE_DEFAULT /*, 0x70*/); /* encoding buffer, ckennedy */ - - /* TODO: implement the stream ID stuff: - ts_pid_pmt, ts_pid_audio, ts_pid_video, ts_pid_pcr, - ps_size, au_pesid, vi_pesid - */ -} -#define CHECK_PARAM( name ) ( dev->params.name != params->name ) -#define IF_PARAM( name ) if( CHECK_PARAM( name ) ) -#define UPDATE_PARAM( name ) dev->params.name = params->name -void blackbird_set_params(struct cx8802_dev *dev, struct v4l2_mpeg_compression *params) -{ - u32 au_params; - - /* assign stream type */ - if( params->st_type >= ARRAY_SIZE(mpeg_stream_types) ) - params->st_type = V4L2_MPEG_PS_2; - if( params->st_type == V4L2_MPEG_SS_1 ) - params->vi_type = V4L2_MPEG_VI_1; - else - params->vi_type = V4L2_MPEG_VI_2; - if( CHECK_PARAM( st_type ) || CHECK_PARAM( vi_type ) ) - { - UPDATE_PARAM( st_type ); - UPDATE_PARAM( vi_type ); - blackbird_api_cmd(dev, CX2341X_ENC_SET_STREAM_TYPE, 1, 0, mpeg_stream_types[params->st_type]); - } - - /* assign framerate */ - if( params->vi_frame_rate <= 25 ) - params->vi_frame_rate = 25; - else - params->vi_frame_rate = 30; - IF_PARAM( vi_frame_rate ) - { - UPDATE_PARAM( vi_frame_rate ); - if( params->vi_frame_rate == 25 ) - blackbird_api_cmd(dev, CX2341X_ENC_SET_FRAME_RATE, 1, 0, BLACKBIRD_FRAMERATE_PAL_25); - else - blackbird_api_cmd(dev, CX2341X_ENC_SET_FRAME_RATE, 1, 0, BLACKBIRD_FRAMERATE_NTSC_30); - } - - /* assign aspect ratio */ - if( params->vi_aspect_ratio >= ARRAY_SIZE(mpeg_stream_ratios) ) - params->vi_aspect_ratio = V4L2_MPEG_ASPECT_4_3; - IF_PARAM( vi_aspect_ratio ) - { - UPDATE_PARAM( vi_aspect_ratio ); - blackbird_api_cmd(dev, CX2341X_ENC_SET_ASPECT_RATIO, 1, 0, mpeg_stream_ratios[params->vi_aspect_ratio]); - } - - /* assign gop properties */ - if( CHECK_PARAM( vi_frames_per_gop ) || CHECK_PARAM( vi_bframes_count ) ) - { - UPDATE_PARAM( vi_frames_per_gop ); - UPDATE_PARAM( vi_bframes_count ); - blackbird_api_cmd(dev, CX2341X_ENC_SET_GOP_PROPERTIES, 2, 0, params->vi_frames_per_gop, params->vi_bframes_count+1); - } - - /* assign gop closure */ - IF_PARAM( closed_gops ) - { - UPDATE_PARAM( closed_gops ); - blackbird_api_cmd(dev, CX2341X_ENC_SET_GOP_CLOSURE, 1, 0, params->closed_gops); - } - - /* assign 3 2 pulldown */ - IF_PARAM( pulldown ) - { - UPDATE_PARAM( pulldown ); - blackbird_api_cmd(dev, CX2341X_ENC_SET_3_2_PULLDOWN, 1, 0, params->pulldown); - } - - /* make sure the params are within bounds */ - if( params->st_bitrate.mode >= ARRAY_SIZE(mpeg_video_bitrates) ) - params->vi_bitrate.mode = V4L2_BITRATE_NONE; - if( params->vi_bitrate.mode >= ARRAY_SIZE(mpeg_video_bitrates) ) - params->vi_bitrate.mode = V4L2_BITRATE_NONE; - if( params->au_bitrate.mode >= ARRAY_SIZE(mpeg_video_bitrates) ) - params->au_bitrate.mode = V4L2_BITRATE_NONE; - - /* assign audio properties */ - /* note: it's not necessary to set the samplerate, the mpeg encoder seems to autodetect/adjust */ - au_params = BLACKBIRD_AUDIO_BITS_STEREO | - /* BLACKBIRD_AUDIO_BITS_BOUND_4 | */ - BLACKBIRD_AUDIO_BITS_EMPHASIS_NONE | - BLACKBIRD_AUDIO_BITS_CRC_OFF | - BLACKBIRD_AUDIO_BITS_COPYRIGHT_OFF | - BLACKBIRD_AUDIO_BITS_COPY | - 0; - if( params->au_sample_rate < 32000 ) - { - params->au_sample_rate = 32000; - au_params |= BLACKBIRD_AUDIO_BITS_32000HZ; - } - else if( params->au_sample_rate < 44100 ) - { - params->au_sample_rate = 44100; - au_params |= BLACKBIRD_AUDIO_BITS_44100HZ; - } - else - { - params->au_sample_rate = 48000; - au_params |= BLACKBIRD_AUDIO_BITS_48000HZ; - } - if( params->au_type == V4L2_MPEG_AU_2_I ) - { - au_params |= BLACKBIRD_AUDIO_BITS_LAYER_1; - } - else - { - /* TODO: try to handle the other formats more gracefully */ - params->au_type = V4L2_MPEG_AU_2_II; - au_params |= BLACKBIRD_AUDIO_BITS_LAYER_2; - } - if( params->au_bitrate.mode ) - { - int layer; - - if( params->au_bitrate.mode == V4L2_BITRATE_CBR ) - params->au_bitrate.max = params->vi_bitrate.target; - else - params->au_bitrate.target = params->vi_bitrate.max; - - layer = params->au_type; - if( params->au_bitrate.target == 0 ) - { - /* TODO: use the minimum possible bitrate instead of 0 ? */ - au_params |= 0; - } - else if( params->au_bitrate.target >= - mpeg_audio_bitrates[BITRATES_SIZE-1].layer[layer].rate ) - { - /* clamp the bitrate to the max supported by the standard */ - params->au_bitrate.target = mpeg_audio_bitrates[BITRATES_SIZE-1].layer[layer].rate; - params->au_bitrate.max = params->au_bitrate.target; - au_params |= mpeg_audio_bitrates[BITRATES_SIZE-1].layer[layer].bits; - } - else - { - /* round up to the nearest supported bitrate */ - int i; - for(i = 1; i < BITRATES_SIZE; i++) - { - if( params->au_bitrate.target > mpeg_audio_bitrates[i-1].layer[layer].rate && - params->au_bitrate.target <= mpeg_audio_bitrates[i].layer[layer].rate ) - { - params->au_bitrate.target = mpeg_audio_bitrates[i].layer[layer].rate; - params->au_bitrate.max = params->au_bitrate.target; - au_params |= mpeg_audio_bitrates[i].layer[layer].bits; - break; - } - } - } - } - else - { - /* TODO: ??? */ - params->au_bitrate.target = params->au_bitrate.max = 0; - au_params |= 0; - } - if( CHECK_PARAM( au_type ) || CHECK_PARAM( au_sample_rate ) - || CHECK_PARAM( au_bitrate.mode ) || CHECK_PARAM( au_bitrate.max ) - || CHECK_PARAM( au_bitrate.target ) - ) - { - UPDATE_PARAM( au_type ); - UPDATE_PARAM( au_sample_rate ); - UPDATE_PARAM( au_bitrate ); - blackbird_api_cmd(dev, CX2341X_ENC_SET_AUDIO_PROPERTIES, 1, 0, au_params ); - } - - /* assign bitrates */ - if( params->vi_bitrate.mode ) - { - /* bitrate is set, let's figure out the cbr/vbr mess */ - if( params->vi_bitrate.max < params->vi_bitrate.target ) - { - if( params->vi_bitrate.mode == V4L2_BITRATE_CBR ) - params->vi_bitrate.max = params->vi_bitrate.target; - else - params->vi_bitrate.target = params->vi_bitrate.max; - } - } - else - { - if( params->st_bitrate.max < params->st_bitrate.target ) - { - if( params->st_bitrate.mode == V4L2_BITRATE_VBR ) - params->st_bitrate.target = params->st_bitrate.max; - else - params->st_bitrate.max = params->st_bitrate.target; - } - /* calculate vi_bitrate = st_bitrate - au_bitrate */ - params->vi_bitrate.max = params->st_bitrate.max - params->au_bitrate.max; - params->vi_bitrate.target = params->st_bitrate.target - params->au_bitrate.target; - } - UPDATE_PARAM( st_bitrate ); - if( CHECK_PARAM( vi_bitrate.mode ) || CHECK_PARAM( vi_bitrate.max ) - || CHECK_PARAM( vi_bitrate.target ) - ) - { - UPDATE_PARAM( vi_bitrate ); - blackbird_api_cmd(dev, CX2341X_ENC_SET_BIT_RATE, 4, 0, - mpeg_video_bitrates[params->vi_bitrate.mode], - params->vi_bitrate.target * 1000, /* kbps -> bps */ - params->vi_bitrate.max * 1000 / BLACKBIRD_PEAK_RATE_DIVISOR, /* peak/400 */ - BLACKBIRD_MUX_RATE_DEFAULT /*, 0x70*/); /* encoding buffer, ckennedy */ - } - - /* TODO: implement the stream ID stuff: - ts_pid_pmt, ts_pid_audio, ts_pid_video, ts_pid_pcr, - ps_size, au_pesid, vi_pesid - */ - UPDATE_PARAM( ts_pid_pmt ); - UPDATE_PARAM( ts_pid_audio ); - UPDATE_PARAM( ts_pid_video ); - UPDATE_PARAM( ts_pid_pcr ); - UPDATE_PARAM( ps_size ); - UPDATE_PARAM( au_pesid ); - UPDATE_PARAM( vi_pesid ); -} - -static void blackbird_set_default_dnr_params(struct cx8802_dev *dev) -{ - /* assign dnr filter mode */ - if( dev->dnr_params.mode > BLACKBIRD_DNR_BITS_AUTO ) - dev->dnr_params.mode = BLACKBIRD_DNR_BITS_MANUAL; - if( dev->dnr_params.type > BLACKBIRD_MEDIAN_FILTER_DIAGONAL ) - dev->dnr_params.type = BLACKBIRD_MEDIAN_FILTER_DISABLED; - blackbird_api_cmd(dev, CX2341X_ENC_SET_DNR_FILTER_MODE, 2, 0, - dev->dnr_params.mode, - dev->dnr_params.type - ); - - /* assign dnr filter props*/ - if( dev->dnr_params.spatial > 15 ) - dev->dnr_params.spatial = 15; - if( dev->dnr_params.temporal > 31 ) - dev->dnr_params.temporal = 31; - blackbird_api_cmd(dev, CX2341X_ENC_SET_DNR_FILTER_PROPS, 2, 0, - dev->dnr_params.spatial, - dev->dnr_params.temporal - ); -} -#define CHECK_DNR_PARAM( name ) ( dev->dnr_params.name != dnr_params->name ) -#define UPDATE_DNR_PARAM( name ) dev->dnr_params.name = dnr_params->name -void blackbird_set_dnr_params(struct cx8802_dev *dev, struct blackbird_dnr* dnr_params) -{ - /* assign dnr filter mode */ - /* clamp values */ - if( dnr_params->mode > BLACKBIRD_DNR_BITS_AUTO ) - dnr_params->mode = BLACKBIRD_DNR_BITS_MANUAL; - if( dnr_params->type > BLACKBIRD_MEDIAN_FILTER_DIAGONAL ) - dnr_params->type = BLACKBIRD_MEDIAN_FILTER_DISABLED; - /* check if the params actually changed */ - if( CHECK_DNR_PARAM( mode ) || CHECK_DNR_PARAM( type ) ) - { - UPDATE_DNR_PARAM( mode ); - UPDATE_DNR_PARAM( type ); - blackbird_api_cmd(dev, CX2341X_ENC_SET_DNR_FILTER_MODE, 2, 0, dnr_params->mode, dnr_params->type); - } - - /* assign dnr filter props*/ - if( dnr_params->spatial > 15 ) - dnr_params->spatial = 15; - if( dnr_params->temporal > 31 ) - dnr_params->temporal = 31; - if( CHECK_DNR_PARAM( spatial ) || CHECK_DNR_PARAM( temporal ) ) - { - UPDATE_DNR_PARAM( spatial ); - UPDATE_DNR_PARAM( temporal ); - blackbird_api_cmd(dev, CX2341X_ENC_SET_DNR_FILTER_PROPS, 2, 0, dnr_params->spatial, dnr_params->temporal); - } -} - -static void blackbird_codec_settings(struct cx8802_dev *dev) -{ - - /* assign output port */ - blackbird_api_cmd(dev, CX2341X_ENC_SET_OUTPUT_PORT, 1, 0, BLACKBIRD_OUTPUT_PORT_STREAMING); /* Host */ - - /* assign frame size */ - blackbird_api_cmd(dev, CX2341X_ENC_SET_FRAME_SIZE, 2, 0, - dev->height, dev->width); - - /* assign coring levels (luma_h, luma_l, chroma_h, chroma_l) */ - blackbird_api_cmd(dev, CX2341X_ENC_SET_CORING_LEVELS, 4, 0, 0, 255, 0, 255); - - /* assign spatial filter type: luma_t: horiz_only, chroma_t: horiz_only */ - blackbird_api_cmd(dev, CX2341X_ENC_SET_SPATIAL_FILTER_TYPE, 2, 0, - BLACKBIRD_SPATIAL_FILTER_LUMA_1D_HORIZ, - BLACKBIRD_SPATIAL_FILTER_CHROMA_1D_HORIZ - ); - - /* assign frame drop rate */ - /* blackbird_api_cmd(dev, IVTV_API_ASSIGN_FRAME_DROP_RATE, 1, 0, 0); */ - - blackbird_set_default_params(dev); - blackbird_set_default_dnr_params(dev); -} - static int blackbird_initialize_codec(struct cx8802_dev *dev) { struct cx88_core *core = dev->core; @@ -1478,15 +838,35 @@ static int mpeg_do_ioctl(struct inode *inode, struct file *file, { struct v4l2_mpeg_compression *f = arg; - memcpy(f,&dev->params,sizeof(*f)); + memcpy(f,&default_mpeg_params,sizeof(*f)); return 0; } case VIDIOC_S_MPEGCOMP: + return 0; + case VIDIOC_G_EXT_CTRLS: { - struct v4l2_mpeg_compression *f = arg; + struct v4l2_ext_controls *f = arg; - blackbird_set_params(dev, f); - return 0; + if (f->ctrl_class != V4L2_CTRL_CLASS_MPEG) + return -EINVAL; + return cx2341x_ext_ctrls(&dev->params, f, cmd); + } + case VIDIOC_S_EXT_CTRLS: + case VIDIOC_TRY_EXT_CTRLS: + { + struct v4l2_ext_controls *f = arg; + struct cx2341x_mpeg_params p; + int err; + + if (f->ctrl_class != V4L2_CTRL_CLASS_MPEG) + return -EINVAL; + p = dev->params; + err = cx2341x_ext_ctrls(&p, f, cmd); + if (err == 0 && cmd == VIDIOC_S_EXT_CTRLS) { + err = cx2341x_update(dev, blackbird_mbox_func, &dev->params, &p); + dev->params = p; + } + return err; } case VIDIOC_S_FREQUENCY: { @@ -1691,26 +1071,21 @@ static int __devinit blackbird_probe(struct pci_dev *pci_dev, dev->core = core; dev->width = 720; dev->height = 576; - memcpy(&dev->params,&default_mpeg_params,sizeof(default_mpeg_params)); - memcpy(&dev->dnr_params,&default_dnr_params,sizeof(default_dnr_params)); + cx2341x_fill_defaults(&dev->params); switch (core->board) { case CX88_BOARD_HAUPPAUGE_ROSLYN: if (core->tuner_formats & V4L2_STD_525_60) { dev->height = 480; - dev->params.vi_frame_rate = 30; } else { dev->height = 576; - dev->params.vi_frame_rate = 25; } break; case CX88_BOARD_KWORLD_HARDWARE_MPEG_TV_XPERT: if (core->tvnorm->id & V4L2_STD_525_60) { dev->height = 480; - dev->params.vi_frame_rate = 30; } else { dev->height = 576; - dev->params.vi_frame_rate = 25; } break; } @@ -1818,8 +1193,6 @@ module_exit(blackbird_fini); EXPORT_SYMBOL(cx88_ioctl_hook); EXPORT_SYMBOL(cx88_ioctl_translator); -EXPORT_SYMBOL(blackbird_set_params); -EXPORT_SYMBOL(blackbird_set_dnr_params); /* ----------------------------------------------------------- */ /* diff --git a/linux/drivers/media/video/cx88/cx88.h b/linux/drivers/media/video/cx88/cx88.h index efeef4b47..c8049ec2b 100644 --- a/linux/drivers/media/video/cx88/cx88.h +++ b/linux/drivers/media/video/cx88/cx88.h @@ -29,6 +29,7 @@ #include #include #include +#include #ifdef HAVE_VIDEO_BUF_DVB #include #endif @@ -432,14 +433,6 @@ struct cx8802_suspend_state { int disabled; }; -/* TODO: move this to struct v4l2_mpeg_compression ? */ -struct blackbird_dnr { - u32 mode; - u32 type; - u32 spatial; - u32 temporal; -}; - struct cx8802_dev { struct cx88_core *core; #if 0 @@ -479,8 +472,7 @@ struct cx8802_dev { unsigned char ts_gen_cntrl; /* mpeg params */ - struct v4l2_mpeg_compression params; - struct blackbird_dnr dnr_params; + struct cx2341x_mpeg_params params; }; /* ----------------------------------------------------------- */ @@ -645,10 +637,6 @@ extern int cx88_do_ioctl(struct inode *inode, struct file *file, int radio, extern int (*cx88_ioctl_hook)(struct inode *inode, struct file *file, unsigned int cmd, void *arg); extern unsigned int (*cx88_ioctl_translator)(unsigned int cmd); -void blackbird_set_params(struct cx8802_dev *dev, - struct v4l2_mpeg_compression *params); -void blackbird_set_dnr_params(struct cx8802_dev *dev, - struct blackbird_dnr* dnr_params); /* * Local variables: -- cgit v1.2.3 From 523686db1e20dffeb8509a4092cb3d8f425ef930 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Sun, 18 Jun 2006 21:40:10 +0200 Subject: Port new MPEG API to saa7134-empress with saa6752hs From: Hans Verkuil Signed-off-by: Hans Verkuil --- linux/drivers/media/video/saa7134/saa6752hs.c | 295 ++++++++++++++++++--- .../drivers/media/video/saa7134/saa7134-empress.c | 20 +- 2 files changed, 271 insertions(+), 44 deletions(-) diff --git a/linux/drivers/media/video/saa7134/saa6752hs.c b/linux/drivers/media/video/saa7134/saa6752hs.c index eac8bfba9..1ea68207a 100644 --- a/linux/drivers/media/video/saa7134/saa6752hs.c +++ b/linux/drivers/media/video/saa7134/saa6752hs.c @@ -46,6 +46,23 @@ enum saa6752hs_videoformat { SAA6752HS_VF_UNKNOWN, }; +struct saa6752hs_mpeg_params { + /* transport streams */ + __u16 ts_pid_pmt; + __u16 ts_pid_audio; + __u16 ts_pid_video; + __u16 ts_pid_pcr; + + /* audio */ + enum v4l2_mpeg_audio_l2_bitrate au_l2_bitrate; + + /* video */ + enum v4l2_mpeg_video_aspect vi_aspect; + enum v4l2_mpeg_video_bitrate_mode vi_bitrate_mode; + __u32 vi_bitrate; + __u32 vi_bitrate_peak; +}; + static const struct v4l2_format v4l2_format_table[] = { [SAA6752HS_VF_D1] = @@ -62,7 +79,8 @@ static const struct v4l2_format v4l2_format_table[] = struct saa6752hs_state { struct i2c_client client; - struct v4l2_mpeg_compression params; + struct v4l2_mpeg_compression old_params; + struct saa6752hs_mpeg_params params; enum saa6752hs_videoformat video_format; v4l2_std_id standard; }; @@ -136,7 +154,22 @@ static u8 PMT[] = { 0x00, 0x00, 0x00, 0x00 /* CRC32 */ }; -static struct v4l2_mpeg_compression param_defaults = +static struct saa6752hs_mpeg_params param_defaults = +{ + .ts_pid_pmt = 16, + .ts_pid_video = 260, + .ts_pid_audio = 256, + .ts_pid_pcr = 259, + + .vi_aspect = V4L2_MPEG_VIDEO_ASPECT_4x3, + .vi_bitrate = 4000, + .vi_bitrate_peak = 6000, + .vi_bitrate_mode = V4L2_MPEG_VIDEO_BITRATE_MODE_VBR, + + .au_l2_bitrate = V4L2_MPEG_AUDIO_L2_BITRATE_256K, +}; + +static struct v4l2_mpeg_compression old_param_defaults = { .st_type = V4L2_MPEG_TS_2, .st_bitrate = { @@ -239,45 +272,57 @@ static int saa6752hs_chip_command(struct i2c_client* client, static int saa6752hs_set_bitrate(struct i2c_client* client, - struct v4l2_mpeg_compression* params) + struct saa6752hs_mpeg_params* params) { u8 buf[3]; + int tot_bitrate; /* set the bitrate mode */ buf[0] = 0x71; - buf[1] = (params->vi_bitrate.mode == V4L2_BITRATE_VBR) ? 0 : 1; + buf[1] = (params->vi_bitrate_mode == V4L2_MPEG_VIDEO_BITRATE_MODE_VBR) ? 0 : 1; i2c_master_send(client, buf, 2); /* set the video bitrate */ - if (params->vi_bitrate.mode == V4L2_BITRATE_VBR) { + if (params->vi_bitrate_mode == V4L2_MPEG_VIDEO_BITRATE_MODE_VBR) { /* set the target bitrate */ buf[0] = 0x80; - buf[1] = params->vi_bitrate.target >> 8; - buf[2] = params->vi_bitrate.target & 0xff; + buf[1] = params->vi_bitrate >> 8; + buf[2] = params->vi_bitrate & 0xff; i2c_master_send(client, buf, 3); /* set the max bitrate */ buf[0] = 0x81; - buf[1] = params->vi_bitrate.max >> 8; - buf[2] = params->vi_bitrate.max & 0xff; + buf[1] = params->vi_bitrate_peak >> 8; + buf[2] = params->vi_bitrate_peak & 0xff; i2c_master_send(client, buf, 3); + tot_bitrate = params->vi_bitrate_peak; } else { /* set the target bitrate (no max bitrate for CBR) */ buf[0] = 0x81; - buf[1] = params->vi_bitrate.target >> 8; - buf[2] = params->vi_bitrate.target & 0xff; + buf[1] = params->vi_bitrate >> 8; + buf[2] = params->vi_bitrate & 0xff; i2c_master_send(client, buf, 3); + tot_bitrate = params->vi_bitrate; } /* set the audio bitrate */ buf[0] = 0x94; - buf[1] = (256 == params->au_bitrate.target) ? 0 : 1; + buf[1] = (V4L2_MPEG_AUDIO_L2_BITRATE_256K == params->au_l2_bitrate) ? 0 : 1; i2c_master_send(client, buf, 2); + tot_bitrate += (V4L2_MPEG_AUDIO_L2_BITRATE_256K == params->au_l2_bitrate) ? 256 : 384; + + /* 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 + safe side. If more control should be required, then an extra MPEG control + should be added. */ + tot_bitrate += 768; + if (tot_bitrate > MPEG_TOTAL_TARGET_BITRATE_MAX) + tot_bitrate = MPEG_TOTAL_TARGET_BITRATE_MAX; /* set the total bitrate */ buf[0] = 0xb1; - buf[1] = params->st_bitrate.target >> 8; - buf[2] = params->st_bitrate.target & 0xff; + buf[1] = tot_bitrate >> 8; + buf[2] = tot_bitrate & 0xff; i2c_master_send(client, buf, 3); return 0; @@ -329,50 +374,188 @@ static void saa6752hs_set_subsampling(struct i2c_client* client, } -static void saa6752hs_set_params(struct i2c_client* client, +static void saa6752hs_old_set_params(struct i2c_client* client, struct v4l2_mpeg_compression* params) { struct saa6752hs_state *h = i2c_get_clientdata(client); /* check PIDs */ - if (params->ts_pid_pmt <= MPEG_PID_MAX) + if (params->ts_pid_pmt <= MPEG_PID_MAX) { + h->old_params.ts_pid_pmt = params->ts_pid_pmt; h->params.ts_pid_pmt = params->ts_pid_pmt; - if (params->ts_pid_pcr <= MPEG_PID_MAX) + } + if (params->ts_pid_pcr <= MPEG_PID_MAX) { + h->old_params.ts_pid_pcr = params->ts_pid_pcr; h->params.ts_pid_pcr = params->ts_pid_pcr; - if (params->ts_pid_video <= MPEG_PID_MAX) + } + if (params->ts_pid_video <= MPEG_PID_MAX) { + h->old_params.ts_pid_video = params->ts_pid_video; h->params.ts_pid_video = params->ts_pid_video; - if (params->ts_pid_audio <= MPEG_PID_MAX) + } + if (params->ts_pid_audio <= MPEG_PID_MAX) { + h->old_params.ts_pid_audio = params->ts_pid_audio; h->params.ts_pid_audio = params->ts_pid_audio; + } /* check bitrate parameters */ if ((params->vi_bitrate.mode == V4L2_BITRATE_CBR) || - (params->vi_bitrate.mode == V4L2_BITRATE_VBR)) - h->params.vi_bitrate.mode = params->vi_bitrate.mode; + (params->vi_bitrate.mode == V4L2_BITRATE_VBR)) { + h->old_params.vi_bitrate.mode = params->vi_bitrate.mode; + h->params.vi_bitrate_mode = (params->vi_bitrate.mode == V4L2_BITRATE_VBR) ? + V4L2_MPEG_VIDEO_BITRATE_MODE_VBR : V4L2_MPEG_VIDEO_BITRATE_MODE_CBR; + } if (params->vi_bitrate.mode != V4L2_BITRATE_NONE) - h->params.st_bitrate.target = params->st_bitrate.target; + h->old_params.st_bitrate.target = params->st_bitrate.target; if (params->vi_bitrate.mode != V4L2_BITRATE_NONE) - h->params.vi_bitrate.target = params->vi_bitrate.target; + h->old_params.vi_bitrate.target = params->vi_bitrate.target; if (params->vi_bitrate.mode == V4L2_BITRATE_VBR) - h->params.vi_bitrate.max = params->vi_bitrate.max; + h->old_params.vi_bitrate.max = params->vi_bitrate.max; if (params->au_bitrate.mode != V4L2_BITRATE_NONE) - h->params.au_bitrate.target = params->au_bitrate.target; + h->old_params.au_bitrate.target = params->au_bitrate.target; /* aspect ratio */ if (params->vi_aspect_ratio == V4L2_MPEG_ASPECT_4_3 || - params->vi_aspect_ratio == V4L2_MPEG_ASPECT_16_9) - h->params.vi_aspect_ratio = params->vi_aspect_ratio; + params->vi_aspect_ratio == V4L2_MPEG_ASPECT_16_9) { + h->old_params.vi_aspect_ratio = params->vi_aspect_ratio; + if (params->vi_aspect_ratio == V4L2_MPEG_ASPECT_4_3) + h->params.vi_aspect = V4L2_MPEG_VIDEO_ASPECT_4x3; + else + h->params.vi_aspect = V4L2_MPEG_VIDEO_ASPECT_16x9; + } /* range checks */ - if (h->params.st_bitrate.target > MPEG_TOTAL_TARGET_BITRATE_MAX) - h->params.st_bitrate.target = MPEG_TOTAL_TARGET_BITRATE_MAX; - if (h->params.vi_bitrate.target > MPEG_VIDEO_TARGET_BITRATE_MAX) - h->params.vi_bitrate.target = MPEG_VIDEO_TARGET_BITRATE_MAX; - if (h->params.vi_bitrate.max > MPEG_VIDEO_MAX_BITRATE_MAX) - h->params.vi_bitrate.max = MPEG_VIDEO_MAX_BITRATE_MAX; - if (h->params.au_bitrate.target <= 256) - h->params.au_bitrate.target = 256; + if (h->old_params.st_bitrate.target > MPEG_TOTAL_TARGET_BITRATE_MAX) + h->old_params.st_bitrate.target = MPEG_TOTAL_TARGET_BITRATE_MAX; + if (h->old_params.vi_bitrate.target > MPEG_VIDEO_TARGET_BITRATE_MAX) + h->old_params.vi_bitrate.target = MPEG_VIDEO_TARGET_BITRATE_MAX; + if (h->old_params.vi_bitrate.max > MPEG_VIDEO_MAX_BITRATE_MAX) + h->old_params.vi_bitrate.max = MPEG_VIDEO_MAX_BITRATE_MAX; + h->params.vi_bitrate = params->vi_bitrate.target; + h->params.vi_bitrate_peak = params->vi_bitrate.max; + if (h->old_params.au_bitrate.target <= 256) { + h->old_params.au_bitrate.target = 256; + h->params.au_l2_bitrate = V4L2_MPEG_AUDIO_L2_BITRATE_256K; + } + else { + h->old_params.au_bitrate.target = 384; + h->params.au_l2_bitrate = V4L2_MPEG_AUDIO_L2_BITRATE_384K; + } +} + +static int handle_ctrl(struct saa6752hs_mpeg_params *params, + struct v4l2_ext_control *ctrl, int cmd) +{ + int old = 0, new; + int set = cmd == VIDIOC_S_EXT_CTRLS; + + new = ctrl->value; + switch (ctrl->id) { + case V4L2_CID_MPEG_STREAM_TYPE: + old = V4L2_MPEG_STREAM_TYPE_MPEG2_TS; + if (set && new != old) + return -ERANGE; + new = old; + break; + case V4L2_CID_MPEG_STREAM_PID_PMT: + old = params->ts_pid_pmt; + if (set && new > MPEG_PID_MAX) + return -ERANGE; + if (new > MPEG_PID_MAX) + new = MPEG_PID_MAX; + params->ts_pid_pmt = new; + break; + case V4L2_CID_MPEG_STREAM_PID_AUDIO: + old = params->ts_pid_audio; + if (set && new > MPEG_PID_MAX) + return -ERANGE; + if (new > MPEG_PID_MAX) + new = MPEG_PID_MAX; + params->ts_pid_audio = new; + break; + case V4L2_CID_MPEG_STREAM_PID_VIDEO: + old = params->ts_pid_video; + if (set && new > MPEG_PID_MAX) + return -ERANGE; + if (new > MPEG_PID_MAX) + new = MPEG_PID_MAX; + params->ts_pid_video = new; + break; + case V4L2_CID_MPEG_STREAM_PID_PCR: + old = params->ts_pid_pcr; + if (set && new > MPEG_PID_MAX) + return -ERANGE; + if (new > MPEG_PID_MAX) + new = MPEG_PID_MAX; + params->ts_pid_pcr = new; + break; + case V4L2_CID_MPEG_AUDIO_ENCODING: + old = V4L2_MPEG_AUDIO_ENCODING_LAYER_2; + if (set && new != old) + return -ERANGE; + new = old; + break; + case V4L2_CID_MPEG_AUDIO_L2_BITRATE: + old = params->au_l2_bitrate; + if (set && new != V4L2_MPEG_AUDIO_L2_BITRATE_256K && + new != V4L2_MPEG_AUDIO_L2_BITRATE_384K) + return -ERANGE; + if (new <= V4L2_MPEG_AUDIO_L2_BITRATE_256K) + new = V4L2_MPEG_AUDIO_L2_BITRATE_256K; + else + new = V4L2_MPEG_AUDIO_L2_BITRATE_384K; + params->au_l2_bitrate = new; + break; + case V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ: + old = V4L2_MPEG_AUDIO_SAMPLING_FREQ_48000; + if (set && new != old) + return -ERANGE; + new = old; + break; + case V4L2_CID_MPEG_VIDEO_ENCODING: + old = V4L2_MPEG_VIDEO_ENCODING_MPEG_2; + if (set && new != old) + return -ERANGE; + new = old; + break; + case V4L2_CID_MPEG_VIDEO_ASPECT: + old = params->vi_aspect; + if (set && new != V4L2_MPEG_VIDEO_ASPECT_16x9 && + new != V4L2_MPEG_VIDEO_ASPECT_4x3) + return -ERANGE; + if (new != V4L2_MPEG_VIDEO_ASPECT_16x9) + new = V4L2_MPEG_VIDEO_ASPECT_4x3; + params->vi_aspect = new; + break; + case V4L2_CID_MPEG_VIDEO_BITRATE: + old = params->vi_bitrate * 1000; + new = 1000 * (new / 1000); + if (set && new > MPEG_VIDEO_TARGET_BITRATE_MAX * 1000) + return -ERANGE; + if (new > MPEG_VIDEO_TARGET_BITRATE_MAX * 1000) + new = MPEG_VIDEO_TARGET_BITRATE_MAX * 1000; + params->vi_bitrate = new / 1000; + break; + case V4L2_CID_MPEG_VIDEO_BITRATE_PEAK: + old = params->vi_bitrate_peak * 1000; + new = 1000 * (new / 1000); + if (set && new > MPEG_VIDEO_TARGET_BITRATE_MAX * 1000) + return -ERANGE; + if (new > MPEG_VIDEO_TARGET_BITRATE_MAX * 1000) + new = MPEG_VIDEO_TARGET_BITRATE_MAX * 1000; + params->vi_bitrate_peak = new / 1000; + break; + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE: + old = params->vi_bitrate_mode; + params->vi_bitrate_mode = new; + break; + default: + return -EINVAL; + } + if (cmd == VIDIOC_G_EXT_CTRLS) + ctrl->value = old; else - h->params.au_bitrate.target = 384; + ctrl->value = new; + return 0; } static int saa6752hs_init(struct i2c_client* client) @@ -500,11 +683,11 @@ static int saa6752hs_init(struct i2c_client* client) buf[3] = 0x82; buf[4] = 0xB0; buf[5] = buf2[0]; - switch(h->params.vi_aspect_ratio) { - case V4L2_MPEG_ASPECT_16_9: + switch(h->params.vi_aspect) { + case V4L2_MPEG_VIDEO_ASPECT_16x9: buf[6] = buf2[1] | 0x40; break; - case V4L2_MPEG_ASPECT_4_3: + case V4L2_MPEG_VIDEO_ASPECT_4x3: default: buf[6] = buf2[1] & 0xBF; break; @@ -530,6 +713,7 @@ static int saa6752hs_attach(struct i2c_adapter *adap, int addr, unsigned short f return -ENOMEM; h->client = client_template; h->params = param_defaults; + h->old_params = old_param_defaults; h->client.adapter = adap; h->client.addr = addr; @@ -572,20 +756,45 @@ static int saa6752hs_command(struct i2c_client *client, unsigned int cmd, void *arg) { struct saa6752hs_state *h = i2c_get_clientdata(client); - struct v4l2_mpeg_compression *params = arg; + struct v4l2_ext_controls *ctrls = arg; + struct v4l2_mpeg_compression *old_params = arg; + struct saa6752hs_mpeg_params params; int err = 0; + int i; switch (cmd) { case VIDIOC_S_MPEGCOMP: - if (NULL == params) { + if (NULL == old_params) { /* apply settings and start encoder */ saa6752hs_init(client); break; } - saa6752hs_set_params(client, params); + saa6752hs_old_set_params(client, old_params); /* fall through */ case VIDIOC_G_MPEGCOMP: - *params = h->params; + *old_params = h->old_params; + break; + case VIDIOC_S_EXT_CTRLS: + if (ctrls->ctrl_class != V4L2_CTRL_CLASS_MPEG) + return -EINVAL; + if (ctrls->count == 0) { + /* apply settings and start encoder */ + saa6752hs_init(client); + break; + } + /* fall through */ + case VIDIOC_TRY_EXT_CTRLS: + case VIDIOC_G_EXT_CTRLS: + if (ctrls->ctrl_class != V4L2_CTRL_CLASS_MPEG) + return -EINVAL; + params = h->params; + for (i = 0; i < ctrls->count; i++) { + if ((err = handle_ctrl(¶ms, ctrls->controls + i, cmd))) { + ctrls->error_idx = i; + return err; + } + } + h->params = params; break; case VIDIOC_G_FMT: { diff --git a/linux/drivers/media/video/saa7134/saa7134-empress.c b/linux/drivers/media/video/saa7134/saa7134-empress.c index 5c311210e..46c5fdaf7 100644 --- a/linux/drivers/media/video/saa7134/saa7134-empress.c +++ b/linux/drivers/media/video/saa7134/saa7134-empress.c @@ -74,8 +74,10 @@ static void ts_reset_encoder(struct saa7134_dev* dev) static int ts_init_encoder(struct saa7134_dev* dev) { + struct v4l2_ext_controls ctrls = { V4L2_CTRL_CLASS_MPEG, 0 }; + ts_reset_encoder(dev); - saa7134_i2c_call_clients(dev, VIDIOC_S_MPEGCOMP, NULL); + saa7134_i2c_call_clients(dev, VIDIOC_S_EXT_CTRLS, &ctrls); dev->empress_started = 1; return 0; } @@ -172,6 +174,7 @@ static int ts_do_ioctl(struct inode *inode, struct file *file, unsigned int cmd, void *arg) { struct saa7134_dev *dev = file->private_data; + struct v4l2_ext_controls *ctrls = arg; if (debug > 1) v4l_print_ioctl(dev->name,cmd); @@ -294,6 +297,21 @@ static int ts_do_ioctl(struct inode *inode, struct file *file, case VIDIOC_G_MPEGCOMP: saa7134_i2c_call_clients(dev, VIDIOC_G_MPEGCOMP, arg); return 0; + case VIDIOC_S_EXT_CTRLS: + /* count == 0 is abused in saa6752hs.c, so that special + case is handled here explicitly. */ + if (ctrls->count == 0) + return 0; + if (ctrls->ctrl_class != V4L2_CTRL_CLASS_MPEG) + return -EINVAL; + saa7134_i2c_call_clients(dev, VIDIOC_S_EXT_CTRLS, arg); + ts_init_encoder(dev); + return 0; + case VIDIOC_G_EXT_CTRLS: + if (ctrls->ctrl_class != V4L2_CTRL_CLASS_MPEG) + return -EINVAL; + saa7134_i2c_call_clients(dev, VIDIOC_G_EXT_CTRLS, arg); + return 0; default: return -ENOIOCTLCMD; -- cgit v1.2.3 From 6cdc5db5eecbf7385e190aab3718ccfbdc981077 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Sun, 18 Jun 2006 21:54:20 +0200 Subject: Put old MPEGCOMP API under #if __KERNEL__ and issue warnings when used. From: Hans Verkuil Signed-off-by: Hans Verkuil --- linux/drivers/media/video/cx88/cx88-blackbird.c | 4 ++++ linux/drivers/media/video/saa7134/saa7134-empress.c | 4 ++++ linux/drivers/media/video/videodev.c | 1 + linux/include/linux/videodev2.h | 9 +++++---- 4 files changed, 14 insertions(+), 4 deletions(-) diff --git a/linux/drivers/media/video/cx88/cx88-blackbird.c b/linux/drivers/media/video/cx88/cx88-blackbird.c index cad6f4a92..1a86d337f 100644 --- a/linux/drivers/media/video/cx88/cx88-blackbird.c +++ b/linux/drivers/media/video/cx88/cx88-blackbird.c @@ -838,10 +838,14 @@ static int mpeg_do_ioctl(struct inode *inode, struct file *file, { struct v4l2_mpeg_compression *f = arg; + printk(KERN_WARNING "VIDIOC_G_MPEGCOMP is obsolete. " + "Replace with VIDIOC_G_EXT_CTRLS!"); memcpy(f,&default_mpeg_params,sizeof(*f)); return 0; } case VIDIOC_S_MPEGCOMP: + printk(KERN_WARNING "VIDIOC_S_MPEGCOMP is obsolete. " + "Replace with VIDIOC_S_EXT_CTRLS!"); return 0; case VIDIOC_G_EXT_CTRLS: { diff --git a/linux/drivers/media/video/saa7134/saa7134-empress.c b/linux/drivers/media/video/saa7134/saa7134-empress.c index 46c5fdaf7..690891588 100644 --- a/linux/drivers/media/video/saa7134/saa7134-empress.c +++ b/linux/drivers/media/video/saa7134/saa7134-empress.c @@ -291,10 +291,14 @@ static int ts_do_ioctl(struct inode *inode, struct file *file, return saa7134_common_ioctl(dev, cmd, arg); case VIDIOC_S_MPEGCOMP: + printk(KERN_WARNING "VIDIOC_S_MPEGCOMP is obsolete. " + "Replace with VIDIOC_S_EXT_CTRLS!"); saa7134_i2c_call_clients(dev, VIDIOC_S_MPEGCOMP, arg); ts_init_encoder(dev); return 0; case VIDIOC_G_MPEGCOMP: + printk(KERN_WARNING "VIDIOC_G_MPEGCOMP is obsolete. " + "Replace with VIDIOC_G_EXT_CTRLS!"); saa7134_i2c_call_clients(dev, VIDIOC_G_MPEGCOMP, arg); return 0; case VIDIOC_S_EXT_CTRLS: diff --git a/linux/drivers/media/video/videodev.c b/linux/drivers/media/video/videodev.c index 8eaf1b8ca..342ccf3ff 100644 --- a/linux/drivers/media/video/videodev.c +++ b/linux/drivers/media/video/videodev.c @@ -1235,6 +1235,7 @@ static int __video_do_ioctl(struct inode *inode, struct file *file, case VIDIOC_G_MPEGCOMP: { struct v4l2_mpeg_compression *p=arg; + /*FIXME: Several fields not shown */ if (!vfd->vidioc_g_mpegcomp) break; diff --git a/linux/include/linux/videodev2.h b/linux/include/linux/videodev2.h index d095481c0..3512e05f7 100644 --- a/linux/include/linux/videodev2.h +++ b/linux/include/linux/videodev2.h @@ -306,12 +306,13 @@ struct v4l2_timecode #define V4L2_TC_USERBITS_8BITCHARS 0x0008 /* The above is based on SMPTE timecodes */ -#if 1 +#ifdef __KERNEL__ /* * M P E G C O M P R E S S I O N P A R A M E T E R S * - * ### WARNING: this is still work-in-progress right now, most likely - * ### there will be some incompatible changes. + * ### WARNING: This experimental MPEG compression API is obsolete. + * ### It is replaced by the MPEG controls API. + * ### This old API will disappear in the near future! * */ enum v4l2_bitrate_mode { @@ -1253,7 +1254,7 @@ struct v4l2_streamparm #define VIDIOC_ENUM_FMT _IOWR ('V', 2, struct v4l2_fmtdesc) #define VIDIOC_G_FMT _IOWR ('V', 4, struct v4l2_format) #define VIDIOC_S_FMT _IOWR ('V', 5, struct v4l2_format) -#if 1 /* experimental */ +#ifdef __KERNEL__ #define VIDIOC_G_MPEGCOMP _IOR ('V', 6, struct v4l2_mpeg_compression) #define VIDIOC_S_MPEGCOMP _IOW ('V', 7, struct v4l2_mpeg_compression) #endif -- cgit v1.2.3 From 6fd7eb0bb3091e8cec9b432135ed92425a999a72 Mon Sep 17 00:00:00 2001 From: Michael Krufky Date: Mon, 19 Jun 2006 14:49:20 +0200 Subject: Backed out changeset e3215d345e206c37b4a72a6f41d0a8c6696de3fa --- linux/drivers/media/video/cx88/cx88-video.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/linux/drivers/media/video/cx88/cx88-video.c b/linux/drivers/media/video/cx88/cx88-video.c index 59a7e096d..9c2f0dd39 100644 --- a/linux/drivers/media/video/cx88/cx88-video.c +++ b/linux/drivers/media/video/cx88/cx88-video.c @@ -266,10 +266,10 @@ static struct cx88_ctrl cx8800_ctls[] = { .minimum = 0, .maximum = 0xff, .step = 1, - .default_value = 0x7f, + .default_value = 0x3f, .type = V4L2_CTRL_TYPE_INTEGER, }, - .off = 64, + .off = 0, .reg = MO_CONTR_BRIGHT, .mask = 0xff00, .shift = 8, -- cgit v1.2.3 From 16659a1919874e2a99f44778de6594b8a6b3f65f Mon Sep 17 00:00:00 2001 From: Michael Krufky Date: Mon, 19 Jun 2006 14:54:00 +0200 Subject: cx88-tvaudio.c must #include From: Michael Krufky Signed-off-by: Michael Krufky --- linux/drivers/media/video/cx88/cx88-tvaudio.c | 1 + 1 file changed, 1 insertion(+) diff --git a/linux/drivers/media/video/cx88/cx88-tvaudio.c b/linux/drivers/media/video/cx88/cx88-tvaudio.c index 7920e2d22..e0eb173db 100644 --- a/linux/drivers/media/video/cx88/cx88-tvaudio.c +++ b/linux/drivers/media/video/cx88/cx88-tvaudio.c @@ -52,6 +52,7 @@ #include #include #include +#include #include "compat.h" #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0) #include -- cgit v1.2.3 From af650bccdb8afcbd266fd7521df4b15bab26124e Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Mon, 19 Jun 2006 22:53:08 +0200 Subject: Add cx2341x-specific control array to cx2341x.c From: Hans Verkuil Signed-off-by: Hans Verkuil --- linux/drivers/media/video/cx2341x.c | 35 +++++++++++++++++++++++++++++++++++ linux/include/media/cx2341x.h | 1 + 2 files changed, 36 insertions(+) diff --git a/linux/drivers/media/video/cx2341x.c b/linux/drivers/media/video/cx2341x.c index 3df06694d..1381fdc63 100644 --- a/linux/drivers/media/video/cx2341x.c +++ b/linux/drivers/media/video/cx2341x.c @@ -44,6 +44,40 @@ static int debug = 0; module_param(debug, int, 0644); MODULE_PARM_DESC(debug, "Debug level (0-1)"); +const u32 cx2341x_mpeg_ctrls[] = { + V4L2_CID_MPEG_CLASS, + V4L2_CID_MPEG_STREAM_TYPE, + V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ, + V4L2_CID_MPEG_AUDIO_ENCODING, + V4L2_CID_MPEG_AUDIO_L2_BITRATE, + V4L2_CID_MPEG_AUDIO_MODE, + V4L2_CID_MPEG_AUDIO_MODE_EXTENSION, + V4L2_CID_MPEG_AUDIO_EMPHASIS, + V4L2_CID_MPEG_AUDIO_CRC, + V4L2_CID_MPEG_VIDEO_ENCODING, + V4L2_CID_MPEG_VIDEO_ASPECT, + V4L2_CID_MPEG_VIDEO_B_FRAMES, + V4L2_CID_MPEG_VIDEO_GOP_SIZE, + V4L2_CID_MPEG_VIDEO_GOP_CLOSURE, + V4L2_CID_MPEG_VIDEO_PULLDOWN, + V4L2_CID_MPEG_VIDEO_BITRATE_MODE, + V4L2_CID_MPEG_VIDEO_BITRATE, + V4L2_CID_MPEG_VIDEO_BITRATE_PEAK, + V4L2_CID_MPEG_VIDEO_TEMPORAL_DECIMATION, + V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE, + V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER, + V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE, + V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE, + V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE, + V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER, + V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE, + V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_BOTTOM, + V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_TOP, + V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_BOTTOM, + V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_MEDIAN_FILTER_TOP, + 0 +}; + /* Map the control ID to the correct field in the cx2341x_mpeg_params struct. Return -EINVAL if the ID is unknown, else return 0. */ @@ -868,6 +902,7 @@ EXPORT_SYMBOL(cx2341x_ctrl_get_menu); EXPORT_SYMBOL(cx2341x_ext_ctrls); EXPORT_SYMBOL(cx2341x_update); EXPORT_SYMBOL(cx2341x_log_status); +EXPORT_SYMBOL(cx2341x_mpeg_ctrls); /* * Local variables: diff --git a/linux/include/media/cx2341x.h b/linux/include/media/cx2341x.h index 81ebead2d..0c9292fa5 100644 --- a/linux/include/media/cx2341x.h +++ b/linux/include/media/cx2341x.h @@ -66,6 +66,7 @@ struct cx2341x_mpeg_params { #define CX2341X_MBOX_MAX_DATA 16 +extern const u32 cx2341x_mpeg_ctrls[]; typedef int (*cx2341x_mbox_func)(void *priv, int cmd, int in, int out, u32 data[CX2341X_MBOX_MAX_DATA]); int cx2341x_update(void *priv, cx2341x_mbox_func func, -- cgit v1.2.3 From 0f9c47f021dff0b36a1d13014e814fd5de03dc84 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Mon, 19 Jun 2006 23:00:06 +0200 Subject: Disable bitrate_mode when encoding mpeg-1. From: Hans Verkuil MPEG-1 always uses CBR, so make the BITRATE_MODE control inactive. Signed-off-by: Hans Verkuil --- linux/drivers/media/video/cx2341x.c | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/linux/drivers/media/video/cx2341x.c b/linux/drivers/media/video/cx2341x.c index 1381fdc63..33e955f7c 100644 --- a/linux/drivers/media/video/cx2341x.c +++ b/linux/drivers/media/video/cx2341x.c @@ -410,6 +410,12 @@ int cx2341x_ctrl_query(struct cx2341x_mpeg_params *params, struct v4l2_queryctrl qctrl->flags |= V4L2_CTRL_FLAG_READ_ONLY; return err; + case V4L2_CID_MPEG_VIDEO_BITRATE_MODE: + err = v4l2_ctrl_query_fill_std(qctrl); + if (err == 0 && params->video_encoding == V4L2_MPEG_VIDEO_ENCODING_MPEG_1) + qctrl->flags |= V4L2_CTRL_FLAG_INACTIVE; + return err; + case V4L2_CID_MPEG_VIDEO_BITRATE_PEAK: err = v4l2_ctrl_query_fill_std(qctrl); if (err == 0 && params->video_bitrate_mode == V4L2_MPEG_VIDEO_BITRATE_MODE_CBR) -- cgit v1.2.3 From 92867da514a9a5ade64ab29b9342c633d74e0987 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Mon, 19 Jun 2006 19:49:20 -0300 Subject: saa7134 card (LifeView3000 NTSC) From: Zac Bowling Add detection for the LifeView3000 NTSC model (right now the PAL version is the only one in there, which is sort of annoying for me living in the US and all.. sigh...) This is one of those things that I like to classify "as a works for me so take it or leave it" :-) . Not that worried because its an $18 video capture card that didn't look it was selling to well in the US, but then again who knows. The documentation needs updating too I bet but its behind anyways usually to what is in the code. Signed-off-by: Mauro Carvalho Chehab Signed-off-by: Zac Bowling Signed-off-by: Andrew Morton --- linux/drivers/media/video/saa7134/saa7134-cards.c | 56 +++++++++++++++++++++++ linux/drivers/media/video/saa7134/saa7134.h | 1 + 2 files changed, 57 insertions(+) diff --git a/linux/drivers/media/video/saa7134/saa7134-cards.c b/linux/drivers/media/video/saa7134/saa7134-cards.c index 04812f5f8..b00224184 100644 --- a/linux/drivers/media/video/saa7134/saa7134-cards.c +++ b/linux/drivers/media/video/saa7134/saa7134-cards.c @@ -2882,6 +2882,55 @@ struct saa7134_board saa7134_boards[] = { .gpio = 0x000000, /* GPIO21=Low for FM radio antenna */ }, }, + [SAA7134_BOARD_FLYVIDEO3000_NTSC] = { + /* "Zac Bowling" */ + .name = "LifeView FlyVIDEO3000 (NTSC)", + .audio_clock = 0x00200000, + .tuner_type = TUNER_PHILIPS_NTSC, + .radio_type = UNSET, + .tuner_addr = ADDR_UNSET, + .radio_addr = ADDR_UNSET, + + .gpiomask = 0xe000, + .inputs = {{ + .name = name_tv, + .vmux = 1, + .amux = TV, + .gpio = 0x8000, + .tv = 1, + },{ + .name = name_tv_mono, + .vmux = 1, + .amux = LINE2, + .gpio = 0x0000, + .tv = 1, + },{ + .name = name_comp1, + .vmux = 0, + .amux = LINE2, + .gpio = 0x4000, + },{ + .name = name_comp2, + .vmux = 3, + .amux = LINE2, + .gpio = 0x4000, + },{ + .name = name_svideo, + .vmux = 8, + .amux = LINE2, + .gpio = 0x4000, + }}, + .radio = { + .name = name_radio, + .amux = LINE2, + .gpio = 0x2000, + }, + .mute = { + .name = name_mute, + .amux = TV, + .gpio = 0x8000, + }, + }, }; const unsigned int saa7134_bcount = ARRAY_SIZE(saa7134_boards); @@ -2938,6 +2987,12 @@ struct pci_device_id saa7134_pci_tbl[] = { .subvendor = 0x153b, .subdevice = 0x1162, .driver_data = SAA7134_BOARD_CINERGY400_CARDBUS, + },{ + .vendor = PCI_VENDOR_ID_PHILIPS, + .device = PCI_DEVICE_ID_PHILIPS_SAA7134, + .subvendor = 0x5169, + .subdevice = 0x0138, + .driver_data = SAA7134_BOARD_FLYVIDEO3000_NTSC, },{ .vendor = PCI_VENDOR_ID_PHILIPS, .device = PCI_DEVICE_ID_PHILIPS_SAA7134, @@ -3536,6 +3591,7 @@ int saa7134_board_init1(struct saa7134_dev *dev) switch (dev->board) { case SAA7134_BOARD_FLYVIDEO2000: case SAA7134_BOARD_FLYVIDEO3000: + case SAA7134_BOARD_FLYVIDEO3000_NTSC: dev->has_remote = SAA7134_REMOTE_GPIO; board_flyvideo(dev); break; diff --git a/linux/drivers/media/video/saa7134/saa7134.h b/linux/drivers/media/video/saa7134/saa7134.h index c30d512c7..672a980cb 100644 --- a/linux/drivers/media/video/saa7134/saa7134.h +++ b/linux/drivers/media/video/saa7134/saa7134.h @@ -231,6 +231,7 @@ struct saa7134_format { #define SAA7134_BOARD_AVERMEDIA_A169_B1 92 #define SAA7134_BOARD_MD7134_BRIDGE_2 93 #define SAA7134_BOARD_FLYDVBT_HYBRID_CARDBUS 94 +#define SAA7134_BOARD_FLYVIDEO3000_NTSC 95 #define SAA7134_MAXBOARDS 8 #define SAA7134_INPUT_MAX 8 -- cgit v1.2.3 From d02b60987a9d04d3f7a58c04c1000797b8563b92 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Mon, 19 Jun 2006 19:49:57 -0300 Subject: Improved to accept also patches from akpm. From: Mauro Carvalho Chehab Signed-off-by: Mauro Carvalho Chehab --- v4l/scripts/hghead.pl | 20 +++++++++++++++----- 1 file changed, 15 insertions(+), 5 deletions(-) diff --git a/v4l/scripts/hghead.pl b/v4l/scripts/hghead.pl index 16e566ea9..3f8b4b0ba 100755 --- a/v4l/scripts/hghead.pl +++ b/v4l/scripts/hghead.pl @@ -12,6 +12,7 @@ my $sub_ok=0; my $init=0; my $num=0; my $hgimport=0; +my $mmimport=0; my $maint_ok=0; my $noblank=1; my $maintainer_name=$ENV{CHANGE_LOG_NAME}; @@ -33,6 +34,10 @@ while ($line = ) { if ($line =~ m/^\-\-\- .*/) { last; } + if ($line =~ m/^\-\-\-\-.*/) { + $body=""; + next; + } if ($line =~ m/^\-\-\-.*/) { last; } @@ -62,7 +67,11 @@ while ($line = ) { $from= "From: $fromname\n"; next; } - print "Bad: author line have a wrong syntax\n"; + if ($line =~ m/^From:\sakpm\@osdl.org/) { + $mmimport=1; + next; + } + print "Bad: author line have a wrong syntax: $line\n"; die; } @@ -87,11 +96,11 @@ while ($line = ) { $signed="$signed$line"; next; } - if ($line =~ m/^\# HG changeset patch/) { + if ( ($line =~ m/^\# HG changeset patch/) || + ($line =~ m/^has been added to the -mm tree. Its filename is/) ) { $sub_ok=0; $init=0; $num=0; - $hgimport=0; $maint_ok=0; $noblank=1; $from=""; @@ -100,6 +109,7 @@ while ($line = ) { $hgimport=1; next; } + if ($line =~ m/^Acked-by:.*/) { $signed="$signed$line"; @@ -164,8 +174,8 @@ if (!$signed =~ m/$from/) { die; } -$body=~s/\n+$//; -$body=~s/^\n+$//; +$body=~s/[\n\s]+$//; +$body=~s/^[\n\s]+//; # First from is used by hg to recognize commiter name print "#Committer: $maintainer_name <$maintainer_email>\n"; -- cgit v1.2.3 From 5da0337a0500257e93259472d26bca4ca9a6be9a Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Tue, 20 Jun 2006 00:24:50 -0300 Subject: Faster strip whitespace cleaning script From: Trent Piepho Faster script that doesn't use any temporary files. The old one would also miss cleaning four spaces in a row in places where it would clean one to eight spaces. Has two options: fast Only clean whitespace in files Hg thinks are modified or added. Used by make whitespace and much (about 100x) faster. manifest Clean all files controlled by Hg, using "hg manifest" The default with no options is the old behaviour, clean all files under the linux directory, except CVS files. Signed-off-by: Trent Piepho Signed-off-by: Mauro Carvalho Chehab --- Makefile | 2 +- v4l/scripts/strip-trailing-whitespaces.sh | 56 +++++++++++++------------------ 2 files changed, 24 insertions(+), 34 deletions(-) diff --git a/Makefile b/Makefile index 1f11bcb3f..42c22f72a 100644 --- a/Makefile +++ b/Makefile @@ -43,5 +43,5 @@ push:: whitespace: @echo "Cleaning bad whitespaces" - @v4l/scripts/strip-trailing-whitespaces.sh | patch -p0 + @v4l/scripts/strip-trailing-whitespaces.sh fast | patch -p0 diff --git a/v4l/scripts/strip-trailing-whitespaces.sh b/v4l/scripts/strip-trailing-whitespaces.sh index 1a23e436d..5bd7784e4 100755 --- a/v4l/scripts/strip-trailing-whitespaces.sh +++ b/v4l/scripts/strip-trailing-whitespaces.sh @@ -1,37 +1,27 @@ #!/bin/sh +# Strips trailing whitespace. Leading spaces and spaces after tabs are +# converted to the equivalent sequence of tabs only. -# tmp dir for my files -WORK="${TMPDIR-/tmp}/${0##*/}-$$" -mkdir "$WORK" || exit 1 -trap 'rm -rf "$WORK"' EXIT +# Use the option "fast" to only check files Hg thinks are new or modified. +# The option "manifest" will use Hg's manifest command to check all files +# under Hg revision control. +# Otherwise, all files under the linux tree are checked, except files in CVS +# directories and .cvsignore files. This is the historical behavior. -for file in `find linux -type d | grep -v CVS | grep -v .cvsignore` ; do - mkdir -p "$WORK/${file}" -done -for file in `find linux -type f | grep -v CVS | grep -v .cvsignore` ; do - tmpfile="$WORK/${file}.$$" - perl -ne 's/[ \t]+$//; - s/^\ \ \ \ \ \ \ \ /\t/; - s/^\ \ \ \ \ \ \ \t/\t/; - s/^\ \ \ \ \ \ \t/\t/; - s/^\ \ \ \ \ \t/\t/; - s/^\ \ \ \t/\t/; - s/^\ \ \t/\t/; - s/^\ \t/\t/; - $m=1; - while ($m>0) { - $m=0; - $m= s/\t\ \ \ \ \ \ \ \ /\t\t/g; - $m=$m+s/\t\ \ \ \ \ \ \ \t/\t\t/g; - $m=$m+s/\t\ \ \ \ \ \ \t/\t\t/g; - $m=$m+s/\t\ \ \ \ \ \t/\t\t/g; - $m=$m+s/\t\ \ \ \t/\t\t/g; - $m=$m+s/\t\ \ \t/\t\t/g; - $m=$m+s/\t\ \t/\t\t/g; - } - print' < "${file}" > "${tmpfile}" - diff -u "${file}" "${tmpfile}" | sed \ - -e "s|^--- ${file}|--- ${file}.orig|" \ - -e "s|^+++ ${tmpfile}|+++ ${file}|" - rm -f "$tmpfile" + +if [ "x$1" = "xfast" ]; then + files="hg status -man" +elif [ "x$1" = "xmanifest" ]; then + files="hg manifest | cut '-d ' -f3" +else + files="find linux -name CVS -prune -o -type f -not -name .cvsignore -print" +fi + +for file in `eval $files`; do + perl -ne ' + s/[ \t]+$//; + s<^ {8}> <\t>; + s<^ {1,7}\t> <\t>; + while( s<\t {8}> <\t\t>g || s<\t {1,7}\t> <\t\t>g ) {}; + print' < "${file}" | diff -u "${file}" - done -- cgit v1.2.3 From 6a148432b8af513981b96fef00deeda1f7c52171 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Tue, 20 Jun 2006 00:30:57 -0300 Subject: Whitespace cleanups From: Trent Piepho Signed-off-by: Trent Piepho Signed-off-by: Mauro Carvalho Chehab --- .../video4linux/cx2341x/fw-decoder-api.txt | 8 +-- .../video4linux/cx2341x/fw-encoder-api.txt | 80 +++++++++++----------- .../video4linux/cx2341x/fw-memory.txt | 2 +- linux/drivers/media/radio/radio-typhoon.c | 2 +- linux/drivers/media/video/arv.c | 2 +- linux/drivers/media/video/bt8xx/bttv-cards.c | 2 +- linux/drivers/media/video/bt8xx/bttv-input.c | 2 +- linux/drivers/media/video/bw-qcam.c | 2 +- linux/drivers/media/video/cpia2/cpia2_v4l.c | 4 +- linux/drivers/media/video/cx88/cx88-dvb.c | 2 +- linux/drivers/media/video/ov511.c | 4 +- linux/drivers/media/video/pms.c | 2 +- linux/drivers/media/video/pwc/pwc-ctrl.c | 2 +- linux/drivers/media/video/pwc/pwc-dec23.c | 4 +- linux/drivers/media/video/pwc/pwc-if.c | 10 +-- linux/drivers/media/video/pwc/pwc-v4l.c | 38 +++++----- linux/drivers/media/video/saa7134/saa6752hs.c | 26 +++---- linux/drivers/media/video/saa7134/saa7134-alsa.c | 2 +- linux/drivers/media/video/saa7134/saa7134-cards.c | 2 +- linux/drivers/media/video/tda9875.c | 2 +- linux/drivers/media/video/tuner-simple.c | 2 +- 21 files changed, 100 insertions(+), 100 deletions(-) diff --git a/linux/Documentation/video4linux/cx2341x/fw-decoder-api.txt b/linux/Documentation/video4linux/cx2341x/fw-decoder-api.txt index 59193b6b5..9df4fb3ea 100644 --- a/linux/Documentation/video4linux/cx2341x/fw-decoder-api.txt +++ b/linux/Documentation/video4linux/cx2341x/fw-decoder-api.txt @@ -280,7 +280,7 @@ Description Param[0] Bitmask: 0:1 Data size: - '00' 16 bit + '00' 16 bit '01' 20 bit '10' 24 bit 2:7 Unused @@ -292,9 +292,9 @@ Param[0] (for left justified MSB first mode, 20 bit only) 10:11 Unused 12:13 Channel format: - '00' right justified MSB first mode - '01' left justified MSB first mode - '10' I2S mode + '00' right justified MSB first mode + '01' left justified MSB first mode + '10' I2S mode 14:15 Unused 16:21 Right justify bit count 22:31 Unused diff --git a/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt b/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt index 64cd11134..08ee9f530 100644 --- a/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt +++ b/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt @@ -281,64 +281,64 @@ Description Param[0] Bitmask: 0:1 '00' 44.1Khz - '01' 48Khz - '10' 32Khz - '11' reserved + '01' 48Khz + '10' 32Khz + '11' reserved 2:3 '01'=Layer I '10'=Layer II 4:7 Bitrate: - Index | Layer I | Layer II - ------+-------------+------------ - '0000' | free format | free format - '0001' | 32 kbit/s | 32 kbit/s - '0010' | 64 kbit/s | 48 kbit/s - '0011' | 96 kbit/s | 56 kbit/s - '0100' | 128 kbit/s | 64 kbit/s - '0101' | 160 kbit/s | 80 kbit/s - '0110' | 192 kbit/s | 96 kbit/s - '0111' | 224 kbit/s | 112 kbit/s - '1000' | 256 kbit/s | 128 kbit/s - '1001' | 288 kbit/s | 160 kbit/s - '1010' | 320 kbit/s | 192 kbit/s - '1011' | 352 kbit/s | 224 kbit/s - '1100' | 384 kbit/s | 256 kbit/s - '1101' | 416 kbit/s | 320 kbit/s - '1110' | 448 kbit/s | 384 kbit/s - Note: For Layer II, not all combinations of total bitrate - and mode are allowed. See ISO11172-3 3-Annex B, Table 3-B.2 + Index | Layer I | Layer II + ------+-------------+------------ + '0000' | free format | free format + '0001' | 32 kbit/s | 32 kbit/s + '0010' | 64 kbit/s | 48 kbit/s + '0011' | 96 kbit/s | 56 kbit/s + '0100' | 128 kbit/s | 64 kbit/s + '0101' | 160 kbit/s | 80 kbit/s + '0110' | 192 kbit/s | 96 kbit/s + '0111' | 224 kbit/s | 112 kbit/s + '1000' | 256 kbit/s | 128 kbit/s + '1001' | 288 kbit/s | 160 kbit/s + '1010' | 320 kbit/s | 192 kbit/s + '1011' | 352 kbit/s | 224 kbit/s + '1100' | 384 kbit/s | 256 kbit/s + '1101' | 416 kbit/s | 320 kbit/s + '1110' | 448 kbit/s | 384 kbit/s + Note: For Layer II, not all combinations of total bitrate + and mode are allowed. See ISO11172-3 3-Annex B, Table 3-B.2 8:9 '00'=Stereo - '01'=JointStereo - '10'=Dual - '11'=Mono + '01'=JointStereo + '10'=Dual + '11'=Mono 10:11 Mode Extension used in joint_stereo mode. - In Layer I and II they indicate which subbands are in + In Layer I and II they indicate which subbands are in intensity_stereo. All other subbands are coded in stereo. - '00' subbands 4-31 in intensity_stereo, bound==4 - '01' subbands 8-31 in intensity_stereo, bound==8 - '10' subbands 12-31 in intensity_stereo, bound==12 - '11' subbands 16-31 in intensity_stereo, bound==16 + '00' subbands 4-31 in intensity_stereo, bound==4 + '01' subbands 8-31 in intensity_stereo, bound==8 + '10' subbands 12-31 in intensity_stereo, bound==12 + '11' subbands 16-31 in intensity_stereo, bound==16 12:13 Emphasis: - '00' None - '01' 50/15uS - '10' reserved - '11' CCITT J.17 + '00' None + '01' 50/15uS + '10' reserved + '11' CCITT J.17 14 CRC: - '0' off - '1' on + '0' off + '1' on 15 Copyright: - '0' off - '1' on + '0' off + '1' on 16 Generation: - '0' copy - '1' original + '0' copy + '1' original ------------------------------------------------------------------------------- diff --git a/linux/Documentation/video4linux/cx2341x/fw-memory.txt b/linux/Documentation/video4linux/cx2341x/fw-memory.txt index 336d8208e..ef0aad3f8 100644 --- a/linux/Documentation/video4linux/cx2341x/fw-memory.txt +++ b/linux/Documentation/video4linux/cx2341x/fw-memory.txt @@ -60,7 +60,7 @@ DMA Registers 0x000-0xff: if changed to 0xffffffff DMA write interrupts break. 0x50 - always 0xffffffff 0x54 - always 0xffffffff (0x4c, 0x50, 0x54 seem like interrupt masks, are - 3 processors on chip, Java ones, VPU, SPU, APU, maybe these are the + 3 processors on chip, Java ones, VPU, SPU, APU, maybe these are the interrupt masks???). 0x60-0x7C - random values 0x80 - first write linked list reg, for Encoder Memory addr diff --git a/linux/drivers/media/radio/radio-typhoon.c b/linux/drivers/media/radio/radio-typhoon.c index 519899793..4f5adce15 100644 --- a/linux/drivers/media/radio/radio-typhoon.c +++ b/linux/drivers/media/radio/radio-typhoon.c @@ -368,7 +368,7 @@ static int __init typhoon_init(void) #ifdef CONFIG_RADIO_TYPHOON_PROC_FS if (!create_proc_info_entry("driver/radio-typhoon", 0, NULL, typhoon_get_info)) - printk(KERN_ERR "radio-typhoon: registering /proc/driver/radio-typhoon failed\n"); + printk(KERN_ERR "radio-typhoon: registering /proc/driver/radio-typhoon failed\n"); #endif return 0; diff --git a/linux/drivers/media/video/arv.c b/linux/drivers/media/video/arv.c index 6c82b2fef..24c0ddc33 100644 --- a/linux/drivers/media/video/arv.c +++ b/linux/drivers/media/video/arv.c @@ -214,7 +214,7 @@ void init_iic(void) ar_outl(0x0300, PLDI2CMOD); /* I2CMOD ACK/8b-data/7b-addr/auto */ ar_outl(0x1, PLDI2CACK); /* I2CACK ACK */ - /* I2C CLK */ + /* I2C CLK */ /* 50MH-100k */ if (freq == 75) { ar_outl(369, PLDI2CFREQ); /* BCLK = 75MHz */ diff --git a/linux/drivers/media/video/bt8xx/bttv-cards.c b/linux/drivers/media/video/bt8xx/bttv-cards.c index 8dab6b9b1..3772493ec 100644 --- a/linux/drivers/media/video/bt8xx/bttv-cards.c +++ b/linux/drivers/media/video/bt8xx/bttv-cards.c @@ -292,7 +292,7 @@ static struct CARD { { 0x41a0a051, BTTV_BOARD_FLYVIDEO_98FM, "Lifeview FlyVideo 98 LR50 Rev Q" }, { 0x18501f7f, BTTV_BOARD_FLYVIDEO_98, "Lifeview Flyvideo 98" }, - { 0x010115cb, BTTV_BOARD_GMV1, "AG GMV1" }, + { 0x010115cb, BTTV_BOARD_GMV1, "AG GMV1" }, { 0x010114c7, BTTV_BOARD_MODTEC_205, "Modular Technology MM201/MM202/MM205/MM210/MM215 PCTV" }, { 0x10b42636, BTTV_BOARD_HAUPPAUGE878, "STB ???" }, diff --git a/linux/drivers/media/video/bt8xx/bttv-input.c b/linux/drivers/media/video/bt8xx/bttv-input.c index bab7cb123..ce5ce470a 100644 --- a/linux/drivers/media/video/bt8xx/bttv-input.c +++ b/linux/drivers/media/video/bt8xx/bttv-input.c @@ -356,7 +356,7 @@ int bttv_input_init(struct bttv *btv) if (ir->rc5_gpio) { u32 gpio; - /* enable remote irq */ + /* enable remote irq */ bttv_gpio_inout(&btv->c, (1 << 4), 1 << 4); gpio = bttv_gpio_read(&btv->c); bttv_gpio_write(&btv->c, gpio & ~(1 << 4)); diff --git a/linux/drivers/media/video/bw-qcam.c b/linux/drivers/media/video/bw-qcam.c index 108612e1f..497fc3418 100644 --- a/linux/drivers/media/video/bw-qcam.c +++ b/linux/drivers/media/video/bw-qcam.c @@ -763,7 +763,7 @@ static int qcam_do_ioctl(struct inode *inode, struct file *file, { struct video_picture *p = arg; if(p->palette!=VIDEO_PALETTE_GREY) - return -EINVAL; + return -EINVAL; if(p->depth!=4 && p->depth!=6) return -EINVAL; diff --git a/linux/drivers/media/video/cpia2/cpia2_v4l.c b/linux/drivers/media/video/cpia2/cpia2_v4l.c index 481e178ef..28d93c595 100644 --- a/linux/drivers/media/video/cpia2/cpia2_v4l.c +++ b/linux/drivers/media/video/cpia2/cpia2_v4l.c @@ -1167,9 +1167,9 @@ static int ioctl_g_ctrl(void *arg,struct camera_data *cam) } else { if(cam->params.flicker_control.cam_register & CPIA2_VP_FLICKER_MODES_50HZ) { - mode = FLICKER_50; + mode = FLICKER_50; } else { - mode = FLICKER_60; + mode = FLICKER_60; } } for(i=0; ibytes_recvd, 8, max_raw); if (frame->scanstate == STATE_LINES) { - int nextf; + int nextf; frame->grabstate = FRAME_DONE; wake_up_interruptible(&frame->wq); @@ -3405,7 +3405,7 @@ eof: RESTRICT_TO_RANGE(frame->bytes_recvd, 8, max_raw); if (frame->scanstate == STATE_LINES) { - int nextf; + int nextf; frame->grabstate = FRAME_DONE; wake_up_interruptible(&frame->wq); diff --git a/linux/drivers/media/video/pms.c b/linux/drivers/media/video/pms.c index d129072a9..e13a7f8b8 100644 --- a/linux/drivers/media/video/pms.c +++ b/linux/drivers/media/video/pms.c @@ -812,7 +812,7 @@ static int pms_do_ioctl(struct inode *inode, struct file *file, struct video_picture *p = arg; if(!((p->palette==VIDEO_PALETTE_RGB565 && p->depth==16) ||(p->palette==VIDEO_PALETTE_RGB555 && p->depth==15))) - return -EINVAL; + return -EINVAL; pd->picture= *p; /* diff --git a/linux/drivers/media/video/pwc/pwc-ctrl.c b/linux/drivers/media/video/pwc/pwc-ctrl.c index c64f498f1..0f25d4eac 100644 --- a/linux/drivers/media/video/pwc/pwc-ctrl.c +++ b/linux/drivers/media/video/pwc/pwc-ctrl.c @@ -1404,7 +1404,7 @@ int pwc_ioctl(struct pwc_device *pdev, unsigned int cmd, void *arg) ARG_IN(leds) ret = pwc_set_leds(pdev, ARGR(leds).led_on, ARGR(leds).led_off); - break; + break; } diff --git a/linux/drivers/media/video/pwc/pwc-dec23.c b/linux/drivers/media/video/pwc/pwc-dec23.c index 39eaf5839..9e2d91f26 100644 --- a/linux/drivers/media/video/pwc/pwc-dec23.c +++ b/linux/drivers/media/video/pwc/pwc-dec23.c @@ -105,7 +105,7 @@ static void build_bit_powermask_table(struct pwc_dec23_private *pdec) static void build_table_color(const unsigned int romtable[16][8], - unsigned char p0004[16][1024], + unsigned char p0004[16][1024], unsigned char p8004[16][256]) { int compression_mode, j, k, bit, pw; @@ -787,7 +787,7 @@ static void DecompressBand23(struct pwc_dec23_private *pdec, * */ static void DecompressBandBayer(struct pwc_dec23_private *pdec, - const unsigned char *rawyuv, + const unsigned char *rawyuv, unsigned char *rgbbayer, unsigned int compressed_image_width, unsigned int real_image_width) diff --git a/linux/drivers/media/video/pwc/pwc-if.c b/linux/drivers/media/video/pwc/pwc-if.c index fbe7ae2a9..844b7fcfb 100644 --- a/linux/drivers/media/video/pwc/pwc-if.c +++ b/linux/drivers/media/video/pwc/pwc-if.c @@ -1097,7 +1097,7 @@ static const char *pwc_sensor_type_to_string(unsigned int sensor_type) case 0x101: return "PAL MR sensor"; default: - return "unknown type of sensor"; + return "unknown type of sensor"; } } #endif @@ -1744,10 +1744,10 @@ static int usb_pwc_probe(struct usb_interface *intf, const struct usb_device_id (device_hint[hint].pdev == NULL)) { /* so far, so good... try serial number */ if ((device_hint[hint].serial_number[0] == '*') || !strcmp(device_hint[hint].serial_number, serial_number)) { - /* match! */ - video_nr = device_hint[hint].device_node; - PWC_DEBUG_PROBE("Found hint, will try to register as /dev/video%d\n", video_nr); - break; + /* match! */ + video_nr = device_hint[hint].device_node; + PWC_DEBUG_PROBE("Found hint, will try to register as /dev/video%d\n", video_nr); + break; } } } diff --git a/linux/drivers/media/video/pwc/pwc-v4l.c b/linux/drivers/media/video/pwc/pwc-v4l.c index 86faadd48..bd918b87c 100644 --- a/linux/drivers/media/video/pwc/pwc-v4l.c +++ b/linux/drivers/media/video/pwc/pwc-v4l.c @@ -678,9 +678,9 @@ int pwc_video_do_ioctl(struct inode *inode, struct file *file, break; } - /* V4L2 Layer */ - case VIDIOC_QUERYCAP: - { + /* V4L2 Layer */ + case VIDIOC_QUERYCAP: + { struct v4l2_capability *cap = arg; PWC_DEBUG_IOCTL("ioctl(VIDIOC_QUERYCAP) This application "\ @@ -696,8 +696,8 @@ int pwc_video_do_ioctl(struct inode *inode, struct file *file, return 0; } - case VIDIOC_ENUMINPUT: - { + case VIDIOC_ENUMINPUT: + { struct v4l2_input *i = arg; if ( i->index ) /* Only one INPUT is supported */ @@ -708,14 +708,14 @@ int pwc_video_do_ioctl(struct inode *inode, struct file *file, return 0; } - case VIDIOC_G_INPUT: + case VIDIOC_G_INPUT: { int *i = arg; *i = 0; /* Only one INPUT is supported */ return 0; } - case VIDIOC_S_INPUT: - { + case VIDIOC_S_INPUT: + { int *i = arg; if ( *i ) { /* Only one INPUT is supported */ @@ -727,7 +727,7 @@ int pwc_video_do_ioctl(struct inode *inode, struct file *file, } /* TODO: */ - case VIDIOC_QUERYCTRL: + case VIDIOC_QUERYCTRL: { struct v4l2_queryctrl *c = arg; int i; @@ -965,13 +965,13 @@ int pwc_video_do_ioctl(struct inode *inode, struct file *file, case VIDIOC_ENUM_FMT: { - struct v4l2_fmtdesc *f = arg; + struct v4l2_fmtdesc *f = arg; int index; if (f->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) return -EINVAL; - /* We only support two format: the raw format, and YUV */ + /* We only support two format: the raw format, and YUV */ index = f->index; memset(f,0,sizeof(struct v4l2_fmtdesc)); f->type = V4L2_BUF_TYPE_VIDEO_CAPTURE; @@ -980,23 +980,23 @@ int pwc_video_do_ioctl(struct inode *inode, struct file *file, { case 0: /* RAW format */ - f->pixelformat = pdev->type<=646?V4L2_PIX_FMT_PWC1:V4L2_PIX_FMT_PWC2; + f->pixelformat = pdev->type<=646?V4L2_PIX_FMT_PWC1:V4L2_PIX_FMT_PWC2; f->flags = V4L2_FMT_FLAG_COMPRESSED; - strlcpy(f->description,"Raw Philips Webcam",sizeof(f->description)); + strlcpy(f->description,"Raw Philips Webcam",sizeof(f->description)); break; case 1: - f->pixelformat = V4L2_PIX_FMT_YUV420; - strlcpy(f->description,"4:2:0, planar, Y-Cb-Cr",sizeof(f->description)); + f->pixelformat = V4L2_PIX_FMT_YUV420; + strlcpy(f->description,"4:2:0, planar, Y-Cb-Cr",sizeof(f->description)); break; - default: + default: return -EINVAL; } return 0; } - case VIDIOC_G_FMT: + case VIDIOC_G_FMT: { - struct v4l2_format *f = arg; + struct v4l2_format *f = arg; PWC_DEBUG_IOCTL("ioctl(VIDIOC_G_FMT) return size %dx%d\n",pdev->image.x,pdev->image.y); if (f->type != V4L2_BUF_TYPE_VIDEO_CAPTURE) @@ -1010,7 +1010,7 @@ int pwc_video_do_ioctl(struct inode *inode, struct file *file, case VIDIOC_TRY_FMT: return pwc_vidioc_try_fmt(pdev, arg); - case VIDIOC_S_FMT: + case VIDIOC_S_FMT: return pwc_vidioc_set_fmt(pdev, arg); case VIDIOC_G_STD: diff --git a/linux/drivers/media/video/saa7134/saa6752hs.c b/linux/drivers/media/video/saa7134/saa6752hs.c index eac8bfba9..16685386c 100644 --- a/linux/drivers/media/video/saa7134/saa6752hs.c +++ b/linux/drivers/media/video/saa7134/saa6752hs.c @@ -69,11 +69,11 @@ struct saa6752hs_state { enum saa6752hs_command { SAA6752HS_COMMAND_RESET = 0, - SAA6752HS_COMMAND_STOP = 1, - SAA6752HS_COMMAND_START = 2, - SAA6752HS_COMMAND_PAUSE = 3, - SAA6752HS_COMMAND_RECONFIGURE = 4, - SAA6752HS_COMMAND_SLEEP = 5, + SAA6752HS_COMMAND_STOP = 1, + SAA6752HS_COMMAND_START = 2, + SAA6752HS_COMMAND_PAUSE = 3, + SAA6752HS_COMMAND_RECONFIGURE = 4, + SAA6752HS_COMMAND_SLEEP = 5, SAA6752HS_COMMAND_RECONFIGURE_FORCE = 6, SAA6752HS_COMMAND_MAX @@ -252,19 +252,19 @@ static int saa6752hs_set_bitrate(struct i2c_client* client, if (params->vi_bitrate.mode == V4L2_BITRATE_VBR) { /* set the target bitrate */ buf[0] = 0x80; - buf[1] = params->vi_bitrate.target >> 8; + buf[1] = params->vi_bitrate.target >> 8; buf[2] = params->vi_bitrate.target & 0xff; i2c_master_send(client, buf, 3); /* set the max bitrate */ buf[0] = 0x81; - buf[1] = params->vi_bitrate.max >> 8; + buf[1] = params->vi_bitrate.max >> 8; buf[2] = params->vi_bitrate.max & 0xff; i2c_master_send(client, buf, 3); } else { /* set the target bitrate (no max bitrate for CBR) */ buf[0] = 0x81; - buf[1] = params->vi_bitrate.target >> 8; + buf[1] = params->vi_bitrate.target >> 8; buf[2] = params->vi_bitrate.target & 0xff; i2c_master_send(client, buf, 3); } @@ -406,22 +406,22 @@ static int saa6752hs_init(struct i2c_client* client) buf[2] = 0x0D; i2c_master_send(client,buf,3); - /* Set minimum Q-scale {4} */ + /* Set minimum Q-scale {4} */ buf[0] = 0x82; buf[1] = 0x04; i2c_master_send(client,buf,2); - /* Set maximum Q-scale {12} */ + /* Set maximum Q-scale {12} */ buf[0] = 0x83; buf[1] = 0x0C; i2c_master_send(client,buf,2); - /* Set Output Protocol */ + /* Set Output Protocol */ buf[0] = 0xD0; buf[1] = 0x81; i2c_master_send(client,buf,2); - /* Set video output stream format {TS} */ + /* Set video output stream format {TS} */ buf[0] = 0xB0; buf[1] = 0x05; i2c_master_send(client,buf,2); @@ -452,7 +452,7 @@ static int saa6752hs_init(struct i2c_client* client) localPMT[sizeof(PMT) - 2] = (crc >> 8) & 0xFF; localPMT[sizeof(PMT) - 1] = crc & 0xFF; - /* Set Audio PID */ + /* Set Audio PID */ buf[0] = 0xC1; buf[1] = (h->params.ts_pid_audio >> 8) & 0xFF; buf[2] = h->params.ts_pid_audio & 0xFF; diff --git a/linux/drivers/media/video/saa7134/saa7134-alsa.c b/linux/drivers/media/video/saa7134/saa7134-alsa.c index fefcce8f6..7807397a5 100644 --- a/linux/drivers/media/video/saa7134/saa7134-alsa.c +++ b/linux/drivers/media/video/saa7134/saa7134-alsa.c @@ -926,7 +926,7 @@ static int snd_saa7134_capsrc_put(struct snd_kcontrol * kcontrol, break; } - /* output xbar always main channel */ + /* output xbar always main channel */ saa_dsp_writel(dev, SAA7133_DIGITAL_OUTPUT_SEL1, 0xbbbb10); if (left || right) { // We've got data, turn the input on diff --git a/linux/drivers/media/video/saa7134/saa7134-cards.c b/linux/drivers/media/video/saa7134/saa7134-cards.c index b00224184..389f05b3c 100644 --- a/linux/drivers/media/video/saa7134/saa7134-cards.c +++ b/linux/drivers/media/video/saa7134/saa7134-cards.c @@ -2161,7 +2161,7 @@ struct saa7134_board saa7134_boards[] = { .radio = { .name = name_radio, .amux = LINE2, - }, + }, }, [SAA7134_BOARD_GOTVIEW_7135] = { /* Mike Baikov */ diff --git a/linux/drivers/media/video/tda9875.c b/linux/drivers/media/video/tda9875.c index 42f28e6b0..279f1ecd7 100644 --- a/linux/drivers/media/video/tda9875.c +++ b/linux/drivers/media/video/tda9875.c @@ -185,7 +185,7 @@ static void do_tda9875_init(struct i2c_client *client) struct tda9875 *t = i2c_get_clientdata(client); dprintk("In tda9875_init\n"); tda9875_write(client, TDA9875_CFG, 0xd0 ); /*reg de config 0 (reset)*/ - tda9875_write(client, TDA9875_MSR, 0x03 ); /* Monitor 0b00000XXX*/ + tda9875_write(client, TDA9875_MSR, 0x03 ); /* Monitor 0b00000XXX*/ tda9875_write(client, TDA9875_C1MSB, 0x00 ); /*Car1(FM) MSB XMHz*/ tda9875_write(client, TDA9875_C1MIB, 0x00 ); /*Car1(FM) MIB XMHz*/ tda9875_write(client, TDA9875_C1LSB, 0x00 ); /*Car1(FM) LSB XMHz*/ diff --git a/linux/drivers/media/video/tuner-simple.c b/linux/drivers/media/video/tuner-simple.c index 0b82156ed..f3cbe151d 100644 --- a/linux/drivers/media/video/tuner-simple.c +++ b/linux/drivers/media/video/tuner-simple.c @@ -114,7 +114,7 @@ static int tuner_stereo(struct i2c_client *c) switch (t->type) { case TUNER_PHILIPS_FM1216ME_MK3: - case TUNER_PHILIPS_FM1236_MK3: + case TUNER_PHILIPS_FM1236_MK3: case TUNER_PHILIPS_FM1256_IH3: stereo = ((status & TUNER_SIGNAL) == TUNER_STEREO_MK3); break; -- cgit v1.2.3 From 5a87ea92654687aedb0e6dcdbbb0718e10d7eecb Mon Sep 17 00:00:00 2001 From: Michael Krufky Date: Tue, 20 Jun 2006 08:17:48 -0400 Subject: update cardlist documentation From: Michael Krufky Signed-off-by: Michael Krufky --- linux/Documentation/video4linux/CARDLIST.saa7134 | 1 + 1 file changed, 1 insertion(+) diff --git a/linux/Documentation/video4linux/CARDLIST.saa7134 b/linux/Documentation/video4linux/CARDLIST.saa7134 index bca509032..9068b669f 100644 --- a/linux/Documentation/video4linux/CARDLIST.saa7134 +++ b/linux/Documentation/video4linux/CARDLIST.saa7134 @@ -93,3 +93,4 @@ 92 -> AVerMedia A169 B1 [1461:6360] 93 -> Medion 7134 Bridge #2 [16be:0005] 94 -> LifeView FlyDVB-T Hybrid Cardbus [5168:3306,5168:3502] + 95 -> LifeView FlyVIDEO3000 (NTSC) [5169:0138] -- cgit v1.2.3 From f90de21871e817db194b7904ac76ab19a7797fa2 Mon Sep 17 00:00:00 2001 From: Michael Krufky Date: Tue, 20 Jun 2006 08:18:13 -0400 Subject: lgdt330x: fix missing line in VSB snr decoding logic From: Mac Michaels - fix missing line in VSB snr decoding logic for lgdt3303 Signed-off-by: Mac Michaels Signed-off-by: Michael Krufky --- linux/drivers/media/dvb/frontends/lgdt330x.c | 1 + 1 file changed, 1 insertion(+) diff --git a/linux/drivers/media/dvb/frontends/lgdt330x.c b/linux/drivers/media/dvb/frontends/lgdt330x.c index 2a28b768c..b48b82b11 100644 --- a/linux/drivers/media/dvb/frontends/lgdt330x.c +++ b/linux/drivers/media/dvb/frontends/lgdt330x.c @@ -685,6 +685,7 @@ static int lgdt3303_read_snr(struct dvb_frontend* fe, u16* snr) if (state->current_modulation == VSB_8) { + i2c_read_demod_bytes(state, 0x6e, buf, 5); #if 0 /* Equalizer Mean-Square Error Register for VSB */ noise = ((buf[0] & 0x78) << 13) | (buf[1] << 8) | buf[2]; -- cgit v1.2.3 From ecddc353539730fcf011b1e9d60ba3acca577e04 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Tue, 20 Jun 2006 13:17:11 -0300 Subject: Makefile.media were rewritten even when not required. From: Mauro Carvalho Chehab make 3.81 were suffering some endless loop that might be caused by Makefile.media rewrites. After this patch, make_makefile will only write Makefile.media if needed. Signed-off-by: Mauro Carvalho Chehab --- v4l/scripts/make_makefile.pl | 26 ++++++++++++++++++++++++-- 1 file changed, 24 insertions(+), 2 deletions(-) diff --git a/v4l/scripts/make_makefile.pl b/v4l/scripts/make_makefile.pl index 238c5082f..bcfb3764f 100755 --- a/v4l/scripts/make_makefile.pl +++ b/v4l/scripts/make_makefile.pl @@ -109,7 +109,7 @@ sub open_makefile($) { close $in; } -open OUT,">Makefile.media"; +open OUT,">Makefile.media.new"; open_makefile ("../linux/drivers/media/Makefile"); # Creating Install rule @@ -156,7 +156,29 @@ while ( my ($key, $value) = each(%depend) ) { } close OUT; -if (open OUT,".myconfig") { +if (open IN,"Makefile.media") { + close IN; + my $changed=0; + if (open IN,"diff Makefile.media Makefile.media.new|") { + while () { + if ($_ ne "") { + $changed=1; + } + } + close IN; + if ($changed) { + printf("One or more linux Makefiles had changed. Makefile.media rewrited.\n"); + system ("mv Makefile.media.new Makefile.media"); + } else { + system ("rm Makefile.media.new"); + } + } +} else { + printf("Creating Makefile.media.\n"); + system "mv Makefile.media.new Makefile.media"; +} + +if (open IN,".myconfig") { close IN; } else { system "make allmodconfig"; -- cgit v1.2.3 From 4ea4995bb837bf08c755327949a61752324b53c9 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Tue, 20 Jun 2006 15:03:19 -0300 Subject: Ovcamship position at Kconfig changed From: Mauro Carvalho Chehab Ovcamship is used only on some USB webcams (OV511 and W9968CF) Bettet to leave this item just after those webcams. Signed-off-by: Mauro Carvalho Chehab --- linux/drivers/media/video/Kconfig | 58 +++++++++++++++++++-------------------- 1 file changed, 29 insertions(+), 29 deletions(-) diff --git a/linux/drivers/media/video/Kconfig b/linux/drivers/media/video/Kconfig index 134af1cad..89d621193 100644 --- a/linux/drivers/media/video/Kconfig +++ b/linux/drivers/media/video/Kconfig @@ -312,17 +312,6 @@ config VIDEO_HEXIUM_GEMINI source "drivers/media/video/cx88/Kconfig" -config VIDEO_OVCAMCHIP - tristate "OmniVision Camera Chip support" - depends on I2C && VIDEO_V4L1 - ---help--- - Support for the OmniVision OV6xxx and OV7xxx series of camera chips. - This driver is intended to be used with the ov511 and w9968cf USB - camera drivers. - - To compile this driver as a module, choose M here: the - module will be called ovcamchip. - config VIDEO_M32R_AR tristate "AR devices" depends on M32R && VIDEO_V4L1 @@ -464,6 +453,35 @@ source "drivers/media/video/usbvideo/Kconfig" source "drivers/media/video/et61x251/Kconfig" +config VIDEO_OVCAMCHIP + tristate "OmniVision Camera Chip support" + depends on I2C && VIDEO_V4L1 + ---help--- + Support for the OmniVision OV6xxx and OV7xxx series of camera chips. + This driver is intended to be used with the ov511 and w9968cf USB + camera drivers. + + To compile this driver as a module, choose M here: the + module will be called ovcamchip. + +config USB_W9968CF + tristate "USB W996[87]CF JPEG Dual Mode Camera support" + depends on USB && VIDEO_V4L1 && I2C + select VIDEO_OVCAMCHIP + ---help--- + Say Y here if you want support for cameras based on OV681 or + Winbond W9967CF/W9968CF JPEG USB Dual Mode Camera Chips. + + This driver has an optional plugin, which is distributed as a + separate module only (released under GPL). It allows to use higher + resolutions and framerates, but cannot be included in the official + Linux kernel for performance purposes. + + See for more info. + + To compile this driver as a module, choose M here: the + module will be called w9968cf. + config USB_OV511 tristate "USB OV511 Camera support" depends on USB && VIDEO_V4L1 @@ -500,24 +518,6 @@ config USB_STV680 To compile this driver as a module, choose M here: the module will be called stv680. -config USB_W9968CF - tristate "USB W996[87]CF JPEG Dual Mode Camera support" - depends on USB && VIDEO_V4L1 && I2C - select VIDEO_OVCAMCHIP - ---help--- - Say Y here if you want support for cameras based on OV681 or - Winbond W9967CF/W9968CF JPEG USB Dual Mode Camera Chips. - - This driver has an optional plugin, which is distributed as a - separate module only (released under GPL). It allows to use higher - resolutions and framerates, but cannot be included in the official - Linux kernel for performance purposes. - - See for more info. - - To compile this driver as a module, choose M here: the - module will be called w9968cf. - source "drivers/media/video/zc0301/Kconfig" source "drivers/media/video/pwc/Kconfig" -- cgit v1.2.3 From a4a842549ba31d9342385a2727185b793bd8ced6 Mon Sep 17 00:00:00 2001 From: Michael Krufky Date: Tue, 20 Jun 2006 14:56:02 -0400 Subject: Kconfig: fix description for saa7115 module From: Michael Krufky This Kconfig description is incorrect, due to a previous merge a while back. CONFIG_SAA711X builds module saa7115, which is the newer module, and is not obsoleted. Signed-off-by: Michael Krufky --- linux/drivers/media/video/Kconfig | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/linux/drivers/media/video/Kconfig b/linux/drivers/media/video/Kconfig index 89d621193..44ae23419 100644 --- a/linux/drivers/media/video/Kconfig +++ b/linux/drivers/media/video/Kconfig @@ -384,10 +384,10 @@ config VIDEO_WM8739 source "drivers/media/video/cx25840/Kconfig" config VIDEO_SAA711X - tristate "Philips SAA7113/4/5 video decoders (OBSOLETED)" + tristate "Philips SAA7113/4/5 video decoders" depends on VIDEO_V4L1 && I2C && EXPERIMENTAL ---help--- - Old support for the Philips SAA7113/4 video decoders. + Support for the Philips SAA7113/4/5 video decoders. To compile this driver as a module, choose M here: the module will be called saa7115. -- cgit v1.2.3 From b27ac015d8030bb7062bcbc0ea0a7f5ab45c2a95 Mon Sep 17 00:00:00 2001 From: Michael Krufky Date: Tue, 20 Jun 2006 15:43:59 -0400 Subject: kconfig: saa7115 depends on VIDEO_DEV, not VIDEO_V4l1 From: Michael Krufky ... another leftover bug from a previous merge Signed-off-by: Michael Krufky --- linux/drivers/media/video/Kconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/linux/drivers/media/video/Kconfig b/linux/drivers/media/video/Kconfig index 44ae23419..2ed46e87e 100644 --- a/linux/drivers/media/video/Kconfig +++ b/linux/drivers/media/video/Kconfig @@ -385,7 +385,7 @@ source "drivers/media/video/cx25840/Kconfig" config VIDEO_SAA711X tristate "Philips SAA7113/4/5 video decoders" - depends on VIDEO_V4L1 && I2C && EXPERIMENTAL + depends on VIDEO_DEV && I2C && EXPERIMENTAL ---help--- Support for the Philips SAA7113/4/5 video decoders. -- cgit v1.2.3 From 71f2bbd7d30a3c7ea2e220dd61e37e4e05f56b95 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Tue, 20 Jun 2006 22:21:49 +0200 Subject: Fix v4l2-ctl usage text. From: Hans Verkuil Signed-off-by: Hans Verkuil --- test/v4l2-ctl.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/v4l2-ctl.cpp b/test/v4l2-ctl.cpp index ade779546..a75d7c144 100644 --- a/test/v4l2-ctl.cpp +++ b/test/v4l2-ctl.cpp @@ -165,7 +165,7 @@ void usage(void) printf(" -c, --set-ctrl==[,=...]\n"); printf(" set the controls to the values specified [VIDIOC_S_EXT_CTRLS]\n"); printf(" -D, --info show driver info [VIDIOC_QUERYCAP]\n"); - printf(" -d, --device= use device instead of /dev/video0 [VIDIOC_S_EXT_CTRLS]\n"); + printf(" -d, --device= use device instead of /dev/video0\n"); printf(" if is a single digit, then /dev/video is used\n"); printf(" -F, --get-freq query the current frequency [VIDIOC_G_FREQUENCY]\n"); printf(" -f, --set-freq=\n"); -- cgit v1.2.3 From a65cbc3b7aa2eaf072f20f362966f0b0055077b3 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Tue, 20 Jun 2006 20:01:22 -0300 Subject: Adjust distclean target to clean a few more files From: Trent Piepho distclean was not cleaning the v4l/.myconfig file, or the symlinks made for the lxdialog program. This caused problems especially if you were switching between different kernel versions for testing. Signed-off-by: Trent Piepho Signed-off-by: Mauro Carvalho Chehab --- v4l/Makefile | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/v4l/Makefile b/v4l/Makefile index d20e68d4e..5be5f40ba 100644 --- a/v4l/Makefile +++ b/v4l/Makefile @@ -216,8 +216,9 @@ clean:: distclean:: clean -rm -f .version .*.o.flags .*.o.d Makefile.media \ - Kconfig Kconfig.kern .config .config.cmd + Kconfig Kconfig.kern .config .config.cmd .myconfig -rm -rf .tmp_versions + -rm -f scripts/lxdialog scripts/kconfig @find .. -name '*.orig' -exec rm '{}' \; @find .. -name '*.rej' -exec rm '{}' \; -- cgit v1.2.3 From 74e1ed0781b35cfd53baba71c84dfbf6c59c5403 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 21 Jun 2006 10:04:08 -0300 Subject: Fixes circular dependencies at building system From: Mauro Carvalho Chehab There were a circular dependency at scripts/make_makefile.pl that were affecting mostly building with GNU make 3.81. Also, scripts/make_noconfig.pl is, in fact, building .myconfig file, so, better to name it as make_myconfig.pl. Signed-off-by: Mauro Carvalho Chehab --- v4l/Makefile | 14 ++++++----- v4l/scripts/make_makefile.pl | 2 +- v4l/scripts/make_myconfig.pl | 58 ++++++++++++++++++++++++++++++++++++++++++++ v4l/scripts/make_noconfig.pl | 58 -------------------------------------------- 4 files changed, 67 insertions(+), 65 deletions(-) create mode 100755 v4l/scripts/make_myconfig.pl delete mode 100755 v4l/scripts/make_noconfig.pl diff --git a/v4l/Makefile b/v4l/Makefile index d20e68d4e..27a79a181 100644 --- a/v4l/Makefile +++ b/v4l/Makefile @@ -180,7 +180,9 @@ links:: @find ../linux/drivers/media -name '*.[ch]' -type f -exec ln -sf '{}' . \; @find ../linux/sound -name '*.[ch]' -type f -exec ln -sf '{}' . \; -config-compat.h:: .myconfig +config-compat.h:: + scripts/make_myconfig.pl + @echo \#ifndef __CONFIG_COMPAT_H__ > config-compat.h @echo \#define __CONFIG_COMPAT_H__ >> config-compat.h @echo >> config-compat.h @@ -253,26 +255,26 @@ LXDIALOG := $(KDIR)/scripts/$(LXDIALOG_DIR)lxdialog/lxdialog xconfig:: links .version $(QCONF) ./scripts/make_kconfig.pl $(QCONF) Kconfig - ./scripts/make_noconfig.pl + ./scripts/make_myconfig.pl gconfig:: links .version $(GCONF) ./scripts/make_kconfig.pl $(QCONF) Kconfig - ./scripts/make_noconfig.pl + ./scripts/make_myconfig.pl config:: links .version $(CONF) ./scripts/make_kconfig.pl $(CONF) Kconfig - ./scripts/make_noconfig.pl + ./scripts/make_myconfig.pl menuconfig:: links .version $(MCONF) lxdialog ./scripts/make_kconfig.pl $(MCONF) Kconfig - ./scripts/make_noconfig.pl + ./scripts/make_myconfig.pl allyesconfig allmodconfig:: links .version ./scripts/make_kconfig.pl 1 - ./scripts/make_noconfig.pl + ./scripts/make_myconfig.pl # rule to build kernel conf programs KMAKEVARS := config-targets=1 mixed-targets=0 dot-config=0 diff --git a/v4l/scripts/make_makefile.pl b/v4l/scripts/make_makefile.pl index bcfb3764f..f0d9aef7f 100755 --- a/v4l/scripts/make_makefile.pl +++ b/v4l/scripts/make_makefile.pl @@ -181,5 +181,5 @@ if (open IN,"Makefile.media") { if (open IN,".myconfig") { close IN; } else { - system "make allmodconfig"; + system "./scripts/make_kconfig.pl 1"; } diff --git a/v4l/scripts/make_myconfig.pl b/v4l/scripts/make_myconfig.pl new file mode 100755 index 000000000..7323f419c --- /dev/null +++ b/v4l/scripts/make_myconfig.pl @@ -0,0 +1,58 @@ +#!/usr/bin/perl + +# The purpose of this script is to produce a file named '.myconfig', in +# the same style as the '.config' file. Except .myconfig has disabled +# options explicitly set to 'n' rather than just omitted. This is to +# make sure they override any corresponding options that may be turned on +# in the Kernel's config files. +# The .myconfig file is what will be included in the v4l-dvb Makefile +# to control which drivers are built. + +my %config = (); +my %allconfig = (); + +open IN,".config"; +while () { + if (m/\s*(\w+)=\s*(\S*)/) { +#printf "%s=%s\n",$1,$2; + $config { $1 } = $2; + } +} +close IN; + +# Build table of _all_ bool and tristate config variables +my $key = 0; +open IN,"Kconfig"; +while () { + if (/^config\s+(\w+)\s*$/) { + $key == 0 or die "Couldn't find type of config '$key'"; + $key = "CONFIG_$1"; + } elsif (/^\s+bool(ean)?\s/) { + $allconfig{$key} = 'bool'; + $key = 0; + } elsif (/^\s+tristate\s/) { + $allconfig{$key} = 'tristate'; + $key = 0; + } elsif (/^\s+(int|hex|string)\s/) { + $allconfig{$key} = 'data'; + $key = 0; + } +} +close IN; + +exists $allconfig{0} and die "Unable to correctly parse Kconfig file"; + +# Produce output for including in a Makefile +# Explicitly set bool/tri options that didn't appear in .config to n +# 'data' options are only output if they appeared in .config +open OUT,">.myconfig"; +while ( my ($key, $value) = each(%allconfig) ) { + if ($value eq 'data') { + next unless (exists $config{$key}); + $value = $config{$key}; + } else { + $value = exists $config{$key} ? $config{$key} : 'n'; + } + printf OUT "%-44s := %s\n",$key,$value; +} +close OUT; diff --git a/v4l/scripts/make_noconfig.pl b/v4l/scripts/make_noconfig.pl deleted file mode 100755 index 7323f419c..000000000 --- a/v4l/scripts/make_noconfig.pl +++ /dev/null @@ -1,58 +0,0 @@ -#!/usr/bin/perl - -# The purpose of this script is to produce a file named '.myconfig', in -# the same style as the '.config' file. Except .myconfig has disabled -# options explicitly set to 'n' rather than just omitted. This is to -# make sure they override any corresponding options that may be turned on -# in the Kernel's config files. -# The .myconfig file is what will be included in the v4l-dvb Makefile -# to control which drivers are built. - -my %config = (); -my %allconfig = (); - -open IN,".config"; -while () { - if (m/\s*(\w+)=\s*(\S*)/) { -#printf "%s=%s\n",$1,$2; - $config { $1 } = $2; - } -} -close IN; - -# Build table of _all_ bool and tristate config variables -my $key = 0; -open IN,"Kconfig"; -while () { - if (/^config\s+(\w+)\s*$/) { - $key == 0 or die "Couldn't find type of config '$key'"; - $key = "CONFIG_$1"; - } elsif (/^\s+bool(ean)?\s/) { - $allconfig{$key} = 'bool'; - $key = 0; - } elsif (/^\s+tristate\s/) { - $allconfig{$key} = 'tristate'; - $key = 0; - } elsif (/^\s+(int|hex|string)\s/) { - $allconfig{$key} = 'data'; - $key = 0; - } -} -close IN; - -exists $allconfig{0} and die "Unable to correctly parse Kconfig file"; - -# Produce output for including in a Makefile -# Explicitly set bool/tri options that didn't appear in .config to n -# 'data' options are only output if they appeared in .config -open OUT,">.myconfig"; -while ( my ($key, $value) = each(%allconfig) ) { - if ($value eq 'data') { - next unless (exists $config{$key}); - $value = $config{$key}; - } else { - $value = exists $config{$key} ? $config{$key} : 'n'; - } - printf OUT "%-44s := %s\n",$key,$value; -} -close OUT; -- cgit v1.2.3 From 6cfc8eeff6261fb1153a67e5bc3c71616f332044 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 21 Jun 2006 12:23:13 -0300 Subject: Some improvements at the building system From: Mauro Carvalho Chehab Building system now looks kernel config.h and autoconf.h files, seeking for the compiled options at kernel. If something is missing, it will disable compilation for that driver, printing a warning message. Signed-off-by: Mauro Carvalho Chehab --- v4l/Makefile | 33 +++++----- v4l/scripts/make_kconfig.pl | 152 +++++++++++++++++++++++++++++++++++++++---- v4l/scripts/make_makefile.pl | 3 +- v4l/versions.txt | 8 +-- 4 files changed, 162 insertions(+), 34 deletions(-) diff --git a/v4l/Makefile b/v4l/Makefile index 58354a035..881329d7d 100644 --- a/v4l/Makefile +++ b/v4l/Makefile @@ -17,7 +17,12 @@ else ifneq ($(SRCDIR),) KDIR := $(SRCDIR) else +ifneq ($(KERNELRELEASE),) KDIR := /lib/modules/$(KERNELRELEASE)/build +else +KDIR := /lib/modules/$(shell uname -r|perl -ne 'if (/^([0-9]*)\.([0-9])*\.([0-9]*)(.*)$$/) { printf ("%s.%s.%s%s\n",$$1,$$2,$$3,$$4); };')/build + +endif endif endif @@ -133,9 +138,6 @@ remove rminstall:: media-rminstall ivtv-rminstall ################################################# # Compiling preparation rules -Makefile.media:: .version - scripts/make_makefile.pl - .version:: ifneq ($(KERNELRELEASE),) @echo -e VERSION=$(VERSION)\\nPATCHLEVEL:=$(PATCHLEVEL)\\nSUBLEVEL:=$(SUBLEVEL)\\nKERNELRELEASE:=$(KERNELRELEASE) > $(obj)/.version @@ -147,6 +149,9 @@ else @uname -r|perl -ne 'if (/^([0-9]*)\.([0-9])*\.([0-9]*)(.*)$$/) { printf ("VERSION=%s\nPATCHLEVEL:=%s\nSUBLEVEL:=%s\nKERNELRELEASE:=%s.%s.%s%s\n",$$1,$$2,$$3,$$1,$$2,$$3,$$4); };' > $(obj)/.version endif +Makefile.media:: .version + scripts/make_makefile.pl $(KDIR) + release:: ifneq ($(VER),) @echo "Forcing compiling to version $(VER)." @@ -180,9 +185,7 @@ links:: @find ../linux/drivers/media -name '*.[ch]' -type f -exec ln -sf '{}' . \; @find ../linux/sound -name '*.[ch]' -type f -exec ln -sf '{}' . \; -config-compat.h:: - scripts/make_myconfig.pl - +config-compat.h:: .myconfig @echo \#ifndef __CONFIG_COMPAT_H__ > config-compat.h @echo \#define __CONFIG_COMPAT_H__ >> config-compat.h @echo >> config-compat.h @@ -253,29 +256,27 @@ LXDIALOG_DIR := $(shell if [ -d $(KDIR)/scripts/kconfig/lxdialog ]; then echo kc LXDIALOG_LNK := $(if $(LXDIALOG_DIR),scripts/kconfig,scripts/lxdialog) LXDIALOG := $(KDIR)/scripts/$(LXDIALOG_DIR)lxdialog/lxdialog +.myconfig : .config + ./scripts/make_myconfig.pl + xconfig:: links .version $(QCONF) - ./scripts/make_kconfig.pl + ./scripts/make_kconfig.pl $(KDIR) $(QCONF) Kconfig - ./scripts/make_myconfig.pl gconfig:: links .version $(GCONF) - ./scripts/make_kconfig.pl + ./scripts/make_kconfig.pl $(KDIR) $(QCONF) Kconfig - ./scripts/make_myconfig.pl config:: links .version $(CONF) - ./scripts/make_kconfig.pl + ./scripts/make_kconfig.pl $(KDIR) $(CONF) Kconfig - ./scripts/make_myconfig.pl menuconfig:: links .version $(MCONF) lxdialog - ./scripts/make_kconfig.pl + ./scripts/make_kconfig.pl $(KDIR) $(MCONF) Kconfig - ./scripts/make_myconfig.pl allyesconfig allmodconfig:: links .version - ./scripts/make_kconfig.pl 1 - ./scripts/make_myconfig.pl + ./scripts/make_kconfig.pl $(KDIR) 1 # rule to build kernel conf programs KMAKEVARS := config-targets=1 mixed-targets=0 dot-config=0 diff --git a/v4l/scripts/make_kconfig.pl b/v4l/scripts/make_kconfig.pl index b499fefa1..33a53d772 100755 --- a/v4l/scripts/make_kconfig.pl +++ b/v4l/scripts/make_kconfig.pl @@ -7,10 +7,69 @@ my %config = (); my %intopt = (); my %hexopt = (); my %tristate = (); +my %kernopts = (); +my %depmods = (); my $version, $level, $sublevel; +my $kernel=shift; my $force_kconfig=shift; +#!/usr/bin/perl +use FileHandle; + +########################################################### +# Checks config.h and autoconf.h for current kernel defines +sub process_config ($) +{ + my $filename = shift; + my $in = new FileHandle; + + open $in,"$kernel/include/$filename" or die; + while (<$in>) { + if (m|\#include\s+\<(.*)\>|) { + process_config ($1); + next; + } + if (m/\#define\s+CONFIG_([^ ]*)_ON_SMP\s+(.*)\n/) { + my $key=$1; + my $value=$2; +# printf "defined $key as $value\n"; + if ( $value == 1 ) { + $value='y'; + } + $kernopts{$key}=$value; + next; + } + if (m/\#define\s+CONFIG_([^ ]*)_MODULE\s+(.*)\n/) { + my $key=$1; + my $value=$2; +# printf "defined $key as $value\n"; + if ( $value == 1 ) { + $value='m'; + } + $kernopts{$key}=$value; + next; + } + if (m/\#define\s+CONFIG_([^ ]*)\s+(.*)\n/) { + my $key=$1; + my $value=$2; +# printf "defined $key as $value\n"; + if ( $value == 1 ) { + $value='y'; + } + $kernopts{$key}=$value; + next; + } + if (m/\#undef\s+CONFIG_([^ ]*)\n/) { +# printf "undefined $1\n"; + $kernopts{$1}='n'; + next; + } + } + + close $in; +} + sub add_bool($) { my $arg=shift; @@ -18,6 +77,8 @@ sub add_bool($) exists $config{$arg} or die "Adding unknown boolean '$arg'"; $tristate{$arg}="bool"; # printf "Boolean:%s\n",$arg; + + $kernopts{$arg}='y'; } sub add_tristate($) @@ -26,7 +87,8 @@ sub add_tristate($) exists $config{$arg} or die "Adding unknown tristate '$arg'"; $tristate{$arg}="tristate"; -# printf "Tristate:%s\n",$arg; + + $kernopts{$arg}='m'; } sub add_int($) @@ -75,6 +137,7 @@ sub add_config($) } } +######################################## # Turn option off, iff it already exists sub disable_config($) { @@ -83,9 +146,14 @@ sub disable_config($) $config{$key} = 0 if (exists $config{$key}); } -sub check_deps($) +################################################################# +# Make a list of dependencies and the number of references for it +sub check_deps($$) { + my $key=shift; my $arg=shift; + + $depmods{$key}=$arg; $arg=$arg." "; while ($arg ne "") { @@ -96,6 +164,44 @@ sub check_deps($) } $arg =~ s/^[^ ]+ //; } + + return $ok; +} + +###################################################### +# Checks if all dependencies for the key are satisfied +sub deps_ok($) +{ + my $key=shift; + my $arg=$depmods{$key}; + my $ok=1; + + if ($arg eq "") { + return $ok; + } + + $arg=$arg." "; + + +# printf "$key: deps are '$arg'\n"; + + while ($arg ne "") { + if ($arg =~ m/^([A-Z0-9_]+) /) { + if ((! exists $kernopts {$1}) || ($kernopts {$1} eq 'n')) { + printf "$key: Required kernel opt '$1' is not present\n"; + $ok=0; + } + } + if ($arg =~ m/^\!([A-Z0-9_]+) /) { + if ($kernopts {$1} eq 'y') { + printf "$key: Driver is incompatible with '$1'\n"; + $ok=0; + } + } + $arg =~ s/^[^ ]+ //; + } + + return $ok; } sub open_kconfig($$) { @@ -105,7 +211,7 @@ sub open_kconfig($$) { my $key; #print "opening $file\n"; - open $in,"$file"; + open $in,"$file" or die; while (<$in>) { # if (m;^\s*source[\s\"]+drivers/media/(video|dvb)/Kconfig;) { # next; @@ -124,10 +230,10 @@ sub open_kconfig($$) { next; } if (m|^\s+depends on\s+(.*)\n|) { - check_deps ($1); + check_deps ($key,$1); } if (m|^\s+select\s+(.*)\n|) { - check_deps ($1); + check_deps ($key,$1); } if (m|^\s+bool(ean)?\s|) { add_bool($key); @@ -155,7 +261,6 @@ sub open_kconfig($$) { $default_seen = 1; $_ = "\tdefault n\n"; } - # check for end of config definition for disabled drivers # we need to make sure we've disabled it, and add a bit # to the help text @@ -211,7 +316,7 @@ sub parse_versions () my $in = new FileHandle; my $ver; - open $in,"versions.txt"; + open $in,"versions.txt" or die; while (<$in>) { if (m/\[([\d.]*)\]/) { $ver=$1; @@ -226,9 +331,11 @@ sub parse_versions () close $in; } +process_config("linux/config.h"); + parse_versions; -open IN,".version"; +open IN,".version" or die; while () { if (m/KERNELRELEASE\s*[:]*[=]+\s*(\d+)\.(\d+)\.(\d+)/) { $version=$1; @@ -240,7 +347,7 @@ close IN; printf "Preparing to compile for kernel version %d.%d.%d\n",$version,$level,$sublevel; -open OUT,">Kconfig"; +open OUT,">Kconfig" or die; print OUT <<"EOF"; mainmenu "V4L/DVB menu" @@ -273,14 +380,19 @@ while ( my ($key, $value) = each(%config) ) { delete $depend{$key}; } -open OUT,">Kconfig.kern"; +open OUT,">Kconfig.kern" or die; print OUT "config MODULES\n\tboolean\n\tdefault y\n\n"; add_config('MODULES'); add_bool('MODULES'); while ( my ($key, $value) = each(%depend) ) { - print OUT "# $key with $value refs\nconfig $key\n\ttristate\n\tdefault m\n\n"; + if ($kernopts{$key}) { + print OUT "# $key with $value refs\nconfig $key\n\ttristate\n\tdefault ". + $kernopts{$key}."\n\n"; + } else { + print OUT "# $key with $value refs\nconfig $key\n\ttristate\n\tdefault n #not found\n\n"; + } } close OUT; @@ -290,10 +402,24 @@ disable_config('DVB_CINERGYT2_TUNING'); # Produce a .config file if it's forced or one doesn't already exist if (($force_kconfig eq 1) || !open IN,".config") { - open OUT,">.config"; + open OUT,">.config" or die; while ( my ($key,$value) = each(%tristate) ) { if (!$config{$key}) { - print OUT "CONFIG_$key=n\n"; + print OUT "# CONFIG_$key is not set\n"; + } elsif ($kernopts{$key}) { + my $ok=deps_ok($key); + + # If deps are not ok, mark default as n + if (!$ok) { +# print "$key disabled due to missing kernel required prereq\n"; + $kernopts{$key}='n'; + } + + if ($kernopts{$key} eq 'n') { + print OUT "# CONFIG_$key is not set\n"; + } else { + print OUT "CONFIG_$key=".$kernopts{$key}."\n"; + } } elsif ($value eq 'tristate') { print OUT "CONFIG_$key=m\n"; } else { # must be 'bool' diff --git a/v4l/scripts/make_makefile.pl b/v4l/scripts/make_makefile.pl index f0d9aef7f..e0a099e9b 100755 --- a/v4l/scripts/make_makefile.pl +++ b/v4l/scripts/make_makefile.pl @@ -1,6 +1,7 @@ #!/usr/bin/perl use FileHandle; +my $kernel=shift; my $instdir = (); sub check_line($$$) @@ -181,5 +182,5 @@ if (open IN,"Makefile.media") { if (open IN,".myconfig") { close IN; } else { - system "./scripts/make_kconfig.pl 1"; + system "./scripts/make_kconfig.pl $kernel 1"; } diff --git a/v4l/versions.txt b/v4l/versions.txt index 35cb44fc6..6da410612 100644 --- a/v4l/versions.txt +++ b/v4l/versions.txt @@ -6,10 +6,6 @@ VIDEO_ZR36120 # This is also marked as broken VIDEO_PLANB -# Those are architecture-dependent -VIDEO_VINO -VIDEO_M32R_AR_M64278 - [2.6.16] VIDEO_USBVIDEO USB_VICAM @@ -23,6 +19,10 @@ USB_ZC0301 VIDEO_ZORAN_AVS6EYES VIDEO_TLV320AIC23B +# Those are architecture-dependent +VIDEO_VINO +VIDEO_M32R_AR_M64278 + [2.6.14] VIDEO_ZORAN VIDEO_ZORAN_BUZ -- cgit v1.2.3 From 498a9414b7297324bcf449471e2962250bc507e4 Mon Sep 17 00:00:00 2001 From: Michael Krufky Date: Wed, 21 Jun 2006 15:04:33 -0400 Subject: cx88: add support for FusionHDTV 3 Gold (original revision) From: Michael Krufky Add support for FusionHDTV 3 Gold (original revision), using the card definition for FusionHDTV3 Gold-Q Signed-off-by: Michael Krufky --- linux/Documentation/video4linux/CARDLIST.cx88 | 2 +- linux/drivers/media/video/cx88/cx88-cards.c | 4 ++++ 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/linux/Documentation/video4linux/CARDLIST.cx88 b/linux/Documentation/video4linux/CARDLIST.cx88 index 19a0a6a46..6cb63ddf6 100644 --- a/linux/Documentation/video4linux/CARDLIST.cx88 +++ b/linux/Documentation/video4linux/CARDLIST.cx88 @@ -15,7 +15,7 @@ 14 -> KWorld/VStream XPert DVB-T [17de:08a6] 15 -> DViCO FusionHDTV DVB-T1 [18ac:db00] 16 -> KWorld LTV883RF - 17 -> DViCO FusionHDTV 3 Gold-Q [18ac:d810] + 17 -> DViCO FusionHDTV 3 Gold-Q [18ac:d810,18ac:d800] 18 -> Hauppauge Nova-T DVB-T [0070:9002,0070:9001] 19 -> Conexant DVB-T reference design [14f1:0187] 20 -> Provideo PV259 [1540:2580] diff --git a/linux/drivers/media/video/cx88/cx88-cards.c b/linux/drivers/media/video/cx88/cx88-cards.c index 5431d591e..9de27a929 100644 --- a/linux/drivers/media/video/cx88/cx88-cards.c +++ b/linux/drivers/media/video/cx88/cx88-cards.c @@ -1468,6 +1468,10 @@ struct cx88_subid cx88_subids[] = { .subvendor = 0x107d, .subdevice = 0x665e, .card = CX88_BOARD_WINFAST_DTV2000H, + },{ + .subvendor = 0x18ac, + .subdevice = 0xd800, /* FusionHDTV 3 Gold (original revision) */ + .card = CX88_BOARD_DVICO_FUSIONHDTV_3_GOLD_Q, }, }; const unsigned int cx88_idcount = ARRAY_SIZE(cx88_subids); -- cgit v1.2.3 From e7a1d090b86f3e99145a255967b4d49cbaf36087 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 21 Jun 2006 16:30:43 -0300 Subject: Option disabling should be recursive. Fixing it. From: Mauro Carvalho Chehab Signed-off-by: Mauro Carvalho Chehab --- v4l/scripts/make_kconfig.pl | 21 +++++++++++++-------- 1 file changed, 13 insertions(+), 8 deletions(-) diff --git a/v4l/scripts/make_kconfig.pl b/v4l/scripts/make_kconfig.pl index 33a53d772..5f8866220 100755 --- a/v4l/scripts/make_kconfig.pl +++ b/v4l/scripts/make_kconfig.pl @@ -400,6 +400,19 @@ close OUT; disable_config('DVB_AV7110_FIRMWARE'); disable_config('DVB_CINERGYT2_TUNING'); +my $i; +do { + $i=0; + while ( my ($key,$value) = each(%kernopts) ) { + if ($value ne 'n') { + if (!deps_ok($key)) { + $kernopts{$key}='n'; + } + $i=$i+1; + } + } +} until (!$disable); + # Produce a .config file if it's forced or one doesn't already exist if (($force_kconfig eq 1) || !open IN,".config") { open OUT,">.config" or die; @@ -407,14 +420,6 @@ if (($force_kconfig eq 1) || !open IN,".config") { if (!$config{$key}) { print OUT "# CONFIG_$key is not set\n"; } elsif ($kernopts{$key}) { - my $ok=deps_ok($key); - - # If deps are not ok, mark default as n - if (!$ok) { -# print "$key disabled due to missing kernel required prereq\n"; - $kernopts{$key}='n'; - } - if ($kernopts{$key} eq 'n') { print OUT "# CONFIG_$key is not set\n"; } else { -- cgit v1.2.3 From ba915ac86439f7c2e134346710e2c95835fa8b68 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 21 Jun 2006 16:31:24 -0300 Subject: Some cleanups at the release script From: Mauro Carvalho Chehab Signed-off-by: Mauro Carvalho Chehab --- v4l/Makefile | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-) diff --git a/v4l/Makefile b/v4l/Makefile index 881329d7d..a034be061 100644 --- a/v4l/Makefile +++ b/v4l/Makefile @@ -158,12 +158,13 @@ ifneq ($(VER),) @echo $(VER)|perl -ne 'if (/^([0-9]*)\.([0-9])*\.([0-9]*)(.*)$$/) { printf ("VERSION=%s\nPATCHLEVEL:=%s\nSUBLEVEL:=%s\nKERNELRELEASE:=%s.%s.%s%s\n",$$1,$$2,$$3,$$1,$$2,$$3,$$4); };' > $(obj)/.version else ifneq ($(DIR),) - @perl -e 'open IN,"<$(DIR)/Makefile"; \ + @echo "Seeking for a version at $(DIR)/Makefile." + @perl -e 'open IN,"$(DIR)/Makefile"; \ while () { \ - if (/^VERSION\s*=\s*([0-9]+)/){ $$version=$$1; next; }\ - if (/^PATCHLEVEL\s*=\s*([0-9]+)/){ $$level=$$1; next; }\ - if (/^SUBLEVEL\s*=\s*([0-9]+)/){ $$sublevel=$$1; next; }\ - if (/^EXTRAVERSION\s*=\s*([^\s]+)\n/){ $$extra=$$1; next; }\ + if (/^VERSION\s*=\s*([0-9]+)/){ $$version=$$1; }\ + elsif (/^PATCHLEVEL\s*=\s*([0-9]+)/){ $$level=$$1; }\ + elsif (/^SUBLEVEL\s*=\s*([0-9]+)/){ $$sublevel=$$1; }\ + elsif (/^EXTRAVERSION\s*=\s*([^\s]+)\n/){ $$extra=$$1; }\ }; \ printf ("VERSION=%s\nPATCHLEVEL:=%s\nSUBLEVEL:=%s\nKERNELRELEASE:=%s.%s.%s%s\n", \ $$version,$$level,$$sublevel,$$version,$$level,$$sublevel,$$extra); \ -- cgit v1.2.3 From c3c161df40114ed8f7c0a3bebd385c173919de18 Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Wed, 21 Jun 2006 22:04:13 +0200 Subject: CX2341X port was always set to 'memory', but 'streaming' is also possible From: Hans Verkuil ivtv uses the memory (DMA) interface with the CX2341X, while pvrusb2 and cx88-blackbird use the streaming interface. This setting is now selectable by the driver. Signed-off-by: Hans Verkuil --- linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt | 8 +++++++- linux/drivers/media/video/cx2341x.c | 3 ++- linux/drivers/media/video/cx88/cx88-blackbird.c | 1 + linux/include/media/cx2341x.h | 7 +++++++ 4 files changed, 17 insertions(+), 2 deletions(-) diff --git a/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt b/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt index 58c7243d0..9834b4c76 100644 --- a/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt +++ b/linux/Documentation/video4linux/cx2341x/fw-encoder-api.txt @@ -270,11 +270,17 @@ Param[0] Name CX2341X_ENC_SET_OUTPUT_PORT Enum 187/0xBB Description - Assign stream output port (not recommended you change setting from default) + Assign stream output port. Normally 0 when the data is copied through + the PCI bus (DMA), and 1 when the data is streamed to another chip + (pvrusb and cx88-blackbird). Param[0] 0=Memory (default) 1=Streaming 2=Serial +Param[1] + Unknown, but leaving this to 0 seems to work best. Indications are that + this might have to do with USB support, although passing anything but 0 + onl breaks things. ------------------------------------------------------------------------------- diff --git a/linux/drivers/media/video/cx2341x.c b/linux/drivers/media/video/cx2341x.c index 33e955f7c..29a5c8e5c 100644 --- a/linux/drivers/media/video/cx2341x.c +++ b/linux/drivers/media/video/cx2341x.c @@ -643,6 +643,7 @@ void cx2341x_fill_defaults(struct cx2341x_mpeg_params *p) { static struct cx2341x_mpeg_params default_params = { /* misc */ + .port = CX2341X_PORT_MEMORY, .width = 720, .height = 480, .is_50hz = 0, @@ -718,7 +719,7 @@ int cx2341x_update(void *priv, cx2341x_mbox_func func, int err = 0; - cx2341x_api(priv, func, CX2341X_ENC_SET_OUTPUT_PORT, 1, 0); /* 0 = Memory */ + cx2341x_api(priv, func, CX2341X_ENC_SET_OUTPUT_PORT, 2, new->port, 0); if (old == NULL || old->is_50hz != new->is_50hz) { err = cx2341x_api(priv, func, CX2341X_ENC_SET_FRAME_RATE, 1, new->is_50hz); diff --git a/linux/drivers/media/video/cx88/cx88-blackbird.c b/linux/drivers/media/video/cx88/cx88-blackbird.c index 1a86d337f..d6d19a71e 100644 --- a/linux/drivers/media/video/cx88/cx88-blackbird.c +++ b/linux/drivers/media/video/cx88/cx88-blackbird.c @@ -1076,6 +1076,7 @@ static int __devinit blackbird_probe(struct pci_dev *pci_dev, dev->width = 720; dev->height = 576; cx2341x_fill_defaults(&dev->params); + dev->params.port = CX2341X_PORT_STREAMING; switch (core->board) { case CX88_BOARD_HAUPPAUGE_ROSLYN: diff --git a/linux/include/media/cx2341x.h b/linux/include/media/cx2341x.h index 0c9292fa5..fb170d4b5 100644 --- a/linux/include/media/cx2341x.h +++ b/linux/include/media/cx2341x.h @@ -19,8 +19,15 @@ #ifndef CX2341X_H #define CX2341X_H +enum cx2341x_port { + CX2341X_PORT_MEMORY, + CX2341X_PORT_STREAMING, + CX2341X_PORT_SERIAL +}; + struct cx2341x_mpeg_params { /* misc */ + enum cx2341x_port port; u16 width; u16 height; u16 is_50hz; -- cgit v1.2.3 From 6ed34e3a513dd73f39d804e9416524bf5eb54be6 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Wed, 21 Jun 2006 19:07:45 -0300 Subject: building system fix: miropcm20 depends on sound/oss/aci.h From: Mauro Carvalho Chehab Most V4L/DVB hg tree users are just compiling using kernel headers. This is bad, due to: 1) the lack of support for make *config 2) the kernel itself have unknown patches from the distros Anyway, it is useful to provide they some support. This patch provides a "hack" for such users, by checking if the sound/oss/aci.h file is present under kernel tree. If not, it will disable miropcm20 and print a warning about the usage of a kernel-headers only package. Signed-off-by: Mauro Carvalho Chehab --- v4l/scripts/make_kconfig.pl | 14 ++++++++++++++ 1 file changed, 14 insertions(+) diff --git a/v4l/scripts/make_kconfig.pl b/v4l/scripts/make_kconfig.pl index 5f8866220..807fea2e6 100755 --- a/v4l/scripts/make_kconfig.pl +++ b/v4l/scripts/make_kconfig.pl @@ -400,6 +400,20 @@ close OUT; disable_config('DVB_AV7110_FIRMWARE'); disable_config('DVB_CINERGYT2_TUNING'); +# Hack for check sound/oss/aci.h header + +my $mirodep="$kernel/sound/oss/aci.h"; +if (!open IN, $mirodep) { + my $key="RADIO_MIROPCM20"; + printf "$key: $mirodep is missing.\n"; + printf "It seems that you are using a kernel-headers only package\n"; + printf "kernel-headers only won't provide you make menuconfig/xconfig/qconfig\n"; + + $kernopts{$key}='n'; +} +close IN; + +# Recursively check for broken dependencies my $i; do { $i=0; -- cgit v1.2.3 From 443a49ca134a2691307741a3f7e4744f52d1eb49 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Thu, 22 Jun 2006 11:08:17 -0300 Subject: The new POSIX backslash behavior on GNU make 3.81 breaks make release From: Mauro Carvalho Chehab On make 3.81, backslash isn't removed anymore when inside of a single quotted string. This makes make release to fail, since perl won't understand the backslash. This patch just make all script into one line. Bad to understand, but, at least, it will work fine with both GNU make 3.80 and make 3.81. Signed-off-by: Mauro Carvalho Chehab --- v4l/Makefile | 12 +----------- 1 file changed, 1 insertion(+), 11 deletions(-) diff --git a/v4l/Makefile b/v4l/Makefile index a034be061..0e90e13d8 100644 --- a/v4l/Makefile +++ b/v4l/Makefile @@ -159,22 +159,12 @@ ifneq ($(VER),) else ifneq ($(DIR),) @echo "Seeking for a version at $(DIR)/Makefile." - @perl -e 'open IN,"$(DIR)/Makefile"; \ - while () { \ - if (/^VERSION\s*=\s*([0-9]+)/){ $$version=$$1; }\ - elsif (/^PATCHLEVEL\s*=\s*([0-9]+)/){ $$level=$$1; }\ - elsif (/^SUBLEVEL\s*=\s*([0-9]+)/){ $$sublevel=$$1; }\ - elsif (/^EXTRAVERSION\s*=\s*([^\s]+)\n/){ $$extra=$$1; }\ - }; \ - printf ("VERSION=%s\nPATCHLEVEL:=%s\nSUBLEVEL:=%s\nKERNELRELEASE:=%s.%s.%s%s\n", \ - $$version,$$level,$$sublevel,$$version,$$level,$$sublevel,$$extra); \ - printf ("SRCDIR:=$(DIR)\n");' > $(obj)/.version + @perl -e 'open IN,"$(DIR)/Makefile"; while () { if (/^VERSION\s*=\s*([0-9]+)/){ $$version=$$1; } elsif (/^PATCHLEVEL\s*=\s*([0-9]+)/){ $$level=$$1; } elsif (/^SUBLEVEL\s*=\s*([0-9]+)/){ $$sublevel=$$1; } elsif (/^EXTRAVERSION\s*=\s*([^\s]+)\n/){ $$extra=$$1; } }; printf ("VERSION=%s\nPATCHLEVEL:=%s\nSUBLEVEL:=%s\nKERNELRELEASE:=%s.%s.%s%s\n", $$version,$$level,$$sublevel,$$version,$$level,$$sublevel,$$extra); printf ("SRCDIR:=$(DIR)\n");' > $(obj)/.version @cat .version|grep KERNELRELEASE:|sed s,'KERNELRELEASE:=','Forcing compiling to version ', @if [ ! -f $(DIR)/scripts/kallsyms ]; then \ echo "*** Warning: You should configure and build kernel before compiling V4L"; \ fi - else @echo "No version specified. Using `uname -r`." @uname -r|perl -ne 'if (/^([0-9]*)\.([0-9])*\.([0-9]*)(.*)$$/) { printf ("VERSION=%s\nPATCHLEVEL:=%s\nSUBLEVEL:=%s\nKERNELRELEASE:=%s.%s.%s%s\n",$$1,$$2,$$3,$$1,$$2,$$3,$$4); };' > $(obj)/.version -- cgit v1.2.3 From 78d2d7a1fea8c058e3ffa9dae7b6f96c3491a7ac Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Thu, 22 Jun 2006 11:47:13 -0300 Subject: Adjust filenames in the strip whitespace script output From: Trent Piepho Before: --- Makefile +++ - 2006-06-20 22:16:36.320564000 -0700 Now: --- Makefile +++ Makefile patch handles both correctly, but diffstat will use the "+++" filename rather than the "---" filename, making diffstat output rather useless. Signed-off-by: Trent Piepho Signed-off-by: Mauro Carvalho Chehab --- v4l/scripts/strip-trailing-whitespaces.sh | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/v4l/scripts/strip-trailing-whitespaces.sh b/v4l/scripts/strip-trailing-whitespaces.sh index 5bd7784e4..a546a0b9f 100755 --- a/v4l/scripts/strip-trailing-whitespaces.sh +++ b/v4l/scripts/strip-trailing-whitespaces.sh @@ -23,5 +23,6 @@ for file in `eval $files`; do s<^ {8}> <\t>; s<^ {1,7}\t> <\t>; while( s<\t {8}> <\t\t>g || s<\t {1,7}\t> <\t\t>g ) {}; - print' < "${file}" | diff -u "${file}" - + print' < "${file}" | \ + diff -u --label="$file" "$file" --label="$file" - done -- cgit v1.2.3 From 9a9c8e49eea524960d5fbead3d5794a0bd936500 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Thu, 22 Jun 2006 11:51:24 -0300 Subject: Have the commit auto-check code tell you when it does something From: Trent Piepho When the make commit checks for whitespace errors, it will save a copy of the changes it makes to $(TMP)/v4l_hg_whitespace. The prep_commit_msg.pl script will look for this file and include a note in the prepared commit message with diffstat output. The changes that scripts/cardlist might make are not included, but that can be added later. The prep_commit_msg.pl script is effectively totally re-written. This one will try some extra stuff to some up with the user's e-mail, such as looking in the ~/.hgrc file. The Makefile is changed so that temporary files created by make commit and make whitespace will honor the $TMP environment variable, if set. Signed-off-by: Trent Piepho Signed-off-by: Mauro Carvalho Chehab --- Makefile | 12 ++++--- v4l/scripts/prep_commit_msg.pl | 73 ++++++++++++++++++++++++++++-------------- 2 files changed, 56 insertions(+), 29 deletions(-) diff --git a/Makefile b/Makefile index 42c22f72a..9d6f7c3e7 100644 --- a/Makefile +++ b/Makefile @@ -1,4 +1,5 @@ BUILD_DIR := $(shell pwd)/v4l +TMP ?= /tmp REPO_PULL := http://linuxtv.org/hg/v4l-dvb ifeq ($(REPO_PUSH),) ifneq ($(CHANGE_LOG_LOGIN),) @@ -26,9 +27,10 @@ install: commit cvscommit hgcommit change changes changelog:: whitespace cd $(BUILD_DIR); scripts/cardlist; cd .. - v4l/scripts/prep_commit_msg.pl >/tmp/v4l_hg_commit.msg - $(EDITOR) /tmp/v4l_hg_commit.msg - grep -v ^# /tmp/v4l_hg_commit.msg | hg commit -l - + v4l/scripts/prep_commit_msg.pl $(TMP)/v4l_hg_whitespace > \ + $(TMP)/v4l_hg_commit.msg + $(EDITOR) $(TMP)/v4l_hg_commit.msg + grep -v '^#' $(TMP)/v4l_hg_commit.msg | hg commit -l - @echo "*** PLEASE CHECK IF LOG IS OK:" @hg log -v -r -1 @echo "*** If not ok, do hg undo and make commit again" @@ -43,5 +45,5 @@ push:: whitespace: @echo "Cleaning bad whitespaces" - @v4l/scripts/strip-trailing-whitespaces.sh fast | patch -p0 - + @v4l/scripts/strip-trailing-whitespaces.sh fast | \ + tee $(TMP)/v4l_hg_whitespace | patch -p0 diff --git a/v4l/scripts/prep_commit_msg.pl b/v4l/scripts/prep_commit_msg.pl index ac958667b..a4594c7f9 100755 --- a/v4l/scripts/prep_commit_msg.pl +++ b/v4l/scripts/prep_commit_msg.pl @@ -1,34 +1,59 @@ #!/usr/bin/perl -$f=shift; -open IN,"hg diff|diffstat -p1 |"; -my $n=2; -my $from=""; -my $first=""; -my $changed=""; -$out=""; -while () { - $changed="$changed#$_"; -} +my $autopatch = shift; +# Get Hg username from environment my $user = $ENV{HGUSER}; -if ( $user eq "" ) { +# Didn't work? Try the .hgrc file +if ($user eq "") { + open IN, "<$ENV{HOME}/.hgrc"; + while () { + if(/^\s*username\s*=\s*(\S.*)$/) { + $user = $1; + last; + } + } + close IN; +} + +# Still no luck? Try some other environment variables +if ($user eq "") { my $name = $ENV{CHANGE_LOG_NAME}; my $email = $ENV{CHANGE_LOG_EMAIL_ADDRESS}; + $user = "$name <$email>" if ($name ne "" || $email ne ""); +} + +# Last try to come up with something +if ($user eq "") { + $user = "$ENV{USER} <>"; +} - $user="$name <$email>"; +print "# Added/removed/changed files:\n"; +system "hg diff | diffstat -p1 -c"; +if (-s $autopatch) { + print "#\n# Note, a problem with your patch was detected! These changes were made\n"; + print "# automatically: $autopatch\n"; + system "diffstat -p0 -c $autopatch"; + print "#\n# Please review these changes and see if they belong in your patch or not.\n"; } +print <<"EOF"; +# +# For better log display, please keep a blank line after subject, after from, +# and before signed-off-by. +# First line should be the subject, without Subject: +# + + +# Now, patch author (just the main one), on a From: field +# Please change below if the committer is not the patch author. +# +From: $user + +# Then a detailed description: + -$first= "# Please change below if you are not patch author\n#\nFrom: $user"; -$out= "# At the end Signed-off-by: fields by patch author and committer, at least\n#\nSigned-off-by: $user"; -$from= "From: $user"; - -printf "#Added/removed/changed files:\n%s#\n" . - "# For better log display, please keep a blank line after subject, after from\n" . - "# and before signed-off-by\n" . - "# First line should be the subject, without Subject:\n#\n\n\n" . - "# Now, patch author (just the main one), on a From: field\n" . - "# Please change below if the committer is not the patch author\n#\n%s\n\n" . - "# Then a detailed description:\n\n\n%s", - $changed,$from,$out; +# At the end Signed-off-by: fields by patch author and committer, at least. +# +Signed-off-by: $user +EOF -- cgit v1.2.3 From b00987276ad2c4bef7891591a6ca2081a7d1e1d4 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Thu, 22 Jun 2006 18:52:04 -0300 Subject: Improved message when only kernel headers are found From: Mauro Carvalho Chehab Signed-off-by: Mauro Carvalho Chehab --- v4l/scripts/make_kconfig.pl | 23 ++++++++++++++++++++--- 1 file changed, 20 insertions(+), 3 deletions(-) diff --git a/v4l/scripts/make_kconfig.pl b/v4l/scripts/make_kconfig.pl index 807fea2e6..c58f5b028 100755 --- a/v4l/scripts/make_kconfig.pl +++ b/v4l/scripts/make_kconfig.pl @@ -405,10 +405,27 @@ disable_config('DVB_CINERGYT2_TUNING'); my $mirodep="$kernel/sound/oss/aci.h"; if (!open IN, $mirodep) { my $key="RADIO_MIROPCM20"; - printf "$key: $mirodep is missing.\n"; - printf "It seems that you are using a kernel-headers only package\n"; - printf "kernel-headers only won't provide you make menuconfig/xconfig/qconfig\n"; +print <<"EOF2"; +$key: $mirodep is missing. +***WARNING:*** You do not have the full kernel sources installed. +This does not prevent you from building the v4l-dvb tree if you have the +kernel headers, but the full kernel source is required in order to use +make menuconfig / xconfig / qconfig. + +If you are experiencing problems building the v4l-dvb tree, please try +building against a vanilla kernel before reporting a bug. + +Vanilla kernels are available at http://kernel.org. +On most distros, this will compile a newly downloaded kernel: + +cp /boot/config-`uname -r` /.config +cd +make all modules_install install + +Please see your distro's web site for instructions to build a new kernel. + +EOF2 $kernopts{$key}='n'; } close IN; -- cgit v1.2.3 From c8e0ee905cdfe4183f753600fcbbfe3114df03d5 Mon Sep 17 00:00:00 2001 From: Michael Krufky Date: Thu, 22 Jun 2006 20:47:07 -0400 Subject: cx88-blackbird: always set encoder height based on tvnorm->id From: Michael Krufky Removed the switch..case block in blackbird_probe for setting encoder height based on video standard. All blackbird devices can rely on tvnorm->id to retrieve this information from the cx2388x video decoder - tuner_formats should not be used to determine the encoding video standard. Signed-off-by: Michael Krufky --- linux/drivers/media/video/cx88/cx88-blackbird.c | 19 ++++--------------- 1 file changed, 4 insertions(+), 15 deletions(-) diff --git a/linux/drivers/media/video/cx88/cx88-blackbird.c b/linux/drivers/media/video/cx88/cx88-blackbird.c index d6d19a71e..b85dfe85e 100644 --- a/linux/drivers/media/video/cx88/cx88-blackbird.c +++ b/linux/drivers/media/video/cx88/cx88-blackbird.c @@ -1078,21 +1078,10 @@ static int __devinit blackbird_probe(struct pci_dev *pci_dev, cx2341x_fill_defaults(&dev->params); dev->params.port = CX2341X_PORT_STREAMING; - switch (core->board) { - case CX88_BOARD_HAUPPAUGE_ROSLYN: - if (core->tuner_formats & V4L2_STD_525_60) { - dev->height = 480; - } else { - dev->height = 576; - } - break; - case CX88_BOARD_KWORLD_HARDWARE_MPEG_TV_XPERT: - if (core->tvnorm->id & V4L2_STD_525_60) { - dev->height = 480; - } else { - dev->height = 576; - } - break; + if (core->tvnorm->id & V4L2_STD_525_60) { + dev->height = 480; + } else { + dev->height = 576; } err = cx8802_init_common(dev); -- cgit v1.2.3 From d98d9ea5be4cd00ab3e3125637adab2be58bfe44 Mon Sep 17 00:00:00 2001 From: Michael Krufky Date: Thu, 22 Jun 2006 22:13:06 -0400 Subject: cx88: clear EN_I2SIN_ENABLE bit for ASUS PVR-416 to enable audio From: Michael Krufky clear EN_I2SIN_ENABLE bit for ASUS PVR-416 to enable audio streaming in both raw video and blackbird mpeg encoder modes. Signed-off-by: Michael Krufky --- linux/drivers/media/video/cx88/cx88-tvaudio.c | 1 + 1 file changed, 1 insertion(+) diff --git a/linux/drivers/media/video/cx88/cx88-tvaudio.c b/linux/drivers/media/video/cx88/cx88-tvaudio.c index e0eb173db..9a42e9a6b 100644 --- a/linux/drivers/media/video/cx88/cx88-tvaudio.c +++ b/linux/drivers/media/video/cx88/cx88-tvaudio.c @@ -157,6 +157,7 @@ static void set_audio_finish(struct cx88_core *core, u32 ctl) case CX88_BOARD_KWORLD_MCE200_DELUXE: case CX88_BOARD_KWORLD_HARDWARE_MPEG_TV_XPERT: case CX88_BOARD_PIXELVIEW_PLAYTV_P7000: + case CX88_BOARD_ASUS_PVR_416: cx_clear(AUD_CTL, EN_I2SIN_ENABLE); break; default: -- cgit v1.2.3 From f2efbf913f2cb04d30a696d3bccaa7320f2a34d1 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Fri, 23 Jun 2006 06:42:44 -0300 Subject: drivers/media/video/vivi.c: make 2 functions static From: Adrian Bunk Make two needlessly global functions static. Signed-off-by: Adrian Bunk Signed-off-by: Andrew Morton Signed-off-by: Mauro Carvalho Chehab --- linux/drivers/media/video/vivi.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/linux/drivers/media/video/vivi.c b/linux/drivers/media/video/vivi.c index 5fd42153f..614cdc60e 100644 --- a/linux/drivers/media/video/vivi.c +++ b/linux/drivers/media/video/vivi.c @@ -1092,7 +1092,7 @@ static int vidiocgmbuf (struct file *file, void *priv, struct video_mbuf *mbuf) } #endif -int vidioc_streamon (struct file *file, void *priv, enum v4l2_buf_type i) +static int vidioc_streamon(struct file *file, void *priv, enum v4l2_buf_type i) { struct vivi_fh *fh=priv; struct vivi_dev *dev = fh->dev; @@ -1107,7 +1107,7 @@ int vidioc_streamon (struct file *file, void *priv, enum v4l2_buf_type i) return (videobuf_streamon(&fh->vb_vidq)); } -int vidioc_streamoff (struct file *file, void *priv, enum v4l2_buf_type i) +static int vidioc_streamoff(struct file *file, void *priv, enum v4l2_buf_type i) { struct vivi_fh *fh=priv; struct vivi_dev *dev = fh->dev; -- cgit v1.2.3 From 58bf3ce7ee0c87c3aa9055e19a886b470dd09d0f Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Fri, 23 Jun 2006 06:49:34 -0300 Subject: drivers/media/video/pwc/: make code static From: Adrian Bunk This patch makes the following needlessly global code static: - pwc-ctrl.c: pwc_get_leds() - pwc_preferred_compression Signed-off-by: Adrian Bunk Signed-off-by: Andrew Morton Signed-off-by: Mauro Carvalho Chehab --- linux/drivers/media/video/pwc/pwc-ctrl.c | 2 +- linux/drivers/media/video/pwc/pwc-if.c | 2 +- linux/drivers/media/video/pwc/pwc.h | 2 -- 3 files changed, 2 insertions(+), 4 deletions(-) diff --git a/linux/drivers/media/video/pwc/pwc-ctrl.c b/linux/drivers/media/video/pwc/pwc-ctrl.c index 0f25d4eac..acd8d4af1 100644 --- a/linux/drivers/media/video/pwc/pwc-ctrl.c +++ b/linux/drivers/media/video/pwc/pwc-ctrl.c @@ -925,7 +925,7 @@ int pwc_set_leds(struct pwc_device *pdev, int on_value, int off_value) return SendControlMsg(SET_STATUS_CTL, LED_FORMATTER, 2); } -int pwc_get_leds(struct pwc_device *pdev, int *on_value, int *off_value) +static int pwc_get_leds(struct pwc_device *pdev, int *on_value, int *off_value) { unsigned char buf[2]; int ret; diff --git a/linux/drivers/media/video/pwc/pwc-if.c b/linux/drivers/media/video/pwc/pwc-if.c index 844b7fcfb..a241a3060 100644 --- a/linux/drivers/media/video/pwc/pwc-if.c +++ b/linux/drivers/media/video/pwc/pwc-if.c @@ -133,7 +133,7 @@ static int default_fbufs = 3; /* Default number of frame buffers */ #endif static int power_save = 0; static int led_on = 100, led_off = 0; /* defaults to LED that is on while in use */ - int pwc_preferred_compression = 1; /* 0..3 = uncompressed..high */ +static int pwc_preferred_compression = 1; /* 0..3 = uncompressed..high */ static struct { int type; char serial_number[30]; diff --git a/linux/drivers/media/video/pwc/pwc.h b/linux/drivers/media/video/pwc/pwc.h index a087108d0..629f79e44 100644 --- a/linux/drivers/media/video/pwc/pwc.h +++ b/linux/drivers/media/video/pwc/pwc.h @@ -274,7 +274,6 @@ extern "C" { #if CONFIG_PWC_DEBUG extern int pwc_trace; #endif -extern int pwc_preferred_compression; extern int pwc_mbufs; /** functions in pwc-if.c */ @@ -308,7 +307,6 @@ extern int pwc_set_gamma(struct pwc_device *pdev, int value); extern int pwc_get_saturation(struct pwc_device *pdev, int *value); extern int pwc_set_saturation(struct pwc_device *pdev, int value); extern int pwc_set_leds(struct pwc_device *pdev, int on_value, int off_value); -extern int pwc_get_leds(struct pwc_device *pdev, int *on_value, int *off_value); extern int pwc_get_cmos_sensor(struct pwc_device *pdev, int *sensor); extern int pwc_restore_user(struct pwc_device *pdev); extern int pwc_save_user(struct pwc_device *pdev); -- cgit v1.2.3 From 0bd0aae26b024aaa9e5882814b9ad2dd92ea6e03 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Fri, 23 Jun 2006 07:05:22 -0300 Subject: fix userbits debug prints From: Mauro Carvalho Chehab Previously, it were showing the pointer value, instead of the setted bits. Signed-off-by: Mauro Carvalho Chehab --- linux/drivers/media/video/v4l2-common.c | 4 ++-- linux/drivers/media/video/videodev.c | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/linux/drivers/media/video/v4l2-common.c b/linux/drivers/media/video/v4l2-common.c index c1697f045..c701982cf 100644 --- a/linux/drivers/media/video/v4l2-common.c +++ b/linux/drivers/media/video/v4l2-common.c @@ -506,9 +506,9 @@ void v4l_printk_ioctl_arg(char *s,unsigned int cmd, void *arg) prt_names(p->memory,v4l2_memory_names), p->m.userptr); printk ("%s: timecode= %02d:%02d:%02d type=%d, " - "flags=0x%08x, frames=%d, userbits=0x%p\n", + "flags=0x%08x, frames=%d, userbits=0x%08x\n", s,tc->hours,tc->minutes,tc->seconds, - tc->type, tc->flags, tc->frames, tc->userbits); + tc->type, tc->flags, tc->frames, *(__u32 *) tc->userbits); break; } case VIDIOC_QUERYCAP: diff --git a/linux/drivers/media/video/videodev.c b/linux/drivers/media/video/videodev.c index 9241cf5be..976ce381b 100644 --- a/linux/drivers/media/video/videodev.c +++ b/linux/drivers/media/video/videodev.c @@ -342,7 +342,7 @@ static void dbgbuf(unsigned int cmd, struct video_device *vfd, dbgarg2 ("timecode= %02d:%02d:%02d type=%d, " "flags=0x%08d, frames=%d, userbits=0x%08x\n", tc->hours,tc->minutes,tc->seconds, - tc->type, tc->flags, tc->frames, (__u32) tc->userbits); + tc->type, tc->flags, tc->frames, *(__u32 *) tc->userbits); } static inline void dbgrect(struct video_device *vfd, char *s, -- cgit v1.2.3 From 4e3bc28a15ab1b9a6bc0c629fdea9ee0818cca15 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Fri, 23 Jun 2006 09:01:42 -0300 Subject: fix up funky logic in dvb From: Dave Jones Signed-off-by: Dave Jones Signed-off-by: Andrew Morton Signed-off-by: Mauro Carvalho Chehab --- linux/drivers/media/dvb/dvb-core/dvb_demux.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/linux/drivers/media/dvb/dvb-core/dvb_demux.c b/linux/drivers/media/dvb/dvb-core/dvb_demux.c index 83ec5e06c..fcff5eab2 100644 --- a/linux/drivers/media/dvb/dvb-core/dvb_demux.c +++ b/linux/drivers/media/dvb/dvb-core/dvb_demux.c @@ -473,7 +473,7 @@ void dvb_dmx_swfilter_204(struct dvb_demux *demux, const u8 *buf, size_t count) goto bailout; } memcpy(&demux->tsbuf[i], buf, j); - if ((demux->tsbuf[0] == 0x47) | (demux->tsbuf[0] == 0xB8)) { + if ((demux->tsbuf[0] == 0x47) || (demux->tsbuf[0] == 0xB8)) { memcpy(tmppack, demux->tsbuf, 188); if (tmppack[0] == 0xB8) tmppack[0] = 0x47; @@ -484,7 +484,7 @@ void dvb_dmx_swfilter_204(struct dvb_demux *demux, const u8 *buf, size_t count) } while (p < count) { - if ((buf[p] == 0x47) | (buf[p] == 0xB8)) { + if ((buf[p] == 0x47) || (buf[p] == 0xB8)) { if (count - p >= 204) { memcpy(tmppack, &buf[p], 188); if (tmppack[0] == 0xB8) -- cgit v1.2.3 From d6f3e25616ac528ec4630545e5f5b7600f51c16f Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Fri, 23 Jun 2006 12:19:41 -0300 Subject: Have config-compat.h, undefine options turned off From: Trent Piepho Use a (make 3.81 safe!) in-line perl script to generate config-compat.h from .myconfig. The output will be more like the Kernel's output: Options set to 'm' will define CONFIG_WHATEVER_MODULE to 1, rather than define CONFIG_WHATEVER to m. Options set to 'y' to be defined to 1 instead of y. Options that are off will be #undef'ed, rather that omitted, so that they will override the settings from the kernel autoconf.h file. The last change will fix a problem where certain options, like CinergyT2 tuning and AV7110 firmware, wouldn't work properly if they were on in the kernel but off for v4l-dvb Hg. Signed-off-by: Trent Piepho Signed-off-by: Mauro Carvalho Chehab --- v4l/Makefile | 27 +++++++++++++-------------- 1 file changed, 13 insertions(+), 14 deletions(-) diff --git a/v4l/Makefile b/v4l/Makefile index 0e90e13d8..b162ddcc3 100644 --- a/v4l/Makefile +++ b/v4l/Makefile @@ -177,20 +177,19 @@ links:: @find ../linux/sound -name '*.[ch]' -type f -exec ln -sf '{}' . \; config-compat.h:: .myconfig - @echo \#ifndef __CONFIG_COMPAT_H__ > config-compat.h - @echo \#define __CONFIG_COMPAT_H__ >> config-compat.h - @echo >> config-compat.h - @echo \#include \ >> config-compat.h - @echo >> config-compat.h - @grep "CONFIG\_" .myconfig | grep -v "\:\= n" | \ - sed s/"CONFIG\_"/"\#undef CONFIG\_"/1 | \ - sed s/"\:\= .*"/""/1 >> config-compat.h >> config-compat.h - @echo >> config-compat.h - @grep "CONFIG\_" .myconfig | grep -v "\:\= n" | \ - sed s/"CONFIG\_"/"\#define CONFIG\_"/1 | \ - sed s/"\:\="/""/1 >> config-compat.h >> config-compat.h - @echo >> config-compat.h - @echo \#endif >> config-compat.h + @perl \ + -e 'print "#ifndef __CONFIG_COMPAT_H__\n";' \ + -e 'print "#define __CONFIG_COMPAT_H__\n\n";' \ + -e 'print "#include \n\n";' \ + -e 'while(<>) {'\ + -e ' next unless /^(\S+)\s*:= (\S+)$$/;' \ + -e ' print "#undef $$1\n";' \ + -e ' if($$2 eq "n") { next; }' \ + -e ' elsif($$2 eq "m") { print "#define $$1_MODULE 1\n"; }' \ + -e ' elsif($$2 eq "y") { print "#define $$1 1\n"; }' \ + -e ' else { print "#define $$1 $$2\n"; }' \ + -e '} print "\n#endif\n";' \ + < .myconfig > config-compat.h kernel-links makelinks:: cd ..; v4l/scripts/makelinks.sh $(KDIR) -- cgit v1.2.3 From 7bbcab1af264a64efd2772c7e078e2137a24e018 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Fri, 23 Jun 2006 13:26:14 -0300 Subject: Break make release into several lines keeping it work with make 3.81 From: Mauro Carvalho Chehab Also, fixes a trouble with make 3.81 introduced by the latest patch. make 3.81 doesn't work fine with something like: 'foo'\ It should be, instead: 'foo' \ Signed-off-by: Mauro Carvalho Chehab --- v4l/Makefile | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/v4l/Makefile b/v4l/Makefile index b162ddcc3..663369674 100644 --- a/v4l/Makefile +++ b/v4l/Makefile @@ -159,7 +159,17 @@ ifneq ($(VER),) else ifneq ($(DIR),) @echo "Seeking for a version at $(DIR)/Makefile." - @perl -e 'open IN,"$(DIR)/Makefile"; while () { if (/^VERSION\s*=\s*([0-9]+)/){ $$version=$$1; } elsif (/^PATCHLEVEL\s*=\s*([0-9]+)/){ $$level=$$1; } elsif (/^SUBLEVEL\s*=\s*([0-9]+)/){ $$sublevel=$$1; } elsif (/^EXTRAVERSION\s*=\s*([^\s]+)\n/){ $$extra=$$1; } }; printf ("VERSION=%s\nPATCHLEVEL:=%s\nSUBLEVEL:=%s\nKERNELRELEASE:=%s.%s.%s%s\n", $$version,$$level,$$sublevel,$$version,$$level,$$sublevel,$$extra); printf ("SRCDIR:=$(DIR)\n");' > $(obj)/.version + @perl \ + -e 'open IN,"$(DIR)/Makefile"; ' \ + -e 'while () {' \ + -e ' if (/^VERSION\s*=\s*([0-9]+)/){ $$version=$$1; }' \ + -e ' elsif (/^PATCHLEVEL\s*=\s*([0-9]+)/){ $$level=$$1; }' \ + -e ' elsif (/^SUBLEVEL\s*=\s*([0-9]+)/){ $$sublevel=$$1; }' \ + -e ' elsif (/^EXTRAVERSION\s*=\s*([^\s]+)\n/){ $$extra=$$1; }' \ + -e '};' \ + -e 'printf ("VERSION=%s\nPATCHLEVEL:=%s\nSUBLEVEL:=%s\nKERNELRELEASE:=%s.%s.%s%s\n",' \ + -e ' $$version,$$level,$$sublevel,$$version,$$level,$$sublevel,$$extra);' \ + -e 'printf ("SRCDIR:=$(DIR)\n");' > $(obj)/.version @cat .version|grep KERNELRELEASE:|sed s,'KERNELRELEASE:=','Forcing compiling to version ', @if [ ! -f $(DIR)/scripts/kallsyms ]; then \ @@ -181,7 +191,7 @@ config-compat.h:: .myconfig -e 'print "#ifndef __CONFIG_COMPAT_H__\n";' \ -e 'print "#define __CONFIG_COMPAT_H__\n\n";' \ -e 'print "#include \n\n";' \ - -e 'while(<>) {'\ + -e 'while(<>) {' \ -e ' next unless /^(\S+)\s*:= (\S+)$$/;' \ -e ' print "#undef $$1\n";' \ -e ' if($$2 eq "n") { next; }' \ -- cgit v1.2.3 From 515941d047746d1026ffe99a794edd9ffea7a4d1 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Fri, 23 Jun 2006 13:27:36 -0300 Subject: Fix use-after-free bug in cpia2 driver From: Jesper Juhl The coverity checker detected a use-after-free error in drivers/media/video/cpia2/cpia2_v4l.c::cpia2_close() (coverity error #1281). What happens is that we lock cam->busy_lock, then proceed to free resources, and in the case of (--cam->open_count == 0) we finish off by doing a kfree(cam) and then at the end of the function we do a mutex_unlock(&cam->busy_lock) which will explode since it'll dereference the free'd `cam' : ... mutex_lock(&cam->busy_lock); ... if (--cam->open_count == 0) { ... if (!cam->present) { video_unregister_device(dev); kfree(cam); } } mutex_unlock(&cam->busy_lock); <--- PROBLEM, cam no longer around. ... Since this only happens in the case of open_count going down to zero I don't see a problem with just releasing the mutex after unregistering the device and just before the kfree(). In this case there is nothing around that we can race against; we are in the release method, open_count is zero, (!cam->present) and the device has just been unregistered, so letting go of the mutex at this point looks safe to me. Patch below to implement that solution. Signed-off-by: Jesper Juhl Signed-off-by: Andrew Morton Acked-by: Randy Dunlap Signed-off-by: Mauro Carvalho Chehab --- linux/drivers/media/video/cpia2/cpia2_v4l.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/linux/drivers/media/video/cpia2/cpia2_v4l.c b/linux/drivers/media/video/cpia2/cpia2_v4l.c index 28d93c595..d129db57f 100644 --- a/linux/drivers/media/video/cpia2/cpia2_v4l.c +++ b/linux/drivers/media/video/cpia2/cpia2_v4l.c @@ -343,7 +343,9 @@ static int cpia2_close(struct inode *inode, struct file *file) cpia2_free_buffers(cam); if (!cam->present) { video_unregister_device(dev); + mutex_unlock(&cam->busy_lock); kfree(cam); + return 0; } } -- cgit v1.2.3 From 47e7619ed0e11061799a387d580aa2aa90561ead Mon Sep 17 00:00:00 2001 From: Hans Verkuil Date: Fri, 23 Jun 2006 20:52:50 +0200 Subject: Explicitly set the enum values. From: Hans Verkuil It's better to use explicit enums. It reduces the chance of someone inserting new enums in the middle which would break things. Signed-off-by: Hans Verkuil --- linux/include/linux/videodev2.h | 182 ++++++++++++++++++++-------------------- linux/include/media/cx2341x.h | 6 +- 2 files changed, 94 insertions(+), 94 deletions(-) diff --git a/linux/include/linux/videodev2.h b/linux/include/linux/videodev2.h index 3512e05f7..952fcd831 100644 --- a/linux/include/linux/videodev2.h +++ b/linux/include/linux/videodev2.h @@ -808,12 +808,12 @@ struct v4l2_querymenu /* MPEG streams */ #define V4L2_CID_MPEG_STREAM_TYPE (V4L2_CID_MPEG_BASE+0) enum v4l2_mpeg_stream_type { - V4L2_MPEG_STREAM_TYPE_MPEG2_PS, /* MPEG-2 program stream */ - V4L2_MPEG_STREAM_TYPE_MPEG2_TS, /* MPEG-2 transport stream */ - V4L2_MPEG_STREAM_TYPE_MPEG1_SS, /* MPEG-1 system stream */ - V4L2_MPEG_STREAM_TYPE_MPEG2_DVD, /* MPEG-2 DVD-compatible stream */ - V4L2_MPEG_STREAM_TYPE_MPEG1_VCD, /* MPEG-1 VCD-compatible stream */ - V4L2_MPEG_STREAM_TYPE_MPEG2_SVCD, /* MPEG-2 SVCD-compatible stream */ + V4L2_MPEG_STREAM_TYPE_MPEG2_PS = 0, /* MPEG-2 program stream */ + V4L2_MPEG_STREAM_TYPE_MPEG2_TS = 1, /* MPEG-2 transport stream */ + V4L2_MPEG_STREAM_TYPE_MPEG1_SS = 2, /* MPEG-1 system stream */ + V4L2_MPEG_STREAM_TYPE_MPEG2_DVD = 3, /* MPEG-2 DVD-compatible stream */ + V4L2_MPEG_STREAM_TYPE_MPEG1_VCD = 4, /* MPEG-1 VCD-compatible stream */ + V4L2_MPEG_STREAM_TYPE_MPEG2_SVCD = 5, /* MPEG-2 SVCD-compatible stream */ }; #define V4L2_CID_MPEG_STREAM_PID_PMT (V4L2_CID_MPEG_BASE+1) #define V4L2_CID_MPEG_STREAM_PID_AUDIO (V4L2_CID_MPEG_BASE+2) @@ -825,105 +825,105 @@ enum v4l2_mpeg_stream_type { /* MPEG audio */ #define V4L2_CID_MPEG_AUDIO_SAMPLING_FREQ (V4L2_CID_MPEG_BASE+100) enum v4l2_mpeg_audio_sampling_freq { - V4L2_MPEG_AUDIO_SAMPLING_FREQ_44100, - V4L2_MPEG_AUDIO_SAMPLING_FREQ_48000, - V4L2_MPEG_AUDIO_SAMPLING_FREQ_32000, + V4L2_MPEG_AUDIO_SAMPLING_FREQ_44100 = 0, + V4L2_MPEG_AUDIO_SAMPLING_FREQ_48000 = 1, + V4L2_MPEG_AUDIO_SAMPLING_FREQ_32000 = 2, }; #define V4L2_CID_MPEG_AUDIO_ENCODING (V4L2_CID_MPEG_BASE+101) enum v4l2_mpeg_audio_encoding { - V4L2_MPEG_AUDIO_ENCODING_LAYER_1, - V4L2_MPEG_AUDIO_ENCODING_LAYER_2, - V4L2_MPEG_AUDIO_ENCODING_LAYER_3, + V4L2_MPEG_AUDIO_ENCODING_LAYER_1 = 0, + V4L2_MPEG_AUDIO_ENCODING_LAYER_2 = 1, + V4L2_MPEG_AUDIO_ENCODING_LAYER_3 = 2, }; #define V4L2_CID_MPEG_AUDIO_L1_BITRATE (V4L2_CID_MPEG_BASE+102) enum v4l2_mpeg_audio_l1_bitrate { - V4L2_MPEG_AUDIO_L1_BITRATE_32K, - V4L2_MPEG_AUDIO_L1_BITRATE_64K, - V4L2_MPEG_AUDIO_L1_BITRATE_96K, - V4L2_MPEG_AUDIO_L1_BITRATE_128K, - V4L2_MPEG_AUDIO_L1_BITRATE_160K, - V4L2_MPEG_AUDIO_L1_BITRATE_192K, - V4L2_MPEG_AUDIO_L1_BITRATE_224K, - V4L2_MPEG_AUDIO_L1_BITRATE_256K, - V4L2_MPEG_AUDIO_L1_BITRATE_288K, - V4L2_MPEG_AUDIO_L1_BITRATE_320K, - V4L2_MPEG_AUDIO_L1_BITRATE_352K, - V4L2_MPEG_AUDIO_L1_BITRATE_384K, - V4L2_MPEG_AUDIO_L1_BITRATE_416K, - V4L2_MPEG_AUDIO_L1_BITRATE_448K, + V4L2_MPEG_AUDIO_L1_BITRATE_32K = 0, + V4L2_MPEG_AUDIO_L1_BITRATE_64K = 1, + V4L2_MPEG_AUDIO_L1_BITRATE_96K = 2, + V4L2_MPEG_AUDIO_L1_BITRATE_128K = 3, + V4L2_MPEG_AUDIO_L1_BITRATE_160K = 4, + V4L2_MPEG_AUDIO_L1_BITRATE_192K = 5, + V4L2_MPEG_AUDIO_L1_BITRATE_224K = 6, + V4L2_MPEG_AUDIO_L1_BITRATE_256K = 7, + V4L2_MPEG_AUDIO_L1_BITRATE_288K = 8, + V4L2_MPEG_AUDIO_L1_BITRATE_320K = 9, + V4L2_MPEG_AUDIO_L1_BITRATE_352K = 10, + V4L2_MPEG_AUDIO_L1_BITRATE_384K = 11, + V4L2_MPEG_AUDIO_L1_BITRATE_416K = 12, + V4L2_MPEG_AUDIO_L1_BITRATE_448K = 13, }; #define V4L2_CID_MPEG_AUDIO_L2_BITRATE (V4L2_CID_MPEG_BASE+103) enum v4l2_mpeg_audio_l2_bitrate { - V4L2_MPEG_AUDIO_L2_BITRATE_32K, - V4L2_MPEG_AUDIO_L2_BITRATE_48K, - V4L2_MPEG_AUDIO_L2_BITRATE_56K, - V4L2_MPEG_AUDIO_L2_BITRATE_64K, - V4L2_MPEG_AUDIO_L2_BITRATE_80K, - V4L2_MPEG_AUDIO_L2_BITRATE_96K, - V4L2_MPEG_AUDIO_L2_BITRATE_112K, - V4L2_MPEG_AUDIO_L2_BITRATE_128K, - V4L2_MPEG_AUDIO_L2_BITRATE_160K, - V4L2_MPEG_AUDIO_L2_BITRATE_192K, - V4L2_MPEG_AUDIO_L2_BITRATE_224K, - V4L2_MPEG_AUDIO_L2_BITRATE_256K, - V4L2_MPEG_AUDIO_L2_BITRATE_320K, - V4L2_MPEG_AUDIO_L2_BITRATE_384K, + V4L2_MPEG_AUDIO_L2_BITRATE_32K = 0, + V4L2_MPEG_AUDIO_L2_BITRATE_48K = 1, + V4L2_MPEG_AUDIO_L2_BITRATE_56K = 2, + V4L2_MPEG_AUDIO_L2_BITRATE_64K = 3, + V4L2_MPEG_AUDIO_L2_BITRATE_80K = 4, + V4L2_MPEG_AUDIO_L2_BITRATE_96K = 5, + V4L2_MPEG_AUDIO_L2_BITRATE_112K = 6, + V4L2_MPEG_AUDIO_L2_BITRATE_128K = 7, + V4L2_MPEG_AUDIO_L2_BITRATE_160K = 8, + V4L2_MPEG_AUDIO_L2_BITRATE_192K = 9, + V4L2_MPEG_AUDIO_L2_BITRATE_224K = 10, + V4L2_MPEG_AUDIO_L2_BITRATE_256K = 11, + V4L2_MPEG_AUDIO_L2_BITRATE_320K = 12, + V4L2_MPEG_AUDIO_L2_BITRATE_384K = 13, }; #define V4L2_CID_MPEG_AUDIO_L3_BITRATE (V4L2_CID_MPEG_BASE+104) enum v4l2_mpeg_audio_l3_bitrate { - V4L2_MPEG_AUDIO_L3_BITRATE_32K, - V4L2_MPEG_AUDIO_L3_BITRATE_40K, - V4L2_MPEG_AUDIO_L3_BITRATE_48K, - V4L2_MPEG_AUDIO_L3_BITRATE_56K, - V4L2_MPEG_AUDIO_L3_BITRATE_64K, - V4L2_MPEG_AUDIO_L3_BITRATE_80K, - V4L2_MPEG_AUDIO_L3_BITRATE_96K, - V4L2_MPEG_AUDIO_L3_BITRATE_112K, - V4L2_MPEG_AUDIO_L3_BITRATE_128K, - V4L2_MPEG_AUDIO_L3_BITRATE_160K, - V4L2_MPEG_AUDIO_L3_BITRATE_192K, - V4L2_MPEG_AUDIO_L3_BITRATE_224K, - V4L2_MPEG_AUDIO_L3_BITRATE_256K, - V4L2_MPEG_AUDIO_L3_BITRATE_320K, + V4L2_MPEG_AUDIO_L3_BITRATE_32K = 0, + V4L2_MPEG_AUDIO_L3_BITRATE_40K = 1, + V4L2_MPEG_AUDIO_L3_BITRATE_48K = 2, + V4L2_MPEG_AUDIO_L3_BITRATE_56K = 3, + V4L2_MPEG_AUDIO_L3_BITRATE_64K = 4, + V4L2_MPEG_AUDIO_L3_BITRATE_80K = 5, + V4L2_MPEG_AUDIO_L3_BITRATE_96K = 6, + V4L2_MPEG_AUDIO_L3_BITRATE_112K = 7, + V4L2_MPEG_AUDIO_L3_BITRATE_128K = 8, + V4L2_MPEG_AUDIO_L3_BITRATE_160K = 9, + V4L2_MPEG_AUDIO_L3_BITRATE_192K = 10, + V4L2_MPEG_AUDIO_L3_BITRATE_224K = 11, + V4L2_MPEG_AUDIO_L3_BITRATE_256K = 12, + V4L2_MPEG_AUDIO_L3_BITRATE_320K = 13, }; #define V4L2_CID_MPEG_AUDIO_MODE (V4L2_CID_MPEG_BASE+105) enum v4l2_mpeg_audio_mode { - V4L2_MPEG_AUDIO_MODE_STEREO, - V4L2_MPEG_AUDIO_MODE_JOINT_STEREO, - V4L2_MPEG_AUDIO_MODE_DUAL, - V4L2_MPEG_AUDIO_MODE_MONO, + V4L2_MPEG_AUDIO_MODE_STEREO = 0, + V4L2_MPEG_AUDIO_MODE_JOINT_STEREO = 1, + V4L2_MPEG_AUDIO_MODE_DUAL = 2, + V4L2_MPEG_AUDIO_MODE_MONO = 3, }; #define V4L2_CID_MPEG_AUDIO_MODE_EXTENSION (V4L2_CID_MPEG_BASE+106) enum v4l2_mpeg_audio_mode_extension { - V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_4, - V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_8, - V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_12, - V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_16, + V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_4 = 0, + V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_8 = 1, + V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_12 = 2, + V4L2_MPEG_AUDIO_MODE_EXTENSION_BOUND_16 = 3, }; #define V4L2_CID_MPEG_AUDIO_EMPHASIS (V4L2_CID_MPEG_BASE+107) enum v4l2_mpeg_audio_emphasis { - V4L2_MPEG_AUDIO_EMPHASIS_NONE, - V4L2_MPEG_AUDIO_EMPHASIS_50_DIV_15_uS, - V4L2_MPEG_AUDIO_EMPHASIS_CCITT_J17, + V4L2_MPEG_AUDIO_EMPHASIS_NONE = 0, + V4L2_MPEG_AUDIO_EMPHASIS_50_DIV_15_uS = 1, + V4L2_MPEG_AUDIO_EMPHASIS_CCITT_J17 = 2, }; #define V4L2_CID_MPEG_AUDIO_CRC (V4L2_CID_MPEG_BASE+108) enum v4l2_mpeg_audio_crc { - V4L2_MPEG_AUDIO_CRC_NONE, - V4L2_MPEG_AUDIO_CRC_CRC16, + V4L2_MPEG_AUDIO_CRC_NONE = 0, + V4L2_MPEG_AUDIO_CRC_CRC16 = 1, }; /* MPEG video */ #define V4L2_CID_MPEG_VIDEO_ENCODING (V4L2_CID_MPEG_BASE+200) enum v4l2_mpeg_video_encoding { - V4L2_MPEG_VIDEO_ENCODING_MPEG_1, - V4L2_MPEG_VIDEO_ENCODING_MPEG_2, + V4L2_MPEG_VIDEO_ENCODING_MPEG_1 = 0, + V4L2_MPEG_VIDEO_ENCODING_MPEG_2 = 1, }; #define V4L2_CID_MPEG_VIDEO_ASPECT (V4L2_CID_MPEG_BASE+201) enum v4l2_mpeg_video_aspect { - V4L2_MPEG_VIDEO_ASPECT_1x1, - V4L2_MPEG_VIDEO_ASPECT_4x3, - V4L2_MPEG_VIDEO_ASPECT_16x9, - V4L2_MPEG_VIDEO_ASPECT_221x100, + V4L2_MPEG_VIDEO_ASPECT_1x1 = 0, + V4L2_MPEG_VIDEO_ASPECT_4x3 = 1, + V4L2_MPEG_VIDEO_ASPECT_16x9 = 2, + V4L2_MPEG_VIDEO_ASPECT_221x100 = 3, }; #define V4L2_CID_MPEG_VIDEO_B_FRAMES (V4L2_CID_MPEG_BASE+202) #define V4L2_CID_MPEG_VIDEO_GOP_SIZE (V4L2_CID_MPEG_BASE+203) @@ -931,8 +931,8 @@ enum v4l2_mpeg_video_aspect { #define V4L2_CID_MPEG_VIDEO_PULLDOWN (V4L2_CID_MPEG_BASE+205) #define V4L2_CID_MPEG_VIDEO_BITRATE_MODE (V4L2_CID_MPEG_BASE+206) enum v4l2_mpeg_video_bitrate_mode { - V4L2_MPEG_VIDEO_BITRATE_MODE_VBR, - V4L2_MPEG_VIDEO_BITRATE_MODE_CBR, + V4L2_MPEG_VIDEO_BITRATE_MODE_VBR = 0, + V4L2_MPEG_VIDEO_BITRATE_MODE_CBR = 1, }; #define V4L2_CID_MPEG_VIDEO_BITRATE (V4L2_CID_MPEG_BASE+207) #define V4L2_CID_MPEG_VIDEO_BITRATE_PEAK (V4L2_CID_MPEG_BASE+208) @@ -942,36 +942,36 @@ enum v4l2_mpeg_video_bitrate_mode { #define V4L2_CID_MPEG_CX2341X_BASE (V4L2_CTRL_CLASS_MPEG | 0x1000) #define V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE (V4L2_CID_MPEG_CX2341X_BASE+0) enum v4l2_mpeg_cx2341x_video_spatial_filter_mode { - V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_MANUAL, - V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_AUTO, + V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_MANUAL = 0, + V4L2_MPEG_CX2341X_VIDEO_SPATIAL_FILTER_MODE_AUTO = 1, }; #define V4L2_CID_MPEG_CX2341X_VIDEO_SPATIAL_FILTER (V4L2_CID_MPEG_CX2341X_BASE+1) #define V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE (V4L2_CID_MPEG_CX2341X_BASE+2) enum v4l2_mpeg_cx2341x_video_luma_spatial_filter_type { - V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_OFF, - V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_1D_HOR, - V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_1D_VERT, - V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_2D_HV_SEPARABLE, - V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_2D_SYM_NON_SEPARABLE, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_OFF = 0, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_1D_HOR = 1, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_1D_VERT = 2, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_2D_HV_SEPARABLE = 3, + V4L2_MPEG_CX2341X_VIDEO_LUMA_SPATIAL_FILTER_TYPE_2D_SYM_NON_SEPARABLE = 4, }; #define V4L2_CID_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE (V4L2_CID_MPEG_CX2341X_BASE+3) enum v4l2_mpeg_cx2341x_video_chroma_spatial_filter_type { - V4L2_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE_OFF, - V4L2_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE_1D_HOR, + V4L2_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE_OFF = 0, + V4L2_MPEG_CX2341X_VIDEO_CHROMA_SPATIAL_FILTER_TYPE_1D_HOR = 1, }; #define V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE (V4L2_CID_MPEG_CX2341X_BASE+4) enum v4l2_mpeg_cx2341x_video_temporal_filter_mode { - V4L2_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE_MANUAL, - V4L2_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE_AUTO, + V4L2_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE_MANUAL = 0, + V4L2_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER_MODE_AUTO = 1, }; #define V4L2_CID_MPEG_CX2341X_VIDEO_TEMPORAL_FILTER (V4L2_CID_MPEG_CX2341X_BASE+5) #define V4L2_CID_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE (V4L2_CID_MPEG_CX2341X_BASE+6) enum v4l2_mpeg_cx2341x_video_median_filter_type { - V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_OFF, - V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_HOR, - V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_VERT, - V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_HOR_VERT, - V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_DIAG, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_OFF = 0, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_HOR = 1, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_VERT = 2, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_HOR_VERT = 3, + V4L2_MPEG_CX2341X_VIDEO_MEDIAN_FILTER_TYPE_DIAG = 4, }; #define V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_BOTTOM (V4L2_CID_MPEG_CX2341X_BASE+7) #define V4L2_CID_MPEG_CX2341X_VIDEO_LUMA_MEDIAN_FILTER_TOP (V4L2_CID_MPEG_CX2341X_BASE+8) diff --git a/linux/include/media/cx2341x.h b/linux/include/media/cx2341x.h index fb170d4b5..51fb06b4c 100644 --- a/linux/include/media/cx2341x.h +++ b/linux/include/media/cx2341x.h @@ -20,9 +20,9 @@ #define CX2341X_H enum cx2341x_port { - CX2341X_PORT_MEMORY, - CX2341X_PORT_STREAMING, - CX2341X_PORT_SERIAL + CX2341X_PORT_MEMORY = 0, + CX2341X_PORT_STREAMING = 1, + CX2341X_PORT_SERIAL = 2 }; struct cx2341x_mpeg_params { -- cgit v1.2.3 From 2b9b626849d56a89bbccfc172636a16cb2a513f1 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Fri, 23 Jun 2006 16:13:56 -0300 Subject: Merge tda9887 module into tuner. From: Mauro Carvalho Chehab Most uses a tda988[5/6/7] IF demodulator as part of the device. Having this as a separate stuff makes harder to configure it, since there are some tda9887 options that are tuner-dependent and should be bound into tuner-types structures. This patch merges tda9887 module into tuner. More work is required to make tuner-types to properly use it. Signed-off-by: Mauro Carvalho Chehab --- linux/drivers/media/video/Makefile | 4 +- linux/drivers/media/video/em28xx/em28xx-i2c.c | 13 +- linux/drivers/media/video/tda9887.c | 521 ++++---------------------- linux/drivers/media/video/tuner-core.c | 32 +- linux/drivers/media/video/tuner-types.c | 5 + linux/include/media/tuner.h | 10 + 6 files changed, 130 insertions(+), 455 deletions(-) diff --git a/linux/drivers/media/video/Makefile b/linux/drivers/media/video/Makefile index 572e84835..353d61cfa 100644 --- a/linux/drivers/media/video/Makefile +++ b/linux/drivers/media/video/Makefile @@ -6,7 +6,7 @@ zoran-objs := zr36120.o zr36120_i2c.o zr36120_mem.o zr36067-objs := zoran_procfs.o zoran_device.o \ zoran_driver.o zoran_card.o tuner-objs := tuner-core.o tuner-types.o tuner-simple.o \ - mt20xx.o tda8290.o tea5767.o + mt20xx.o tda8290.o tea5767.o tda9887.o msp3400-objs := msp3400-driver.o msp3400-kthreads.o @@ -61,7 +61,7 @@ obj-$(CONFIG_VIDEO_HEXIUM_GEMINI) += hexium_gemini.o obj-$(CONFIG_VIDEO_DPC) += saa7111.o dpc7146.o obj-$(CONFIG_TUNER_3036) += tuner-3036.o -obj-$(CONFIG_VIDEO_TUNER) += tuner.o tda9887.o +obj-$(CONFIG_VIDEO_TUNER) += tuner.o obj-$(CONFIG_VIDEO_BUF) += video-buf.o obj-$(CONFIG_VIDEO_BUF_DVB) += video-buf-dvb.o obj-$(CONFIG_VIDEO_BTCX) += btcx-risc.o diff --git a/linux/drivers/media/video/em28xx/em28xx-i2c.c b/linux/drivers/media/video/em28xx/em28xx-i2c.c index c077c39c2..4ee4cea10 100644 --- a/linux/drivers/media/video/em28xx/em28xx-i2c.c +++ b/linux/drivers/media/video/em28xx/em28xx-i2c.c @@ -436,9 +436,19 @@ static int attach_inform(struct i2c_client *client) struct em28xx *dev = client->adapter->algo_data; switch (client->addr << 1) { - case 0x86: + case 0x43: + case 0x4b: + { + struct tuner_setup tun_setup; + + tun_setup.mode_mask = T_ANALOG_TV | T_RADIO; + tun_setup.type = TUNER_TDA9887; + tun_setup.addr = client->addr; + + em28xx_i2c_call_clients(dev, TUNER_SET_TYPE_ADDR, &tun_setup); em28xx_i2c_call_clients(dev, TDA9887_SET_CONFIG, &dev->tda9887_conf); break; + } case 0x42: dprintk1(1,"attach_inform: saa7114 detected.\n"); break; @@ -464,6 +474,7 @@ static int attach_inform(struct i2c_client *client) case 0xba: dprintk1(1,"attach_inform: tvp5150 detected.\n"); break; + default: dprintk1(1,"attach inform: detected I2C address %x\n", client->addr << 1); dev->tuner_addr = client->addr; diff --git a/linux/drivers/media/video/tda9887.c b/linux/drivers/media/video/tda9887.c index ab134a8c0..ba9488594 100644 --- a/linux/drivers/media/video/tda9887.c +++ b/linux/drivers/media/video/tda9887.c @@ -22,52 +22,21 @@ TDA9886 (PAL, SECAM, NTSC) TDA9887 (PAL, SECAM, NTSC, FM Radio) - found on: - - Pinnacle PCTV (Jul.2002 Version with MT2032, bttv) - TDA9887 (world), TDA9885 (USA) - Note: OP2 of tda988x must be set to 1, else MT2032 is disabled! - - KNC One TV-Station RDS (saa7134) - - Hauppauge PVR-150/500 (possibly more) + Used as part of several tuners */ +#define tda9887_info(fmt, arg...) do {\ + printk(KERN_INFO "%s %d-%04x (tda9887): " fmt, t->i2c.name, \ + i2c_adapter_id(t->i2c.adapter), t->i2c.addr , ##arg); } while (0) +#define tda9887_dbg(fmt, arg...) do {\ + if (tuner_debug) \ + printk(KERN_INFO "%s %d-%04x (tda9887): " fmt, t->i2c.name, \ + i2c_adapter_id(t->i2c.adapter), t->i2c.addr , ##arg); } while (0) -/* Addresses to scan */ -static unsigned short normal_i2c[] = { - 0x84 >>1, - 0x86 >>1, - 0x96 >>1, - I2C_CLIENT_END, -}; -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,13) -static unsigned short normal_i2c_range[] = { I2C_CLIENT_END }; -#endif -I2C_CLIENT_INSMOD; - -/* insmod options */ -static unsigned int debug = 0; -module_param(debug, int, 0644); -MODULE_LICENSE("GPL"); /* ---------------------------------------------------------------------- */ #define UNSET (-1U) -#define tda9887_info(fmt, arg...) do {\ - printk(KERN_INFO "%s %d-%04x: " fmt, t->client.name, \ - i2c_adapter_id(t->client.adapter), t->client.addr , ##arg); } while (0) -#define tda9887_dbg(fmt, arg...) do {\ - if (debug) \ - printk(KERN_INFO "%s %d-%04x: " fmt, t->client.name, \ - i2c_adapter_id(t->client.adapter), t->client.addr , ##arg); } while (0) - -struct tda9887 { - struct i2c_client client; - v4l2_std_id std; - enum tuner_mode mode; - unsigned int config; - unsigned int using_v4l2; - unsigned int radio_mode; - unsigned char data[4]; -}; struct tvnorm { v4l2_std_id std; @@ -77,9 +46,6 @@ struct tvnorm { unsigned char e; }; -static struct i2c_driver driver; -static struct i2c_client client_template; - /* ---------------------------------------------------------------------- */ // @@ -288,7 +254,7 @@ static struct tvnorm radio_mono = { /* ---------------------------------------------------------------------- */ -static void dump_read_message(struct tda9887 *t, unsigned char *buf) +static void dump_read_message(struct tuner *t, unsigned char *buf) { static char *afc[16] = { "- 12.5 kHz", @@ -316,7 +282,7 @@ static void dump_read_message(struct tda9887 *t, unsigned char *buf) tda9887_info(" vfi level : %s\n", (buf[0] & 0x80) ? "high" : "low"); } -static void dump_write_message(struct tda9887 *t, unsigned char *buf) +static void dump_write_message(struct tuner *t, unsigned char *buf) { static char *sound[4] = { "AM/TV", @@ -412,13 +378,13 @@ static void dump_write_message(struct tda9887 *t, unsigned char *buf) /* ---------------------------------------------------------------------- */ -static int tda9887_set_tvnorm(struct tda9887 *t, char *buf) +static int tda9887_set_tvnorm(struct tuner *t, char *buf) { struct tvnorm *norm = NULL; int i; - if (t->mode == T_RADIO) { - if (t->radio_mode == V4L2_TUNER_MODE_MONO) + if (t->mode == V4L2_TUNER_RADIO) { + if (t->audmode == V4L2_TUNER_MODE_MONO) norm = &radio_mono; else norm = &radio_stereo; @@ -459,7 +425,7 @@ module_param(qss, int, 0644); module_param(adjust, int, 0644); #endif -static int tda9887_set_insmod(struct tda9887 *t, char *buf) +static int tda9887_set_insmod(struct tuner *t, char *buf) { if (UNSET != port1) { if (port1) @@ -488,27 +454,27 @@ static int tda9887_set_insmod(struct tda9887 *t, char *buf) return 0; } -static int tda9887_set_config(struct tda9887 *t, char *buf) +static int tda9887_set_config(struct tuner *t, char *buf) { - if (t->config & TDA9887_PORT1_ACTIVE) + if (t->tda9887_config & TDA9887_PORT1_ACTIVE) buf[1] &= ~cOutputPort1Inactive; - if (t->config & TDA9887_PORT1_INACTIVE) + if (t->tda9887_config & TDA9887_PORT1_INACTIVE) buf[1] |= cOutputPort1Inactive; - if (t->config & TDA9887_PORT2_ACTIVE) + if (t->tda9887_config & TDA9887_PORT2_ACTIVE) buf[1] &= ~cOutputPort2Inactive; - if (t->config & TDA9887_PORT2_INACTIVE) + if (t->tda9887_config & TDA9887_PORT2_INACTIVE) buf[1] |= cOutputPort2Inactive; - if (t->config & TDA9887_QSS) + if (t->tda9887_config & TDA9887_QSS) buf[1] |= cQSS; - if (t->config & TDA9887_INTERCARRIER) + if (t->tda9887_config & TDA9887_INTERCARRIER) buf[1] &= ~cQSS; - if (t->config & TDA9887_AUTOMUTE) + if (t->tda9887_config & TDA9887_AUTOMUTE) buf[1] |= cAutoMuteFmActive; - if (t->config & TDA9887_DEEMPHASIS_MASK) { + if (t->tda9887_config & TDA9887_DEEMPHASIS_MASK) { buf[2] &= ~0x60; - switch (t->config & TDA9887_DEEMPHASIS_MASK) { + switch (t->tda9887_config & TDA9887_DEEMPHASIS_MASK) { case TDA9887_DEEMPHASIS_NONE: buf[2] |= cDeemphasisOFF; break; @@ -520,159 +486,36 @@ static int tda9887_set_config(struct tda9887 *t, char *buf) break; } } - if (t->config & TDA9887_TOP_SET) { + if (t->tda9887_config & TDA9887_TOP_SET) { buf[2] &= ~cTopMask; - buf[2] |= (t->config >> 8) & cTopMask; + buf[2] |= (t->tda9887_config >> 8) & cTopMask; } - if ((t->config & TDA9887_INTERCARRIER_NTSC) && (t->std & V4L2_STD_NTSC)) + if ((t->tda9887_config & TDA9887_INTERCARRIER_NTSC) && (t->std & V4L2_STD_NTSC)) buf[1] &= ~cQSS; return 0; } /* ---------------------------------------------------------------------- */ -static char pal[] = "--"; -static char secam[] = "--"; -static char ntsc[] = "-"; - -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0) -MODULE_PARM(pal,"s"); -MODULE_PARM(secam,"s"); -MODULE_PARM(ntsc,"s"); -#else -module_param_string(pal, pal, sizeof(pal), 0644); -module_param_string(secam, secam, sizeof(secam), 0644); -module_param_string(ntsc, ntsc, sizeof(ntsc), 0644); -#endif - -static int tda9887_fixup_std(struct tda9887 *t) -{ - /* get more precise norm info from insmod option */ - if ((t->std & V4L2_STD_PAL) == V4L2_STD_PAL) { - switch (pal[0]) { - case 'b': - case 'B': - case 'g': - case 'G': - case 'h': - case 'H': - case 'n': - case 'N': - if (pal[1] == 'c' || pal[1] == 'C') { - tda9887_dbg("insmod fixup: PAL => PAL-Nc\n"); - t->std = V4L2_STD_PAL_Nc; - } else { - tda9887_dbg("insmod fixup: PAL => PAL-BGHN\n"); - t->std = V4L2_STD_PAL_BG | V4L2_STD_PAL_H | V4L2_STD_PAL_N; - } - break; - case 'i': - case 'I': - tda9887_dbg("insmod fixup: PAL => PAL-I\n"); - t->std = V4L2_STD_PAL_I; - break; - case 'd': - case 'D': - case 'k': - case 'K': - tda9887_dbg("insmod fixup: PAL => PAL-DK\n"); - t->std = V4L2_STD_PAL_DK; - break; - case 'm': - case 'M': - tda9887_dbg("insmod fixup: PAL => PAL-M\n"); - t->std = V4L2_STD_PAL_M; - break; - case '-': - /* default parameter, do nothing */ - break; - default: - tda9887_info("pal= argument not recognised\n"); - break; - } - } - if ((t->std & V4L2_STD_SECAM) == V4L2_STD_SECAM) { - switch (secam[0]) { - case 'b': - case 'B': - case 'g': - case 'G': - case 'h': - case 'H': - tda9887_dbg("insmod fixup: SECAM => SECAM-BGH\n"); - t->std = V4L2_STD_SECAM_B | V4L2_STD_SECAM_G | V4L2_STD_SECAM_H; - break; - case 'd': - case 'D': - case 'k': - case 'K': - tda9887_dbg("insmod fixup: SECAM => SECAM-DK\n"); - t->std = V4L2_STD_SECAM_DK; - break; - case 'l': - case 'L': - if (secam[1] == 'c' || secam[1] == 'C') { - tda9887_dbg("insmod fixup: SECAM => SECAM-L'\n"); - t->std = V4L2_STD_SECAM_LC; - } else { - tda9887_dbg("insmod fixup: SECAM => SECAM-L\n"); - t->std = V4L2_STD_SECAM_L; - } - break; - case '-': - /* default parameter, do nothing */ - break; - default: - tda9887_info("secam= argument not recognised\n"); - break; - } - } - if ((t->std & V4L2_STD_NTSC) == V4L2_STD_NTSC) { - switch (ntsc[0]) { - case 'm': - case 'M': - tda9887_dbg("insmod fixup: NTSC => NTSC-M\n"); - t->std = V4L2_STD_NTSC_M; - break; - case 'j': - case 'J': - tda9887_dbg("insmod fixup: NTSC => NTSC_M_JP\n"); - t->std = V4L2_STD_NTSC_M_JP; - break; - case 'k': - case 'K': - tda9887_dbg("insmod fixup: NTSC => NTSC_M_KR\n"); - t->std = V4L2_STD_NTSC_M_KR; - break; - case '-': - /* default parameter, do nothing */ - break; - default: - tda9887_info("ntsc= argument not recognised\n"); - break; - } - } - return 0; -} - -static int tda9887_status(struct tda9887 *t) +static int tda9887_status(struct tuner *t) { unsigned char buf[1]; int rc; memset(buf,0,sizeof(buf)); - if (1 != (rc = i2c_master_recv(&t->client,buf,1))) + if (1 != (rc = i2c_master_recv(&t->i2c,buf,1))) tda9887_info("i2c i/o error: rc == %d (should be 1)\n",rc); dump_read_message(t, buf); return 0; } -static int tda9887_configure(struct tda9887 *t) +static void tda9887_configure(struct i2c_client *client) { + struct tuner *t = i2c_get_clientdata(client); int rc; - memset(t->data,0,sizeof(t->data)); - tda9887_set_tvnorm(t,t->data); + memset(t->tda9887_data,0,sizeof(t->tda9887_data)); + tda9887_set_tvnorm(t,t->tda9887_data); /* A note on the port settings: These settings tend to depend on the specifics of the board. @@ -687,300 +530,84 @@ static int tda9887_configure(struct tda9887 *t) the ports should be set to active (0), but, again, that may differ depending on the precise hardware configuration. */ - t->data[1] |= cOutputPort1Inactive; - t->data[1] |= cOutputPort2Inactive; + t->tda9887_data[1] |= cOutputPort1Inactive; + t->tda9887_data[1] |= cOutputPort2Inactive; - tda9887_set_config(t,t->data); - tda9887_set_insmod(t,t->data); + tda9887_set_config(t,t->tda9887_data); + tda9887_set_insmod(t,t->tda9887_data); if (t->mode == T_STANDBY) { - t->data[1] |= cForcedMuteAudioON; + t->tda9887_data[1] |= cForcedMuteAudioON; } tda9887_dbg("writing: b=0x%02x c=0x%02x e=0x%02x\n", - t->data[1],t->data[2],t->data[3]); - if (debug > 1) - dump_write_message(t, t->data); + t->tda9887_data[1],t->tda9887_data[2],t->tda9887_data[3]); + if (tuner_debug > 1) + dump_write_message(t, t->tda9887_data); - if (4 != (rc = i2c_master_send(&t->client,t->data,4))) + if (4 != (rc = i2c_master_send(&t->i2c,t->tda9887_data,4))) tda9887_info("i2c i/o error: rc == %d (should be 4)\n",rc); - if (debug > 2) { + if (tuner_debug > 2) { msleep_interruptible(1000); tda9887_status(t); } - return 0; } /* ---------------------------------------------------------------------- */ -#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0) -static int tda9887_attach(struct i2c_adapter *adap, int addr, int kind) -#else -static int tda9887_attach(struct i2c_adapter *adap, int addr, - unsigned short flags, int kind) -#endif +static void tda9887_tuner_status(struct i2c_client *client) { - struct tda9887 *t; - - client_template.adapter = adap; - client_template.addr = addr; - - if (NULL == (t = kzalloc(sizeof(*t), GFP_KERNEL))) - return -ENOMEM; - - t->client = client_template; - t->std = 0; - t->radio_mode = V4L2_TUNER_MODE_STEREO; - - tda9887_info("chip found @ 0x%x (%s)\n", addr<<1, adap->name); - - i2c_set_clientdata(&t->client, t); - i2c_attach_client(&t->client); - -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0) - MOD_INC_USE_COUNT; -#endif - return 0; + struct tuner *t = i2c_get_clientdata(client); + tda9887_info("Data bytes: b=0x%02x c=0x%02x e=0x%02x\n", t->tda9887_data[1], t->tda9887_data[2], t->tda9887_data[3]); } -static int tda9887_probe(struct i2c_adapter *adap) +static int tda9887_get_afc(struct i2c_client *client) { -#ifdef I2C_CLASS_TV_ANALOG - if (adap->class & I2C_CLASS_TV_ANALOG) - return i2c_probe(adap, &addr_data, tda9887_attach); -#else - switch (adap->id) { - case I2C_HW_B_BT848: - case I2C_HW_B_RIVA: -#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0) - case I2C_HW_SAA7134: -#endif - return i2c_probe(adap, &addr_data, tda9887_attach); - break; - } -#endif - return 0; -} + struct tuner *t = i2c_get_clientdata(client); + static int AFC_BITS_2_kHz[] = { + -12500, -37500, -62500, -97500, + -112500, -137500, -162500, -187500, + 187500, 162500, 137500, 112500, + 97500 , 62500, 37500 , 12500 + }; + int afc=0; + __u8 reg = 0; -static int tda9887_detach(struct i2c_client *client) -{ - struct tda9887 *t = i2c_get_clientdata(client); + if (1 == i2c_master_recv(&t->i2c,®,1)) + afc = AFC_BITS_2_kHz[(reg>>1)&0x0f]; - i2c_detach_client(client); - kfree(t); -#if LINUX_VERSION_CODE < KERNEL_VERSION(2,5,0) - MOD_DEC_USE_COUNT; -#endif - return 0; + return afc; } -#define SWITCH_V4L2 if (!t->using_v4l2 && debug) \ - tda9887_info("switching to v4l2\n"); \ - t->using_v4l2 = 1; -#define CHECK_V4L2 if (t->using_v4l2) { if (debug) \ - tda9887_info("ignore v4l1 call\n"); \ - return 0; } - -static int -tda9887_command(struct i2c_client *client, unsigned int cmd, void *arg) +static void tda9887_standby(struct i2c_client *client) { - struct tda9887 *t = i2c_get_clientdata(client); - - switch (cmd) { - - /* --- configuration --- */ - case AUDC_SET_RADIO: - { - t->mode = T_RADIO; - tda9887_configure(t); - break; - } - case TUNER_SET_STANDBY: - { - t->mode = T_STANDBY; - tda9887_configure(t); - break; - } - case TDA9887_SET_CONFIG: - { - int *i = arg; - - t->config = *i; - tda9887_configure(t); - break; - } - /* --- v4l ioctls --- */ - /* take care: bttv does userspace copying, we'll get a - kernel pointer here... */ - case VIDIOCSCHAN: - { - static const v4l2_std_id map[] = { - [ VIDEO_MODE_PAL ] = V4L2_STD_PAL, - [ VIDEO_MODE_NTSC ] = V4L2_STD_NTSC_M, - [ VIDEO_MODE_SECAM ] = V4L2_STD_SECAM, - [ 4 /* bttv */ ] = V4L2_STD_PAL_M, - [ 5 /* bttv */ ] = V4L2_STD_PAL_N, - [ 6 /* bttv */ ] = V4L2_STD_NTSC_M_JP, - }; - struct video_channel *vc = arg; - - CHECK_V4L2; - t->mode = T_ANALOG_TV; - if (vc->norm < ARRAY_SIZE(map)) - t->std = map[vc->norm]; - tda9887_fixup_std(t); - tda9887_configure(t); - break; - } - case VIDIOC_S_STD: - { - v4l2_std_id *id = arg; - - SWITCH_V4L2; - t->mode = T_ANALOG_TV; - t->std = *id; - tda9887_fixup_std(t); - tda9887_configure(t); - break; - } - case VIDIOC_S_FREQUENCY: - { - struct v4l2_frequency *f = arg; - - SWITCH_V4L2; - if (V4L2_TUNER_ANALOG_TV == f->type) { - if (t->mode == T_ANALOG_TV) - return 0; - t->mode = T_ANALOG_TV; - } - if (V4L2_TUNER_RADIO == f->type) { - if (t->mode == T_RADIO) - return 0; - t->mode = T_RADIO; - } - tda9887_configure(t); - break; - } - case VIDIOC_G_TUNER: - { - static int AFC_BITS_2_kHz[] = { - -12500, -37500, -62500, -97500, - -112500, -137500, -162500, -187500, - 187500, 162500, 137500, 112500, - 97500 , 62500, 37500 , 12500 - }; - struct v4l2_tuner* tuner = arg; - - if (t->mode == T_RADIO) { - __u8 reg = 0; - tuner->afc=0; - if (1 == i2c_master_recv(&t->client,®,1)) - tuner->afc = AFC_BITS_2_kHz[(reg>>1)&0x0f]; - } - break; - } - case VIDIOC_S_TUNER: - { - struct v4l2_tuner* tuner = arg; - - if (t->mode == T_RADIO) { - t->radio_mode = tuner->audmode; - tda9887_configure (t); - } - break; - } - case VIDIOC_LOG_STATUS: - { - tda9887_info("Data bytes: b=0x%02x c=0x%02x e=0x%02x\n", t->data[1], t->data[2], t->data[3]); - break; - } - default: - /* nothing */ - break; - } - return 0; + tda9887_configure(client); } -#if LINUX_VERSION_CODE > KERNEL_VERSION(2,5,0) -#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,14) -static int tda9887_suspend(struct device * dev, pm_message_t state) -#else -#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,13) -static int tda9887_suspend(struct device * dev, pm_message_t state, u32 level) -#else -static int tda9887_suspend(struct device * dev, u32 state, u32 level) -#endif -#endif +static void tda9887_set_freq(struct i2c_client *client, unsigned int freq) { - struct i2c_client *c = container_of(dev, struct i2c_client, dev); - struct tda9887 *t = i2c_get_clientdata(c); - - tda9887_dbg("suspend\n"); - return 0; + tda9887_configure(client); } -#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,14) -static int tda9887_resume(struct device * dev) -#else -static int tda9887_resume(struct device * dev, u32 level) -#endif +int tda9887_tuner_init(struct i2c_client *c) { - struct i2c_client *c = container_of(dev, struct i2c_client, dev); - struct tda9887 *t = i2c_get_clientdata(c); - - tda9887_dbg("resume\n"); - tda9887_configure(t); - return 0; -} -#endif + struct tuner *t = i2c_get_clientdata(c); -/* ----------------------------------------------------------------------- */ + strlcpy(c->name, "tda9887", sizeof(c->name)); -static struct i2c_driver driver = { -#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0))&&(LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,15)) - .owner = THIS_MODULE, -#endif -#if LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,15) - .name = "tda9887", - .flags = I2C_DF_NOTIFY, -#endif - .id = I2C_DRIVERID_TDA9887, - .attach_adapter = tda9887_probe, - .detach_client = tda9887_detach, - .command = tda9887_command, -#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0) - .driver = { -#if LINUX_VERSION_CODE > KERNEL_VERSION(2,6,15) - .name = "tda9887", -#endif - .suspend = tda9887_suspend, - .resume = tda9887_resume, - }, -#endif -}; -static struct i2c_client client_template = -{ - .name = "tda9887", -#if LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,15) - .flags = I2C_CLIENT_ALLOW_USE, -#endif - .driver = &driver, -}; + tda9887_info("tda988[5/6/7] found @ 0x%x (%s)\n", t->i2c.addr, + t->i2c.driver->driver.name); -static int __init tda9887_init_module(void) -{ - return i2c_add_driver(&driver); -} + t->set_tv_freq = tda9887_set_freq; + t->set_radio_freq = tda9887_set_freq; + t->standby = tda9887_standby; + t->tuner_status=tda9887_tuner_status; + t->get_afc=tda9887_get_afc; -static void __exit tda9887_cleanup_module(void) -{ - i2c_del_driver(&driver); + return 0; } -module_init(tda9887_init_module); -module_exit(tda9887_cleanup_module); - /* * Overrides for Emacs so that we follow Linus's tabbing style. * --------------------------------------------------------------------------- diff --git a/linux/drivers/media/video/tuner-core.c b/linux/drivers/media/video/tuner-core.c index 21bc09dda..be47ad3b3 100644 --- a/linux/drivers/media/video/tuner-core.c +++ b/linux/drivers/media/video/tuner-core.c @@ -243,6 +243,9 @@ static void set_type(struct i2c_client *c, unsigned int type, i2c_master_send(c,buffer,4); default_tuner_init(c); break; + case TUNER_TDA9887: + tda9887_tuner_init(c); + break; #ifdef CONFIG_XC3028 case TUNER_XCEIVE_XC3028: xc3028_init(c); @@ -280,6 +283,8 @@ static void set_addr(struct i2c_client *c, struct tuner_setup *tun_setup) { struct tuner *t = i2c_get_clientdata(c); + tuner_dbg("set addr for type %i\n", t->type); + if ( t->type == UNSET && ((tun_setup->addr == ADDR_UNSET && (t->mode_mask & tun_setup->mode_mask)) || tun_setup->addr == c->addr)) { @@ -483,6 +488,7 @@ static int tuner_attach(struct i2c_adapter *adap, int addr, t->radio_if2 = 10700 * 1000; /* 10.7MHz - FM radio */ t->audmode = V4L2_TUNER_MODE_STEREO; t->mode_mask = T_UNINITIALIZED; + t->tuner_status = tuner_status; if (tuner_debug_old) { tuner_debug = tuner_debug_old; printk(KERN_ERR "tuner: tuner_debug is deprecated and will be removed in 2.6.17.\n"); @@ -509,10 +515,14 @@ static int tuner_attach(struct i2c_adapter *adap, int addr, case 0x4b: /* If chip is not tda8290, don't register. since it can be tda9887*/ - if (tda8290_probe(&t->i2c) != 0) { - tuner_dbg("chip at addr %x is not a tda8290\n", addr); - kfree(t); - return 0; + if (tda8290_probe(&t->i2c) == 0) { + tuner_dbg("chip at addr %x is a tda8290\n", addr); + } else { + /* Default is being tda9887 */ + t->type = TUNER_TDA9887; + t->mode_mask = T_RADIO | T_ANALOG_TV | T_DIGITAL_TV; + t->mode = T_STANDBY; + goto register_client; } break; case 0x60: @@ -656,6 +666,7 @@ static int tuner_command(struct i2c_client *client, unsigned int cmd, void *arg) case TUNER_SET_STANDBY: if (check_mode(t, "TUNER_SET_STANDBY") == EINVAL) return 0; + t->mode = T_STANDBY; if (t->standby) t->standby (client); break; @@ -668,6 +679,14 @@ static int tuner_command(struct i2c_client *client, unsigned int cmd, void *arg) /* Should be implemented, since bttv calls it */ tuner_dbg("VIDIOCSAUDIO not implemented.\n"); break; + case TDA9887_SET_CONFIG: + { + int *i = arg; + + t->tda9887_config = *i; + set_freq(client, t->tv_freq); + break; + } /* --- v4l ioctls --- */ /* take care: bttv does userspace copying, we'll get a kernel pointer here... */ @@ -808,6 +827,8 @@ static int tuner_command(struct i2c_client *client, unsigned int cmd, void *arg) switch_v4l2(); tuner->type = t->mode; + if (t->get_afc) + tuner->afc=t->get_afc(client); if (t->mode == V4L2_TUNER_ANALOG_TV) tuner->capability |= V4L2_TUNER_CAP_NORM; if (t->mode != V4L2_TUNER_RADIO) { @@ -851,7 +872,8 @@ static int tuner_command(struct i2c_client *client, unsigned int cmd, void *arg) break; } case VIDIOC_LOG_STATUS: - tuner_status(client); + if (t->tuner_status) + t->tuner_status(client); break; } diff --git a/linux/drivers/media/video/tuner-types.c b/linux/drivers/media/video/tuner-types.c index 4657df313..a87683a49 100644 --- a/linux/drivers/media/video/tuner-types.c +++ b/linux/drivers/media/video/tuner-types.c @@ -1469,6 +1469,11 @@ struct tunertype tuners[] = { .params = tuner_samsung_tcpg_6121p30a_params, .count = ARRAY_SIZE(tuner_samsung_tcpg_6121p30a_params), }, + [TUNER_TDA9887] = { /* Philips TDA 9887 IF PLL Demodulator. + This chip is part of some modern tuners */ + .name = "Philips TDA988[5,6,7] IF PLL Demodulator", + /* see tda9887.c for details */ + }, }; unsigned const int tuner_count = ARRAY_SIZE(tuners); diff --git a/linux/include/media/tuner.h b/linux/include/media/tuner.h index 4548ede84..fa5829c4c 100644 --- a/linux/include/media/tuner.h +++ b/linux/include/media/tuner.h @@ -25,6 +25,8 @@ #include #include +extern int tuner_debug; + #define ADDR_UNSET (255) #define TUNER_TEMIC_PAL 0 /* 4002 FH5 (3X 7756, 9483) */ @@ -120,6 +122,7 @@ #define TUNER_THOMSON_FE6600 72 /* DViCO FusionHDTV DVB-T Hybrid */ #define TUNER_SAMSUNG_TCPG_6121P30A 73 /* Hauppauge PVR-500 PAL */ +#define TUNER_TDA9887 74 /* This tuner should be used only internally */ /* tv card specific */ #define TDA9887_PRESENT (1<<0) @@ -191,6 +194,10 @@ struct tuner { int using_v4l2; + /* used by tda9887 */ + unsigned int tda9887_config; + unsigned char tda9887_data[4]; + /* used by MT2032 */ unsigned int xogc; unsigned int radio_if2; @@ -207,6 +214,8 @@ struct tuner { void (*set_radio_freq)(struct i2c_client *c, unsigned int freq); int (*has_signal)(struct i2c_client *c); int (*is_stereo)(struct i2c_client *c); + int (*get_afc)(struct i2c_client *c); + void (*tuner_status)(struct i2c_client *c); void (*standby)(struct i2c_client *c); }; @@ -219,6 +228,7 @@ extern int tda8290_probe(struct i2c_client *c); extern int tea5767_tuner_init(struct i2c_client *c); extern int default_tuner_init(struct i2c_client *c); extern int tea5767_autodetection(struct i2c_client *c); +extern int tda9887_tuner_init(struct i2c_client *c); #if LINUX_VERSION_CODE <= KERNEL_VERSION(2,6,15) #define tuner_warn(fmt, arg...) do {\ -- cgit v1.2.3 From f36035a9e66e7645ee1ce15fdf1093493539be1e Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Sat, 24 Jun 2006 08:18:58 -0300 Subject: Add blacklist capability to tuner.pl and remove TDA9887 from the cardlist From: Mauro Carvalho Chehab tda9887 is not really an independent tuner, but part of one. It shouldn't be ponted at a userlist. Signed-off-by: Mauro Carvalho Chehab --- v4l/scripts/tuner.pl | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/v4l/scripts/tuner.pl b/v4l/scripts/tuner.pl index fcfa22e26..104c16dae 100755 --- a/v4l/scripts/tuner.pl +++ b/v4l/scripts/tuner.pl @@ -8,12 +8,17 @@ my %data; my $H = shift; my $C = shift; +my %blacklist; open IN, "<$H"; while () { # defines in header file if (/#define\s+(TUNER_\w+)\s+(\d+)/) { - $data{$1}->{nr} = $2; + my $num=$2; + $data{$1}->{nr} = $num; + if (/#define\s+TUNER_TDA9887/) { + $blacklist{$num}=1; + } next; } } @@ -37,6 +42,10 @@ while () { } foreach my $item (sort { $data{$a}->{nr} <=> $data{$b}->{nr} } keys %data) { + if ($blacklist{$data{$item}->{nr}}) { + next; + } + printf("tuner=%d - %s", $data{$item}->{nr}, $data{$item}->{name}); print "\n"; } -- cgit v1.2.3 From de2d21cb87c4d4e3124c02d856e632f355f1a002 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Sat, 24 Jun 2006 08:20:05 -0300 Subject: Added some BTTV PCI IDs for newer boards From: Mauro Carvalho Chehab Signed-off-by: Mauro Carvalho Chehab --- linux/Documentation/video4linux/CARDLIST.bttv | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/linux/Documentation/video4linux/CARDLIST.bttv b/linux/Documentation/video4linux/CARDLIST.bttv index b8dde0fb9..4efa46458 100644 --- a/linux/Documentation/video4linux/CARDLIST.bttv +++ b/linux/Documentation/video4linux/CARDLIST.bttv @@ -111,7 +111,7 @@ 110 -> IVC-100 [ff00:a132] 111 -> IVC-120G [ff00:a182,ff01:a182,ff02:a182,ff03:a182,ff04:a182,ff05:a182,ff06:a182,ff07:a182,ff08:a182,ff09:a182,ff0a:a182,ff0b:a182,ff0c:a182,ff0d:a182,ff0e:a182,ff0f:a182] 112 -> pcHDTV HD-2000 TV [7063:2000] -113 -> Twinhan DST + clones [11bd:0026,1822:0001,270f:fc00] +113 -> Twinhan DST + clones [11bd:0026,1822:0001,270f:fc00,1822:0026] 114 -> Winfast VC100 [107d:6607] 115 -> Teppro TEV-560/InterVision IV-560 116 -> SIMUS GVC1100 [aa6a:82b2] -- cgit v1.2.3 From 04e2c76f8d845ee90c1e85ee6a170618b22ff933 Mon Sep 17 00:00:00 2001 From: Mauro Carvalho Chehab Date: Sat, 24 Jun 2006 08:32:26 -0300 Subject: Whitespace cleanups From: Mauro Carvalho Chehab Signed-off-by: Mauro Carvalho Chehab --- linux/drivers/media/video/tuner-types.c | 2 +- v4l_experimental/cx88-ivtv.c | 2 +- v4l_experimental/dpl3518.c | 52 ++--- v4l_experimental/firesat/avc_api.c | 182 ++++++++--------- v4l_experimental/firesat/cmp.c | 18 +- v4l_experimental/firesat/firesat-ci.c | 10 +- v4l_experimental/firesat/firesat-rc.c | 6 +- v4l_experimental/firesat/firesat.c | 332 ++++++++++++++++---------------- v4l_experimental/v3tv/i2c-voodoo3.c | 10 +- v4l_experimental/v3tv/v3tv.c | 96 ++++----- v4l_experimental/v3tv/vpx3224.c | 24 +-- v4l_experimental/xc3028/convert.c | 2 +- v4l_experimental/xc3028/xc3028.c | 62 +++--- 13 files changed, 399 insertions(+), 399 deletions(-) diff --git a/linux/drivers/media/video/tuner-types.c b/linux/drivers/media/video/tuner-types.c index a87683a49..921ddc398 100644 --- a/linux/drivers/media/video/tuner-types.c +++ b/linux/drivers/media/video/tuner-types.c @@ -1469,7 +1469,7 @@ struct tunertype tuners[] = { .params = tuner_samsung_tcpg_6121p30a_params, .count = ARRAY_SIZE(tuner_samsung_tcpg_6121p30a_params), }, - [TUNER_TDA9887] = { /* Philips TDA 9887 IF PLL Demodulator. + [TUNER_TDA9887] = { /* Philips TDA 9887 IF PLL Demodulator. This chip is part of some modern tuners */ .name = "Philips TDA988[5,6,7] IF PLL Demodulator", /* see tda9887.c for details */ diff --git a/v4l_experimental/cx88-ivtv.c b/v4l_experimental/cx88-ivtv.c index a747e2372..8247d4286 100644 --- a/v4l_experimental/cx88-ivtv.c +++ b/v4l_experimental/cx88-ivtv.c @@ -102,7 +102,7 @@ static unsigned int ivtv_translate_ioctl(unsigned int cmd) } static int ivtv_do_ioctl(struct inode *inode, struct file *file, - unsigned int cmd, void *arg) + unsigned int cmd, void *arg) { struct cx8802_fh *fh = file->private_data; struct cx8802_dev *dev = fh->dev; diff --git a/v4l_experimental/dpl3518.c b/v4l_experimental/dpl3518.c index a7df1f078..43533767e 100644 --- a/v4l_experimental/dpl3518.c +++ b/v4l_experimental/dpl3518.c @@ -96,27 +96,27 @@ MODULE_LICENSE("GPL"); static int dpl3518_reset(struct i2c_client *client) { - static char reset_off[3] = { 0x00, 0x80, 0x00 }; - static char reset_on[3] = { 0x00, 0x00, 0x00 }; + static char reset_off[3] = { 0x00, 0x80, 0x00 }; + static char reset_on[3] = { 0x00, 0x00, 0x00 }; - i2c_master_send(client,reset_off,3); /* ignore errors here */ - if (3 != i2c_master_send(client,reset_on, 3)) { + i2c_master_send(client,reset_off,3); /* ignore errors here */ + if (3 != i2c_master_send(client,reset_on, 3)) { printk(KERN_ERR "dpl3518: chip reset failed, penguin on i2c bus?\n"); return -1; } - return 0; + return 0; } static int dpl3518_write(struct i2c_client *client, int dev, int addr, int val) { int err; - unsigned char buffer[5]; + unsigned char buffer[5]; - buffer[0] = dev; - buffer[1] = addr >> 8; - buffer[2] = addr & 0xff; - buffer[3] = val >> 8; - buffer[4] = val & 0xff; + buffer[0] = dev; + buffer[1] = addr >> 8; + buffer[2] = addr & 0xff; + buffer[3] = val >> 8; + buffer[4] = val & 0xff; for (err = 0; err < 3;) { if (5 == i2c_master_send(client, buffer, 5)) @@ -248,9 +248,9 @@ static int dpl3518_attach(struct i2c_adapter *adap, int addr, client = kmalloc(sizeof *client,GFP_KERNEL); if (!client) return -ENOMEM; - memcpy(client,&client_template,sizeof(struct i2c_client)); - client->adapter = adap; - client->addr = addr; + memcpy(client,&client_template,sizeof(struct i2c_client)); + client->adapter = adap; + client->addr = addr; dpl = kmalloc(sizeof *dpl, GFP_KERNEL); if (NULL == dpl) @@ -306,8 +306,8 @@ static int dpl3518_dev_ioctl(struct inode *inode, struct file *file, dpl3518_reset(client); break; case DPL_IOC_VERSION: - if (put_user(DPL_VERSION_CODE, (int *) arg)) - ret = -EFAULT; + if (put_user(DPL_VERSION_CODE, (int *) arg)) + ret = -EFAULT; break; case DPL_IOC_INIT: dpl3518_ioc_init(client); @@ -325,8 +325,8 @@ static int dpl3518_dev_ioctl(struct inode *inode, struct file *file, dpl3518_setmode(client, (int) arg); break; case DPL_IOC_GET_MODE: - if (put_user(dpl_device->mode, (int *) arg)) - ret = -EFAULT; + if (put_user(dpl_device->mode, (int *) arg)) + ret = -EFAULT; break; case DPL_IOC_NOISE_MODE: dpl3518_setnoisemode(client, (int) arg); @@ -368,18 +368,18 @@ static struct i2c_driver driver = { #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,54) .owner = THIS_MODULE, #endif - .name = "i2c dpl3518 driver", - .id = I2C_DRIVERID_DPL3518, - .flags = I2C_DF_NOTIFY, - .attach_adapter = dpl3518_probe, - .detach_client = dpl3518_detach, + .name = "i2c dpl3518 driver", + .id = I2C_DRIVERID_DPL3518, + .flags = I2C_DF_NOTIFY, + .attach_adapter = dpl3518_probe, + .detach_client = dpl3518_detach, }; static struct i2c_client client_template = { - I2C_DEVNAME("dpl3518"), - .id = -1, - .driver = &driver + I2C_DEVNAME("dpl3518"), + .id = -1, + .driver = &driver }; static struct file_operations dpl3518_fops = diff --git a/v4l_experimental/firesat/avc_api.c b/v4l_experimental/firesat/avc_api.c index bff42413c..eb597eaa4 100644 --- a/v4l_experimental/firesat/avc_api.c +++ b/v4l_experimental/firesat/avc_api.c @@ -11,7 +11,7 @@ #include #include -#include +#include #include #include "firesat.h" #include "avc_api.h" @@ -47,51 +47,51 @@ static int avc_down_timeout(atomic_t *done, int timeout) } static int __AVCWrite(struct firesat *firesat, const AVCCmdFrm *CmdFrm, AVCRspFrm *RspFrm) { - struct hpsb_packet *packet; + struct hpsb_packet *packet; struct node_entry *ne; - + ne = firesat->nodeentry; if(!ne) { printk("%s: lost node!\n",__FUNCTION__); return -EIO; } - + /* need all input data */ if(!firesat || !ne || !CmdFrm) return -EINVAL; - + // printk(KERN_INFO "AVCWrite command %x\n",CmdFrm->opcode); - + // for(k=0;klength;k++) // printk(KERN_INFO "CmdFrm[%d] = %08x\n", k, ((quadlet_t*)CmdFrm)[k]); - + packet=hpsb_make_writepacket(ne->host, ne->nodeid, COMMAND_REGISTER, (quadlet_t*)CmdFrm, CmdFrm->length); - + hpsb_set_packet_complete_task(packet, (void (*)(void*))avc_free_packet, packet); - + hpsb_node_fill_packet(ne, packet); - if(RspFrm) + if(RspFrm) atomic_set(&firesat->avc_reply_received, 0); if (hpsb_send_packet(packet) < 0) { - avc_free_packet(packet); - atomic_set(&firesat->avc_reply_received, 1); + avc_free_packet(packet); + atomic_set(&firesat->avc_reply_received, 1); return -EIO; } - + if(RspFrm) { - if(avc_down_timeout(&firesat->avc_reply_received,HZ/2)) { - printk("%s: timeout waiting for avc response\n",__FUNCTION__); - atomic_set(&firesat->avc_reply_received, 1); - return -ETIMEDOUT; - } - + if(avc_down_timeout(&firesat->avc_reply_received,HZ/2)) { + printk("%s: timeout waiting for avc response\n",__FUNCTION__); + atomic_set(&firesat->avc_reply_received, 1); + return -ETIMEDOUT; + } + memcpy(RspFrm,firesat->respfrm,firesat->resp_length); } - + return 0; } @@ -99,9 +99,9 @@ int AVCWrite(struct firesat*firesat, const AVCCmdFrm *CmdFrm, AVCRspFrm *RspFrm) int ret; if(down_interruptible(&firesat->avc_sem)) return -EINTR; - + ret = __AVCWrite(firesat, CmdFrm, RspFrm); - + up(&firesat->avc_sem); return ret; } @@ -111,7 +111,7 @@ DECLARE_TASKLET(schedule_remotecontrol, do_schedule_remotecontrol, 0); static void do_schedule_remotecontrol(unsigned long ignored) { struct firesat *firesat; - unsigned long flags; + unsigned long flags; spin_lock_irqsave(&firesat_list_lock, flags); list_for_each_entry(firesat,&firesat_list,list) { @@ -125,7 +125,7 @@ static void do_schedule_remotecontrol(unsigned long ignored) { tasklet_schedule(&schedule_remotecontrol); up(&firesat->avc_sem); - } + } } } spin_unlock_irqrestore(&firesat_list_lock, flags); @@ -135,8 +135,8 @@ int AVCRecv(struct firesat *firesat, u8 *data, size_t length) { // printk(KERN_INFO "%s\n",__FUNCTION__); // remote control handling - - AVCRspFrm *RspFrm = (AVCRspFrm*)data; + + AVCRspFrm *RspFrm = (AVCRspFrm*)data; if(/*RspFrm->length >= 8 && ###*/ ((RspFrm->operand[0] == SFE_VENDOR_DE_COMPANYID_0 && @@ -144,59 +144,59 @@ int AVCRecv(struct firesat *firesat, u8 *data, size_t length) { RspFrm->operand[2] == SFE_VENDOR_DE_COMPANYID_2) || (RspFrm->operand[0] == SFE_VENDOR_EL_COMPANYID_0 && RspFrm->operand[1] == SFE_VENDOR_EL_COMPANYID_1 && - RspFrm->operand[2] == SFE_VENDOR_EL_COMPANYID_2)) && + RspFrm->operand[2] == SFE_VENDOR_EL_COMPANYID_2)) && RspFrm->operand[3] == SFE_VENDOR_OPCODE_REGISTER_REMOTE_CONTROL) { if(RspFrm->resp == CHANGED) { // printk(KERN_INFO "%s: code = %02x %02x\n",__FUNCTION__,RspFrm->operand[4],RspFrm->operand[5]); firesat_got_remotecontrolcode((((u16)RspFrm->operand[4]) << 8) | ((u16)RspFrm->operand[5])); - // schedule + // schedule atomic_set(&firesat->reschedule_remotecontrol, 1); tasklet_schedule(&schedule_remotecontrol); } else if(RspFrm->resp != INTERIM) printk(KERN_INFO "%s: remote control result = %d\n",__FUNCTION__, RspFrm->resp); return 0; } - + if(atomic_read(&firesat->avc_reply_received) == 1) { printk("%s: received out-of-order AVC response, ignored\n",__FUNCTION__); return -EINVAL; } // AVCRspFrm *resp=(AVCRspFrm *)data; // int k; -/* +/* printk(KERN_INFO "resp=0x%x\n",resp->resp); printk(KERN_INFO "cts=0x%x\n",resp->cts); printk(KERN_INFO "suid=0x%x\n",resp->suid); printk(KERN_INFO "sutyp=0x%x\n",resp->sutyp); printk(KERN_INFO "opcode=0x%x\n",resp->opcode); printk(KERN_INFO "length=%d\n",resp->length); -*/ +*/ // for(k=0;k<2;k++) // printk(KERN_INFO "operand[%d]=%02x\n",k,resp->operand[k]); - + memcpy(firesat->respfrm,data,length); firesat->resp_length=length; atomic_set(&firesat->avc_reply_received, 1); - + return 0; } // tuning command for setting the relative LNB frequency (not supported by the AVC standard) static void AVCTuner_DSD_directcmd(struct firesat *firesat, struct dvb_frontend_parameters *params, AVCCmdFrm *CmdFrm) { memset(CmdFrm, 0, sizeof(AVCCmdFrm)); - + CmdFrm->cts = AVC; CmdFrm->ctype = CONTROL; CmdFrm->sutyp = 0x5; CmdFrm->suid = firesat->subunit; CmdFrm->opcode = VENDOR; - /* ### should check for elgato and use SFE_VENDOR_EL_COMPANYID_0 in this case */ - CmdFrm->operand[0]=SFE_VENDOR_DE_COMPANYID_0; - CmdFrm->operand[1]=SFE_VENDOR_DE_COMPANYID_1; - CmdFrm->operand[2]=SFE_VENDOR_DE_COMPANYID_2; + /* ### should check for elgato and use SFE_VENDOR_EL_COMPANYID_0 in this case */ + CmdFrm->operand[0]=SFE_VENDOR_DE_COMPANYID_0; + CmdFrm->operand[1]=SFE_VENDOR_DE_COMPANYID_1; + CmdFrm->operand[2]=SFE_VENDOR_DE_COMPANYID_2; CmdFrm->operand[3]=0x58; printk(KERN_INFO "%s: tuning to frequency %u\n",__FUNCTION__,params->frequency); @@ -207,7 +207,7 @@ static void AVCTuner_DSD_directcmd(struct firesat *firesat, struct dvb_frontend_ CmdFrm->operand[7] = params->frequency & 0xFF; printk(KERN_INFO "%s: symbol rate = %uBd\n",__FUNCTION__,params->u.qpsk.symbol_rate); - + CmdFrm->operand[8] = ((params->u.qpsk.symbol_rate/1000) >> 8) & 0xFF; CmdFrm->operand[9] = (params->u.qpsk.symbol_rate/1000) & 0xFF; @@ -233,7 +233,7 @@ static void AVCTuner_DSD_directcmd(struct firesat *firesat, struct dvb_frontend_ default: CmdFrm->operand[10] = 0x0; } - + if(firesat->voltage == 0xff) CmdFrm->operand[11] = 0xff; else @@ -242,7 +242,7 @@ static void AVCTuner_DSD_directcmd(struct firesat *firesat, struct dvb_frontend_ CmdFrm->operand[12] = 0xff; else CmdFrm->operand[12] = (firesat->tone==SEC_TONE_ON)?1:0; // band - + CmdFrm->length = 16; } @@ -251,9 +251,9 @@ int AVCTuner_DSD(struct firesat *firesat, struct dvb_frontend_parameters *params AVCRspFrm RspFrm; M_VALID_FLAGS flags; int k; - + // printk(KERN_INFO "%s\n", __FUNCTION__); - + if(firesat->type == FireSAT_DVB_S) AVCTuner_DSD_directcmd(firesat, params, &CmdFrm); else { @@ -290,15 +290,15 @@ int AVCTuner_DSD(struct firesat *firesat, struct dvb_frontend_parameters *params flags.Bits.reserved1 = 0; flags.Bits.Network_ID = 0; } - + memset(&CmdFrm, 0, sizeof(AVCCmdFrm)); - + CmdFrm.cts = AVC; CmdFrm.ctype = CONTROL; CmdFrm.sutyp = 0x5; CmdFrm.suid = firesat->subunit; CmdFrm.opcode = DSD; - + CmdFrm.operand[0] = 0; // source plug CmdFrm.operand[1] = 0xD2; // subfunction replace CmdFrm.operand[2] = 0x20; // system id = DVB @@ -306,7 +306,7 @@ int AVCTuner_DSD(struct firesat *firesat, struct dvb_frontend_parameters *params CmdFrm.operand[4] = (firesat->type == FireSAT_DVB_T)?0x0c:0x11; // system_specific_multiplex selection_length CmdFrm.operand[5] = flags.Valid_Word.ByteHi; // valid_flags [0] CmdFrm.operand[6] = flags.Valid_Word.ByteLo; // valid_flags [1] - + if(firesat->type == FireSAT_DVB_T) { CmdFrm.operand[7] = 0x0; CmdFrm.operand[8] = (params->frequency/10) >> 24; @@ -408,18 +408,18 @@ int AVCTuner_DSD(struct firesat *firesat, struct dvb_frontend_parameters *params default: break; } - + CmdFrm.operand[15] = 0x00; // network_ID[0] CmdFrm.operand[16] = 0x00; // network_ID[1] CmdFrm.operand[17] = 0x00; // Nr_of_dsd_sel_specs = 0 - > No PIDs are transmitted - + CmdFrm.length = 20; } else { CmdFrm.operand[7] = 0x00; CmdFrm.operand[8] = (((firesat->voltage==SEC_VOLTAGE_18)?0:1)<<6); /* 0 = H, 1 = V */ CmdFrm.operand[9] = 0x00; CmdFrm.operand[10] = 0x00; - + if(firesat->type == FireSAT_DVB_S) { /* ### relative frequency -> absolute frequency */ CmdFrm.operand[11] = (((params->frequency/4) >> 16) & 0xFF) | (2 << 6); @@ -430,11 +430,11 @@ int AVCTuner_DSD(struct firesat *firesat, struct dvb_frontend_parameters *params CmdFrm.operand[12] = ((params->frequency/4000) >> 8) & 0xFF; CmdFrm.operand[13] = (params->frequency/4000) & 0xFF; } - + CmdFrm.operand[14] = ((params->u.qpsk.symbol_rate/1000) >> 12) & 0xFF; CmdFrm.operand[15] = ((params->u.qpsk.symbol_rate/1000) >> 4) & 0xFF; CmdFrm.operand[16] = ((params->u.qpsk.symbol_rate/1000) << 4) & 0xF0; - + CmdFrm.operand[17] = 0x00; switch(params->u.qpsk.fec_inner) { case FEC_1_2: @@ -485,7 +485,7 @@ int AVCTuner_DSD(struct firesat *firesat, struct dvb_frontend_parameters *params CmdFrm.operand[20] = 0x00; CmdFrm.operand[21] = 0x00; CmdFrm.operand[22] = 0x00; // Nr_of_dsd_sel_specs = 0 - > No PIDs are transmitted - + CmdFrm.length=28; } } // AVCTuner_DSD_direct @@ -495,7 +495,7 @@ int AVCTuner_DSD(struct firesat *firesat, struct dvb_frontend_parameters *params // msleep(250); mdelay(500); - + if(status) *status=RspFrm.operand[2]; return 0; @@ -505,9 +505,9 @@ int AVCTuner_SetPIDs(struct firesat *firesat, unsigned char pidc, u16 pid[]) { AVCCmdFrm CmdFrm; AVCRspFrm RspFrm; int pos,k; - + printk(KERN_INFO "%s\n", __FUNCTION__); - + if(pidc > 16 && pidc != 0xFF) return -EINVAL; @@ -518,7 +518,7 @@ int AVCTuner_SetPIDs(struct firesat *firesat, unsigned char pidc, u16 pid[]) { CmdFrm.sutyp = 0x5; CmdFrm.suid = firesat->subunit; CmdFrm.opcode = DSD; - + CmdFrm.operand[0] = 0; // source plug CmdFrm.operand[1] = 0xD2; // subfunction replace CmdFrm.operand[2] = 0x20; // system id = DVB @@ -526,7 +526,7 @@ int AVCTuner_SetPIDs(struct firesat *firesat, unsigned char pidc, u16 pid[]) { CmdFrm.operand[4] = 0x11; // system_specific_multiplex selection_length CmdFrm.operand[5] = 0x00; // valid_flags [0] CmdFrm.operand[6] = 0x00; // valid_flags [1] - + if(firesat->type == FireSAT_DVB_T) { /* CmdFrm.operand[7] = 0x00; CmdFrm.operand[8] = 0x00;//(params->frequency/10) >> 24; @@ -536,7 +536,7 @@ int AVCTuner_SetPIDs(struct firesat *firesat, unsigned char pidc, u16 pid[]) { CmdFrm.operand[12] = 0x00; CmdFrm.operand[13] = 0x00; CmdFrm.operand[14] = 0x00; - + CmdFrm.operand[15] = 0x00; // network_ID[0] CmdFrm.operand[16] = 0x00; // network_ID[1] */ CmdFrm.operand[17] = pidc; // Nr_of_dsd_sel_specs @@ -547,22 +547,22 @@ int AVCTuner_SetPIDs(struct firesat *firesat, unsigned char pidc, u16 pid[]) { CmdFrm.operand[8] = 0x00; CmdFrm.operand[9] = 0x00; CmdFrm.operand[10] = 0x00; - + CmdFrm.operand[11] = 0x00;//(((params->frequency/4) >> 16) & 0xFF) | (2 << 6); CmdFrm.operand[12] = 0x00;//((params->frequency/4) >> 8) & 0xFF; CmdFrm.operand[13] = 0x00;//(params->frequency/4) & 0xFF; - + CmdFrm.operand[14] = 0x00;//((params->u.qpsk.symbol_rate/1000) >> 12) & 0xFF; CmdFrm.operand[15] = 0x00;//((params->u.qpsk.symbol_rate/1000) >> 4) & 0xFF; CmdFrm.operand[16] = 0x00;//((params->u.qpsk.symbol_rate/1000) << 4) & 0xF0; - + CmdFrm.operand[17] = 0x00; CmdFrm.operand[18] = 0x00; CmdFrm.operand[19] = 0x00; // modulation CmdFrm.operand[20] = 0x00; CmdFrm.operand[21] = 0x00;*/ CmdFrm.operand[22] = pidc; // Nr_of_dsd_sel_specs - + pos=23; } if(pidc != 0xFF) @@ -576,7 +576,7 @@ int AVCTuner_SetPIDs(struct firesat *firesat, unsigned char pidc, u16 pid[]) { } CmdFrm.length = pos+3; - + if((pos+3)%4) CmdFrm.length += 4 - ((pos+3)%4); @@ -584,14 +584,14 @@ int AVCTuner_SetPIDs(struct firesat *firesat, unsigned char pidc, u16 pid[]) { return k; mdelay(250); - + return 0; } int AVCIdentifySubunit(struct firesat *firesat, unsigned char *systemId, int *transport, int *has_ci) { AVCCmdFrm CmdFrm; AVCRspFrm RspFrm; - + memset(&CmdFrm,0,sizeof(AVCCmdFrm)); CmdFrm.cts = AVC; @@ -612,7 +612,7 @@ int AVCIdentifySubunit(struct firesat *firesat, unsigned char *systemId, int *tr if(AVCWrite(firesat,&CmdFrm,&RspFrm)<0) return -EIO; - + if(RspFrm.resp != STABLE && RspFrm.resp != ACCEPTED) { printk("%s: AVCWrite returned error code %d\n",__FUNCTION__,RspFrm.resp); return -EINVAL; @@ -649,15 +649,15 @@ int AVCTunerStatus(struct firesat *firesat, ANTENNA_INPUT_INFO *antenna_input_in int length; printk(KERN_INFO "%s\n", __FUNCTION__); - + memset(&CmdFrm, 0, sizeof(AVCCmdFrm)); - + CmdFrm.cts=AVC; CmdFrm.ctype=CONTROL; CmdFrm.sutyp=0x05; // tuner CmdFrm.suid=firesat->subunit; CmdFrm.opcode=READ_DESCRIPTOR; - + CmdFrm.operand[0]=DESCRIPTOR_TUNER_STATUS; CmdFrm.operand[1]=0xff; CmdFrm.operand[2]=0x00; @@ -669,7 +669,7 @@ int AVCTunerStatus(struct firesat *firesat, ANTENNA_INPUT_INFO *antenna_input_in //Absenden des AVC request und warten auf response if (AVCWrite(firesat,&CmdFrm,&RspFrm) < 0) return -EIO; - + if(RspFrm.resp != STABLE && RspFrm.resp != ACCEPTED) { printk("%s: AVCWrite returned code %d\n",__FUNCTION__,RspFrm.resp); return -EINVAL; @@ -678,7 +678,7 @@ int AVCTunerStatus(struct firesat *firesat, ANTENNA_INPUT_INFO *antenna_input_in length = (RspFrm.operand[3] << 8) + RspFrm.operand[4]; if(length == sizeof(ANTENNA_INPUT_INFO)) { - memcpy(antenna_input_info,&RspFrm.operand[7],length); + memcpy(antenna_input_info,&RspFrm.operand[7],length); return 0; } printk("%s: invalid info returned from AVC\n",__FUNCTION__); @@ -689,17 +689,17 @@ int AVCLNBControl(struct firesat *firesat, char voltage, char burst, char contto AVCCmdFrm CmdFrm; AVCRspFrm RspFrm; int i,j; - + printk(KERN_INFO "%s: voltage = %x, burst = %x, conttone = %x\n",__FUNCTION__,voltage,burst,conttone); - + memset(&CmdFrm, 0, sizeof(AVCCmdFrm)); - + CmdFrm.cts=AVC; CmdFrm.ctype=CONTROL; CmdFrm.sutyp=0x05; CmdFrm.suid=firesat->subunit; CmdFrm.opcode=VENDOR; - + /* ### should check for elgato and use SFE_VENDOR_EL_COMPANYID_0 in this case */ CmdFrm.operand[0]=SFE_VENDOR_DE_COMPANYID_0; CmdFrm.operand[1]=SFE_VENDOR_DE_COMPANYID_1; @@ -708,40 +708,40 @@ int AVCLNBControl(struct firesat *firesat, char voltage, char burst, char contto CmdFrm.operand[4]=voltage; CmdFrm.operand[5]=nrdiseq; - + i=6; - + for(j=0;javc_sem)) return -EINTR; - + ret = hpsb_read(firesat->host, firesat->nodeentry->nodeid, firesat->nodeentry->generation, addr, buffer, length); - + up(&firesat->avc_sem); return ret; } @@ -41,10 +41,10 @@ static int cmp_lock(struct firesat *firesat, quadlet_t *data, u64 addr, quadlet_ int ret; if(down_interruptible(&firesat->avc_sem)) return -EINTR; - + ret = hpsb_lock(firesat->host, firesat->nodeentry->nodeid, firesat->nodeentry->generation, addr, ext_tcode, data, arg); - + up(&firesat->avc_sem); return ret; } @@ -52,13 +52,13 @@ static int cmp_lock(struct firesat *firesat, quadlet_t *data, u64 addr, quadlet_ //try establishing a point-to-point connection (may be interrupted by a busreset int try_CMPEstablishPPconnection(struct firesat *firesat, int output_plug, int iso_channel) { unsigned int BWU; //bandwidth to allocate - + quadlet_t old_oPCR,test_oPCR = 0x0; u64 oPCR_address=0xfffff0000904ull+(output_plug << 2); int result=cmp_read(firesat, &test_oPCR, oPCR_address, 4); - + printk(KERN_INFO "%s: nodeid = %d\n",__FUNCTION__,firesat->nodeentry->nodeid); - + if (result < 0) { printk("%s: cannot read oPCR\n", __FUNCTION__); return result; @@ -100,7 +100,7 @@ int try_CMPEstablishPPconnection(struct firesat *firesat, int output_plug, int i printk(KERN_INFO "%s: trying compare_swap...\n",__FUNCTION__); printk(KERN_INFO "%s: oPCR_old: %08x, oPCR_new: %08x\n",__FUNCTION__, old_oPCR, new_oPCR); result=cmp_lock(firesat, &test_oPCR, oPCR_address, old_oPCR, 2); - + if (result < 0) { printk("%s: cannot compare_swap oPCR\n",__FUNCTION__); return result; @@ -131,7 +131,7 @@ int try_CMPBreakPPconnection(struct firesat *firesat, int output_plug,int iso_ch u64 oPCR_address=0xfffff0000904ull+(output_plug << 2); int result=cmp_read(firesat, &test_oPCR, oPCR_address, 4); - + printk(KERN_INFO "%s\n",__FUNCTION__); if (result < 0) { diff --git a/v4l_experimental/firesat/firesat-ci.c b/v4l_experimental/firesat/firesat-ci.c index 1fd96cf63..3d005cb56 100644 --- a/v4l_experimental/firesat/firesat-ci.c +++ b/v4l_experimental/firesat/firesat-ci.c @@ -11,7 +11,7 @@ static int firesat_ca_do_ioctl(struct inode *inode, struct file *file, unsigned int err; // printk(KERN_INFO "%s: ioctl %d\n",__FUNCTION__,cmd); - + switch(cmd) { case CA_RESET: err = AVCResetTPDU(firesat); @@ -67,7 +67,7 @@ static ssize_t firesat_ca_io_read(struct file *file, char __user *buf, size_t co struct firesat *firesat = (struct firesat*)((struct dvb_device*)file->private_data)->priv; char *data=kmalloc(count,GFP_KERNEL); // printk(KERN_INFO "%s: count = %d\n",__FUNCTION__,count); - int r=AVCReadTPDU(firesat, data, &count); + int r=AVCReadTPDU(firesat, data, &count); if(!r) { copy_to_user(buf,data,count); kfree(data); @@ -77,9 +77,9 @@ static ssize_t firesat_ca_io_read(struct file *file, char __user *buf, size_t co return 0; } -static int firesat_ca_io_open(struct inode *inode, struct file *file) { +static int firesat_ca_io_open(struct inode *inode, struct file *file) { printk(KERN_INFO "%s!\n",__FUNCTION__); - return dvb_generic_open(inode, file); + return dvb_generic_open(inode, file); } static int firesat_ca_io_release(struct inode *inode, struct file *file) { @@ -89,7 +89,7 @@ static int firesat_ca_io_release(struct inode *inode, struct file *file) { static unsigned int firesat_ca_io_poll(struct file *file, poll_table *wait) { // printk(KERN_INFO "%s!\n",__FUNCTION__); - return POLLIN; + return POLLIN; } static struct file_operations firesat_ca_fops = { diff --git a/v4l_experimental/firesat/firesat-rc.c b/v4l_experimental/firesat/firesat-rc.c index 8cc57573d..702f90f6c 100644 --- a/v4l_experimental/firesat/firesat-rc.c +++ b/v4l_experimental/firesat/firesat-rc.c @@ -49,7 +49,7 @@ int firesat_register_rc(void) { memset(&firesat_idev, 0, sizeof(firesat_idev)); firesat_idev.evbit[0] = BIT(EV_KEY); - + for(index=0;firesat_irtable[index] != 0; index++) set_bit(firesat_irtable[index], firesat_idev.keybit); @@ -65,7 +65,7 @@ int firesat_unregister_rc(void) { int firesat_got_remotecontrolcode(u16 code) { u16 keycode; - + if(code > 0x4500 && code < 0x4520) keycode = firesat_irtable[code - 0x4501]; else if(code > 0x453f && code < 0x4543) @@ -73,7 +73,7 @@ int firesat_got_remotecontrolcode(u16 code) { else { printk("%s: invalid key code 0x%04x\n",__FUNCTION__,code); return -EINVAL; - } + } input_report_key(&firesat_idev, keycode, 1); input_report_key(&firesat_idev, keycode, 0); diff --git a/v4l_experimental/firesat/firesat.c b/v4l_experimental/firesat/firesat.c index 167c5a709..dcf268702 100644 --- a/v4l_experimental/firesat/firesat.c +++ b/v4l_experimental/firesat/firesat.c @@ -44,111 +44,111 @@ static struct ieee1394_device_id firesat_id_table[] = { { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, - .model_id = 0x11, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x11, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, - .model_id = 0x12, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x12, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x13, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x13, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x14, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x14, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x21, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x21, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x22, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x22, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x23, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x23, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x24, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x24, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x25, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x25, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x26, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x26, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x27, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x27, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x34, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x34, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x35, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x35, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { .match_flags = /*IEEE1394_MATCH_VENDOR_ID |*/ IEEE1394_MATCH_MODEL_ID | IEEE1394_MATCH_SPECIFIER_ID | IEEE1394_MATCH_VERSION, // .vendor_id = FIRESAT_Vendor_ID & 0xffffff, // .vendor_id = 0x000000, - .model_id = 0x36, - .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, - .version = AVC_SW_VERSION_ENTRY & 0xffffff + .model_id = 0x36, + .specifier_id = AVC_UNIT_SPEC_ID_ENTRY & 0xffffff, + .version = AVC_SW_VERSION_ENTRY & 0xffffff }, { } }; @@ -163,7 +163,7 @@ static void firesat_add_host (struct hpsb_host *host); static void firesat_remove_host (struct hpsb_host *host); static void firesat_host_reset(struct hpsb_host *host); static void iso_receive(struct hpsb_host *host, int channel, quadlet_t *data, - size_t length); + size_t length); static void fcp_request(struct hpsb_host *host, int nodeid, int direction, int cts, u8 *data, size_t length); @@ -187,7 +187,7 @@ static struct dvb_frontend_info firesat_S_frontend_info = { .symbol_rate_max = 40000000, .caps = FE_CAN_INVERSION_AUTO | FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 | FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | - FE_CAN_FEC_AUTO | FE_CAN_QPSK, + FE_CAN_FEC_AUTO | FE_CAN_QPSK, }; static struct dvb_frontend_info firesat_C_frontend_info = { @@ -217,18 +217,18 @@ static struct dvb_frontend_info firesat_T_frontend_info = { static void firesat_add_host (struct hpsb_host *host) { struct ti_ohci *ohci; // printk(KERN_INFO "FireSAT add_host (nodeid = 0x%x)\n",host->node_id); - + /* We only work with the OHCI-1394 driver */ if (strcmp(host->driver->name, OHCI1394_DRIVER_NAME)) return; - + ohci = (struct ti_ohci *)host->hostdata; - + if (!hpsb_create_hostinfo(&firesat_highlevel, host, 0)) { printk(KERN_ERR "Cannot allocate hostinfo\n"); return; } - + hpsb_set_hostinfo(&firesat_highlevel, host, ohci); hpsb_set_hostinfo_key(&firesat_highlevel, host, ohci->host->id); } @@ -243,65 +243,65 @@ static void firesat_host_reset(struct hpsb_host *host) { struct firewireheader { union { - struct { - unsigned char tcode:4; - unsigned char sy:4; - unsigned char tag:2; - unsigned char channel:6; - - unsigned char length_l; - unsigned char length_h; - } hdr; - unsigned long val; + struct { + unsigned char tcode:4; + unsigned char sy:4; + unsigned char tag:2; + unsigned char channel:6; + + unsigned char length_l; + unsigned char length_h; + } hdr; + unsigned long val; }; }; struct CIPHeader { union { - struct { - unsigned char syncbits:2; - unsigned char sid:6; - unsigned char dbs; - unsigned char fn:2; - unsigned char qpc:3; - unsigned char sph:1; - unsigned char rsv:2; - unsigned char dbc; - unsigned char syncbits2:2; - unsigned char fmt:6; - unsigned long fdf:24; - } cip; - unsigned long long val; + struct { + unsigned char syncbits:2; + unsigned char sid:6; + unsigned char dbs; + unsigned char fn:2; + unsigned char qpc:3; + unsigned char sph:1; + unsigned char rsv:2; + unsigned char dbc; + unsigned char syncbits2:2; + unsigned char fmt:6; + unsigned long fdf:24; + } cip; + unsigned long long val; }; }; struct MPEG2Header { union { - struct { - unsigned char sync; // must be 0x47 - unsigned char transport_error_indicator:1; - unsigned char payload_unit_start_indicator:1; - unsigned char transport_priority:1; - unsigned short pid:13; - unsigned char transport_scrambling_control:2; - unsigned char adaption_field_control:2; - unsigned char continuity_counter:4; - } hdr; - unsigned long val; + struct { + unsigned char sync; // must be 0x47 + unsigned char transport_error_indicator:1; + unsigned char payload_unit_start_indicator:1; + unsigned char transport_priority:1; + unsigned short pid:13; + unsigned char transport_scrambling_control:2; + unsigned char adaption_field_control:2; + unsigned char continuity_counter:4; + } hdr; + unsigned long val; }; }; static void iso_receive(struct hpsb_host *host, int channel, quadlet_t *data, - size_t length) { + size_t length) { // printk(KERN_INFO "FireSAT iso_receive: channel %d, length = %d\n", channel, length); - + if(length <= 12) return; // ignore empty packets else { struct firesat *firesat=NULL; struct firesat *firesat_entry; unsigned long flags; - + spin_lock_irqsave(&firesat_list_lock, flags); list_for_each_entry(firesat_entry,&firesat_list,list) { if(firesat_entry->host == host && firesat_entry->isochannel == channel) { @@ -310,15 +310,15 @@ static void iso_receive(struct hpsb_host *host, int channel, quadlet_t *data, } } spin_unlock_irqrestore(&firesat_list_lock, flags); - + if(firesat) { char *buf=((char*)data) + sizeof(struct firewireheader)+sizeof(struct CIPHeader); int count = (length-sizeof(struct CIPHeader)) / 192; - + // printk(KERN_INFO "%s: length = %u\n data[0] = %08x\n data[1] = %08x\n data[2] = %08x\n data[3] = %08x\n data[4] = %08x\n",__FUNCTION__, length, data[0],data[1],data[2],data[3],data[4]); - + while (count--) { - + if(buf[sizeof(quadlet_t) /*timestamp*/] == 0x47) dvb_dmx_swfilter_packet(&firesat->demux, &buf[sizeof(quadlet_t)]); else @@ -332,10 +332,10 @@ static void iso_receive(struct hpsb_host *host, int channel, quadlet_t *data, static void fcp_request(struct hpsb_host *host, int nodeid, int direction, int cts, u8 *data, size_t length) { // printk(KERN_INFO "FireSAT fcp_request length=%d\n",length); - if(length>0 && ((data[0] & 0xF0) >> 4) == 0) { + if(length>0 && ((data[0] & 0xF0) >> 4) == 0) { struct firesat *firesat=NULL; struct firesat *firesat_entry; - unsigned long flags; + unsigned long flags; spin_lock_irqsave(&firesat_list_lock, flags); list_for_each_entry(firesat_entry,&firesat_list,list) { @@ -356,7 +356,7 @@ static void fcp_request(struct hpsb_host *host, int nodeid, int direction, static int firesat_frontend_ioctl(struct dvb_frontend *frontend, unsigned int cmd, void *arg) { struct firesat *firesat=frontend->data; - + switch(cmd) { case FE_INIT: firesat->isochannel = firesat->adapter->num << 1 | (firesat->subunit & 0x1); // ### ask IRM @@ -401,13 +401,13 @@ static int firesat_frontend_ioctl(struct dvb_frontend *frontend, if(AVCTunerStatus(firesat,&info)) { return -EINVAL; } -// printk(KERN_INFO "%s: NoRF=%c\n",__FUNCTION__,info.NoRF?'y':'n'); +// printk(KERN_INFO "%s: NoRF=%c\n",__FUNCTION__,info.NoRF?'y':'n'); if(info.NoRF) *status = 0; else *status = *status = FE_HAS_SIGNAL | FE_HAS_VITERBI | FE_HAS_SYNC | FE_HAS_CARRIER | FE_HAS_LOCK; - + break; } case FE_READ_BER: { @@ -418,10 +418,10 @@ static int firesat_frontend_ioctl(struct dvb_frontend *frontend, if(AVCTunerStatus(firesat,&info)) { return -EINVAL; } - + // *ber = *(u32*)info.BER; /* might need some byte ordering correction */ *ber = ((info.BER[0] << 24) & 0xFF) | ((info.BER[1] << 16) & 0xFF) | ((info.BER[2] << 8) & 0xFF) | (info.BER[3] & 0xFF); - + break; } case FE_READ_SIGNAL_STRENGTH: { @@ -432,9 +432,9 @@ static int firesat_frontend_ioctl(struct dvb_frontend *frontend, if(AVCTunerStatus(firesat,&info)) { return -EINVAL; } - + *signal = info.SignalStrength; - + break; } case FE_READ_SNR: @@ -444,18 +444,18 @@ static int firesat_frontend_ioctl(struct dvb_frontend *frontend, struct dvb_frontend_parameters *p = (struct dvb_frontend_parameters *)arg; // printk(KERN_INFO "FE_GET_INFO\n"); - + // printk(KERN_INFO "%s: FE_SET_FRONTEND\n", __FUNCTION__); - + // printk(KERN_INFO " frequency->%d\n", p->frequency); // printk(KERN_INFO " symbol_rate->%d\n",p->u.qam.symbol_rate); // printk(KERN_INFO " inversion->%d\n", p->inversion); - + // if(AVCTuner_DSIT(firesat, 0/*###*/, p, NULL)) // return -EINVAL; if(AVCTuner_DSD(firesat, p, NULL) != ACCEPTED) return -EINVAL; - + break; } case FE_GET_FRONTEND: @@ -464,7 +464,7 @@ static int firesat_frontend_ioctl(struct dvb_frontend *frontend, default: return -EINVAL; } - + return 0; } @@ -472,10 +472,10 @@ static struct firesat_channel *firesat_channel_allocate(struct firesat *firesat) int k; printk(KERN_INFO "%s\n",__FUNCTION__); - + if(down_interruptible(&firesat->demux_sem)) return NULL; - + for(k=0;k<16;k++) { printk(KERN_INFO "%s: channel %d: active = %d, pid = 0x%x\n",__FUNCTION__,k,firesat->channel[k].active,firesat->channel[k].pid); if(firesat->channel[k].active == 0) { @@ -484,25 +484,25 @@ static struct firesat_channel *firesat_channel_allocate(struct firesat *firesat) return &firesat->channel[k]; } } - + up(&firesat->demux_sem); return NULL; // no more channels available } static int firesat_channel_collect(struct firesat *firesat, int *pidc, u16 pid[]) { int k, l=0; - + if(down_interruptible(&firesat->demux_sem)) return -EINTR; - + for(k=0;k<16;k++) if(firesat->channel[k].active == 1) pid[l++] = firesat->channel[k].pid; - + up(&firesat->demux_sem); - + *pidc = l; - + return 0; } @@ -523,7 +523,7 @@ static int firesat_start_feed(struct dvb_demux_feed *dvbdmxfeed) { u16 pids[16]; printk(KERN_INFO "%s (pid %u)\n",__FUNCTION__,dvbdmxfeed->pid); - + switch (dvbdmxfeed->type) { case DMX_TYPE_TS: case DMX_TYPE_SEC: @@ -549,30 +549,30 @@ static int firesat_start_feed(struct dvb_demux_feed *dvbdmxfeed) { } else { channel = firesat_channel_allocate(firesat); } - + if(!channel) { printk("%s: busy!\n",__FUNCTION__); return -EBUSY; } - + dvbdmxfeed->priv = channel; channel->dvbdmxfeed = dvbdmxfeed; channel->pid = dvbdmxfeed->pid; channel->type = dvbdmxfeed->type; channel->firesat = firesat; - + if(firesat_channel_collect(firesat, &pidc, pids)) { firesat_channel_release(firesat, channel); return -EINTR; } - + if((k=AVCTuner_SetPIDs(firesat, pidc, pids))) { firesat_channel_release(firesat, channel); printk("%s: AVCTuner failed with error %d\n",__FUNCTION__,k); return k; } - + return 0; } @@ -581,11 +581,11 @@ static int firesat_stop_feed(struct dvb_demux_feed *dvbdmxfeed) { struct firesat *firesat=(struct firesat*)demux->priv; int k, l=0; u16 pids[16]; - + printk(KERN_INFO "%s (pid %u)\n",__FUNCTION__,dvbdmxfeed->pid); - if (dvbdmxfeed->type == DMX_TYPE_TS && !((dvbdmxfeed->ts_type & TS_PACKET) && - (demux->dmx.frontend->source != DMX_MEMORY_FE))) { + if (dvbdmxfeed->type == DMX_TYPE_TS && !((dvbdmxfeed->ts_type & TS_PACKET) && + (demux->dmx.frontend->source != DMX_MEMORY_FE))) { if (dvbdmxfeed->ts_type & TS_DECODER) { if (dvbdmxfeed->pes_type >= DMX_TS_PES_OTHER || !demux->pesfilter[dvbdmxfeed->pes_type]) @@ -596,7 +596,7 @@ static int firesat_stop_feed(struct dvb_demux_feed *dvbdmxfeed) { if (!(dvbdmxfeed->ts_type & TS_DECODER && dvbdmxfeed->pes_type < DMX_TS_PES_OTHER)) { return 0; - } + } } if(down_interruptible(&firesat->demux_sem)) @@ -611,11 +611,11 @@ static int firesat_stop_feed(struct dvb_demux_feed *dvbdmxfeed) { up(&firesat->demux_sem); return k; } - + ((struct firesat_channel*)dvbdmxfeed->priv)->active = 0; up(&firesat->demux_sem); - + return 0; } @@ -631,16 +631,16 @@ static int firesat_probe(struct device *dev) { printk("%s: couldn't allocate memory.\n", __FUNCTION__); return -ENOMEM; } - + // printk(KERN_INFO "FireSAT: Detected device with GUID %08lx%04lx%04lx\n",(unsigned long)((ud->ne->guid)>>32),(unsigned long)(ud->ne->guid & 0xFFFF),(unsigned long)ud->ne->guid_vendor_id); printk(KERN_INFO "%s: loading device\n", __FUNCTION__); - + firesats[0]=NULL; firesats[1]=NULL; - + ud->device.driver_data = firesats; - - for(subunit=0;subunitavc_sem, 1); atomic_set(&firesat->avc_reply_received, 1); sema_init(&firesat->demux_sem, 1); atomic_set(&firesat->reschedule_remotecontrol, 0); - + spin_lock_irqsave(&firesat_list_lock, flags); INIT_LIST_HEAD(&firesat->list); list_add_tail(&firesat->list, &firesat_list); @@ -727,18 +727,18 @@ static int firesat_probe(struct device *dev) { firesat->model_name, THIS_MODULE)) < 0) { printk("%s: dvb_register_adapter failed: error %d\n", __FUNCTION__, result); - + /* ### cleanup */ spin_lock_irqsave(&firesat_list_lock, flags); list_del(&firesat->list); spin_unlock_irqrestore(&firesat_list_lock, flags); kfree(firesat); - + return result; } - + firesat->demux.dmx.capabilities = 0/*DMX_TS_FILTERING | DMX_SECTION_FILTERING*/; - + firesat->demux.priv = (void *)firesat; firesat->demux.filternum = 16; firesat->demux.feednum = 16; @@ -746,82 +746,82 @@ static int firesat_probe(struct device *dev) { firesat->demux.stop_feed = firesat_stop_feed; firesat->demux.write_to_decoder = NULL; - + if ((result = dvb_dmx_init(&firesat->demux)) < 0) { printk("%s: dvb_dmx_init failed: error %d\n", __FUNCTION__, result); - + dvb_unregister_adapter(firesat->adapter); - + return result; } - + firesat->dmxdev.filternum = 16; firesat->dmxdev.demux = &firesat->demux.dmx; firesat->dmxdev.capabilities = 0; - + if ((result = dvb_dmxdev_init(&firesat->dmxdev, firesat->adapter)) < 0) { printk("%s: dvb_dmxdev_init failed: error %d\n", __FUNCTION__, result); - + dvb_dmx_release(&firesat->demux); dvb_unregister_adapter(firesat->adapter); - + return result; } - + firesat->frontend.source = DMX_FRONTEND_0; - + if ((result = firesat->demux.dmx.add_frontend(&firesat->demux.dmx, &firesat->frontend)) < 0) { printk("%s: dvb_dmx_init failed: error %d\n", __FUNCTION__, result); - + dvb_dmxdev_release(&firesat->dmxdev); dvb_dmx_release(&firesat->demux); dvb_unregister_adapter(firesat->adapter); - + return result; } - + if ((result = firesat->demux.dmx.connect_frontend(&firesat->demux.dmx, &firesat->frontend)) < 0) { printk("%s: dvb_dmx_init failed: error %d\n", __FUNCTION__, result); - + firesat->demux.dmx.remove_frontend(&firesat->demux.dmx, &firesat->frontend); dvb_dmxdev_release(&firesat->dmxdev); dvb_dmx_release(&firesat->demux); dvb_unregister_adapter(firesat->adapter); - + return result; } - + dvb_net_init(firesat->adapter, &firesat->dvbnet, &firesat->demux.dmx); - + if((result= dvb_register_frontend(firesat_frontend_ioctl,firesat->adapter,firesat,firesat->frontend_info,THIS_MODULE)) < 0) { printk("%s: dvb_register_frontend_new failed: error %d\n", __FUNCTION__, result); /* ### cleanup */ - + return result; } if(firesat->has_ci) firesat_ca_init(firesat); - + firesats[subunit] = firesat; } // loop fuer alle tuner am board if(firesats[0]) AVCRegisterRemoteControl(firesats[0]); - + return 0; } static int firesat_remove(struct device *dev) { struct unit_directory *ud=container_of(dev, struct unit_directory, device); struct firesat **firesats=ud->device.driver_data; - + if(firesats) { int k; for(k=0;k<2;k++) @@ -830,7 +830,7 @@ static int firesat_remove(struct device *dev) { if(firesats[k]->has_ci) firesat_ca_release(firesats[k]); dvb_unregister_frontend(firesat_frontend_ioctl,firesats[k]->adapter); - + dvb_net_release(&firesats[k]->dvbnet); firesats[k]->demux.dmx.close(&firesats[k]->demux.dmx); firesats[k]->demux.dmx.remove_frontend(&firesats[k]->demux.dmx, &firesats[k]->frontend); @@ -841,14 +841,14 @@ static int firesat_remove(struct device *dev) { spin_lock_irqsave(&firesat_list_lock, flags); list_del(&firesats[k]->list); spin_unlock_irqrestore(&firesat_list_lock, flags); - + kfree(firesats[k]->respfrm); kfree(firesats[k]); } kfree(firesats); } else printk("%s: can't get firesat handle\n",__FUNCTION__); - + printk(KERN_INFO "FireSAT: Removing device with vendor id 0x%x, model id 0x%x.\n",ud->vendor_id,ud->model_id); return 0; } @@ -858,7 +858,7 @@ static int firesat_update(struct unit_directory *ud) { struct firesat **firesats=ud->device.driver_data; int k; // loop over subunits - + for(k=0;k<2;k++) if(firesats[k]) { firesats[k]->nodeentry=ud->ne; @@ -877,8 +877,8 @@ static struct hpsb_protocol_driver firesat_driver = { .driver = { .name = "firesat", .bus = &ieee1394_bus_type, - .probe = firesat_probe, - .remove = firesat_remove, + .probe = firesat_probe, + .remove = firesat_remove, }, }; @@ -889,20 +889,20 @@ static int __init firesat_init(void) hpsb_register_highlevel(&firesat_highlevel); ret = hpsb_register_protocol(&firesat_driver); if(ret) { - printk(KERN_ERR "FireSAT: failed to register protocol\n"); - hpsb_unregister_highlevel(&firesat_highlevel); - return ret; + printk(KERN_ERR "FireSAT: failed to register protocol\n"); + hpsb_unregister_highlevel(&firesat_highlevel); + return ret; } if((ret=firesat_register_rc())) printk("%s: firesat_register_rc return error code %d (ignored)\n",__FUNCTION__,ret); - + return 0; } static void __exit firesat_exit(void){ firesat_unregister_rc(); - + hpsb_unregister_protocol(&firesat_driver); hpsb_unregister_highlevel(&firesat_highlevel); printk("FireSAT quit\n"); diff --git a/v4l_experimental/v3tv/i2c-voodoo3.c b/v4l_experimental/v3tv/i2c-voodoo3.c index 3ec720f78..d303a6a9c 100644 --- a/v4l_experimental/v3tv/i2c-voodoo3.c +++ b/v4l_experimental/v3tv/i2c-voodoo3.c @@ -1,11 +1,11 @@ /* voodoo3.c - Part of lm_sensors, Linux kernel modules for hardware - monitoring + monitoring Copyright (c) 1998, 1999 Frodo Looijaard , Philip Edelbrock , Ralph Metzler , and Mark D. Studebaker - + Based on code written by Ralph Metzler and Simon Vogl @@ -168,7 +168,7 @@ static struct i2c_algo_bit_data voo_i2c_bit_data = { static struct i2c_adapter voodoo3_i2c_adapter = { .owner = THIS_MODULE, - .class = I2C_CLASS_TV_ANALOG, + .class = I2C_CLASS_TV_ANALOG, .name = "I2C Voodoo3/Banshee adapter", .algo_data = &voo_i2c_bit_data, }; @@ -185,7 +185,7 @@ static struct i2c_algo_bit_data voo_ddc_bit_data = { static struct i2c_adapter voodoo3_ddc_adapter = { .owner = THIS_MODULE, - .class = I2C_CLASS_DDC, + .class = I2C_CLASS_DDC, .name = "DDC Voodoo3/Banshee adapter", .algo_data = &voo_ddc_bit_data, }; @@ -222,7 +222,7 @@ static int __devinit voodoo3_probe(struct pci_dev *dev, const struct pci_device_ static void __devexit voodoo3_remove(struct pci_dev *dev) { i2c_bit_del_bus(&voodoo3_i2c_adapter); - i2c_bit_del_bus(&voodoo3_ddc_adapter); + i2c_bit_del_bus(&voodoo3_ddc_adapter); iounmap(ioaddr); } diff --git a/v4l_experimental/v3tv/v3tv.c b/v4l_experimental/v3tv/v3tv.c index a29569c6a..6f105cb3b 100644 --- a/v4l_experimental/v3tv/v3tv.c +++ b/v4l_experimental/v3tv/v3tv.c @@ -321,21 +321,21 @@ static struct conf_struct voodoo3_init_reg[] = { static struct conf_struct Chromakey_Enable[] = { {V3REG_vidProcCfg, 1, 5, 5} }; -static struct conf_struct Horizontal_Decimation_Enable[] = +static struct conf_struct Horizontal_Decimation_Enable[] = { {V3REG_vidInFormat, 1, 20, 20} }; /* Horizontal Decimation enable */ -static struct conf_struct Horizontal_Decimation_Disable[] = +static struct conf_struct Horizontal_Decimation_Disable[] = { {V3REG_vidInFormat, 0, 20, 20} }; /* Horizontal Decimation disable */ -static struct conf_struct Vertical_Decimation_Enable[] = +static struct conf_struct Vertical_Decimation_Enable[] = { {V3REG_vidInFormat, 1, 21, 21} }; /* Vertical Decimation enable */ -static struct conf_struct Vertical_Decimation_Disable[] = +static struct conf_struct Vertical_Decimation_Disable[] = { {V3REG_vidInFormat, 0, 21, 21} }; /* Vertical Decimation enable */ -static struct conf_struct Horizontal_Magnification_Enable[] = +static struct conf_struct Horizontal_Magnification_Enable[] = { {V3REG_vidProcCfg, 1, 14, 14} }; /* Horizontal Scaling enable */ -static struct conf_struct Horizontal_Magnification_Disable[] = +static struct conf_struct Horizontal_Magnification_Disable[] = { {V3REG_vidProcCfg, 0, 14, 14} }; /* Horizontal Scaling disable */ -static struct conf_struct Vertical_Magnification_Enable[] = +static struct conf_struct Vertical_Magnification_Enable[] = { {V3REG_vidProcCfg, 1, 15, 15} }; /* Vertical Scaling enable */ -static struct conf_struct Vertical_Magnification_Disable[] = +static struct conf_struct Vertical_Magnification_Disable[] = { {V3REG_vidProcCfg, 0, 15, 15} }; /* Vertical Scaling disable */ static struct conf_struct Overlay_Disable[] = @@ -356,9 +356,9 @@ static struct conf_struct Overlay_Enable[] = { {V3REG_vidProcCfg, 0, 31, 31}, /* No overlay backend de-interlacing */ {V3REG_vidInFormat, 1, 14, 14}, /* VMI interface enable */ {V3REG_vidSerialParallelPort, 1, 0, 0} }; /* VMI host interface enable */ -static struct conf_struct Overlay_Filter_Off[] = { +static struct conf_struct Overlay_Filter_Off[] = { {V3REG_vidProcCfg, 0, 17, 16} }; /* overlay filter OFF */ -static struct conf_struct Overlay_Filter_On[] = { +static struct conf_struct Overlay_Filter_On[] = { {V3REG_vidProcCfg, 3, 17, 16} }; /* overlay filter ON */ static struct conf_struct Disable_VMI_Interrupt[] = { @@ -465,7 +465,7 @@ inline static void voodoo3_regor(unsigned int reg, unsigned int data, unsigned i if (!voodoo || !voodoo->io_base) return; - + reg_ptr = (unsigned int *) voodoo->io_base + reg; *reg_ptr = (*reg_ptr & ~mask) | (data & mask); } @@ -619,7 +619,7 @@ void inline *rvmalloc(signed long size) adr = (unsigned long)mem; while (size > 0) { page = kvirt_to_pa(adr); - mem_map_reserve(virt_to_page(__va(page))); + mem_map_reserve(virt_to_page(__va(page))); adr += PAGE_SIZE; size -= PAGE_SIZE; } @@ -636,7 +636,7 @@ void inline rvfree(void *mem, signed long size) adr = (unsigned long)mem; while (size > 0) { page = kvirt_to_pa(adr); - mem_map_unreserve(virt_to_page(__va(page))); + mem_map_unreserve(virt_to_page(__va(page))); adr += PAGE_SIZE; size -= PAGE_SIZE; } @@ -744,7 +744,7 @@ int v3tv_get_adapter(struct i2c_adapter *adapter) default: return 0; } -#endif +#endif if (debug) printk(KERN_INFO "v3tv: i2c_attach_client found adapter: %s\n", adapter->name); @@ -1364,7 +1364,7 @@ static int fbuffer_alloc() /* * This maps the vmalloced and reserved fbuffer to user space. * - * FIXME: + * FIXME: * - PAGE_READONLY should suffice!? * - remap_page_range is kind of inefficient for page by page remapping. * But e.g. pte_alloc() does not work in modules ... :-( @@ -1495,7 +1495,7 @@ static int get_control(struct voodoo_data *voodoo, struct v4l2_control *c) { struct video_audio va; int i; - + for (i = 0; i < V3TV_CTLS; i++) if (v3tv_ctls[i].id == c->id) break; @@ -1623,7 +1623,7 @@ static int v3tv_radio_do_ioctl(struct inode *inode, struct file *file, case VIDIOC_ENUMINPUT: { struct v4l2_input *i = arg; - + printk("v3tv: VIDIOC_ENUMINPUT %d.\n",i->index); if( i->index != 0 ) { return -EINVAL; @@ -1693,8 +1693,8 @@ static int v3tv_radio_do_ioctl(struct inode *inode, struct file *file, printk("v3tv: VIDIOC_QUERYCAP\n"); - strcpy(cap->driver,"v3tv radio"); - strcpy(cap->card,"Voodoo3 TV 3500"); + strcpy(cap->driver,"v3tv radio"); + strcpy(cap->card,"Voodoo3 TV 3500"); strcpy(cap->bus_info,"AGP Slot 0"); cap->version = KERNEL_VERSION(0,1,0); cap->capabilities = @@ -1801,7 +1801,7 @@ static int v3tv_radio_do_ioctl(struct inode *inode, struct file *file, return -EINVAL; if (unlikely(f->type != V4L2_TUNER_RADIO)) return -EINVAL; -#if 0 +#if 0 if (f->frequency < 45 * 16000) { // if (f->frequency < 696000) { printk ("v3tv: Radio program does not support the VIDEO_TUNER_LOW flag\n"); @@ -1953,7 +1953,7 @@ static int v3tv_radio_do_ioctl(struct inode *inode, struct file *file, printk ("v3tv: FIXME: VIDIOSAUDIO: Audio=%d\n", va.audio); - // FIXME. This should really be checked. + // FIXME. This should really be checked. // If only user programs respected it :-( return -EINVAL; } @@ -2028,9 +2028,9 @@ static int v3tv_radio_open(struct inode *inode, struct file *file) i2c_clients_command(voodoo->voodoo_i2c_adapter, TUNER_SET_TYPE_ADDR, &tun_setup); - } + } - i2c_clients_command(voodoo->voodoo_i2c_adapter, + i2c_clients_command(voodoo->voodoo_i2c_adapter, AUDC_SET_RADIO, &voodoo->tuner_type); // up(&voodoo->lock); @@ -2158,19 +2158,19 @@ static irqreturn_t v3tv_video_irq(int irq, void *dev_id, struct pt_regs *regs) voodoo->initialized &= ~I_irq; voodoo->decoder_enabled = 0; - i2c_clients_command(voodoo->voodoo_i2c_adapter, + i2c_clients_command(voodoo->voodoo_i2c_adapter, DECODER_ENABLE_OUTPUT, &voodoo->decoder_enabled); - struct video_audio va; + struct video_audio va; - i2c_clients_command(voodoo->voodoo_i2c_adapter, VIDIOCGAUDIO, &va); + i2c_clients_command(voodoo->voodoo_i2c_adapter, VIDIOCGAUDIO, &va); - va.volume = 0; - va.balance = 32768; - i2c_clients_command(voodoo->voodoo_i2c_adapter, VIDIOCSAUDIO, &va); + va.volume = 0; + va.balance = 32768; + i2c_clients_command(voodoo->voodoo_i2c_adapter, VIDIOCSAUDIO, &va); */ -/* Optionaly disable Video In. */ +/* Optionaly disable Video In. */ // v3tv_conf(VMI_Disable, CONF_SIZE(VMI_Disable)); break; } @@ -2225,7 +2225,7 @@ static int v3tv_video_open(struct inode *inode, struct file *file) if (debug) printk(KERN_DEBUG "v3tv: open minor=%d\n",minor); - if (voodoo->vbi_dev && + if (voodoo->vbi_dev && voodoo->vbi_dev->minor == minor) type = V4L2_BUF_TYPE_VBI_CAPTURE; if (voodoo->video_dev && @@ -2279,12 +2279,12 @@ static int v3tv_video_open(struct inode *inode, struct file *file) i2c_clients_command(voodoo->voodoo_i2c_adapter, TUNER_SET_TYPE_ADDR, &tun_setup); - } + } // struct video_audio va; // i2c_clients_command(voodoo->voodoo_i2c_adapter, VIDIOCGAUDIO, &va); - + // va.flags = VIDEO_AUDIO_MUTE; // va.volume = 65535; // va.balance = 32768; /* FIXME. This shouldn't be necessary */ @@ -2311,7 +2311,7 @@ static int v3tv_video_release(struct inode *inode, struct file *file) struct voodoo_data *voodoo_tv = file->private_data; if (voodoo_tv->initialized & I_irq) { - free_irq(voodoo_tv->dev->irq, voodoo_tv->dev); + free_irq(voodoo_tv->dev->irq, voodoo_tv->dev); voodoo_tv->initialized &= ~I_irq; } @@ -2337,7 +2337,7 @@ static int v3tv_video_release(struct inode *inode, struct file *file) return 0; } -/* No poll now +/* No poll now static int v4l_voodoo_poll (struct video_device*dev, structfile *file, struct poll_table *wait) @@ -2422,14 +2422,14 @@ static long v3tv_voodoo_read(struct video_device *dev, char *buf,unsigned long c current->state = TASK_RUNNING; return -ERESTARTSYS; } - schedule(); + schedule(); current->state = TASK_INTERRUPTIBLE; } remove_wait_queue(&capture_wait, &wait); current->state = TASK_RUNNING; - capture_ready = 0; + capture_ready = 0; ptr = (u8 *)buf; len=capture_w * 3 * capture_h; @@ -2585,7 +2585,7 @@ static int v3tv_video_do_ioctl(struct inode *inode, struct file *file, i2c_clients_command(voodoo_tv->voodoo_i2c_adapter, VIDIOCSCHAN, &vchan); - sarg = (voodoo_tv->channel) ? AUDIO_EXTERN_2 : + sarg = (voodoo_tv->channel) ? AUDIO_EXTERN_2 : AUDIO_TUNER; i2c_clients_command(voodoo_tv->voodoo_i2c_adapter, AUDC_SET_INPUT, &sarg); @@ -2615,7 +2615,7 @@ static int v3tv_video_do_ioctl(struct inode *inode, struct file *file, "contrast: 0x%04x colour: 0x%04x " "w: 0x%04x\n", voodoo_tv->picture_settings.brightness, - voodoo_tv->picture_settings.hue, + voodoo_tv->picture_settings.hue, voodoo_tv->picture_settings.contrast, voodoo_tv->picture_settings.colour, voodoo_tv->picture_settings.whiteness); @@ -2651,7 +2651,7 @@ static int v3tv_video_do_ioctl(struct inode *inode, struct file *file, /* Set picture parameters here */ if ((pic->palette != VIDEO_PALETTE_RGB565) && (pic->palette != VIDEO_PALETTE_RGB24) && - (pic->palette != VIDEO_PALETTE_RGB32)) + (pic->palette != VIDEO_PALETTE_RGB32)) v3tv_set_palette(pic); #else if (pic->palette != voodoo_tv->picture_settings.palette) { @@ -2840,7 +2840,7 @@ static int v3tv_video_do_ioctl(struct inode *inode, struct file *file, return 0; } case VIDIOCSTUNER: - { + { struct video_tuner *tuner_info = arg; if (tuner_info->tuner) /* Only tuner 0 */ @@ -2853,7 +2853,7 @@ static int v3tv_video_do_ioctl(struct inode *inode, struct file *file, DECODER_SET_NORM, &voodoo_tv->norm); return 0; - } + } case VIDIOCGFREQ: { @@ -3068,7 +3068,7 @@ static void v3tv_unregister_video(struct voodoo_data *voodoo) if (voodoo->video_dev) { if (-1 != voodoo->video_dev->minor) { printk("v3tv: unregistering device video%d (%d)\n", - voodoo->video_dev->minor & 0x1f, + voodoo->video_dev->minor & 0x1f, voodoo->video_dev->minor); video_unregister_device(voodoo->video_dev); } @@ -3078,7 +3078,7 @@ static void v3tv_unregister_video(struct voodoo_data *voodoo) if (voodoo->vbi_dev) { if (-1 != voodoo->vbi_dev->minor) { printk("v3tv: unregistering device vbi%d (%d)\n", - voodoo->vbi_dev->minor & 0x1f, + voodoo->vbi_dev->minor & 0x1f, voodoo->vbi_dev->minor); video_unregister_device(voodoo->vbi_dev); } @@ -3088,7 +3088,7 @@ static void v3tv_unregister_video(struct voodoo_data *voodoo) if (voodoo->radio_dev) { if (-1 != voodoo->radio_dev->minor) { printk("v3tv: unregistering device radio%d (%d)\n", - voodoo->radio_dev->minor & 0x1f, + voodoo->radio_dev->minor & 0x1f, voodoo->radio_dev->minor); video_unregister_device(voodoo->radio_dev); } @@ -3108,7 +3108,7 @@ static int __devinit v3tv_register_video(struct voodoo_data *voodoo) /* vbi */ voodoo->vbi_dev = &v3tv_vdev_vbi; - if (video_register_device(voodoo->vbi_dev,VFL_TYPE_VBI,vbi_nr)<0) + if (video_register_device(voodoo->vbi_dev,VFL_TYPE_VBI,vbi_nr)<0) goto err; printk(KERN_INFO "v3tv: registered device vbi%d (%d)\n", voodoo->vbi_dev->minor & 0x1f, voodoo->vbi_dev->minor); @@ -3135,7 +3135,7 @@ int v3tv_video_init(struct voodoo_data *voodoo) switch (voodoo->model) { case VOODOO3_MODEL_NTSC: printk(KERN_INFO "v3tv: NTSC model.\n"); - snprintf(voodoo->name, sizeof(voodoo->name), + snprintf(voodoo->name, sizeof(voodoo->name), "Voodoo3 TV 3500 %s", "NTSC"); voodoo->norm = VIDEO_MODE_NTSC; voodoo->tuner_type = TUNER_PHILIPS_NTSC; /* 2 */ @@ -3178,7 +3178,7 @@ int v3tv_video_init(struct voodoo_data *voodoo) i2c_clients_command(voodoo->voodoo_i2c_adapter, TUNER_SET_TYPE_ADDR, &tun_setup); - } + } voodoo->picture_settings.brightness = 0x8000; voodoo->picture_settings.hue = 0x8000; diff --git a/v4l_experimental/v3tv/vpx3224.c b/v4l_experimental/v3tv/vpx3224.c index 5e4a10694..fb5f05b79 100644 --- a/v4l_experimental/v3tv/vpx3224.c +++ b/v4l_experimental/v3tv/vpx3224.c @@ -1,4 +1,4 @@ -/* +/* * vpx3224d & vpx3225d video decoder driver version 0.0.1 * @@ -407,26 +407,26 @@ static const u16 init_ntsc[] = { static const u16 init_pal[] = { RFP_vbegin1, 0, /* Window 1 vertical begin */ // RFP_vbegin1, 23, /* Window 1 vertical begin */ - RFP_vlinesin1, 288 + 16, /* Vertical lines in (16 lines + RFP_vlinesin1, 288 + 16, /* Vertical lines in (16 lines * skipped by the VFE) */ RFP_vlinesout1, 288 + 16, /* Vertical lines out (16 lines * skipped by the VFE) */ RFP_hbeg1, 16, /* Horizontal begin */ RFP_hlen1, 768, /* Horizontal length */ - RFP_npix1, 784, /* Number of pixels + RFP_npix1, 784, /* Number of pixels * Must be >= Horizontal begin + Horizontal length */ RFP_sdt, 0, /* PAL B,G,H,I, */ }; static const u16 init_secam[] = { RFP_vbegin1, 23 - 16, /* Window 1 vertical begin */ - RFP_vlinesin1, 288 + 16, /* Vertical lines in (16 lines + RFP_vlinesin1, 288 + 16, /* Vertical lines in (16 lines * skipped by the VFE) */ - RFP_vlinesout1, 288 + 16, /* Vertical lines out (16 lines + RFP_vlinesout1, 288 + 16, /* Vertical lines out (16 lines * skipped by the VFE) */ RFP_hbeg1, 16, /* Horizontal begin */ RFP_hlen1, 768, /* Horizontal length */ - RFP_npix1, 784, /* Number of pixels + RFP_npix1, 784, /* Number of pixels * Must be >= Horizontal begin + Horizontal length */ RFP_sdt, 2, /* SECAM, */ }; @@ -447,7 +447,7 @@ static const u16 init_fp[] = { /* 16 reg-value pairs */ static const unsigned char init_common[] = { R_llc, 0, /* active mode, outputs enabled */ - R_driver_a, 0x24, /* Port A, PIXCLK, HF# & FE# + R_driver_a, 0x24, /* Port A, PIXCLK, HF# & FE# * stra1 = 100; stra2 = 100 */ R_driver_b, 0x20, /* Port B, HREF, VREF, PREF & * strb2 = 100 */ @@ -672,7 +672,7 @@ static int vpx3224_get_status(struct i2c_client *client) static int vpx3224_auto_norm(struct i2c_client *client) { /* * Auto is not supported by the vpx3224/5d. - * Scan the valid modes, read RFP_asr for score, pick the highest score. + * Scan the valid modes, read RFP_asr for score, pick the highest score. * With an NTSC M signal, there is no clear winner... */ DEB(printk (KERN_INFO "%s: Auto video mode detection not supported.\n", @@ -735,7 +735,7 @@ static int vpx3224_set_norm(struct i2c_client *client, int norm) break; /* case VIDEO_MODE_AUTO: norm = vpx3224_auto_norm(client); - break; + break; */ default: return -EINVAL; @@ -886,7 +886,7 @@ static int vpx3224_init_client(struct i2c_client *client) return res; /* * We cycle through the supported modes - * and read RFP_asr to see which is valid. + * and read RFP_asr to see which is valid. * restore this line to see output when module loads */ /* vpx3224_auto_norm(client); */ res = vpx3224_set_norm(client, VIDEO_MODE_NTSC); @@ -1209,8 +1209,8 @@ static int vpx3224_detect_client(struct i2c_adapter *adapter, int address, /* i2c_attach_client adds client to client->adapter->clients[] returns: - -EBUSY - -ENOMEM enlarge I2C_CLIENT_MAX */ + -EBUSY + -ENOMEM enlarge I2C_CLIENT_MAX */ res = i2c_attach_client(client); DEB2(printk(KERN_INFO "%s: i2c_attach_client returned %d\n", client->name, res)); diff --git a/v4l_experimental/xc3028/convert.c b/v4l_experimental/xc3028/convert.c index ca765f269..9d3be0c29 100644 --- a/v4l_experimental/xc3028/convert.c +++ b/v4l_experimental/xc3028/convert.c @@ -12,7 +12,7 @@ struct{ int length2; } xc_firmware[]={{"Terratec","\x2a\x03\xe5\xe0\x00\x07\xf4\xd0\x01\xc0\x70\xe0\x00\x07","\x2a\x00\xbc\xe0\x00\x07\xb0\xf1\x05\x01\x67\x82\x02\x82",2480,3890}, {"Terratec 2006-02-08","\x2a\x03\x9a\xe0\x00\x07\xf4\xd0\x01\xc0\x70\xe0\x00\x07","\x2a\x00\xcf\xe0\x00\x07\xb0\xf1\x05\x01\x78\x82\x02\x82",2632,3852}, - {"Hauppauge","\x2a\x03\xcc\xe0\x00\x07\xf4\xd0\x01\xc0\x70\xe0\x00\x07","\x2a\x00\xbe\xe0\x00\x07\xb9\xf1\x05\x01\x69\x82\x02\x82",2532,3886}}; + {"Hauppauge","\x2a\x03\xcc\xe0\x00\x07\xf4\xd0\x01\xc0\x70\xe0\x00\x07","\x2a\x00\xbe\xe0\x00\x07\xb9\xf1\x05\x01\x69\x82\x02\x82",2532,3886}}; int main(int argc, char **argv){ FILE *file; diff --git a/v4l_experimental/xc3028/xc3028.c b/v4l_experimental/xc3028/xc3028.c index d2936638e..5db6107eb 100644 --- a/v4l_experimental/xc3028/xc3028.c +++ b/v4l_experimental/xc3028/xc3028.c @@ -51,7 +51,7 @@ int xc3028_probe(struct i2c_client *c) static void xc3028_set_tv_freq(struct i2c_client *c, unsigned int freq){ // the frequency is just shifted and there's a 1:1 relation for all frequencies // E11 is Das Erste in Germany/Ulm all other channels match their frequency too - + unsigned char chanbuf[4]; freq<<=2; chanbuf[0]=0; @@ -84,7 +84,7 @@ int xc3028_init(struct i2c_client *c) // request firmware from /lib/firmware, note that the file got extracted by the convert application I wrote and which is available // on linuxtv.org / xc3028 - + ret = request_firmware(&fw, XC3028_DEFAULT_FIRMWARE, &t->i2c.dev); if (ret) { printk("xc3028: no firmware uploaded please check %s\n",XC3028_DEFAULT_FIRMWARE); @@ -94,7 +94,7 @@ int xc3028_init(struct i2c_client *c) firmware_size = fw->size; // small firmware check, both firmwares I have are between 6 and 7k bytes - + if(fw->size>7000||fw->size<6000){ printk("xc3028: wrong firmware provided!\n"); release_firmware(fw); @@ -111,7 +111,7 @@ int xc3028_init(struct i2c_client *c) } linebuffer[d++]=0x2a; - dev=c->adapter->algo_data; + dev=c->adapter->algo_data; // 0x08 is a GPIO address of the em28xx has to get replaced with something generic here @@ -122,23 +122,23 @@ int xc3028_init(struct i2c_client *c) // the firmware always starts with 0x2a + 0x40 bytes payload I use to add the offset of the first part // as the first line into the firmware binary - + while(i!=fw->size){ linebuffer[d++]=firmware[i]; if((d%64==0&&d!=0)||i==fwoff+txtlen){ i2c_master_send(c,linebuffer,d); if(i==(fwoff+txtlen)){ - i2c_master_send(c,"\x02\x02",2); - i2c_master_send(c,"\x02\x03",2); - i2c_master_send(c,"\x00\x8c",2); - i2c_master_send(c,"\x00\x00\x00\x00",4); + i2c_master_send(c,"\x02\x02",2); + i2c_master_send(c,"\x02\x03",2); + i2c_master_send(c,"\x00\x8c",2); + i2c_master_send(c,"\x00\x00\x00\x00",4); // another reset here dev->em28xx_write_regs(dev, 0x08, "\x6d", 1); mdelay(100); dev->em28xx_write_regs(dev, 0x08, "\x7d", 1); mdelay(100); - - } + + } linebuffer[0]=0x2a; d=1; } @@ -149,30 +149,30 @@ int xc3028_init(struct i2c_client *c) firmware[firmware_size-1]=0; release_firmware(fw); - + /* MAGIC VALUES */ - i2c_master_send(c,"\x13\x39",2); - i2c_master_send(c,"\x0c\x80\xf0\xf7\x3e\x75\xc1\x8a\xe4\x02\x00",11); - i2c_master_send(c,"\x05\x0f\xee\xaa\x5f\xea\x90",7); - i2c_master_send(c,"\x06\x00\x0a\x4d\x8c\xf2\xd8\xcf\x30\x79\x9f",11); - i2c_master_send(c,"\x0b\x0d\xa4\x6c",4); - i2c_master_send(c,"\x0a\x01\x67\x24\x40\x08\xc3\x20\x10\x64\x3c\xfa\xf7\xe1\x0c\x2c",0x10); - i2c_master_send(c,"\x09\x0b",0x2); - i2c_master_send(c,"\x10\x13",0x2); - i2c_master_send(c,"\x16\x12",0x2); - i2c_master_send(c,"\x1f\x02",0x2); - i2c_master_send(c,"\x21\x02",0x2); - i2c_master_send(c,"\x01\x02",0x2); - i2c_master_send(c,"\x2b\x10",0x2); - i2c_master_send(c,"\x02\x02",0x2); - i2c_master_send(c,"\x02\x03",0x2); - i2c_master_send(c,"\x00\x8c",0x2); + i2c_master_send(c,"\x13\x39",2); + i2c_master_send(c,"\x0c\x80\xf0\xf7\x3e\x75\xc1\x8a\xe4\x02\x00",11); + i2c_master_send(c,"\x05\x0f\xee\xaa\x5f\xea\x90",7); + i2c_master_send(c,"\x06\x00\x0a\x4d\x8c\xf2\xd8\xcf\x30\x79\x9f",11); + i2c_master_send(c,"\x0b\x0d\xa4\x6c",4); + i2c_master_send(c,"\x0a\x01\x67\x24\x40\x08\xc3\x20\x10\x64\x3c\xfa\xf7\xe1\x0c\x2c",0x10); + i2c_master_send(c,"\x09\x0b",0x2); + i2c_master_send(c,"\x10\x13",0x2); + i2c_master_send(c,"\x16\x12",0x2); + i2c_master_send(c,"\x1f\x02",0x2); + i2c_master_send(c,"\x21\x02",0x2); + i2c_master_send(c,"\x01\x02",0x2); + i2c_master_send(c,"\x2b\x10",0x2); + i2c_master_send(c,"\x02\x02",0x2); + i2c_master_send(c,"\x02\x03",0x2); + i2c_master_send(c,"\x00\x8c",0x2); #if 0 // if set video will mostly be black/white - if set_color is called instead the video will have color - i2c_master_send(c,"\x80\x01\x00\x00",0x4); - i2c_master_send(c,"\x00\x5e\x00\x29",0x4); - i2c_master_send(c,"\x2b\x1a",0x2); + i2c_master_send(c,"\x80\x01\x00\x00",0x4); + i2c_master_send(c,"\x00\x5e\x00\x29",0x4); + i2c_master_send(c,"\x2b\x1a",0x2); #endif xceive_set_color(c); t->set_tv_freq = xc3028_set_tv_freq; -- cgit v1.2.3