V4L/DVB (9648): em28xx: get audio config from em28xx register
[safe/jmp/linux-2.6] / drivers / media / video / em28xx / em28xx.h
index 10f6465..f47c8d3 100644 (file)
@@ -35,6 +35,7 @@
 #include <media/videobuf-dvb.h>
 #endif
 #include "tuner-xc2028.h"
+#include "em28xx-reg.h"
 
 /* Boards supported by driver */
 #define EM2800_BOARD_UNKNOWN                   0
 #define EM2880_BOARD_TERRATEC_PRODIGY_XS       13
 #define EM2820_BOARD_PROLINK_PLAYTV_USB2       14
 #define EM2800_BOARD_VGEAR_POCKETTV             15
-#define EM2880_BOARD_HAUPPAUGE_WINTV_HVR_950   16
+#define EM2883_BOARD_HAUPPAUGE_WINTV_HVR_950   16
+#define EM2880_BOARD_PINNACLE_PCTV_HD_PRO      17
+#define EM2880_BOARD_HAUPPAUGE_WINTV_HVR_900_R2        18
+#define EM2860_BOARD_POINTNIX_INTRAORAL_CAMERA  19
+#define EM2880_BOARD_AMD_ATI_TV_WONDER_HD_600   20
+#define EM2800_BOARD_GRABBEEX_USB2800           21
+#define EM2750_BOARD_UNKNOWN                     22
+#define EM2750_BOARD_DLCW_130                    23
+#define EM2820_BOARD_DLINK_USB_TV                24
+#define EM2820_BOARD_GADMEI_UTV310               25
+#define EM2820_BOARD_HERCULES_SMART_TV_USB2      26
+#define EM2820_BOARD_PINNACLE_USB_2_FM1216ME     27
+#define EM2820_BOARD_LEADTEK_WINFAST_USBII_DELUXE 28
+#define EM2820_BOARD_PINNACLE_DVC_100            29
+#define EM2820_BOARD_VIDEOLOGY_20K14XUSB         30
+#define EM2821_BOARD_USBGEAR_VD204               31
+#define EM2821_BOARD_SUPERCOMP_USB_2             32
+#define EM2821_BOARD_PROLINK_PLAYTV_USB2         33
+#define EM2860_BOARD_TERRATEC_HYBRID_XS                  34
+#define EM2860_BOARD_TYPHOON_DVD_MAKER           35
+#define EM2860_BOARD_NETGMBH_CAM                 36
+#define EM2860_BOARD_GADMEI_UTV330               37
+#define EM2861_BOARD_YAKUMO_MOVIE_MIXER                  38
+#define EM2861_BOARD_KWORLD_PVRTV_300U           39
+#define EM2861_BOARD_PLEXTOR_PX_TV100U           40
+#define EM2870_BOARD_KWORLD_350U                 41
+#define EM2870_BOARD_KWORLD_355U                 42
+#define EM2870_BOARD_TERRATEC_XS                 43
+#define EM2870_BOARD_TERRATEC_XS_MT2060                  44
+#define EM2870_BOARD_PINNACLE_PCTV_DVB           45
+#define EM2870_BOARD_COMPRO_VIDEOMATE            46
+#define EM2880_BOARD_KWORLD_DVB_305U             47
+#define EM2880_BOARD_KWORLD_DVB_310U             48
+#define EM2880_BOARD_MSI_DIGIVOX_AD              49
+#define EM2880_BOARD_MSI_DIGIVOX_AD_II           50
+#define EM2880_BOARD_TERRATEC_HYBRID_XS_FR       51
+#define EM2881_BOARD_DNT_DA2_HYBRID              52
+#define EM2881_BOARD_PINNACLE_HYBRID_PRO         53
+#define EM2882_BOARD_KWORLD_VS_DVBT              54
+#define EM2882_BOARD_TERRATEC_HYBRID_XS                  55
+#define EM2882_BOARD_PINNACLE_HYBRID_PRO         56
+#define EM2883_BOARD_KWORLD_HYBRID_A316                  57
+#define EM2820_BOARD_COMPRO_VIDEOMATE_FORYOU     58
+#define EM2874_BOARD_PINNACLE_PCTV_80E           59
 
 /* Limits minimum and default number of buffers */
 #define EM28XX_MIN_BUF 4
 #define EM28XX_DEF_BUF 8
 
