/*
 * Intel & MS High Precision Event Timer Implementation.
 *
 * Copyright (C) 2003 Intel Corporation
 *	Venki Pallipadi
 * (c) Copyright 2004 Hewlett-Packard Development Company, L.P.
 *	Bob Picco <robert.picco@hp.com>
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 as
 * published by the Free Software Foundation.
 */

#include <linux/config.h>
#include <linux/interrupt.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/miscdevice.h>
#include <linux/major.h>
#include <linux/ioport.h>
#include <linux/fcntl.h>
#include <linux/init.h>
#include <linux/poll.h>
#include <linux/proc_fs.h>
#include <linux/spinlock.h>
#include <linux/sysctl.h>
#include <linux/wait.h>
#include <linux/bcd.h>
#include <linux/seq_file.h>
#include <linux/bitops.h>

#include <asm/current.h>
#include <asm/uaccess.h>
#include <asm/system.h>
#include <asm/io.h>
#include <asm/irq.h>
#include <asm/div64.h>

#include <linux/acpi.h>
#include <acpi/acpi_bus.h>
#include <linux/hpet.h>

/*
 * The High Precision Event Timer driver.
 * This driver is closely modelled after the rtc.c driver.
 * http://www.intel.com/hardwaredesign/hpetspec.htm
 */
#define	HPET_USER_FREQ	(64)
#define	HPET_DRIFT	(500)

static u32 hpet_ntimer, hpet_nhpet, hpet_max_freq = HPET_USER_FREQ;

/* A lock for concurrent access by app and isr hpet activity. */
static DEFINE_SPINLOCK(hpet_lock);
/* A lock for concurrent intermodule access to hpet and isr hpet activity. */
static DEFINE_SPINLOCK(hpet_task_lock);

#define	HPET_DEV_NAME	(7)

struct hpet_dev {
	struct hpets *hd_hpets;
	struct hpet __iomem *hd_hpet;
	struct hpet_timer __iomem *hd_timer;
	unsigned long hd_ireqfreq;
	unsigned long hd_irqdata;
	wait_queue_head_t hd_waitqueue;
	struct fasync_struct *hd_async_queue;
	struct hpet_task *hd_task;
	unsigned int hd_flags;
	unsigned int hd_irq;
	unsigned int hd_hdwirq;
	char hd_name[HPET_DEV_NAME];
};

struct hpets {
	struct hpets *hp_next;
	struct hpet __iomem *hp_hpet;
	unsigned long hp_hpet_phys;
	struct time_interpolator *hp_interpolator;
	unsigned long hp_period;
	unsigned long hp_delta;
	unsigned int hp_ntimer;
	unsigned int hp_which;
	struct hpet_dev hp_dev[1];
};

static struct hpets *hpets;

#define	HPET_OPEN		0x0001
#define	HPET_IE			0x0002	/* interrupt enabled */
#define	HPET_PERIODIC		0x0004

#if BITS_PER_LONG == 64
#define	write_counter(V, MC)	writeq(V, MC)
#define	read_counter(MC)	readq(MC)
#else
#define	write_counter(V, MC) 	writel(V, MC)
#define	read_counter(MC)	readl(MC)
#endif

#ifndef readq
static inline unsigned long long readq(void __iomem *addr)
{
	return readl(addr) | (((unsigned long long)readl(addr + 4)) << 32LL);
}
#endif

#ifndef writeq
static inline void writeq(unsigned long long v, void __iomem *addr)
{
	writel(v & 0xffffffff, addr);
	writel(v >> 32, addr + 4);
}
#endif

static irqreturn_t hpet_interrupt(int irq, void *data, struct pt_regs *regs)
{
	struct hpet_dev *devp;
	unsigned long isr;

	devp = data;

	spin_lock(&hpet_lock);
	devp->hd_irqdata++;

	/*
	 * For non-periodic timers, increment the accumulator.
	 * This has the effect of treating non-periodic like periodic.
	 */
	if ((devp->hd_flags & (HPET_IE | HPET_PERIODIC)) == HPET_IE) {
		unsigned long m, t;

		t = devp->hd_ireqfreq;
		m = read_counter(&devp->hd_hpet->hpet_mc);
		write_counter(t + m + devp->hd_hpets->hp_delta,
			      &devp->hd_timer->hpet_compare);
	}

	isr = (1 << (devp - devp->hd_hpets->hp_dev));
	writeq(isr, &devp->hd_hpet->hpet_isr);
	spin_unlock(&hpet_lock);

	spin_lock(&hpet_task_lock);
	if (devp->hd_task)
		devp->hd_task->ht_func(devp->hd_task->ht_data);
	spin_unlock(&hpet_task_lock);

	wake_up_interruptible(&devp->hd_waitqueue);

	kill_fasync(&devp->hd_async_queue, SIGIO, POLL_IN);

	return IRQ_HANDLED;
}

