// SPDX-License-Identifier: GPL-2.0-only
/*
 * linux/arch/arm/mach-omap1/serial.c
 *
 * OMAP1 serial support.
 */
#include <linux/gpio/machine.h>
#include <linux/gpio/consumer.h>
#include <linux/module.h>
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/irq.h>
#include <linux/delay.h>
#include <linux/serial.h>
#include <linux/tty.h>
#include <linux/serial_8250.h>
#include <linux/serial_reg.h>
#include <linux/clk.h>
#include <linux/io.h>

#include <asm/mach-types.h>

#include "common.h"
#include "serial.h"
#include "mux.h"
#include "pm.h"
#include "soc.h"

static struct clk * uart1_ck;
static struct clk * uart2_ck;
static struct clk * uart3_ck;

static inline unsigned int omap_serial_in(struct plat_serial8250_port *up,
					  int offset)
{
	offset <<= up->regshift;
	return (unsigned int)__raw_readb(up->membase + offset);
}

static inline void omap_serial_outp(struct plat_serial8250_port *p, int offset,
				    int value)
{
	offset <<= p->regshift;
	__raw_writeb(value, p->membase + offset);
}

/*
 * Internal UARTs need to be initialized for the 8250 autoconfig to work
 * properly. Note that the TX watermark initialization may not be needed
 * once the 8250.c watermark handling code is merged.
 */
static void __init omap_serial_reset(struct plat_serial8250_port *p)
{
	omap_serial_outp(p, UART_OMAP_MDR1,
			UART_OMAP_MDR1_DISABLE);	/* disable UART */
	omap_serial_outp(p, UART_OMAP_SCR, 0x08);	/* TX watermark */
	omap_serial_outp(p, UART_OMAP_MDR1,
			UART_OMAP_MDR1_16X_MODE);	/* enable UART */

	if (!cpu_is_omap15xx()) {
		omap_serial_outp(p, UART_OMAP_SYSC, 0x01);
		while (!(omap_serial_in(p, UART_OMAP_SYSC) & 0x01));
	}
}

static struct plat_serial8250_port serial_platform_data[] = {
	{
		.mapbase	= OMAP1_UART1_BASE,
		.irq		= INT_UART1,
		.flags		= UPF_BOOT_AUTOCONF,
		.iotype		= UPIO_MEM,
		.regshift	= 2,
		.uartclk	= OMAP16XX_BASE_BAUD * 16,
	},
	{
		.mapbase	= OMAP1_UART2_BASE,
		.irq		= INT_UART2,
		.flags		= UPF_BOOT_AUTOCONF,
		.iotype		= UPIO_MEM,
		.regshift	= 2,
		.uartclk	= OMAP16XX_BASE_BAUD * 16,
	},
	{
		.mapbase	= OMAP1_UART3_BASE,
		.irq		= INT_UART3,
		.flags		= UPF_BOOT_AUTOCONF,
		.iotype		= UPIO_MEM,
		.regshift	= 2,
		.uartclk	= OMAP16XX_BASE_BAUD * 16,
	},
	{ },
};

static struct platform_device serial_device = {
	.name			= "serial8250",
	.id			= PLAT8250_DEV_PLATFORM,
	.dev			= {
		.platform_data	= serial_platform_data,
	},
};

/*
 * Note that on Innovator-1510 UART2 pins conflict with USB2.
 * By default UART2 does not work on Innovator-1510 if you have
 * USB OHCI enabled. To use UART2, you must disable USB2 first.
 */
