/* radio-trust.c - Trust FM Radio card driver for Linux 2.2
 * by Eric Lammerts <eric@scintilla.utwente.nl>
 *
 * Based on radio-aztech.c. Original notes:
 *
 * Adapted to support the Video for Linux API by
 * Russell Kroll <rkroll@exploits.org>.  Based on original tuner code by:
 *
 * Quay Ly
 * Donald Song
 * Jason Lewis      (jlewis@twilight.vtc.vsc.edu)
 * Scott McGrath    (smcgrath@twilight.vtc.vsc.edu)
 * William McGrath  (wmcgrath@twilight.vtc.vsc.edu)
 *
 * The basis for this code may be found at http://bigbang.vtc.vsc.edu/fmradio/
 */

#include <stdarg.h>
#include <linux/module.h>
#include <linux/init.h>
#include <linux/ioport.h>
#include <asm/io.h>
#include <asm/uaccess.h>
#include <linux/videodev.h>
#include <media/v4l2-common.h>
#include <linux/config.h>	/* CONFIG_RADIO_TRUST_PORT 	*/

/* acceptable ports: 0x350 (JP3 shorted), 0x358 (JP3 open) */

#ifndef CONFIG_RADIO_TRUST_PORT
#define CONFIG_RADIO_TRUST_PORT -1
#endif

static int io = CONFIG_RADIO_TRUST_PORT;
static int radio_nr = -1;
static int ioval = 0xf;
static __u16 curvol;
static __u16 curbass;
static __u16 curtreble;
static unsigned long curfreq;
static int curstereo;
static int curmute;

/* i2c addresses */
#define TDA7318_ADDR 0x88
#define TSA6060T_ADDR 0xc4

#define TR_DELAY do { inb(io); inb(io); inb(io); } while(0)
#define TR_SET_SCL outb(ioval |= 2, io)
#define TR_CLR_SCL outb(ioval &= 0xfd, io)
#define TR_SET_SDA outb(ioval |= 1, io)
#define TR_CLR_SDA outb(ioval &= 0xfe, io)

static void write_i2c(int n, ...)
{
	unsigned char val, mask;
	va_list args;

	va_start(args, n);

	/* start condition */
	TR_SET_SDA;
	TR_SET_SCL;
	TR_DELAY;
	TR_CLR_SDA;
	TR_CLR_SCL;
	TR_DELAY;

	for(; n; n--) {
		val = va_arg(args, unsigned);
		for(mask = 0x80; mask; mask >>= 1) {
			if(val & mask)
				TR_SET_SDA;
			else
				TR_CLR_SDA;
			TR_SET_SCL;
			TR_DELAY;
			TR_CLR_SCL;
			TR_DELAY;
		}
		/* acknowledge bit */
		TR_SET_SDA;
		TR_SET_SCL;
		TR_DELAY;
		TR_CLR_SCL;
		TR_DELAY;
	}

	/* stop condition */
	TR_CLR_SDA;
	TR_DELAY;
	TR_SET_SCL;
	TR_DELAY;
	TR_SET_SDA;
	TR_DELAY;

	va_end(args);
}

static void tr_setvol(__u16 vol)
{
	curvol = vol / 2048;
	write_i2c(2, TDA7318_ADDR, curvol ^ 0x1f);
}

static int basstreble2chip[15] = {
	0, 1, 2, 3, 4, 5, 6, 7, 14, 13, 12, 11, 10, 9, 8
};

static void tr_setbass(__u16 bass)
{
	curbass = bass / 4370;
	write_i2c(2, TDA7318_ADDR, 0x60 | basstreble2chip[curbass]);
}

static void tr_settreble(__u16 treble)
{
	curtreble = treble / 4370;
	write_i2c(2, TDA7318_ADDR, 0x70 | basstreble2chip[curtreble]);
}

static void tr_setstereo(int stereo)
{
	curstereo = !!stereo;
	ioval = (ioval & 0xfb) | (!curstereo << 2);
	outb(ioval, io);
}

static void tr_setmute(int mute)
{
	curmute = !!mute;
	ioval = (ioval & 0xf7) | (curmute << 3);
	outb(ioval, io);
}

static int tr_getsigstr(void)
{
	int i, v;

	for(i = 0, v = 0; i < 100; i++) v |= inb(io);
	return (v & 1)? 0 : 0xffff;
}

static int tr_getstereo(void)
{
	/* don't know how to determine it, just return the setting */
	return curstereo;
}

static void tr_setfreq(unsigned long f)
{
	f /= 160;	/* Convert to 10 kHz units	*/
	f += 1070;	/* Add 10.7 MHz IF			*/

	write_i2c(5, TSA6060T_ADDR, (f << 1) | 1, f >> 7, 0x60 | ((f >> 15) & 1), 0);
}

