drivers/media/dvb-frontends/si2168.c

Source file repositories/reference/linux-study-clean/drivers/media/dvb-frontends/si2168.c

File Facts

System
Linux kernel
Corpus path
drivers/media/dvb-frontends/si2168.c
Extension
.c
Size
19702 bytes
Lines
817
Domain
Driver Families
Bucket
drivers/media
Inferred role
Driver Families: implementation source
Status
source implementation candidate

Why This File Exists

Repeatable hardware-adapter layer. Deep compatibility for every driver is out of scope; this atlas records patterns, probe lifecycles, bus glue, IRQ/DMA usage, and links back to core abstractions.

Dependency Surface

Detected Declarations

Annotated Snippet

if (ret < 0) {
			goto err_mutex_unlock;
		} else if (ret != cmd->wlen) {
			ret = -EREMOTEIO;
			goto err_mutex_unlock;
		}
	}

	if (cmd->rlen) {
		/* wait cmd execution terminate */
		#define TIMEOUT 140
		timeout = jiffies + msecs_to_jiffies(TIMEOUT);
		while (!time_after(jiffies, timeout)) {
			ret = i2c_master_recv(client, cmd->args, cmd->rlen);
			if (ret < 0) {
				goto err_mutex_unlock;
			} else if (ret != cmd->rlen) {
				ret = -EREMOTEIO;
				goto err_mutex_unlock;
			}

			/* firmware ready? */
			if ((cmd->args[0] >> 7) & 0x01)
				break;

			usleep_range(2500, 3500);
		}

		dev_dbg(&client->dev, "cmd execution took %d ms\n",
				jiffies_to_msecs(jiffies) -
				(jiffies_to_msecs(timeout) - TIMEOUT));

		/* error bit set? */
		if ((cmd->args[0] >> 6) & 0x01) {
			ret = -EREMOTEIO;
			goto err_mutex_unlock;
		}

		if (!((cmd->args[0] >> 7) & 0x01)) {
			ret = -ETIMEDOUT;
			goto err_mutex_unlock;
		}
	}

	mutex_unlock(&dev->i2c_mutex);
	return 0;
err_mutex_unlock:
	mutex_unlock(&dev->i2c_mutex);
	dev_dbg(&client->dev, "failed=%d\n", ret);
	return ret;
}

static int si2168_ts_bus_ctrl(struct dvb_frontend *fe, int acquire)
{
	struct i2c_client *client = fe->demodulator_priv;
	struct si2168_dev *dev = i2c_get_clientdata(client);
	struct si2168_cmd cmd;
	int ret = 0;

	dev_dbg(&client->dev, "%s acquire: %d\n", __func__, acquire);

	/* set manual value */
	if (dev->ts_mode & SI2168_TS_CLK_MANUAL) {
		cmd_init(&cmd, "\x14\x00\x0d\x10\xe8\x03", 6, 4);
		ret = si2168_cmd_execute(client, &cmd);
		if (ret)
			return ret;
	}
	/* set TS_MODE property */
	cmd_init(&cmd, "\x14\x00\x01\x10\x10\x00", 6, 4);
	if (dev->ts_mode & SI2168_TS_CLK_MANUAL)
		cmd.args[4] = SI2168_TS_CLK_MANUAL;
	if (acquire)
		cmd.args[4] |= dev->ts_mode;
	else
		cmd.args[4] |= SI2168_TS_TRISTATE;
	if (dev->ts_clock_gapped)
		cmd.args[4] |= 0x40;
	ret = si2168_cmd_execute(client, &cmd);

	return ret;
}

static int si2168_read_status(struct dvb_frontend *fe, enum fe_status *status)
{
	struct i2c_client *client = fe->demodulator_priv;
	struct si2168_dev *dev = i2c_get_clientdata(client);
	struct dtv_frontend_properties *c = &fe->dtv_property_cache;
	int ret, i;
	unsigned int utmp, utmp1, utmp2;

Annotation

Implementation Notes