/* OmniVision OV6620/OV6120 Camera Chip Support Code
 *
 * Copyright (c) 1999-2004 Mark McClelland <mark@alpha.dyndns.org>
 * http://alpha.dyndns.org/ov511/
 *
 * This program is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License as published by the
 * Free Software Foundation; either version 2 of the License, or (at your
 * option) any later version. NO WARRANTY OF ANY KIND is expressed or implied.
 */

#define DEBUG

#include <linux/slab.h>
#include "ovcamchip_priv.h"

/* Registers */
#define REG_GAIN		0x00	/* gain [5:0] */
#define REG_BLUE		0x01	/* blue gain */
#define REG_RED			0x02	/* red gain */
#define REG_SAT			0x03	/* saturation */
#define REG_CNT			0x05	/* Y contrast */
#define REG_BRT			0x06	/* Y brightness */
#define REG_WB_BLUE		0x0C	/* WB blue ratio [5:0] */
#define REG_WB_RED		0x0D	/* WB red ratio [5:0] */
#define REG_EXP			0x10	/* exposure */

/* Window parameters */
#define HWSBASE 0x38
#define HWEBASE 0x3A
#define VWSBASE 0x05
#define VWEBASE 0x06

struct ov6x20 {
	int auto_brt;
	int auto_exp;
	int backlight;
	int bandfilt;
	int mirror;
};

/* Initial values for use with OV511/OV511+ cameras */
static struct ovcamchip_regvals regvals_init_6x20_511[] = {
	{ 0x12, 0x80 }, /* reset */
	{ 0x11, 0x01 },
	{ 0x03, 0x60 },
	{ 0x05, 0x7f }, /* For when autoadjust is off */
	{ 0x07, 0xa8 },
	{ 0x0c, 0x24 },
	{ 0x0d, 0x24 },
	{ 0x0f, 0x15 }, /* COMS */
	{ 0x10, 0x75 }, /* AEC Exposure time */
	{ 0x12, 0x24 }, /* Enable AGC and AWB */
	{ 0x14, 0x04 },
	{ 0x16, 0x03 },
	{ 0x26, 0xb2 }, /* BLC enable */
	/* 0x28: 0x05 Selects RGB format if RGB on */
	{ 0x28, 0x05 },
	{ 0x2a, 0x04 }, /* Disable framerate adjust */
	{ 0x2d, 0x99 },
	{ 0x33, 0xa0 }, /* Color Processing Parameter */
	{ 0x34, 0xd2 }, /* Max A/D range */
	{ 0x38, 0x8b },
	{ 0x39, 0x40 },

	{ 0x3c, 0x39 }, /* Enable AEC mode changing */
	{ 0x3c, 0x3c }, /* Change AEC mode */
	{ 0x3c, 0x24 }, /* Disable AEC mode changing */

	{ 0x3d, 0x80 },
	/* These next two registers (0x4a, 0x4b) are undocumented. They
	 * control the color balance */
	{ 0x4a, 0x80 },
	{ 0x4b, 0x80 },
	{ 0x4d, 0xd2 }, /* This reduces noise a bit */
	{ 0x4e, 0xc1 },
	{ 0x4f, 0x04 },
	{ 0xff, 0xff },	/* END MARKER */
};