static int hpet_open(struct inode *inode, struct file *file)
{
	struct hpet_dev *devp;
	struct hpets *hpetp;
	int i;

	if (file->f_mode & FMODE_WRITE)
		return -EINVAL;

	spin_lock_irq(&hpet_lock);

	for (devp = NULL, hpetp = hpets; hpetp && !devp; hpetp = hpetp->hp_next)
		for (i = 0; i < hpetp->hp_ntimer; i++)
			if (hpetp->hp_dev[i].hd_flags & HPET_OPEN
			    || hpetp->hp_dev[i].hd_task)
				continue;
			else {
				devp = &hpetp->hp_dev[i];
				break;
			}

	if (!devp) {
		spin_unlock_irq(&hpet_lock);
		return -EBUSY;
	}

	file->private_data = devp;
	devp->hd_irqdata = 0;
	devp->hd_flags |= HPET_OPEN;
	spin_unlock_irq(&hpet_lock);

	return 0;
}

static ssize_t
hpet_read(struct file *file, char __user *buf, size_t count, loff_t * ppos)
{
	DECLARE_WAITQUEUE(wait, current);
	unsigned long data;
	ssize_t retval;
	struct hpet_dev *devp;

	devp = file->private_data;
	if (!devp->hd_ireqfreq)
		return -EIO;

	if (count < sizeof(unsigned long))
		return -EINVAL;

	add_wait_queue(&devp->hd_waitqueue, &wait);

	for ( ; ; ) {
		set_current_state(TASK_INTERRUPTIBLE);

		spin_lock_irq(&hpet_lock);
		data = devp->hd_irqdata;
		devp->hd_irqdata = 0;
		spin_unlock_irq(&hpet_lock);

		if (data)
			break;
		else if (file->f_flags & O_NONBLOCK) {
			retval = -EAGAIN;
			goto out;
		} else if (signal_pending(current)) {
			retval = -ERESTARTSYS;
			goto out;
		}
		schedule();
	}

	retval = put_user(data, (unsigned long __user *)buf);
	if (!retval)
		retval = sizeof(unsigned long);
out:
	__set_current_state(TASK_RUNNING);
	remove_wait_queue(&devp->hd_waitqueue, &wait);

	return retval;
}

static unsigned int hpet_poll(struct file *file, poll_table * wait)
{
	unsigned long v;
	struct hpet_dev *devp;

	devp = file->private_data;

	if (!devp->hd_ireqfreq)
		return 0;

	poll_wait(file, &devp->hd_waitqueue, wait);

	spin_lock_irq(&hpet_lock);
	v = devp->hd_irqdata;
	spin_unlock_irq(&hpet_lock);

	if (v != 0)
		return POLLIN | POLLRDNORM;

	return 0;
}

static int hpet_mmap(struct file *file, struct vm_area_struct *vma)
{
#ifdef	CONFIG_HPET_MMAP
	struct hpet_dev *devp;
	unsigned long addr;

	if (((vma->vm_end - vma->vm_start) != PAGE_SIZE) || vma->vm_pgoff)
		return -EINVAL;

	devp = file->private_data;
	addr = devp->hd_hpets->hp_hpet_phys;

	if (addr & (PAGE_SIZE - 1))
		return -ENOSYS;

	vma->vm_flags |= VM_IO;
	vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot);
	addr = __pa(addr);

	if (io_remap_pfn_range(vma, vma->vm_start, addr >> PAGE_SHIFT,
					PAGE_SIZE, vma->vm_page_prot)) {
		printk(KERN_ERR "remap_pfn_range failed in hpet.c\n");
		return -EAGAIN;
	}

	return 0;
#else
	return -ENOSYS;
#endif
}

