/*
 *  Driver for Microtune MT2060 "Single chip dual conversion broadband tuner"
 *
 *  Copyright (c) 2006 Olivier DANET <odanet@caramail.com>
 *
 *  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.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *
 *  GNU General Public License for more details.
 */

/* In that file, frequencies are expressed in kiloHertz to avoid 32 bits overflows */

#include <linux/module.h>
#include <linux/delay.h>
#include <linux/dvb/frontend.h>
#include <linux/i2c.h>
#include <linux/slab.h>

#include <media/dvb_frontend.h>

#include "mt2060.h"
#include "mt2060_priv.h"

static int debug;
module_param(debug, int, 0644);
MODULE_PARM_DESC(debug, "Turn on/off debugging (default:off).");

#define dprintk(args...) do { if (debug) {printk(KERN_DEBUG "MT2060: " args); printk("\n"); }} while (0)

// Reads a single register
static int mt2060_readreg(struct mt2060_priv *priv, u8 reg, u8 *val)
{
	struct i2c_msg msg[2] = {
		{ .addr = priv->cfg->i2c_address, .flags = 0, .len = 1 },
		{ .addr = priv->cfg->i2c_address, .flags = I2C_M_RD, .len = 1 },
	};
	int rc = 0;
	u8 *b;

	b = kmalloc(2, GFP_KERNEL);
	if (!b)
		return -ENOMEM;

	b[0] = reg;
	b[1] = 0;

	msg[0].buf = b;
	msg[1].buf = b + 1;

	if (i2c_transfer(priv->i2c, msg, 2) != 2) {
		printk(KERN_WARNING "mt2060 I2C read failed\n");
		rc = -EREMOTEIO;
	}
	*val = b[1];
	kfree(b);

	return rc;
}

// Writes a single register
static int mt2060_writereg(struct mt2060_priv *priv, u8 reg, u8 val)
{
	struct i2c_msg msg = {
		.addr = priv->cfg->i2c_address, .flags = 0, .len = 2
	};
	u8 *buf;
	int rc = 0;

	buf = kmalloc(2, GFP_KERNEL);
	if (!buf)
		return -ENOMEM;

	buf[0] = reg;
	buf[1] = val;

	msg.buf = buf;

	if (i2c_transfer(priv->i2c, &msg, 1) != 1) {
		printk(KERN_WARNING "mt2060 I2C write failed\n");
		rc = -EREMOTEIO;
	}
	kfree(buf);
	return rc;
}

// Writes a set of consecutive registers
static int mt2060_writeregs(struct mt2060_priv *priv,u8 *buf, u8 len)
{
	int rem, val_len;
	u8 *xfer_buf;
	int rc = 0;
	struct i2c_msg msg = {
		.addr = priv->cfg->i2c_address, .flags = 0
	};

	xfer_buf = kmalloc(16, GFP_KERNEL);
	if (!xfer_buf)
		return -ENOMEM;

	msg.buf = xfer_buf;

	for (rem = len - 1; rem > 0; rem -= priv->i2c_max_regs) {
		val_len = min_t(int, rem, priv->i2c_max_regs);
		msg.len = 1 + val_len;
		xfer_buf[0] = buf[0] + len - 1 - rem;
		memcpy(&xfer_buf[1], &buf[1 + len - 1 - rem], val_len);

		if (i2c_transfer(priv->i2c, &msg, 1) != 1) {
			printk(KERN_WARNING "mt2060 I2C write failed (len=%i)\n", val_len);
			rc = -EREMOTEIO;
			break;
		}
	}

	kfree(xfer_buf);
	return rc;
}

// Initialisation sequences
// LNABAND=3, NUM1=0x3C, DIV1=0x74, NUM2=0x1080, DIV2=0x49
static u8 mt2060_config1[] = {
	REG_LO1C1,
	0x3F,	0x74,	0x00,	0x08,	0x93
};

// FMCG=2, GP2=0, GP1=0
static u8 mt2060_config2[] = {
	REG_MISC_CTRL,
	0x20,	0x1E,	0x30,	0xff,	0x80,	0xff,	0x00,	0x2c,	0x42
};

//  VGAG=3, V1CSE=1

#ifdef  MT2060_SPURCHECK
/* The function below calculates the frequency offset between the output frequency if2
 and the closer cross modulation subcarrier between lo1 and lo2 up to the tenth harmonic */