void __init omap_serial_init(void)
{
	int i;

	if (cpu_is_omap15xx()) {
		serial_platform_data[0].uartclk = OMAP1510_BASE_BAUD * 16;
		serial_platform_data[1].uartclk = OMAP1510_BASE_BAUD * 16;
		serial_platform_data[2].uartclk = OMAP1510_BASE_BAUD * 16;
	}

	for (i = 0; i < ARRAY_SIZE(serial_platform_data) - 1; i++) {
		/* Static mapping, never released */
		serial_platform_data[i].membase =
			ioremap(serial_platform_data[i].mapbase, SZ_2K);
		if (!serial_platform_data[i].membase) {
			printk(KERN_ERR "Could not ioremap uart%i\n", i);
			continue;
		}
		switch (i) {
		case 0:
			uart1_ck = clk_get(NULL, "uart1_ck");
			if (IS_ERR(uart1_ck))
				printk("Could not get uart1_ck\n");
			else {
				clk_prepare_enable(uart1_ck);
				if (cpu_is_omap15xx())
					clk_set_rate(uart1_ck, 12000000);
			}
			break;
		case 1:
			uart2_ck = clk_get(NULL, "uart2_ck");
			if (IS_ERR(uart2_ck))
				printk("Could not get uart2_ck\n");
			else {
				clk_prepare_enable(uart2_ck);
				if (cpu_is_omap15xx())
					clk_set_rate(uart2_ck, 12000000);
				else
					clk_set_rate(uart2_ck, 48000000);
			}
			break;
		case 2:
			uart3_ck = clk_get(NULL, "uart3_ck");
			if (IS_ERR(uart3_ck))
				printk("Could not get uart3_ck\n");
			else {
				clk_prepare_enable(uart3_ck);
				if (cpu_is_omap15xx())
					clk_set_rate(uart3_ck, 12000000);
			}
			break;
		}
		omap_serial_reset(&serial_platform_data[i]);
	}
}

#ifdef CONFIG_OMAP_SERIAL_WAKE

static irqreturn_t omap_serial_wake_interrupt(int irq, void *dev_id)
{
	/* Need to do something with serial port right after wake-up? */
	return IRQ_HANDLED;
}

/*
 * Reroutes serial RX lines to GPIO lines for the duration of
 * sleep to allow waking up the device from serial port even
 * in deep sleep.
 */
void omap_serial_wake_trigger(int enable)
{
	if (!cpu_is_omap16xx())
		return;

	if (uart1_ck != NULL) {
		if (enable)
			omap_cfg_reg(V14_16XX_GPIO37);
		else
			omap_cfg_reg(V14_16XX_UART1_RX);
	}
	if (uart2_ck != NULL) {
		if (enable)
			omap_cfg_reg(R9_16XX_GPIO18);
		else
			omap_cfg_reg(R9_16XX_UART2_RX);
	}
	if (uart3_ck != NULL) {
		if (enable)
			omap_cfg_reg(L14_16XX_GPIO49);
		else
			omap_cfg_reg(L14_16XX_UART3_RX);
	}
}

static void __init omap_serial_set_port_wakeup(int idx)
{
	struct gpio_desc *d;
	int ret;

	d = gpiod_get_index(NULL, "wakeup", idx, GPIOD_IN);
	if (IS_ERR(d)) {
		pr_err("Unable to get UART wakeup GPIO descriptor\n");
		return;
	}
	ret = request_irq(gpiod_to_irq(d), &omap_serial_wake_interrupt,
			  IRQF_TRIGGER_RISING, "serial wakeup", NULL);
	if (ret) {
		gpiod_put(d);
		pr_err("No interrupt for UART%d wake GPIO\n", idx + 1);
		return;
	}
	enable_irq_wake(gpiod_to_irq(d));
}


int __init omap_serial_wakeup_init(void)
{
	if (!cpu_is_omap16xx())
		return 0;

	if (uart1_ck != NULL)
		omap_serial_set_port_wakeup(0);
	if (uart2_ck != NULL)
		omap_serial_set_port_wakeup(1);
	if (uart3_ck != NULL)
		omap_serial_set_port_wakeup(2);

	return 0;
}

#endif	/* CONFIG_OMAP_SERIAL_WAKE */

static int __init omap_init(void)
{
	if (!cpu_class_is_omap1())
		return -ENODEV;

	return platform_device_register(&serial_device);
}
arch_initcall(omap_init);