static int hpet_fasync(int fd, struct file *file, int on)
{
	struct hpet_dev *devp;

	devp = file->private_data;

	if (fasync_helper(fd, file, on, &devp->hd_async_queue) >= 0)
		return 0;
	else
		return -EIO;
}

static int hpet_release(struct inode *inode, struct file *file)
{
	struct hpet_dev *devp;
	struct hpet_timer __iomem *timer;
	int irq = 0;

	devp = file->private_data;
	timer = devp->hd_timer;

	spin_lock_irq(&hpet_lock);

	writeq((readq(&timer->hpet_config) & ~Tn_INT_ENB_CNF_MASK),
	       &timer->hpet_config);

	irq = devp->hd_irq;
	devp->hd_irq = 0;

	devp->hd_ireqfreq = 0;

	if (devp->hd_flags & HPET_PERIODIC
	    && readq(&timer->hpet_config) & Tn_TYPE_CNF_MASK) {
		unsigned long v;

		v = readq(&timer->hpet_config);
		v ^= Tn_TYPE_CNF_MASK;
		writeq(v, &timer->hpet_config);
	}

	devp->hd_flags &= ~(HPET_OPEN | HPET_IE | HPET_PERIODIC);
	spin_unlock_irq(&hpet_lock);

	if (irq)
		free_irq(irq, devp);

	if (file->f_flags & FASYNC)
		hpet_fasync(-1, file, 0);

	file->private_data = NULL;
	return 0;
}

static int hpet_ioctl_common(struct hpet_dev *, int, unsigned long, int);

static int
hpet_ioctl(struct inode *inode, struct file *file, unsigned int cmd,
	   unsigned long arg)
{
	struct hpet_dev *devp;

	devp = file->private_data;
	return hpet_ioctl_common(devp, cmd, arg, 0);
}

static int hpet_ioctl_ieon(struct hpet_dev *devp)
{
	struct hpet_timer __iomem *timer;
	struct hpet __iomem *hpet;
	struct hpets *hpetp;
	int irq;
	unsigned long g, v, t, m;
	unsigned long flags, isr;

	timer = devp->hd_timer;
	hpet = devp->hd_hpet;
	hpetp = devp->hd_hpets;

	v = readq(&timer->hpet_config);
	spin_lock_irq(&hpet_lock);

	if (devp->hd_flags & HPET_IE) {
		spin_unlock_irq(&hpet_lock);
		return -EBUSY;
	}

	devp->hd_flags |= HPET_IE;
	spin_unlock_irq(&hpet_lock);

	t = readq(&timer->hpet_config);
	irq = devp->hd_hdwirq;

	if (irq) {
		sprintf(devp->hd_name, "hpet%d", (int)(devp - hpetp->hp_dev));

		if (request_irq
		    (irq, hpet_interrupt, SA_INTERRUPT, devp->hd_name, (void *)devp)) {
			printk(KERN_ERR "hpet: IRQ %d is not free\n", irq);
			irq = 0;
		}
	}

	if (irq == 0) {
		spin_lock_irq(&hpet_lock);
		devp->hd_flags ^= HPET_IE;
		spin_unlock_irq(&hpet_lock);
		return -EIO;
	}

	devp->hd_irq = irq;
	t = devp->hd_ireqfreq;
	v = readq(&timer->hpet_config);
	g = v | Tn_INT_ENB_CNF_MASK;

	if (devp->hd_flags & HPET_PERIODIC) {
		write_counter(t, &timer->hpet_compare);
		g |= Tn_TYPE_CNF_MASK;
		v |= Tn_TYPE_CNF_MASK;
		writeq(v, &timer->hpet_config);
		v |= Tn_VAL_SET_CNF_MASK;
		writeq(v, &timer->hpet_config);
		local_irq_save(flags);
		m = read_counter(&hpet->hpet_mc);
		write_counter(t + m + hpetp->hp_delta, &timer->hpet_compare);
	} else {
		local_irq_save(flags);
		m = read_counter(&hpet->hpet_mc);
		write_counter(t + m + hpetp->hp_delta, &timer->hpet_compare);
	}

	isr = (1 << (devp - hpets->hp_dev));
	writeq(isr, &hpet->hpet_isr);
	writeq(g, &timer->hpet_config);
	local_irq_restore(flags);

	return 0;
}

static inline unsigned long hpet_time_div(unsigned long dis)
{
	unsigned long long m = 1000000000000000ULL;

	do_div(m, dis);

	return (unsigned long)m;
}