static int mt2060_spurcalc(u32 lo1,u32 lo2,u32 if2)
{
	int I,J;
	int dia,diamin,diff;
	diamin=1000000;
	for (I = 1; I < 10; I++) {
		J = ((2*I*lo1)/lo2+1)/2;
		diff = I*(int)lo1-J*(int)lo2;
		if (diff < 0) diff=-diff;
		dia = (diff-(int)if2);
		if (dia < 0) dia=-dia;
		if (diamin > dia) diamin=dia;
	}
	return diamin;
}

#define BANDWIDTH 4000 // kHz

/* Calculates the frequency offset to add to avoid spurs. Returns 0 if no offset is needed */
static int mt2060_spurcheck(u32 lo1,u32 lo2,u32 if2)
{
	u32 Spur,Sp1,Sp2;
	int I,J;
	I=0;
	J=1000;

	Spur=mt2060_spurcalc(lo1,lo2,if2);
	if (Spur < BANDWIDTH) {
		/* Potential spurs detected */
		dprintk("Spurs before : f_lo1: %d  f_lo2: %d  (kHz)",
			(int)lo1,(int)lo2);
		I=1000;
		Sp1 = mt2060_spurcalc(lo1+I,lo2+I,if2);
		Sp2 = mt2060_spurcalc(lo1-I,lo2-I,if2);

		if (Sp1 < Sp2) {
			J=-J; I=-I; Spur=Sp2;
		} else
			Spur=Sp1;

		while (Spur < BANDWIDTH) {
			I += J;
			Spur = mt2060_spurcalc(lo1+I,lo2+I,if2);
		}
		dprintk("Spurs after  : f_lo1: %d  f_lo2: %d  (kHz)",
			(int)(lo1+I),(int)(lo2+I));
	}
	return I;
}
#endif

#define IF2  36150       // IF2 frequency = 36.150 MHz
#define FREF 16000       // Quartz oscillator 16 MHz

static int mt2060_set_params(struct dvb_frontend *fe)
{
	struct dtv_frontend_properties *c = &fe->dtv_property_cache;
	struct mt2060_priv *priv;
	int i=0;
	u32 freq;
	u8  lnaband;
	u32 f_lo1,f_lo2;
	u32 div1,num1,div2,num2;
	u8  b[8];
	u32 if1;

	priv = fe->tuner_priv;

	if1 = priv->if1_freq;
	b[0] = REG_LO1B1;
	b[1] = 0xFF;

	if (fe->ops.i2c_gate_ctrl)
		fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */

	mt2060_writeregs(priv,b,2);

	freq = c->frequency / 1000; /* Hz -> kHz */

	f_lo1 = freq + if1 * 1000;
	f_lo1 = (f_lo1 / 250) * 250;
	f_lo2 = f_lo1 - freq - IF2;
	// From the Comtech datasheet, the step used is 50kHz. The tuner chip could be more precise
	f_lo2 = ((f_lo2 + 25) / 50) * 50;
	priv->frequency =  (f_lo1 - f_lo2 - IF2) * 1000,

#ifdef MT2060_SPURCHECK
	// LO-related spurs detection and correction
	num1   = mt2060_spurcheck(f_lo1,f_lo2,IF2);
	f_lo1 += num1;
	f_lo2 += num1;
#endif
	//Frequency LO1 = 16MHz * (DIV1 + NUM1/64 )
	num1 = f_lo1 / (FREF / 64);
	div1 = num1 / 64;
	num1 &= 0x3f;

	// Frequency LO2 = 16MHz * (DIV2 + NUM2/8192 )
	num2 = f_lo2 * 64 / (FREF / 128);
	div2 = num2 / 8192;
	num2 &= 0x1fff;

	if (freq <=  95000) lnaband = 0xB0; else
	if (freq <= 180000) lnaband = 0xA0; else
	if (freq <= 260000) lnaband = 0x90; else
	if (freq <= 335000) lnaband = 0x80; else
	if (freq <= 425000) lnaband = 0x70; else
	if (freq <= 480000) lnaband = 0x60; else
	if (freq <= 570000) lnaband = 0x50; else
	if (freq <= 645000) lnaband = 0x40; else
	if (freq <= 730000) lnaband = 0x30; else
	if (freq <= 810000) lnaband = 0x20; else lnaband = 0x10;

	b[0] = REG_LO1C1;
	b[1] = lnaband | ((num1 >>2) & 0x0F);
	b[2] = div1;
	b[3] = (num2 & 0x0F)  | ((num1 & 3) << 4);
	b[4] = num2 >> 4;
	b[5] = ((num2 >>12) & 1) | (div2 << 1);

	dprintk("IF1: %dMHz",(int)if1);
	dprintk("PLL freq=%dkHz  f_lo1=%dkHz  f_lo2=%dkHz",(int)freq,(int)f_lo1,(int)f_lo2);
	dprintk("PLL div1=%d  num1=%d  div2=%d  num2=%d",(int)div1,(int)num1,(int)div2,(int)num2);
	dprintk("PLL [1..5]: %2x %2x %2x %2x %2x",(int)b[1],(int)b[2],(int)b[3],(int)b[4],(int)b[5]);

	mt2060_writeregs(priv,b,6);

	//Waits for pll lock or timeout
	i = 0;
	do {
		mt2060_readreg(priv,REG_LO_STATUS,b);
		if ((b[0] & 0x88)==0x88)
			break;
		msleep(4);
		i++;
	} while (i<10);

	if (fe->ops.i2c_gate_ctrl)
		fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */

	return 0;
}

