/*
 * Driver for the i2c/i2s based TA3004 sound chip used
 * on some Apple hardware. Also known as "snapper".
 *
 * Tobias Sargeant <tobias.sargeant@bigpond.com>
 * Based upon, tas3001c.c by Christopher C. Chimelis <chris@debian.org>:
 *
 *   TODO:
 *   -----
 *   * Enable control over input line 2 (is this connected?)
 *   * Implement sleep support (at least mute everything and
 *   * set gains to minimum during sleep)
 *   * Look into some of Darwin's tweaks regarding the mute
 *   * lines (delays & different behaviour on some HW)
 *
 */

#include <linux/module.h>
#include <linux/slab.h>
#include <linux/proc_fs.h>
#include <linux/ioport.h>
#include <linux/sysctl.h>
#include <linux/types.h>
#include <linux/i2c.h>
#include <linux/init.h>
#include <linux/soundcard.h>
#include <linux/workqueue.h>
#include <asm/uaccess.h>
#include <asm/errno.h>
#include <asm/io.h>
#include <asm/prom.h>

#include "dmasound.h"
#include "tas_common.h"
#include "tas3001c.h"

#include "tas_ioctl.h"

#define TAS3001C_BIQUAD_FILTER_COUNT  6
#define TAS3001C_BIQUAD_CHANNEL_COUNT 2

#define VOL_DEFAULT	(100 * 4 / 5)
#define INPUT_DEFAULT	(100 * 4 / 5)
#define BASS_DEFAULT	(100 / 2)
#define TREBLE_DEFAULT	(100 / 2)

struct tas3001c_data_t {
	struct tas_data_t super;
	int device_id;
	int output_id;
	int speaker_id;
	struct tas_drce_t drce_state;
	struct work_struct change;
};


static const union tas_biquad_t
tas3001c_eq_unity={
	.buf = { 0x100000, 0x000000, 0x000000, 0x000000, 0x000000 }
};


static inline unsigned char db_to_regval(short db) {
	int r=0;

	r=(db+0x59a0) / 0x60;

	if (r < 0x91) return 0x91;
	if (r > 0xef) return 0xef;
	return r;
}

static inline short quantize_db(short db) {
	return db_to_regval(db) * 0x60 - 0x59a0;
}


static inline int
register_width(enum tas3001c_reg_t r)
{
	switch(r) {
	case TAS3001C_REG_MCR:
 	case TAS3001C_REG_TREBLE:
	case TAS3001C_REG_BASS:
		return 1;

	case TAS3001C_REG_DRC:
		return 2;

	case TAS3001C_REG_MIXER1:
	case TAS3001C_REG_MIXER2:
		return 3;

	case TAS3001C_REG_VOLUME:
		return 6;

	case TAS3001C_REG_LEFT_BIQUAD0:
	case TAS3001C_REG_LEFT_BIQUAD1:
	case TAS3001C_REG_LEFT_BIQUAD2:
	case TAS3001C_REG_LEFT_BIQUAD3:
	case TAS3001C_REG_LEFT_BIQUAD4:
	case TAS3001C_REG_LEFT_BIQUAD5:
	case TAS3001C_REG_LEFT_BIQUAD6:

	case TAS3001C_REG_RIGHT_BIQUAD0:
	case TAS3001C_REG_RIGHT_BIQUAD1:
	case TAS3001C_REG_RIGHT_BIQUAD2:
	case TAS3001C_REG_RIGHT_BIQUAD3:
	case TAS3001C_REG_RIGHT_BIQUAD4:
	case TAS3001C_REG_RIGHT_BIQUAD5:
	case TAS3001C_REG_RIGHT_BIQUAD6:
		return 15;

	default:
		return 0;
	}
}

static int
tas3001c_write_register(	struct tas3001c_data_t *self,
				enum tas3001c_reg_t reg_num,
				char *data,
				uint write_mode)
{
	if (reg_num==TAS3001C_REG_MCR ||
	    reg_num==TAS3001C_REG_BASS ||
	    reg_num==TAS3001C_REG_TREBLE) {
		return tas_write_byte_register(&self->super,
					       (uint)reg_num,
					       *data,
					       write_mode);
	} else {
		return tas_write_register(&self->super,
					  (uint)reg_num,
					  register_width(reg_num),
					  data,
					  write_mode);
	}
}