static int
hpet_ioctl_common(struct hpet_dev *devp, int cmd, unsigned long arg, int kernel)
{
	struct hpet_timer __iomem *timer;
	struct hpet __iomem *hpet;
	struct hpets *hpetp;
	int err;
	unsigned long v;

	switch (cmd) {
	case HPET_IE_OFF:
	case HPET_INFO:
	case HPET_EPI:
	case HPET_DPI:
	case HPET_IRQFREQ:
		timer = devp->hd_timer;
		hpet = devp->hd_hpet;
		hpetp = devp->hd_hpets;
		break;
	case HPET_IE_ON:
		return hpet_ioctl_ieon(devp);
	default:
		return -EINVAL;
	}

	err = 0;

	switch (cmd) {
	case HPET_IE_OFF:
		if ((devp->hd_flags & HPET_IE) == 0)
			break;
		v = readq(&timer->hpet_config);
		v &= ~Tn_INT_ENB_CNF_MASK;
		writeq(v, &timer->hpet_config);
		if (devp->hd_irq) {
			free_irq(devp->hd_irq, devp);
			devp->hd_irq = 0;
		}
		devp->hd_flags ^= HPET_IE;
		break;
	case HPET_INFO:
		{
			struct hpet_info info;

			info.hi_ireqfreq = hpet_time_div(hpetp->hp_period *
							 devp->hd_ireqfreq);
			info.hi_flags =
			    readq(&timer->hpet_config) & Tn_PER_INT_CAP_MASK;
			info.hi_hpet = devp->hd_hpets->hp_which;
			info.hi_timer = devp - devp->hd_hpets->hp_dev;
			if (copy_to_user((void __user *)arg, &info, sizeof(info)))
				err = -EFAULT;
			break;
		}
	case HPET_EPI:
		v = readq(&timer->hpet_config);
		if ((v & Tn_PER_INT_CAP_MASK) == 0) {
			err = -ENXIO;
			break;
		}
		devp->hd_flags |= HPET_PERIODIC;
		break;
	case HPET_DPI:
		v = readq(&timer->hpet_config);
		if ((v & Tn_PER_INT_CAP_MASK) == 0) {
			err = -ENXIO;
			break;
		}
		if (devp->hd_flags & HPET_PERIODIC &&
		    readq(&timer->hpet_config) & Tn_TYPE_CNF_MASK) {
			v = readq(&timer->hpet_config);
			v ^= Tn_TYPE_CNF_MASK;
			writeq(v, &timer->hpet_config);
		}
		devp->hd_flags &= ~HPET_PERIODIC;
		break;
	case HPET_IRQFREQ:
		if (!kernel && (arg > hpet_max_freq) &&
		    !capable(CAP_SYS_RESOURCE)) {
			err = -EACCES;
			break;
		}

		if (arg & (arg - 1)) {
			err = -EINVAL;
			break;
		}

		devp->hd_ireqfreq = hpet_time_div(hpetp->hp_period * arg);
	}

	return err;
}

static struct file_operations hpet_fops = {
	.owner = THIS_MODULE,
	.llseek = no_llseek,
	.read = hpet_read,
	.poll = hpet_poll,
	.ioctl = hpet_ioctl,
	.open = hpet_open,
	.release = hpet_release,
	.fasync = hpet_fasync,
	.mmap = hpet_mmap,
};

EXPORT_SYMBOL(hpet_alloc);
EXPORT_SYMBOL(hpet_register);
EXPORT_SYMBOL(hpet_unregister);
EXPORT_SYMBOL(hpet_control);

int hpet_register(struct hpet_task *tp, int periodic)
{
	unsigned int i;
	u64 mask;
	struct hpet_timer __iomem *timer;
	struct hpet_dev *devp;
	struct hpets *hpetp;

	switch (periodic) {
	case 1:
		mask = Tn_PER_INT_CAP_MASK;
		break;
	case 0:
		mask = 0;
		break;
	default:
		return -EINVAL;
	}

	spin_lock_irq(&hpet_task_lock);
	spin_lock(&hpet_lock);

	for (devp = NULL, hpetp = hpets; hpetp && !devp; hpetp = hpetp->hp_next)
		for (timer = hpetp->hp_hpet->hpet_timers, i = 0;
		     i < hpetp->hp_ntimer; i++, timer++) {
			if ((readq(&timer->hpet_config) & Tn_PER_INT_CAP_MASK)
			    != mask)
				continue;

			devp = &hpetp->hp_dev[i];

			if (devp->hd_flags & HPET_OPEN || devp->hd_task) {
				devp = NULL;
				continue;
			}

			tp->ht_opaque = devp;
			devp->hd_task = tp;
			break;
		}

	spin_unlock(&hpet_lock);
	spin_unlock_irq(&hpet_task_lock);

	if (tp->ht_opaque)
		return 0;
	else
		return -EBUSY;
}