static void mt2060_calibrate(struct mt2060_priv *priv)
{
	u8 b = 0;
	int i = 0;

	if (mt2060_writeregs(priv,mt2060_config1,sizeof(mt2060_config1)))
		return;
	if (mt2060_writeregs(priv,mt2060_config2,sizeof(mt2060_config2)))
		return;

	/* initialize the clock output */
	mt2060_writereg(priv, REG_VGAG, (priv->cfg->clock_out << 6) | 0x30);

	do {
		b |= (1 << 6); // FM1SS;
		mt2060_writereg(priv, REG_LO2C1,b);
		msleep(20);

		if (i == 0) {
			b |= (1 << 7); // FM1CA;
			mt2060_writereg(priv, REG_LO2C1,b);
			b &= ~(1 << 7); // FM1CA;
			msleep(20);
		}

		b &= ~(1 << 6); // FM1SS
		mt2060_writereg(priv, REG_LO2C1,b);

		msleep(20);
		i++;
	} while (i < 9);

	i = 0;
	while (i++ < 10 && mt2060_readreg(priv, REG_MISC_STAT, &b) == 0 && (b & (1 << 6)) == 0)
		msleep(20);

	if (i <= 10) {
		mt2060_readreg(priv, REG_FM_FREQ, &priv->fmfreq); // now find out, what is fmreq used for :)
		dprintk("calibration was successful: %d", (int)priv->fmfreq);
	} else
		dprintk("FMCAL timed out");
}

static int mt2060_get_frequency(struct dvb_frontend *fe, u32 *frequency)
{
	struct mt2060_priv *priv = fe->tuner_priv;
	*frequency = priv->frequency;
	return 0;
}

static int mt2060_get_if_frequency(struct dvb_frontend *fe, u32 *frequency)
{
	*frequency = IF2 * 1000;
	return 0;
}

static int mt2060_init(struct dvb_frontend *fe)
{
	struct mt2060_priv *priv = fe->tuner_priv;
	int ret;

	if (fe->ops.i2c_gate_ctrl)
		fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */

	if (priv->sleep) {
		ret = mt2060_writereg(priv, REG_MISC_CTRL, 0x20);
		if (ret)
			goto err_i2c_gate_ctrl;
	}

	ret = mt2060_writereg(priv, REG_VGAG,
			      (priv->cfg->clock_out << 6) | 0x33);

err_i2c_gate_ctrl:
	if (fe->ops.i2c_gate_ctrl)
		fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */

	return ret;
}

static int mt2060_sleep(struct dvb_frontend *fe)
{
	struct mt2060_priv *priv = fe->tuner_priv;
	int ret;

	if (fe->ops.i2c_gate_ctrl)
		fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */

	ret = mt2060_writereg(priv, REG_VGAG,
			      (priv->cfg->clock_out << 6) | 0x30);
	if (ret)
		goto err_i2c_gate_ctrl;

	if (priv->sleep)
		ret = mt2060_writereg(priv, REG_MISC_CTRL, 0xe8);

err_i2c_gate_ctrl:
	if (fe->ops.i2c_gate_ctrl)
		fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */

	return ret;
}

static void mt2060_release(struct dvb_frontend *fe)
{
	kfree(fe->tuner_priv);
	fe->tuner_priv = NULL;
}

static const struct dvb_tuner_ops mt2060_tuner_ops = {
	.info = {
		.name              = "Microtune MT2060",
		.frequency_min_hz  =  48 * MHz,
		.frequency_max_hz  = 860 * MHz,
		.frequency_step_hz =  50 * kHz,
	},

	.release       = mt2060_release,

	.init          = mt2060_init,
	.sleep         = mt2060_sleep,

	.set_params    = mt2060_set_params,
	.get_frequency = mt2060_get_frequency,
	.get_if_frequency = mt2060_get_if_frequency,
};