+/*Limits the max URB message size */
+#define URB_MAX_CTRL_SIZE 80
+
+/* Params for validated field */
+#define EM28XX_BOARD_NOT_VALIDATED 1
+#define EM28XX_BOARD_VALIDATED    0
+
 /* maximum number of em28xx boards */
 #define EM28XX_MAXBOARDS 4 /*FIXME: should be bigger */
 
 #define EM2800_I2C_WRITE_TIMEOUT 20
 
 enum em28xx_mode {
+       EM28XX_MODE_UNDEFINED,
        EM28XX_ANALOG_MODE,
        EM28XX_DIGITAL_MODE,
 };
@@ -119,6 +171,8 @@ enum em28xx_stream_state {
        STREAM_ON,
 };
 
+struct em28xx;
+
 struct em28xx_usb_isoc_ctl {
                /* max packet size of isoc transaction */
        int                             max_pkt_size;
@@ -148,6 +202,10 @@ struct em28xx_usb_isoc_ctl {
 
                /* Stores the number of received fields */
        int                             nfields;
+
+               /* isoc urb callback */
+       int (*isoc_copy) (struct em28xx *dev, struct urb *urb);
+
 };
 
 struct em28xx_fmt {
@@ -198,6 +256,13 @@ enum enum28xx_itype {
        EM28XX_RADIO,
 };
 
+enum em28xx_audio_mode {
+       EM28XX_NO_AUDIO,
+       EM28XX_I2S_3_SAMPLE_RATES,
+       EM28XX_I2S_5_SAMPLE_RATES,
+       EM28XX_AC97,
+};
+
 enum em28xx_amux {
        EM28XX_AMUX_VIDEO,
        EM28XX_AMUX_LINE_IN,
@@ -214,30 +279,23 @@ struct em28xx_input {
 #define INPUT(nr) (&em28xx_boards[dev->model].input[nr])
 
 enum em28xx_decoder {
+       EM28XX_NODECODER,
        EM28XX_TVP5150,
        EM28XX_SAA7113,
        EM28XX_SAA7114
 };
 
-#define MAX_GPIO 2
-struct gpio_ctl {
-               /* Register to be set */
-       unsigned char reg;
-               /* Initial/final value */
-       unsigned char val;
-               /* reset value - if set, it will do:
-                  val1 - val2 - val1
-                */
-       unsigned char rst;
-               /* Sleep times
-                */
-       unsigned int  t1, t2, t3;
+struct em28xx_reg_seq {
+       int reg;
+       unsigned char val, mask;
+       int sleep;
 };
 
 struct em28xx_board {
        char *name;
        int vchannels;
        int tuner_type;
+       int tuner_addr;
 
        /* i2c flags */
        unsigned int tda9887_conf;
@@ -248,14 +306,14 @@ struct em28xx_board {
        unsigned int has_12mhz_i2s:1;
        unsigned int max_range_640_480:1;
        unsigned int has_dvb:1;
-
-       struct gpio_ctl analog_gpio[MAX_GPIO];
-       struct gpio_ctl digital_gpio[MAX_GPIO];
+       unsigned int has_snapshot_button:1;
+       unsigned int valid:1;
 
        enum em28xx_decoder decoder;
 
        struct em28xx_input       input[MAX_EM28XX_INPUT];
        struct em28xx_input       radio;
+       IR_KEYTAB_TYPE            *ir_codes;
 };
 
 struct em28xx_eeprom {
@@ -304,23 +362,47 @@ struct em28xx_audio {
        spinlock_t slock;
 };
 
+struct em28xx;
+
+struct em28xx_fh {
+       struct em28xx *dev;
+       unsigned int  stream_on:1;      /* Locks streams */
+       int           radio;
+
+       struct videobuf_queue        vb_vidq;
+
+       enum v4l2_buf_type           type;
+};
+
 /* main device struct */
 struct em28xx {
        /* generic device properties */
        char name[30];          /* name (including minor) of the device */
        int model;              /* index in the device_data struct */
        int devno;              /* marks the number of this device */
+       enum em28xx_chip_id chip_id;
        unsigned int is_em2800:1;
        unsigned int has_msp34xx:1;
        unsigned int has_tda9887:1;
        unsigned int stream_on:1;       /* Locks streams */
        unsigned int has_audio_class:1;
+       unsigned int has_alsa_audio:1;
        unsigned int has_12mhz_i2s:1;
        unsigned int max_range_640_480:1;
        unsigned int has_dvb:1;
+       unsigned int has_snapshot_button:1;
+       unsigned int valid:1;           /* report for validated boards */
+
+       struct em28xx_IR *ir;
+
+       /* Some older em28xx chips needs a waiting time after writing */
+       unsigned int wait_after_write;
+
+       /* GPIO sequences for analog and digital mode */
+       struct em28xx_reg_seq *analog_gpio, *digital_gpio;
 
-       struct gpio_ctl *analog_gpio;
-       struct gpio_ctl *digital_gpio;
+       /* GPIO sequences for tuner callbacks */
+       struct em28xx_reg_seq *tun_analog_gpio, *tun_digital_gpio;
 
        int video_inputs;       /* number of video inputs */
        struct list_head        devlist;
@@ -328,6 +410,7 @@ struct em28xx {
        u32 i2s_speed;          /* I2S speed for audio digital stream */
 
        enum em28xx_decoder decoder;
+       enum em28xx_audio_mode audio_mode;
 
        int tuner_type;         /* type of the tuner */
        int tuner_addr;         /* tuner address */
@@ -341,19 +424,20 @@ struct em28xx {
        v4l2_std_id norm;       /* selected tv norm */
        int ctl_freq;           /* selected frequency */
        unsigned int ctl_input; /* selected input */
-       unsigned int ctl_ainput;        /* slected audio input */
+       unsigned int ctl_ainput;/* selected audio input */
        int mute;
        int volume;
        /* frame properties */
        int width;              /* current frame width */
        int height;             /* current frame height */
-       int hscale;             /* horizontal scale factor (see datasheet) */
-       int vscale;             /* vertical scale factor (see datasheet) */
+       unsigned hscale;        /* horizontal scale factor (see datasheet) */
+       unsigned vscale;        /* vertical scale factor (see datasheet) */
        int interlaced;         /* 1=interlace fileds, 0=just top fileds */
        unsigned int video_bytesread;   /* Number of bytes read */
 
        unsigned long hash;     /* eeprom hash - for boards with generic ID */
-       unsigned long i2c_hash; /* i2c devicelist hash - for boards with generic ID */
+       unsigned long i2c_hash; /* i2c devicelist hash -
+                                  for boards with generic ID */
 
        struct em28xx_audio *adev;
 
@@ -365,6 +449,7 @@ struct em28xx {
 
        /* locks */
        struct mutex lock;
+       struct mutex ctrl_urb_lock;     /* protects urb_buf */
        /* spinlock_t queue_lock; */
        struct list_head inqueue, outqueue;
        wait_queue_head_t open, wait_frame, wait_stream;
@@ -386,32 +471,35 @@ struct em28xx {
        unsigned int *alt_max_pkt_size; /* array of wMaxPacketSize */
        struct urb *urb[EM28XX_NUM_BUFS];       /* urb for isoc transfers */
        char *transfer_buffer[EM28XX_NUM_BUFS]; /* transfer buffers for isoc transfer */
+       char urb_buf[URB_MAX_CTRL_SIZE];        /* urb control msg buffer */
+
        /* helper funcs that call usb_control_msg */
-       int (*em28xx_write_regs) (struct em28xx * dev, u16 reg, char *buf,
-                                 int len);
-       int (*em28xx_read_reg) (struct em28xx * dev, u16 reg);
-       int (*em28xx_read_reg_req_len) (struct em28xx * dev, u8 req, u16 reg,
+       int (*em28xx_write_regs) (struct em28xx *dev, u16 reg,
+                                       char *buf, int len);
+       int (*em28xx_read_reg) (struct em28xx *dev, u16 reg);
+       int (*em28xx_read_reg_req_len) (struct em28xx *dev, u8 req, u16 reg,
                                        char *buf, int len);
-       int (*em28xx_write_regs_req) (struct em28xx * dev, u8 req, u16 reg,
+       int (*em28xx_write_regs_req) (struct em28xx *dev, u8 req, u16 reg,
                                      char *buf, int len);
-       int (*em28xx_read_reg_req) (struct em28xx * dev, u8 req, u16 reg);
+       int (*em28xx_read_reg_req) (struct em28xx *dev, u8 req, u16 reg);
 
        enum em28xx_mode mode;
 
-#if defined(CONFIG_VIDEO_EM28XX_DVB) || defined(CONFIG_VIDEO_EM28XX_DVB_MODULE)
-       struct videobuf_dvb        dvb;
-       struct videobuf_queue_ops  *qops;
-#endif
-};
+       /* register numbers for GPO/GPIO registers */
+       u16 reg_gpo_num, reg_gpio_num;
 
-struct em28xx_fh {
-       struct em28xx *dev;
-       unsigned int  stream_on:1;      /* Locks streams */
-       int           radio;
+       /* Caches GPO and GPIO registers */
+       unsigned char   reg_gpo, reg_gpio;
 
-       struct videobuf_queue        vb_vidq;
+       /* Infrared remote control support */
+       IR_KEYTAB_TYPE *ir_codes;
 
-       enum v4l2_buf_type           type;
+       /* Snapshot button */
+       char snapshot_button_path[30];  /* path of the input dev */
+       struct input_dev *sbutton_input_dev;
+       struct delayed_work sbutton_query_work;
+
+       struct em28xx_dvb *dvb;
 };
 
 struct em28xx_ops {
@@ -449,93 +537,37 @@ int em28xx_capture_start(struct em28xx *dev, int start);
 int em28xx_outfmt_set_yuv422(struct em28xx *dev);
 int em28xx_resolution_set(struct em28xx *dev);
 int em28xx_set_alternate(struct em28xx *dev);
+int em28xx_init_isoc(struct em28xx *dev, int max_packets,
+                    int num_bufs, int max_pkt_size,
+                    int (*isoc_copy) (struct em28xx *dev, struct urb *urb));
+void em28xx_uninit_isoc(struct em28xx *dev);
+int em28xx_set_mode(struct em28xx *dev, enum em28xx_mode set_mode);
+int em28xx_gpio_set(struct em28xx *dev, struct em28xx_reg_seq *gpio);
 
 /* Provided by em28xx-video.c */
 int em28xx_register_extension(struct em28xx_ops *dev);
 void em28xx_unregister_extension(struct em28xx_ops *dev);
 
 /* Provided by em28xx-cards.c */
-extern int em2800_variant_detect(struct usb_device* udev,int model);
+extern int em2800_variant_detect(struct usb_device *udev, int model);
 extern void em28xx_pre_card_setup(struct em28xx *dev);
 extern void em28xx_card_setup(struct em28xx *dev);
 extern struct em28xx_board em28xx_boards[];
 extern struct usb_device_id em28xx_id_table[];
 extern const unsigned int em28xx_bcount;
 void em28xx_set_ir(struct em28xx *dev, struct IR_i2c *ir);
-int em28xx_tuner_callback(void *ptr, int command, int arg);
-void em28xx_setup_xc3028(struct em28xx *dev, struct xc2028_ctrl *ctl);
+int em28xx_tuner_callback(void *ptr, int component, int command, int arg);
 
 /* Provided by em28xx-input.c */
-/* TODO: Check if the standard get_key handlers on ir-common can be used */
 int em28xx_get_key_terratec(struct IR_i2c *ir, u32 *ir_key, u32 *ir_raw);
 int em28xx_get_key_em_haup(struct IR_i2c *ir, u32 *ir_key, u32 *ir_raw);
 int em28xx_get_key_pinnacle_usb_grey(struct IR_i2c *ir, u32 *ir_key,
                                     u32 *ir_raw);
+void em28xx_register_snapshot_button(struct em28xx *dev);
+void em28xx_deregister_snapshot_button(struct em28xx *dev);
 
-/* em2800 registers */
-#define EM2800_AUDIOSRC_REG 0x08
-
-/* em28xx registers */
-#define I2C_CLK_REG    0x06
-#define CHIPID_REG     0x0a
-#define USBSUSP_REG    0x0c    /* */
-
-#define AUDIOSRC_REG   0x0e
-#define XCLK_REG       0x0f
-
-#define VINMODE_REG    0x10
-#define VINCTRL_REG    0x11
-#define VINENABLE_REG  0x12    /* */
-
-#define GAMMA_REG      0x14
-#define RGAIN_REG      0x15
-#define GGAIN_REG      0x16
-#define BGAIN_REG      0x17
-#define ROFFSET_REG    0x18
-#define GOFFSET_REG    0x19
-#define BOFFSET_REG    0x1a
-
-#define OFLOW_REG      0x1b
-#define HSTART_REG     0x1c
-#define VSTART_REG     0x1d
-#define CWIDTH_REG     0x1e
-#define CHEIGHT_REG    0x1f
-
-#define YGAIN_REG      0x20
-#define YOFFSET_REG    0x21
-#define UVGAIN_REG     0x22
-#define UOFFSET_REG    0x23
-#define VOFFSET_REG    0x24
-#define SHARPNESS_REG  0x25
-
-#define COMPR_REG      0x26
-#define OUTFMT_REG     0x27
-
-#define XMIN_REG       0x28
-#define XMAX_REG       0x29
-#define YMIN_REG       0x2a
-#define YMAX_REG       0x2b
-
-#define HSCALELOW_REG  0x30
-#define HSCALEHIGH_REG 0x31
-#define VSCALELOW_REG  0x32
-#define VSCALEHIGH_REG 0x33
-
-#define AC97LSB_REG    0x40
-#define AC97MSB_REG    0x41
-#define AC97ADDR_REG   0x42
-#define AC97BUSY_REG   0x43
-
-/* em202 registers */
-#define MASTER_AC97    0x02
-#define LINE_IN_AC97    0x10
-#define VIDEO_AC97     0x14
-
-/* register settings */
-#define EM2800_AUDIO_SRC_TUNER  0x0d
-#define EM2800_AUDIO_SRC_LINE   0x0c
-#define EM28XX_AUDIO_SRC_TUNER 0xc0
-#define EM28XX_AUDIO_SRC_LINE  0x80
+int em28xx_ir_init(struct em28xx *dev);
+int em28xx_ir_fini(struct em28xx *dev);
 
 /* printk macros */
 
@@ -553,80 +585,80 @@ int em28xx_get_key_pinnacle_usb_grey(struct IR_i2c *ir, u32 *ir_key,
        printk(KERN_WARNING "%s: "fmt,\
                        dev->name , ##arg); } while (0)
 
-inline static int em28xx_compression_disable(struct em28xx *dev)
+static inline int em28xx_compression_disable(struct em28xx *dev)
 {
        /* side effect of disabling scaler and mixer */
-       return em28xx_write_regs(dev, COMPR_REG, "\x00", 1);
+       return em28xx_write_regs(dev, EM28XX_R26_COMPR, "\x00", 1);
 }
 
-inline static int em28xx_contrast_get(struct em28xx *dev)
+static inline int em28xx_contrast_get(struct em28xx *dev)
 {
-       return em28xx_read_reg(dev, YGAIN_REG) & 0x1f;
+       return em28xx_read_reg(dev, EM28XX_R20_YGAIN) & 0x1f;
 }
 
-inline static int em28xx_brightness_get(struct em28xx *dev)
+static inline int em28xx_brightness_get(struct em28xx *dev)
 {
-       return em28xx_read_reg(dev, YOFFSET_REG);
+       return em28xx_read_reg(dev, EM28XX_R21_YOFFSET);
 }
 
-inline static int em28xx_saturation_get(struct em28xx *dev)
+static inline int em28xx_saturation_get(struct em28xx *dev)
 {
-       return em28xx_read_reg(dev, UVGAIN_REG) & 0x1f;
+       return em28xx_read_reg(dev, EM28XX_R22_UVGAIN) & 0x1f;
 }
 
-inline static int em28xx_u_balance_get(struct em28xx *dev)
+static inline int em28xx_u_balance_get(struct em28xx *dev)
 {
-       return em28xx_read_reg(dev, UOFFSET_REG);
+       return em28xx_read_reg(dev, EM28XX_R23_UOFFSET);
 }
 
-inline static int em28xx_v_balance_get(struct em28xx *dev)
+static inline int em28xx_v_balance_get(struct em28xx *dev)
 {
-       return em28xx_read_reg(dev, VOFFSET_REG);
+       return em28xx_read_reg(dev, EM28XX_R24_VOFFSET);
 }
 
-inline static int em28xx_gamma_get(struct em28xx *dev)
+static inline int em28xx_gamma_get(struct em28xx *dev)
 {
-       return em28xx_read_reg(dev, GAMMA_REG) & 0x3f;
+       return em28xx_read_reg(dev, EM28XX_R14_GAMMA) & 0x3f;
 }
 
-inline static int em28xx_contrast_set(struct em28xx *dev, s32 val)
+static inline int em28xx_contrast_set(struct em28xx *dev, s32 val)
 {
        u8 tmp = (u8) val;
-       return em28xx_write_regs(dev, YGAIN_REG, &tmp, 1);
+       return em28xx_write_regs(dev, EM28XX_R20_YGAIN, &tmp, 1);
 }
 
-inline static int em28xx_brightness_set(struct em28xx *dev, s32 val)
+static inline int em28xx_brightness_set(struct em28xx *dev, s32 val)
 {
        u8 tmp = (u8) val;
-       return em28xx_write_regs(dev, YOFFSET_REG, &tmp, 1);
+       return em28xx_write_regs(dev, EM28XX_R21_YOFFSET, &tmp, 1);
 }
 
-inline static int em28xx_saturation_set(struct em28xx *dev, s32 val)
+static inline int em28xx_saturation_set(struct em28xx *dev, s32 val)
 {
        u8 tmp = (u8) val;
-       return em28xx_write_regs(dev, UVGAIN_REG, &tmp, 1);
+       return em28xx_write_regs(dev, EM28XX_R22_UVGAIN, &tmp, 1);
 }
 
-inline static int em28xx_u_balance_set(struct em28xx *dev, s32 val)
+static inline int em28xx_u_balance_set(struct em28xx *dev, s32 val)
 {
        u8 tmp = (u8) val;
-       return em28xx_write_regs(dev, UOFFSET_REG, &tmp, 1);
+       return em28xx_write_regs(dev, EM28XX_R23_UOFFSET, &tmp, 1);
 }
 
-inline static int em28xx_v_balance_set(struct em28xx *dev, s32 val)
+static inline int em28xx_v_balance_set(struct em28xx *dev, s32 val)
 {
        u8 tmp = (u8) val;
-       return em28xx_write_regs(dev, VOFFSET_REG, &tmp, 1);
+       return em28xx_write_regs(dev, EM28XX_R24_VOFFSET, &tmp, 1);
 }
 
-inline static int em28xx_gamma_set(struct em28xx *dev, s32 val)
+static inline int em28xx_gamma_set(struct em28xx *dev, s32 val)
 {
        u8 tmp = (u8) val;
-       return em28xx_write_regs(dev, GAMMA_REG, &tmp, 1);
+       return em28xx_write_regs(dev, EM28XX_R14_GAMMA, &tmp, 1);
 }
 
 /*FIXME: maxw should be dependent of alt mode */
-inline static unsigned int norm_maxw(struct em28xx *dev)
+static inline unsigned int norm_maxw(struct em28xx *dev)
 {
        if (dev->max_range_640_480)
                return 640;
@@ -634,7 +666,7 @@ inline static unsigned int norm_maxw(struct em28xx *dev)
                return 720;
 }
 
-inline static unsigned int norm_maxh(struct em28xx *dev)
+static inline unsigned int norm_maxh(struct em28xx *dev)
 {
        if (dev->max_range_640_480)
                return 480;