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

mt9m032.c (24815B)


      1// SPDX-License-Identifier: GPL-2.0-only
      2/*
      3 * Driver for MT9M032 CMOS Image Sensor from Micron
      4 *
      5 * Copyright (C) 2010-2011 Lund Engineering
      6 * Contact: Gil Lund <gwlund@lundeng.com>
      7 * Author: Martin Hostettler <martin@neutronstar.dyndns.org>
      8 */
      9
     10#include <linux/delay.h>
     11#include <linux/i2c.h>
     12#include <linux/init.h>
     13#include <linux/kernel.h>
     14#include <linux/math64.h>
     15#include <linux/module.h>
     16#include <linux/mutex.h>
     17#include <linux/slab.h>
     18#include <linux/v4l2-mediabus.h>
     19
     20#include <media/media-entity.h>
     21#include <media/i2c/mt9m032.h>
     22#include <media/v4l2-ctrls.h>
     23#include <media/v4l2-device.h>
     24#include <media/v4l2-subdev.h>
     25
     26#include "aptina-pll.h"
     27
     28/*
     29 * width and height include active boundary and black parts
     30 *
     31 * column    0-  15 active boundary
     32 * column   16-1455 image
     33 * column 1456-1471 active boundary
     34 * column 1472-1599 black
     35 *
     36 * row       0-  51 black
     37 * row      53-  59 active boundary
     38 * row      60-1139 image
     39 * row    1140-1147 active boundary
     40 * row    1148-1151 black
     41 */
     42
     43#define MT9M032_PIXEL_ARRAY_WIDTH			1600
     44#define MT9M032_PIXEL_ARRAY_HEIGHT			1152
     45
     46#define MT9M032_CHIP_VERSION				0x00
     47#define		MT9M032_CHIP_VERSION_VALUE		0x1402
     48#define MT9M032_ROW_START				0x01
     49#define		MT9M032_ROW_START_MIN			0
     50#define		MT9M032_ROW_START_MAX			1152
     51#define		MT9M032_ROW_START_DEF			60
     52#define MT9M032_COLUMN_START				0x02
     53#define		MT9M032_COLUMN_START_MIN		0
     54#define		MT9M032_COLUMN_START_MAX		1600
     55#define		MT9M032_COLUMN_START_DEF		16
     56#define MT9M032_ROW_SIZE				0x03
     57#define		MT9M032_ROW_SIZE_MIN			32
     58#define		MT9M032_ROW_SIZE_MAX			1152
     59#define		MT9M032_ROW_SIZE_DEF			1080
     60#define MT9M032_COLUMN_SIZE				0x04
     61#define		MT9M032_COLUMN_SIZE_MIN			32
     62#define		MT9M032_COLUMN_SIZE_MAX			1600
     63#define		MT9M032_COLUMN_SIZE_DEF			1440
     64#define MT9M032_HBLANK					0x05
     65#define MT9M032_VBLANK					0x06
     66#define		MT9M032_VBLANK_MAX			0x7ff
     67#define MT9M032_SHUTTER_WIDTH_HIGH			0x08
     68#define MT9M032_SHUTTER_WIDTH_LOW			0x09
     69#define		MT9M032_SHUTTER_WIDTH_MIN		1
     70#define		MT9M032_SHUTTER_WIDTH_MAX		1048575
     71#define		MT9M032_SHUTTER_WIDTH_DEF		1943
     72#define MT9M032_PIX_CLK_CTRL				0x0a
     73#define		MT9M032_PIX_CLK_CTRL_INV_PIXCLK		0x8000
     74#define MT9M032_RESTART					0x0b
     75#define MT9M032_RESET					0x0d
     76#define MT9M032_PLL_CONFIG1				0x11
     77#define		MT9M032_PLL_CONFIG1_PREDIV_MASK		0x3f
     78#define		MT9M032_PLL_CONFIG1_MUL_SHIFT		8
     79#define MT9M032_READ_MODE1				0x1e
     80#define		MT9M032_READ_MODE1_OUTPUT_BAD_FRAMES	(1 << 13)
     81#define		MT9M032_READ_MODE1_MAINTAIN_FRAME_RATE	(1 << 12)
     82#define		MT9M032_READ_MODE1_XOR_LINE_VALID	(1 << 11)
     83#define		MT9M032_READ_MODE1_CONT_LINE_VALID	(1 << 10)
     84#define		MT9M032_READ_MODE1_INVERT_TRIGGER	(1 << 9)
     85#define		MT9M032_READ_MODE1_SNAPSHOT		(1 << 8)
     86#define		MT9M032_READ_MODE1_GLOBAL_RESET		(1 << 7)
     87#define		MT9M032_READ_MODE1_BULB_EXPOSURE	(1 << 6)
     88#define		MT9M032_READ_MODE1_INVERT_STROBE	(1 << 5)
     89#define		MT9M032_READ_MODE1_STROBE_ENABLE	(1 << 4)
     90#define		MT9M032_READ_MODE1_STROBE_START_TRIG1	(0 << 2)
     91#define		MT9M032_READ_MODE1_STROBE_START_EXP	(1 << 2)
     92#define		MT9M032_READ_MODE1_STROBE_START_SHUTTER	(2 << 2)
     93#define		MT9M032_READ_MODE1_STROBE_START_TRIG2	(3 << 2)
     94#define		MT9M032_READ_MODE1_STROBE_END_TRIG1	(0 << 0)
     95#define		MT9M032_READ_MODE1_STROBE_END_EXP	(1 << 0)
     96#define		MT9M032_READ_MODE1_STROBE_END_SHUTTER	(2 << 0)
     97#define		MT9M032_READ_MODE1_STROBE_END_TRIG2	(3 << 0)
     98#define MT9M032_READ_MODE2				0x20
     99#define		MT9M032_READ_MODE2_VFLIP_SHIFT		15
    100#define		MT9M032_READ_MODE2_HFLIP_SHIFT		14
    101#define		MT9M032_READ_MODE2_ROW_BLC		0x40
    102#define MT9M032_GAIN_GREEN1				0x2b
    103#define MT9M032_GAIN_BLUE				0x2c
    104#define MT9M032_GAIN_RED				0x2d
    105#define MT9M032_GAIN_GREEN2				0x2e
    106
    107/* write only */
    108#define MT9M032_GAIN_ALL				0x35
    109#define		MT9M032_GAIN_DIGITAL_MASK		0x7f
    110#define		MT9M032_GAIN_DIGITAL_SHIFT		8
    111#define		MT9M032_GAIN_AMUL_SHIFT			6
    112#define		MT9M032_GAIN_ANALOG_MASK		0x3f
    113#define MT9M032_FORMATTER1				0x9e
    114#define		MT9M032_FORMATTER1_PLL_P1_6		(1 << 8)
    115#define		MT9M032_FORMATTER1_PARALLEL		(1 << 12)
    116#define MT9M032_FORMATTER2				0x9f
    117#define		MT9M032_FORMATTER2_DOUT_EN		0x1000
    118#define		MT9M032_FORMATTER2_PIXCLK_EN		0x2000
    119
    120/*
    121 * The available MT9M032 datasheet is missing documentation for register 0x10
    122 * MT9P031 seems to be close enough, so use constants from that datasheet for
    123 * now.
    124 * But keep the name MT9P031 to remind us, that this isn't really confirmed
    125 * for this sensor.
    126 */
    127#define MT9P031_PLL_CONTROL				0x10
    128#define		MT9P031_PLL_CONTROL_PWROFF		0x0050
    129#define		MT9P031_PLL_CONTROL_PWRON		0x0051
    130#define		MT9P031_PLL_CONTROL_USEPLL		0x0052
    131
    132struct mt9m032 {
    133	struct v4l2_subdev subdev;
    134	struct media_pad pad;
    135	struct mt9m032_platform_data *pdata;
    136
    137	unsigned int pix_clock;
    138
    139	struct v4l2_ctrl_handler ctrls;
    140	struct {
    141		struct v4l2_ctrl *hflip;
    142		struct v4l2_ctrl *vflip;
    143	};
    144
    145	struct mutex lock; /* Protects streaming, format, interval and crop */
    146
    147	bool streaming;
    148
    149	struct v4l2_mbus_framefmt format;
    150	struct v4l2_rect crop;
    151	struct v4l2_fract frame_interval;
    152};
    153
    154#define to_mt9m032(sd)	container_of(sd, struct mt9m032, subdev)
    155#define to_dev(sensor) \
    156	(&((struct i2c_client *)v4l2_get_subdevdata(&(sensor)->subdev))->dev)
    157
    158static int mt9m032_read(struct i2c_client *client, u8 reg)
    159{
    160	return i2c_smbus_read_word_swapped(client, reg);
    161}
    162
    163static int mt9m032_write(struct i2c_client *client, u8 reg, const u16 data)
    164{
    165	return i2c_smbus_write_word_swapped(client, reg, data);
    166}
    167
    168static u32 mt9m032_row_time(struct mt9m032 *sensor, unsigned int width)
    169{
    170	unsigned int effective_width;
    171	u32 ns;
    172
    173	effective_width = width + 716; /* empirical value */
    174	ns = div_u64(1000000000ULL * effective_width, sensor->pix_clock);
    175	dev_dbg(to_dev(sensor),	"MT9M032 line time: %u ns\n", ns);
    176	return ns;
    177}
    178
    179static int mt9m032_update_timing(struct mt9m032 *sensor,
    180				 struct v4l2_fract *interval)
    181{
    182	struct i2c_client *client = v4l2_get_subdevdata(&sensor->subdev);
    183	struct v4l2_rect *crop = &sensor->crop;
    184	unsigned int min_vblank;
    185	unsigned int vblank;
    186	u32 row_time;
    187
    188	if (!interval)
    189		interval = &sensor->frame_interval;
    190
    191	row_time = mt9m032_row_time(sensor, crop->width);
    192
    193	vblank = div_u64(1000000000ULL * interval->numerator,
    194			 (u64)row_time * interval->denominator)
    195	       - crop->height;
    196
    197	if (vblank > MT9M032_VBLANK_MAX) {
    198		/* hardware limits to 11 bit values */
    199		interval->denominator = 1000;
    200		interval->numerator =
    201			div_u64((crop->height + MT9M032_VBLANK_MAX) *
    202				(u64)row_time * interval->denominator,
    203				1000000000ULL);
    204		vblank = div_u64(1000000000ULL * interval->numerator,
    205				 (u64)row_time * interval->denominator)
    206		       - crop->height;
    207	}
    208	/* enforce minimal 1.6ms blanking time. */
    209	min_vblank = 1600000 / row_time;
    210	vblank = clamp_t(unsigned int, vblank, min_vblank, MT9M032_VBLANK_MAX);
    211
    212	return mt9m032_write(client, MT9M032_VBLANK, vblank);
    213}
    214
    215static int mt9m032_update_geom_timing(struct mt9m032 *sensor)
    216{
    217	struct i2c_client *client = v4l2_get_subdevdata(&sensor->subdev);
    218	int ret;
    219
    220	ret = mt9m032_write(client, MT9M032_COLUMN_SIZE,
    221			    sensor->crop.width - 1);
    222	if (!ret)
    223		ret = mt9m032_write(client, MT9M032_ROW_SIZE,
    224				    sensor->crop.height - 1);
    225	if (!ret)
    226		ret = mt9m032_write(client, MT9M032_COLUMN_START,
    227				    sensor->crop.left);
    228	if (!ret)
    229		ret = mt9m032_write(client, MT9M032_ROW_START,
    230				    sensor->crop.top);
    231	if (!ret)
    232		ret = mt9m032_update_timing(sensor, NULL);
    233	return ret;
    234}
    235
    236static int update_formatter2(struct mt9m032 *sensor, bool streaming)
    237{
    238	struct i2c_client *client = v4l2_get_subdevdata(&sensor->subdev);
    239	u16 reg_val =   MT9M032_FORMATTER2_DOUT_EN
    240		      | 0x0070;  /* parts reserved! */
    241				 /* possibly for changing to 14-bit mode */
    242
    243	if (streaming)
    244		reg_val |= MT9M032_FORMATTER2_PIXCLK_EN;   /* pixclock enable */
    245
    246	return mt9m032_write(client, MT9M032_FORMATTER2, reg_val);
    247}
    248
    249static int mt9m032_setup_pll(struct mt9m032 *sensor)
    250{
    251	static const struct aptina_pll_limits limits = {
    252		.ext_clock_min = 8000000,
    253		.ext_clock_max = 16500000,
    254		.int_clock_min = 2000000,
    255		.int_clock_max = 24000000,
    256		.out_clock_min = 322000000,
    257		.out_clock_max = 693000000,
    258		.pix_clock_max = 99000000,
    259		.n_min = 1,
    260		.n_max = 64,
    261		.m_min = 16,
    262		.m_max = 255,
    263		.p1_min = 6,
    264		.p1_max = 7,
    265	};
    266
    267	struct i2c_client *client = v4l2_get_subdevdata(&sensor->subdev);
    268	struct mt9m032_platform_data *pdata = sensor->pdata;
    269	struct aptina_pll pll;
    270	u16 reg_val;
    271	int ret;
    272
    273	pll.ext_clock = pdata->ext_clock;
    274	pll.pix_clock = pdata->pix_clock;
    275
    276	ret = aptina_pll_calculate(&client->dev, &limits, &pll);
    277	if (ret < 0)
    278		return ret;
    279
    280	sensor->pix_clock = pdata->pix_clock;
    281
    282	ret = mt9m032_write(client, MT9M032_PLL_CONFIG1,
    283			    (pll.m << MT9M032_PLL_CONFIG1_MUL_SHIFT) |
    284			    ((pll.n - 1) & MT9M032_PLL_CONFIG1_PREDIV_MASK));
    285	if (!ret)
    286		ret = mt9m032_write(client, MT9P031_PLL_CONTROL,
    287				    MT9P031_PLL_CONTROL_PWRON |
    288				    MT9P031_PLL_CONTROL_USEPLL);
    289	if (!ret)		/* more reserved, Continuous, Master Mode */
    290		ret = mt9m032_write(client, MT9M032_READ_MODE1, 0x8000 |
    291				    MT9M032_READ_MODE1_STROBE_START_EXP |
    292				    MT9M032_READ_MODE1_STROBE_END_SHUTTER);
    293	if (!ret) {
    294		reg_val = (pll.p1 == 6 ? MT9M032_FORMATTER1_PLL_P1_6 : 0)
    295			| MT9M032_FORMATTER1_PARALLEL | 0x001e; /* 14-bit */
    296		ret = mt9m032_write(client, MT9M032_FORMATTER1, reg_val);
    297	}
    298
    299	return ret;
    300}
    301
    302/* -----------------------------------------------------------------------------
    303 * Subdev pad operations
    304 */
    305
    306static int mt9m032_enum_mbus_code(struct v4l2_subdev *subdev,
    307				  struct v4l2_subdev_state *sd_state,
    308				  struct v4l2_subdev_mbus_code_enum *code)
    309{
    310	if (code->index != 0)
    311		return -EINVAL;
    312
    313	code->code = MEDIA_BUS_FMT_Y8_1X8;
    314	return 0;
    315}
    316
    317static int mt9m032_enum_frame_size(struct v4l2_subdev *subdev,
    318				   struct v4l2_subdev_state *sd_state,
    319				   struct v4l2_subdev_frame_size_enum *fse)
    320{
    321	if (fse->index != 0 || fse->code != MEDIA_BUS_FMT_Y8_1X8)
    322		return -EINVAL;
    323
    324	fse->min_width = MT9M032_COLUMN_SIZE_DEF;
    325	fse->max_width = MT9M032_COLUMN_SIZE_DEF;
    326	fse->min_height = MT9M032_ROW_SIZE_DEF;
    327	fse->max_height = MT9M032_ROW_SIZE_DEF;
    328
    329	return 0;
    330}
    331
    332/**
    333 * __mt9m032_get_pad_crop() - get crop rect
    334 * @sensor: pointer to the sensor struct
    335 * @sd_state: v4l2_subdev_state for getting the try crop rect from
    336 * @which: select try or active crop rect
    337 *
    338 * Returns a pointer the current active or fh relative try crop rect
    339 */
    340static struct v4l2_rect *
    341__mt9m032_get_pad_crop(struct mt9m032 *sensor,
    342		       struct v4l2_subdev_state *sd_state,
    343		       enum v4l2_subdev_format_whence which)
    344{
    345	switch (which) {
    346	case V4L2_SUBDEV_FORMAT_TRY:
    347		return v4l2_subdev_get_try_crop(&sensor->subdev, sd_state, 0);
    348	case V4L2_SUBDEV_FORMAT_ACTIVE:
    349		return &sensor->crop;
    350	default:
    351		return NULL;
    352	}
    353}
    354
    355/**
    356 * __mt9m032_get_pad_format() - get format
    357 * @sensor: pointer to the sensor struct
    358 * @sd_state: v4l2_subdev_state for getting the try format from
    359 * @which: select try or active format
    360 *
    361 * Returns a pointer the current active or fh relative try format
    362 */
    363static struct v4l2_mbus_framefmt *
    364__mt9m032_get_pad_format(struct mt9m032 *sensor,
    365			 struct v4l2_subdev_state *sd_state,
    366			 enum v4l2_subdev_format_whence which)
    367{
    368	switch (which) {
    369	case V4L2_SUBDEV_FORMAT_TRY:
    370		return v4l2_subdev_get_try_format(&sensor->subdev, sd_state,
    371						  0);
    372	case V4L2_SUBDEV_FORMAT_ACTIVE:
    373		return &sensor->format;
    374	default:
    375		return NULL;
    376	}
    377}
    378
    379static int mt9m032_get_pad_format(struct v4l2_subdev *subdev,
    380				  struct v4l2_subdev_state *sd_state,
    381				  struct v4l2_subdev_format *fmt)
    382{
    383	struct mt9m032 *sensor = to_mt9m032(subdev);
    384
    385	mutex_lock(&sensor->lock);
    386	fmt->format = *__mt9m032_get_pad_format(sensor, sd_state, fmt->which);
    387	mutex_unlock(&sensor->lock);
    388
    389	return 0;
    390}
    391
    392static int mt9m032_set_pad_format(struct v4l2_subdev *subdev,
    393				  struct v4l2_subdev_state *sd_state,
    394				  struct v4l2_subdev_format *fmt)
    395{
    396	struct mt9m032 *sensor = to_mt9m032(subdev);
    397	int ret;
    398
    399	mutex_lock(&sensor->lock);
    400
    401	if (sensor->streaming && fmt->which == V4L2_SUBDEV_FORMAT_ACTIVE) {
    402		ret = -EBUSY;
    403		goto done;
    404	}
    405
    406	/* Scaling is not supported, the format is thus fixed. */
    407	fmt->format = *__mt9m032_get_pad_format(sensor, sd_state, fmt->which);
    408	ret = 0;
    409
    410done:
    411	mutex_unlock(&sensor->lock);
    412	return ret;
    413}
    414
    415static int mt9m032_get_pad_selection(struct v4l2_subdev *subdev,
    416				     struct v4l2_subdev_state *sd_state,
    417				     struct v4l2_subdev_selection *sel)
    418{
    419	struct mt9m032 *sensor = to_mt9m032(subdev);
    420
    421	if (sel->target != V4L2_SEL_TGT_CROP)
    422		return -EINVAL;
    423
    424	mutex_lock(&sensor->lock);
    425	sel->r = *__mt9m032_get_pad_crop(sensor, sd_state, sel->which);
    426	mutex_unlock(&sensor->lock);
    427
    428	return 0;
    429}
    430
    431static int mt9m032_set_pad_selection(struct v4l2_subdev *subdev,
    432				     struct v4l2_subdev_state *sd_state,
    433				     struct v4l2_subdev_selection *sel)
    434{
    435	struct mt9m032 *sensor = to_mt9m032(subdev);
    436	struct v4l2_mbus_framefmt *format;
    437	struct v4l2_rect *__crop;
    438	struct v4l2_rect rect;
    439	int ret = 0;
    440
    441	if (sel->target != V4L2_SEL_TGT_CROP)
    442		return -EINVAL;
    443
    444	mutex_lock(&sensor->lock);
    445
    446	if (sensor->streaming && sel->which == V4L2_SUBDEV_FORMAT_ACTIVE) {
    447		ret = -EBUSY;
    448		goto done;
    449	}
    450
    451	/* Clamp the crop rectangle boundaries and align them to a multiple of 2
    452	 * pixels to ensure a GRBG Bayer pattern.
    453	 */
    454	rect.left = clamp(ALIGN(sel->r.left, 2), MT9M032_COLUMN_START_MIN,
    455			  MT9M032_COLUMN_START_MAX);
    456	rect.top = clamp(ALIGN(sel->r.top, 2), MT9M032_ROW_START_MIN,
    457			 MT9M032_ROW_START_MAX);
    458	rect.width = clamp_t(unsigned int, ALIGN(sel->r.width, 2),
    459			     MT9M032_COLUMN_SIZE_MIN, MT9M032_COLUMN_SIZE_MAX);
    460	rect.height = clamp_t(unsigned int, ALIGN(sel->r.height, 2),
    461			      MT9M032_ROW_SIZE_MIN, MT9M032_ROW_SIZE_MAX);
    462
    463	rect.width = min_t(unsigned int, rect.width,
    464			   MT9M032_PIXEL_ARRAY_WIDTH - rect.left);
    465	rect.height = min_t(unsigned int, rect.height,
    466			    MT9M032_PIXEL_ARRAY_HEIGHT - rect.top);
    467
    468	__crop = __mt9m032_get_pad_crop(sensor, sd_state, sel->which);
    469
    470	if (rect.width != __crop->width || rect.height != __crop->height) {
    471		/* Reset the output image size if the crop rectangle size has
    472		 * been modified.
    473		 */
    474		format = __mt9m032_get_pad_format(sensor, sd_state,
    475						  sel->which);
    476		format->width = rect.width;
    477		format->height = rect.height;
    478	}
    479
    480	*__crop = rect;
    481	sel->r = rect;
    482
    483	if (sel->which == V4L2_SUBDEV_FORMAT_ACTIVE)
    484		ret = mt9m032_update_geom_timing(sensor);
    485
    486done:
    487	mutex_unlock(&sensor->lock);
    488	return ret;
    489}
    490
    491static int mt9m032_get_frame_interval(struct v4l2_subdev *subdev,
    492				      struct v4l2_subdev_frame_interval *fi)
    493{
    494	struct mt9m032 *sensor = to_mt9m032(subdev);
    495
    496	mutex_lock(&sensor->lock);
    497	memset(fi, 0, sizeof(*fi));
    498	fi->interval = sensor->frame_interval;
    499	mutex_unlock(&sensor->lock);
    500
    501	return 0;
    502}
    503
    504static int mt9m032_set_frame_interval(struct v4l2_subdev *subdev,
    505				      struct v4l2_subdev_frame_interval *fi)
    506{
    507	struct mt9m032 *sensor = to_mt9m032(subdev);
    508	int ret;
    509
    510	mutex_lock(&sensor->lock);
    511
    512	if (sensor->streaming) {
    513		ret = -EBUSY;
    514		goto done;
    515	}
    516
    517	/* Avoid divisions by 0. */
    518	if (fi->interval.denominator == 0)
    519		fi->interval.denominator = 1;
    520
    521	ret = mt9m032_update_timing(sensor, &fi->interval);
    522	if (!ret)
    523		sensor->frame_interval = fi->interval;
    524
    525done:
    526	mutex_unlock(&sensor->lock);
    527	return ret;
    528}
    529
    530static int mt9m032_s_stream(struct v4l2_subdev *subdev, int streaming)
    531{
    532	struct mt9m032 *sensor = to_mt9m032(subdev);
    533	int ret;
    534
    535	mutex_lock(&sensor->lock);
    536	ret = update_formatter2(sensor, streaming);
    537	if (!ret)
    538		sensor->streaming = streaming;
    539	mutex_unlock(&sensor->lock);
    540
    541	return ret;
    542}
    543
    544/* -----------------------------------------------------------------------------
    545 * V4L2 subdev core operations
    546 */
    547
    548#ifdef CONFIG_VIDEO_ADV_DEBUG
    549static int mt9m032_g_register(struct v4l2_subdev *sd,
    550			      struct v4l2_dbg_register *reg)
    551{
    552	struct mt9m032 *sensor = to_mt9m032(sd);
    553	struct i2c_client *client = v4l2_get_subdevdata(&sensor->subdev);
    554	int val;
    555
    556	if (reg->reg > 0xff)
    557		return -EINVAL;
    558
    559	val = mt9m032_read(client, reg->reg);
    560	if (val < 0)
    561		return -EIO;
    562
    563	reg->size = 2;
    564	reg->val = val;
    565
    566	return 0;
    567}
    568
    569static int mt9m032_s_register(struct v4l2_subdev *sd,
    570			      const struct v4l2_dbg_register *reg)
    571{
    572	struct mt9m032 *sensor = to_mt9m032(sd);
    573	struct i2c_client *client = v4l2_get_subdevdata(&sensor->subdev);
    574
    575	if (reg->reg > 0xff)
    576		return -EINVAL;
    577
    578	return mt9m032_write(client, reg->reg, reg->val);
    579}
    580#endif
    581
    582/* -----------------------------------------------------------------------------
    583 * V4L2 subdev control operations
    584 */
    585
    586static int update_read_mode2(struct mt9m032 *sensor, bool vflip, bool hflip)
    587{
    588	struct i2c_client *client = v4l2_get_subdevdata(&sensor->subdev);
    589	int reg_val = (vflip << MT9M032_READ_MODE2_VFLIP_SHIFT)
    590		    | (hflip << MT9M032_READ_MODE2_HFLIP_SHIFT)
    591		    | MT9M032_READ_MODE2_ROW_BLC
    592		    | 0x0007;
    593
    594	return mt9m032_write(client, MT9M032_READ_MODE2, reg_val);
    595}
    596
    597static int mt9m032_set_gain(struct mt9m032 *sensor, s32 val)
    598{
    599	struct i2c_client *client = v4l2_get_subdevdata(&sensor->subdev);
    600	int digital_gain_val;	/* in 1/8th (0..127) */
    601	int analog_mul;		/* 0 or 1 */
    602	int analog_gain_val;	/* in 1/16th. (0..63) */
    603	u16 reg_val;
    604
    605	digital_gain_val = 51; /* from setup example */
    606
    607	if (val < 63) {
    608		analog_mul = 0;
    609		analog_gain_val = val;
    610	} else {
    611		analog_mul = 1;
    612		analog_gain_val = val / 2;
    613	}
    614
    615	/* a_gain = (1 + analog_mul) + (analog_gain_val + 1) / 16 */
    616	/* overall_gain = a_gain * (1 + digital_gain_val / 8) */
    617
    618	reg_val = ((digital_gain_val & MT9M032_GAIN_DIGITAL_MASK)
    619		   << MT9M032_GAIN_DIGITAL_SHIFT)
    620		| ((analog_mul & 1) << MT9M032_GAIN_AMUL_SHIFT)
    621		| (analog_gain_val & MT9M032_GAIN_ANALOG_MASK);
    622
    623	return mt9m032_write(client, MT9M032_GAIN_ALL, reg_val);
    624}
    625
    626static int mt9m032_try_ctrl(struct v4l2_ctrl *ctrl)
    627{
    628	if (ctrl->id == V4L2_CID_GAIN && ctrl->val >= 63) {
    629		/* round because of multiplier used for values >= 63 */
    630		ctrl->val &= ~1;
    631	}
    632
    633	return 0;
    634}
    635
    636static int mt9m032_set_ctrl(struct v4l2_ctrl *ctrl)
    637{
    638	struct mt9m032 *sensor =
    639		container_of(ctrl->handler, struct mt9m032, ctrls);
    640	struct i2c_client *client = v4l2_get_subdevdata(&sensor->subdev);
    641	int ret;
    642
    643	switch (ctrl->id) {
    644	case V4L2_CID_GAIN:
    645		return mt9m032_set_gain(sensor, ctrl->val);
    646
    647	case V4L2_CID_HFLIP:
    648	/* case V4L2_CID_VFLIP: -- In the same cluster */
    649		return update_read_mode2(sensor, sensor->vflip->val,
    650					 sensor->hflip->val);
    651
    652	case V4L2_CID_EXPOSURE:
    653		ret = mt9m032_write(client, MT9M032_SHUTTER_WIDTH_HIGH,
    654				    (ctrl->val >> 16) & 0xffff);
    655		if (ret < 0)
    656			return ret;
    657
    658		return mt9m032_write(client, MT9M032_SHUTTER_WIDTH_LOW,
    659				     ctrl->val & 0xffff);
    660	}
    661
    662	return 0;
    663}
    664
    665static const struct v4l2_ctrl_ops mt9m032_ctrl_ops = {
    666	.s_ctrl = mt9m032_set_ctrl,
    667	.try_ctrl = mt9m032_try_ctrl,
    668};
    669
    670/* -------------------------------------------------------------------------- */
    671
    672static const struct v4l2_subdev_core_ops mt9m032_core_ops = {
    673#ifdef CONFIG_VIDEO_ADV_DEBUG
    674	.g_register = mt9m032_g_register,
    675	.s_register = mt9m032_s_register,
    676#endif
    677};
    678
    679static const struct v4l2_subdev_video_ops mt9m032_video_ops = {
    680	.s_stream = mt9m032_s_stream,
    681	.g_frame_interval = mt9m032_get_frame_interval,
    682	.s_frame_interval = mt9m032_set_frame_interval,
    683};
    684
    685static const struct v4l2_subdev_pad_ops mt9m032_pad_ops = {
    686	.enum_mbus_code = mt9m032_enum_mbus_code,
    687	.enum_frame_size = mt9m032_enum_frame_size,
    688	.get_fmt = mt9m032_get_pad_format,
    689	.set_fmt = mt9m032_set_pad_format,
    690	.set_selection = mt9m032_set_pad_selection,
    691	.get_selection = mt9m032_get_pad_selection,
    692};
    693
    694static const struct v4l2_subdev_ops mt9m032_ops = {
    695	.core = &mt9m032_core_ops,
    696	.video = &mt9m032_video_ops,
    697	.pad = &mt9m032_pad_ops,
    698};
    699
    700/* -----------------------------------------------------------------------------
    701 * Driver initialization and probing
    702 */
    703
    704static int mt9m032_probe(struct i2c_client *client,
    705			 const struct i2c_device_id *devid)
    706{
    707	struct mt9m032_platform_data *pdata = client->dev.platform_data;
    708	struct i2c_adapter *adapter = client->adapter;
    709	struct mt9m032 *sensor;
    710	int chip_version;
    711	int ret;
    712
    713	if (pdata == NULL) {
    714		dev_err(&client->dev, "No platform data\n");
    715		return -EINVAL;
    716	}
    717
    718	if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_WORD_DATA)) {
    719		dev_warn(&client->dev,
    720			 "I2C-Adapter doesn't support I2C_FUNC_SMBUS_WORD\n");
    721		return -EIO;
    722	}
    723
    724	if (!client->dev.platform_data)
    725		return -ENODEV;
    726
    727	sensor = devm_kzalloc(&client->dev, sizeof(*sensor), GFP_KERNEL);
    728	if (sensor == NULL)
    729		return -ENOMEM;
    730
    731	mutex_init(&sensor->lock);
    732
    733	sensor->pdata = pdata;
    734
    735	v4l2_i2c_subdev_init(&sensor->subdev, client, &mt9m032_ops);
    736	sensor->subdev.flags |= V4L2_SUBDEV_FL_HAS_DEVNODE;
    737
    738	chip_version = mt9m032_read(client, MT9M032_CHIP_VERSION);
    739	if (chip_version != MT9M032_CHIP_VERSION_VALUE) {
    740		dev_err(&client->dev, "MT9M032 not detected, wrong version "
    741			"0x%04x\n", chip_version);
    742		ret = -ENODEV;
    743		goto error_sensor;
    744	}
    745
    746	dev_info(&client->dev, "MT9M032 detected at address 0x%02x\n",
    747		 client->addr);
    748
    749	sensor->frame_interval.numerator = 1;
    750	sensor->frame_interval.denominator = 30;
    751
    752	sensor->crop.left = MT9M032_COLUMN_START_DEF;
    753	sensor->crop.top = MT9M032_ROW_START_DEF;
    754	sensor->crop.width = MT9M032_COLUMN_SIZE_DEF;
    755	sensor->crop.height = MT9M032_ROW_SIZE_DEF;
    756
    757	sensor->format.width = sensor->crop.width;
    758	sensor->format.height = sensor->crop.height;
    759	sensor->format.code = MEDIA_BUS_FMT_Y8_1X8;
    760	sensor->format.field = V4L2_FIELD_NONE;
    761	sensor->format.colorspace = V4L2_COLORSPACE_SRGB;
    762
    763	v4l2_ctrl_handler_init(&sensor->ctrls, 5);
    764
    765	v4l2_ctrl_new_std(&sensor->ctrls, &mt9m032_ctrl_ops,
    766			  V4L2_CID_GAIN, 0, 127, 1, 64);
    767
    768	sensor->hflip = v4l2_ctrl_new_std(&sensor->ctrls,
    769					  &mt9m032_ctrl_ops,
    770					  V4L2_CID_HFLIP, 0, 1, 1, 0);
    771	sensor->vflip = v4l2_ctrl_new_std(&sensor->ctrls,
    772					  &mt9m032_ctrl_ops,
    773					  V4L2_CID_VFLIP, 0, 1, 1, 0);
    774
    775	v4l2_ctrl_new_std(&sensor->ctrls, &mt9m032_ctrl_ops,
    776			  V4L2_CID_EXPOSURE, MT9M032_SHUTTER_WIDTH_MIN,
    777			  MT9M032_SHUTTER_WIDTH_MAX, 1,
    778			  MT9M032_SHUTTER_WIDTH_DEF);
    779	v4l2_ctrl_new_std(&sensor->ctrls, &mt9m032_ctrl_ops,
    780			  V4L2_CID_PIXEL_RATE, pdata->pix_clock,
    781			  pdata->pix_clock, 1, pdata->pix_clock);
    782
    783	if (sensor->ctrls.error) {
    784		ret = sensor->ctrls.error;
    785		dev_err(&client->dev, "control initialization error %d\n", ret);
    786		goto error_ctrl;
    787	}
    788
    789	v4l2_ctrl_cluster(2, &sensor->hflip);
    790
    791	sensor->subdev.ctrl_handler = &sensor->ctrls;
    792	sensor->subdev.entity.function = MEDIA_ENT_F_CAM_SENSOR;
    793	sensor->pad.flags = MEDIA_PAD_FL_SOURCE;
    794	ret = media_entity_pads_init(&sensor->subdev.entity, 1, &sensor->pad);
    795	if (ret < 0)
    796		goto error_ctrl;
    797
    798	ret = mt9m032_write(client, MT9M032_RESET, 1);	/* reset on */
    799	if (ret < 0)
    800		goto error_entity;
    801	ret = mt9m032_write(client, MT9M032_RESET, 0);	/* reset off */
    802	if (ret < 0)
    803		goto error_entity;
    804
    805	ret = mt9m032_setup_pll(sensor);
    806	if (ret < 0)
    807		goto error_entity;
    808	usleep_range(10000, 11000);
    809
    810	ret = v4l2_ctrl_handler_setup(&sensor->ctrls);
    811	if (ret < 0)
    812		goto error_entity;
    813
    814	/* SIZE */
    815	ret = mt9m032_update_geom_timing(sensor);
    816	if (ret < 0)
    817		goto error_entity;
    818
    819	ret = mt9m032_write(client, 0x41, 0x0000);	/* reserved !!! */
    820	if (ret < 0)
    821		goto error_entity;
    822	ret = mt9m032_write(client, 0x42, 0x0003);	/* reserved !!! */
    823	if (ret < 0)
    824		goto error_entity;
    825	ret = mt9m032_write(client, 0x43, 0x0003);	/* reserved !!! */
    826	if (ret < 0)
    827		goto error_entity;
    828	ret = mt9m032_write(client, 0x7f, 0x0000);	/* reserved !!! */
    829	if (ret < 0)
    830		goto error_entity;
    831	if (sensor->pdata->invert_pixclock) {
    832		ret = mt9m032_write(client, MT9M032_PIX_CLK_CTRL,
    833				    MT9M032_PIX_CLK_CTRL_INV_PIXCLK);
    834		if (ret < 0)
    835			goto error_entity;
    836	}
    837
    838	ret = mt9m032_write(client, MT9M032_RESTART, 1); /* Restart on */
    839	if (ret < 0)
    840		goto error_entity;
    841	msleep(100);
    842	ret = mt9m032_write(client, MT9M032_RESTART, 0); /* Restart off */
    843	if (ret < 0)
    844		goto error_entity;
    845	msleep(100);
    846	ret = update_formatter2(sensor, false);
    847	if (ret < 0)
    848		goto error_entity;
    849
    850	return ret;
    851
    852error_entity:
    853	media_entity_cleanup(&sensor->subdev.entity);
    854error_ctrl:
    855	v4l2_ctrl_handler_free(&sensor->ctrls);
    856error_sensor:
    857	mutex_destroy(&sensor->lock);
    858	return ret;
    859}
    860
    861static int mt9m032_remove(struct i2c_client *client)
    862{
    863	struct v4l2_subdev *subdev = i2c_get_clientdata(client);
    864	struct mt9m032 *sensor = to_mt9m032(subdev);
    865
    866	v4l2_device_unregister_subdev(subdev);
    867	v4l2_ctrl_handler_free(&sensor->ctrls);
    868	media_entity_cleanup(&subdev->entity);
    869	mutex_destroy(&sensor->lock);
    870	return 0;
    871}
    872
    873static const struct i2c_device_id mt9m032_id_table[] = {
    874	{ MT9M032_NAME, 0 },
    875	{ }
    876};
    877
    878MODULE_DEVICE_TABLE(i2c, mt9m032_id_table);
    879
    880static struct i2c_driver mt9m032_i2c_driver = {
    881	.driver = {
    882		.name = MT9M032_NAME,
    883	},
    884	.probe = mt9m032_probe,
    885	.remove = mt9m032_remove,
    886	.id_table = mt9m032_id_table,
    887};
    888
    889module_i2c_driver(mt9m032_i2c_driver);
    890
    891MODULE_AUTHOR("Martin Hostettler <martin@neutronstar.dyndns.org>");
    892MODULE_DESCRIPTION("MT9M032 camera sensor driver");
    893MODULE_LICENSE("GPL v2");