/*
 * 8250_moxa.c - MOXA Smartio/Industio MUE multiport serial driver.
 *
 * Author: Mathieu OTHACEHE <m.othacehe@gmail.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/module.h>
#include <linux/pci.h>

#include "8250.h"

#define	PCI_DEVICE_ID_MOXA_CP102E	0x1024
#define	PCI_DEVICE_ID_MOXA_CP102EL	0x1025
#define	PCI_DEVICE_ID_MOXA_CP104EL_A	0x1045
#define	PCI_DEVICE_ID_MOXA_CP114EL	0x1144
#define	PCI_DEVICE_ID_MOXA_CP116E_A_A	0x1160
#define	PCI_DEVICE_ID_MOXA_CP116E_A_B	0x1161
#define	PCI_DEVICE_ID_MOXA_CP118EL_A	0x1182
#define	PCI_DEVICE_ID_MOXA_CP118E_A_I	0x1183
#define	PCI_DEVICE_ID_MOXA_CP132EL	0x1322
#define	PCI_DEVICE_ID_MOXA_CP134EL_A	0x1342
#define	PCI_DEVICE_ID_MOXA_CP138E_A	0x1381
#define	PCI_DEVICE_ID_MOXA_CP168EL_A	0x1683

#define MOXA_BASE_BAUD 921600
#define MOXA_UART_OFFSET 0x200
#define MOXA_BASE_BAR 1

struct moxa8250_board {
	unsigned int num_ports;
	int line[0];
};

enum {
	moxa8250_2p = 0,
	moxa8250_4p,
	moxa8250_8p
};

static struct moxa8250_board moxa8250_boards[] = {
	[moxa8250_2p] = { .num_ports = 2},
	[moxa8250_4p] = { .num_ports = 4},
	[moxa8250_8p] = { .num_ports = 8},
};

static int moxa8250_probe(struct pci_dev *pdev, const struct pci_device_id *id)
{
	struct uart_8250_port uart;
	struct moxa8250_board *brd;
	void __iomem *ioaddr;
	resource_size_t baseaddr;
	unsigned int i, nr_ports;
	unsigned int offset;
	int ret;

	brd = &moxa8250_boards[id->driver_data];
	nr_ports = brd->num_ports;

	ret = pcim_enable_device(pdev);
	if (ret)
		return ret;

	brd = devm_kzalloc(&pdev->dev, sizeof(struct moxa8250_board) +
			   sizeof(unsigned int) * nr_ports, GFP_KERNEL);
	if (!brd)
		return -ENOMEM;

	memset(&uart, 0, sizeof(struct uart_8250_port));

	uart.port.dev = &pdev->dev;
	uart.port.irq = pdev->irq;
	uart.port.uartclk = MOXA_BASE_BAUD * 16;
	uart.port.flags = UPF_SKIP_TEST | UPF_BOOT_AUTOCONF | UPF_SHARE_IRQ;

	baseaddr = pci_resource_start(pdev, MOXA_BASE_BAR);
	ioaddr = pcim_iomap(pdev, MOXA_BASE_BAR, 0);
	if (!ioaddr)
		return -ENOMEM;

	for (i = 0; i < nr_ports; i++) {

		/*
		 * MOXA Smartio MUE boards with 4 ports have
		 * a different offset for port #3
		 */
		if (nr_ports == 4 && i == 3)
			offset = 7 * MOXA_UART_OFFSET;
		else
			offset = i * MOXA_UART_OFFSET;

		uart.port.iotype = UPIO_MEM;
		uart.port.iobase = 0;
		uart.port.mapbase = baseaddr + offset;
		uart.port.membase = ioaddr + offset;
		uart.port.regshift = 0;

		dev_dbg(&pdev->dev, "Setup PCI port: port %lx, irq %d, type %d\n",
			uart.port.iobase, uart.port.irq, uart.port.iotype);

		brd->line[i] = serial8250_register_8250_port(&uart);
		if (brd->line[i] < 0) {
			dev_err(&pdev->dev,
				"Couldn't register serial port %lx, irq %d, type %d, error %d\n",
				uart.port.iobase, uart.port.irq,
				uart.port.iotype, brd->line[i]);
			break;
		}
	}

	pci_set_drvdata(pdev, brd);
	return 0;
}

static void moxa8250_remove(struct pci_dev *pdev)
{
	struct moxa8250_board *brd = pci_get_drvdata(pdev);
	unsigned int i;

	for (i = 0; i < brd->num_ports; i++)
		serial8250_unregister_port(brd->line[i]);
}

#define MOXA_DEVICE(id, data) { PCI_VDEVICE(MOXA, id), (kernel_ulong_t)data }

static const struct pci_device_id pci_ids[] = {
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP102E, moxa8250_2p),
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP102EL, moxa8250_2p),
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP104EL_A, moxa8250_4p),
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP114EL, moxa8250_4p),
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP116E_A_A, moxa8250_8p),
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP116E_A_B, moxa8250_8p),
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP118EL_A, moxa8250_8p),
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP118E_A_I, moxa8250_8p),
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP132EL, moxa8250_2p),
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP134EL_A, moxa8250_4p),
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP138E_A, moxa8250_8p),
	MOXA_DEVICE(PCI_DEVICE_ID_MOXA_CP168EL_A, moxa8250_8p),
	{0}
};
MODULE_DEVICE_TABLE(pci, pci_ids);

static struct pci_driver moxa8250_pci_driver = {
	.name           = "8250_moxa",
	.id_table       = pci_ids,
	.probe          = moxa8250_probe,
	.remove         = moxa8250_remove,
};

module_pci_driver(moxa8250_pci_driver);

MODULE_AUTHOR("Mathieu OTHACEHE");
MODULE_DESCRIPTION("MOXA SmartIO MUE driver");
MODULE_LICENSE("GPL v2");