/* Initial values for use with OV518 cameras */
static struct ovcamchip_regvals regvals_init_6x20_518[] = {
	{ 0x12, 0x80 }, /* Do a reset */
	{ 0x03, 0xc0 }, /* Saturation */
	{ 0x05, 0x8a }, /* Contrast */
	{ 0x0c, 0x24 }, /* AWB blue */
	{ 0x0d, 0x24 }, /* AWB red */
	{ 0x0e, 0x8d }, /* Additional 2x gain */
	{ 0x0f, 0x25 }, /* Black expanding level = 1.3V */
	{ 0x11, 0x01 }, /* Clock div. */
	{ 0x12, 0x24 }, /* Enable AGC and AWB */
	{ 0x13, 0x01 }, /* (default) */
	{ 0x14, 0x80 }, /* Set reserved bit 7 */
	{ 0x15, 0x01 }, /* (default) */
	{ 0x16, 0x03 }, /* (default) */
	{ 0x17, 0x38 }, /* (default) */
	{ 0x18, 0xea }, /* (default) */
	{ 0x19, 0x04 },
	{ 0x1a, 0x93 },
	{ 0x1b, 0x00 }, /* (default) */
	{ 0x1e, 0xc4 }, /* (default) */
	{ 0x1f, 0x04 }, /* (default) */
	{ 0x20, 0x20 }, /* Enable 1st stage aperture correction */
	{ 0x21, 0x10 }, /* Y offset */
	{ 0x22, 0x88 }, /* U offset */
	{ 0x23, 0xc0 }, /* Set XTAL power level */
	{ 0x24, 0x53 }, /* AEC bright ratio */
	{ 0x25, 0x7a }, /* AEC black ratio */
	{ 0x26, 0xb2 }, /* BLC enable */
	{ 0x27, 0xa2 }, /* Full output range */
	{ 0x28, 0x01 }, /* (default) */
	{ 0x29, 0x00 }, /* (default) */
	{ 0x2a, 0x84 }, /* (default) */
	{ 0x2b, 0xa8 }, /* Set custom frame rate */
	{ 0x2c, 0xa0 }, /* (reserved) */
	{ 0x2d, 0x95 }, /* Enable banding filter */
	{ 0x2e, 0x88 }, /* V offset */
	{ 0x33, 0x22 }, /* Luminance gamma on */
	{ 0x34, 0xc7 }, /* A/D bias */
	{ 0x36, 0x12 }, /* (reserved) */
	{ 0x37, 0x63 }, /* (reserved) */
	{ 0x38, 0x8b }, /* Quick AEC/AEB */
	{ 0x39, 0x00 }, /* (default) */
	{ 0x3a, 0x0f }, /* (default) */
	{ 0x3b, 0x3c }, /* (default) */
	{ 0x3c, 0x5c }, /* AEC controls */
	{ 0x3d, 0x80 }, /* Drop 1 (bad) frame when AEC change */
	{ 0x3e, 0x80 }, /* (default) */
	{ 0x3f, 0x02 }, /* (default) */
	{ 0x40, 0x10 }, /* (reserved) */
	{ 0x41, 0x10 }, /* (reserved) */
	{ 0x42, 0x00 }, /* (reserved) */
	{ 0x43, 0x7f }, /* (reserved) */
	{ 0x44, 0x80 }, /* (reserved) */
	{ 0x45, 0x1c }, /* (reserved) */
	{ 0x46, 0x1c }, /* (reserved) */
	{ 0x47, 0x80 }, /* (reserved) */
	{ 0x48, 0x5f }, /* (reserved) */
	{ 0x49, 0x00 }, /* (reserved) */
	{ 0x4a, 0x00 }, /* Color balance (undocumented) */
	{ 0x4b, 0x80 }, /* Color balance (undocumented) */
	{ 0x4c, 0x58 }, /* (reserved) */
	{ 0x4d, 0xd2 }, /* U *= .938, V *= .838 */
	{ 0x4e, 0xa0 }, /* (default) */
	{ 0x4f, 0x04 }, /* UV 3-point average */
	{ 0x50, 0xff }, /* (reserved) */
	{ 0x51, 0x58 }, /* (reserved) */
	{ 0x52, 0xc0 }, /* (reserved) */
	{ 0x53, 0x42 }, /* (reserved) */
	{ 0x27, 0xa6 }, /* Enable manual offset adj. (reg 21 & 22) */
	{ 0x12, 0x20 },
	{ 0x12, 0x24 },

	{ 0xff, 0xff },	/* END MARKER */
};

/* This initializes the OV6x20 camera chip and relevant variables. */
static int ov6x20_init(struct i2c_client *c)
{
	struct ovcamchip *ov = i2c_get_clientdata(c);
	struct ov6x20 *s;
	int rc;

	DDEBUG(4, &c->dev, "entered");

	switch (c->adapter->id) {
	case I2C_ALGO_SMBUS | I2C_HW_SMBUS_OV511:
		rc = ov_write_regvals(c, regvals_init_6x20_511);
		break;
	case I2C_ALGO_SMBUS | I2C_HW_SMBUS_OV518:
		rc = ov_write_regvals(c, regvals_init_6x20_518);
		break;
	default:
		dev_err(&c->dev, "ov6x20: Unsupported adapter\n");
		rc = -ENODEV;
	}

	if (rc < 0)
		return rc;

	ov->spriv = s = kmalloc(sizeof *s, GFP_KERNEL);
	if (!s)
		return -ENOMEM;
	memset(s, 0, sizeof *s);

	s->auto_brt = 1;
	s->auto_exp = 1;

	return rc;
}

