PATCH 8/44 multiproto + backward compatibility [CX22700]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 




--- v4l-dvb/linux/drivers/media/dvb/frontends/cx22700.c	2006-06-30 19:59:10.000000000 +0400
+++ mp-bc1/linux/drivers/media/dvb/frontends/cx22700.c	2006-07-23 11:37:11.000000000 +0400
@@ -122,7 +122,8 @@ static int cx22700_set_inversion (struct
 	}
 }
 
-static int cx22700_set_tps (struct cx22700_state *state, struct dvb_ofdm_parameters *p)
+static int cx22700_set_tps_compat(struct cx22700_state *state,
+				  struct dvb_ofdm_parameters *p)
 {
 	static const u8 qam_tab [4] = { 0, 1, 0, 2 };
 	static const u8 fec_tab [6] = { 0, 1, 2, 0, 3, 4 };
@@ -185,7 +186,177 @@ static int cx22700_set_tps (struct cx227
 	return 0;
 }
 
-static int cx22700_get_tps (struct cx22700_state* state, struct dvb_ofdm_parameters *p)
+static int cx22700_set_tps(struct cx22700_state *state, struct dvbt_params *p)
+{
+	u8 val = 0;
+
+	dprintk ("%s\n", __FUNCTION__);
+
+	if (p->code_rate_HP < DVBFE_FEC_1_2 || p->code_rate_HP > DVBFE_FEC_7_8)
+		return -EINVAL;
+
+	if (p->code_rate_LP < DVBFE_FEC_1_2 || p->code_rate_LP > DVBFE_FEC_7_8)
+		return -EINVAL;
+
+	if (p->code_rate_HP == DVBFE_FEC_4_5 || p->code_rate_LP == DVBFE_FEC_4_5)
+		return -EINVAL;
+
+	if (p->guard_interval < DVBFE_GUARD_INTERVAL_1_32 ||
+	    p->guard_interval > DVBFE_GUARD_INTERVAL_1_4)
+		return -EINVAL;
+
+	if (p->transmission_mode != DVBFE_TRANSMISSION_MODE_2K &&
+	    p->transmission_mode != DVBFE_TRANSMISSION_MODE_8K)
+		return -EINVAL;
+
+	if (p->constellation != DVBFE_MOD_QPSK &&
+	    p->constellation != DVBFE_MOD_QAM16 &&
+	    p->constellation != DVBFE_MOD_QAM64)
+		return -EINVAL;
+
+	if (p->bandwidth < DVBFE_BANDWIDTH_8_MHZ &&
+	    p->bandwidth > DVBFE_BANDWIDTH_6_MHZ)
+		return -EINVAL;
+
+	if (p->bandwidth == DVBFE_BANDWIDTH_7_MHZ)
+		cx22700_writereg (state, 0x09, cx22700_readreg (state, 0x09 | 0x10));
+	else
+		cx22700_writereg (state, 0x09, cx22700_readreg (state, 0x09 & ~0x10));
+
+	switch (p->constellation) {
+	case DVBFE_MOD_QPSK:
+		val = 0;
+		break;
+	case DVBFE_MOD_QAM16:
+		val = 1;
+		break;
+	case DVBFE_MOD_QAM64:
+		val = 2;
+		break;
+	default:
+		break;
+	}
+
+	switch (p->hierarchy) {
+	case DVBFE_HIERARCHY_OFF:
+		val |= 0;
+		break;
+	case DVBFE_HIERARCHY_ON:
+		switch(p->alpha) {
+		case DVBFE_ALPHA_1:
+			val |= 1;
+			break;
+		case DVBFE_ALPHA_2:
+			val |= 2;
+			break;
+		case DVBFE_ALPHA_4:
+			val |= 3;
+			break;
+		default:
+			break;
+		}
+		break;
+	case DVBFE_HIERARCHY_AUTO:
+		val |= 4;
+		break;
+	default:
+		break;
+	}
+
+	cx22700_writereg (state, 0x04, val);
+
+	switch (p->code_rate_HP) {
+	case DVBFE_FEC_1_2:
+		val = (0 << 3);
+		break;
+	case DVBFE_FEC_2_3:
+		val = (1 << 3);
+		break;
+	case DVBFE_FEC_3_4:
+		val = (2 << 3);
+		break;
+	case DVBFE_FEC_5_6:
+		val = (3 << 3);
+		break;
+	case DVBFE_FEC_7_8:
+		val = (4 << 3);
+		break;
+	case DVBFE_FEC_NONE:
+	case DVBFE_FEC_AUTO:
+		break;
+	default:
+		break;
+	}
+
+	switch (p->code_rate_LP) {
+	case DVBFE_FEC_1_2:
+		val |= 0;
+		break;
+	case DVBFE_FEC_2_3:
+		val |= 1;
+		break;
+	case DVBFE_FEC_3_4:
+		val |= 2;
+		break;
+	case DVBFE_FEC_5_6:
+		val |= 3;
+		break;
+	case DVBFE_FEC_7_8:
+		val |= 4;
+		break;
+	case DVBFE_FEC_NONE:
+	case DVBFE_FEC_AUTO:
+		break;
+	default:
+		break;
+	}
+
+	cx22700_writereg (state, 0x05, val);
+
+	switch (p->guard_interval) {
+	case DVBFE_GUARD_INTERVAL_1_32:
+		val = (0 << 2);
+		break;
+	case DVBFE_GUARD_INTERVAL_1_16:
+		val = (1 << 2);
+		break;
+	case DVBFE_GUARD_INTERVAL_1_8:
+		val = (2 << 2);
+		break;
+	case DVBFE_GUARD_INTERVAL_1_4:
+		val = (3 << 2);
+		break;
+	case DVBFE_GUARD_INTERVAL_AUTO:
+		val = (4 << 2);
+		break;
+	default:
+		break;
+	}
+
+	switch (p->transmission_mode) {
+	case DVBFE_TRANSMISSION_MODE_2K:
+		val |= 0;
+		break;
+	case DVBFE_TRANSMISSION_MODE_8K:
+		val |= 1;
+		break;
+	case DVBFE_TRANSMISSION_MODE_AUTO:
+		val |= 2;
+		break;
+	default:
+		break;
+	}
+
+	cx22700_writereg (state, 0x06, val);
+
+	cx22700_writereg (state, 0x08, 0x04 | 0x02);  /* use user tps parameters */
+	cx22700_writereg (state, 0x08, 0x04);         /* restart aquisition */
+
+	return 0;
+}
+
+static int cx22700_get_tps_compat (struct cx22700_state* state,
+				   struct dvb_ofdm_parameters *p)
 {
 	static const fe_modulation_t qam_tab [3] = { QPSK, QAM_16, QAM_64 };
 	static const fe_code_rate_t fec_tab [5] = { FEC_1_2, FEC_2_3, FEC_3_4,
@@ -229,6 +400,51 @@ static int cx22700_get_tps (struct cx227
 	return 0;
 }
 
+static int cx22700_get_tps(struct cx22700_state* state,
+			   struct dvbt_params *p)
+{
+	static const fe_modulation_t qam_tab [3] = { QPSK, QAM_16, QAM_64 };
+	static const fe_code_rate_t fec_tab [5] = { FEC_1_2, FEC_2_3, FEC_3_4,
+						    FEC_5_6, FEC_7_8 };
+	u8 val;
+
+	dprintk ("%s\n", __FUNCTION__);
+
+	if (!(cx22700_readreg(state, 0x07) & 0x20))  /*  tps valid? */
+		return -EAGAIN;
+
+	val = cx22700_readreg (state, 0x01);
+
+	if ((val & 0x7) > 4)
+		p->hierarchy = DVBFE_HIERARCHY_AUTO;
+	else
+		p->hierarchy = (val & 0x7);
+
+	if (((val >> 3) & 0x3) > 2)
+		p->constellation = DVBFE_MOD_QAMAUTO;
+	else
+		p->constellation = qam_tab[(val >> 3) & 0x3];
+
+	val = cx22700_readreg (state, 0x02);
+
+	if (((val >> 3) & 0x07) > 4)
+		p->code_rate_HP = DVBFE_FEC_AUTO;
+	else
+		p->code_rate_HP = fec_tab[(val >> 3) & 0x07];
+
+	if ((val & 0x07) > 4)
+		p->code_rate_LP = DVBFE_FEC_AUTO;
+	else
+		p->code_rate_LP = fec_tab[val & 0x07];
+
+	val = cx22700_readreg (state, 0x03);
+
+	p->guard_interval = ((val >> 6) & 0x3);
+	p->transmission_mode = ((val >> 5) & 0x1);
+
+	return 0;
+}
+
 static int cx22700_init (struct dvb_frontend* fe)
 
 {	struct cx22700_state* state = fe->demodulator_priv;
@@ -326,13 +542,14 @@ static int cx22700_set_frontend(struct d
 	cx22700_writereg (state, 0x00, 0x02); /* XXX CHECKME: soft reset*/
 	cx22700_writereg (state, 0x00, 0x00);
 
-	if (fe->ops.tuner_ops.set_params) {
-		fe->ops.tuner_ops.set_params(fe, p);
-		if (fe->ops.i2c_gate_ctrl) fe->ops.i2c_gate_ctrl(fe, 0);
+	if (fe->ops.tuner_ops.set_params_compat) {
+		fe->ops.tuner_ops.set_params_compat(fe, p);
+		if (fe->ops.i2c_gate_ctrl)
+			fe->ops.i2c_gate_ctrl(fe, 0);
 	}
 
 	cx22700_set_inversion (state, p->inversion);
-	cx22700_set_tps (state, &p->u.ofdm);
+	cx22700_set_tps_compat(state, &p->u.ofdm);
 	cx22700_writereg (state, 0x37, 0x01);  /* PAL loop filter off */
 	cx22700_writereg (state, 0x00, 0x01);  /* restart acquire */
 
@@ -345,7 +562,7 @@ static int cx22700_get_frontend(struct d
 	u8 reg09 = cx22700_readreg (state, 0x09);
 
 	p->inversion = reg09 & 0x1 ? INVERSION_ON : INVERSION_OFF;
-	return cx22700_get_tps (state, &p->u.ofdm);
+	return cx22700_get_tps_compat(state, &p->u.ofdm);
 }
 
 static int cx22700_i2c_gate_ctrl(struct dvb_frontend* fe, int enable)
@@ -401,6 +618,71 @@ error:
 	return NULL;
 }
 
+static int cx22700_set_params(struct dvb_frontend* fe,
+			      struct dvbfe_params *p)
+{
+	struct cx22700_state* state = fe->demodulator_priv;
+
+	cx22700_writereg (state, 0x00, 0x02); /* XXX CHECKME: soft reset*/
+	cx22700_writereg (state, 0x00, 0x00);
+
+	if (fe->ops.tuner_ops.set_params) {
+		fe->ops.tuner_ops.set_params(fe, p);
+		if (fe->ops.i2c_gate_ctrl)
+			fe->ops.i2c_gate_ctrl(fe, 0);
+	}
+
+	cx22700_set_inversion(state, p->inversion);
+	cx22700_set_tps(state, &p->delsys.dvbt);
+	cx22700_writereg(state, 0x37, 0x01);  /* PAL loop filter off */
+	cx22700_writereg(state, 0x00, 0x01);  /* restart acquire */
+
+	return 0;
+}
+
+static int cx22700_get_params(struct dvb_frontend* fe,
+			      struct dvbfe_params *p)
+{
+	struct cx22700_state* state = fe->demodulator_priv;
+	u8 reg09 = cx22700_readreg (state, 0x09);
+
+	p->inversion = reg09 & 0x1 ? INVERSION_ON : INVERSION_OFF;
+	return cx22700_get_tps(state, &p->delsys.dvbt);
+}
+
+static struct dvbfe_info dvbt_info	= {
+	.name				= "Conexant CX22700 DVB-T",
+	.delivery			= DVBFE_DELSYS_DVBT,
+	.delsys				= {
+		.dvbt.modulation	= DVBFE_MOD_OFDM,
+		.dvbt.stream_priority	= DVBFE_STREAM_PRIORITY_HP |
+					  DVBFE_STREAM_PRIORITY_LP
+	},
+
+	.frequency_min			= 470000000,
+	.frequency_max			= 860000000,
+	.frequency_step			= 166667,
+};
+
+static int cx22700_get_info(struct dvb_frontend *fe, struct dvbfe_info *fe_info)
+{
+	memcpy(fe_info, &dvbt_info, sizeof (dvbt_info));
+
+	return 0;
+}
+
+static int cx22700_get_delsys(struct dvb_frontend *fe, enum dvbfe_delsys *fe_delsys)
+{
+	*fe_delsys = DVBFE_DELSYS_DVBT;
+
+	return 0;
+}
+
+static enum dvbfe_algo cx22700_get_algo(struct dvb_frontend *fe)
+{
+	return DVBFE_ALGO_RECOVERY;
+}
+
 static struct dvb_frontend_ops cx22700_ops = {
 
 	.info = {
@@ -429,6 +711,12 @@ static struct dvb_frontend_ops cx22700_o
 	.read_signal_strength = cx22700_read_signal_strength,
 	.read_snr = cx22700_read_snr,
 	.read_ucblocks = cx22700_read_ucblocks,
+
+	.set_params		= cx22700_set_params,
+	.get_params		= cx22700_get_params,
+	.get_info		= cx22700_get_info,
+	.get_delsys		= cx22700_get_delsys,
+	.get_frontend_algo	= cx22700_get_algo,
 };
 
 module_param(debug, int, 0644);

_______________________________________________

linux-dvb@xxxxxxxxxxx
http://www.linuxtv.org/cgi-bin/mailman/listinfo/linux-dvb

[Index of Archives]     [Linux Media]     [Video 4 Linux]     [Asterisk]     [Samba]     [Xorg]     [Xfree86]     [Linux USB]

  Powered by Linux