Exemplo n.º 1
0
static int lme2510_pid_filter_ctrl(struct dvb_usb_adapter *adap, int onoff)
{
	struct dvb_usb_device *d = adap_to_d(adap);
	struct lme2510_state *st = adap_to_priv(adap);
	static u8 clear_pid_reg[] = LME_ALL_PIDS;
	static u8 rbuf[1];
	int ret = 0;

	deb_info(1, "PID Clearing Filter");

	mutex_lock(&d->i2c_mutex);

	if (!onoff) {
		ret |= lme2510_usb_talk(d, clear_pid_reg,
			sizeof(clear_pid_reg), rbuf, sizeof(rbuf));
		st->pid_off = true;
	} else
		st->pid_off = false;

	st->pid_size = 0;

	mutex_unlock(&d->i2c_mutex);

	return 0;
}
Exemplo n.º 2
0
static int lme2510_streaming_ctrl(struct dvb_frontend *fe, int onoff)
{
	struct dvb_usb_adapter *adap = fe_to_adap(fe);
	struct dvb_usb_device *d = adap_to_d(adap);
	struct lme2510_state *st = adap_to_priv(adap);
	static u8 clear_reg_3[] = LME_ALL_PIDS;
	static u8 rbuf[1];
	int ret = 0, rlen = sizeof(rbuf);

	deb_info(1, "STM  (%02x)", onoff);

	/* Streaming is started by FE_HAS_LOCK */
	if (onoff == 1)
		st->stream_on = 1;
	else {
		deb_info(1, "STM Steam Off");
		/* mutex is here only to avoid collision with I2C */
		mutex_lock(&d->i2c_mutex);

		ret = lme2510_usb_talk(d, clear_reg_3,
				sizeof(clear_reg_3), rbuf, rlen);
		st->stream_on = 0;
		st->i2c_talk_onoff = 1;

		mutex_unlock(&d->i2c_mutex);
	}

	return (ret < 0) ? -ENODEV : 0;
}
Exemplo n.º 3
0
static int lme2510_int_read(struct dvb_usb_adapter *adap)
{
	struct dvb_usb_device *d = adap_to_d(adap);
	struct lme2510_state *lme_int = adap_to_priv(adap);

	lme_int->lme_urb = usb_alloc_urb(0, GFP_ATOMIC);

	if (lme_int->lme_urb == NULL)
			return -ENOMEM;

	lme_int->buffer = usb_alloc_coherent(d->udev, 128, GFP_ATOMIC,
					&lme_int->lme_urb->transfer_dma);

	if (lme_int->buffer == NULL)
			return -ENOMEM;

	usb_fill_int_urb(lme_int->lme_urb,
				d->udev,
				usb_rcvintpipe(d->udev, 0xa),
				lme_int->buffer,
				128,
				lme2510_int_response,
				adap,
				8);

	lme_int->lme_urb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;

	usb_submit_urb(lme_int->lme_urb, GFP_ATOMIC);
	info("INT Interrupt Service Started");

	return 0;
}
Exemplo n.º 4
0
static int az6007_ci_init(struct dvb_usb_adapter *adap)
{
	struct dvb_usb_device *d = adap_to_d(adap);
	struct az6007_device_state *state = adap_to_priv(adap);
	int ret;

	pr_debug("%s()\n", __func__);

	mutex_init(&state->ca_mutex);
	state->ca.owner			= THIS_MODULE;
	state->ca.read_attribute_mem	= az6007_ci_read_attribute_mem;
	state->ca.write_attribute_mem	= az6007_ci_write_attribute_mem;
	state->ca.read_cam_control	= az6007_ci_read_cam_control;
	state->ca.write_cam_control	= az6007_ci_write_cam_control;
	state->ca.slot_reset		= az6007_ci_slot_reset;
	state->ca.slot_shutdown		= az6007_ci_slot_shutdown;
	state->ca.slot_ts_enable	= az6007_ci_slot_ts_enable;
	state->ca.poll_slot_status	= az6007_ci_poll_slot_status;
	state->ca.data			= d;

	ret = dvb_ca_en50221_init(&adap->dvb_adap,
				  &state->ca,
				  0, /* flags */
				  1);/* n_slots */
	if (ret != 0) {
		pr_err("Cannot initialize CI: Error %d.\n", ret);
		memset(&state->ca, 0, sizeof(state->ca));
		return ret;
	}

	pr_debug("CI initialized.\n");

	return 0;
}
Exemplo n.º 5
0
static int mxl111sf_attach_tuner(struct dvb_usb_adapter *adap)
{
	struct mxl111sf_state *state = adap_to_priv(adap);
#ifdef CONFIG_MEDIA_CONTROLLER_DVB
	struct media_device *mdev = dvb_get_media_controller(&adap->dvb_adap);
	int ret;
#endif
	int i;

	pr_debug("%s()\n", __func__);

	for (i = 0; i < state->num_frontends; i++) {
		if (dvb_attach(mxl111sf_tuner_attach, adap->fe[i], state,
				&mxl_tuner_config) == NULL)
			return -EIO;
		adap->fe[i]->ops.read_signal_strength = adap->fe[i]->ops.tuner_ops.get_rf_strength;
	}

#ifdef CONFIG_MEDIA_CONTROLLER_DVB
	state->tuner.function = MEDIA_ENT_F_TUNER;
	state->tuner.name = "mxl111sf tuner";
	state->tuner_pads[TUNER_PAD_RF_INPUT].flags = MEDIA_PAD_FL_SINK;
	state->tuner_pads[TUNER_PAD_IF_OUTPUT].flags = MEDIA_PAD_FL_SOURCE;

	ret = media_entity_pads_init(&state->tuner,
				     TUNER_NUM_PADS, state->tuner_pads);
	if (ret)
		return ret;

	ret = media_device_register_entity(mdev, &state->tuner);
	if (ret)
		return ret;
#endif
	return 0;
}
Exemplo n.º 6
0
static int rtl28xxu_frontend_attach(struct dvb_usb_adapter *adap)
{
	struct rtl28xxu_dev *dev = adap_to_priv(adap);

	if (dev->chip_id == CHIP_ID_RTL2831U)
		return rtl2831u_frontend_attach(adap);
	else
		return rtl2832u_frontend_attach(adap);
}
Exemplo n.º 7
0
static void lme2510_update_stats(struct dvb_usb_adapter *adap)
{
	struct lme2510_state *st = adap_to_priv(adap);
	struct dvb_frontend *fe = adap->fe[0];
	struct dtv_frontend_properties *c;
	u32 s_tmp = 0, c_tmp = 0;

	if (!fe)
		return;

	c = &fe->dtv_property_cache;

	c->block_count.len = 1;
	c->block_count.stat[0].scale = FE_SCALE_NOT_AVAILABLE;
	c->block_error.len = 1;
	c->block_error.stat[0].scale = FE_SCALE_NOT_AVAILABLE;
	c->post_bit_count.len = 1;
	c->post_bit_count.stat[0].scale = FE_SCALE_NOT_AVAILABLE;
	c->post_bit_error.len = 1;
	c->post_bit_error.stat[0].scale = FE_SCALE_NOT_AVAILABLE;

	if (st->i2c_talk_onoff) {
		c->strength.len = 1;
		c->strength.stat[0].scale = FE_SCALE_NOT_AVAILABLE;
		c->cnr.len = 1;
		c->cnr.stat[0].scale = FE_SCALE_NOT_AVAILABLE;
		return;
	}

	switch (st->tuner_config) {
	case TUNER_LG:
		s_tmp = reg_to_16bits(0xff - st->signal_level);
		c_tmp = reg_to_16bits(0xff - st->signal_sn);
		break;
	case TUNER_S7395:
	case TUNER_S0194:
		s_tmp = 0xffff - (((st->signal_level * 2) << 8) * 5 / 4);
		c_tmp = reg_to_16bits((0xff - st->signal_sn - 0xa1) * 3);
		break;
	case TUNER_RS2000:
		s_tmp = reg_to_16bits(st->signal_level);
		c_tmp = reg_to_16bits(st->signal_sn);
	}

	c->strength.len = 1;
	c->strength.stat[0].scale = FE_SCALE_RELATIVE;
	c->strength.stat[0].uvalue = (u64)s_tmp;

	c->cnr.len = 1;
	c->cnr.stat[0].scale = FE_SCALE_RELATIVE;
	c->cnr.stat[0].uvalue = (u64)c_tmp;
}
Exemplo n.º 8
0
static int az6007_read_mac_addr(struct dvb_usb_adapter *adap, u8 mac[6])
{
	struct dvb_usb_device *d = adap_to_d(adap);
	struct az6007_device_state *st = adap_to_priv(adap);
	int ret;

	ret = az6007_read(d, AZ6007_READ_DATA, 6, 0, st->data, 6);
	memcpy(mac, st->data, 6);

	if (ret > 0)
		pr_debug("%s: mac is %pM\n", __func__, mac);

	return ret;
}
Exemplo n.º 9
0
static int rtl28xxu_pid_filter_ctrl(struct dvb_usb_adapter *adap, int onoff)
{
	struct rtl28xxu_dev *dev = adap_to_priv(adap);

	if (dev->chip_id == CHIP_ID_RTL2831U) {
		struct rtl2830_platform_data *pdata = &dev->rtl2830_platform_data;

		return pdata->pid_filter_ctrl(adap->fe[0], onoff);
	} else {
		struct rtl2832_platform_data *pdata = &dev->rtl2832_platform_data;

		return pdata->pid_filter_ctrl(adap->fe[0], onoff);
	}
}
Exemplo n.º 10
0
static int lme_name(struct dvb_usb_adapter *adap)
{
	struct dvb_usb_device *d = adap_to_d(adap);
	struct lme2510_state *st = adap_to_priv(adap);
	const char *desc = d->name;
	char *fe_name[] = {"", " LG TDQY-P001F", " SHARP:BS2F7HZ7395",
				" SHARP:BS2F7HZ0194", " RS2000"};
	char *name = adap->fe[0]->ops.info.name;

	strlcpy(name, desc, 128);
	strlcat(name, fe_name[st->tuner_config], 128);

	return 0;
}
Exemplo n.º 11
0
static int dm04_lme2510_tuner(struct dvb_usb_adapter *adap)
{
	struct dvb_usb_device *d = adap_to_d(adap);
	struct lme2510_state *st = adap_to_priv(adap);
	static const char * const tun_msg[] = {"", "TDA8263", "IX2505V", "DVB_PLL_OPERA", "RS2000"};
	int ret = 0;

	switch (st->tuner_config) {
	case TUNER_LG:
		if (dvb_attach(tda826x_attach, adap->fe[0], 0x60,
			&d->i2c_adap, 1))
			ret = st->tuner_config;
		break;
	case TUNER_S7395:
		if (dvb_attach(ix2505v_attach , adap->fe[0], &lme_tuner,
			&d->i2c_adap))
			ret = st->tuner_config;
		break;
	case TUNER_S0194:
		if (dvb_attach(dvb_pll_attach , adap->fe[0], 0x60,
			&d->i2c_adap, DVB_PLL_OPERA1))
			ret = st->tuner_config;
		break;
	case TUNER_RS2000:
		if (dvb_attach(ts2020_attach, adap->fe[0],
			       &ts2020_config, &d->i2c_adap))
			ret = st->tuner_config;
		break;
	default:
		break;
	}

	if (ret) {
		info("TUN Found %s tuner", tun_msg[ret]);
	} else {
		info("TUN No tuner found");
		return -ENODEV;
	}

	/* Start the Interrupt*/
	ret = lme2510_int_read(adap);
	if (ret < 0) {
		info("INT Unable to start Interrupt Service");
		return -ENODEV;
	}

	return ret;
}
Exemplo n.º 12
0
static int mxl111sf_attach_tuner(struct dvb_usb_adapter *adap)
{
	struct mxl111sf_state *state = adap_to_priv(adap);
	int i;

	deb_adv("%s()\n", __func__);

	for (i = 0; i < state->num_frontends; i++) {
		if (dvb_attach(mxl111sf_tuner_attach, adap->fe[i], state,
				&mxl_tuner_config) == NULL)
			return -EIO;
		adap->fe[i]->ops.read_signal_strength = adap->fe[i]->ops.tuner_ops.get_rf_strength;
	}

	return 0;
}
Exemplo n.º 13
0
static int az6007_frontend_attach(struct dvb_usb_adapter *adap)
{
	struct az6007_device_state *st = adap_to_priv(adap);
	struct dvb_usb_device *d = adap_to_d(adap);

	pr_debug("attaching demod drxk\n");

	adap->fe[0] = dvb_attach(drxk_attach, &terratec_h7_drxk,
				 &d->i2c_adap);
	if (!adap->fe[0])
		return -EINVAL;

	adap->fe[0]->sec_priv = adap;
	st->gate_ctrl = adap->fe[0]->ops.i2c_gate_ctrl;
	adap->fe[0]->ops.i2c_gate_ctrl = drxk_gate_ctrl;

	az6007_ci_init(adap);

	return 0;
}
Exemplo n.º 14
0
static int lme2510_int_read(struct dvb_usb_adapter *adap)
{
	struct dvb_usb_device *d = adap_to_d(adap);
	struct lme2510_state *lme_int = adap_to_priv(adap);
	struct usb_host_endpoint *ep;

	lme_int->lme_urb = usb_alloc_urb(0, GFP_ATOMIC);

	if (lme_int->lme_urb == NULL)
			return -ENOMEM;

	lme_int->buffer = usb_alloc_coherent(d->udev, 128, GFP_ATOMIC,
					&lme_int->lme_urb->transfer_dma);

	if (lme_int->buffer == NULL)
			return -ENOMEM;

	usb_fill_int_urb(lme_int->lme_urb,
				d->udev,
				usb_rcvintpipe(d->udev, 0xa),
				lme_int->buffer,
				128,
				lme2510_int_response,
				adap,
				8);

	/* Quirk of pipe reporting PIPE_BULK but behaves as interrupt */
	ep = usb_pipe_endpoint(d->udev, lme_int->lme_urb->pipe);

	if (usb_endpoint_type(&ep->desc) == USB_ENDPOINT_XFER_BULK)
		lme_int->lme_urb->pipe = usb_rcvbulkpipe(d->udev, 0xa),

	lme_int->lme_urb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP;

	usb_submit_urb(lme_int->lme_urb, GFP_ATOMIC);
	info("INT Interrupt Service Started");

	return 0;
}
Exemplo n.º 15
0
static int af9015_af9013_frontend_attach(struct dvb_usb_adapter *adap)
{
    int ret;
    struct af9015_state *state = adap_to_priv(adap);

    if (adap->id == 0) {
        state->af9013_config[0].ts_mode = AF9013_TS_USB;
        memcpy(state->af9013_config[0].api_version, "\x0\x1\x9\x0", 4);
        state->af9013_config[0].gpio[0] = AF9013_GPIO_HI;
        state->af9013_config[0].gpio[3] = AF9013_GPIO_TUNER_ON;
    } else if (adap->id == 1) {
        state->af9013_config[1].ts_mode = AF9013_TS_SERIAL;
        memcpy(state->af9013_config[1].api_version, "\x0\x1\x9\x0", 4);
        state->af9013_config[1].gpio[0] = AF9013_GPIO_TUNER_ON;
        state->af9013_config[1].gpio[1] = AF9013_GPIO_LO;

        /* copy firmware to 2nd demodulator */
        if (state->dual_mode) {
            ret = af9015_copy_firmware(adap_to_d(adap));
            if (ret) {
                dev_err(&adap_to_d(adap)->udev->dev,
                        "%s: firmware copy to 2nd " \
                        "frontend failed, will " \
                        "disable it\n", KBUILD_MODNAME);
                state->dual_mode = 0;
                return -ENODEV;
            }
        } else {
            return -ENODEV;
        }
    }

    /* attach demodulator */
    adap->fe[0] = dvb_attach(af9013_attach,
                             &state->af9013_config[adap->id], &adap_to_d(adap)->i2c_adap);

    /*
     * AF9015 firmware does not like if it gets interrupted by I2C adapter
     * request on some critical phases. During normal operation I2C adapter
     * is used only 2nd demodulator and tuner on dual tuner devices.
     * Override demodulator callbacks and use mutex for limit access to
     * those "critical" paths to keep AF9015 happy.
     */
    if (adap->fe[0]) {
        state->set_frontend[adap->id] =
            adap->fe[0]->ops.set_frontend;
        adap->fe[0]->ops.set_frontend =
            af9015_af9013_set_frontend;

        state->read_status[adap->id] =
            adap->fe[0]->ops.read_status;
        adap->fe[0]->ops.read_status =
            af9015_af9013_read_status;

        state->init[adap->id] = adap->fe[0]->ops.init;
        adap->fe[0]->ops.init = af9015_af9013_init;

        state->sleep[adap->id] = adap->fe[0]->ops.sleep;
        adap->fe[0]->ops.sleep = af9015_af9013_sleep;
    }

    return adap->fe[0] == NULL ? -ENODEV : 0;
}
Exemplo n.º 16
0
static void lme2510_int_response(struct urb *lme_urb)
{
	struct dvb_usb_adapter *adap = lme_urb->context;
	struct lme2510_state *st = adap_to_priv(adap);
	static u8 *ibuf, *rbuf;
	int i = 0, offset;
	u32 key;

	switch (lme_urb->status) {
	case 0:
	case -ETIMEDOUT:
		break;
	case -ECONNRESET:
	case -ENOENT:
	case -ESHUTDOWN:
		return;
	default:
		info("Error %x", lme_urb->status);
		break;
	}

	rbuf = (u8 *) lme_urb->transfer_buffer;

	offset = ((lme_urb->actual_length/8) > 4)
			? 4 : (lme_urb->actual_length/8) ;

	for (i = 0; i < offset; ++i) {
		ibuf = (u8 *)&rbuf[i*8];
		deb_info(5, "INT O/S C =%02x C/O=%02x Type =%02x%02x",
		offset, i, ibuf[0], ibuf[1]);

		switch (ibuf[0]) {
		case 0xaa:
			debug_data_snipet(1, "INT Remote data snipet", ibuf);
			if ((ibuf[4] + ibuf[5]) == 0xff) {
				key = RC_SCANCODE_NECX((ibuf[2] ^ 0xff) << 8 |
						       (ibuf[3] > 0) ? (ibuf[3] ^ 0xff) : 0,
						       ibuf[5]);
				deb_info(1, "INT Key =%08x", key);
				if (adap_to_d(adap)->rc_dev != NULL)
					rc_keydown(adap_to_d(adap)->rc_dev,
						   RC_TYPE_NEC, key, 0);
			}
			break;
		case 0xbb:
			switch (st->tuner_config) {
			case TUNER_LG:
				if (ibuf[2] > 0)
					st->signal_lock = ibuf[2];
				st->signal_level = ibuf[4];
				st->signal_sn = ibuf[3];
				st->time_key = ibuf[7];
				break;
			case TUNER_S7395:
			case TUNER_S0194:
				/* Tweak for earlier firmware*/
				if (ibuf[1] == 0x03) {
					if (ibuf[2] > 1)
						st->signal_lock = ibuf[2];
					st->signal_level = ibuf[3];
					st->signal_sn = ibuf[4];
				} else {
					st->signal_level = ibuf[4];
					st->signal_sn = ibuf[5];
					st->signal_lock =
						(st->signal_lock & 0xf7) +
						((ibuf[2] & 0x01) << 0x03);
				}
				break;
			case TUNER_RS2000:
				if (ibuf[2] & 0x1)
					st->signal_lock = 0xff;
				else
					st->signal_lock = 0x00;
				st->signal_level = ibuf[5];
				st->signal_sn = ibuf[4];
				st->time_key = ibuf[7];
			default:
				break;
			}
			debug_data_snipet(5, "INT Remote data snipet in", ibuf);
		break;
		case 0xcc:
			debug_data_snipet(1, "INT Control data snipet", ibuf);
			break;
		default:
			debug_data_snipet(1, "INT Unknown data snipet", ibuf);
		break;
		}
	}

	usb_submit_urb(lme_urb, GFP_ATOMIC);

	/* interrupt urb is due every 48 msecs while streaming
	 *	add 12msecs for system lag */
	st->int_urb_due = jiffies + msecs_to_jiffies(60);
}
Exemplo n.º 17
0
static int rtl2832u_tuner_attach(struct dvb_usb_adapter *adap)
{
	int ret;
	struct dvb_usb_device *d = adap_to_d(adap);
	struct rtl28xxu_dev *dev = d_to_priv(d);
	struct dvb_frontend *fe = NULL;
	struct i2c_board_info info;
	struct i2c_client *client;
	struct v4l2_subdev *subdev = NULL;
	struct platform_device *pdev;
	struct rtl2832_sdr_platform_data pdata;

	dev_dbg(&d->intf->dev, "\n");

	memset(&info, 0, sizeof(struct i2c_board_info));
	memset(&pdata, 0, sizeof(pdata));

	switch (dev->tuner) {
	case TUNER_RTL2832_FC0012:
		fe = dvb_attach(fc0012_attach, adap->fe[0],
			dev->demod_i2c_adapter, &rtl2832u_fc0012_config);

		/* since fc0012 includs reading the signal strength delegate
		 * that to the tuner driver */
		adap->fe[0]->ops.read_signal_strength =
				adap->fe[0]->ops.tuner_ops.get_rf_strength;
		break;
	case TUNER_RTL2832_FC0013:
		fe = dvb_attach(fc0013_attach, adap->fe[0],
			dev->demod_i2c_adapter, 0xc6>>1, 0, FC_XTAL_28_8_MHZ);

		/* fc0013 also supports signal strength reading */
		adap->fe[0]->ops.read_signal_strength =
				adap->fe[0]->ops.tuner_ops.get_rf_strength;
		break;
	case TUNER_RTL2832_E4000: {
			struct e4000_config e4000_config = {
				.fe = adap->fe[0],
				.clock = 28800000,
			};

			strlcpy(info.type, "e4000", I2C_NAME_SIZE);
			info.addr = 0x64;
			info.platform_data = &e4000_config;

			request_module(info.type);
			client = i2c_new_device(dev->demod_i2c_adapter, &info);
			if (client == NULL || client->dev.driver == NULL)
				break;

			if (!try_module_get(client->dev.driver->owner)) {
				i2c_unregister_device(client);
				break;
			}

			dev->i2c_client_tuner = client;
			subdev = i2c_get_clientdata(client);
		}
		break;
	case TUNER_RTL2832_FC2580:
		fe = dvb_attach(fc2580_attach, adap->fe[0],
				dev->demod_i2c_adapter,
				&rtl2832u_fc2580_config);
		break;
	case TUNER_RTL2832_TUA9001:
		/* enable GPIO1 and GPIO4 as output */
		ret = rtl28xxu_wr_reg_mask(d, SYS_GPIO_DIR, 0x00, 0x12);
		if (ret)
			goto err;

		ret = rtl28xxu_wr_reg_mask(d, SYS_GPIO_OUT_EN, 0x12, 0x12);
		if (ret)
			goto err;

		fe = dvb_attach(tua9001_attach, adap->fe[0],
				dev->demod_i2c_adapter,
				&rtl2832u_tua9001_config);
		break;
	case TUNER_RTL2832_R820T:
		fe = dvb_attach(r820t_attach, adap->fe[0],
				dev->demod_i2c_adapter,
				&rtl2832u_r820t_config);

		/* Use tuner to get the signal strength */
		adap->fe[0]->ops.read_signal_strength =
				adap->fe[0]->ops.tuner_ops.get_rf_strength;
		break;
	case TUNER_RTL2832_R828D:
		fe = dvb_attach(r820t_attach, adap->fe[0],
				dev->demod_i2c_adapter,
				&rtl2832u_r828d_config);
		adap->fe[0]->ops.read_signal_strength =
				adap->fe[0]->ops.tuner_ops.get_rf_strength;

		if (adap->fe[1]) {
			fe = dvb_attach(r820t_attach, adap->fe[1],
					dev->demod_i2c_adapter,
					&rtl2832u_r828d_config);
			adap->fe[1]->ops.read_signal_strength =
					adap->fe[1]->ops.tuner_ops.get_rf_strength;
		}
		break;
	default:
		dev_err(&d->intf->dev, "unknown tuner %d\n", dev->tuner);
	}
	if (fe == NULL && dev->i2c_client_tuner == NULL) {
		ret = -ENODEV;
		goto err;
	}

	/* register SDR */
	switch (dev->tuner) {
	case TUNER_RTL2832_FC0012:
	case TUNER_RTL2832_FC0013:
	case TUNER_RTL2832_E4000:
	case TUNER_RTL2832_R820T:
	case TUNER_RTL2832_R828D:
		pdata.clk = dev->rtl2832_platform_data.clk;
		pdata.tuner = dev->tuner;
		pdata.i2c_client = dev->i2c_client_demod;
		pdata.bulk_read = dev->rtl2832_platform_data.bulk_read;
		pdata.bulk_write = dev->rtl2832_platform_data.bulk_write;
		pdata.update_bits = dev->rtl2832_platform_data.update_bits;
		pdata.dvb_frontend = adap->fe[0];
		pdata.dvb_usb_device = d;
		pdata.v4l2_subdev = subdev;

		request_module("%s", "rtl2832_sdr");
		pdev = platform_device_register_data(&d->intf->dev,
						     "rtl2832_sdr",
						     PLATFORM_DEVID_AUTO,
						     &pdata, sizeof(pdata));
		if (pdev == NULL || pdev->dev.driver == NULL)
			break;
		dev->platform_device_sdr = pdev;
		break;
	default:
		dev_dbg(&d->intf->dev, "no SDR for tuner=%d\n", dev->tuner);
	}

	return 0;
err:
	dev_dbg(&d->intf->dev, "failed=%d\n", ret);
	return ret;
}

