/* parport.h: sparc64 specific parport initialization and dma.
 *
 * Copyright (C) 1999  Eddie C. Dost  (ecd@skynet.be)
 */

#ifndef _ASM_SPARC64_PARPORT_H
#define _ASM_SPARC64_PARPORT_H 1

#include <asm/ebus.h>
#include <asm/ns87303.h>
#include <asm/of_device.h>
#include <asm/prom.h>

#define PARPORT_PC_MAX_PORTS	PARPORT_MAX

/*
 * While sparc64 doesn't have an ISA DMA API, we provide something that looks
 * close enough to make parport_pc happy
 */
#define HAS_DMA

static DEFINE_SPINLOCK(dma_spin_lock);

#define claim_dma_lock() \
({	unsigned long flags; \
	spin_lock_irqsave(&dma_spin_lock, flags); \
	flags; \
})

#define release_dma_lock(__flags) \
	spin_unlock_irqrestore(&dma_spin_lock, __flags);

static struct sparc_ebus_info {
	struct ebus_dma_info info;
	unsigned int addr;
	unsigned int count;
	int lock;

	struct parport *port;
} sparc_ebus_dmas[PARPORT_PC_MAX_PORTS];

static DECLARE_BITMAP(dma_slot_map, PARPORT_PC_MAX_PORTS);

static inline int request_dma(unsigned int dmanr, const char *device_id)
{
	if (dmanr >= PARPORT_PC_MAX_PORTS)
		return -EINVAL;
	if (xchg(&sparc_ebus_dmas[dmanr].lock, 1) != 0)
		return -EBUSY;
	return 0;
}

static inline void free_dma(unsigned int dmanr)
{
	if (dmanr >= PARPORT_PC_MAX_PORTS) {
		printk(KERN_WARNING "Trying to free DMA%d\n", dmanr);
		return;
	}
	if (xchg(&sparc_ebus_dmas[dmanr].lock, 0) == 0) {
		printk(KERN_WARNING "Trying to free free DMA%d\n", dmanr);
		return;
	}
}

static inline void enable_dma(unsigned int dmanr)
{
	ebus_dma_enable(&sparc_ebus_dmas[dmanr].info, 1);

	if (ebus_dma_request(&sparc_ebus_dmas[dmanr].info,
			     sparc_ebus_dmas[dmanr].addr,
			     sparc_ebus_dmas[dmanr].count))
		BUG();
}

static inline void disable_dma(unsigned int dmanr)
{
	ebus_dma_enable(&sparc_ebus_dmas[dmanr].info, 0);
}

static inline void clear_dma_ff(unsigned int dmanr)
{
	/* nothing */
}

static inline void set_dma_mode(unsigned int dmanr, char mode)
{
	ebus_dma_prepare(&sparc_ebus_dmas[dmanr].info, (mode != DMA_MODE_WRITE));
}

static inline void set_dma_addr(unsigned int dmanr, unsigned int addr)
{
	sparc_ebus_dmas[dmanr].addr = addr;
}

static inline void set_dma_count(unsigned int dmanr, unsigned int count)
{
	sparc_ebus_dmas[dmanr].count = count;
}

static inline unsigned int get_dma_residue(unsigned int dmanr)
{
	return ebus_dma_residue(&sparc_ebus_dmas[dmanr].info);
}