static inline int hpet_tpcheck(struct hpet_task *tp)
{
	struct hpet_dev *devp;
	struct hpets *hpetp;

	devp = tp->ht_opaque;

	if (!devp)
		return -ENXIO;

	for (hpetp = hpets; hpetp; hpetp = hpetp->hp_next)
		if (devp >= hpetp->hp_dev
		    && devp < (hpetp->hp_dev + hpetp->hp_ntimer)
		    && devp->hd_hpet == hpetp->hp_hpet)
			return 0;

	return -ENXIO;
}

int hpet_unregister(struct hpet_task *tp)
{
	struct hpet_dev *devp;
	struct hpet_timer __iomem *timer;
	int err;

	if ((err = hpet_tpcheck(tp)))
		return err;

	spin_lock_irq(&hpet_task_lock);
	spin_lock(&hpet_lock);

	devp = tp->ht_opaque;
	if (devp->hd_task != tp) {
		spin_unlock(&hpet_lock);
		spin_unlock_irq(&hpet_task_lock);
		return -ENXIO;
	}

	timer = devp->hd_timer;
	writeq((readq(&timer->hpet_config) & ~Tn_INT_ENB_CNF_MASK),
	       &timer->hpet_config);
	devp->hd_flags &= ~(HPET_IE | HPET_PERIODIC);
	devp->hd_task = NULL;
	spin_unlock(&hpet_lock);
	spin_unlock_irq(&hpet_task_lock);

	return 0;
}

int hpet_control(struct hpet_task *tp, unsigned int cmd, unsigned long arg)
{
	struct hpet_dev *devp;
	int err;

	if ((err = hpet_tpcheck(tp)))
		return err;

	spin_lock_irq(&hpet_lock);
	devp = tp->ht_opaque;
	if (devp->hd_task != tp) {
		spin_unlock_irq(&hpet_lock);
		return -ENXIO;
	}
	spin_unlock_irq(&hpet_lock);
	return hpet_ioctl_common(devp, cmd, arg, 1);
}

static ctl_table hpet_table[] = {
	{
	 .ctl_name = 1,
	 .procname = "max-user-freq",
	 .data = &hpet_max_freq,
	 .maxlen = sizeof(int),
	 .mode = 0644,
	 .proc_handler = &proc_dointvec,
	 },
	{.ctl_name = 0}
};

static ctl_table hpet_root[] = {
	{
	 .ctl_name = 1,
	 .procname = "hpet",
	 .maxlen = 0,
	 .mode = 0555,
	 .child = hpet_table,
	 },
	{.ctl_name = 0}
};

static ctl_table dev_root[] = {
	{
	 .ctl_name = CTL_DEV,
	 .procname = "dev",
	 .maxlen = 0,
	 .mode = 0555,
	 .child = hpet_root,
	 },
	{.ctl_name = 0}
};

static struct ctl_table_header *sysctl_header;

static void hpet_register_interpolator(struct hpets *hpetp)
{
#ifdef	CONFIG_TIME_INTERPOLATION
	struct time_interpolator *ti;

	ti = kmalloc(sizeof(*ti), GFP_KERNEL);
	if (!ti)
		return;

	memset(ti, 0, sizeof(*ti));
	ti->source = TIME_SOURCE_MMIO64;
	ti->shift = 10;
	ti->addr = &hpetp->hp_hpet->hpet_mc;
	ti->frequency = hpet_time_div(hpets->hp_period);
	ti->drift = HPET_DRIFT;
	ti->mask = -1;

	hpetp->hp_interpolator = ti;
	register_time_interpolator(ti);
#endif
}

/*
 * Adjustment for when arming the timer with
 * initial conditions.  That is, main counter
 * ticks expired before interrupts are enabled.
 */