static int ov6x20_free(struct i2c_client *c)
{
	struct ovcamchip *ov = i2c_get_clientdata(c);

	kfree(ov->spriv);
	return 0;
}

static int ov6x20_set_control(struct i2c_client *c,
			      struct ovcamchip_control *ctl)
{
	struct ovcamchip *ov = i2c_get_clientdata(c);
	struct ov6x20 *s = ov->spriv;
	int rc;
	int v = ctl->value;

	switch (ctl->id) {
	case OVCAMCHIP_CID_CONT:
		rc = ov_write(c, REG_CNT, v >> 8);
		break;
	case OVCAMCHIP_CID_BRIGHT:
		rc = ov_write(c, REG_BRT, v >> 8);
		break;
	case OVCAMCHIP_CID_SAT:
		rc = ov_write(c, REG_SAT, v >> 8);
		break;
	case OVCAMCHIP_CID_HUE:
		rc = ov_write(c, REG_RED, 0xFF - (v >> 8));
		if (rc < 0)
			goto out;

		rc = ov_write(c, REG_BLUE, v >> 8);
		break;
	case OVCAMCHIP_CID_EXP:
		rc = ov_write(c, REG_EXP, v);
		break;
	case OVCAMCHIP_CID_FREQ:
	{
		int sixty = (v == 60);

		rc = ov_write(c, 0x2b, sixty?0xa8:0x28);
		if (rc < 0)
			goto out;

		rc = ov_write(c, 0x2a, sixty?0x84:0xa4);
		break;
	}
	case OVCAMCHIP_CID_BANDFILT:
		rc = ov_write_mask(c, 0x2d, v?0x04:0x00, 0x04);
		s->bandfilt = v;
		break;
	case OVCAMCHIP_CID_AUTOBRIGHT:
		rc = ov_write_mask(c, 0x2d, v?0x10:0x00, 0x10);
		s->auto_brt = v;
		break;
	case OVCAMCHIP_CID_AUTOEXP:
		rc = ov_write_mask(c, 0x13, v?0x01:0x00, 0x01);
		s->auto_exp = v;
		break;
	case OVCAMCHIP_CID_BACKLIGHT:
	{
		rc = ov_write_mask(c, 0x4e, v?0xe0:0xc0, 0xe0);
		if (rc < 0)
			goto out;

		rc = ov_write_mask(c, 0x29, v?0x08:0x00, 0x08);
		if (rc < 0)
			goto out;

		rc = ov_write_mask(c, 0x0e, v?0x80:0x00, 0x80);
		s->backlight = v;
		break;
	}
	case OVCAMCHIP_CID_MIRROR:
		rc = ov_write_mask(c, 0x12, v?0x40:0x00, 0x40);
		s->mirror = v;
		break;
	default:
		DDEBUG(2, &c->dev, "control not supported: %d", ctl->id);
		return -EPERM;
	}

out:
	DDEBUG(3, &c->dev, "id=%d, arg=%d, rc=%d", ctl->id, v, rc);
	return rc;
}

static int ov6x20_get_control(struct i2c_client *c,
			      struct ovcamchip_control *ctl)
{
	struct ovcamchip *ov = i2c_get_clientdata(c);
	struct ov6x20 *s = ov->spriv;
	int rc = 0;
	unsigned char val = 0;

