cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

mt9t001.c (27310B)


      1// SPDX-License-Identifier: GPL-2.0-only
      2/*
      3 * Driver for MT9T001 CMOS Image Sensor from Aptina (Micron)
      4 *
      5 * Copyright (C) 2010-2011, Laurent Pinchart <laurent.pinchart@ideasonboard.com>
      6 *
      7 * Based on the MT9M001 driver,
      8 *
      9 * Copyright (C) 2008, Guennadi Liakhovetski <kernel@pengutronix.de>
     10 */
     11
     12#include <linux/clk.h>
     13#include <linux/i2c.h>
     14#include <linux/log2.h>
     15#include <linux/module.h>
     16#include <linux/regulator/consumer.h>
     17#include <linux/slab.h>
     18#include <linux/videodev2.h>
     19#include <linux/v4l2-mediabus.h>
     20
     21#include <media/i2c/mt9t001.h>
     22#include <media/v4l2-ctrls.h>
     23#include <media/v4l2-device.h>
     24#include <media/v4l2-subdev.h>
     25
     26#define MT9T001_PIXEL_ARRAY_HEIGHT			1568
     27#define MT9T001_PIXEL_ARRAY_WIDTH			2112
     28
     29#define MT9T001_CHIP_VERSION				0x00
     30#define		MT9T001_CHIP_ID				0x1621
     31#define MT9T001_ROW_START				0x01
     32#define		MT9T001_ROW_START_MIN			0
     33#define		MT9T001_ROW_START_DEF			20
     34#define		MT9T001_ROW_START_MAX			1534
     35#define MT9T001_COLUMN_START				0x02
     36#define		MT9T001_COLUMN_START_MIN		0
     37#define		MT9T001_COLUMN_START_DEF		32
     38#define		MT9T001_COLUMN_START_MAX		2046
     39#define MT9T001_WINDOW_HEIGHT				0x03
     40#define		MT9T001_WINDOW_HEIGHT_MIN		1
     41#define		MT9T001_WINDOW_HEIGHT_DEF		1535
     42#define		MT9T001_WINDOW_HEIGHT_MAX		1567
     43#define MT9T001_WINDOW_WIDTH				0x04
     44#define		MT9T001_WINDOW_WIDTH_MIN		1
     45#define		MT9T001_WINDOW_WIDTH_DEF		2047
     46#define		MT9T001_WINDOW_WIDTH_MAX		2111
     47#define MT9T001_HORIZONTAL_BLANKING			0x05
     48#define		MT9T001_HORIZONTAL_BLANKING_MIN		21
     49#define		MT9T001_HORIZONTAL_BLANKING_MAX		1023
     50#define MT9T001_VERTICAL_BLANKING			0x06
     51#define		MT9T001_VERTICAL_BLANKING_MIN		3
     52#define		MT9T001_VERTICAL_BLANKING_MAX		1023
     53#define MT9T001_OUTPUT_CONTROL				0x07
     54#define		MT9T001_OUTPUT_CONTROL_SYNC		(1 << 0)
     55#define		MT9T001_OUTPUT_CONTROL_CHIP_ENABLE	(1 << 1)
     56#define		MT9T001_OUTPUT_CONTROL_TEST_DATA	(1 << 6)
     57#define		MT9T001_OUTPUT_CONTROL_DEF		0x0002
     58#define MT9T001_SHUTTER_WIDTH_HIGH			0x08
     59#define MT9T001_SHUTTER_WIDTH_LOW			0x09
     60#define		MT9T001_SHUTTER_WIDTH_MIN		1
     61#define		MT9T001_SHUTTER_WIDTH_DEF		1561
     62#define		MT9T001_SHUTTER_WIDTH_MAX		(1024 * 1024)
     63#define MT9T001_PIXEL_CLOCK				0x0a
     64#define		MT9T001_PIXEL_CLOCK_INVERT		(1 << 15)
     65#define		MT9T001_PIXEL_CLOCK_SHIFT_MASK		(7 << 8)
     66#define		MT9T001_PIXEL_CLOCK_SHIFT_SHIFT		8
     67#define		MT9T001_PIXEL_CLOCK_DIVIDE_MASK		(0x7f << 0)
     68#define MT9T001_FRAME_RESTART				0x0b
     69#define MT9T001_SHUTTER_DELAY				0x0c
     70#define		MT9T001_SHUTTER_DELAY_MAX		2047
     71#define MT9T001_RESET					0x0d
     72#define MT9T001_READ_MODE1				0x1e
     73#define		MT9T001_READ_MODE_SNAPSHOT		(1 << 8)
     74#define		MT9T001_READ_MODE_STROBE_ENABLE		(1 << 9)
     75#define		MT9T001_READ_MODE_STROBE_WIDTH		(1 << 10)
     76#define		MT9T001_READ_MODE_STROBE_OVERRIDE	(1 << 11)
     77#define MT9T001_READ_MODE2				0x20
     78#define		MT9T001_READ_MODE_BAD_FRAMES		(1 << 0)
     79#define		MT9T001_READ_MODE_LINE_VALID_CONTINUOUS	(1 << 9)
     80#define		MT9T001_READ_MODE_LINE_VALID_FRAME	(1 << 10)
     81#define MT9T001_READ_MODE3				0x21
     82#define		MT9T001_READ_MODE_GLOBAL_RESET		(1 << 0)
     83#define		MT9T001_READ_MODE_GHST_CTL		(1 << 1)
     84#define MT9T001_ROW_ADDRESS_MODE			0x22
     85#define		MT9T001_ROW_SKIP_MASK			(7 << 0)
     86#define		MT9T001_ROW_BIN_MASK			(3 << 3)
     87#define		MT9T001_ROW_BIN_SHIFT			3
     88#define MT9T001_COLUMN_ADDRESS_MODE			0x23
     89#define		MT9T001_COLUMN_SKIP_MASK		(7 << 0)
     90#define		MT9T001_COLUMN_BIN_MASK			(3 << 3)
     91#define		MT9T001_COLUMN_BIN_SHIFT		3
     92#define MT9T001_GREEN1_GAIN				0x2b
     93#define MT9T001_BLUE_GAIN				0x2c
     94#define MT9T001_RED_GAIN				0x2d
     95#define MT9T001_GREEN2_GAIN				0x2e
     96#define MT9T001_TEST_DATA				0x32
     97#define MT9T001_GLOBAL_GAIN				0x35
     98#define		MT9T001_GLOBAL_GAIN_MIN			8
     99#define		MT9T001_GLOBAL_GAIN_MAX			1024
    100#define MT9T001_BLACK_LEVEL				0x49
    101#define MT9T001_ROW_BLACK_DEFAULT_OFFSET		0x4b
    102#define MT9T001_BLC_DELTA_THRESHOLDS			0x5d
    103#define MT9T001_CAL_THRESHOLDS				0x5f
    104#define MT9T001_GREEN1_OFFSET				0x60
    105#define MT9T001_GREEN2_OFFSET				0x61
    106#define MT9T001_BLACK_LEVEL_CALIBRATION			0x62
    107#define		MT9T001_BLACK_LEVEL_OVERRIDE		(1 << 0)
    108#define		MT9T001_BLACK_LEVEL_DISABLE_OFFSET	(1 << 1)
    109#define		MT9T001_BLACK_LEVEL_RECALCULATE		(1 << 12)
    110#define		MT9T001_BLACK_LEVEL_LOCK_RED_BLUE	(1 << 13)
    111#define		MT9T001_BLACK_LEVEL_LOCK_GREEN		(1 << 14)
    112#define MT9T001_RED_OFFSET				0x63
    113#define MT9T001_BLUE_OFFSET				0x64
    114
    115struct mt9t001 {
    116	struct v4l2_subdev subdev;
    117	struct media_pad pad;
    118
    119	struct clk *clk;
    120	struct regulator_bulk_data regulators[2];
    121
    122	struct mutex power_lock; /* lock to protect power_count */
    123	int power_count;
    124
    125	struct v4l2_mbus_framefmt format;
    126	struct v4l2_rect crop;
    127
    128	struct v4l2_ctrl_handler ctrls;
    129	struct v4l2_ctrl *gains[4];
    130
    131	u16 output_control;
    132	u16 black_level;
    133};
    134
    135static inline struct mt9t001 *to_mt9t001(struct v4l2_subdev *sd)
    136{
    137	return container_of(sd, struct mt9t001, subdev);
    138}
    139
    140static int mt9t001_read(struct i2c_client *client, u8 reg)
    141{
    142	return i2c_smbus_read_word_swapped(client, reg);
    143}
    144
    145static int mt9t001_write(struct i2c_client *client, u8 reg, u16 data)
    146{
    147	return i2c_smbus_write_word_swapped(client, reg, data);
    148}
    149
    150static int mt9t001_set_output_control(struct mt9t001 *mt9t001, u16 clear,
    151				      u16 set)
    152{
    153	struct i2c_client *client = v4l2_get_subdevdata(&mt9t001->subdev);
    154	u16 value = (mt9t001->output_control & ~clear) | set;
    155	int ret;
    156
    157	if (value == mt9t001->output_control)
    158		return 0;
    159
    160	ret = mt9t001_write(client, MT9T001_OUTPUT_CONTROL, value);
    161	if (ret < 0)
    162		return ret;
    163
    164	mt9t001->output_control = value;
    165	return 0;
    166}
    167
    168static int mt9t001_reset(struct mt9t001 *mt9t001)
    169{
    170	struct i2c_client *client = v4l2_get_subdevdata(&mt9t001->subdev);
    171	int ret;
    172
    173	/* Reset the chip and stop data read out */
    174	ret = mt9t001_write(client, MT9T001_RESET, 1);
    175	if (ret < 0)
    176		return ret;
    177
    178	ret = mt9t001_write(client, MT9T001_RESET, 0);
    179	if (ret < 0)
    180		return ret;
    181
    182	mt9t001->output_control = MT9T001_OUTPUT_CONTROL_DEF;
    183
    184	return mt9t001_set_output_control(mt9t001,
    185					  MT9T001_OUTPUT_CONTROL_CHIP_ENABLE,
    186					  0);
    187}
    188
    189static int mt9t001_power_on(struct mt9t001 *mt9t001)
    190{
    191	int ret;
    192
    193	/* Bring up the supplies */
    194	ret = regulator_bulk_enable(ARRAY_SIZE(mt9t001->regulators),
    195				   mt9t001->regulators);
    196	if (ret < 0)
    197		return ret;
    198
    199	/* Enable clock */
    200	ret = clk_prepare_enable(mt9t001->clk);
    201	if (ret < 0)
    202		regulator_bulk_disable(ARRAY_SIZE(mt9t001->regulators),
    203				       mt9t001->regulators);
    204
    205	return ret;
    206}
    207
    208static void mt9t001_power_off(struct mt9t001 *mt9t001)
    209{
    210	regulator_bulk_disable(ARRAY_SIZE(mt9t001->regulators),
    211			       mt9t001->regulators);
    212
    213	clk_disable_unprepare(mt9t001->clk);
    214}
    215
    216static int __mt9t001_set_power(struct mt9t001 *mt9t001, bool on)
    217{
    218	struct i2c_client *client = v4l2_get_subdevdata(&mt9t001->subdev);
    219	int ret;
    220
    221	if (!on) {
    222		mt9t001_power_off(mt9t001);
    223		return 0;
    224	}
    225
    226	ret = mt9t001_power_on(mt9t001);
    227	if (ret < 0)
    228		return ret;
    229
    230	ret = mt9t001_reset(mt9t001);
    231	if (ret < 0) {
    232		dev_err(&client->dev, "Failed to reset the camera\n");
    233		goto e_power;
    234	}
    235
    236	ret = v4l2_ctrl_handler_setup(&mt9t001->ctrls);
    237	if (ret < 0) {
    238		dev_err(&client->dev, "Failed to set up control handlers\n");
    239		goto e_power;
    240	}
    241
    242	return 0;
    243
    244e_power:
    245	mt9t001_power_off(mt9t001);
    246
    247	return ret;
    248}
    249
    250/* -----------------------------------------------------------------------------
    251 * V4L2 subdev video operations
    252 */
    253
    254static struct v4l2_mbus_framefmt *
    255__mt9t001_get_pad_format(struct mt9t001 *mt9t001,
    256			 struct v4l2_subdev_state *sd_state,
    257			 unsigned int pad, enum v4l2_subdev_format_whence which)
    258{
    259	switch (which) {
    260	case V4L2_SUBDEV_FORMAT_TRY:
    261		return v4l2_subdev_get_try_format(&mt9t001->subdev, sd_state,
    262						  pad);
    263	case V4L2_SUBDEV_FORMAT_ACTIVE:
    264		return &mt9t001->format;
    265	default:
    266		return NULL;
    267	}
    268}
    269
    270static struct v4l2_rect *
    271__mt9t001_get_pad_crop(struct mt9t001 *mt9t001,
    272		       struct v4l2_subdev_state *sd_state,
    273		       unsigned int pad, enum v4l2_subdev_format_whence which)
    274{
    275	switch (which) {
    276	case V4L2_SUBDEV_FORMAT_TRY:
    277		return v4l2_subdev_get_try_crop(&mt9t001->subdev, sd_state,
    278						pad);
    279	case V4L2_SUBDEV_FORMAT_ACTIVE:
    280		return &mt9t001->crop;
    281	default:
    282		return NULL;
    283	}
    284}
    285
    286static int mt9t001_s_stream(struct v4l2_subdev *subdev, int enable)
    287{
    288	const u16 mode = MT9T001_OUTPUT_CONTROL_CHIP_ENABLE;
    289	struct i2c_client *client = v4l2_get_subdevdata(subdev);
    290	struct mt9t001_platform_data *pdata = client->dev.platform_data;
    291	struct mt9t001 *mt9t001 = to_mt9t001(subdev);
    292	struct v4l2_mbus_framefmt *format = &mt9t001->format;
    293	struct v4l2_rect *crop = &mt9t001->crop;
    294	unsigned int hratio;
    295	unsigned int vratio;
    296	int ret;
    297
    298	if (!enable)
    299		return mt9t001_set_output_control(mt9t001, mode, 0);
    300
    301	/* Configure the pixel clock polarity */
    302	if (pdata->clk_pol) {
    303		ret  = mt9t001_write(client, MT9T001_PIXEL_CLOCK,
    304				     MT9T001_PIXEL_CLOCK_INVERT);
    305		if (ret < 0)
    306			return ret;
    307	}
    308
    309	/* Configure the window size and row/column bin */
    310	hratio = DIV_ROUND_CLOSEST(crop->width, format->width);
    311	vratio = DIV_ROUND_CLOSEST(crop->height, format->height);
    312
    313	ret = mt9t001_write(client, MT9T001_ROW_ADDRESS_MODE, hratio - 1);
    314	if (ret < 0)
    315		return ret;
    316
    317	ret = mt9t001_write(client, MT9T001_COLUMN_ADDRESS_MODE, vratio - 1);
    318	if (ret < 0)
    319		return ret;
    320
    321	ret = mt9t001_write(client, MT9T001_COLUMN_START, crop->left);
    322	if (ret < 0)
    323		return ret;
    324
    325	ret = mt9t001_write(client, MT9T001_ROW_START, crop->top);
    326	if (ret < 0)
    327		return ret;
    328
    329	ret = mt9t001_write(client, MT9T001_WINDOW_WIDTH, crop->width - 1);
    330	if (ret < 0)
    331		return ret;
    332
    333	ret = mt9t001_write(client, MT9T001_WINDOW_HEIGHT, crop->height - 1);
    334	if (ret < 0)
    335		return ret;
    336
    337	/* Switch to master "normal" mode */
    338	return mt9t001_set_output_control(mt9t001, 0, mode);
    339}
    340
    341static int mt9t001_enum_mbus_code(struct v4l2_subdev *subdev,
    342				  struct v4l2_subdev_state *sd_state,
    343				  struct v4l2_subdev_mbus_code_enum *code)
    344{
    345	if (code->index > 0)
    346		return -EINVAL;
    347
    348	code->code = MEDIA_BUS_FMT_SGRBG10_1X10;
    349	return 0;
    350}
    351
    352static int mt9t001_enum_frame_size(struct v4l2_subdev *subdev,
    353				   struct v4l2_subdev_state *sd_state,
    354				   struct v4l2_subdev_frame_size_enum *fse)
    355{
    356	if (fse->index >= 8 || fse->code != MEDIA_BUS_FMT_SGRBG10_1X10)
    357		return -EINVAL;
    358
    359	fse->min_width = (MT9T001_WINDOW_WIDTH_DEF + 1) / fse->index;
    360	fse->max_width = fse->min_width;
    361	fse->min_height = (MT9T001_WINDOW_HEIGHT_DEF + 1) / fse->index;
    362	fse->max_height = fse->min_height;
    363
    364	return 0;
    365}
    366
    367static int mt9t001_get_format(struct v4l2_subdev *subdev,
    368			      struct v4l2_subdev_state *sd_state,
    369			      struct v4l2_subdev_format *format)
    370{
    371	struct mt9t001 *mt9t001 = to_mt9t001(subdev);
    372
    373	format->format = *__mt9t001_get_pad_format(mt9t001, sd_state,
    374						   format->pad,
    375						   format->which);
    376	return 0;
    377}
    378
    379static int mt9t001_set_format(struct v4l2_subdev *subdev,
    380			      struct v4l2_subdev_state *sd_state,
    381			      struct v4l2_subdev_format *format)
    382{
    383	struct mt9t001 *mt9t001 = to_mt9t001(subdev);
    384	struct v4l2_mbus_framefmt *__format;
    385	struct v4l2_rect *__crop;
    386	unsigned int width;
    387	unsigned int height;
    388	unsigned int hratio;
    389	unsigned int vratio;
    390
    391	__crop = __mt9t001_get_pad_crop(mt9t001, sd_state, format->pad,
    392					format->which);
    393
    394	/* Clamp the width and height to avoid dividing by zero. */
    395	width = clamp_t(unsigned int, ALIGN(format->format.width, 2),
    396			max_t(unsigned int, __crop->width / 8,
    397			      MT9T001_WINDOW_HEIGHT_MIN + 1),
    398			__crop->width);
    399	height = clamp_t(unsigned int, ALIGN(format->format.height, 2),
    400			 max_t(unsigned int, __crop->height / 8,
    401			       MT9T001_WINDOW_HEIGHT_MIN + 1),
    402			 __crop->height);
    403
    404	hratio = DIV_ROUND_CLOSEST(__crop->width, width);
    405	vratio = DIV_ROUND_CLOSEST(__crop->height, height);
    406
    407	__format = __mt9t001_get_pad_format(mt9t001, sd_state, format->pad,
    408					    format->which);
    409	__format->width = __crop->width / hratio;
    410	__format->height = __crop->height / vratio;
    411
    412	format->format = *__format;
    413
    414	return 0;
    415}
    416
    417static int mt9t001_get_selection(struct v4l2_subdev *subdev,
    418				 struct v4l2_subdev_state *sd_state,
    419				 struct v4l2_subdev_selection *sel)
    420{
    421	struct mt9t001 *mt9t001 = to_mt9t001(subdev);
    422
    423	if (sel->target != V4L2_SEL_TGT_CROP)
    424		return -EINVAL;
    425
    426	sel->r = *__mt9t001_get_pad_crop(mt9t001, sd_state, sel->pad,
    427					 sel->which);
    428	return 0;
    429}
    430
    431static int mt9t001_set_selection(struct v4l2_subdev *subdev,
    432				 struct v4l2_subdev_state *sd_state,
    433				 struct v4l2_subdev_selection *sel)
    434{
    435	struct mt9t001 *mt9t001 = to_mt9t001(subdev);
    436	struct v4l2_mbus_framefmt *__format;
    437	struct v4l2_rect *__crop;
    438	struct v4l2_rect rect;
    439
    440	if (sel->target != V4L2_SEL_TGT_CROP)
    441		return -EINVAL;
    442
    443	/* Clamp the crop rectangle boundaries and align them to a multiple of 2
    444	 * pixels.
    445	 */
    446	rect.left = clamp(ALIGN(sel->r.left, 2),
    447			  MT9T001_COLUMN_START_MIN,
    448			  MT9T001_COLUMN_START_MAX);
    449	rect.top = clamp(ALIGN(sel->r.top, 2),
    450			 MT9T001_ROW_START_MIN,
    451			 MT9T001_ROW_START_MAX);
    452	rect.width = clamp_t(unsigned int, ALIGN(sel->r.width, 2),
    453			     MT9T001_WINDOW_WIDTH_MIN + 1,
    454			     MT9T001_WINDOW_WIDTH_MAX + 1);
    455	rect.height = clamp_t(unsigned int, ALIGN(sel->r.height, 2),
    456			      MT9T001_WINDOW_HEIGHT_MIN + 1,
    457			      MT9T001_WINDOW_HEIGHT_MAX + 1);
    458
    459	rect.width = min_t(unsigned int, rect.width,
    460			   MT9T001_PIXEL_ARRAY_WIDTH - rect.left);
    461	rect.height = min_t(unsigned int, rect.height,
    462			    MT9T001_PIXEL_ARRAY_HEIGHT - rect.top);
    463
    464	__crop = __mt9t001_get_pad_crop(mt9t001, sd_state, sel->pad,
    465					sel->which);
    466
    467	if (rect.width != __crop->width || rect.height != __crop->height) {
    468		/* Reset the output image size if the crop rectangle size has
    469		 * been modified.
    470		 */
    471		__format = __mt9t001_get_pad_format(mt9t001, sd_state,
    472						    sel->pad,
    473						    sel->which);
    474		__format->width = rect.width;
    475		__format->height = rect.height;
    476	}
    477
    478	*__crop = rect;
    479	sel->r = rect;
    480
    481	return 0;
    482}
    483
    484/* -----------------------------------------------------------------------------
    485 * V4L2 subdev control operations
    486 */
    487
    488#define V4L2_CID_TEST_PATTERN_COLOR	(V4L2_CID_USER_BASE | 0x1001)
    489#define V4L2_CID_BLACK_LEVEL_AUTO	(V4L2_CID_USER_BASE | 0x1002)
    490#define V4L2_CID_BLACK_LEVEL_OFFSET	(V4L2_CID_USER_BASE | 0x1003)
    491#define V4L2_CID_BLACK_LEVEL_CALIBRATE	(V4L2_CID_USER_BASE | 0x1004)
    492
    493#define V4L2_CID_GAIN_RED		(V4L2_CTRL_CLASS_CAMERA | 0x1001)
    494#define V4L2_CID_GAIN_GREEN_RED		(V4L2_CTRL_CLASS_CAMERA | 0x1002)
    495#define V4L2_CID_GAIN_GREEN_BLUE	(V4L2_CTRL_CLASS_CAMERA | 0x1003)
    496#define V4L2_CID_GAIN_BLUE		(V4L2_CTRL_CLASS_CAMERA | 0x1004)
    497
    498static u16 mt9t001_gain_value(s32 *gain)
    499{
    500	/* Gain is controlled by 2 analog stages and a digital stage. Valid
    501	 * values for the 3 stages are
    502	 *
    503	 * Stage		Min	Max	Step
    504	 * ------------------------------------------
    505	 * First analog stage	x1	x2	1
    506	 * Second analog stage	x1	x4	0.125
    507	 * Digital stage	x1	x16	0.125
    508	 *
    509	 * To minimize noise, the gain stages should be used in the second
    510	 * analog stage, first analog stage, digital stage order. Gain from a
    511	 * previous stage should be pushed to its maximum value before the next
    512	 * stage is used.
    513	 */
    514	if (*gain <= 32)
    515		return *gain;
    516
    517	if (*gain <= 64) {
    518		*gain &= ~1;
    519		return (1 << 6) | (*gain >> 1);
    520	}
    521
    522	*gain &= ~7;
    523	return ((*gain - 64) << 5) | (1 << 6) | 32;
    524}
    525
    526static int mt9t001_ctrl_freeze(struct mt9t001 *mt9t001, bool freeze)
    527{
    528	return mt9t001_set_output_control(mt9t001,
    529		freeze ? 0 : MT9T001_OUTPUT_CONTROL_SYNC,
    530		freeze ? MT9T001_OUTPUT_CONTROL_SYNC : 0);
    531}
    532
    533static int mt9t001_s_ctrl(struct v4l2_ctrl *ctrl)
    534{
    535	static const u8 gains[4] = {
    536		MT9T001_RED_GAIN, MT9T001_GREEN1_GAIN,
    537		MT9T001_GREEN2_GAIN, MT9T001_BLUE_GAIN
    538	};
    539
    540	struct mt9t001 *mt9t001 =
    541			container_of(ctrl->handler, struct mt9t001, ctrls);
    542	struct i2c_client *client = v4l2_get_subdevdata(&mt9t001->subdev);
    543	unsigned int count;
    544	unsigned int i;
    545	u16 value;
    546	int ret;
    547
    548	switch (ctrl->id) {
    549	case V4L2_CID_GAIN_RED:
    550	case V4L2_CID_GAIN_GREEN_RED:
    551	case V4L2_CID_GAIN_GREEN_BLUE:
    552	case V4L2_CID_GAIN_BLUE:
    553
    554		/* Disable control updates if more than one control has changed
    555		 * in the cluster.
    556		 */
    557		for (i = 0, count = 0; i < 4; ++i) {
    558			struct v4l2_ctrl *gain = mt9t001->gains[i];
    559
    560			if (gain->val != gain->cur.val)
    561				count++;
    562		}
    563
    564		if (count > 1) {
    565			ret = mt9t001_ctrl_freeze(mt9t001, true);
    566			if (ret < 0)
    567				return ret;
    568		}
    569
    570		/* Update the gain controls. */
    571		for (i = 0; i < 4; ++i) {
    572			struct v4l2_ctrl *gain = mt9t001->gains[i];
    573
    574			if (gain->val == gain->cur.val)
    575				continue;
    576
    577			value = mt9t001_gain_value(&gain->val);
    578			ret = mt9t001_write(client, gains[i], value);
    579			if (ret < 0) {
    580				mt9t001_ctrl_freeze(mt9t001, false);
    581				return ret;
    582			}
    583		}
    584
    585		/* Enable control updates. */
    586		if (count > 1) {
    587			ret = mt9t001_ctrl_freeze(mt9t001, false);
    588			if (ret < 0)
    589				return ret;
    590		}
    591
    592		break;
    593
    594	case V4L2_CID_EXPOSURE:
    595		ret = mt9t001_write(client, MT9T001_SHUTTER_WIDTH_LOW,
    596				    ctrl->val & 0xffff);
    597		if (ret < 0)
    598			return ret;
    599
    600		return mt9t001_write(client, MT9T001_SHUTTER_WIDTH_HIGH,
    601				     ctrl->val >> 16);
    602
    603	case V4L2_CID_TEST_PATTERN:
    604		return mt9t001_set_output_control(mt9t001,
    605			ctrl->val ? 0 : MT9T001_OUTPUT_CONTROL_TEST_DATA,
    606			ctrl->val ? MT9T001_OUTPUT_CONTROL_TEST_DATA : 0);
    607
    608	case V4L2_CID_TEST_PATTERN_COLOR:
    609		return mt9t001_write(client, MT9T001_TEST_DATA, ctrl->val << 2);
    610
    611	case V4L2_CID_BLACK_LEVEL_AUTO:
    612		value = ctrl->val ? 0 : MT9T001_BLACK_LEVEL_OVERRIDE;
    613		ret = mt9t001_write(client, MT9T001_BLACK_LEVEL_CALIBRATION,
    614				    value);
    615		if (ret < 0)
    616			return ret;
    617
    618		mt9t001->black_level = value;
    619		break;
    620
    621	case V4L2_CID_BLACK_LEVEL_OFFSET:
    622		ret = mt9t001_write(client, MT9T001_GREEN1_OFFSET, ctrl->val);
    623		if (ret < 0)
    624			return ret;
    625
    626		ret = mt9t001_write(client, MT9T001_GREEN2_OFFSET, ctrl->val);
    627		if (ret < 0)
    628			return ret;
    629
    630		ret = mt9t001_write(client, MT9T001_RED_OFFSET, ctrl->val);
    631		if (ret < 0)
    632			return ret;
    633
    634		return mt9t001_write(client, MT9T001_BLUE_OFFSET, ctrl->val);
    635
    636	case V4L2_CID_BLACK_LEVEL_CALIBRATE:
    637		return mt9t001_write(client, MT9T001_BLACK_LEVEL_CALIBRATION,
    638				     MT9T001_BLACK_LEVEL_RECALCULATE |
    639				     mt9t001->black_level);
    640	}
    641
    642	return 0;
    643}
    644
    645static const struct v4l2_ctrl_ops mt9t001_ctrl_ops = {
    646	.s_ctrl = mt9t001_s_ctrl,
    647};
    648
    649static const char * const mt9t001_test_pattern_menu[] = {
    650	"Disabled",
    651	"Enabled",
    652};
    653
    654static const struct v4l2_ctrl_config mt9t001_ctrls[] = {
    655	{
    656		.ops		= &mt9t001_ctrl_ops,
    657		.id		= V4L2_CID_TEST_PATTERN_COLOR,
    658		.type		= V4L2_CTRL_TYPE_INTEGER,
    659		.name		= "Test Pattern Color",
    660		.min		= 0,
    661		.max		= 1023,
    662		.step		= 1,
    663		.def		= 0,
    664		.flags		= 0,
    665	}, {
    666		.ops		= &mt9t001_ctrl_ops,
    667		.id		= V4L2_CID_BLACK_LEVEL_AUTO,
    668		.type		= V4L2_CTRL_TYPE_BOOLEAN,
    669		.name		= "Black Level, Auto",
    670		.min		= 0,
    671		.max		= 1,
    672		.step		= 1,
    673		.def		= 1,
    674		.flags		= 0,
    675	}, {
    676		.ops		= &mt9t001_ctrl_ops,
    677		.id		= V4L2_CID_BLACK_LEVEL_OFFSET,
    678		.type		= V4L2_CTRL_TYPE_INTEGER,
    679		.name		= "Black Level, Offset",
    680		.min		= -256,
    681		.max		= 255,
    682		.step		= 1,
    683		.def		= 32,
    684		.flags		= 0,
    685	}, {
    686		.ops		= &mt9t001_ctrl_ops,
    687		.id		= V4L2_CID_BLACK_LEVEL_CALIBRATE,
    688		.type		= V4L2_CTRL_TYPE_BUTTON,
    689		.name		= "Black Level, Calibrate",
    690		.min		= 0,
    691		.max		= 0,
    692		.step		= 0,
    693		.def		= 0,
    694		.flags		= V4L2_CTRL_FLAG_WRITE_ONLY,
    695	},
    696};
    697
    698static const struct v4l2_ctrl_config mt9t001_gains[] = {
    699	{
    700		.ops		= &mt9t001_ctrl_ops,
    701		.id		= V4L2_CID_GAIN_RED,
    702		.type		= V4L2_CTRL_TYPE_INTEGER,
    703		.name		= "Gain, Red",
    704		.min		= MT9T001_GLOBAL_GAIN_MIN,
    705		.max		= MT9T001_GLOBAL_GAIN_MAX,
    706		.step		= 1,
    707		.def		= MT9T001_GLOBAL_GAIN_MIN,
    708		.flags		= 0,
    709	}, {
    710		.ops		= &mt9t001_ctrl_ops,
    711		.id		= V4L2_CID_GAIN_GREEN_RED,
    712		.type		= V4L2_CTRL_TYPE_INTEGER,
    713		.name		= "Gain, Green (R)",
    714		.min		= MT9T001_GLOBAL_GAIN_MIN,
    715		.max		= MT9T001_GLOBAL_GAIN_MAX,
    716		.step		= 1,
    717		.def		= MT9T001_GLOBAL_GAIN_MIN,
    718		.flags		= 0,
    719	}, {
    720		.ops		= &mt9t001_ctrl_ops,
    721		.id		= V4L2_CID_GAIN_GREEN_BLUE,
    722		.type		= V4L2_CTRL_TYPE_INTEGER,
    723		.name		= "Gain, Green (B)",
    724		.min		= MT9T001_GLOBAL_GAIN_MIN,
    725		.max		= MT9T001_GLOBAL_GAIN_MAX,
    726		.step		= 1,
    727		.def		= MT9T001_GLOBAL_GAIN_MIN,
    728		.flags		= 0,
    729	}, {
    730		.ops		= &mt9t001_ctrl_ops,
    731		.id		= V4L2_CID_GAIN_BLUE,
    732		.type		= V4L2_CTRL_TYPE_INTEGER,
    733		.name		= "Gain, Blue",
    734		.min		= MT9T001_GLOBAL_GAIN_MIN,
    735		.max		= MT9T001_GLOBAL_GAIN_MAX,
    736		.step		= 1,
    737		.def		= MT9T001_GLOBAL_GAIN_MIN,
    738		.flags		= 0,
    739	},
    740};
    741
    742/* -----------------------------------------------------------------------------
    743 * V4L2 subdev core operations
    744 */
    745
    746static int mt9t001_set_power(struct v4l2_subdev *subdev, int on)
    747{
    748	struct mt9t001 *mt9t001 = to_mt9t001(subdev);
    749	int ret = 0;
    750
    751	mutex_lock(&mt9t001->power_lock);
    752
    753	/* If the power count is modified from 0 to != 0 or from != 0 to 0,
    754	 * update the power state.
    755	 */
    756	if (mt9t001->power_count == !on) {
    757		ret = __mt9t001_set_power(mt9t001, !!on);
    758		if (ret < 0)
    759			goto out;
    760	}
    761
    762	/* Update the power count. */
    763	mt9t001->power_count += on ? 1 : -1;
    764	WARN_ON(mt9t001->power_count < 0);
    765
    766out:
    767	mutex_unlock(&mt9t001->power_lock);
    768	return ret;
    769}
    770
    771/* -----------------------------------------------------------------------------
    772 * V4L2 subdev internal operations
    773 */
    774
    775static int mt9t001_registered(struct v4l2_subdev *subdev)
    776{
    777	struct i2c_client *client = v4l2_get_subdevdata(subdev);
    778	struct mt9t001 *mt9t001 = to_mt9t001(subdev);
    779	s32 data;
    780	int ret;
    781
    782	ret = mt9t001_power_on(mt9t001);
    783	if (ret < 0) {
    784		dev_err(&client->dev, "MT9T001 power up failed\n");
    785		return ret;
    786	}
    787
    788	/* Read out the chip version register */
    789	data = mt9t001_read(client, MT9T001_CHIP_VERSION);
    790	mt9t001_power_off(mt9t001);
    791
    792	if (data != MT9T001_CHIP_ID) {
    793		dev_err(&client->dev,
    794			"MT9T001 not detected, wrong version 0x%04x\n", data);
    795		return -ENODEV;
    796	}
    797
    798	dev_info(&client->dev, "MT9T001 detected at address 0x%02x\n",
    799		 client->addr);
    800
    801	return 0;
    802}
    803
    804static int mt9t001_open(struct v4l2_subdev *subdev, struct v4l2_subdev_fh *fh)
    805{
    806	struct v4l2_mbus_framefmt *format;
    807	struct v4l2_rect *crop;
    808
    809	crop = v4l2_subdev_get_try_crop(subdev, fh->state, 0);
    810	crop->left = MT9T001_COLUMN_START_DEF;
    811	crop->top = MT9T001_ROW_START_DEF;
    812	crop->width = MT9T001_WINDOW_WIDTH_DEF + 1;
    813	crop->height = MT9T001_WINDOW_HEIGHT_DEF + 1;
    814
    815	format = v4l2_subdev_get_try_format(subdev, fh->state, 0);
    816	format->code = MEDIA_BUS_FMT_SGRBG10_1X10;
    817	format->width = MT9T001_WINDOW_WIDTH_DEF + 1;
    818	format->height = MT9T001_WINDOW_HEIGHT_DEF + 1;
    819	format->field = V4L2_FIELD_NONE;
    820	format->colorspace = V4L2_COLORSPACE_SRGB;
    821
    822	return mt9t001_set_power(subdev, 1);
    823}
    824
    825static int mt9t001_close(struct v4l2_subdev *subdev, struct v4l2_subdev_fh *fh)
    826{
    827	return mt9t001_set_power(subdev, 0);
    828}
    829
    830static const struct v4l2_subdev_core_ops mt9t001_subdev_core_ops = {
    831	.s_power = mt9t001_set_power,
    832};
    833
    834static const struct v4l2_subdev_video_ops mt9t001_subdev_video_ops = {
    835	.s_stream = mt9t001_s_stream,
    836};
    837
    838static const struct v4l2_subdev_pad_ops mt9t001_subdev_pad_ops = {
    839	.enum_mbus_code = mt9t001_enum_mbus_code,
    840	.enum_frame_size = mt9t001_enum_frame_size,
    841	.get_fmt = mt9t001_get_format,
    842	.set_fmt = mt9t001_set_format,
    843	.get_selection = mt9t001_get_selection,
    844	.set_selection = mt9t001_set_selection,
    845};
    846
    847static const struct v4l2_subdev_ops mt9t001_subdev_ops = {
    848	.core = &mt9t001_subdev_core_ops,
    849	.video = &mt9t001_subdev_video_ops,
    850	.pad = &mt9t001_subdev_pad_ops,
    851};
    852
    853static const struct v4l2_subdev_internal_ops mt9t001_subdev_internal_ops = {
    854	.registered = mt9t001_registered,
    855	.open = mt9t001_open,
    856	.close = mt9t001_close,
    857};
    858
    859static int mt9t001_probe(struct i2c_client *client,
    860			 const struct i2c_device_id *did)
    861{
    862	struct mt9t001_platform_data *pdata = client->dev.platform_data;
    863	struct mt9t001 *mt9t001;
    864	unsigned int i;
    865	int ret;
    866
    867	if (pdata == NULL) {
    868		dev_err(&client->dev, "No platform data\n");
    869		return -EINVAL;
    870	}
    871
    872	if (!i2c_check_functionality(client->adapter,
    873				     I2C_FUNC_SMBUS_WORD_DATA)) {
    874		dev_warn(&client->adapter->dev,
    875			 "I2C-Adapter doesn't support I2C_FUNC_SMBUS_WORD\n");
    876		return -EIO;
    877	}
    878
    879	mt9t001 = devm_kzalloc(&client->dev, sizeof(*mt9t001), GFP_KERNEL);
    880	if (!mt9t001)
    881		return -ENOMEM;
    882
    883	mutex_init(&mt9t001->power_lock);
    884	mt9t001->output_control = MT9T001_OUTPUT_CONTROL_DEF;
    885
    886	mt9t001->regulators[0].supply = "vdd";
    887	mt9t001->regulators[1].supply = "vaa";
    888
    889	ret = devm_regulator_bulk_get(&client->dev, 2, mt9t001->regulators);
    890	if (ret < 0) {
    891		dev_err(&client->dev, "Unable to get regulators\n");
    892		return ret;
    893	}
    894
    895	mt9t001->clk = devm_clk_get(&client->dev, NULL);
    896	if (IS_ERR(mt9t001->clk)) {
    897		dev_err(&client->dev, "Unable to get clock\n");
    898		return PTR_ERR(mt9t001->clk);
    899	}
    900
    901	v4l2_ctrl_handler_init(&mt9t001->ctrls, ARRAY_SIZE(mt9t001_ctrls) +
    902						ARRAY_SIZE(mt9t001_gains) + 4);
    903
    904	v4l2_ctrl_new_std(&mt9t001->ctrls, &mt9t001_ctrl_ops,
    905			  V4L2_CID_EXPOSURE, MT9T001_SHUTTER_WIDTH_MIN,
    906			  MT9T001_SHUTTER_WIDTH_MAX, 1,
    907			  MT9T001_SHUTTER_WIDTH_DEF);
    908	v4l2_ctrl_new_std(&mt9t001->ctrls, &mt9t001_ctrl_ops,
    909			  V4L2_CID_BLACK_LEVEL, 1, 1, 1, 1);
    910	v4l2_ctrl_new_std(&mt9t001->ctrls, &mt9t001_ctrl_ops,
    911			  V4L2_CID_PIXEL_RATE, pdata->ext_clk, pdata->ext_clk,
    912			  1, pdata->ext_clk);
    913	v4l2_ctrl_new_std_menu_items(&mt9t001->ctrls, &mt9t001_ctrl_ops,
    914			V4L2_CID_TEST_PATTERN,
    915			ARRAY_SIZE(mt9t001_test_pattern_menu) - 1, 0,
    916			0, mt9t001_test_pattern_menu);
    917
    918	for (i = 0; i < ARRAY_SIZE(mt9t001_ctrls); ++i)
    919		v4l2_ctrl_new_custom(&mt9t001->ctrls, &mt9t001_ctrls[i], NULL);
    920
    921	for (i = 0; i < ARRAY_SIZE(mt9t001_gains); ++i)
    922		mt9t001->gains[i] = v4l2_ctrl_new_custom(&mt9t001->ctrls,
    923			&mt9t001_gains[i], NULL);
    924
    925	v4l2_ctrl_cluster(ARRAY_SIZE(mt9t001_gains), mt9t001->gains);
    926
    927	mt9t001->subdev.ctrl_handler = &mt9t001->ctrls;
    928
    929	if (mt9t001->ctrls.error) {
    930		printk(KERN_INFO "%s: control initialization error %d\n",
    931		       __func__, mt9t001->ctrls.error);
    932		ret = -EINVAL;
    933		goto done;
    934	}
    935
    936	mt9t001->crop.left = MT9T001_COLUMN_START_DEF;
    937	mt9t001->crop.top = MT9T001_ROW_START_DEF;
    938	mt9t001->crop.width = MT9T001_WINDOW_WIDTH_DEF + 1;
    939	mt9t001->crop.height = MT9T001_WINDOW_HEIGHT_DEF + 1;
    940
    941	mt9t001->format.code = MEDIA_BUS_FMT_SGRBG10_1X10;
    942	mt9t001->format.width = MT9T001_WINDOW_WIDTH_DEF + 1;
    943	mt9t001->format.height = MT9T001_WINDOW_HEIGHT_DEF + 1;
    944	mt9t001->format.field = V4L2_FIELD_NONE;
    945	mt9t001->format.colorspace = V4L2_COLORSPACE_SRGB;
    946
    947	v4l2_i2c_subdev_init(&mt9t001->subdev, client, &mt9t001_subdev_ops);
    948	mt9t001->subdev.internal_ops = &mt9t001_subdev_internal_ops;
    949	mt9t001->subdev.flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
    950
    951	mt9t001->subdev.entity.function = MEDIA_ENT_F_CAM_SENSOR;
    952	mt9t001->pad.flags = MEDIA_PAD_FL_SOURCE;
    953	ret = media_entity_pads_init(&mt9t001->subdev.entity, 1, &mt9t001->pad);
    954
    955done:
    956	if (ret < 0) {
    957		v4l2_ctrl_handler_free(&mt9t001->ctrls);
    958		media_entity_cleanup(&mt9t001->subdev.entity);
    959	}
    960
    961	return ret;
    962}
    963
    964static int mt9t001_remove(struct i2c_client *client)
    965{
    966	struct v4l2_subdev *subdev = i2c_get_clientdata(client);
    967	struct mt9t001 *mt9t001 = to_mt9t001(subdev);
    968
    969	v4l2_ctrl_handler_free(&mt9t001->ctrls);
    970	v4l2_device_unregister_subdev(subdev);
    971	media_entity_cleanup(&subdev->entity);
    972	return 0;
    973}
    974
    975static const struct i2c_device_id mt9t001_id[] = {
    976	{ "mt9t001", 0 },
    977	{ }
    978};
    979MODULE_DEVICE_TABLE(i2c, mt9t001_id);
    980
    981static struct i2c_driver mt9t001_driver = {
    982	.driver = {
    983		.name = "mt9t001",
    984	},
    985	.probe		= mt9t001_probe,
    986	.remove		= mt9t001_remove,
    987	.id_table	= mt9t001_id,
    988};
    989
    990module_i2c_driver(mt9t001_driver);
    991
    992MODULE_DESCRIPTION("Aptina (Micron) MT9T001 Camera driver");
    993MODULE_AUTHOR("Laurent Pinchart <laurent.pinchart@ideasonboard.com>");
    994MODULE_LICENSE("GPL");