static int
tas3001c_sync_register(	struct tas3001c_data_t *self,
			enum tas3001c_reg_t reg_num)
{
	if (reg_num==TAS3001C_REG_MCR ||
	    reg_num==TAS3001C_REG_BASS ||
	    reg_num==TAS3001C_REG_TREBLE) {
		return tas_sync_byte_register(&self->super,
					      (uint)reg_num,
					      register_width(reg_num));
	} else {
		return tas_sync_register(&self->super,
					 (uint)reg_num,
					 register_width(reg_num));
	}
}

static int
tas3001c_read_register(	struct tas3001c_data_t *self,
			enum tas3001c_reg_t reg_num,
			char *data,
			uint write_mode)
{
	return tas_read_register(&self->super,
				 (uint)reg_num,
				 register_width(reg_num),
				 data);
}

static inline int
tas3001c_fast_load(struct tas3001c_data_t *self, int fast)
{
	if (fast)
		self->super.shadow[TAS3001C_REG_MCR][0] |= 0x80;
	else
		self->super.shadow[TAS3001C_REG_MCR][0] &= 0x7f;
	return tas3001c_sync_register(self,TAS3001C_REG_MCR);
}

static uint
tas3001c_supported_mixers(struct tas3001c_data_t *self)
{
	return SOUND_MASK_VOLUME |
		SOUND_MASK_PCM |
		SOUND_MASK_ALTPCM |
		SOUND_MASK_TREBLE |
		SOUND_MASK_BASS;
}

static int
tas3001c_mixer_is_stereo(struct tas3001c_data_t *self,int mixer)
{
	switch(mixer) {
	case SOUND_MIXER_VOLUME:
		return 1;
	default:
		return 0;
	}
}

static uint
tas3001c_stereo_mixers(struct tas3001c_data_t *self)
{
	uint r=tas3001c_supported_mixers(self);
	uint i;
	
	for (i=1; i<SOUND_MIXER_NRDEVICES; i++)
		if (r&(1<<i) && !tas3001c_mixer_is_stereo(self,i))
			r &= ~(1<<i);
	return r;
}

static int
tas3001c_get_mixer_level(struct tas3001c_data_t *self,int mixer,uint *level)
{
	if (!self)
		return -1;
		
	*level=self->super.mixer[mixer];
	
	return 0;
}

static int
tas3001c_set_mixer_level(struct tas3001c_data_t *self,int mixer,uint level)
{
	int rc;
	tas_shadow_t *shadow;

	uint temp;
	uint offset=0;

	if (!self)
		return -1;
		
	shadow=self->super.shadow;

	if (!tas3001c_mixer_is_stereo(self,mixer))
		level = tas_mono_to_stereo(level);

	switch(mixer) {
	case SOUND_MIXER_VOLUME:
		temp = tas3001c_gain.master[level&0xff];
		shadow[TAS3001C_REG_VOLUME][0] = (temp >> 16) & 0xff;
		shadow[TAS3001C_REG_VOLUME][1] = (temp >> 8)  & 0xff;
		shadow[TAS3001C_REG_VOLUME][2] = (temp >> 0)  & 0xff;
		temp = tas3001c_gain.master[(level>>8)&0xff];
		shadow[TAS3001C_REG_VOLUME][3] = (temp >> 16) & 0xff;
		shadow[TAS3001C_REG_VOLUME][4] = (temp >> 8)  & 0xff;
		shadow[TAS3001C_REG_VOLUME][5] = (temp >> 0)  & 0xff;
		rc = tas3001c_sync_register(self,TAS3001C_REG_VOLUME);
		break;
	case SOUND_MIXER_ALTPCM:
		/* tas3001c_fast_load(self, 1); */
		level = tas_mono_to_stereo(level);
		temp = tas3001c_gain.mixer[level&0xff];
		shadow[TAS3001C_REG_MIXER2][offset+0] = (temp >> 16) & 0xff;
		shadow[TAS3001C_REG_MIXER2][offset+1] = (temp >> 8)  & 0xff;
		shadow[TAS3001C_REG_MIXER2][offset+2] = (temp >> 0)  & 0xff;
		rc = tas3001c_sync_register(self,TAS3001C_REG_MIXER2);
		/* tas3001c_fast_load(self, 0); */
		break;
	case SOUND_MIXER_PCM:
		/* tas3001c_fast_load(self, 1); */
		level = tas_mono_to_stereo(level);
		temp = tas3001c_gain.mixer[level&0xff];
		shadow[TAS3001C_REG_MIXER1][offset+0] = (temp >> 16) & 0xff;
		shadow[TAS3001C_REG_MIXER1][offset+1] = (temp >> 8)  & 0xff;
		shadow[TAS3001C_REG_MIXER1][offset+2] = (temp >> 0)  & 0xff;
		rc = tas3001c_sync_register(self,TAS3001C_REG_MIXER1);
		/* tas3001c_fast_load(self, 0); */
		break;
	case SOUND_MIXER_TREBLE:
		temp = tas3001c_gain.treble[level&0xff];
		shadow[TAS3001C_REG_TREBLE][0]=temp&0xff;
		rc = tas3001c_sync_register(self,TAS3001C_REG_TREBLE);
		break;
	case SOUND_MIXER_BASS:
		temp = tas3001c_gain.bass[level&0xff];
		shadow[TAS3001C_REG_BASS][0]=temp&0xff;
		rc = tas3001c_sync_register(self,TAS3001C_REG_BASS);
		break;
	default:
		rc = -1;
		break;
	}
	if (rc < 0)
		return rc;
	self->super.mixer[mixer]=level;
	return 0;
}