/* This functions tries to identify a MT2060 tuner by reading the PART/REV register. This is hasty. */
struct dvb_frontend * mt2060_attach(struct dvb_frontend *fe, struct i2c_adapter *i2c, struct mt2060_config *cfg, u16 if1)
{
	struct mt2060_priv *priv = NULL;
	u8 id = 0;

	priv = kzalloc(sizeof(struct mt2060_priv), GFP_KERNEL);
	if (priv == NULL)
		return NULL;

	priv->cfg      = cfg;
	priv->i2c      = i2c;
	priv->if1_freq = if1;
	priv->i2c_max_regs = ~0;

	if (fe->ops.i2c_gate_ctrl)
		fe->ops.i2c_gate_ctrl(fe, 1); /* open i2c_gate */

	if (mt2060_readreg(priv,REG_PART_REV,&id) != 0) {
		kfree(priv);
		return NULL;
	}

	if (id != PART_REV) {
		kfree(priv);
		return NULL;
	}
	printk(KERN_INFO "MT2060: successfully identified (IF1 = %d)\n", if1);
	memcpy(&fe->ops.tuner_ops, &mt2060_tuner_ops, sizeof(struct dvb_tuner_ops));

	fe->tuner_priv = priv;

	mt2060_calibrate(priv);

	if (fe->ops.i2c_gate_ctrl)
		fe->ops.i2c_gate_ctrl(fe, 0); /* close i2c_gate */

	return fe;
}
EXPORT_SYMBOL_GPL(mt2060_attach);

static int mt2060_probe(struct i2c_client *client,
			const struct i2c_device_id *id)
{
	struct mt2060_platform_data *pdata = client->dev.platform_data;
	struct dvb_frontend *fe;
	struct mt2060_priv *dev;
	int ret;
	u8 chip_id;

	dev_dbg(&client->dev, "\n");

	if (!pdata) {
		dev_err(&client->dev, "Cannot proceed without platform data\n");
		ret = -EINVAL;
		goto err;
	}

	dev = devm_kzalloc(&client->dev, sizeof(*dev), GFP_KERNEL);
	if (!dev) {
		ret = -ENOMEM;
		goto err;
	}

	fe = pdata->dvb_frontend;
	dev->config.i2c_address = client->addr;
	dev->config.clock_out = pdata->clock_out;
	dev->cfg = &dev->config;
	dev->i2c = client->adapter;
	dev->if1_freq = pdata->if1 ? pdata->if1 : 1220;
	dev->client = client;
	dev->i2c_max_regs = pdata->i2c_write_max ? pdata->i2c_write_max - 1 : ~0;
	dev->sleep = true;

	ret = mt2060_readreg(dev, REG_PART_REV, &chip_id);
	if (ret) {
		ret = -ENODEV;
		goto err;
	}

	dev_dbg(&client->dev, "chip id=%02x\n", chip_id);

	if (chip_id != PART_REV) {
		ret = -ENODEV;
		goto err;
	}

	/* Power on, calibrate, sleep */
	ret = mt2060_writereg(dev, REG_MISC_CTRL, 0x20);
	if (ret)
		goto err;
	mt2060_calibrate(dev);
	ret = mt2060_writereg(dev, REG_MISC_CTRL, 0xe8);
	if (ret)
		goto err;

	dev_info(&client->dev, "Microtune MT2060 successfully identified\n");
	memcpy(&fe->ops.tuner_ops, &mt2060_tuner_ops, sizeof(fe->ops.tuner_ops));
	fe->ops.tuner_ops.release = NULL;
	fe->tuner_priv = dev;
	i2c_set_clientdata(client, dev);

	return 0;
err:
	dev_dbg(&client->dev, "failed=%d\n", ret);
	return ret;
}

static int mt2060_remove(struct i2c_client *client)
{
	dev_dbg(&client->dev, "\n");

	return 0;
}

static const struct i2c_device_id mt2060_id_table[] = {
	{"mt2060", 0},
	{}
};
MODULE_DEVICE_TABLE(i2c, mt2060_id_table);

static struct i2c_driver mt2060_driver = {
	.driver = {
		.name = "mt2060",
		.suppress_bind_attrs = true,
	},
	.probe		= mt2060_probe,
	.remove		= mt2060_remove,
	.id_table	= mt2060_id_table,
};

module_i2c_driver(mt2060_driver);

MODULE_AUTHOR("Olivier DANET");
MODULE_DESCRIPTION("Microtune MT2060 silicon tuner driver");
MODULE_LICENSE("GPL");