static int rtl28xxu_tuner_attach(struct dvb_usb_adapter *adap)
{
	struct rtl28xxu_dev *dev = adap_to_priv(adap);

	if (dev->chip_id == CHIP_ID_RTL2831U)
		return rtl2831u_tuner_attach(adap);
	else
		return rtl2832u_tuner_attach(adap);
}

static int rtl28xxu_tuner_detach(struct dvb_usb_adapter *adap)
{
	struct dvb_usb_device *d = adap_to_d(adap);
	struct rtl28xxu_dev *dev = d_to_priv(d);
	struct i2c_client *client;
	struct platform_device *pdev;

	dev_dbg(&d->intf->dev, "\n");

	/* remove platform SDR */
	pdev = dev->platform_device_sdr;
	if (pdev)
		platform_device_unregister(pdev);

	/* remove I2C tuner */
	client = dev->i2c_client_tuner;
	if (client) {
		module_put(client->dev.driver->owner);
		i2c_unregister_device(client);
	}

	return 0;
}

static int rtl28xxu_init(struct dvb_usb_device *d)
{
	int ret;
	u8 val;

	dev_dbg(&d->intf->dev, "\n");

	/* init USB endpoints */
	ret = rtl28xxu_rd_reg(d, USB_SYSCTL_0, &val);
	if (ret)
		goto err;

	/* enable DMA and Full Packet Mode*/
	val |= 0x09;
	ret = rtl28xxu_wr_reg(d, USB_SYSCTL_0, val);
	if (ret)
		goto err;

	/* set EPA maximum packet size to 0x0200 */
	ret = rtl28xxu_wr_regs(d, USB_EPA_MAXPKT, "\x00\x02\x00\x00", 4);
	if (ret)
		goto err;

	/* change EPA FIFO length */
	ret = rtl28xxu_wr_regs(d, USB_EPA_FIFO_CFG, "\x14\x00\x00\x00", 4);
	if (ret)
		goto err;

	return ret;
err:
	dev_dbg(&d->intf->dev, "failed=%d\n", ret);
	return ret;
}
Exemplo n.º 18
0
static void lme2510_int_response(struct urb *lme_urb)
{
	struct dvb_usb_adapter *adap = lme_urb->context;
	struct lme2510_state *st = adap_to_priv(adap);
	u8 *ibuf, *rbuf;
	int i = 0, offset;
	u32 key;
	u8 signal_lock = 0;

	switch (lme_urb->status) {
	case 0:
	case -ETIMEDOUT:
		break;
	case -ECONNRESET:
	case -ENOENT:
	case -ESHUTDOWN:
		return;
	default:
		info("Error %x", lme_urb->status);
		break;
	}

	rbuf = (u8 *) lme_urb->transfer_buffer;

	offset = ((lme_urb->actual_length/8) > 4)
			? 4 : (lme_urb->actual_length/8) ;

	for (i = 0; i < offset; ++i) {
		ibuf = (u8 *)&rbuf[i*8];
		deb_info(5, "INT O/S C =%02x C/O=%02x Type =%02x%02x",
		offset, i, ibuf[0], ibuf[1]);

		switch (ibuf[0]) {
		case 0xaa:
			debug_data_snipet(1, "INT Remote data snipet", ibuf);
			if (!adap_to_d(adap)->rc_dev)
				break;

			key = RC_SCANCODE_NEC32(ibuf[2] << 24 |
						ibuf[3] << 16 |
						ibuf[4] << 8  |
						ibuf[5]);

			deb_info(1, "INT Key = 0x%08x", key);
			rc_keydown(adap_to_d(adap)->rc_dev, RC_TYPE_NEC32, key,
									0);
			break;
		case 0xbb:
			switch (st->tuner_config) {
			case TUNER_LG:
				signal_lock = ibuf[2] & BIT(5);
				st->signal_level = ibuf[4];
				st->signal_sn = ibuf[3];
				st->time_key = ibuf[7];
				break;
			case TUNER_S7395:
			case TUNER_S0194:
				/* Tweak for earlier firmware*/
				if (ibuf[1] == 0x03) {
					signal_lock = ibuf[2] & BIT(4);
					st->signal_level = ibuf[3];
					st->signal_sn = ibuf[4];
				} else {
					st->signal_level = ibuf[4];
					st->signal_sn = ibuf[5];
				}
				break;
			case TUNER_RS2000:
				signal_lock = ibuf[2] & 0xee;
				st->signal_level = ibuf[5];
				st->signal_sn = ibuf[4];
				st->time_key = ibuf[7];
			default:
				break;
			}

			/* Interrupt will also throw just BIT 0 as lock */
			signal_lock |= ibuf[2] & BIT(0);

			if (!signal_lock)
				st->lock_status &= ~FE_HAS_LOCK;

			lme2510_update_stats(adap);

			debug_data_snipet(5, "INT Remote data snipet in", ibuf);
		break;
		case 0xcc:
			debug_data_snipet(1, "INT Control data snipet", ibuf);
			break;
		default:
			debug_data_snipet(1, "INT Unknown data snipet", ibuf);
		break;
		}
	}

	usb_submit_urb(lme_urb, GFP_ATOMIC);

	/* Interrupt urb is due every 48 msecs while streaming the buffer
	 * stores up to 4 periods if missed. Allow 200 msec for next interrupt.
	 */
	st->int_urb_due = jiffies + msecs_to_jiffies(200);
}