static int
tas3001c_leave_sleep(struct tas3001c_data_t *self)
{
	unsigned char mcr = (1<<6)+(2<<4)+(2<<2);

	if (!self)
		return -1;

	/* Make sure something answers on the i2c bus */
	if (tas3001c_write_register(self, TAS3001C_REG_MCR, &mcr,
	    WRITE_NORMAL|FORCE_WRITE) < 0)
	    	return -1;

	tas3001c_fast_load(self, 1);

	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD0);
	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD1);
	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD2);
	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD3);
	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD4);
	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD5);

	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD0);
	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD1);
	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD2);
	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD3);
	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD4);
	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD5);

	tas3001c_fast_load(self, 0);

	(void)tas3001c_sync_register(self,TAS3001C_REG_BASS);
	(void)tas3001c_sync_register(self,TAS3001C_REG_TREBLE);
	(void)tas3001c_sync_register(self,TAS3001C_REG_MIXER1);
	(void)tas3001c_sync_register(self,TAS3001C_REG_MIXER2);
	(void)tas3001c_sync_register(self,TAS3001C_REG_VOLUME);

	return 0;
}

static int
tas3001c_enter_sleep(struct tas3001c_data_t *self)
{
	/* Stub for now, but I have the details on low-power mode */
	if (!self)
		return -1; 
	return 0;
}

static int
tas3001c_sync_biquad(	struct tas3001c_data_t *self,
			u_int channel,
			u_int filter)
{
	enum tas3001c_reg_t reg;

	if (channel >= TAS3001C_BIQUAD_CHANNEL_COUNT ||
	    filter  >= TAS3001C_BIQUAD_FILTER_COUNT) return -EINVAL;

	reg=( channel ? TAS3001C_REG_RIGHT_BIQUAD0 : TAS3001C_REG_LEFT_BIQUAD0 ) + filter;

	return tas3001c_sync_register(self,reg);
}

static int
tas3001c_write_biquad_shadow(	struct tas3001c_data_t *self,
				u_int channel,
				u_int filter,
				const union tas_biquad_t *biquad)
{
	tas_shadow_t *shadow=self->super.shadow;
	enum tas3001c_reg_t reg;

	if (channel >= TAS3001C_BIQUAD_CHANNEL_COUNT ||
	    filter  >= TAS3001C_BIQUAD_FILTER_COUNT) return -EINVAL;

	reg=( channel ? TAS3001C_REG_RIGHT_BIQUAD0 : TAS3001C_REG_LEFT_BIQUAD0 ) + filter;

	SET_4_20(shadow[reg], 0,biquad->coeff.b0);
	SET_4_20(shadow[reg], 3,biquad->coeff.b1);
	SET_4_20(shadow[reg], 6,biquad->coeff.b2);
	SET_4_20(shadow[reg], 9,biquad->coeff.a1);
	SET_4_20(shadow[reg],12,biquad->coeff.a2);

	return 0;
}

