Beispiel #1
0
static int qup_update_state(struct qup_i2c_dev *dev, unsigned state)
{
    if (qup_i2c_poll_state(dev, 0) != 0)
        return -EIO;
    writel(state, dev->base + QUP_STATE);
    if (qup_i2c_poll_state(dev, state) != 0)
        return -EIO;
    return 0;
}
Beispiel #2
0
static int
qup_update_state(struct qup_i2c_dev *dev, uint32_t state)
{
	if (qup_i2c_poll_state(dev, 0) != 0)
		return -EIO;
	writel_relaxed(state, dev->base + QUP_STATE);
	if (qup_i2c_poll_state(dev, state) != 0)
		return -EIO;
	return 0;
}
Beispiel #3
0
static int qup_i2c_change_state(struct qup_i2c_dev *qup, u32 state)
{
	if (qup_i2c_poll_state_valid(qup) != 0)
		return -EIO;

	writel(state, qup->base + QUP_STATE);

	if (qup_i2c_poll_state(qup, state) != 0)
		return -EIO;
	return 0;
}
Beispiel #4
0
static int qup_i2c_xfer(struct i2c_adapter *adap,
			struct i2c_msg msgs[],
			int num)
{
	struct qup_i2c_dev *qup = i2c_get_adapdata(adap);
	int ret, idx;

	ret = pm_runtime_get_sync(qup->dev);
	if (ret < 0)
		goto out;

	writel(1, qup->base + QUP_SW_RESET);
	ret = qup_i2c_poll_state(qup, QUP_RESET_STATE);
	if (ret)
		goto out;

	/* Configure QUP as I2C mini core */
	writel(I2C_MINI_CORE | I2C_N_VAL, qup->base + QUP_CONFIG);

	for (idx = 0; idx < num; idx++) {
		if (msgs[idx].len == 0) {
			ret = -EINVAL;
			goto out;
		}

		if (qup_i2c_poll_state_i2c_master(qup)) {
			ret = -EIO;
			goto out;
		}

		if (msgs[idx].flags & I2C_M_RD)
			ret = qup_i2c_read_one(qup, &msgs[idx]);
		else
			ret = qup_i2c_write_one(qup, &msgs[idx]);

		if (ret)
			break;

		ret = qup_i2c_change_state(qup, QUP_RESET_STATE);
		if (ret)
			break;
	}

	if (ret == 0)
		ret = num;
out:

	pm_runtime_mark_last_busy(qup->dev);
	pm_runtime_put_autosuspend(qup->dev);

	return ret;
}