drivers/staging/media/atomisp/i2c/atomisp-ov2722.c

Source file repositories/reference/linux-study-clean/drivers/staging/media/atomisp/i2c/atomisp-ov2722.c

File Facts

System
Linux kernel
Corpus path
drivers/staging/media/atomisp/i2c/atomisp-ov2722.c
Extension
.c
Size
23186 bytes
Lines
1016
Domain
Driver Families
Bucket
drivers/staging
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

switch (next->type & OV2722_TOK_MASK) {
		case OV2722_TOK_DELAY:
			err = __ov2722_flush_reg_array(client, &ctrl);
			if (err)
				return err;
			msleep(next->val);
			break;
		default:
			/*
			 * If next address is not consecutive, data needs to be
			 * flushed before proceed.
			 */
			if (!__ov2722_write_reg_is_consecutive(client, &ctrl,
							       next)) {
				err = __ov2722_flush_reg_array(client, &ctrl);
				if (err)
					return err;
			}
			err = __ov2722_buf_reg_array(client, &ctrl, next);
			if (err) {
				dev_err(&client->dev, "%s: write error, aborted\n",
					__func__);
				return err;
			}
			break;
		}
	}

	return __ov2722_flush_reg_array(client, &ctrl);
}

static long __ov2722_set_exposure(struct v4l2_subdev *sd, int coarse_itg,
				  int gain, int digitgain)

{
	struct i2c_client *client = v4l2_get_subdevdata(sd);
	struct ov2722_device *dev = to_ov2722_sensor(sd);
	u16 hts, vts;
	int ret;

	dev_dbg(&client->dev, "set_exposure without group hold\n");

	/* clear VTS_DIFF on manual mode */
	ret = ov2722_write_reg(client, OV2722_16BIT, OV2722_VTS_DIFF_H, 0);
	if (ret)
		return ret;

	hts = dev->pixels_per_line;
	vts = dev->lines_per_frame;

	if ((coarse_itg + OV2722_COARSE_INTG_TIME_MAX_MARGIN) > vts)
		vts = coarse_itg + OV2722_COARSE_INTG_TIME_MAX_MARGIN;

	coarse_itg <<= 4;
	digitgain <<= 2;

	ret = ov2722_write_reg(client, OV2722_16BIT,
			       OV2722_VTS_H, vts);
	if (ret)
		return ret;

	ret = ov2722_write_reg(client, OV2722_16BIT,
			       OV2722_HTS_H, hts);
	if (ret)
		return ret;

	/* set exposure */
	ret = ov2722_write_reg(client, OV2722_8BIT,
			       OV2722_AEC_PK_EXPO_L,
			       coarse_itg & 0xff);
	if (ret)
		return ret;

	ret = ov2722_write_reg(client, OV2722_16BIT,
			       OV2722_AEC_PK_EXPO_H,
			       (coarse_itg >> 8) & 0xfff);
	if (ret)
		return ret;

	/* set analog gain */
	ret = ov2722_write_reg(client, OV2722_16BIT,
			       OV2722_AGC_ADJ_H, gain);
	if (ret)
		return ret;

	/* set digital gain */
	ret = ov2722_write_reg(client, OV2722_16BIT,
			       OV2722_MWB_GAIN_R_H, digitgain);
	if (ret)
		return ret;

Annotation

Implementation Notes