static int
tas3001c_write_biquad(	struct tas3001c_data_t *self,
			u_int channel,
			u_int filter,
			const union tas_biquad_t *biquad)
{
	int rc;

	rc=tas3001c_write_biquad_shadow(self, channel, filter, biquad);
	if (rc < 0) return rc;

	return tas3001c_sync_biquad(self, channel, filter);
}

static int
tas3001c_write_biquad_list(	struct tas3001c_data_t *self,
				u_int filter_count,
				u_int flags,
				struct tas_biquad_ctrl_t *biquads)
{
	int i;
	int rc;

	if (flags & TAS_BIQUAD_FAST_LOAD) tas3001c_fast_load(self,1);

	for (i=0; i<filter_count; i++) {
		rc=tas3001c_write_biquad(self,
					 biquads[i].channel,
					 biquads[i].filter,
					 &biquads[i].data);
		if (rc < 0) break;
	}

	if (flags & TAS_BIQUAD_FAST_LOAD) {
		tas3001c_fast_load(self,0);

		(void)tas3001c_sync_register(self,TAS3001C_REG_BASS);
		(void)tas3001c_sync_register(self,TAS3001C_REG_TREBLE);
		(void)tas3001c_sync_register(self,TAS3001C_REG_MIXER1);
		(void)tas3001c_sync_register(self,TAS3001C_REG_MIXER2);
		(void)tas3001c_sync_register(self,TAS3001C_REG_VOLUME);
	}

	return rc;
}

static int
tas3001c_read_biquad(	struct tas3001c_data_t *self,
			u_int channel,
			u_int filter,
			union tas_biquad_t *biquad)
{
	tas_shadow_t *shadow=self->super.shadow;
	enum tas3001c_reg_t reg;

	if (channel >= TAS3001C_BIQUAD_CHANNEL_COUNT ||
	    filter  >= TAS3001C_BIQUAD_FILTER_COUNT) return -EINVAL;

	reg=( channel ? TAS3001C_REG_RIGHT_BIQUAD0 : TAS3001C_REG_LEFT_BIQUAD0 ) + filter;

	biquad->coeff.b0=GET_4_20(shadow[reg], 0);
	biquad->coeff.b1=GET_4_20(shadow[reg], 3);
	biquad->coeff.b2=GET_4_20(shadow[reg], 6);
	biquad->coeff.a1=GET_4_20(shadow[reg], 9);
	biquad->coeff.a2=GET_4_20(shadow[reg],12);
	
	return 0;	
}

static int
tas3001c_eq_rw(	struct tas3001c_data_t *self,
		u_int cmd,
		u_long arg)
{
	int rc;
	struct tas_biquad_ctrl_t biquad;
	void __user *argp = (void __user *)arg;

	if (copy_from_user(&biquad, argp, sizeof(struct tas_biquad_ctrl_t))) {
		return -EFAULT;
	}

	if (cmd & SIOC_IN) {
		rc=tas3001c_write_biquad(self, biquad.channel, biquad.filter, &biquad.data);
		if (rc != 0) return rc;
	}

	if (cmd & SIOC_OUT) {
		rc=tas3001c_read_biquad(self, biquad.channel, biquad.filter, &biquad.data);
		if (rc != 0) return rc;

		if (copy_to_user(argp, &biquad, sizeof(struct tas_biquad_ctrl_t))) {
			return -EFAULT;
		}

	}
	return 0;
}