	switch (ctl->id) {
	case OVCAMCHIP_CID_CONT:
		rc = ov_read(c, REG_CNT, &val);
		ctl->value = val << 8;
		break;
	case OVCAMCHIP_CID_BRIGHT:
		rc = ov_read(c, REG_BRT, &val);
		ctl->value = val << 8;
		break;
	case OVCAMCHIP_CID_SAT:
		rc = ov_read(c, REG_SAT, &val);
		ctl->value = val << 8;
		break;
	case OVCAMCHIP_CID_HUE:
		rc = ov_read(c, REG_BLUE, &val);
		ctl->value = val << 8;
		break;
	case OVCAMCHIP_CID_EXP:
		rc = ov_read(c, REG_EXP, &val);
		ctl->value = val;
		break;
	case OVCAMCHIP_CID_BANDFILT:
		ctl->value = s->bandfilt;
		break;
	case OVCAMCHIP_CID_AUTOBRIGHT:
		ctl->value = s->auto_brt;
		break;
	case OVCAMCHIP_CID_AUTOEXP:
		ctl->value = s->auto_exp;
		break;
	case OVCAMCHIP_CID_BACKLIGHT:
		ctl->value = s->backlight;
		break;
	case OVCAMCHIP_CID_MIRROR:
		ctl->value = s->mirror;
		break;
	default:
		DDEBUG(2, &c->dev, "control not supported: %d", ctl->id);
		return -EPERM;
	}

	DDEBUG(3, &c->dev, "id=%d, arg=%d, rc=%d", ctl->id, ctl->value, rc);
	return rc;
}

static int ov6x20_mode_init(struct i2c_client *c, struct ovcamchip_window *win)
{
	/******** QCIF-specific regs ********/

	ov_write(c, 0x14, win->quarter?0x24:0x04);

	/******** Palette-specific regs ********/

	/* OV518 needs 8 bit multiplexed in color mode, and 16 bit in B&W */
	if (c->adapter->id == (I2C_ALGO_SMBUS | I2C_HW_SMBUS_OV518)) {
		if (win->format == VIDEO_PALETTE_GREY)
			ov_write_mask(c, 0x13, 0x00, 0x20);
		else
			ov_write_mask(c, 0x13, 0x20, 0x20);
	} else {
		if (win->format == VIDEO_PALETTE_GREY)
			ov_write_mask(c, 0x13, 0x20, 0x20);
		else
			ov_write_mask(c, 0x13, 0x00, 0x20);
	}

	/******** Clock programming ********/

	/* The OV6620 needs special handling. This prevents the
	 * severe banding that normally occurs */

	/* Clock down */
	ov_write(c, 0x2a, 0x04);

	ov_write(c, 0x11, win->clockdiv);

	ov_write(c, 0x2a, 0x84);
	/* This next setting is critical. It seems to improve
	 * the gain or the contrast. The "reserved" bits seem
	 * to have some effect in this case. */
	ov_write(c, 0x2d, 0x85); /* FIXME: This messes up banding filter */

	return 0;
}

static int ov6x20_set_window(struct i2c_client *c, struct ovcamchip_window *win)
{
	int ret, hwscale, vwscale;

	ret = ov6x20_mode_init(c, win);
	if (ret < 0)
		return ret;

	if (win->quarter) {
		hwscale = 0;
		vwscale = 0;
	} else {
		hwscale = 1;
		vwscale = 1;	/* The datasheet says 0; it's wrong */
	}

	ov_write(c, 0x17, HWSBASE + (win->x >> hwscale));
	ov_write(c, 0x18, HWEBASE + ((win->x + win->width) >> hwscale));
	ov_write(c, 0x19, VWSBASE + (win->y >> vwscale));
	ov_write(c, 0x1a, VWEBASE + ((win->y + win->height) >> vwscale));

	return 0;
}

static int ov6x20_command(struct i2c_client *c, unsigned int cmd, void *arg)
{
	switch (cmd) {
	case OVCAMCHIP_CMD_S_CTRL:
		return ov6x20_set_control(c, arg);
	case OVCAMCHIP_CMD_G_CTRL:
		return ov6x20_get_control(c, arg);
	case OVCAMCHIP_CMD_S_MODE:
		return ov6x20_set_window(c, arg);
	default:
		DDEBUG(2, &c->dev, "command not supported: %d", cmd);
		return -ENOIOCTLCMD;
	}
}

struct ovcamchip_ops ov6x20_ops = {
	.init    =	ov6x20_init,
	.free    =	ov6x20_free,
	.command =	ov6x20_command,
};