static int __devinit ecpp_probe(struct of_device *op, const struct of_device_id *match)
{
	unsigned long base = op->resource[0].start;
	unsigned long config = op->resource[1].start;
	unsigned long d_base = op->resource[2].start;
	unsigned long d_len;
	struct device_node *parent;
	struct parport *p;
	int slot, err;

	parent = op->node->parent;
	if (!strcmp(parent->name, "dma")) {
		p = parport_pc_probe_port(base, base + 0x400,
					  op->irqs[0], PARPORT_DMA_NOFIFO,
					  op->dev.parent->parent);
		if (!p)
			return -ENOMEM;
		dev_set_drvdata(&op->dev, p);
		return 0;
	}

	for (slot = 0; slot < PARPORT_PC_MAX_PORTS; slot++) {
		if (!test_and_set_bit(slot, dma_slot_map))
			break;
	}
	err = -ENODEV;
	if (slot >= PARPORT_PC_MAX_PORTS)
		goto out_err;

	spin_lock_init(&sparc_ebus_dmas[slot].info.lock);

	d_len = (op->resource[2].end - d_base) + 1UL;
	sparc_ebus_dmas[slot].info.regs =
		of_ioremap(&op->resource[2], 0, d_len, "ECPP DMA");

	if (!sparc_ebus_dmas[slot].info.regs)
		goto out_clear_map;

	sparc_ebus_dmas[slot].info.flags = 0;
	sparc_ebus_dmas[slot].info.callback = NULL;
	sparc_ebus_dmas[slot].info.client_cookie = NULL;
	sparc_ebus_dmas[slot].info.irq = 0xdeadbeef;
	strcpy(sparc_ebus_dmas[slot].info.name, "parport");
	if (ebus_dma_register(&sparc_ebus_dmas[slot].info))
		goto out_unmap_regs;

	ebus_dma_irq_enable(&sparc_ebus_dmas[slot].info, 1);

	/* Configure IRQ to Push Pull, Level Low */
	/* Enable ECP, set bit 2 of the CTR first */
	outb(0x04, base + 0x02);
	ns87303_modify(config, PCR,
		       PCR_EPP_ENABLE |
		       PCR_IRQ_ODRAIN,
		       PCR_ECP_ENABLE |
		       PCR_ECP_CLK_ENA |
		       PCR_IRQ_POLAR);

	/* CTR bit 5 controls direction of port */
	ns87303_modify(config, PTR,
		       0, PTR_LPT_REG_DIR);

	p = parport_pc_probe_port(base, base + 0x400,
				  op->irqs[0],
				  slot,
				  op->dev.parent);
	err = -ENOMEM;
	if (!p)
		goto out_disable_irq;

	dev_set_drvdata(&op->dev, p);

	return 0;

out_disable_irq:
	ebus_dma_irq_enable(&sparc_ebus_dmas[slot].info, 0);
	ebus_dma_unregister(&sparc_ebus_dmas[slot].info);

out_unmap_regs:
	of_iounmap(&op->resource[2], sparc_ebus_dmas[slot].info.regs, d_len);

out_clear_map:
	clear_bit(slot, dma_slot_map);

out_err:
	return err;
}

static int __devexit ecpp_remove(struct of_device *op)
{
	struct parport *p = dev_get_drvdata(&op->dev);
	int slot = p->dma;

	parport_pc_unregister_port(p);

	if (slot != PARPORT_DMA_NOFIFO) {
		unsigned long d_base = op->resource[2].start;
		unsigned long d_len;

		d_len = (op->resource[2].end - d_base) + 1UL;

		ebus_dma_irq_enable(&sparc_ebus_dmas[slot].info, 0);
		ebus_dma_unregister(&sparc_ebus_dmas[slot].info);
		of_iounmap(&op->resource[2],
			   sparc_ebus_dmas[slot].info.regs,
			   d_len);
		clear_bit(slot, dma_slot_map);
	}

	return 0;
}

static struct of_device_id ecpp_match[] = {
	{
		.name = "ecpp",
	},
	{
		.name = "parallel",
		.compatible = "ecpp",
	},
	{
		.name = "parallel",
		.compatible = "ns87317-ecpp",
	},
	{},
};

static struct of_platform_driver ecpp_driver = {
	.name			= "ecpp",
	.match_table		= ecpp_match,
	.probe			= ecpp_probe,
	.remove			= __devexit_p(ecpp_remove),
};

static int parport_pc_find_nonpci_ports(int autoirq, int autodma)
{
	of_register_driver(&ecpp_driver, &of_bus_type);

	return 0;
}

#endif /* !(_ASM_SPARC64_PARPORT_H */