static int
tas3001c_eq_list_rw(	struct tas3001c_data_t *self,
			u_int cmd,
			u_long arg)
{
	int rc;
	int filter_count;
	int flags;
	int i,j;
	char sync_required[2][6];
	struct tas_biquad_ctrl_t biquad;
	struct tas_biquad_ctrl_list_t __user *argp = (void __user *)arg;

	memset(sync_required,0,sizeof(sync_required));

	if (copy_from_user(&filter_count, &argp->filter_count, sizeof(int)))
		return -EFAULT;

	if (copy_from_user(&flags, &argp->flags, sizeof(int)))
		return -EFAULT;

	if (cmd & SIOC_IN) {
	}

	for (i=0; i < filter_count; i++) {
		if (copy_from_user(&biquad, &argp->biquads[i],
				   sizeof(struct tas_biquad_ctrl_t))) {
			return -EFAULT;
		}

		if (cmd & SIOC_IN) {
			sync_required[biquad.channel][biquad.filter]=1;
			rc=tas3001c_write_biquad_shadow(self, biquad.channel, biquad.filter, &biquad.data);
			if (rc != 0) return rc;
		}

		if (cmd & SIOC_OUT) {
			rc=tas3001c_read_biquad(self, biquad.channel, biquad.filter, &biquad.data);
			if (rc != 0) return rc;

			if (copy_to_user(&argp->biquads[i], &biquad,
					 sizeof(struct tas_biquad_ctrl_t))) {
				return -EFAULT;
			}
		}
	}

	if (cmd & SIOC_IN) {
		if (flags & TAS_BIQUAD_FAST_LOAD) tas3001c_fast_load(self,1);
		for (i=0; i<2; i++) {
			for (j=0; j<6; j++) {
				if (sync_required[i][j]) {
					rc=tas3001c_sync_biquad(self, i, j);
					if (rc < 0) return rc;
				}
			}
		}
		if (flags & TAS_BIQUAD_FAST_LOAD) {
			tas3001c_fast_load(self,0);
			/* now we need to set up the mixers again,
			   because leaving fast mode resets them. */
			(void)tas3001c_sync_register(self,TAS3001C_REG_BASS);
			(void)tas3001c_sync_register(self,TAS3001C_REG_TREBLE);
			(void)tas3001c_sync_register(self,TAS3001C_REG_MIXER1);
			(void)tas3001c_sync_register(self,TAS3001C_REG_MIXER2);
			(void)tas3001c_sync_register(self,TAS3001C_REG_VOLUME);
		}
	}

	return 0;
}

static int
tas3001c_update_drce(	struct tas3001c_data_t *self,
			int flags,
			struct tas_drce_t *drce)
{
	tas_shadow_t *shadow;
	shadow=self->super.shadow;

	shadow[TAS3001C_REG_DRC][1] = 0xc1;

	if (flags & TAS_DRCE_THRESHOLD) {
		self->drce_state.threshold=quantize_db(drce->threshold);
		shadow[TAS3001C_REG_DRC][2] = db_to_regval(self->drce_state.threshold);
	}

	if (flags & TAS_DRCE_ENABLE) {
		self->drce_state.enable = drce->enable;
	}

	if (!self->drce_state.enable) {
		shadow[TAS3001C_REG_DRC][0] = 0xf0;
	}

#ifdef DEBUG_DRCE
	printk("DRCE IOCTL: set [ ENABLE:%x THRESH:%x\n",
	       self->drce_state.enable,
	       self->drce_state.threshold);

	printk("DRCE IOCTL: reg [ %02x %02x ]\n",
	       (unsigned char)shadow[TAS3001C_REG_DRC][0],
	       (unsigned char)shadow[TAS3001C_REG_DRC][1]);
#endif

	return tas3001c_sync_register(self, TAS3001C_REG_DRC);
}

static int
tas3001c_drce_rw(	struct tas3001c_data_t *self,
			u_int cmd,
			u_long arg)
{
	int rc;
	struct tas_drce_ctrl_t drce_ctrl;
	void __user *argp = (void __user *)arg;

	if (copy_from_user(&drce_ctrl, argp, sizeof(struct tas_drce_ctrl_t)))
		return -EFAULT;

#ifdef DEBUG_DRCE
	printk("DRCE IOCTL: input [ FLAGS:%x ENABLE:%x THRESH:%x\n",
	       drce_ctrl.flags,
	       drce_ctrl.data.enable,
	       drce_ctrl.data.threshold);
#endif

	if (cmd & SIOC_IN) {
		rc = tas3001c_update_drce(self, drce_ctrl.flags, &drce_ctrl.data);
		if (rc < 0)
			return rc;
	}

	if (cmd & SIOC_OUT) {
		if (drce_ctrl.flags & TAS_DRCE_ENABLE)
			drce_ctrl.data.enable = self->drce_state.enable;

		if (drce_ctrl.flags & TAS_DRCE_THRESHOLD)
			drce_ctrl.data.threshold = self->drce_state.threshold;

		if (copy_to_user(argp, &drce_ctrl,
				 sizeof(struct tas_drce_ctrl_t))) {
			return -EFAULT;
		}
	}

	return 0;
}

