/*
 *    Support for OR51211 (pcHDTV HD-2000) - VSB
 *
 *    Copyright (C) 2005 Kirk Lapray <kirk_lapray@bigfoot.com>
 *
 *    Based on code from Jack Kelliher (kelliher@xmission.com)
 *                           Copyright (C) 2002 & pcHDTV, inc.
 *
 *    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.
 *
*/

#define pr_fmt(fmt)	KBUILD_MODNAME ": %s: " fmt, __func__

/*
 * This driver needs external firmware. Please use the command
 * "<kerneldir>/scripts/get_dvb_firmware or51211" to
 * download/extract it, and then copy it to /usr/lib/hotplug/firmware
 * or /lib/firmware (depending on configuration of firmware hotplug).
 */
#define OR51211_DEFAULT_FIRMWARE "dvb-fe-or51211.fw"

#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/device.h>
#include <linux/firmware.h>
#include <linux/string.h>
#include <linux/slab.h>
#include <asm/byteorder.h>

#include <media/dvb_math.h>
#include <media/dvb_frontend.h>
#include "or51211.h"

static int debug;
#define dprintk(args...) \
	do { if (debug) pr_debug(args); } while (0)

static u8 run_buf[] = {0x7f,0x01};
static u8 cmd_buf[] = {0x04,0x01,0x50,0x80,0x06}; // ATSC

struct or51211_state {

	struct i2c_adapter* i2c;

	/* Configuration settings */
	const struct or51211_config* config;

	struct dvb_frontend frontend;
	struct bt878* bt;

	/* Demodulator private data */
	u8 initialized:1;
	u32 snr; /* Result of last SNR claculation */

	/* Tuner private data */
	u32 current_frequency;
};

static int i2c_writebytes (struct or51211_state* state, u8 reg, const u8 *buf,
			   int len)
{
	int err;
	struct i2c_msg msg;
	msg.addr	= reg;
	msg.flags	= 0;
	msg.len		= len;
	msg.buf		= (u8 *)buf;

	if ((err = i2c_transfer (state->i2c, &msg, 1)) != 1) {
		pr_warn("error (addr %02x, err == %i)\n", reg, err);
		return -EREMOTEIO;
	}

	return 0;
}

static int i2c_readbytes(struct or51211_state *state, u8 reg, u8 *buf, int len)
{
	int err;
	struct i2c_msg msg;
	msg.addr	= reg;
	msg.flags	= I2C_M_RD;
	msg.len		= len;
	msg.buf		= buf;

	if ((err = i2c_transfer (state->i2c, &msg, 1)) != 1) {
		pr_warn("error (addr %02x, err == %i)\n", reg, err);
		return -EREMOTEIO;
	}

	return 0;
}

static int or51211_load_firmware (struct dvb_frontend* fe,
				  const struct firmware *fw)
{
	struct or51211_state* state = fe->demodulator_priv;
	u8 tudata[585];
	int i;

	dprintk("Firmware is %zu bytes\n", fw->size);

	/* Get eprom data */
	tudata[0] = 17;
	if (i2c_writebytes(state,0x50,tudata,1)) {
		pr_warn("error eprom addr\n");
		return -1;
	}
	if (i2c_readbytes(state,0x50,&tudata[145],192)) {
		pr_warn("error eprom\n");
		return -1;
	}

	/* Create firmware buffer */
	for (i = 0; i < 145; i++)
		tudata[i] = fw->data[i];

	for (i = 0; i < 248; i++)
		tudata[i+337] = fw->data[145+i];

	state->config->reset(fe);

	if (i2c_writebytes(state,state->config->demod_address,tudata,585)) {
		pr_warn("error 1\n");
		return -1;
	}
	msleep(1);

	if (i2c_writebytes(state,state->config->demod_address,
			   &fw->data[393],8125)) {
		pr_warn("error 2\n");
		return -1;
	}
	msleep(1);

	if (i2c_writebytes(state,state->config->demod_address,run_buf,2)) {
		pr_warn("error 3\n");
		return -1;
	}

	/* Wait at least 5 msec */
	msleep(10);
	if (i2c_writebytes(state,state->config->demod_address,run_buf,2)) {
		pr_warn("error 4\n");
		return -1;
	}
	msleep(10);

	pr_info("Done.\n");
	return 0;
};

