提交 062ef0d4 编写于 作者: E Ezequiel García 提交者: Mauro Carvalho Chehab

[media] staging: media: Remove easycap driver

This driver has been replaced by stk1160.
Signed-off-by: NEzequiel Garcia <elezegarcia@gmail.com>
Signed-off-by: NMauro Carvalho Chehab <mchehab@redhat.com>
上级 9cb2173e
......@@ -25,8 +25,6 @@ source "drivers/staging/media/cxd2099/Kconfig"
source "drivers/staging/media/dt3155v4l/Kconfig"
source "drivers/staging/media/easycap/Kconfig"
source "drivers/staging/media/go7007/Kconfig"
source "drivers/staging/media/solo6x10/Kconfig"
......
obj-$(CONFIG_DVB_AS102) += as102/
obj-$(CONFIG_DVB_CXD2099) += cxd2099/
obj-$(CONFIG_EASYCAP) += easycap/
obj-$(CONFIG_LIRC_STAGING) += lirc/
obj-$(CONFIG_SOLO6X10) += solo6x10/
obj-$(CONFIG_VIDEO_DT3155) += dt3155v4l/
......
config EASYCAP
tristate "EasyCAP USB ID 05e1:0408 support"
depends on USB && VIDEO_DEV && SND
select SND_PCM
---help---
This is an integrated audio/video driver for EasyCAP cards with
USB ID 05e1:0408. It supports two hardware variants:
* EasyCAP USB 2.0 Video Adapter with Audio, Model DC60,
having input cables labelled CVBS, S-VIDEO, AUDIO(L), AUDIO(R)
* EasyCAP002 4-Channel USB 2.0 DVR, having input cables labelled
1, 2, 3, 4 and an unlabelled input cable for a microphone.
To compile this driver as a module, choose M here: the
module will be called easycap
config EASYCAP_DEBUG
bool "Enable EasyCAP driver debugging"
depends on EASYCAP
---help---
This option enables debug printouts
To enable debug, pass the debug level to the debug module
parameter:
modprobe easycap debug=[0..9]
easycap-objs := easycap_main.o
easycap-objs += easycap_low.o
easycap-objs += easycap_ioctl.o
easycap-objs += easycap_settings.o
easycap-objs += easycap_testcard.o
easycap-objs += easycap_sound.o
obj-$(CONFIG_EASYCAP) += easycap.o
ccflags-y := -Wall
***********************************************************
* EasyCAP USB 2.0 Video Adapter with Audio, Model DC60 *
* and *
* EasyCAP002 4-Channel USB 2.0 DVR *
***********************************************************
Mike Thomas <rmthomas@sciolus.org>
SUPPORTED HARDWARE
------------------
This driver is intended for use with hardware having USB ID 05e1:0408.
Two kinds of EasyCAP have this USB ID, namely:
* EasyCAP USB 2.0 Video Adapter with Audio, Model DC60,
having input cables labelled CVBS, S-VIDEO, AUDIO(L), AUDIO(R)
* EasyCAP002 4-Channel USB 2.0 DVR, having input cables labelled
1, 2, 3, 4 and an unlabelled input cable for a microphone.
BUILD OPTIONS AND DEPENDENCIES
------------------------------
Unless EASYCAP_DEBUG is defined during compilation it will not be possible
to select a debug level at the time of module installation.
KNOWN RUNTIME ISSUES
--------------------
(1) Intentionally, this driver will not stream material which is unambiguously
identified by the hardware as copy-protected. Normal video output will be
present for about a minute but will then freeze when this situation arises.
(2) The controls for luminance, contrast, saturation, hue and volume may not
always work properly.
(3) Reduced-resolution S-Video seems to suffer from moire artefacts.
INPUT NUMBERING
---------------
For the EasyCAP with S-VIDEO input cable the driver regards a request for
inputs numbered 0 or 1 as referring to CVBS and a request for input
numbered 5 as referring to S-VIDEO.
For the EasyCAP with four CVBS inputs the driver expects to be asked for
any one of inputs numbered 1,2,3,4. If input 0 is asked for, it is
interpreted as input 1.
MODULE PARAMETERS
-----------------
Three module parameters are defined:
debug the easycap module is configured at diagnostic level n (0 to 9)
gain audio gain level n (0 to 31, default is 16)
bars whether to display testcard bars when incoming video signal is lost
0 => no, 1 => yes (default)
SUPPORTED TV STANDARDS AND RESOLUTIONS
--------------------------------------
The following TV standards are natively supported by the hardware and are
usable as (for example) the "norm=" parameter in the mplayer command:
PAL_BGHIN, NTSC_N_443,
PAL_Nc, NTSC_N,
SECAM, NTSC_M, NTSC_M_JP,
PAL_60, NTSC_443,
PAL_M.
In addition, the driver offers "custom" pseudo-standards with a framerate
which is 20% of the usual framerate. These pseudo-standards are named:
PAL_BGHIN_SLOW, NTSC_N_443_SLOW,
PAL_Nc_SLOW, NTSC_N_SLOW,
SECAM_SLOW, NTSC_M_SLOW, NTSC_M_JP_SLOW,
PAL_60_SLOW, NTSC_443_SLOW,
PAL_M_SLOW.
The available picture sizes are:
at 25 frames per second: 720x576, 704x576, 640x480, 360x288, 320x240;
at 30 frames per second: 720x480, 640x480, 360x240, 320x240.
WHAT'S TESTED AND WHAT'S NOT
----------------------------
This driver is known to work with mplayer, mencoder, tvtime, zoneminder,
xawtv, gstreamer and sufficiently recent versions of vlc. An interface
to ffmpeg is implemented, but serious audio-video synchronization problems
remain.
The driver is designed to support all the TV standards accepted by the
hardware, but as yet it has actually been tested on only a few of these.
I have been unable to test and calibrate the S-video input myself because I
do not possess any equipment with S-video output.
UDEV RULES
----------
In order that the special files /dev/easycap0 and /dev/easysnd1 are created
with conveniently relaxed permissions when the EasyCAP is plugged in, a file
is preferably to be provided in directory /etc/udev/rules.d with content:
ACTION!="add|change", GOTO="easycap_rules_end"
ATTRS{idVendor}=="05e1", ATTRS{idProduct}=="0408", \
MODE="0666", OWNER="root", GROUP="root"
LABEL="easycap_rules_end"
MODPROBE CONFIGURATION
----------------------
The easycap module is in competition with the module snd-usb-audio for the
EasyCAP's audio channel, and its installation can be aided by providing a
file in directory /etc/modprobe.d with content:
options easycap gain=16 bars=1
install easycap /sbin/rmmod snd-usb-audio; /sbin/modprobe --ignore-install easycap
ACKNOWLEGEMENTS AND REFERENCES
------------------------------
This driver makes use of information contained in the Syntek Semicon DC-1125
Driver, presently maintained at http://sourceforge.net/projects/syntekdriver/
by Nicolas Vivien. Particularly useful has been a patch to the latter driver
provided by Ivor Hewitt in January 2009. The NTSC implementation is taken
from the work of Ben Trask.
/*****************************************************************************
* *
* easycap.h *
* *
*****************************************************************************/
/*
*
* Copyright (C) 2010 R.M. Thomas <rmthomas@sciolus.org>
*
*
* This 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.
*
* The software 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 software; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
*/
/*****************************************************************************/
/*---------------------------------------------------------------------------*/
/*
* THE FOLLOWING PARAMETERS ARE UNDEFINED:
*
* EASYCAP_DEBUG
*
* IF REQUIRED THEY MUST BE EXTERNALLY DEFINED, FOR EXAMPLE AS COMPILER
* OPTIONS.
*/
/*---------------------------------------------------------------------------*/
#ifndef __EASYCAP_H__
#define __EASYCAP_H__
/*---------------------------------------------------------------------------*/
/*
* THESE ARE NORMALLY DEFINED
*/
/*---------------------------------------------------------------------------*/
#define PATIENCE 500
#define PERSEVERE
/*---------------------------------------------------------------------------*/
/*
* THESE ARE FOR MAINTENANCE ONLY - NORMALLY UNDEFINED:
*/
/*---------------------------------------------------------------------------*/
#undef EASYCAP_TESTCARD
/*---------------------------------------------------------------------------*/
#include <linux/kernel.h>
#include <linux/errno.h>
#include <linux/init.h>
#include <linux/slab.h>
#include <linux/module.h>
#include <linux/kref.h>
#include <linux/usb.h>
#include <linux/uaccess.h>
#include <linux/i2c.h>
#include <linux/workqueue.h>
#include <linux/poll.h>
#include <linux/mm.h>
#include <linux/fs.h>
#include <linux/delay.h>
#include <linux/types.h>
#include <linux/vmalloc.h>
#include <linux/sound.h>
#include <sound/core.h>
#include <sound/pcm.h>
#include <sound/pcm_params.h>
#include <sound/info.h>
#include <sound/initval.h>
#include <sound/control.h>
#include <media/v4l2-dev.h>
#include <media/v4l2-device.h>
#include <linux/videodev2.h>
#include <linux/soundcard.h>
/*---------------------------------------------------------------------------*/
/* VENDOR, PRODUCT: Syntek Semiconductor Co., Ltd
*
* EITHER EasyCAP USB 2.0 Video Adapter with Audio, Model No. DC60
* with input cabling: AUDIO(L), AUDIO(R), CVBS, S-VIDEO.
*
* OR EasyCAP 4CHANNEL USB 2.0 DVR, Model No. EasyCAP002
* with input cabling: MICROPHONE, CVBS1, CVBS2, CVBS3, CVBS4.
*/
/*---------------------------------------------------------------------------*/
#define USB_EASYCAP_VENDOR_ID 0x05e1
#define USB_EASYCAP_PRODUCT_ID 0x0408
#define EASYCAP_DRIVER_VERSION "0.9.01"
#define EASYCAP_DRIVER_DESCRIPTION "easycapdc60"
#define DONGLE_MANY 8
#define INPUT_MANY 6
/*---------------------------------------------------------------------------*/
/*
* DEFAULT LUMINANCE, CONTRAST, SATURATION AND HUE
*/
/*---------------------------------------------------------------------------*/
#define SAA_0A_DEFAULT 0x7F
#define SAA_0B_DEFAULT 0x3F
#define SAA_0C_DEFAULT 0x2F
#define SAA_0D_DEFAULT 0x00
/*---------------------------------------------------------------------------*/
/*
* VIDEO STREAMING PARAMETERS:
* USB 2.0 PROVIDES FOR HIGH-BANDWIDTH ENDPOINTS WITH AN UPPER LIMIT
* OF 3072 BYTES PER MICROFRAME for wMaxPacketSize.
*/
/*---------------------------------------------------------------------------*/
#define VIDEO_ISOC_BUFFER_MANY 16
#define VIDEO_ISOC_ORDER 3
#define VIDEO_ISOC_FRAMESPERDESC ((unsigned int) 1 << VIDEO_ISOC_ORDER)
#define USB_2_0_MAXPACKETSIZE 3072
#if (USB_2_0_MAXPACKETSIZE > PAGE_SIZE)
#error video_isoc_buffer[.] will not be big enough
#endif
#define VIDEO_JUNK_TOLERATE VIDEO_ISOC_BUFFER_MANY
#define VIDEO_LOST_TOLERATE 50
/*---------------------------------------------------------------------------*/
/*
* VIDEO BUFFERS
*/
/*---------------------------------------------------------------------------*/
#define FIELD_BUFFER_SIZE (203 * PAGE_SIZE)
#define FRAME_BUFFER_SIZE (405 * PAGE_SIZE)
#define FIELD_BUFFER_MANY 4
#define FRAME_BUFFER_MANY 6
/*---------------------------------------------------------------------------*/
/*
* AUDIO STREAMING PARAMETERS
*/
/*---------------------------------------------------------------------------*/
#define AUDIO_ISOC_BUFFER_MANY 16
#define AUDIO_ISOC_ORDER 1
#define AUDIO_ISOC_FRAMESPERDESC 32
#define AUDIO_ISOC_BUFFER_SIZE (PAGE_SIZE << AUDIO_ISOC_ORDER)
/*---------------------------------------------------------------------------*/
/*
* AUDIO BUFFERS
*/
/*---------------------------------------------------------------------------*/
#define AUDIO_FRAGMENT_MANY 32
#define PAGES_PER_AUDIO_FRAGMENT 4
/*---------------------------------------------------------------------------*/
/*
* IT IS ESSENTIAL THAT EVEN-NUMBERED STANDARDS ARE 25 FRAMES PER SECOND,
* ODD-NUMBERED STANDARDS ARE 30 FRAMES PER SECOND.
* THE NUMBERING OF STANDARDS MUST NOT BE CHANGED WITHOUT DUE CARE. NOT
* ONLY MUST THE PARAMETER
* STANDARD_MANY
* BE CHANGED TO CORRESPOND TO THE NEW NUMBER OF STANDARDS, BUT ALSO THE
* NUMBERING MUST REMAIN AN UNBROKEN ASCENDING SEQUENCE: DUMMY STANDARDS
* MAY NEED TO BE ADDED. APPROPRIATE CHANGES WILL ALWAYS BE REQUIRED IN
* ROUTINE fillin_formats() AND POSSIBLY ELSEWHERE. BEWARE.
*/
/*---------------------------------------------------------------------------*/
#define PAL_BGHIN 0
#define PAL_Nc 2
#define SECAM 4
#define NTSC_N 6
#define NTSC_N_443 8
#define NTSC_M 1
#define NTSC_443 3
#define NTSC_M_JP 5
#define PAL_60 7
#define PAL_M 9
#define PAL_BGHIN_SLOW 10
#define PAL_Nc_SLOW 12
#define SECAM_SLOW 14
#define NTSC_N_SLOW 16
#define NTSC_N_443_SLOW 18
#define NTSC_M_SLOW 11
#define NTSC_443_SLOW 13
#define NTSC_M_JP_SLOW 15
#define PAL_60_SLOW 17
#define PAL_M_SLOW 19
#define STANDARD_MANY 20
/*---------------------------------------------------------------------------*/
/*
* ENUMS
*/
/*---------------------------------------------------------------------------*/
enum {
AT_720x576,
AT_704x576,
AT_640x480,
AT_720x480,
AT_360x288,
AT_320x240,
AT_360x240,
RESOLUTION_MANY
};
enum {
FMT_UYVY,
FMT_YUY2,
FMT_RGB24,
FMT_RGB32,
FMT_BGR24,
FMT_BGR32,
PIXELFORMAT_MANY
};
enum {
FIELD_NONE,
FIELD_INTERLACED,
INTERLACE_MANY
};
#define SETTINGS_MANY (STANDARD_MANY * \
RESOLUTION_MANY * \
2 * \
PIXELFORMAT_MANY * \
INTERLACE_MANY)
/*---------------------------------------------------------------------------*/
/*
* STRUCTURE DEFINITIONS
*/
/*---------------------------------------------------------------------------*/
struct easycap_dongle {
struct easycap *peasycap;
struct mutex mutex_video;
struct mutex mutex_audio;
};
/*---------------------------------------------------------------------------*/
struct data_buffer {
struct list_head list_head;
void *pgo;
void *pto;
u16 kount;
u16 input;
};
/*---------------------------------------------------------------------------*/
struct data_urb {
struct list_head list_head;
struct urb *purb;
int isbuf;
int length;
};
/*---------------------------------------------------------------------------*/
struct easycap_standard {
u16 mask;
struct v4l2_standard v4l2_standard;
};
struct easycap_format {
u16 mask;
char name[128];
struct v4l2_format v4l2_format;
};
struct inputset {
int input;
int input_ok;
int standard_offset;
int standard_offset_ok;
int format_offset;
int format_offset_ok;
int brightness;
int brightness_ok;
int contrast;
int contrast_ok;
int saturation;
int saturation_ok;
int hue;
int hue_ok;
};
/*---------------------------------------------------------------------------*/
/*
* easycap.ilk == 0 => CVBS+S-VIDEO HARDWARE, AUDIO wMaxPacketSize=256
* easycap.ilk == 2 => CVBS+S-VIDEO HARDWARE, AUDIO wMaxPacketSize=9
* easycap.ilk == 3 => FOUR-CVBS HARDWARE, AUDIO wMaxPacketSize=9
*/
/*---------------------------------------------------------------------------*/
struct easycap {
int isdongle;
int minor;
struct video_device video_device;
struct v4l2_device v4l2_device;
int status;
unsigned int audio_pages_per_fragment;
unsigned int audio_bytes_per_fragment;
unsigned int audio_buffer_page_many;
#define UPSAMPLE
#ifdef UPSAMPLE
s16 oldaudio;
#endif /*UPSAMPLE*/
int ilk;
bool microphone;
struct usb_device *pusb_device;
struct usb_interface *pusb_interface;
struct kref kref;
int queued[FRAME_BUFFER_MANY];
int done[FRAME_BUFFER_MANY];
wait_queue_head_t wq_video;
wait_queue_head_t wq_audio;
wait_queue_head_t wq_trigger;
int input;
int polled;
int standard_offset;
int format_offset;
struct inputset inputset[INPUT_MANY];
bool ntsc;
int fps;
int usec;
int tolerate;
int skip;
int skipped;
int lost[INPUT_MANY];
int merit[180];
int video_interface;
int video_altsetting_on;
int video_altsetting_off;
int video_endpointnumber;
int video_isoc_maxframesize;
int video_isoc_buffer_size;
int video_isoc_framesperdesc;
int video_isoc_streaming;
int video_isoc_sequence;
int video_idle;
int video_eof;
int video_junk;
struct data_buffer video_isoc_buffer[VIDEO_ISOC_BUFFER_MANY];
struct data_buffer field_buffer[FIELD_BUFFER_MANY]
[(FIELD_BUFFER_SIZE/PAGE_SIZE)];
struct data_buffer frame_buffer[FRAME_BUFFER_MANY]
[(FRAME_BUFFER_SIZE/PAGE_SIZE)];
struct list_head urb_video_head;
struct list_head *purb_video_head;
u8 cache[8];
u8 *pcache;
int video_mt;
int audio_mt;
u32 isequence;
int vma_many;
/*---------------------------------------------------------------------------*/
/*
* BUFFER INDICATORS
*/
/*---------------------------------------------------------------------------*/
int field_fill; /* Field buffer being filled by easycap_complete(). */
/* Bumped only by easycap_complete(). */
int field_page; /* Page of field buffer page being filled by */
/* easycap_complete(). */
int field_read; /* Field buffer to be read by field2frame(). */
/* Bumped only by easycap_complete(). */
int frame_fill; /* Frame buffer being filled by field2frame(). */
/* Bumped only by easycap_dqbuf() when */
/* field2frame() has created a complete frame. */
int frame_read; /* Frame buffer offered to user by DQBUF. */
/* Set only by easycap_dqbuf() to trail frame_fill.*/
int frame_lock; /* Flag set to 1 by DQBUF and cleared by QBUF */
/*---------------------------------------------------------------------------*/
/*
* IMAGE PROPERTIES
*/
/*---------------------------------------------------------------------------*/
u32 pixelformat;
int width;
int height;
int bytesperpixel;
bool byteswaporder;
bool decimatepixel;
bool offerfields;
int frame_buffer_used;
int frame_buffer_many;
int videofieldamount;
int brightness;
int contrast;
int saturation;
int hue;
int allocation_video_urb;
int allocation_video_page;
int allocation_video_struct;
int registered_video;
/*---------------------------------------------------------------------------*/
/*
* ALSA
*/
/*---------------------------------------------------------------------------*/
struct snd_pcm_hardware alsa_hardware;
struct snd_card *psnd_card;
struct snd_pcm *psnd_pcm;
struct snd_pcm_substream *psubstream;
int dma_fill;
int dma_next;
int dma_read;
/*---------------------------------------------------------------------------*/
/*
* SOUND PROPERTIES
*/
/*---------------------------------------------------------------------------*/
int audio_interface;
int audio_altsetting_on;
int audio_altsetting_off;
int audio_endpointnumber;
int audio_isoc_maxframesize;
int audio_isoc_buffer_size;
int audio_isoc_framesperdesc;
int audio_isoc_streaming;
int audio_idle;
int audio_eof;
int volume;
int mute;
s8 gain;
struct data_buffer audio_isoc_buffer[AUDIO_ISOC_BUFFER_MANY];
struct list_head urb_audio_head;
struct list_head *purb_audio_head;
/*---------------------------------------------------------------------------*/
/*
* BUFFER INDICATORS
*/
/*---------------------------------------------------------------------------*/
int audio_fill; /* Audio buffer being filled by easycap_complete(). */
/* Bumped only by easycap_complete(). */
int audio_read; /* Audio buffer page being read by easycap_read(). */
/* Set by easycap_read() to trail audio_fill by */
/* one fragment. */
/*---------------------------------------------------------------------------*/
/*
* SOUND PROPERTIES
*/
/*---------------------------------------------------------------------------*/
int allocation_audio_urb;
int allocation_audio_page;
int allocation_audio_struct;
int registered_audio;
long long int audio_sample;
long long int audio_niveau;
long long int audio_square;
struct data_buffer audio_buffer[];
};
/*---------------------------------------------------------------------------*/
/*
* VIDEO FUNCTION PROTOTYPES
*/
/*^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^*/
int easycap_newinput(struct easycap *, int);
void easycap_testcard(struct easycap *, int);
int easycap_isdongle(struct easycap *);
long easycap_unlocked_ioctl(struct file *, unsigned int, unsigned long);
int easycap_video_dqbuf(struct easycap *, int);
int easycap_video_submit_urbs(struct easycap *);
int easycap_video_kill_urbs(struct easycap *);
int easycap_video_fillin_formats(void);
int adjust_standard(struct easycap *, v4l2_std_id);
int adjust_format(struct easycap *, u32, u32, u32, int, bool);
int adjust_brightness(struct easycap *, int);
int adjust_contrast(struct easycap *, int);
int adjust_saturation(struct easycap *, int);
int adjust_hue(struct easycap *, int);
/*---------------------------------------------------------------------------*/
/*
* AUDIO FUNCTION PROTOTYPES
*/
/*---------------------------------------------------------------------------*/
int easycap_alsa_probe(struct easycap *);
int easycap_audio_kill_urbs(struct easycap *);
void easycap_alsa_complete(struct urb *);
/*---------------------------------------------------------------------------*/
/*
* LOW-LEVEL FUNCTION PROTOTYPES
*/
/*---------------------------------------------------------------------------*/
int easycap_audio_gainset(struct usb_device *, s8);
int easycap_audio_setup(struct easycap *);
int easycap_wakeup_device(struct usb_device *);
int setup_stk(struct usb_device *, bool);
int setup_saa(struct usb_device *, bool);
int ready_saa(struct usb_device *);
int merit_saa(struct usb_device *);
int check_vt(struct usb_device *);
int select_input(struct usb_device *, int, int);
int set_resolution(struct usb_device *, u16, u16, u16, u16);
int read_saa(struct usb_device *, u16);
int write_saa(struct usb_device *, u16, u16);
int start_100(struct usb_device *);
int stop_100(struct usb_device *);
/*---------------------------------------------------------------------------*/
/*---------------------------------------------------------------------------*/
/*
* MACROS SAM(...) AND JOM(...) ALLOW DIAGNOSTIC OUTPUT TO BE TAGGED WITH
* THE IDENTITY OF THE DONGLE TO WHICH IT APPLIES, BUT IF INVOKED WHEN THE
* POINTER peasycap IS INVALID AN Oops IS LIKELY, AND ITS CAUSE MAY NOT BE
* IMMEDIATELY OBVIOUS FROM A CASUAL READING OF THE SOURCE CODE. BEWARE.
*/
/*---------------------------------------------------------------------------*/
const char *strerror(int err);
#define SAY(format, args...) do { \
printk(KERN_DEBUG "easycap:: %s: " \
format, __func__, ##args); \
} while (0)
#define SAM(format, args...) do { \
printk(KERN_DEBUG "easycap::%i%s: " \
format, peasycap->isdongle, __func__, ##args);\
} while (0)
#ifdef CONFIG_EASYCAP_DEBUG
extern int easycap_debug;
#define JOT(n, format, args...) do { \
if (n <= easycap_debug) { \
printk(KERN_DEBUG "easycap:: %s: " \
format, __func__, ##args);\
} \
} while (0)
#define JOM(n, format, args...) do { \
if (n <= easycap_debug) { \
printk(KERN_DEBUG "easycap::%i%s: " \
format, peasycap->isdongle, __func__, ##args);\
} \
} while (0)
#else
#define JOT(n, format, args...) do {} while (0)
#define JOM(n, format, args...) do {} while (0)
#endif /* CONFIG_EASYCAP_DEBUG */
/*---------------------------------------------------------------------------*/
/*---------------------------------------------------------------------------*/
/* globals
*/
/*---------------------------------------------------------------------------*/
extern bool easycap_readback;
extern const struct easycap_standard easycap_standard[];
extern struct easycap_format easycap_format[];
extern struct v4l2_queryctrl easycap_control[];
extern struct easycap_dongle easycapdc60_dongle[];
#endif /* !__EASYCAP_H__ */
此差异已折叠。
此差异已折叠。
此差异已折叠。
/******************************************************************************
* *
* easycap_settings.c *
* *
******************************************************************************/
/*
*
* Copyright (C) 2010 R.M. Thomas <rmthomas@sciolus.org>
*
*
* This 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.
*
* The software 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 software; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
*/
/*****************************************************************************/
#include "easycap.h"
/*---------------------------------------------------------------------------*/
/*
* THE LEAST SIGNIFICANT BIT OF easycap_standard.mask HAS MEANING:
* 0 => 25 fps
* 1 => 30 fps
*
* THE MOST SIGNIFICANT BIT OF easycap_standard.mask HAS MEANING:
* 0 => full framerate
* 1 => 20% framerate
*/
/*---------------------------------------------------------------------------*/
const struct easycap_standard easycap_standard[] = {
{
.mask = 0x00FF & PAL_BGHIN ,
.v4l2_standard = {
.index = PAL_BGHIN,
.id = (V4L2_STD_PAL_B |
V4L2_STD_PAL_G | V4L2_STD_PAL_H |
V4L2_STD_PAL_I | V4L2_STD_PAL_N),
.name = "PAL_BGHIN",
.frameperiod = {1, 25},
.framelines = 625,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x00FF & NTSC_N_443 ,
.v4l2_standard = {
.index = NTSC_N_443,
.id = V4L2_STD_UNKNOWN,
.name = "NTSC_N_443",
.frameperiod = {1, 25},
.framelines = 480,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x00FF & PAL_Nc ,
.v4l2_standard = {
.index = PAL_Nc,
.id = V4L2_STD_PAL_Nc,
.name = "PAL_Nc",
.frameperiod = {1, 25},
.framelines = 625,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x00FF & NTSC_N ,
.v4l2_standard = {
.index = NTSC_N,
.id = V4L2_STD_UNKNOWN,
.name = "NTSC_N",
.frameperiod = {1, 25},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x00FF & SECAM ,
.v4l2_standard = {
.index = SECAM,
.id = V4L2_STD_SECAM,
.name = "SECAM",
.frameperiod = {1, 25},
.framelines = 625,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x00FF & NTSC_M ,
.v4l2_standard = {
.index = NTSC_M,
.id = V4L2_STD_NTSC_M,
.name = "NTSC_M",
.frameperiod = {1, 30},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x00FF & NTSC_M_JP ,
.v4l2_standard = {
.index = NTSC_M_JP,
.id = V4L2_STD_NTSC_M_JP,
.name = "NTSC_M_JP",
.frameperiod = {1, 30},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x00FF & PAL_60 ,
.v4l2_standard = {
.index = PAL_60,
.id = V4L2_STD_PAL_60,
.name = "PAL_60",
.frameperiod = {1, 30},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x00FF & NTSC_443 ,
.v4l2_standard = {
.index = NTSC_443,
.id = V4L2_STD_NTSC_443,
.name = "NTSC_443",
.frameperiod = {1, 30},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x00FF & PAL_M ,
.v4l2_standard = {
.index = PAL_M,
.id = V4L2_STD_PAL_M,
.name = "PAL_M",
.frameperiod = {1, 30},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x8000 | (0x00FF & PAL_BGHIN_SLOW),
.v4l2_standard = {
.index = PAL_BGHIN_SLOW,
.id = (V4L2_STD_PAL_B | V4L2_STD_PAL_G |
V4L2_STD_PAL_H |
V4L2_STD_PAL_I | V4L2_STD_PAL_N |
(((v4l2_std_id)0x01) << 32)),
.name = "PAL_BGHIN_SLOW",
.frameperiod = {1, 5},
.framelines = 625,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x8000 | (0x00FF & NTSC_N_443_SLOW),
.v4l2_standard = {
.index = NTSC_N_443_SLOW,
.id = (V4L2_STD_UNKNOWN | (((v4l2_std_id)0x11) << 32)),
.name = "NTSC_N_443_SLOW",
.frameperiod = {1, 5},
.framelines = 480,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x8000 | (0x00FF & PAL_Nc_SLOW),
.v4l2_standard = {
.index = PAL_Nc_SLOW,
.id = (V4L2_STD_PAL_Nc | (((v4l2_std_id)0x01) << 32)),
.name = "PAL_Nc_SLOW",
.frameperiod = {1, 5},
.framelines = 625,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x8000 | (0x00FF & NTSC_N_SLOW),
.v4l2_standard = {
.index = NTSC_N_SLOW,
.id = (V4L2_STD_UNKNOWN | (((v4l2_std_id)0x21) << 32)),
.name = "NTSC_N_SLOW",
.frameperiod = {1, 5},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x8000 | (0x00FF & SECAM_SLOW),
.v4l2_standard = {
.index = SECAM_SLOW,
.id = (V4L2_STD_SECAM | (((v4l2_std_id)0x01) << 32)),
.name = "SECAM_SLOW",
.frameperiod = {1, 5},
.framelines = 625,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x8000 | (0x00FF & NTSC_M_SLOW),
.v4l2_standard = {
.index = NTSC_M_SLOW,
.id = (V4L2_STD_NTSC_M | (((v4l2_std_id)0x01) << 32)),
.name = "NTSC_M_SLOW",
.frameperiod = {1, 6},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x8000 | (0x00FF & NTSC_M_JP_SLOW),
.v4l2_standard = {
.index = NTSC_M_JP_SLOW,
.id = (V4L2_STD_NTSC_M_JP |
(((v4l2_std_id)0x01) << 32)),
.name = "NTSC_M_JP_SLOW",
.frameperiod = {1, 6},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x8000 | (0x00FF & PAL_60_SLOW),
.v4l2_standard = {
.index = PAL_60_SLOW,
.id = (V4L2_STD_PAL_60 | (((v4l2_std_id)0x01) << 32)),
.name = "PAL_60_SLOW",
.frameperiod = {1, 6},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x8000 | (0x00FF & NTSC_443_SLOW),
.v4l2_standard = {
.index = NTSC_443_SLOW,
.id = (V4L2_STD_NTSC_443 | (((v4l2_std_id)0x01) << 32)),
.name = "NTSC_443_SLOW",
.frameperiod = {1, 6},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0x8000 | (0x00FF & PAL_M_SLOW),
.v4l2_standard = {
.index = PAL_M_SLOW,
.id = (V4L2_STD_PAL_M | (((v4l2_std_id)0x01) << 32)),
.name = "PAL_M_SLOW",
.frameperiod = {1, 6},
.framelines = 525,
.reserved = {0, 0, 0, 0}
}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.mask = 0xFFFF
}
};
/*---------------------------------------------------------------------------*/
/*
* THE 16-BIT easycap_format.mask HAS MEANING:
* (least significant) BIT 0: 0 => PAL, 25 FPS; 1 => NTSC, 30 FPS
* BITS 2-4: RESERVED FOR DIFFERENTIATING STANDARDS
* BITS 5-7: NUMBER OF BYTES PER PIXEL
* BIT 8: 0 => NATIVE BYTE ORDER; 1 => SWAPPED
* BITS 9-10: RESERVED FOR OTHER BYTE PERMUTATIONS
* BIT 11: 0 => UNDECIMATED; 1 => DECIMATED
* BIT 12: 0 => OFFER FRAMES; 1 => OFFER FIELDS
* BIT 13: 0 => FULL FRAMERATE; 1 => REDUCED
* (most significant) BITS 14-15: RESERVED FOR OTHER FIELD/FRAME OPTIONS
* IT FOLLOWS THAT:
* bytesperpixel IS ((0x00E0 & easycap_format.mask) >> 5)
* byteswaporder IS true IF (0 != (0x0100 & easycap_format.mask))
*
* decimatepixel IS true IF (0 != (0x0800 & easycap_format.mask))
*
* offerfields IS true IF (0 != (0x1000 & easycap_format.mask))
*/
/*---------------------------------------------------------------------------*/
struct easycap_format easycap_format[1 + SETTINGS_MANY];
int easycap_video_fillin_formats(void)
{
const char *name1, *name2, *name3, *name4;
struct v4l2_format *fmt;
int i, j, k, m, n;
u32 width, height, pixelformat, bytesperline, sizeimage;
u16 mask1, mask2, mask3, mask4;
enum v4l2_field field;
enum v4l2_colorspace colorspace;
for (i = 0, n = 0; i < STANDARD_MANY; i++) {
mask1 = 0x0000;
switch (i) {
case PAL_BGHIN: {
mask1 = 0x1F & PAL_BGHIN;
name1 = "PAL_BGHIN";
colorspace = V4L2_COLORSPACE_470_SYSTEM_BG;
break;
}
case SECAM: {
mask1 = 0x1F & SECAM;
name1 = "SECAM";
colorspace = V4L2_COLORSPACE_470_SYSTEM_BG;
break;
}
case PAL_Nc: {
mask1 = 0x1F & PAL_Nc;
name1 = "PAL_Nc";
colorspace = V4L2_COLORSPACE_470_SYSTEM_BG;
break;
}
case PAL_60: {
mask1 = 0x1F & PAL_60;
name1 = "PAL_60";
colorspace = V4L2_COLORSPACE_470_SYSTEM_BG;
break;
}
case PAL_M: {
mask1 = 0x1F & PAL_M;
name1 = "PAL_M";
colorspace = V4L2_COLORSPACE_470_SYSTEM_BG;
break;
}
case NTSC_M: {
mask1 = 0x1F & NTSC_M;
name1 = "NTSC_M";
colorspace = V4L2_COLORSPACE_470_SYSTEM_M;
break;
}
case NTSC_443: {
mask1 = 0x1F & NTSC_443;
name1 = "NTSC_443";
colorspace = V4L2_COLORSPACE_470_SYSTEM_M;
break;
}
case NTSC_M_JP: {
mask1 = 0x1F & NTSC_M_JP;
name1 = "NTSC_M_JP";
colorspace = V4L2_COLORSPACE_470_SYSTEM_M;
break;
}
case NTSC_N: {
mask1 = 0x1F & NTSC_M;
name1 = "NTSC_N";
colorspace = V4L2_COLORSPACE_470_SYSTEM_M;
break;
}
case NTSC_N_443: {
mask1 = 0x1F & NTSC_N_443;
name1 = "NTSC_N_443";
colorspace = V4L2_COLORSPACE_470_SYSTEM_M;
break;
}
case PAL_BGHIN_SLOW: {
mask1 = 0x001F & PAL_BGHIN_SLOW;
mask1 |= 0x0200;
name1 = "PAL_BGHIN_SLOW";
colorspace = V4L2_COLORSPACE_470_SYSTEM_BG;
break;
}
case SECAM_SLOW: {
mask1 = 0x001F & SECAM_SLOW;
mask1 |= 0x0200;
name1 = "SECAM_SLOW";
colorspace = V4L2_COLORSPACE_470_SYSTEM_BG;
break;
}
case PAL_Nc_SLOW: {
mask1 = 0x001F & PAL_Nc_SLOW;
mask1 |= 0x0200;
name1 = "PAL_Nc_SLOW";
colorspace = V4L2_COLORSPACE_470_SYSTEM_BG;
break;
}
case PAL_60_SLOW: {
mask1 = 0x001F & PAL_60_SLOW;
mask1 |= 0x0200;
name1 = "PAL_60_SLOW";
colorspace = V4L2_COLORSPACE_470_SYSTEM_BG;
break;
}
case PAL_M_SLOW: {
mask1 = 0x001F & PAL_M_SLOW;
mask1 |= 0x0200;
name1 = "PAL_M_SLOW";
colorspace = V4L2_COLORSPACE_470_SYSTEM_BG;
break;
}
case NTSC_M_SLOW: {
mask1 = 0x001F & NTSC_M_SLOW;
mask1 |= 0x0200;
name1 = "NTSC_M_SLOW";
colorspace = V4L2_COLORSPACE_470_SYSTEM_M;
break;
}
case NTSC_443_SLOW: {
mask1 = 0x001F & NTSC_443_SLOW;
mask1 |= 0x0200;
name1 = "NTSC_443_SLOW";
colorspace = V4L2_COLORSPACE_470_SYSTEM_M;
break;
}
case NTSC_M_JP_SLOW: {
mask1 = 0x001F & NTSC_M_JP_SLOW;
mask1 |= 0x0200;
name1 = "NTSC_M_JP_SLOW";
colorspace = V4L2_COLORSPACE_470_SYSTEM_M;
break;
}
case NTSC_N_SLOW: {
mask1 = 0x001F & NTSC_N_SLOW;
mask1 |= 0x0200;
name1 = "NTSC_N_SLOW";
colorspace = V4L2_COLORSPACE_470_SYSTEM_M;
break;
}
case NTSC_N_443_SLOW: {
mask1 = 0x001F & NTSC_N_443_SLOW;
mask1 |= 0x0200;
name1 = "NTSC_N_443_SLOW";
colorspace = V4L2_COLORSPACE_470_SYSTEM_M;
break;
}
default:
return -1;
}
for (j = 0; j < RESOLUTION_MANY; j++) {
mask2 = 0x0000;
switch (j) {
case AT_720x576: {
if (0x1 & mask1)
continue;
name2 = "_AT_720x576";
width = 720;
height = 576;
break;
}
case AT_704x576: {
if (0x1 & mask1)
continue;
name2 = "_AT_704x576";
width = 704;
height = 576;
break;
}
case AT_640x480: {
name2 = "_AT_640x480";
width = 640;
height = 480;
break;
}
case AT_720x480: {
if (!(0x1 & mask1))
continue;
name2 = "_AT_720x480";
width = 720;
height = 480;
break;
}
case AT_360x288: {
if (0x1 & mask1)
continue;
name2 = "_AT_360x288";
width = 360;
height = 288;
mask2 = 0x0800;
break;
}
case AT_320x240: {
name2 = "_AT_320x240";
width = 320;
height = 240;
mask2 = 0x0800;
break;
}
case AT_360x240: {
if (!(0x1 & mask1))
continue;
name2 = "_AT_360x240";
width = 360;
height = 240;
mask2 = 0x0800;
break;
}
default:
return -2;
}
for (k = 0; k < PIXELFORMAT_MANY; k++) {
mask3 = 0x0000;
switch (k) {
case FMT_UYVY: {
name3 = __stringify(FMT_UYVY);
pixelformat = V4L2_PIX_FMT_UYVY;
mask3 |= (0x02 << 5);
break;
}
case FMT_YUY2: {
name3 = __stringify(FMT_YUY2);
pixelformat = V4L2_PIX_FMT_YUYV;
mask3 |= (0x02 << 5);
mask3 |= 0x0100;
break;
}
case FMT_RGB24: {
name3 = __stringify(FMT_RGB24);
pixelformat = V4L2_PIX_FMT_RGB24;
mask3 |= (0x03 << 5);
break;
}
case FMT_RGB32: {
name3 = __stringify(FMT_RGB32);
pixelformat = V4L2_PIX_FMT_RGB32;
mask3 |= (0x04 << 5);
break;
}
case FMT_BGR24: {
name3 = __stringify(FMT_BGR24);
pixelformat = V4L2_PIX_FMT_BGR24;
mask3 |= (0x03 << 5);
mask3 |= 0x0100;
break;
}
case FMT_BGR32: {
name3 = __stringify(FMT_BGR32);
pixelformat = V4L2_PIX_FMT_BGR32;
mask3 |= (0x04 << 5);
mask3 |= 0x0100;
break;
}
default:
return -3;
}
bytesperline = width * ((mask3 & 0x00E0) >> 5);
sizeimage = bytesperline * height;
for (m = 0; m < INTERLACE_MANY; m++) {
mask4 = 0x0000;
switch (m) {
case FIELD_NONE: {
name4 = "-n";
field = V4L2_FIELD_NONE;
break;
}
case FIELD_INTERLACED: {
name4 = "-i";
mask4 |= 0x1000;
field = V4L2_FIELD_INTERLACED;
break;
}
default:
return -4;
}
if (SETTINGS_MANY <= n)
return -5;
strcpy(easycap_format[n].name, name1);
strcat(easycap_format[n].name, name2);
strcat(easycap_format[n].name, "_");
strcat(easycap_format[n].name, name3);
strcat(easycap_format[n].name, name4);
easycap_format[n].mask =
mask1 | mask2 | mask3 | mask4;
fmt = &easycap_format[n].v4l2_format;
fmt->type = V4L2_BUF_TYPE_VIDEO_CAPTURE;
fmt->fmt.pix.width = width;
fmt->fmt.pix.height = height;
fmt->fmt.pix.pixelformat = pixelformat;
fmt->fmt.pix.field = field;
fmt->fmt.pix.bytesperline = bytesperline;
fmt->fmt.pix.sizeimage = sizeimage;
fmt->fmt.pix.colorspace = colorspace;
fmt->fmt.pix.priv = 0;
n++;
}
}
}
}
if ((1 + SETTINGS_MANY) <= n)
return -6;
easycap_format[n].mask = 0xFFFF;
return n;
}
/*---------------------------------------------------------------------------*/
struct v4l2_queryctrl easycap_control[] = {
{
.id = V4L2_CID_BRIGHTNESS,
.type = V4L2_CTRL_TYPE_INTEGER,
.name = "Brightness",
.minimum = 0,
.maximum = 255,
.step = 1,
.default_value = SAA_0A_DEFAULT,
.flags = 0,
.reserved = {0, 0}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.id = V4L2_CID_CONTRAST,
.type = V4L2_CTRL_TYPE_INTEGER,
.name = "Contrast",
.minimum = 0,
.maximum = 255,
.step = 1,
.default_value = SAA_0B_DEFAULT + 128,
.flags = 0,
.reserved = {0, 0}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.id = V4L2_CID_SATURATION,
.type = V4L2_CTRL_TYPE_INTEGER,
.name = "Saturation",
.minimum = 0,
.maximum = 255,
.step = 1,
.default_value = SAA_0C_DEFAULT + 128,
.flags = 0,
.reserved = {0, 0}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.id = V4L2_CID_HUE,
.type = V4L2_CTRL_TYPE_INTEGER,
.name = "Hue",
.minimum = 0,
.maximum = 255,
.step = 1,
.default_value = SAA_0D_DEFAULT + 128,
.flags = 0,
.reserved = {0, 0}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.id = V4L2_CID_AUDIO_VOLUME,
.type = V4L2_CTRL_TYPE_INTEGER,
.name = "Volume",
.minimum = 0,
.maximum = 31,
.step = 1,
.default_value = 16,
.flags = 0,
.reserved = {0, 0}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.id = V4L2_CID_AUDIO_MUTE,
.type = V4L2_CTRL_TYPE_BOOLEAN,
.name = "Mute",
.default_value = true,
.flags = 0,
.reserved = {0, 0}
},
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
{
.id = 0xFFFFFFFF
}
};
/*****************************************************************************/
此差异已折叠。
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册