static void
tas3001c_update_device_parameters(struct tas3001c_data_t *self)
{
	int i,j;

	if (!self) return;

	if (self->output_id == TAS_OUTPUT_HEADPHONES) {
		tas3001c_fast_load(self, 1);

		for (i=0; i<TAS3001C_BIQUAD_CHANNEL_COUNT; i++) {
			for (j=0; j<TAS3001C_BIQUAD_FILTER_COUNT; j++) {
				tas3001c_write_biquad(self, i, j, &tas3001c_eq_unity);
			}
		}

		tas3001c_fast_load(self, 0);

		(void)tas3001c_sync_register(self,TAS3001C_REG_BASS);
		(void)tas3001c_sync_register(self,TAS3001C_REG_TREBLE);
		(void)tas3001c_sync_register(self,TAS3001C_REG_MIXER1);
		(void)tas3001c_sync_register(self,TAS3001C_REG_MIXER2);
		(void)tas3001c_sync_register(self,TAS3001C_REG_VOLUME);

		return;
	}

	for (i=0; tas3001c_eq_prefs[i]; i++) {
		struct tas_eq_pref_t *eq = tas3001c_eq_prefs[i];

		if (eq->device_id == self->device_id &&
		    (eq->output_id == 0 || eq->output_id == self->output_id) &&
		    (eq->speaker_id == 0 || eq->speaker_id == self->speaker_id)) {

			tas3001c_update_drce(self, TAS_DRCE_ALL, eq->drce);
			tas3001c_write_biquad_list(self, eq->filter_count, TAS_BIQUAD_FAST_LOAD, eq->biquads);

			break;
		}
	}
}

static void
tas3001c_device_change_handler(struct work_struct *work)
{
	struct tas3001c_data_t *self;
	self = container_of(work, struct tas3001c_data_t, change);
	tas3001c_update_device_parameters(self);
}

static int
tas3001c_output_device_change(	struct tas3001c_data_t *self,
				int device_id,
				int output_id,
				int speaker_id)
{
	self->device_id=device_id;
	self->output_id=output_id;
	self->speaker_id=speaker_id;

	schedule_work(&self->change);
	return 0;
}

static int
tas3001c_device_ioctl(	struct tas3001c_data_t *self,
			u_int cmd,
			u_long arg)
{
	uint __user *argp = (void __user *)arg;
	switch (cmd) {
	case TAS_READ_EQ:
	case TAS_WRITE_EQ:
		return tas3001c_eq_rw(self, cmd, arg);

	case TAS_READ_EQ_LIST:
	case TAS_WRITE_EQ_LIST:
		return tas3001c_eq_list_rw(self, cmd, arg);

	case TAS_READ_EQ_FILTER_COUNT:
		put_user(TAS3001C_BIQUAD_FILTER_COUNT, argp);
		return 0;

	case TAS_READ_EQ_CHANNEL_COUNT:
		put_user(TAS3001C_BIQUAD_CHANNEL_COUNT, argp);
		return 0;

	case TAS_READ_DRCE:
	case TAS_WRITE_DRCE:
		return tas3001c_drce_rw(self, cmd, arg);

	case TAS_READ_DRCE_CAPS:
		put_user(TAS_DRCE_ENABLE | TAS_DRCE_THRESHOLD, argp);
		return 0;

	case TAS_READ_DRCE_MIN:
	case TAS_READ_DRCE_MAX: {
		struct tas_drce_ctrl_t drce_ctrl;

		if (copy_from_user(&drce_ctrl, argp,
				   sizeof(struct tas_drce_ctrl_t))) {
			return -EFAULT;
		}

		if (drce_ctrl.flags & TAS_DRCE_THRESHOLD) {
			if (cmd == TAS_READ_DRCE_MIN) {
				drce_ctrl.data.threshold=-36<<8;
			} else {
				drce_ctrl.data.threshold=-6<<8;
			}
		}

		if (copy_to_user(argp, &drce_ctrl,
				 sizeof(struct tas_drce_ctrl_t))) {
			return -EFAULT;
		}
	}
	}

	return -EINVAL;
}

