/*
 *  RTC based high-frequency timer
 *
 *  Copyright (C) 2000 Takashi Iwai
 *	based on rtctimer.c by Steve Ratcliffe
 *
 *   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.
 *
 *   You should have received a copy of the GNU General Public License
 *   along with this program; if not, write to the Free Software
 *   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
 *
 */

#include <linux/init.h>
#include <linux/interrupt.h>
#include <linux/module.h>
#include <linux/log2.h>
#include <sound/core.h>
#include <sound/timer.h>

#if defined(CONFIG_RTC) || defined(CONFIG_RTC_MODULE)

#include <linux/mc146818rtc.h>

#define RTC_FREQ	1024		/* default frequency */
#define NANO_SEC	1000000000L	/* 10^9 in sec */

/*
 * prototypes
 */
static int rtctimer_open(struct snd_timer *t);
static int rtctimer_close(struct snd_timer *t);
static int rtctimer_start(struct snd_timer *t);
static int rtctimer_stop(struct snd_timer *t);


/*
 * The hardware dependent description for this timer.
 */
static struct snd_timer_hardware rtc_hw = {
	.flags =	SNDRV_TIMER_HW_AUTO |
			SNDRV_TIMER_HW_FIRST |
			SNDRV_TIMER_HW_TASKLET,
	.ticks =	100000000L,		/* FIXME: XXX */
	.open =		rtctimer_open,
	.close =	rtctimer_close,
	.start =	rtctimer_start,
	.stop =		rtctimer_stop,
};

static int rtctimer_freq = RTC_FREQ;		/* frequency */
static struct snd_timer *rtctimer;
static struct tasklet_struct rtc_tasklet;
static rtc_task_t rtc_task;


static int
rtctimer_open(struct snd_timer *t)
{
	int err;

	err = rtc_register(&rtc_task);
	if (err < 0)
		return err;
	t->private_data = &rtc_task;
	return 0;
}

static int
rtctimer_close(struct snd_timer *t)
{
	rtc_task_t *rtc = t->private_data;
	if (rtc) {
		rtc_unregister(rtc);
		tasklet_kill(&rtc_tasklet);
		t->private_data = NULL;
	}
	return 0;
}

static int
rtctimer_start(struct snd_timer *timer)
{
	rtc_task_t *rtc = timer->private_data;
	if (snd_BUG_ON(!rtc))
		return -EINVAL;
	rtc_control(rtc, RTC_IRQP_SET, rtctimer_freq);
	rtc_control(rtc, RTC_PIE_ON, 0);
	return 0;
}

static int
rtctimer_stop(struct snd_timer *timer)
{
	rtc_task_t *rtc = timer->private_data;
	if (snd_BUG_ON(!rtc))
		return -EINVAL;
	rtc_control(rtc, RTC_PIE_OFF, 0);
	return 0;
}

static void rtctimer_tasklet(unsigned long data)
{
	snd_timer_interrupt((struct snd_timer *)data, 1);
}

/*
 * interrupt
 */
static void rtctimer_interrupt(void *private_data)
{
	tasklet_schedule(private_data);
}


/*
 *  ENTRY functions
 */
static int __init rtctimer_init(void)
{
	int err;
	struct snd_timer *timer;

	if (rtctimer_freq < 2 || rtctimer_freq > 8192 ||
	    !is_power_of_2(rtctimer_freq)) {
		snd_printk(KERN_ERR "rtctimer: invalid frequency %d\n",
			   rtctimer_freq);
		return -EINVAL;
	}

	/* Create a new timer and set up the fields */
	err = snd_timer_global_new("rtc", SNDRV_TIMER_GLOBAL_RTC, &timer);
	if (err < 0)
		return err;

	timer->module = THIS_MODULE;
	strcpy(timer->name, "RTC timer");
	timer->hw = rtc_hw;
	timer->hw.resolution = NANO_SEC / rtctimer_freq;

	tasklet_init(&rtc_tasklet, rtctimer_tasklet, (unsigned long)timer);

	/* set up RTC callback */
	rtc_task.func = rtctimer_interrupt;
	rtc_task.private_data = &rtc_tasklet;

	err = snd_timer_global_register(timer);
	if (err < 0) {
		snd_timer_global_free(timer);
		return err;
	}
	rtctimer = timer; /* remember this */

	return 0;
}

static void __exit rtctimer_exit(void)
{
	if (rtctimer) {
		snd_timer_global_free(rtctimer);
		rtctimer = NULL;
	}
}


/*
 * exported stuff
 */
module_init(rtctimer_init)
module_exit(rtctimer_exit)

module_param(rtctimer_freq, int, 0444);
MODULE_PARM_DESC(rtctimer_freq, "timer frequency in Hz");

MODULE_LICENSE("GPL");

MODULE_ALIAS("snd-timer-" __stringify(SNDRV_TIMER_GLOBAL_RTC));

#endif /* CONFIG_RTC || CONFIG_RTC_MODULE */