static int or51211_setmode(struct dvb_frontend* fe, int mode)
{
	struct or51211_state* state = fe->demodulator_priv;
	u8 rec_buf[14];

	state->config->setmode(fe, mode);

	if (i2c_writebytes(state,state->config->demod_address,run_buf,2)) {
		pr_warn("error 1\n");
		return -1;
	}

	/* Wait at least 5 msec */
	msleep(10);
	if (i2c_writebytes(state,state->config->demod_address,run_buf,2)) {
		pr_warn("error 2\n");
		return -1;
	}

	msleep(10);

	/* Set operation mode in Receiver 1 register;
	 * type 1:
	 * data 0x50h  Automatic sets receiver channel conditions
	 *             Automatic NTSC rejection filter
	 *             Enable  MPEG serial data output
	 *             MPEG2tr
	 *             High tuner phase noise
	 *             normal +/-150kHz Carrier acquisition range
	 */
	if (i2c_writebytes(state,state->config->demod_address,cmd_buf,3)) {
		pr_warn("error 3\n");
		return -1;
	}

	rec_buf[0] = 0x04;
	rec_buf[1] = 0x00;
	rec_buf[2] = 0x03;
	rec_buf[3] = 0x00;
	msleep(20);
	if (i2c_writebytes(state,state->config->demod_address,rec_buf,3)) {
		pr_warn("error 5\n");
	}
	msleep(3);
	if (i2c_readbytes(state,state->config->demod_address,&rec_buf[10],2)) {
		pr_warn("error 6\n");
		return -1;
	}
	dprintk("rec status %02x %02x\n", rec_buf[10], rec_buf[11]);

	return 0;
}

static int or51211_set_parameters(struct dvb_frontend *fe)
{
	struct dtv_frontend_properties *p = &fe->dtv_property_cache;
	struct or51211_state* state = fe->demodulator_priv;

	/* Change only if we are actually changing the channel */
	if (state->current_frequency != p->frequency) {
		if (fe->ops.tuner_ops.set_params) {
			fe->ops.tuner_ops.set_params(fe);
			if (fe->ops.i2c_gate_ctrl) fe->ops.i2c_gate_ctrl(fe, 0);
		}

		/* Set to ATSC mode */
		or51211_setmode(fe,0);

		/* Update current frequency */
		state->current_frequency = p->frequency;
	}
	return 0;
}

static int or51211_read_status(struct dvb_frontend *fe, enum fe_status *status)
{
	struct or51211_state* state = fe->demodulator_priv;
	unsigned char rec_buf[2];
	unsigned char snd_buf[] = {0x04,0x00,0x03,0x00};
	*status = 0;

	/* Receiver Status */
	if (i2c_writebytes(state,state->config->demod_address,snd_buf,3)) {
		pr_warn("write error\n");
		return -1;
	}
	msleep(3);
	if (i2c_readbytes(state,state->config->demod_address,rec_buf,2)) {
		pr_warn("read error\n");
		return -1;
	}
	dprintk("%x %x\n", rec_buf[0], rec_buf[1]);

	if (rec_buf[0] &  0x01) { /* Receiver Lock */
		*status |= FE_HAS_SIGNAL;
		*status |= FE_HAS_CARRIER;
		*status |= FE_HAS_VITERBI;
		*status |= FE_HAS_SYNC;
		*status |= FE_HAS_LOCK;
	}
	return 0;
}

/* Calculate SNR estimation (scaled by 2^24)

   8-VSB SNR equation from Oren datasheets

   For 8-VSB:
     SNR[dB] = 10 * log10(219037.9454 / MSE^2 )

   We re-write the snr equation as:
     SNR * 2^24 = 10*(c - 2*intlog10(MSE))
   Where for 8-VSB, c = log10(219037.9454) * 2^24 */

static u32 calculate_snr(u32 mse, u32 c)
{
	if (mse == 0) /* No signal */
		return 0;

	mse = 2*intlog10(mse);
	if (mse > c) {
		/* Negative SNR, which is possible, but realisticly the
		demod will lose lock before the signal gets this bad.  The
		API only allows for unsigned values, so just return 0 */
		return 0;
	}
	return 10*(c - mse);
}

