Browse Source

Merge git://git.kernel.org/pub/scm/linux/kernel/git/mchehab/v4l-dvb

* git://git.kernel.org/pub/scm/linux/kernel/git/mchehab/v4l-dvb: (42 commits)
  V4L/DVB (8108): Fix open/close race in saa7134
  V4L/DVB (8100): V4L/vivi: fix possible memory leak in vivi_fillbuff
  V4L/DVB (8097): xc5000: check device hardware state to determine if firmware download is needed
  V4L/DVB (8096): au8522: prevent false-positive lock status
  V4L/DVB (8092): videodev: simplify and fix standard enumeration
  V4L/DVB (8075): stv0299: Uncorrected block count and bit error rate fixed
  V4L/DVB (8074): av7110: OSD transfers should not be interrupted
  V4L/DVB (8073): av7110: Catch another type of ARM crash
  V4L/DVB (8071): tda10023: Fix possible kernel oops during initialisation
  V4L/DVB (8069): cx18: Fix S-Video and Compsite inputs for the Yuan MPC718 and enable card entry
  V4L/DVB (8068): cx18: Add I2C slave reset via GPIO upon initialization
  V4L/DVB (8067): cx18: Fix firmware load for case when digital capture happens first
  V4L/DVB (8066): cx18: Fix audio mux input definitions for HVR-1600 Line In 2 and FM radio
  V4L/DVB (8063): cx18: Fix unintended auto configurations in cx18-av-core
  V4L/DVB (8061): cx18: only select tuner / frontend modules if !DVB_FE_CUSTOMISE
  V4L/DVB (8048): saa7134: Fix entries for Avermedia A16d and Avermedia E506
  V4L/DVB (8044): au8522: tuning optimizations
  V4L/DVB (8043): au0828: add support for additional USB device id's
  V4L/DVB (8042): DVB-USB UMT-010 channel scan oops
  V4L/DVB (8040): soc-camera: remove soc_camera_host_class class
  ...
Linus Torvalds 17 years ago
parent
commit
1702b52092
43 changed files with 608 additions and 446 deletions
  1. 1 1
      Documentation/video4linux/CARDLIST.au0828
  2. 38 0
      drivers/media/common/ir-keymaps.c
  3. 9 1
      drivers/media/common/tuners/tda18271-common.c
  4. 34 19
      drivers/media/common/tuners/tda18271-fe.c
  5. 23 7
      drivers/media/common/tuners/xc5000.c
  6. 0 1
      drivers/media/common/tuners/xc5000_priv.h
  7. 10 17
      drivers/media/dvb/dvb-usb/gl861.c
  8. 1 1
      drivers/media/dvb/dvb-usb/umt-010.c
  9. 23 6
      drivers/media/dvb/frontends/au8522.c
  10. 11 4
      drivers/media/dvb/frontends/stv0299.c
  11. 12 8
      drivers/media/dvb/frontends/tda10023.c
  12. 25 4
      drivers/media/dvb/frontends/tda1004x.c
  13. 1 0
      drivers/media/dvb/ttpci/Kconfig
  14. 2 3
      drivers/media/dvb/ttpci/av7110_hw.c
  15. 18 0
      drivers/media/video/au0828/au0828-cards.c
  16. 2 2
      drivers/media/video/cx18/Kconfig
  17. 64 9
      drivers/media/video/cx18/cx18-av-core.c
  18. 15 1
      drivers/media/video/cx18/cx18-av-core.h
  19. 49 35
      drivers/media/video/cx18/cx18-cards.c
  20. 9 41
      drivers/media/video/cx18/cx18-cards.h
  21. 16 1
      drivers/media/video/cx18/cx18-dvb.c
  22. 25 1
      drivers/media/video/cx18/cx18-gpio.c
  23. 1 0
      drivers/media/video/cx18/cx18-gpio.h
  24. 2 0
      drivers/media/video/cx18/cx18-i2c.c
  25. 1 1
      drivers/media/video/cx25840/cx25840-core.c
  26. 6 0
      drivers/media/video/cx88/cx88-alsa.c
  27. 18 0
      drivers/media/video/em28xx/em28xx-audio.c
  28. 4 0
      drivers/media/video/em28xx/em28xx-cards.c
  29. 10 0
      drivers/media/video/em28xx/em28xx-dvb.c
  30. 1 0
      drivers/media/video/em28xx/em28xx-reg.h
  31. 10 14
      drivers/media/video/em28xx/em28xx-video.c
  32. 2 2
      drivers/media/video/pxa_camera.c
  33. 7 1
      drivers/media/video/saa7134/saa7134-alsa.c
  34. 32 24
      drivers/media/video/saa7134/saa7134-cards.c
  35. 21 22
      drivers/media/video/saa7134/saa7134-dvb.c
  36. 16 21
      drivers/media/video/saa7134/saa7134-empress.c
  37. 9 0
      drivers/media/video/saa7134/saa7134-input.c
  38. 0 16
      drivers/media/video/soc_camera.c
  39. 68 177
      drivers/media/video/videodev.c
  40. 4 3
      drivers/media/video/vivi.c
  41. 5 1
      include/media/cx25840.h
  42. 1 0
      include/media/ir-common.h
  43. 2 2
      include/media/v4l2-dev.h

+ 1 - 1
Documentation/video4linux/CARDLIST.au0828

@@ -1,4 +1,4 @@
   0 -> Unknown board                            (au0828)
-  1 -> Hauppauge HVR950Q                        (au0828)        [2040:7200]
+  1 -> Hauppauge HVR950Q                        (au0828)        [2040:7200,2040:7210,2040:7217,2040:721b,2040:721f,2040:7280,0fd9:0008]
   2 -> Hauppauge HVR850                         (au0828)        [2040:7240]
   3 -> DViCO FusionHDTV USB                     (au0828)        [0fe9:d620]

+ 38 - 0
drivers/media/common/ir-keymaps.c

@@ -2201,3 +2201,41 @@ IR_KEYTAB_TYPE ir_codes_powercolor_real_angel[IR_KEYTAB_SIZE] = {
 	[0x25] = KEY_POWER,		/* power */
 };
 EXPORT_SYMBOL_GPL(ir_codes_powercolor_real_angel);
+
+IR_KEYTAB_TYPE ir_codes_avermedia_a16d[IR_KEYTAB_SIZE] = {
+	[0x20] = KEY_LIST,
+	[0x00] = KEY_POWER,
+	[0x28] = KEY_1,
+	[0x18] = KEY_2,
+	[0x38] = KEY_3,
+	[0x24] = KEY_4,
+	[0x14] = KEY_5,
+	[0x34] = KEY_6,
+	[0x2c] = KEY_7,
+	[0x1c] = KEY_8,
+	[0x3c] = KEY_9,
+	[0x12] = KEY_SUBTITLE,
+	[0x22] = KEY_0,
+	[0x32] = KEY_REWIND,
+	[0x3a] = KEY_SHUFFLE,
+	[0x02] = KEY_PRINT,
+	[0x11] = KEY_CHANNELDOWN,
+	[0x31] = KEY_CHANNELUP,
+	[0x0c] = KEY_ZOOM,
+	[0x1e] = KEY_VOLUMEDOWN,
+	[0x3e] = KEY_VOLUMEUP,
+	[0x0a] = KEY_MUTE,
+	[0x04] = KEY_AUDIO,
+	[0x26] = KEY_RECORD,
+	[0x06] = KEY_PLAY,
+	[0x36] = KEY_STOP,
+	[0x16] = KEY_PAUSE,
+	[0x2e] = KEY_REWIND,
+	[0x0e] = KEY_FASTFORWARD,
+	[0x30] = KEY_TEXT,
+	[0x21] = KEY_GREEN,
+	[0x01] = KEY_BLUE,
+	[0x08] = KEY_EPG,
+	[0x2a] = KEY_MENU,
+};
+EXPORT_SYMBOL_GPL(ir_codes_avermedia_a16d);

+ 9 - 1
drivers/media/common/tuners/tda18271-common.c

@@ -649,9 +649,17 @@ int tda18271_calc_rf_cal(struct dvb_frontend *fe, u32 *freq)
 	u8 val;
 
 	int ret = tda18271_lookup_map(fe, RF_CAL, freq, &val);
+	/* The TDA18271HD/C1 rf_cal map lookup is expected to go out of range
+	 * for frequencies above 61.1 MHz.  In these cases, the internal RF
+	 * tracking filters calibration mechanism is used.
+	 *
+	 * There is no need to warn the user about this.
+	 */
+	if (ret < 0)
+		goto fail;
 
 	regs[R_EB14] = val;
-
+fail:
 	return ret;
 }
 

+ 34 - 19
drivers/media/common/tuners/tda18271-fe.c

@@ -45,6 +45,21 @@ static inline int charge_pump_source(struct dvb_frontend *fe, int force)
 					   TDA18271_MAIN_PLL, force);
 }
 
+static inline void tda18271_set_if_notch(struct dvb_frontend *fe)
+{
+	struct tda18271_priv *priv = fe->tuner_priv;
+	unsigned char *regs = priv->tda18271_regs;
+
+	switch (priv->mode) {
+	case TDA18271_ANALOG:
+		regs[R_MPD]  &= ~0x80; /* IF notch = 0 */
+		break;
+	case TDA18271_DIGITAL:
+		regs[R_MPD]  |= 0x80; /* IF notch = 1 */
+		break;
+	}
+}
+
 static int tda18271_channel_configuration(struct dvb_frontend *fe,
 					  struct tda18271_std_map_item *map,
 					  u32 freq, u32 bw)