#define	TICK_CALIBRATE	(1000UL)

static unsigned long hpet_calibrate(struct hpets *hpetp)
{
	struct hpet_timer __iomem *timer = NULL;
	unsigned long t, m, count, i, flags, start;
	struct hpet_dev *devp;
	int j;
	struct hpet __iomem *hpet;

	for (j = 0, devp = hpetp->hp_dev; j < hpetp->hp_ntimer; j++, devp++)
		if ((devp->hd_flags & HPET_OPEN) == 0) {
			timer = devp->hd_timer;
			break;
		}

	if (!timer)
		return 0;

	hpet = hpets->hp_hpet;
	t = read_counter(&timer->hpet_compare);

	i = 0;
	count = hpet_time_div(hpetp->hp_period * TICK_CALIBRATE);

	local_irq_save(flags);

	start = read_counter(&hpet->hpet_mc);

	do {
		m = read_counter(&hpet->hpet_mc);
		write_counter(t + m + hpetp->hp_delta, &timer->hpet_compare);
	} while (i++, (m - start) < count);

	local_irq_restore(flags);

	return (m - start) / i;
}

int hpet_alloc(struct hpet_data *hdp)
{
	u64 cap, mcfg;
	struct hpet_dev *devp;
	u32 i, ntimer;
	struct hpets *hpetp;
	size_t siz;
	struct hpet __iomem *hpet;
	static struct hpets *last = (struct hpets *)0;
	unsigned long ns;

	/*
	 * hpet_alloc can be called by platform dependent code.
	 * if platform dependent code has allocated the hpet
	 * ACPI also reports hpet, then we catch it here.
	 */
	for (hpetp = hpets; hpetp; hpetp = hpetp->hp_next)
		if (hpetp->hp_hpet == hdp->hd_address)
			return 0;

	siz = sizeof(struct hpets) + ((hdp->hd_nirqs - 1) *
				      sizeof(struct hpet_dev));

	hpetp = kmalloc(siz, GFP_KERNEL);

	if (!hpetp)
		return -ENOMEM;

	memset(hpetp, 0, siz);

	hpetp->hp_which = hpet_nhpet++;
	hpetp->hp_hpet = hdp->hd_address;
	hpetp->hp_hpet_phys = hdp->hd_phys_address;

	hpetp->hp_ntimer = hdp->hd_nirqs;

	for (i = 0; i < hdp->hd_nirqs; i++)
		hpetp->hp_dev[i].hd_hdwirq = hdp->hd_irq[i];

	hpet = hpetp->hp_hpet;

	cap = readq(&hpet->hpet_cap);

	ntimer = ((cap & HPET_NUM_TIM_CAP_MASK) >> HPET_NUM_TIM_CAP_SHIFT) + 1;

	if (hpetp->hp_ntimer != ntimer) {
		printk(KERN_WARNING "hpet: number irqs doesn't agree"
		       " with number of timers\n");
		kfree(hpetp);
		return -ENODEV;
	}

	if (last)
		last->hp_next = hpetp;
	else
		hpets = hpetp;

	last = hpetp;

	hpetp->hp_period = (cap & HPET_COUNTER_CLK_PERIOD_MASK) >>
	    HPET_COUNTER_CLK_PERIOD_SHIFT;

	printk(KERN_INFO "hpet%d: at MMIO 0x%lx, IRQ%s",
		hpetp->hp_which, hdp->hd_phys_address,
		hpetp->hp_ntimer > 1 ? "s" : "");
	for (i = 0; i < hpetp->hp_ntimer; i++)
		printk("%s %d", i > 0 ? "," : "", hdp->hd_irq[i]);
	printk("\n");

	ns = hpetp->hp_period;	/* femptoseconds, 10^-15 */
	ns /= 1000000;		/* convert to nanoseconds, 10^-9 */
	printk(KERN_INFO "hpet%d: %ldns tick, %d %d-bit timers\n",
		hpetp->hp_which, ns, hpetp->hp_ntimer,
		cap & HPET_COUNTER_SIZE_MASK ? 64 : 32);

	mcfg = readq(&hpet->hpet_config);
	if ((mcfg & HPET_ENABLE_CNF_MASK) == 0) {
		write_counter(0L, &hpet->hpet_mc);
		mcfg |= HPET_ENABLE_CNF_MASK;
		writeq(mcfg, &hpet->hpet_config);
	}

	for (i = 0, devp = hpetp->hp_dev; i < hpetp->hp_ntimer;
	     i++, hpet_ntimer++, devp++) {
		unsigned long v;
		struct hpet_timer __iomem *timer;

		timer = &hpet->hpet_timers[devp - hpetp->hp_dev];
		v = readq(&timer->hpet_config);

		devp->hd_hpets = hpetp;
		devp->hd_hpet = hpet;
		devp->hd_timer = timer;

		/*
		 * If the timer was reserved by platform code,
		 * then make timer unavailable for opens.
		 */
		if (hdp->hd_state & (1 << i)) {
			devp->hd_flags = HPET_OPEN;
			continue;
		}

		init_waitqueue_head(&devp->hd_waitqueue);
	}

	hpetp->hp_delta = hpet_calibrate(hpetp);
	hpet_register_interpolator(hpetp);

	return 0;
}