static int or51211_read_snr(struct dvb_frontend* fe, u16* snr)
{
	struct or51211_state* state = fe->demodulator_priv;
	u8 rec_buf[2];
	u8 snd_buf[3];

	/* SNR after Equalizer */
	snd_buf[0] = 0x04;
	snd_buf[1] = 0x00;
	snd_buf[2] = 0x04;

	if (i2c_writebytes(state,state->config->demod_address,snd_buf,3)) {
		pr_warn("error writing snr reg\n");
		return -1;
	}
	if (i2c_readbytes(state,state->config->demod_address,rec_buf,2)) {
		pr_warn("read_status read error\n");
		return -1;
	}

	state->snr = calculate_snr(rec_buf[0], 89599047);
	*snr = (state->snr) >> 16;

	dprintk("noise = 0x%02x, snr = %d.%02d dB\n", rec_buf[0],
		state->snr >> 24, (((state->snr>>8) & 0xffff) * 100) >> 16);

	return 0;
}

static int or51211_read_signal_strength(struct dvb_frontend* fe, u16* strength)
{
	/* Calculate Strength from SNR up to 35dB */
	/* Even though the SNR can go higher than 35dB, there is some comfort */
	/* factor in having a range of strong signals that can show at 100%   */
	struct or51211_state* state = (struct or51211_state*)fe->demodulator_priv;
	u16 snr;
	int ret;

	ret = fe->ops.read_snr(fe, &snr);
	if (ret != 0)
		return ret;
	/* Rather than use the 8.8 value snr, use state->snr which is 8.24 */
	/* scale the range 0 - 35*2^24 into 0 - 65535 */
	if (state->snr >= 8960 * 0x10000)
		*strength = 0xffff;
	else
		*strength = state->snr / 8960;

	return 0;
}

static int or51211_read_ber(struct dvb_frontend* fe, u32* ber)
{
	*ber = -ENOSYS;
	return 0;
}

static int or51211_read_ucblocks(struct dvb_frontend* fe, u32* ucblocks)
{
	*ucblocks = -ENOSYS;
	return 0;
}

static int or51211_sleep(struct dvb_frontend* fe)
{
	return 0;
}

static int or51211_init(struct dvb_frontend* fe)
{
	struct or51211_state* state = fe->demodulator_priv;
	const struct or51211_config* config = state->config;
	const struct firmware* fw;
	unsigned char get_ver_buf[] = {0x04,0x00,0x30,0x00,0x00};
	unsigned char rec_buf[14];
	int ret,i;

	if (!state->initialized) {
		/* Request the firmware, this will block until it uploads */
		pr_info("Waiting for firmware upload (%s)...\n",
			OR51211_DEFAULT_FIRMWARE);
		ret = config->request_firmware(fe, &fw,
					       OR51211_DEFAULT_FIRMWARE);
		pr_info("Got Hotplug firmware\n");
		if (ret) {
			pr_warn("No firmware uploaded (timeout or file not found?)\n");
			return ret;
		}

		ret = or51211_load_firmware(fe, fw);
		release_firmware(fw);
		if (ret) {
			pr_warn("Writing firmware to device failed!\n");
			return ret;
		}
		pr_info("Firmware upload complete.\n");

		/* Set operation mode in Receiver 1 register;
		 * type 1:
		 * data 0x50h  Automatic sets receiver channel conditions
		 *             Automatic NTSC rejection filter
		 *             Enable  MPEG serial data output
		 *             MPEG2tr
		 *             High tuner phase noise
		 *             normal +/-150kHz Carrier acquisition range
		 */
		if (i2c_writebytes(state,state->config->demod_address,
				   cmd_buf,3)) {
			pr_warn("Load DVR Error 5\n");
			return -1;
		}

		/* Read back ucode version to besure we loaded correctly */
		/* and are really up and running */
		rec_buf[0] = 0x04;
		rec_buf[1] = 0x00;
		rec_buf[2] = 0x03;
		rec_buf[3] = 0x00;
		msleep(30);
		if (i2c_writebytes(state,state->config->demod_address,
				   rec_buf,3)) {
			pr_warn("Load DVR Error A\n");
			return -1;
		}
		msleep(3);
		if (i2c_readbytes(state,state->config->demod_address,
				  &rec_buf[10],2)) {
			pr_warn("Load DVR Error B\n");
			return -1;
		}

		rec_buf[0] = 0x04;
		rec_buf[1] = 0x00;
		rec_buf[2] = 0x01;
		rec_buf[3] = 0x00;
		msleep(20);
		if (i2c_writebytes(state,state->config->demod_address,
				   rec_buf,3)) {
			pr_warn("Load DVR Error C\n");
			return -1;
		}
		msleep(3);
		if (i2c_readbytes(state,state->config->demod_address,
				  &rec_buf[12],2)) {
			pr_warn("Load DVR Error D\n");
			return -1;
		}

		for (i = 0; i < 8; i++)
			rec_buf[i]=0xed;

		for (i = 0; i < 5; i++) {
			msleep(30);
			get_ver_buf[4] = i+1;
			if (i2c_writebytes(state,state->config->demod_address,
					   get_ver_buf,5)) {
				pr_warn("Load DVR Error 6 - %d\n", i);
				return -1;
			}
			msleep(3);

			if (i2c_readbytes(state,state->config->demod_address,
					  &rec_buf[i*2],2)) {
				pr_warn("Load DVR Error 7 - %d\n", i);
				return -1;
			}
			/* If we didn't receive the right index, try again */
			if ((int)rec_buf[i*2+1]!=i+1){
			  i--;
			}
		}
		dprintk("read_fwbits %10ph\n", rec_buf);

		pr_info("ver TU%02x%02x%02x VSB mode %02x Status %02x\n",
			rec_buf[2], rec_buf[4], rec_buf[6], rec_buf[12],
			rec_buf[10]);

		rec_buf[0] = 0x04;
		rec_buf[1] = 0x00;
		rec_buf[2] = 0x03;
		rec_buf[3] = 0x00;
		msleep(20);
		if (i2c_writebytes(state,state->config->demod_address,
				   rec_buf,3)) {
			pr_warn("Load DVR Error 8\n");
			return -1;
		}
		msleep(20);
		if (i2c_readbytes(state,state->config->demod_address,
				  &rec_buf[8],2)) {
			pr_warn("Load DVR Error 9\n");
			return -1;
		}
		state->initialized = 1;
	}

	return 0;
}