static int
tas3001c_init_mixer(struct tas3001c_data_t *self)
{
	unsigned char mcr = (1<<6)+(2<<4)+(2<<2);

	/* Make sure something answers on the i2c bus */
	if (tas3001c_write_register(self, TAS3001C_REG_MCR, &mcr,
	    WRITE_NORMAL|FORCE_WRITE) < 0)
		return -1;

	tas3001c_fast_load(self, 1);

	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD0);
	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD1);
	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD2);
	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD3);
	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD4);
	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD5);
	(void)tas3001c_sync_register(self,TAS3001C_REG_RIGHT_BIQUAD6);

	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD0);
	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD1);
	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD2);
	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD3);
	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD4);
	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD5);
	(void)tas3001c_sync_register(self,TAS3001C_REG_LEFT_BIQUAD6);

	tas3001c_fast_load(self, 0);

	tas3001c_set_mixer_level(self, SOUND_MIXER_VOLUME, VOL_DEFAULT<<8 | VOL_DEFAULT);
	tas3001c_set_mixer_level(self, SOUND_MIXER_PCM, INPUT_DEFAULT<<8 | INPUT_DEFAULT);
	tas3001c_set_mixer_level(self, SOUND_MIXER_ALTPCM, 0);

	tas3001c_set_mixer_level(self, SOUND_MIXER_BASS, BASS_DEFAULT);
	tas3001c_set_mixer_level(self, SOUND_MIXER_TREBLE, TREBLE_DEFAULT);

	return 0;
}

static int
tas3001c_uninit_mixer(struct tas3001c_data_t *self)
{
	tas3001c_set_mixer_level(self, SOUND_MIXER_VOLUME, 0);
	tas3001c_set_mixer_level(self, SOUND_MIXER_PCM,    0);
	tas3001c_set_mixer_level(self, SOUND_MIXER_ALTPCM, 0);

	tas3001c_set_mixer_level(self, SOUND_MIXER_BASS,   0);
	tas3001c_set_mixer_level(self, SOUND_MIXER_TREBLE, 0);

	return 0;
}

static int
tas3001c_init(struct i2c_client *client)
{
	struct tas3001c_data_t *self;
	size_t sz = sizeof(*self) + (TAS3001C_REG_MAX*sizeof(tas_shadow_t));
	int i, j;

	self = kzalloc(sz, GFP_KERNEL);
	if (!self)
		return -ENOMEM;

	self->super.client = client;
	self->super.shadow = (tas_shadow_t *)(self+1);
	self->output_id = TAS_OUTPUT_HEADPHONES;

	dev_set_drvdata(&client->dev, self);

	for (i = 0; i < TAS3001C_BIQUAD_CHANNEL_COUNT; i++)
		for (j = 0; j < TAS3001C_BIQUAD_FILTER_COUNT; j++)
			tas3001c_write_biquad_shadow(self, i, j,
				&tas3001c_eq_unity);

	INIT_WORK(&self->change, tas3001c_device_change_handler);
	return 0;
}

static void
tas3001c_uninit(struct tas3001c_data_t *self)
{
	tas3001c_uninit_mixer(self);
	kfree(self);
}

struct tas_driver_hooks_t tas3001c_hooks = {
	.init			= (tas_hook_init_t)tas3001c_init,
	.post_init		= (tas_hook_post_init_t)tas3001c_init_mixer,
	.uninit			= (tas_hook_uninit_t)tas3001c_uninit,
	.get_mixer_level	= (tas_hook_get_mixer_level_t)tas3001c_get_mixer_level,
	.set_mixer_level	= (tas_hook_set_mixer_level_t)tas3001c_set_mixer_level,
	.enter_sleep		= (tas_hook_enter_sleep_t)tas3001c_enter_sleep,
	.leave_sleep		= (tas_hook_leave_sleep_t)tas3001c_leave_sleep,
	.supported_mixers	= (tas_hook_supported_mixers_t)tas3001c_supported_mixers,
	.mixer_is_stereo	= (tas_hook_mixer_is_stereo_t)tas3001c_mixer_is_stereo,
	.stereo_mixers		= (tas_hook_stereo_mixers_t)tas3001c_stereo_mixers,
	.output_device_change	= (tas_hook_output_device_change_t)tas3001c_output_device_change,
	.device_ioctl		= (tas_hook_device_ioctl_t)tas3001c_device_ioctl
};