static acpi_status hpet_resources(struct acpi_resource *res, void *data)
{
	struct hpet_data *hdp;
	acpi_status status;
	struct acpi_resource_address64 addr;
	struct hpets *hpetp;

	hdp = data;

	status = acpi_resource_to_address64(res, &addr);

	if (ACPI_SUCCESS(status)) {
		unsigned long size;

		size = addr.max_address_range - addr.min_address_range + 1;
		hdp->hd_phys_address = addr.min_address_range;
		hdp->hd_address = ioremap(addr.min_address_range, size);

		for (hpetp = hpets; hpetp; hpetp = hpetp->hp_next)
			if (hpetp->hp_hpet == hdp->hd_address)
				return -EBUSY;
	} else if (res->id == ACPI_RSTYPE_EXT_IRQ) {
		struct acpi_resource_ext_irq *irqp;
		int i;

		irqp = &res->data.extended_irq;

		if (irqp->number_of_interrupts > 0) {
			hdp->hd_nirqs = irqp->number_of_interrupts;

			for (i = 0; i < hdp->hd_nirqs; i++) {
				int rc =
				    acpi_register_gsi(irqp->interrupts[i],
						      irqp->edge_level,
						      irqp->active_high_low);
				if (rc < 0)
					return AE_ERROR;
				hdp->hd_irq[i] = rc;
			}
		}
	}

	return AE_OK;
}

static int hpet_acpi_add(struct acpi_device *device)
{
	acpi_status result;
	struct hpet_data data;

	memset(&data, 0, sizeof(data));

	result =
	    acpi_walk_resources(device->handle, METHOD_NAME__CRS,
				hpet_resources, &data);

	if (ACPI_FAILURE(result))
		return -ENODEV;

	if (!data.hd_address || !data.hd_nirqs) {
		printk("%s: no address or irqs in _CRS\n", __FUNCTION__);
		return -ENODEV;
	}

	return hpet_alloc(&data);
}

static int hpet_acpi_remove(struct acpi_device *device, int type)
{
	/* XXX need to unregister interpolator, dealloc mem, etc */
	return -EINVAL;
}

static struct acpi_driver hpet_acpi_driver = {
	.name = "hpet",
	.ids = "PNP0103",
	.ops = {
		.add = hpet_acpi_add,
		.remove = hpet_acpi_remove,
		},
};

static struct miscdevice hpet_misc = { HPET_MINOR, "hpet", &hpet_fops };

static int __init hpet_init(void)
{
	int result;

	result = misc_register(&hpet_misc);
	if (result < 0)
		return -ENODEV;

	sysctl_header = register_sysctl_table(dev_root, 0);

	result = acpi_bus_register_driver(&hpet_acpi_driver);
	if (result < 0) {
		if (sysctl_header)
			unregister_sysctl_table(sysctl_header);
		misc_deregister(&hpet_misc);
		return result;
	}

	return 0;
}

static void __exit hpet_exit(void)
{
	acpi_bus_unregister_driver(&hpet_acpi_driver);

	if (sysctl_header)
		unregister_sysctl_table(sysctl_header);
	misc_deregister(&hpet_misc);

	return;
}

module_init(hpet_init);
module_exit(hpet_exit);
MODULE_AUTHOR("Bob Picco <Robert.Picco@hp.com>");
MODULE_LICENSE("GPL");