static int or51211_get_tune_settings(struct dvb_frontend* fe,
				     struct dvb_frontend_tune_settings* fesettings)
{
	fesettings->min_delay_ms = 500;
	fesettings->step_size = 0;
	fesettings->max_drift = 0;
	return 0;
}

static void or51211_release(struct dvb_frontend* fe)
{
	struct or51211_state* state = fe->demodulator_priv;
	state->config->sleep(fe);
	kfree(state);
}

static const struct dvb_frontend_ops or51211_ops;

struct dvb_frontend* or51211_attach(const struct or51211_config* config,
				    struct i2c_adapter* i2c)
{
	struct or51211_state* state = NULL;

	/* Allocate memory for the internal state */
	state = kzalloc(sizeof(struct or51211_state), GFP_KERNEL);
	if (state == NULL)
		return NULL;

	/* Setup the state */
	state->config = config;
	state->i2c = i2c;
	state->initialized = 0;
	state->current_frequency = 0;

	/* Create dvb_frontend */
	memcpy(&state->frontend.ops, &or51211_ops, sizeof(struct dvb_frontend_ops));
	state->frontend.demodulator_priv = state;
	return &state->frontend;
}

static const struct dvb_frontend_ops or51211_ops = {
	.delsys = { SYS_ATSC, SYS_DVBC_ANNEX_B },
	.info = {
		.name                  = "Oren OR51211 VSB Frontend",
		.frequency_min_hz      =  44 * MHz,
		.frequency_max_hz      = 958 * MHz,
		.frequency_stepsize_hz = 166666,
		.caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
			FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
			FE_CAN_8VSB
	},

	.release = or51211_release,

	.init = or51211_init,
	.sleep = or51211_sleep,

	.set_frontend = or51211_set_parameters,
	.get_tune_settings = or51211_get_tune_settings,

	.read_status = or51211_read_status,
	.read_ber = or51211_read_ber,
	.read_signal_strength = or51211_read_signal_strength,
	.read_snr = or51211_read_snr,
	.read_ucblocks = or51211_read_ucblocks,
};

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

MODULE_DESCRIPTION("Oren OR51211 VSB [pcHDTV HD-2000] Demodulator Driver");
MODULE_AUTHOR("Kirk Lapray");
MODULE_LICENSE("GPL");

EXPORT_SYMBOL(or51211_attach);