@@ -60,25 +75,18 @@ static int tda18271_channel_configuration(struct dvb_frontend *fe,
 	regs[R_EP3]  &= ~0x1f; /* clear std bits */
 	regs[R_EP3]  |= (map->agc_mode << 3) | map->std;
 
-	/* set rfagc to high speed mode */
-	regs[R_EP3] &= ~0x04;
+	if (priv->id == TDA18271HDC2) {
+		/* set rfagc to high speed mode */
+		regs[R_EP3] &= ~0x04;
+	}
 
 	/* set cal mode to normal */
 	regs[R_EP4]  &= ~0x03;
 
-	/* update IF output level & IF notch frequency */
+	/* update IF output level */
 	regs[R_EP4]  &= ~0x1c; /* clear if level bits */
 	regs[R_EP4]  |= (map->if_lvl << 2);
 
-	switch (priv->mode) {
-	case TDA18271_ANALOG:
-		regs[R_MPD]  &= ~0x80; /* IF notch = 0 */
-		break;
-	case TDA18271_DIGITAL:
-		regs[R_MPD]  |= 0x80; /* IF notch = 1 */
-		break;
-	}
-
 	/* update FM_RFn */
 	regs[R_EP4]  &= ~0x80;
 	regs[R_EP4]  |= map->fm_rfn << 7;
@@ -95,6 +103,9 @@ static int tda18271_channel_configuration(struct dvb_frontend *fe,
 	/* disable Power Level Indicator */
 	regs[R_EP1]  |= 0x40;
 
+	/* make sure thermometer is off */
+	regs[R_TM]   &= ~0x10;
+
 	/* frequency dependent parameters */
 
 	tda18271_calc_ir_measure(fe, &freq);
@@ -135,6 +146,7 @@ static int tda18271_channel_configuration(struct dvb_frontend *fe,
 	switch (priv->role) {
 	case TDA18271_MASTER:
 		tda18271_calc_main_pll(fe, N);
+		tda18271_set_if_notch(fe);
 		tda18271_write_regs(fe, R_MPD, 4);
 		break;
 	case TDA18271_SLAVE:
@@ -142,6 +154,7 @@ static int tda18271_channel_configuration(struct dvb_frontend *fe,
 		tda18271_write_regs(fe, R_CPD, 4);
 
 		regs[R_MPD] = regs[R_CPD] & 0x7f;
+		tda18271_set_if_notch(fe);
 		tda18271_write_regs(fe, R_MPD, 1);
 		break;
 	}
@@ -160,12 +173,14 @@ static int tda18271_channel_configuration(struct dvb_frontend *fe,
 
 	msleep(20);
 
-	/* set rfagc to normal speed mode */
-	if (map->fm_rfn)
-		regs[R_EP3] &= ~0x04;
-	else
-		regs[R_EP3] |= 0x04;
-	ret = tda18271_write_regs(fe, R_EP3, 1);
+	if (priv->id == TDA18271HDC2) {
+		/* set rfagc to normal speed mode */
+		if (map->fm_rfn)
+			regs[R_EP3] &= ~0x04;
+		else
+			regs[R_EP3] |= 0x04;
+		ret = tda18271_write_regs(fe, R_EP3, 1);
+	}
 fail:
 	return ret;
 }
@@ -507,7 +522,7 @@ static int tda18271_powerscan_init(struct dvb_frontend *fe)
 	/* set cal mode to normal */
 	regs[R_EP4]  &= ~0x03;
 
-	/* update IF output level & IF notch frequency */
+	/* update IF output level */
 	regs[R_EP4]  &= ~0x1c; /* clear if level bits */
 
 	ret = tda18271_write_regs(fe, R_EP3, 2);

+ 23 - 7
drivers/media/common/tuners/xc5000.c

@@ -177,6 +177,7 @@ static XC_TV_STANDARD XC5000_Standard[MAX_TV_STANDARD] = {
 	{"FM Radio-INPUT1",   0x0208, 0x9002}
 };
 
+static int  xc5000_is_firmware_loaded(struct dvb_frontend *fe);
 static int  xc5000_writeregs(struct xc5000_priv *priv, u8 *buf, u8 len);
 static int  xc5000_readregs(struct xc5000_priv *priv, u8 *buf, u8 len);
 static void xc5000_TunerReset(struct dvb_frontend *fe);
@@ -352,7 +353,7 @@ static int xc_SetTVStandard(struct xc5000_priv *priv,
 
 static int xc_shutdown(struct xc5000_priv *priv)
 {
-	return 0;
+	return XC_RESULT_SUCCESS;
 	/* Fixme: cannot bring tuner back alive once shutdown
 	 *        without reloading the driver modules.
 	 *    return xc_write_reg(priv, XREG_POWER_DOWN, 0);
@@ -685,6 +686,25 @@ static int xc5000_set_params(struct dvb_frontend *fe,
 	return 0;
 }
 
+static int xc5000_is_firmware_loaded(struct dvb_frontend *fe)
+{
+	struct xc5000_priv *priv = fe->tuner_priv;
+	int ret;
+	u16 id;
+
+	ret = xc5000_readreg(priv, XREG_PRODUCT_ID, &id);
+	if (ret == XC_RESULT_SUCCESS) {
+		if (id == XC_PRODUCT_ID_FW_NOT_LOADED)
+			ret = XC_RESULT_RESET_FAILURE;
+		else
+			ret = XC_RESULT_SUCCESS;
+	}
+
+	dprintk(1, "%s() returns %s id = 0x%x\n", __func__,
+		ret == XC_RESULT_SUCCESS ? "True" : "False", id);
+	return ret;
+}
+
 static int xc_load_fw_and_init_tuner(struct dvb_frontend *fe);
 
 static int xc5000_set_analog_params(struct dvb_frontend *fe,
@@ -693,7 +713,7 @@ static int xc5000_set_analog_params(struct dvb_frontend *fe,
 	struct xc5000_priv *priv = fe->tuner_priv;
 	int ret;
 
-	if(priv->fwloaded == 0)
+	if (xc5000_is_firmware_loaded(fe) != XC_RESULT_SUCCESS)
 		xc_load_fw_and_init_tuner(fe);
 
 	dprintk(1, "%s() frequency=%d (in units of 62.5khz)\n",
@@ -808,11 +828,10 @@ static int xc_load_fw_and_init_tuner(struct dvb_frontend *fe)
 	struct xc5000_priv *priv = fe->tuner_priv;
 	int ret = 0;
 
-	if (priv->fwloaded == 0) {
+	if (xc5000_is_firmware_loaded(fe) != XC_RESULT_SUCCESS) {
 		ret = xc5000_fwupload(fe);
 		if (ret != XC_RESULT_SUCCESS)
 			return ret;
-		priv->fwloaded = 1;
 	}
 
 	/* Start the tuner self-calibration process */
@@ -852,7 +871,6 @@ static int xc5000_sleep(struct dvb_frontend *fe)
 		return -EREMOTEIO;
 	}
 	else {
-		/* priv->fwloaded = 0; */
 		return XC_RESULT_SUCCESS;
 	}
 }
@@ -933,7 +951,6 @@ struct dvb_frontend *xc5000_attach(struct dvb_frontend *fe,
 			cfg->i2c_address);
 		printk(KERN_INFO
 			"xc5000: Firmware has been loaded previously\n");
-		priv->fwloaded = 1;
 		break;
 	case XC_PRODUCT_ID_FW_NOT_LOADED:
 		printk(KERN_INFO
@@ -941,7 +958,6 @@ struct dvb_frontend *xc5000_attach(struct dvb_frontend *fe,
 			cfg->i2c_address);
 		printk(KERN_INFO
 			"xc5000: Firmware has not been loaded previously\n");
-		priv->fwloaded = 0;
 		break;
 	default:
 		printk(KERN_ERR

+ 0 - 1
drivers/media/common/tuners/xc5000_priv.h

@@ -30,7 +30,6 @@ struct xc5000_priv {
 	u32 bandwidth;
 	u8  video_standard;
 	u8  rf_mode;
-	u8  fwloaded;
 
 	void *devptr;
 };

+ 10 - 17
drivers/media/dvb/dvb-usb/gl861.c

@@ -47,6 +47,8 @@ static int gl861_i2c_msg(struct dvb_usb_device *d, u8 addr,
 		return -EINVAL;
 	}
 
+	msleep(1); /* avoid I2C errors */
+
 	return usb_control_msg(d->udev, usb_rcvctrlpipe(d->udev, 0), req, type,
 			       value, index, rbuf, rlen, 2000);
 }
@@ -92,16 +94,6 @@ static struct i2c_algorithm gl861_i2c_algo = {
 };
 
 /* Callbacks for DVB USB */
-static int gl861_identify_state(struct usb_device *udev,
-				struct dvb_usb_device_properties *props,
-				struct dvb_usb_device_description **desc,
-				int *cold)
-{
-	*cold = 0;
-
-	return 0;
-}
-
 static struct zl10353_config gl861_zl10353_config = {
 	.demod_address = 0x0f,
 	.no_tuner = 1,
@@ -172,7 +164,6 @@ static struct dvb_usb_device_properties gl861_properties = {
 
 	.size_of_priv     = 0,
 
-	.identify_state   = gl861_identify_state,
 	.num_adapters = 1,
 	.adapter = {{
 
@@ -194,13 +185,15 @@ static struct dvb_usb_device_properties gl861_properties = {
 
 	.num_device_descs = 2,
 	.devices = {
-		{   "MSI Mega Sky 55801 DVB-T USB2.0",
-			{ &gl861_table[0], NULL },
-			{ NULL },
+		{
+			.name = "MSI Mega Sky 55801 DVB-T USB2.0",
+			.cold_ids = { NULL },
+			.warm_ids = { &gl861_table[0], NULL },
 		},
-		{   "A-LINK DTU DVB-T USB2.0",
-			{ &gl861_table[1], NULL },
-			{ NULL },
+		{
+			.name = "A-LINK DTU DVB-T USB2.0",
+			.cold_ids = { NULL },
+			.warm_ids = { &gl861_table[1], NULL },
 		},
 	}
 };

+ 1 - 1
drivers/media/dvb/dvb-usb/umt-010.c

@@ -107,7 +107,7 @@ static struct dvb_usb_device_properties umt_properties = {
 			/* parameter for the MPEG2-data transfer */
 			.stream = {
 				.type = USB_BULK,
-				.count = 20,
+				.count = MAX_NO_URBS_FOR_DATA_STREAM,
 				.endpoint = 0x06,
 				.u = {
 					.bulk = {

+ 23 - 6
drivers/media/dvb/frontends/au8522.c

@@ -463,10 +463,13 @@ static int au8522_set_frontend(struct dvb_frontend *fe,
 			       struct dvb_frontend_parameters *p)
 {
 	struct au8522_state *state = fe->demodulator_priv;
+	int ret = -EINVAL;
 
 	dprintk("%s(frequency=%d)\n", __func__, p->frequency);
 
-	state->current_frequency = p->frequency;
+	if ((state->current_frequency == p->frequency) &&
+	    (state->current_modulation == p->u.vsb.modulation))
+		return 0;
 
 	au8522_enable_modulation(fe, p->u.vsb.modulation);
 
@@ -476,11 +479,16 @@ static int au8522_set_frontend(struct dvb_frontend *fe,
 	if (fe->ops.tuner_ops.set_params) {
 		if (fe->ops.i2c_gate_ctrl)
 			fe->ops.i2c_gate_ctrl(fe, 1);
-		fe->ops.tuner_ops.set_params(fe, p);
+		ret = fe->ops.tuner_ops.set_params(fe, p);
 		if (fe->ops.i2c_gate_ctrl)
 			fe->ops.i2c_gate_ctrl(fe, 0);
 	}
 
+	if (ret < 0)
+		return ret;
+
+	state->current_frequency = p->frequency;
+
 	return 0;
 }
 
@@ -498,6 +506,16 @@ static int au8522_init(struct dvb_frontend *fe)
 	return 0;
 }
 
+static int au8522_sleep(struct dvb_frontend *fe)
+{
+	struct au8522_state *state = fe->demodulator_priv;
+	dprintk("%s()\n", __func__);
+
+	state->current_frequency = 0;
+
+	return 0;
+}
+
 static int au8522_read_status(struct dvb_frontend *fe, fe_status_t *status)
 {
 	struct au8522_state *state = fe->demodulator_priv;
@@ -509,10 +527,8 @@ static int au8522_read_status(struct dvb_frontend *fe, fe_status_t *status)
 	if (state->current_modulation == VSB_8) {
 		dprintk("%s() Checking VSB_8\n", __func__);
 		reg = au8522_readreg(state, 0x4088);
-		if (reg & 0x01)
-			*status |= FE_HAS_VITERBI;
-		if (reg & 0x02)
-			*status |= FE_HAS_LOCK | FE_HAS_SYNC;
+		if ((reg & 0x03) == 0x03)
+			*status |= FE_HAS_LOCK | FE_HAS_SYNC | FE_HAS_VITERBI;
 	} else {
 		dprintk("%s() Checking QAM\n", __func__);
 		reg = au8522_readreg(state, 0x4541);
@@ -672,6 +688,7 @@ static struct dvb_frontend_ops au8522_ops = {
 	},
 
 	.init                 = au8522_init,
+	.sleep                = au8522_sleep,
 	.i2c_gate_ctrl        = au8522_i2c_gate_ctrl,
 	.set_frontend         = au8522_set_frontend,
 	.get_frontend         = au8522_get_frontend,

+ 11 - 4
drivers/media/dvb/frontends/stv0299.c

@@ -63,6 +63,7 @@ struct stv0299_state {
 	u32 symbol_rate;
 	fe_code_rate_t fec_inner;
 	int errmode;
+	u32 ucblocks;
 };
 
 #define STATUS_BER 0
@@ -501,8 +502,10 @@ static int stv0299_read_ber(struct dvb_frontend* fe, u32* ber)
 {
 	struct stv0299_state* state = fe->demodulator_priv;
 
-	if (state->errmode != STATUS_BER) return 0;
-	*ber = (stv0299_readreg (state, 0x1d) << 8) | stv0299_readreg (state, 0x1e);
+	if (state->errmode != STATUS_BER)
+		return -ENOSYS;
+
+	*ber = stv0299_readreg(state, 0x1e) | (stv0299_readreg(state, 0x1d) << 8);
 
 	return 0;
 }
@@ -540,8 +543,12 @@ static int stv0299_read_ucblocks(struct dvb_frontend* fe, u32* ucblocks)
 {
 	struct stv0299_state* state = fe->demodulator_priv;
 
-	if (state->errmode != STATUS_UCBLOCKS) *ucblocks = 0;
-	else *ucblocks = (stv0299_readreg (state, 0x1d) << 8) | stv0299_readreg (state, 0x1e);
+	if (state->errmode != STATUS_UCBLOCKS)
+		return -ENOSYS;
+
+	state->ucblocks += stv0299_readreg(state, 0x1e);
+	state->ucblocks += (stv0299_readreg(state, 0x1d) << 8);
+	*ucblocks = state->ucblocks;
 
 	return 0;
 }

+ 12 - 8
drivers/media/dvb/frontends/tda10023.c

@@ -116,9 +116,12 @@ static u8 tda10023_readreg (struct tda10023_state* state, u8 reg)
 	int ret;
 
 	ret = i2c_transfer (state->i2c, msg, 2);
-	if (ret != 2)
-		printk("DVB: TDA10023: %s: readreg error (ret == %i)\n",
-				 __func__, ret);
+	if (ret != 2) {
+		int num = state->frontend.dvb ? state->frontend.dvb->num : -1;
+		printk(KERN_ERR "DVB: TDA10023(%d): %s: readreg error "
+			"(reg == 0x%02x, ret == %i)\n",
+			num, __func__, reg, ret);
+	}
 	return b1[0];
 }
 
@@ -129,11 +132,12 @@ static int tda10023_writereg (struct tda10023_state* state, u8 reg, u8 data)
 	int ret;
 
 	ret = i2c_transfer (state->i2c, &msg, 1);
-	if (ret != 1)
-		printk("DVB: TDA10023(%d): %s, writereg error "
+	if (ret != 1) {
+		int num = state->frontend.dvb ? state->frontend.dvb->num : -1;
+		printk(KERN_ERR "DVB: TDA10023(%d): %s, writereg error "
 			"(reg == 0x%02x, val == 0x%02x, ret == %i)\n",
-			state->frontend.dvb->num, __func__, reg, data, ret);
-
+			num, __func__, reg, data, ret);
+	}
 	return (ret != 1) ? -EREMOTEIO : 0;
 }
 
@@ -464,7 +468,7 @@ struct dvb_frontend* tda10023_attach(const struct tda1002x_config* config,
 	int i;
 
 	/* allocate memory for the internal state */
-	state = kmalloc(sizeof(struct tda10023_state), GFP_KERNEL);
+	state = kzalloc(sizeof(struct tda10023_state), GFP_KERNEL);
 	if (state == NULL) goto error;
 
 	/* setup the state */

+ 25 - 4
drivers/media/dvb/frontends/tda1004x.c

@@ -1248,11 +1248,14 @@ struct dvb_frontend* tda10045_attach(const struct tda1004x_config* config,
 				     struct i2c_adapter* i2c)
 {
 	struct tda1004x_state *state;
+	int id;
 
 	/* allocate memory for the internal state */
 	state = kmalloc(sizeof(struct tda1004x_state), GFP_KERNEL);
-	if (!state)
+	if (!state) {
+		printk(KERN_ERR "Can't alocate memory for tda10045 state\n");
 		return NULL;
+	}
 
 	/* setup the state */
 	state->config = config;
@@ -1260,7 +1263,15 @@ struct dvb_frontend* tda10045_attach(const struct tda1004x_config* config,
 	state->demod_type = TDA1004X_DEMOD_TDA10045;
 
 	/* check if the demod is there */
-	if (tda1004x_read_byte(state, TDA1004X_CHIPID) != 0x25) {
+	id = tda1004x_read_byte(state, TDA1004X_CHIPID);
+	if (id < 0) {
+		printk(KERN_ERR "tda10045: chip is not answering. Giving up.\n");
+		kfree(state);
+		return NULL;
+	}
+
+	if (id != 0x25) {
+		printk(KERN_ERR "Invalid tda1004x ID = 0x%02x. Can't proceed\n", id);
 		kfree(state);
 		return NULL;
 	}
@@ -1307,11 +1318,14 @@ struct dvb_frontend* tda10046_attach(const struct tda1004x_config* config,
 				     struct i2c_adapter* i2c)
 {
 	struct tda1004x_state *state;
+	int id;
 
 	/* allocate memory for the internal state */
 	state = kmalloc(sizeof(struct tda1004x_state), GFP_KERNEL);
-	if (!state)
+	if (!state) {
+		printk(KERN_ERR "Can't alocate memory for tda10046 state\n");
 		return NULL;
+	}
 
 	/* setup the state */
 	state->config = config;
@@ -1319,7 +1333,14 @@ struct dvb_frontend* tda10046_attach(const struct tda1004x_config* config,
 	state->demod_type = TDA1004X_DEMOD_TDA10046;
 
 	/* check if the demod is there */
-	if (tda1004x_read_byte(state, TDA1004X_CHIPID) != 0x46) {
+	id = tda1004x_read_byte(state, TDA1004X_CHIPID);
+	if (id < 0) {
+		printk(KERN_ERR "tda10046: chip is not answering. Giving up.\n");
+		kfree(state);
+		return NULL;
+	}
+	if (id != 0x46) {
+		printk(KERN_ERR "Invalid tda1004x ID = 0x%02x. Can't proceed\n", id);
 		kfree(state);
 		return NULL;
 	}

+ 1 - 0
drivers/media/dvb/ttpci/Kconfig

@@ -101,6 +101,7 @@ config DVB_BUDGET
 config DVB_BUDGET_CI
 	tristate "Budget cards with onboard CI connector"
 	depends on DVB_BUDGET_CORE && I2C
+	depends on INPUT # due to IR
 	select DVB_STV0297 if !DVB_FE_CUSTOMISE
 	select DVB_STV0299 if !DVB_FE_CUSTOMISE
 	select DVB_TDA1004X if !DVB_FE_CUSTOMISE

+ 2 - 3
drivers/media/dvb/ttpci/av7110_hw.c

@@ -427,6 +427,7 @@ static int __av7110_send_fw_cmd(struct av7110 *av7110, u16* buf, int length)
 			if (err) {
 				printk(KERN_ERR "%s: timeout waiting on busy %s QUEUE\n",
 					__func__, type);
+				av7110->arm_errors++;
 				return -ETIMEDOUT;
 			}
 			msleep(1);
@@ -853,10 +854,8 @@ static osd_raw_window_t bpp2bit[8] = {
 
 static inline int WaitUntilBmpLoaded(struct av7110 *av7110)
 {
-	int ret = wait_event_interruptible_timeout(av7110->bmpq,
+	int ret = wait_event_timeout(av7110->bmpq,
 				av7110->bmp_state != BMP_LOADING, 10*HZ);
-	if (ret == -ERESTARTSYS)
-		return ret;
 	if (ret == 0) {
 		printk("dvb-ttpci: warning: timeout waiting in LoadBitmap: %d, %d\n",
 		       ret, av7110->bmp_state);

+ 18 - 0
drivers/media/video/au0828/au0828-cards.c

@@ -77,8 +77,14 @@ static void hauppauge_eeprom(struct au0828_dev *dev, u8 *eeprom_data)
 
 	/* Make sure we support the board model */
 	switch (tv.model) {
+	case 72000: /* WinTV-HVR950q (Retail, IR, ATSC/QAM */
 	case 72001: /* WinTV-HVR950q (Retail, IR, ATSC/QAM and basic analog video */
+	case 72211: /* WinTV-HVR950q (OEM, IR, ATSC/QAM and basic analog video */
+	case 72221: /* WinTV-HVR950q (OEM, IR, ATSC/QAM and basic analog video */
+	case 72231: /* WinTV-HVR950q (OEM, IR, ATSC/QAM and basic analog video */
+	case 72241: /* WinTV-HVR950q (OEM, No IR, ATSC/QAM and basic analog video */
 	case 72301: /* WinTV-HVR850 (Retail, IR, ATSC and basic analog video */
+	case 72500: /* WinTV-HVR950q (OEM, No IR, ATSC/QAM */
 		break;
 	default:
 		printk(KERN_WARNING "%s: warning: "
@@ -175,6 +181,18 @@ struct usb_device_id au0828_usb_id_table [] = {
 		.driver_info = AU0828_BOARD_HAUPPAUGE_HVR850 },
 	{ USB_DEVICE(0x0fe9, 0xd620),
 		.driver_info = AU0828_BOARD_DVICO_FUSIONHDTV7 },
+	{ USB_DEVICE(0x2040, 0x7210),
+		.driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
+	{ USB_DEVICE(0x2040, 0x7217),
+		.driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
+	{ USB_DEVICE(0x2040, 0x721b),
+		.driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
+	{ USB_DEVICE(0x2040, 0x721f),
+		.driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
+	{ USB_DEVICE(0x2040, 0x7280),
+		.driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
+	{ USB_DEVICE(0x0fd9, 0x0008),
+		.driver_info = AU0828_BOARD_HAUPPAUGE_HVR950Q },
 	{ },
 };
 

+ 2 - 2
drivers/media/video/cx18/Kconfig

@@ -10,8 +10,8 @@ config VIDEO_CX18
 	select VIDEO_TVEEPROM
 	select VIDEO_CX2341X
 	select VIDEO_CS5345
-	select DVB_S5H1409
-	select MEDIA_TUNER_MXL5005S
+	select DVB_S5H1409 if !DVB_FE_CUSTOMISE
+	select MEDIA_TUNER_MXL5005S if !DVB_FE_CUSTOMISE
 	---help---
 	  This is a video4linux driver for Conexant cx23418 based
 	  PCI combo video recorder devices.

+ 64 - 9
drivers/media/video/cx18/cx18-av-core.c

@@ -69,6 +69,58 @@ int cx18_av_and_or4(struct cx18 *cx, u16 addr, u32 and_mask,
 			     or_value);
 }
 
+int cx18_av_write_no_acfg(struct cx18 *cx, u16 addr, u8 value, int no_acfg_mask)
+{
+	int retval;
+	u32 saved_reg[8] = {0};
+
+	if (no_acfg_mask & CXADEC_NO_ACFG_AFE) {
+		saved_reg[0] = cx18_av_read4(cx, CXADEC_CHIP_CTRL);
+		saved_reg[1] = cx18_av_read4(cx, CXADEC_AFE_CTRL);
+	}
+
+	if (no_acfg_mask & CXADEC_NO_ACFG_PLL) {
+		saved_reg[2] = cx18_av_read4(cx, CXADEC_PLL_CTRL1);
+		saved_reg[3] = cx18_av_read4(cx, CXADEC_VID_PLL_FRAC);
+	}
+
+	if (no_acfg_mask & CXADEC_NO_ACFG_VID) {
+		saved_reg[4] = cx18_av_read4(cx, CXADEC_HORIZ_TIM_CTRL);
+		saved_reg[5] = cx18_av_read4(cx, CXADEC_VERT_TIM_CTRL);
+		saved_reg[6] = cx18_av_read4(cx, CXADEC_SRC_COMB_CFG);
+		saved_reg[7] = cx18_av_read4(cx, CXADEC_CHROMA_VBIOFF_CFG);
+	}
+
+	retval = cx18_av_write(cx, addr, value);
+
+	if (no_acfg_mask & CXADEC_NO_ACFG_AFE) {
+		cx18_av_write4(cx, CXADEC_CHIP_CTRL, saved_reg[0]);
+		cx18_av_write4(cx, CXADEC_AFE_CTRL,  saved_reg[1]);
+	}
+
+	if (no_acfg_mask & CXADEC_NO_ACFG_PLL) {
+		cx18_av_write4(cx, CXADEC_PLL_CTRL1,    saved_reg[2]);
+		cx18_av_write4(cx, CXADEC_VID_PLL_FRAC, saved_reg[3]);
+	}
+
+	if (no_acfg_mask & CXADEC_NO_ACFG_VID) {
+		cx18_av_write4(cx, CXADEC_HORIZ_TIM_CTRL,    saved_reg[4]);
+		cx18_av_write4(cx, CXADEC_VERT_TIM_CTRL,     saved_reg[5]);
+		cx18_av_write4(cx, CXADEC_SRC_COMB_CFG,      saved_reg[6]);
+		cx18_av_write4(cx, CXADEC_CHROMA_VBIOFF_CFG, saved_reg[7]);
+	}
+
+	return retval;
+}
+
+int cx18_av_and_or_no_acfg(struct cx18 *cx, u16 addr, unsigned and_mask,
+			   u8 or_value, int no_acfg_mask)
+{
+	return cx18_av_write_no_acfg(cx, addr,
+				     (cx18_av_read(cx, addr) & and_mask) |
+				     or_value, no_acfg_mask);
+}
+
 /* ----------------------------------------------------------------------- */
 
 static int set_input(struct cx18 *cx, enum cx18_av_video_input vid_input,
@@ -170,13 +222,15 @@ static void input_change(struct cx18 *cx)
 
 	/* Follow step 8c and 8d of section 3.16 in the cx18_av datasheet */
 	if (std & V4L2_STD_SECAM)
-		cx18_av_write(cx, 0x402, 0);
+		cx18_av_write_no_acfg(cx, 0x402, 0, CXADEC_NO_ACFG_ALL);
 	else {
-		cx18_av_write(cx, 0x402, 0x04);
+		cx18_av_write_no_acfg(cx, 0x402, 0x04, CXADEC_NO_ACFG_ALL);
 		cx18_av_write(cx, 0x49f, (std & V4L2_STD_NTSC) ? 0x14 : 0x11);
 	}
-	cx18_av_and_or(cx, 0x401, ~0x60, 0);
-	cx18_av_and_or(cx, 0x401, ~0x60, 0x60);
+	cx18_av_and_or_no_acfg(cx, 0x401, ~0x60, 0,
+				CXADEC_NO_ACFG_PLL | CXADEC_NO_ACFG_VID);
+	cx18_av_and_or_no_acfg(cx, 0x401, ~0x60, 0x60,
+				CXADEC_NO_ACFG_PLL | CXADEC_NO_ACFG_VID);
 
 	if (std & V4L2_STD_525_60) {
 		if (std == V4L2_STD_NTSC_M_JP) {
@@ -228,7 +282,7 @@ static int set_input(struct cx18 *cx, enum cx18_av_video_input vid_input,
 
 		if ((vid_input & ~0xff0) ||
 		    luma < CX18_AV_SVIDEO_LUMA1 ||
-		    luma > CX18_AV_SVIDEO_LUMA4 ||
+		    luma > CX18_AV_SVIDEO_LUMA8 ||
 		    chroma < CX18_AV_SVIDEO_CHROMA4 ||
 		    chroma > CX18_AV_SVIDEO_CHROMA8) {
 			CX18_ERR("0x%04x is not a valid video input!\n",
@@ -262,7 +316,8 @@ static int set_input(struct cx18 *cx, enum cx18_av_video_input vid_input,
 
 	cx18_av_write(cx, 0x103, reg);
 	/* Set INPUT_MODE to Composite (0) or S-Video (1) */
-	cx18_av_and_or(cx, 0x401, ~0x6, is_composite ? 0 : 0x02);
+	cx18_av_and_or_no_acfg(cx, 0x401, ~0x6, is_composite ? 0 : 0x02,
+				CXADEC_NO_ACFG_PLL | CXADEC_NO_ACFG_VID);
 	/* Set CH_SEL_ADC2 to 1 if input comes from CH3 */
 	cx18_av_and_or(cx, 0x102, ~0x2, (reg & 0x80) == 0 ? 2 : 0);
 	/* Set DUAL_MODE_ADC2 to 1 if input comes from both CH2 and CH3 */
@@ -318,12 +373,12 @@ static int set_v4lstd(struct cx18 *cx)
 	   This happens for example with the Yuan MPC622. */
 	if (fmt >= 4 && fmt < 8) {
 		/* Set format to NTSC-M */
-		cx18_av_and_or(cx, 0x400, ~0xf, 1);
+		cx18_av_and_or_no_acfg(cx, 0x400, ~0xf, 1, CXADEC_NO_ACFG_AFE);
 		/* Turn off LCOMB */
 		cx18_av_and_or(cx, 0x47b, ~6, 0);
 	}
-	cx18_av_and_or(cx, 0x400, ~0xf, fmt);
-	cx18_av_and_or(cx, 0x403, ~0x3, pal_m);
+	cx18_av_and_or_no_acfg(cx, 0x400, ~0xf, fmt, CXADEC_NO_ACFG_AFE);
+	cx18_av_and_or_no_acfg(cx, 0x403, ~0x3, pal_m, CXADEC_NO_ACFG_ALL);
 	cx18_av_vbi_setup(cx);
 	input_change(cx);
 	return 0;

+ 15 - 1
drivers/media/video/cx18/cx18-av-core.h

@@ -37,12 +37,16 @@ enum cx18_av_video_input {
 	CX18_AV_COMPOSITE7,
 	CX18_AV_COMPOSITE8,
 
-	/* S-Video inputs consist of one luma input (In1-In4) ORed with one
+	/* S-Video inputs consist of one luma input (In1-In8) ORed with one
 	   chroma input (In5-In8) */
 	CX18_AV_SVIDEO_LUMA1 = 0x10,
 	CX18_AV_SVIDEO_LUMA2 = 0x20,
 	CX18_AV_SVIDEO_LUMA3 = 0x30,
 	CX18_AV_SVIDEO_LUMA4 = 0x40,
+	CX18_AV_SVIDEO_LUMA5 = 0x50,
+	CX18_AV_SVIDEO_LUMA6 = 0x60,
+	CX18_AV_SVIDEO_LUMA7 = 0x70,
+	CX18_AV_SVIDEO_LUMA8 = 0x80,
 	CX18_AV_SVIDEO_CHROMA4 = 0x400,
 	CX18_AV_SVIDEO_CHROMA5 = 0x500,
 	CX18_AV_SVIDEO_CHROMA6 = 0x600,
@@ -291,14 +295,24 @@ struct cx18_av_state {
 #define CXADEC_SELECT_AUDIO_STANDARD_FM    0xF9  /* FM radio */
 #define CXADEC_SELECT_AUDIO_STANDARD_AUTO  0xFF  /* Auto detect */
 
+/* Flags on what to preserve on write to 0x400-0x403 with cx18_av_.*_no_acfg()*/
+#define CXADEC_NO_ACFG_AFE	0x01 /* Preserve 0x100-0x107 */
+#define CXADEC_NO_ACFG_PLL	0x02 /* Preserve 0x108-0x10f */
+#define CXADEC_NO_ACFG_VID	0x04 /* Preserve 0x470-0x47f */
+#define CXADEC_NO_ACFG_ALL	0x07
+
 /* ----------------------------------------------------------------------- */
 /* cx18_av-core.c 							   */
 int cx18_av_write(struct cx18 *cx, u16 addr, u8 value);
 int cx18_av_write4(struct cx18 *cx, u16 addr, u32 value);
+int cx18_av_write_no_acfg(struct cx18 *cx, u16 addr, u8 value,
+				int no_acfg_mask);
 u8 cx18_av_read(struct cx18 *cx, u16 addr);
 u32 cx18_av_read4(struct cx18 *cx, u16 addr);
 int cx18_av_and_or(struct cx18 *cx, u16 addr, unsigned mask, u8 value);
 int cx18_av_and_or4(struct cx18 *cx, u16 addr, u32 mask, u32 value);
+int cx18_av_and_or_no_acfg(struct cx18 *cx, u16 addr, unsigned mask, u8 value,
+				int no_acfg_mask);
 int cx18_av_cmd(struct cx18 *cx, unsigned int cmd, void *arg);
 
 /* ----------------------------------------------------------------------- */

+ 49 - 35
drivers/media/video/cx18/cx18-cards.c

@@ -23,6 +23,7 @@
 
 #include "cx18-driver.h"
 #include "cx18-cards.h"
+#include "cx18-av-core.h"
 #include "cx18-i2c.h"
 #include <media/cs5345.h>
 
@@ -54,22 +55,22 @@ static const struct cx18_card cx18_card_hvr1600_esmt = {
 	.hw_all = CX18_HW_TVEEPROM | CX18_HW_TUNER |
 		  CX18_HW_CS5345 | CX18_HW_DVB,
 	.video_inputs = {
-		{ CX18_CARD_INPUT_VID_TUNER,  0, CX23418_COMPOSITE7 },
-		{ CX18_CARD_INPUT_SVIDEO1,    1, CX23418_SVIDEO1    },
-		{ CX18_CARD_INPUT_COMPOSITE1, 1, CX23418_COMPOSITE3 },
-		{ CX18_CARD_INPUT_SVIDEO2,    2, CX23418_SVIDEO2    },
-		{ CX18_CARD_INPUT_COMPOSITE2, 2, CX23418_COMPOSITE4 },
+		{ CX18_CARD_INPUT_VID_TUNER,  0, CX18_AV_COMPOSITE7 },
+		{ CX18_CARD_INPUT_SVIDEO1,    1, CX18_AV_SVIDEO1    },
+		{ CX18_CARD_INPUT_COMPOSITE1, 1, CX18_AV_COMPOSITE3 },
+		{ CX18_CARD_INPUT_SVIDEO2,    2, CX18_AV_SVIDEO2    },
+		{ CX18_CARD_INPUT_COMPOSITE2, 2, CX18_AV_COMPOSITE4 },
 	},
 	.audio_inputs = {
 		{ CX18_CARD_INPUT_AUD_TUNER,
-		  CX23418_AUDIO8, CS5345_IN_1 | CS5345_MCLK_1_5 },
+		  CX18_AV_AUDIO8, CS5345_IN_1 | CS5345_MCLK_1_5 },
 		{ CX18_CARD_INPUT_LINE_IN1,
-		  CX23418_AUDIO_SERIAL, CS5345_IN_2 },
+		  CX18_AV_AUDIO_SERIAL, CS5345_IN_2 },
 		{ CX18_CARD_INPUT_LINE_IN2,
-		  CX23418_AUDIO_SERIAL, CS5345_IN_2 },
+		  CX18_AV_AUDIO_SERIAL, CS5345_IN_3 },
 	},
 	.radio_input = { CX18_CARD_INPUT_AUD_TUNER,
-			 CX23418_AUDIO_SERIAL, 0 },
+			 CX18_AV_AUDIO_SERIAL, CS5345_IN_4 },
 	.ddr = {
 		/* ESMT M13S128324A-5B memory */
 		.chip_config = 0x003,
@@ -81,6 +82,11 @@ static const struct cx18_card cx18_card_hvr1600_esmt = {
 	},
 	.gpio_init.initial_value = 0x3001,
 	.gpio_init.direction = 0x3001,
+	.gpio_i2c_slave_reset = {
+		.active_lo_mask = 0x3001,
+		.msecs_asserted = 10,
+		.msecs_recovery = 40,
+	},
 	.i2c = &cx18_i2c_std,
 };
 
@@ -94,22 +100,22 @@ static const struct cx18_card cx18_card_hvr1600_samsung = {
 	.hw_all = CX18_HW_TVEEPROM | CX18_HW_TUNER |
 		  CX18_HW_CS5345 | CX18_HW_DVB,
 	.video_inputs = {
-		{ CX18_CARD_INPUT_VID_TUNER,  0, CX23418_COMPOSITE7 },
-		{ CX18_CARD_INPUT_SVIDEO1,    1, CX23418_SVIDEO1    },
-		{ CX18_CARD_INPUT_COMPOSITE1, 1, CX23418_COMPOSITE3 },
-		{ CX18_CARD_INPUT_SVIDEO2,    2, CX23418_SVIDEO2    },
-		{ CX18_CARD_INPUT_COMPOSITE2, 2, CX23418_COMPOSITE4 },
+		{ CX18_CARD_INPUT_VID_TUNER,  0, CX18_AV_COMPOSITE7 },
+		{ CX18_CARD_INPUT_SVIDEO1,    1, CX18_AV_SVIDEO1    },
+		{ CX18_CARD_INPUT_COMPOSITE1, 1, CX18_AV_COMPOSITE3 },
+		{ CX18_CARD_INPUT_SVIDEO2,    2, CX18_AV_SVIDEO2    },
+		{ CX18_CARD_INPUT_COMPOSITE2, 2, CX18_AV_COMPOSITE4 },
 	},
 	.audio_inputs = {
 		{ CX18_CARD_INPUT_AUD_TUNER,
-		  CX23418_AUDIO8, CS5345_IN_1 | CS5345_MCLK_1_5 },
+		  CX18_AV_AUDIO8, CS5345_IN_1 | CS5345_MCLK_1_5 },
 		{ CX18_CARD_INPUT_LINE_IN1,
-		  CX23418_AUDIO_SERIAL, CS5345_IN_2 },
+		  CX18_AV_AUDIO_SERIAL, CS5345_IN_2 },
 		{ CX18_CARD_INPUT_LINE_IN2,
-		  CX23418_AUDIO_SERIAL, CS5345_IN_2 },
+		  CX18_AV_AUDIO_SERIAL, CS5345_IN_3 },
 	},
 	.radio_input = { CX18_CARD_INPUT_AUD_TUNER,
-			 CX23418_AUDIO_SERIAL, 0 },
+			 CX18_AV_AUDIO_SERIAL, CS5345_IN_4 },
 	.ddr = {
 		/* Samsung K4D263238G-VC33 memory */
 		.chip_config = 0x003,
@@ -121,6 +127,11 @@ static const struct cx18_card cx18_card_hvr1600_samsung = {
 	},
 	.gpio_init.initial_value = 0x3001,
 	.gpio_init.direction = 0x3001,
+	.gpio_i2c_slave_reset = {
+		.active_lo_mask = 0x3001,
+		.msecs_asserted = 10,
+		.msecs_recovery = 40,
+	},
 	.i2c = &cx18_i2c_std,
 };
 
@@ -141,19 +152,19 @@ static const struct cx18_card cx18_card_h900 = {
 	.hw_audio_ctrl = CX18_HW_CX23418,
 	.hw_all = CX18_HW_TUNER,
 	.video_inputs = {
-		{ CX18_CARD_INPUT_VID_TUNER,  0, CX23418_COMPOSITE2 },
+		{ CX18_CARD_INPUT_VID_TUNER,  0, CX18_AV_COMPOSITE2 },
 		{ CX18_CARD_INPUT_SVIDEO1,    1,
-			CX23418_SVIDEO_LUMA3 | CX23418_SVIDEO_CHROMA4 },
-		{ CX18_CARD_INPUT_COMPOSITE1, 1, CX23418_COMPOSITE1 },
+			CX18_AV_SVIDEO_LUMA3 | CX18_AV_SVIDEO_CHROMA4 },
+		{ CX18_CARD_INPUT_COMPOSITE1, 1, CX18_AV_COMPOSITE1 },
 	},
 	.audio_inputs = {
 		{ CX18_CARD_INPUT_AUD_TUNER,
-		  CX23418_AUDIO8, 0 },
+		  CX18_AV_AUDIO8, 0 },
 		{ CX18_CARD_INPUT_LINE_IN1,
-		  CX23418_AUDIO_SERIAL, 0 },
+		  CX18_AV_AUDIO_SERIAL, 0 },
 	},
 	.radio_input = { CX18_CARD_INPUT_AUD_TUNER,
-			 CX23418_AUDIO_SERIAL, 0 },
+			 CX18_AV_AUDIO_SERIAL, 0 },
 	.tuners = {
 		{ .std = V4L2_STD_ALL, .tuner = TUNER_XC2028 },
 	},
@@ -183,23 +194,26 @@ static const struct cx18_card_pci_info cx18_pci_mpc718[] = {
 static const struct cx18_card cx18_card_mpc718 = {
 	.type = CX18_CARD_YUAN_MPC718,
 	.name = "Yuan MPC718",
-	.comment = "Not yet supported!\n",
-	.v4l2_capabilities = 0,
+	.comment = "Some Composite and S-Video inputs are currently working.\n",
+	.v4l2_capabilities = CX18_CAP_ENCODER,
 	.hw_audio_ctrl = CX18_HW_CX23418,
 	.hw_all = CX18_HW_TUNER,
 	.video_inputs = {
-		{ CX18_CARD_INPUT_VID_TUNER,  0, CX23418_COMPOSITE7 },
-		{ CX18_CARD_INPUT_SVIDEO1,    1, CX23418_SVIDEO1    },
-		{ CX18_CARD_INPUT_COMPOSITE1, 1, CX23418_COMPOSITE3 },
+		{ CX18_CARD_INPUT_VID_TUNER,  0, CX18_AV_COMPOSITE2 },
+		{ CX18_CARD_INPUT_SVIDEO1,    1,
+				CX18_AV_SVIDEO_LUMA3 | CX18_AV_SVIDEO_CHROMA4 },
+		{ CX18_CARD_INPUT_COMPOSITE1, 1, CX18_AV_COMPOSITE1 },
+		{ CX18_CARD_INPUT_SVIDEO2,    2,
+				CX18_AV_SVIDEO_LUMA7 | CX18_AV_SVIDEO_CHROMA8 },
+		{ CX18_CARD_INPUT_COMPOSITE2, 2, CX18_AV_COMPOSITE6 },
+		{ CX18_CARD_INPUT_COMPOSITE3, 2, CX18_AV_COMPOSITE3 },
 	},
 	.audio_inputs = {
-		{ CX18_CARD_INPUT_AUD_TUNER,
-		  CX23418_AUDIO8, 0 },
-		{ CX18_CARD_INPUT_LINE_IN1,
-		  CX23418_AUDIO_SERIAL, 0 },
+		{ CX18_CARD_INPUT_AUD_TUNER, CX18_AV_AUDIO5,       0 },
+		{ CX18_CARD_INPUT_LINE_IN1,  CX18_AV_AUDIO_SERIAL, 0 },
+		{ CX18_CARD_INPUT_LINE_IN2,  CX18_AV_AUDIO_SERIAL, 0 },
 	},
-	.radio_input = { CX18_CARD_INPUT_AUD_TUNER,
-			 CX23418_AUDIO_SERIAL, 0 },
+	.radio_input = { CX18_CARD_INPUT_AUD_TUNER, CX18_AV_AUDIO_SERIAL, 0 },
 	.tuners = {
 		/* XC3028 tuner */
 		{ .std = V4L2_STD_ALL, .tuner = TUNER_XC2028 },

+ 9 - 41
drivers/media/video/cx18/cx18-cards.h

@@ -36,36 +36,6 @@
 #define	CX18_CARD_INPUT_COMPOSITE2 	5
 #define	CX18_CARD_INPUT_COMPOSITE3 	6
 
-enum cx34180_video_input {
-	/* Composite video inputs In1-In8 */
-	CX23418_COMPOSITE1 = 1,
-	CX23418_COMPOSITE2,
-	CX23418_COMPOSITE3,
-	CX23418_COMPOSITE4,
-	CX23418_COMPOSITE5,
-	CX23418_COMPOSITE6,
-	CX23418_COMPOSITE7,
-	CX23418_COMPOSITE8,
-
-	/* S-Video inputs consist of one luma input (In1-In4) ORed with one
-	   chroma input (In5-In8) */
-	CX23418_SVIDEO_LUMA1 = 0x10,
-	CX23418_SVIDEO_LUMA2 = 0x20,
-	CX23418_SVIDEO_LUMA3 = 0x30,
-	CX23418_SVIDEO_LUMA4 = 0x40,
-	CX23418_SVIDEO_CHROMA4 = 0x400,
-	CX23418_SVIDEO_CHROMA5 = 0x500,
-	CX23418_SVIDEO_CHROMA6 = 0x600,
-	CX23418_SVIDEO_CHROMA7 = 0x700,
-	CX23418_SVIDEO_CHROMA8 = 0x800,
-
-	/* S-Video aliases for common luma/chroma combinations */
-	CX23418_SVIDEO1 = 0x510,
-	CX23418_SVIDEO2 = 0x620,
-	CX23418_SVIDEO3 = 0x730,
-	CX23418_SVIDEO4 = 0x840,
-};
-
 /* audio inputs */
 #define	CX18_CARD_INPUT_AUD_TUNER	1
 #define	CX18_CARD_INPUT_LINE_IN1 	2
@@ -75,16 +45,6 @@ enum cx34180_video_input {
 #define CX18_CARD_MAX_AUDIO_INPUTS 3
 #define CX18_CARD_MAX_TUNERS  	   2
 
-enum cx23418_audio_input {
-	/* Audio inputs: serial or In4-In8 */
-	CX23418_AUDIO_SERIAL,
-	CX23418_AUDIO4 = 4,
-	CX23418_AUDIO5,
-	CX23418_AUDIO6,
-	CX23418_AUDIO7,
-	CX23418_AUDIO8,
-};
-
 /* V4L2 capability aliases */
 #define CX18_CAP_ENCODER (V4L2_CAP_VIDEO_CAPTURE | V4L2_CAP_TUNER | \
 			  V4L2_CAP_AUDIO | V4L2_CAP_READWRITE)
@@ -118,6 +78,13 @@ struct cx18_gpio_init { /* set initial GPIO DIR and OUT values */
 	u32 initial_value;
 };
 
+struct cx18_gpio_i2c_slave_reset {
+	u32 active_lo_mask; /* GPIO outputs that reset i2c chips when low */
+	u32 active_hi_mask; /* GPIO outputs that reset i2c chips when high */
+	int msecs_asserted; /* time period reset must remain asserted */
+	int msecs_recovery; /* time after deassert for chips to be ready */
+};
+
 struct cx18_card_tuner {
 	v4l2_std_id std; 	/* standard for which the tuner is suitable */
 	int 	    tuner; 	/* tuner ID (from tuner.h) */
@@ -154,7 +121,8 @@ struct cx18_card {
 
 	/* GPIO card-specific settings */
 	u8 xceive_pin; 		/* XCeive tuner GPIO reset pin */
-	struct cx18_gpio_init 		gpio_init;
+	struct cx18_gpio_init 		 gpio_init;
+	struct cx18_gpio_i2c_slave_reset gpio_i2c_slave_reset;
 
 	struct cx18_card_tuner tuners[CX18_CARD_MAX_TUNERS];
 	struct cx18_card_tuner_i2c *i2c;

+ 16 - 1
drivers/media/video/cx18/cx18-dvb.c

@@ -69,11 +69,21 @@ static int cx18_dvb_start_feed(struct dvb_demux_feed *feed)
 	struct dvb_demux *demux = feed->demux;
 	struct cx18_stream *stream = (struct cx18_stream *) demux->priv;
 	struct cx18 *cx = stream->cx;
-	int ret = -EINVAL;
+	int ret;
 	u32 v;
 
 	CX18_DEBUG_INFO("Start feed: pid = 0x%x index = %d\n",
 			feed->pid, feed->index);
+
+	mutex_lock(&cx->serialize_lock);
+	ret = cx18_init_on_first_open(cx);
+	mutex_unlock(&cx->serialize_lock);
+	if (ret) {
+		CX18_ERR("Failed to initialize firmware starting DVB feed\n");
+		return ret;
+	}
+	ret = -EINVAL;
+
 	switch (cx->card->type) {
 	case CX18_CARD_HVR_1600_ESMT:
 	case CX18_CARD_HVR_1600_SAMSUNG:
@@ -101,6 +111,11 @@ static int cx18_dvb_start_feed(struct dvb_demux_feed *feed)
 		if (stream->dvb.feeding++ == 0) {
 			CX18_DEBUG_INFO("Starting Transport DMA\n");
 			ret = cx18_start_v4l2_encode_stream(stream);
+			if (ret < 0) {
+				CX18_DEBUG_INFO(
+					"Failed to start Transport DMA\n");
+				stream->dvb.feeding--;
+			}
 		} else
 			ret = 0;
 		mutex_unlock(&stream->dvb.feedlock);

+ 25 - 1
drivers/media/video/cx18/cx18-gpio.c

@@ -53,10 +53,34 @@ static void gpio_write(struct cx18 *cx)
 	write_reg(((dir & 0xffff) << 16) | (val & 0xffff),
 			CX18_REG_GPIO_OUT1);
 	write_reg(dir & 0xffff0000, CX18_REG_GPIO_DIR2);
-	write_reg((dir & 0xffff0000) | ((val & 0xffff0000) >> 16),
+	write_reg_sync((dir & 0xffff0000) | ((val & 0xffff0000) >> 16),
 			CX18_REG_GPIO_OUT2);
 }
 
+void cx18_reset_i2c_slaves_gpio(struct cx18 *cx)
+{
+	const struct cx18_gpio_i2c_slave_reset *p;
+
+	p = &cx->card->gpio_i2c_slave_reset;
+
+	if ((p->active_lo_mask | p->active_hi_mask) == 0)
+		return;
+
+	/* Assuming that the masks are a subset of the bits in gpio_dir */
+
+	/* Assert */
+	cx->gpio_val =
+		(cx->gpio_val | p->active_hi_mask) & ~(p->active_lo_mask);
+	gpio_write(cx);
+	schedule_timeout_uninterruptible(msecs_to_jiffies(p->msecs_asserted));
+
+	/* Deassert */
+	cx->gpio_val =
+		(cx->gpio_val | p->active_lo_mask) & ~(p->active_hi_mask);
+	gpio_write(cx);
+	schedule_timeout_uninterruptible(msecs_to_jiffies(p->msecs_recovery));
+}
+
 void cx18_gpio_init(struct cx18 *cx)
 {
 	cx->gpio_dir = cx->card->gpio_init.direction;

+ 1 - 0
drivers/media/video/cx18/cx18-gpio.h

@@ -21,4 +21,5 @@
  */
 
 void cx18_gpio_init(struct cx18 *cx);
+void cx18_reset_i2c_slaves_gpio(struct cx18 *cx);
 int cx18_reset_tuner_gpio(void *dev, int cmd, int value);

+ 2 - 0
drivers/media/video/cx18/cx18-i2c.c

@@ -405,6 +405,8 @@ int init_cx18_i2c(struct cx18 *cx)
 	cx18_setscl(&cx->i2c_algo_cb_data[1], 1);
 	cx18_setsda(&cx->i2c_algo_cb_data[1], 1);
 
+	cx18_reset_i2c_slaves_gpio(cx);
+
 	return i2c_bit_add_bus(&cx->i2c_adap[0]) ||
 		i2c_bit_add_bus(&cx->i2c_adap[1]);
 }

+ 1 - 1
drivers/media/video/cx25840/cx25840-core.c

@@ -433,7 +433,7 @@ static int set_input(struct i2c_client *client, enum cx25840_video_input vid_inp
 		int chroma = vid_input & 0xf00;
 
 		if ((vid_input & ~0xff0) ||
-		    luma < CX25840_SVIDEO_LUMA1 || luma > CX25840_SVIDEO_LUMA4 ||
+		    luma < CX25840_SVIDEO_LUMA1 || luma > CX25840_SVIDEO_LUMA8 ||
 		    chroma < CX25840_SVIDEO_CHROMA4 || chroma > CX25840_SVIDEO_CHROMA8) {
 			v4l_err(client, "0x%04x is not a valid video input!\n",
 				vid_input);

+ 6 - 0
drivers/media/video/cx88/cx88-alsa.c

@@ -332,6 +332,12 @@ static int snd_cx88_pcm_open(struct snd_pcm_substream *substream)
 	struct snd_pcm_runtime *runtime = substream->runtime;
 	int err;
 
+	if (!chip) {
+		printk(KERN_ERR "BUG: cx88 can't find device struct."
+				" Can't proceed with open\n");
+		return -ENODEV;
+	}
+
 	err = snd_pcm_hw_constraint_pow2(runtime, 0, SNDRV_PCM_HW_PARAM_PERIODS);
 	if (err < 0)
 		goto _error;

+ 18 - 0
drivers/media/video/em28xx/em28xx-audio.c

@@ -268,6 +268,12 @@ static int snd_em28xx_capture_open(struct snd_pcm_substream *substream)
 
 	dprintk("opening device and trying to acquire exclusive lock\n");
 
+	if (!dev) {
+		printk(KERN_ERR "BUG: em28xx can't find device struct."
+				" Can't proceed with open\n");
+		return -ENODEV;
+	}
+
 	/* Sets volume, mute, etc */
 
 	dev->mute = 0;
@@ -415,6 +421,12 @@ static int em28xx_audio_init(struct em28xx *dev)
 	static int          devnr;
 	int                 ret, err;
 
+	if (dev->has_audio_class) {
+		/* This device does not support the extension (in this case
+		   the device is expecting the snd-usb-audio module */
+		return 0;
+	}
+
 	printk(KERN_INFO "em28xx-audio.c: probing for em28x1 "
 			 "non standard usbaudio\n");
 	printk(KERN_INFO "em28xx-audio.c: Copyright (C) 2006 Markus "
@@ -458,6 +470,12 @@ static int em28xx_audio_fini(struct em28xx *dev)
 	if (dev == NULL)
 		return 0;
 
+	if (dev->has_audio_class) {
+		/* This device does not support the extension (in this case
+		   the device is expecting the snd-usb-audio module */
+		return 0;
+	}
+
 	if (dev->adev) {
 		snd_card_free(dev->adev->sndcard);
 		kfree(dev->adev);

+ 4 - 0
drivers/media/video/em28xx/em28xx-cards.c

@@ -157,6 +157,7 @@ struct em28xx_board em28xx_boards[] = {
 		.tda9887_conf = TDA9887_PRESENT,
 		.tuner_type   = TUNER_XC2028,
 		.mts_firmware = 1,
+		.has_dvb        = 1,
 		.decoder      = EM28XX_TVP5150,
 		.input          = { {
 			.type     = EM28XX_VMUX_TELEVISION,
@@ -524,6 +525,9 @@ void em28xx_pre_card_setup(struct em28xx *dev)
 	rc = em28xx_read_reg(dev, EM28XX_R0A_CHIPID);
 	if (rc > 0) {
 		switch (rc) {
+		case CHIP_ID_EM2860:
+			em28xx_info("chip ID is em2860\n");
+			break;
 		case CHIP_ID_EM2883:
 			em28xx_info("chip ID is em2882/em2883\n");
 			dev->wait_after_write = 0;

+ 10 - 0
drivers/media/video/em28xx/em28xx-dvb.c

@@ -382,6 +382,11 @@ static int dvb_init(struct em28xx *dev)
 	int result = 0;
 	struct em28xx_dvb *dvb;
 
+	if (!dev->has_dvb) {
+		/* This device does not support the extension */
+		return 0;
+	}
+
 	dvb = kzalloc(sizeof(struct em28xx_dvb), GFP_KERNEL);
 
 	if (dvb == NULL) {
@@ -444,6 +449,11 @@ out_free:
 
 static int dvb_fini(struct em28xx *dev)
 {
+	if (!dev->has_dvb) {
+		/* This device does not support the extension */
+		return 0;
+	}
+
 	if (dev->dvb) {
 		unregister_dvb(dev->dvb);
 		dev->dvb = NULL;

+ 1 - 0
drivers/media/video/em28xx/em28xx-reg.h

@@ -84,5 +84,6 @@
 
 /* FIXME: Need to be populated with the other chip ID's */
 enum em28xx_chip_id {
+	CHIP_ID_EM2860 = 34,
 	CHIP_ID_EM2883 = 36,
 };

+ 10 - 14
drivers/media/video/em28xx/em28xx-video.c

@@ -1848,32 +1848,28 @@ static DEFINE_MUTEX(em28xx_extension_devlist_lock);
 
 int em28xx_register_extension(struct em28xx_ops *ops)
 {
-	struct em28xx *h, *dev = NULL;
-
-	list_for_each_entry(h, &em28xx_devlist, devlist)
-		dev = h;
+	struct em28xx *dev = NULL;
 
 	mutex_lock(&em28xx_extension_devlist_lock);
 	list_add_tail(&ops->next, &em28xx_extension_devlist);
-	if (dev)
-		ops->init(dev);
-
+	list_for_each_entry(dev, &em28xx_devlist, devlist) {
+		if (dev)
+			ops->init(dev);
+	}
 	printk(KERN_INFO "Em28xx: Initialized (%s) extension\n", ops->name);
 	mutex_unlock(&em28xx_extension_devlist_lock);
-
 	return 0;
 }
 EXPORT_SYMBOL(em28xx_register_extension);
 
 void em28xx_unregister_extension(struct em28xx_ops *ops)
 {
-	struct em28xx *h, *dev = NULL;
-
-	list_for_each_entry(h, &em28xx_devlist, devlist)
-		dev = h;
+	struct em28xx *dev = NULL;
 
-	if (dev)
-		ops->fini(dev);
+	list_for_each_entry(dev, &em28xx_devlist, devlist) {
+		if (dev)
+			ops->fini(dev);
+	}
 
 	mutex_lock(&em28xx_extension_devlist_lock);
 	printk(KERN_INFO "Em28xx: Removed (%s) extension\n", ops->name);

+ 2 - 2
drivers/media/video/pxa_camera.c

@@ -1019,12 +1019,12 @@ static int pxa_camera_probe(struct platform_device *pdev)
 	struct pxa_camera_dev *pcdev;
 	struct resource *res;
 	void __iomem *base;
-	unsigned int irq;
+	int irq;
 	int err = 0;
 
 	res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
 	irq = platform_get_irq(pdev, 0);
-	if (!res || !irq) {
+	if (!res || irq < 0) {
 		err = -ENODEV;
 		goto exit;
 	}

+ 7 - 1
drivers/media/video/saa7134/saa7134-alsa.c

@@ -613,9 +613,15 @@ static int snd_card_saa7134_capture_open(struct snd_pcm_substream * substream)
 	struct snd_pcm_runtime *runtime = substream->runtime;
 	snd_card_saa7134_pcm_t *pcm;
 	snd_card_saa7134_t *saa7134 = snd_pcm_substream_chip(substream);
-	struct saa7134_dev *dev = saa7134->dev;
+	struct saa7134_dev *dev;
 	int amux, err;
 
+	if (!saa7134) {
+		printk(KERN_ERR "BUG: saa7134 can't find device struct."
+				" Can't proceed with open\n");
+		return -ENODEV;
+	}
+	dev = saa7134->dev;
 	mutex_lock(&dev->dmasound.lock);
 
 	dev->dmasound.read_count  = 0;

+ 32 - 24
drivers/media/video/saa7134/saa7134-cards.c

@@ -4114,11 +4114,7 @@ struct saa7134_board saa7134_boards[] = {
 		.radio_type     = UNSET,
 		.tuner_addr	= ADDR_UNSET,
 		.radio_addr	= ADDR_UNSET,
-		 /*
-		    TODO:
 		 .mpeg           = SAA7134_MPEG_DVB,
-		 */
-
 		 .inputs         = {{
 			 .name = name_tv,
 			 .vmux = 1,
@@ -4157,7 +4153,7 @@ struct saa7134_board saa7134_boards[] = {
 		} },
 		.radio = {
 			.name = name_radio,
-			.amux = LINE1,
+			.amux = TV,
 		},
 	},
 	[SAA7134_BOARD_AVERMEDIA_M115] = {
@@ -4167,6 +4163,7 @@ struct saa7134_board saa7134_boards[] = {
 		.radio_type     = UNSET,
 		.tuner_addr	= ADDR_UNSET,
 		.radio_addr	= ADDR_UNSET,
+		.mpeg           = SAA7134_MPEG_DVB,
 		.inputs         = {{
 			.name = name_tv,
 			.vmux = 1,
@@ -5351,22 +5348,21 @@ static int saa7134_xc2028_callback(struct saa7134_dev *dev,
 {
 	switch (command) {
 	case XC2028_TUNER_RESET:
-		saa_andorl(SAA7134_GPIO_GPMODE0 >> 2, 0x06e20000, 0x06e20000);
-		saa_andorl(SAA7134_GPIO_GPSTATUS0 >> 2, 0x06a20000, 0x06a20000);
-		mdelay(250);
-		saa_andorl(SAA7134_GPIO_GPMODE0 >> 2, 0x06e20000, 0);
-		saa_andorl(SAA7134_GPIO_GPSTATUS0 >> 2, 0x06a20000, 0);
-		mdelay(250);
-		saa_andorl(SAA7134_GPIO_GPMODE0 >> 2, 0x06e20000, 0x06e20000);
-		saa_andorl(SAA7134_GPIO_GPSTATUS0 >> 2, 0x06a20000, 0x06a20000);
-		mdelay(250);
-		saa_andorl(SAA7133_ANALOG_IO_SELECT >> 2, 0x02, 0x02);
-		saa_andorl(SAA7134_ANALOG_IN_CTRL1 >> 2, 0x81, 0x81);
-		saa_andorl(SAA7134_AUDIO_CLOCK0 >> 2, 0x03187de7, 0x03187de7);
-		saa_andorl(SAA7134_AUDIO_PLL_CTRL >> 2, 0x03, 0x03);
-		saa_andorl(SAA7134_AUDIO_CLOCKS_PER_FIELD0 >> 2,
-			   0x0001e000, 0x0001e000);
-		return 0;
+		saa_andorl(SAA7134_GPIO_GPSTATUS0 >> 2, 0x00008000, 0x00000000);
+		saa_andorl(SAA7134_GPIO_GPSTATUS0 >> 2, 0x00008000, 0x00008000);
+		switch (dev->board) {
+		case SAA7134_BOARD_AVERMEDIA_CARDBUS_506:
+			saa7134_set_gpio(dev, 23, 0);
+			msleep(10);
+			saa7134_set_gpio(dev, 23, 1);
+		break;
+		case SAA7134_BOARD_AVERMEDIA_A16D:
+			saa7134_set_gpio(dev, 21, 0);
+			msleep(10);
+			saa7134_set_gpio(dev, 21, 1);
+		break;
+		}
+	return 0;
 	}
 	return -EINVAL;
 }
@@ -5553,9 +5549,7 @@ int saa7134_board_init1(struct saa7134_dev *dev)
 		saa_andorl(SAA7134_GPIO_GPSTATUS0 >> 2, 0x08000000, 0x00000000);
 		break;
 	case SAA7134_BOARD_AVERMEDIA_CARDBUS:
-	case SAA7134_BOARD_AVERMEDIA_CARDBUS_506:
 	case SAA7134_BOARD_AVERMEDIA_M115:
-	case SAA7134_BOARD_AVERMEDIA_A16D:
 		/* power-down tuner chip */
 		saa_andorl(SAA7134_GPIO_GPMODE0 >> 2,   0xffffffff, 0);
 		saa_andorl(SAA7134_GPIO_GPSTATUS0 >> 2, 0xffffffff, 0);
@@ -5565,6 +5559,18 @@ int saa7134_board_init1(struct saa7134_dev *dev)
 		saa_andorl(SAA7134_GPIO_GPSTATUS0 >> 2, 0xffffffff, 0xffffffff);
 		msleep(10);
 		break;
+	case SAA7134_BOARD_AVERMEDIA_CARDBUS_506:
+		saa7134_set_gpio(dev, 23, 0);
+		msleep(10);
+		saa7134_set_gpio(dev, 23, 1);
+		break;
+	case SAA7134_BOARD_AVERMEDIA_A16D:
+		saa7134_set_gpio(dev, 21, 0);
+		msleep(10);
+		saa7134_set_gpio(dev, 21, 1);
+		msleep(1);
+		dev->has_remote = SAA7134_REMOTE_GPIO;
+		break;
 	case SAA7134_BOARD_BEHOLD_COLUMBUS_TVFM:
 		/* power-down tuner chip */
 		saa_andorl(SAA7134_GPIO_GPMODE0 >> 2,   0x000A8004, 0x000A8004);
@@ -5615,7 +5621,8 @@ int saa7134_board_init1(struct saa7134_dev *dev)
 		saa_andorl(SAA7134_GPIO_GPMODE0 >> 2,   0x80040100, 0x80040100);
 		saa_andorl(SAA7134_GPIO_GPSTATUS0 >> 2, 0x80040100, 0x00040100);
 		printk("%s: %s: hybrid analog/dvb card\n"
-		       "%s: Sorry, only the analog inputs are supported for now.\n",
+		       "%s: Sorry, only analog s-video and composite input "
+		       "are supported for now.\n",
 			dev->name, card(dev).name, dev->name);
 		break;
 	}
@@ -5675,6 +5682,7 @@ static void saa7134_tuner_setup(struct saa7134_dev *dev)
 
 		switch (dev->board) {
 		case SAA7134_BOARD_AVERMEDIA_A16D:
+		case SAA7134_BOARD_AVERMEDIA_CARDBUS_506:
 			ctl.demod = XC3028_FE_ZARLINK456;
 			break;
 		default:

+ 21 - 22
drivers/media/video/saa7134/saa7134-dvb.c

@@ -153,12 +153,12 @@ static int mt352_aver777_init(struct dvb_frontend* fe)
 	return 0;
 }
 
-static int mt352_aver_a16d_init(struct dvb_frontend *fe)
+static int mt352_avermedia_xc3028_init(struct dvb_frontend *fe)
 {
-	static u8 clock_config []  = { CLOCK_CTL,  0x38, 0x2d };
-	static u8 reset []         = { RESET,      0x80 };
-	static u8 adc_ctl_1_cfg [] = { ADC_CTL_1,  0x40 };
-	static u8 agc_cfg []       = { AGC_TARGET, 0x28, 0xa0 };
+	static u8 clock_config []  = { CLOCK_CTL, 0x38, 0x2d };
+	static u8 reset []         = { RESET, 0x80 };
+	static u8 adc_ctl_1_cfg [] = { ADC_CTL_1, 0x40 };
+	static u8 agc_cfg []       = { AGC_TARGET, 0xe };
 	static u8 capt_range_cfg[] = { CAPT_RANGE, 0x33 };
 
 	mt352_write(fe, clock_config,   sizeof(clock_config));
@@ -167,12 +167,9 @@ static int mt352_aver_a16d_init(struct dvb_frontend *fe)
 	mt352_write(fe, adc_ctl_1_cfg,  sizeof(adc_ctl_1_cfg));
 	mt352_write(fe, agc_cfg,        sizeof(agc_cfg));
 	mt352_write(fe, capt_range_cfg, sizeof(capt_range_cfg));
-
 	return 0;
 }
 
-
-
 static int mt352_pinnacle_tuner_set_params(struct dvb_frontend* fe,
 					   struct dvb_frontend_parameters* params)
 {
@@ -215,14 +212,10 @@ static struct mt352_config avermedia_777 = {
 	.demod_init    = mt352_aver777_init,
 };
 
-static struct mt352_config avermedia_16d = {
-	.demod_address = 0xf,
-	.demod_init    = mt352_aver_a16d_init,
-};
-
-static struct mt352_config avermedia_e506r_mt352_dev = {
+static struct mt352_config avermedia_xc3028_mt352_dev = {
 	.demod_address   = (0x1e >> 1),
 	.no_tuner        = 1,
+	.demod_init      = mt352_avermedia_xc3028_init,
 };
 
 /* ==================================================================
@@ -975,9 +968,10 @@ static int dvb_init(struct saa7134_dev *dev)
 		}
 		break;
 	case SAA7134_BOARD_AVERMEDIA_A16D:
-		dprintk("avertv A16D dvb setup\n");
-		dev->dvb.frontend = dvb_attach(mt352_attach, &avermedia_16d,
-					       &dev->i2c_adap);
+		dprintk("AverMedia A16D dvb setup\n");
+		dev->dvb.frontend = dvb_attach(mt352_attach,
+						&avermedia_xc3028_mt352_dev,
+						&dev->i2c_adap);
 		attach_xc3028 = 1;
 		break;
 	case SAA7134_BOARD_MD7134:
@@ -1091,7 +1085,8 @@ static int dvb_init(struct saa7134_dev *dev)
 					ads_tech_duo_config.tuner_address);
 				goto dettach_frontend;
 			}
-		}
+		} else
+			wprintk("failed to attach tda10046\n");
 		break;
 	case SAA7134_BOARD_TEVION_DVBT_220RF:
 		if (configure_tda827x_fe(dev, &tevion_dvbt220rf_config,
@@ -1260,11 +1255,14 @@ static int dvb_init(struct saa7134_dev *dev)
 			goto dettach_frontend;
 		break;
 	case SAA7134_BOARD_AVERMEDIA_CARDBUS_506:
+		dprintk("AverMedia E506R dvb setup\n");
+		saa7134_set_gpio(dev, 25, 0);
+		msleep(10);
+		saa7134_set_gpio(dev, 25, 1);
 		dev->dvb.frontend = dvb_attach(mt352_attach,
-					       &avermedia_e506r_mt352_dev,
-					       &dev->i2c_adap);
+						&avermedia_xc3028_mt352_dev,
+						&dev->i2c_adap);
 		attach_xc3028 = 1;
-		break;
 	case SAA7134_BOARD_MD7134_BRIDGE_2:
 		dev->dvb.frontend = dvb_attach(tda10086_attach,
 						&sd1878_4m, &dev->i2c_adap);
@@ -1338,7 +1336,8 @@ static int dvb_init(struct saa7134_dev *dev)
 	return ret;
 
 dettach_frontend:
-	dvb_frontend_detach(dev->dvb.frontend);
+	if (dev->dvb.frontend)
+		dvb_frontend_detach(dev->dvb.frontend);
 	dev->dvb.frontend = NULL;
 
 	return -1;

+ 16 - 21
drivers/media/video/saa7134/saa7134-empress.c

@@ -110,9 +110,10 @@ static int ts_release(struct inode *inode, struct file *file)
 {
 	struct saa7134_dev *dev = file->private_data;
 
+	mutex_lock(&dev->empress_tsq.vb_lock);
+
 	videobuf_stop(&dev->empress_tsq);
 	videobuf_mmap_free(&dev->empress_tsq);
-	dev->empress_users--;
 
 	/* stop the encoder */
 	ts_reset_encoder(dev);
@@ -121,6 +122,10 @@ static int ts_release(struct inode *inode, struct file *file)
 	saa_writeb(SAA7134_AUDIO_MUTE_CTRL,
 		saa_readb(SAA7134_AUDIO_MUTE_CTRL) | (1 << 6));
 
+	dev->empress_users--;
+
+	mutex_unlock(&dev->empress_tsq.vb_lock);
+
 	return 0;
 }
 
@@ -218,8 +223,7 @@ static int empress_enum_fmt_cap(struct file *file, void  *priv,
 static int empress_g_fmt_cap(struct file *file, void *priv,
 				struct v4l2_format *f)
 {
-	struct saa7134_fh *fh = priv;
-	struct saa7134_dev *dev = fh->dev;
+	struct saa7134_dev *dev = file->private_data;
 
 	saa7134_i2c_call_clients(dev, VIDIOC_G_FMT, f);
 
@@ -232,8 +236,7 @@ static int empress_g_fmt_cap(struct file *file, void *priv,
 static int empress_s_fmt_cap(struct file *file, void *priv,
 				struct v4l2_format *f)
 {
-	struct saa7134_fh *fh = priv;
-	struct saa7134_dev *dev = fh->dev;
+	struct saa7134_dev *dev = file->private_data;
 
 	saa7134_i2c_call_clients(dev, VIDIOC_S_FMT, f);
 
@@ -247,8 +250,7 @@ static int empress_s_fmt_cap(struct file *file, void *priv,
 static int empress_reqbufs(struct file *file, void *priv,
 					struct v4l2_requestbuffers *p)
 {
-	struct saa7134_fh *fh = priv;
-	struct saa7134_dev *dev = fh->dev;
+	struct saa7134_dev *dev = file->private_data;
 
 	return videobuf_reqbufs(&dev->empress_tsq, p);
 }
@@ -256,24 +258,21 @@ static int empress_reqbufs(struct file *file, void *priv,
 static int empress_querybuf(struct file *file, void *priv,
 					struct v4l2_buffer *b)
 {
-	struct saa7134_fh *fh = priv;
-	struct saa7134_dev *dev = fh->dev;
+	struct saa7134_dev *dev = file->private_data;
 
 	return videobuf_querybuf(&dev->empress_tsq, b);
 }
 
 static int empress_qbuf(struct file *file, void *priv, struct v4l2_buffer *b)
 {
-	struct saa7134_fh *fh = priv;
-	struct saa7134_dev *dev = fh->dev;
+	struct saa7134_dev *dev = file->private_data;
 
 	return videobuf_qbuf(&dev->empress_tsq, b);
 }
 
 static int empress_dqbuf(struct file *file, void *priv, struct v4l2_buffer *b)
 {
-	struct saa7134_fh *fh = priv;
-	struct saa7134_dev *dev = fh->dev;
+	struct saa7134_dev *dev = file->private_data;
 
 	return videobuf_dqbuf(&dev->empress_tsq, b,
 				file->f_flags & O_NONBLOCK);
@@ -282,8 +281,7 @@ static int empress_dqbuf(struct file *file, void *priv, struct v4l2_buffer *b)
 static int empress_streamon(struct file *file, void *priv,
 					enum v4l2_buf_type type)
 {
-	struct saa7134_fh *fh = priv;
-	struct saa7134_dev *dev = fh->dev;
+	struct saa7134_dev *dev = file->private_data;
 
 	return videobuf_streamon(&dev->empress_tsq);
 }
@@ -291,8 +289,7 @@ static int empress_streamon(struct file *file, void *priv,
 static int empress_streamoff(struct file *file, void *priv,
 					enum v4l2_buf_type type)
 {
-	struct saa7134_fh *fh = priv;
-	struct saa7134_dev *dev = fh->dev;
+	struct saa7134_dev *dev = file->private_data;
 
 	return videobuf_streamoff(&dev->empress_tsq);
 }
@@ -300,8 +297,7 @@ static int empress_streamoff(struct file *file, void *priv,
 static int empress_s_ext_ctrls(struct file *file, void *priv,
 			       struct v4l2_ext_controls *ctrls)
 {
-	struct saa7134_fh *fh = priv;
-	struct saa7134_dev *dev = fh->dev;
+	struct saa7134_dev *dev = file->private_data;
 
 	/* count == 0 is abused in saa6752hs.c, so that special
 		case is handled here explicitly. */
@@ -320,8 +316,7 @@ static int empress_s_ext_ctrls(struct file *file, void *priv,
 static int empress_g_ext_ctrls(struct file *file, void *priv,
 			       struct v4l2_ext_controls *ctrls)
 {
-	struct saa7134_fh *fh = priv;
-	struct saa7134_dev *dev = fh->dev;
+	struct saa7134_dev *dev = file->private_data;
 
 	if (ctrls->ctrl_class != V4L2_CTRL_CLASS_MPEG)
 		return -EINVAL;

+ 9 - 0
drivers/media/video/saa7134/saa7134-input.c

@@ -323,6 +323,15 @@ int saa7134_input_init1(struct saa7134_dev *dev)
 		saa_setb(SAA7134_GPIO_GPMODE1, 0x1);
 		saa_setb(SAA7134_GPIO_GPSTATUS1, 0x1);
 		break;
+	case SAA7134_BOARD_AVERMEDIA_A16D:
+		ir_codes     = ir_codes_avermedia_a16d;
+		mask_keycode = 0x02F200;
+		mask_keydown = 0x000400;
+		polling      = 50; /* ms */
+		/* Without this we won't receive key up events */
+		saa_setb(SAA7134_GPIO_GPMODE1, 0x1);
+		saa_setb(SAA7134_GPIO_GPSTATUS1, 0x1);
+		break;
 	case SAA7134_BOARD_KWORLD_TERMINATOR:
 		ir_codes     = ir_codes_pixelview;
 		mask_keycode = 0x00001f;

+ 0 - 16
drivers/media/video/soc_camera.c

@@ -763,15 +763,6 @@ static struct device_driver ic_drv = {
 	.owner	= THIS_MODULE,
 };
 
-/*
- * Image capture host - this is a host device, not a bus device, so,
- * no bus reference, no probing.
- */
-static struct class soc_camera_host_class = {
-	.owner		= THIS_MODULE,
-	.name		= "camera_host",
-};
-
 static void dummy_release(struct device *dev)
 {
 }
@@ -801,7 +792,6 @@ int soc_camera_host_register(struct soc_camera_host *ici)
 
 	/* Number might be equal to the platform device ID */
 	sprintf(ici->dev.bus_id, "camera_host%d", ici->nr);
-	ici->dev.class = &soc_camera_host_class;
 
 	mutex_lock(&list_lock);
 	list_for_each_entry(ix, &hosts, list) {
@@ -1003,14 +993,9 @@ static int __init soc_camera_init(void)
 	ret = driver_register(&ic_drv);
 	if (ret)
 		goto edrvr;
-	ret = class_register(&soc_camera_host_class);
-	if (ret)
-		goto eclr;
 
 	return 0;
 
-eclr:
-	driver_unregister(&ic_drv);
 edrvr:
 	bus_unregister(&soc_camera_bus_type);
 	return ret;
@@ -1018,7 +1003,6 @@ edrvr:
 
 static void __exit soc_camera_exit(void)
 {
-	class_unregister(&soc_camera_host_class);
 	driver_unregister(&ic_drv);
 	bus_unregister(&soc_camera_bus_type);
 }

+ 68 - 177
drivers/media/video/videodev.c

@@ -51,12 +51,51 @@
 #define VIDEO_NUM_DEVICES	256
 #define VIDEO_NAME              "video4linux"
 
+struct std_descr {
+	v4l2_std_id std;
+	const char *descr;
+};
+
+static const struct std_descr standards[] = {
+	{ V4L2_STD_NTSC, 	"NTSC"      },
+	{ V4L2_STD_NTSC_M, 	"NTSC-M"    },
+	{ V4L2_STD_NTSC_M_JP, 	"NTSC-M-JP" },
+	{ V4L2_STD_NTSC_M_KR,	"NTSC-M-KR" },
+	{ V4L2_STD_NTSC_443, 	"NTSC-443"  },
+	{ V4L2_STD_PAL, 	"PAL"       },
+	{ V4L2_STD_PAL_BG, 	"PAL-BG"    },
+	{ V4L2_STD_PAL_B, 	"PAL-B"     },
+	{ V4L2_STD_PAL_B1, 	"PAL-B1"    },
+	{ V4L2_STD_PAL_G, 	"PAL-G"     },
+	{ V4L2_STD_PAL_H, 	"PAL-H"     },
+	{ V4L2_STD_PAL_I, 	"PAL-I"     },
+	{ V4L2_STD_PAL_DK, 	"PAL-DK"    },
+	{ V4L2_STD_PAL_D, 	"PAL-D"     },
+	{ V4L2_STD_PAL_D1, 	"PAL-D1"    },
+	{ V4L2_STD_PAL_K, 	"PAL-K"     },
+	{ V4L2_STD_PAL_M, 	"PAL-M"     },
+	{ V4L2_STD_PAL_N, 	"PAL-N"     },
+	{ V4L2_STD_PAL_Nc, 	"PAL-Nc"    },
+	{ V4L2_STD_PAL_60, 	"PAL-60"    },
+	{ V4L2_STD_SECAM, 	"SECAM"     },
+	{ V4L2_STD_SECAM_B, 	"SECAM-B"   },
+	{ V4L2_STD_SECAM_G, 	"SECAM-G"   },
+	{ V4L2_STD_SECAM_H, 	"SECAM-H"   },
+	{ V4L2_STD_SECAM_DK, 	"SECAM-DK"  },
+	{ V4L2_STD_SECAM_D, 	"SECAM-D"   },
+	{ V4L2_STD_SECAM_K, 	"SECAM-K"   },
+	{ V4L2_STD_SECAM_K1, 	"SECAM-K1"  },
+	{ V4L2_STD_SECAM_L, 	"SECAM-L"   },
+	{ V4L2_STD_SECAM_LC, 	"SECAM-Lc"  },
+	{ 0, 			"Unknown"   }
+};
+
 /* video4linux standard ID conversion to standard name
  */
-char *v4l2_norm_to_name(v4l2_std_id id)
+const char *v4l2_norm_to_name(v4l2_std_id id)
 {
-	char *name;
 	u32 myid = id;
+	int i;
 
 	/* HACK: ppc32 architecture doesn't have __ucmpdi2 function to handle
 	   64 bit comparations. So, on that architecture, with some gcc
@@ -64,110 +103,17 @@ char *v4l2_norm_to_name(v4l2_std_id id)
 	 */
 	BUG_ON(myid != id);
 
-	switch (myid) {
-	case V4L2_STD_PAL:
-		name = "PAL";
-		break;
-	case V4L2_STD_PAL_BG:
-		name = "PAL-BG";
-		break;
-	case V4L2_STD_PAL_DK:
-		name = "PAL-DK";
-		break;
-	case V4L2_STD_PAL_B:
-		name = "PAL-B";
-		break;
-	case V4L2_STD_PAL_B1:
-		name = "PAL-B1";
-		break;
-	case V4L2_STD_PAL_G:
-		name = "PAL-G";
-		break;
-	case V4L2_STD_PAL_H:
-		name = "PAL-H";
-		break;
-	case V4L2_STD_PAL_I:
-		name = "PAL-I";
-		break;
-	case V4L2_STD_PAL_D:
-		name = "PAL-D";
-		break;
-	case V4L2_STD_PAL_D1:
-		name = "PAL-D1";
-		break;
-	case V4L2_STD_PAL_K:
-		name = "PAL-K";
-		break;
-	case V4L2_STD_PAL_M:
-		name = "PAL-M";
-		break;
-	case V4L2_STD_PAL_N:
-		name = "PAL-N";
-		break;
-	case V4L2_STD_PAL_Nc:
-		name = "PAL-Nc";
-		break;
-	case V4L2_STD_PAL_60:
-		name = "PAL-60";
-		break;
-	case V4L2_STD_NTSC:
-		name = "NTSC";
-		break;
-	case V4L2_STD_NTSC_M:
-		name = "NTSC-M";
-		break;
-	case V4L2_STD_NTSC_M_JP:
-		name = "NTSC-M-JP";
-		break;
-	case V4L2_STD_NTSC_443:
-		name = "NTSC-443";
-		break;
-	case V4L2_STD_NTSC_M_KR:
-		name = "NTSC-M-KR";
-		break;
-	case V4L2_STD_SECAM:
-		name = "SECAM";
-		break;
-	case V4L2_STD_SECAM_DK:
-		name = "SECAM-DK";
-		break;
-	case V4L2_STD_SECAM_B:
-		name = "SECAM-B";
-		break;
-	case V4L2_STD_SECAM_D:
-		name = "SECAM-D";
-		break;
-	case V4L2_STD_SECAM_G:
-		name = "SECAM-G";
-		break;
-	case V4L2_STD_SECAM_H:
-		name = "SECAM-H";
-		break;
-	case V4L2_STD_SECAM_K:
-		name = "SECAM-K";
-		break;
-	case V4L2_STD_SECAM_K1:
-		name = "SECAM-K1";
-		break;
-	case V4L2_STD_SECAM_L:
-		name = "SECAM-L";
-		break;
-	case V4L2_STD_SECAM_LC:
-		name = "SECAM-LC";
-		break;
-	default:
-		name = "Unknown";
-		break;
-	}
-
-	return name;
+	for (i = 0; standards[i].std; i++)
+		if (myid == standards[i].std)
+			break;
+	return standards[i].descr;
 }
 EXPORT_SYMBOL(v4l2_norm_to_name);
 
 /* Fill in the fields of a v4l2_standard structure according to the
    'id' and 'transmission' parameters.  Returns negative on error.  */
 int v4l2_video_std_construct(struct v4l2_standard *vs,
-			     int id, char *name)
+			     int id, const char *name)
 {
 	u32 index = vs->index;
 
@@ -1218,95 +1164,40 @@ static int __video_do_ioctl(struct inode *inode, struct file *file,
 	case VIDIOC_ENUMSTD:
 	{
 		struct v4l2_standard *p = arg;
-		v4l2_std_id id = vfd->tvnorms,curr_id=0;
-		unsigned int index = p->index,i;
-
-		if (index<0) {
-			ret=-EINVAL;
-			break;
-		}
-
-		/* Return norm array on a canonical way */
-		for (i=0;i<= index && id; i++) {
-			if ( (id & V4L2_STD_PAL) == V4L2_STD_PAL) {
-				curr_id = V4L2_STD_PAL;
-			} else if ( (id & V4L2_STD_PAL_BG) == V4L2_STD_PAL_BG) {
-				curr_id = V4L2_STD_PAL_BG;
-			} else if ( (id & V4L2_STD_PAL_DK) == V4L2_STD_PAL_DK) {
-				curr_id = V4L2_STD_PAL_DK;
-			} else if ( (id & V4L2_STD_PAL_B) == V4L2_STD_PAL_B) {
-				curr_id = V4L2_STD_PAL_B;
-			} else if ( (id & V4L2_STD_PAL_B1) == V4L2_STD_PAL_B1) {
-				curr_id = V4L2_STD_PAL_B1;
-			} else if ( (id & V4L2_STD_PAL_G) == V4L2_STD_PAL_G) {
-				curr_id = V4L2_STD_PAL_G;
-			} else if ( (id & V4L2_STD_PAL_H) == V4L2_STD_PAL_H) {
-				curr_id = V4L2_STD_PAL_H;
-			} else if ( (id & V4L2_STD_PAL_I) == V4L2_STD_PAL_I) {
-				curr_id = V4L2_STD_PAL_I;
-			} else if ( (id & V4L2_STD_PAL_D) == V4L2_STD_PAL_D) {
-				curr_id = V4L2_STD_PAL_D;
-			} else if ( (id & V4L2_STD_PAL_D1) == V4L2_STD_PAL_D1) {
-				curr_id = V4L2_STD_PAL_D1;
-			} else if ( (id & V4L2_STD_PAL_K) == V4L2_STD_PAL_K) {
-				curr_id = V4L2_STD_PAL_K;
-			} else if ( (id & V4L2_STD_PAL_M) == V4L2_STD_PAL_M) {
-				curr_id = V4L2_STD_PAL_M;
-			} else if ( (id & V4L2_STD_PAL_N) == V4L2_STD_PAL_N) {
-				curr_id = V4L2_STD_PAL_N;
-			} else if ( (id & V4L2_STD_PAL_Nc) == V4L2_STD_PAL_Nc) {
-				curr_id = V4L2_STD_PAL_Nc;
-			} else if ( (id & V4L2_STD_PAL_60) == V4L2_STD_PAL_60) {
-				curr_id = V4L2_STD_PAL_60;
-			} else if ( (id & V4L2_STD_NTSC) == V4L2_STD_NTSC) {
-				curr_id = V4L2_STD_NTSC;
-			} else if ( (id & V4L2_STD_NTSC_M) == V4L2_STD_NTSC_M) {
-				curr_id = V4L2_STD_NTSC_M;
-			} else if ( (id & V4L2_STD_NTSC_M_JP) == V4L2_STD_NTSC_M_JP) {
-				curr_id = V4L2_STD_NTSC_M_JP;
-			} else if ( (id & V4L2_STD_NTSC_443) == V4L2_STD_NTSC_443) {
-				curr_id = V4L2_STD_NTSC_443;
-			} else if ( (id & V4L2_STD_NTSC_M_KR) == V4L2_STD_NTSC_M_KR) {
-				curr_id = V4L2_STD_NTSC_M_KR;
-			} else if ( (id & V4L2_STD_SECAM) == V4L2_STD_SECAM) {
-				curr_id = V4L2_STD_SECAM;
-			} else if ( (id & V4L2_STD_SECAM_DK) == V4L2_STD_SECAM_DK) {
-				curr_id = V4L2_STD_SECAM_DK;
-			} else if ( (id & V4L2_STD_SECAM_B) == V4L2_STD_SECAM_B) {
-				curr_id = V4L2_STD_SECAM_B;
-			} else if ( (id & V4L2_STD_SECAM_D) == V4L2_STD_SECAM_D) {
-				curr_id = V4L2_STD_SECAM_D;
-			} else if ( (id & V4L2_STD_SECAM_G) == V4L2_STD_SECAM_G) {
-				curr_id = V4L2_STD_SECAM_G;
-			} else if ( (id & V4L2_STD_SECAM_H) == V4L2_STD_SECAM_H) {
-				curr_id = V4L2_STD_SECAM_H;
-			} else if ( (id & V4L2_STD_SECAM_K) == V4L2_STD_SECAM_K) {
-				curr_id = V4L2_STD_SECAM_K;
-			} else if ( (id & V4L2_STD_SECAM_K1) == V4L2_STD_SECAM_K1) {
-				curr_id = V4L2_STD_SECAM_K1;
-			} else if ( (id & V4L2_STD_SECAM_L) == V4L2_STD_SECAM_L) {
-				curr_id = V4L2_STD_SECAM_L;
-			} else if ( (id & V4L2_STD_SECAM_LC) == V4L2_STD_SECAM_LC) {
-				curr_id = V4L2_STD_SECAM_LC;
-			} else {
+		v4l2_std_id id = vfd->tvnorms, curr_id = 0;
+		unsigned int index = p->index, i, j = 0;
+		const char *descr = "";
+
+		/* Return norm array in a canonical way */
+		for (i = 0; i <= index && id; i++) {
+			/* last std value in the standards array is 0, so this
+			   while always ends there since (id & 0) == 0. */
+			while ((id & standards[j].std) != standards[j].std)
+				j++;
+			curr_id = standards[j].std;
+			descr = standards[j].descr;
+			j++;
+			if (curr_id == 0)
 				break;
-			}
-			id &= ~curr_id;
+			if (curr_id != V4L2_STD_PAL &&
+			    curr_id != V4L2_STD_SECAM &&
+			    curr_id != V4L2_STD_NTSC)
+				id &= ~curr_id;
 		}
-		if (i<=index)
+		if (i <= index)
 			return -EINVAL;
 
-		v4l2_video_std_construct(p, curr_id,v4l2_norm_to_name(curr_id));
+		v4l2_video_std_construct(p, curr_id, descr);
 		p->index = index;
 
-		dbgarg (cmd, "index=%d, id=%Ld, name=%s, fps=%d/%d, "
+		dbgarg(cmd, "index=%d, id=%Ld, name=%s, fps=%d/%d, "
 				"framelines=%d\n", p->index,
 				(unsigned long long)p->id, p->name,
 				p->frameperiod.numerator,
 				p->frameperiod.denominator,
 				p->framelines);
 
-		ret=0;
+		ret = 0;
 		break;
 	}
 	case VIDIOC_G_STD:

+ 4 - 3
drivers/media/video/vivi.c

@@ -327,13 +327,14 @@ static void vivi_fillbuff(struct vivi_dev *dev, struct vivi_buffer *buf)
 	int hmax  = buf->vb.height;
 	int wmax  = buf->vb.width;
 	struct timeval ts;
-	char *tmpbuf = kmalloc(wmax * 2, GFP_ATOMIC);
+	char *tmpbuf;
 	void *vbuf = videobuf_to_vmalloc(&buf->vb);
 
-	if (!tmpbuf)
+	if (!vbuf)
 		return;
 
-	if (!vbuf)
+	tmpbuf = kmalloc(wmax * 2, GFP_ATOMIC);
+	if (!tmpbuf)
 		return;
 
 	for (h = 0; h < hmax; h++) {

+ 5 - 1
include/media/cx25840.h

@@ -32,12 +32,16 @@ enum cx25840_video_input {
 	CX25840_COMPOSITE7,
 	CX25840_COMPOSITE8,
 
-	/* S-Video inputs consist of one luma input (In1-In4) ORed with one
+	/* S-Video inputs consist of one luma input (In1-In8) ORed with one
 	   chroma input (In5-In8) */
 	CX25840_SVIDEO_LUMA1 = 0x10,
 	CX25840_SVIDEO_LUMA2 = 0x20,
 	CX25840_SVIDEO_LUMA3 = 0x30,
 	CX25840_SVIDEO_LUMA4 = 0x40,
+	CX25840_SVIDEO_LUMA5 = 0x50,
+	CX25840_SVIDEO_LUMA6 = 0x60,
+	CX25840_SVIDEO_LUMA7 = 0x70,
+	CX25840_SVIDEO_LUMA8 = 0x80,
 	CX25840_SVIDEO_CHROMA4 = 0x400,
 	CX25840_SVIDEO_CHROMA5 = 0x500,
 	CX25840_SVIDEO_CHROMA6 = 0x600,

+ 1 - 0
include/media/ir-common.h

@@ -146,6 +146,7 @@ extern IR_KEYTAB_TYPE ir_codes_behold_columbus[IR_KEYTAB_SIZE];
 extern IR_KEYTAB_TYPE ir_codes_pinnacle_pctv_hd[IR_KEYTAB_SIZE];
 extern IR_KEYTAB_TYPE ir_codes_genius_tvgo_a11mce[IR_KEYTAB_SIZE];
 extern IR_KEYTAB_TYPE ir_codes_powercolor_real_angel[IR_KEYTAB_SIZE];
+extern IR_KEYTAB_TYPE ir_codes_avermedia_a16d[IR_KEYTAB_SIZE];
 
 #endif
 

+ 2 - 2
include/media/v4l2-dev.h

@@ -40,9 +40,9 @@
 #define VFL_TYPE_VTX		3
 
 /*  Video standard functions  */
-extern char *v4l2_norm_to_name(v4l2_std_id id);
+extern const char *v4l2_norm_to_name(v4l2_std_id id);
 extern int v4l2_video_std_construct(struct v4l2_standard *vs,
-				    int id, char *name);
+				    int id, const char *name);
 /* Prints the ioctl in a human-readable format */
 extern void v4l_printk_ioctl(unsigned int cmd);