static int tr_do_ioctl(struct inode *inode, struct file *file,
		       unsigned int cmd, void *arg)
{
	switch(cmd)
	{
		case VIDIOCGCAP:
		{
			struct video_capability *v = arg;

			memset(v,0,sizeof(*v));
			v->type=VID_TYPE_TUNER;
			v->channels=1;
			v->audios=1;
			strcpy(v->name, "Trust FM Radio");

			return 0;
		}
		case VIDIOCGTUNER:
		{
			struct video_tuner *v = arg;

			if(v->tuner)	/* Only 1 tuner */
				return -EINVAL;

			v->rangelow = 87500 * 16;
			v->rangehigh = 108000 * 16;
			v->flags = VIDEO_TUNER_LOW;
			v->mode = VIDEO_MODE_AUTO;

			v->signal = tr_getsigstr();
			if(tr_getstereo())
				v->flags |= VIDEO_TUNER_STEREO_ON;

			strcpy(v->name, "FM");

			return 0;
		}
		case VIDIOCSTUNER:
		{
			struct video_tuner *v = arg;
			if(v->tuner != 0)
				return -EINVAL;
			return 0;
		}
		case VIDIOCGFREQ:
		{
			unsigned long *freq = arg;
			*freq = curfreq;
			return 0;
		}
		case VIDIOCSFREQ:
		{
			unsigned long *freq = arg;
			tr_setfreq(*freq);
			return 0;
		}
		case VIDIOCGAUDIO:
		{
			struct video_audio *v = arg;

			memset(v,0, sizeof(*v));
			v->flags = VIDEO_AUDIO_MUTABLE | VIDEO_AUDIO_VOLUME |
				  VIDEO_AUDIO_BASS | VIDEO_AUDIO_TREBLE;
			v->mode = curstereo? VIDEO_SOUND_STEREO : VIDEO_SOUND_MONO;
			v->volume = curvol * 2048;
			v->step = 2048;
			v->bass = curbass * 4370;
			v->treble = curtreble * 4370;

			strcpy(v->name, "Trust FM Radio");
			return 0;
		}
		case VIDIOCSAUDIO:
		{
			struct video_audio *v = arg;

			if(v->audio)
				return -EINVAL;
			tr_setvol(v->volume);
			tr_setbass(v->bass);
			tr_settreble(v->treble);
			tr_setstereo(v->mode & VIDEO_SOUND_STEREO);
			tr_setmute(v->flags & VIDEO_AUDIO_MUTE);
			return 0;
		}
		default:
			return -ENOIOCTLCMD;
	}
}

static int tr_ioctl(struct inode *inode, struct file *file,
		    unsigned int cmd, unsigned long arg)
{
	return video_usercopy(inode, file, cmd, arg, tr_do_ioctl);
}

static struct file_operations trust_fops = {
	.owner		= THIS_MODULE,
	.open           = video_exclusive_open,
	.release        = video_exclusive_release,
	.ioctl		= tr_ioctl,
	.compat_ioctl	= v4l_compat_ioctl32,
	.llseek         = no_llseek,
};

static struct video_device trust_radio=
{
	.owner		= THIS_MODULE,
	.name		= "Trust FM Radio",
	.type		= VID_TYPE_TUNER,
	.hardware	= VID_HARDWARE_TRUST,
	.fops           = &trust_fops,
};

static int __init trust_init(void)
{
	if(io == -1) {
		printk(KERN_ERR "You must set an I/O address with io=0x???\n");
		return -EINVAL;
	}
	if(!request_region(io, 2, "Trust FM Radio")) {
		printk(KERN_ERR "trust: port 0x%x already in use\n", io);
		return -EBUSY;
	}
	if(video_register_device(&trust_radio, VFL_TYPE_RADIO, radio_nr)==-1)
	{
		release_region(io, 2);
		return -EINVAL;
	}

	printk(KERN_INFO "Trust FM Radio card driver v1.0.\n");

	write_i2c(2, TDA7318_ADDR, 0x80);	/* speaker att. LF = 0 dB */
	write_i2c(2, TDA7318_ADDR, 0xa0);	/* speaker att. RF = 0 dB */
	write_i2c(2, TDA7318_ADDR, 0xc0);	/* speaker att. LR = 0 dB */
	write_i2c(2, TDA7318_ADDR, 0xe0);	/* speaker att. RR = 0 dB */
	write_i2c(2, TDA7318_ADDR, 0x40);	/* stereo 1 input, gain = 18.75 dB */

	tr_setvol(0x8000);
	tr_setbass(0x8000);
	tr_settreble(0x8000);
	tr_setstereo(1);

	/* mute card - prevents noisy bootups */
	tr_setmute(1);

	return 0;
}

MODULE_AUTHOR("Eric Lammerts, Russell Kroll, Quay Lu, Donald Song, Jason Lewis, Scott McGrath, William McGrath");
MODULE_DESCRIPTION("A driver for the Trust FM Radio card.");
MODULE_LICENSE("GPL");

module_param(io, int, 0);
MODULE_PARM_DESC(io, "I/O address of the Trust FM Radio card (0x350 or 0x358)");
module_param(radio_nr, int, 0);

static void __exit cleanup_trust_module(void)
{
	video_unregister_device(&trust_radio);
	release_region(io, 2);
}

module_init(trust_init);
module_exit(cleanup_trust_module);
