cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

serial.c (6152B)


      1// SPDX-License-Identifier: GPL-2.0-only
      2/*
      3 * linux/arch/arm/mach-omap1/serial.c
      4 *
      5 * OMAP1 serial support.
      6 */
      7#include <linux/gpio.h>
      8#include <linux/module.h>
      9#include <linux/kernel.h>
     10#include <linux/init.h>
     11#include <linux/irq.h>
     12#include <linux/delay.h>
     13#include <linux/serial.h>
     14#include <linux/tty.h>
     15#include <linux/serial_8250.h>
     16#include <linux/serial_reg.h>
     17#include <linux/clk.h>
     18#include <linux/io.h>
     19
     20#include <asm/mach-types.h>
     21
     22#include "serial.h"
     23#include "mux.h"
     24#include "pm.h"
     25#include "soc.h"
     26
     27static struct clk * uart1_ck;
     28static struct clk * uart2_ck;
     29static struct clk * uart3_ck;
     30
     31static inline unsigned int omap_serial_in(struct plat_serial8250_port *up,
     32					  int offset)
     33{
     34	offset <<= up->regshift;
     35	return (unsigned int)__raw_readb(up->membase + offset);
     36}
     37
     38static inline void omap_serial_outp(struct plat_serial8250_port *p, int offset,
     39				    int value)
     40{
     41	offset <<= p->regshift;
     42	__raw_writeb(value, p->membase + offset);
     43}
     44
     45/*
     46 * Internal UARTs need to be initialized for the 8250 autoconfig to work
     47 * properly. Note that the TX watermark initialization may not be needed
     48 * once the 8250.c watermark handling code is merged.
     49 */
     50static void __init omap_serial_reset(struct plat_serial8250_port *p)
     51{
     52	omap_serial_outp(p, UART_OMAP_MDR1,
     53			UART_OMAP_MDR1_DISABLE);	/* disable UART */
     54	omap_serial_outp(p, UART_OMAP_SCR, 0x08);	/* TX watermark */
     55	omap_serial_outp(p, UART_OMAP_MDR1,
     56			UART_OMAP_MDR1_16X_MODE);	/* enable UART */
     57
     58	if (!cpu_is_omap15xx()) {
     59		omap_serial_outp(p, UART_OMAP_SYSC, 0x01);
     60		while (!(omap_serial_in(p, UART_OMAP_SYSC) & 0x01));
     61	}
     62}
     63
     64static struct plat_serial8250_port serial_platform_data[] = {
     65	{
     66		.mapbase	= OMAP1_UART1_BASE,
     67		.irq		= INT_UART1,
     68		.flags		= UPF_BOOT_AUTOCONF,
     69		.iotype		= UPIO_MEM,
     70		.regshift	= 2,
     71		.uartclk	= OMAP16XX_BASE_BAUD * 16,
     72	},
     73	{
     74		.mapbase	= OMAP1_UART2_BASE,
     75		.irq		= INT_UART2,
     76		.flags		= UPF_BOOT_AUTOCONF,
     77		.iotype		= UPIO_MEM,
     78		.regshift	= 2,
     79		.uartclk	= OMAP16XX_BASE_BAUD * 16,
     80	},
     81	{
     82		.mapbase	= OMAP1_UART3_BASE,
     83		.irq		= INT_UART3,
     84		.flags		= UPF_BOOT_AUTOCONF,
     85		.iotype		= UPIO_MEM,
     86		.regshift	= 2,
     87		.uartclk	= OMAP16XX_BASE_BAUD * 16,
     88	},
     89	{ },
     90};
     91
     92static struct platform_device serial_device = {
     93	.name			= "serial8250",
     94	.id			= PLAT8250_DEV_PLATFORM,
     95	.dev			= {
     96		.platform_data	= serial_platform_data,
     97	},
     98};
     99
    100/*
    101 * Note that on Innovator-1510 UART2 pins conflict with USB2.
    102 * By default UART2 does not work on Innovator-1510 if you have
    103 * USB OHCI enabled. To use UART2, you must disable USB2 first.
    104 */
    105void __init omap_serial_init(void)
    106{
    107	int i;
    108
    109	if (cpu_is_omap7xx()) {
    110		serial_platform_data[0].regshift = 0;
    111		serial_platform_data[1].regshift = 0;
    112		serial_platform_data[0].irq = INT_7XX_UART_MODEM_1;
    113		serial_platform_data[1].irq = INT_7XX_UART_MODEM_IRDA_2;
    114	}
    115
    116	if (cpu_is_omap15xx()) {
    117		serial_platform_data[0].uartclk = OMAP1510_BASE_BAUD * 16;
    118		serial_platform_data[1].uartclk = OMAP1510_BASE_BAUD * 16;
    119		serial_platform_data[2].uartclk = OMAP1510_BASE_BAUD * 16;
    120	}
    121
    122	for (i = 0; i < ARRAY_SIZE(serial_platform_data) - 1; i++) {
    123
    124		/* Don't look at UARTs higher than 2 for omap7xx */
    125		if (cpu_is_omap7xx() && i > 1) {
    126			serial_platform_data[i].membase = NULL;
    127			serial_platform_data[i].mapbase = 0;
    128			continue;
    129		}
    130
    131		/* Static mapping, never released */
    132		serial_platform_data[i].membase =
    133			ioremap(serial_platform_data[i].mapbase, SZ_2K);
    134		if (!serial_platform_data[i].membase) {
    135			printk(KERN_ERR "Could not ioremap uart%i\n", i);
    136			continue;
    137		}
    138		switch (i) {
    139		case 0:
    140			uart1_ck = clk_get(NULL, "uart1_ck");
    141			if (IS_ERR(uart1_ck))
    142				printk("Could not get uart1_ck\n");
    143			else {
    144				clk_prepare_enable(uart1_ck);
    145				if (cpu_is_omap15xx())
    146					clk_set_rate(uart1_ck, 12000000);
    147			}
    148			break;
    149		case 1:
    150			uart2_ck = clk_get(NULL, "uart2_ck");
    151			if (IS_ERR(uart2_ck))
    152				printk("Could not get uart2_ck\n");
    153			else {
    154				clk_prepare_enable(uart2_ck);
    155				if (cpu_is_omap15xx())
    156					clk_set_rate(uart2_ck, 12000000);
    157				else
    158					clk_set_rate(uart2_ck, 48000000);
    159			}
    160			break;
    161		case 2:
    162			uart3_ck = clk_get(NULL, "uart3_ck");
    163			if (IS_ERR(uart3_ck))
    164				printk("Could not get uart3_ck\n");
    165			else {
    166				clk_prepare_enable(uart3_ck);
    167				if (cpu_is_omap15xx())
    168					clk_set_rate(uart3_ck, 12000000);
    169			}
    170			break;
    171		}
    172		omap_serial_reset(&serial_platform_data[i]);
    173	}
    174}
    175
    176#ifdef CONFIG_OMAP_SERIAL_WAKE
    177
    178static irqreturn_t omap_serial_wake_interrupt(int irq, void *dev_id)
    179{
    180	/* Need to do something with serial port right after wake-up? */
    181	return IRQ_HANDLED;
    182}
    183
    184/*
    185 * Reroutes serial RX lines to GPIO lines for the duration of
    186 * sleep to allow waking up the device from serial port even
    187 * in deep sleep.
    188 */
    189void omap_serial_wake_trigger(int enable)
    190{
    191	if (!cpu_is_omap16xx())
    192		return;
    193
    194	if (uart1_ck != NULL) {
    195		if (enable)
    196			omap_cfg_reg(V14_16XX_GPIO37);
    197		else
    198			omap_cfg_reg(V14_16XX_UART1_RX);
    199	}
    200	if (uart2_ck != NULL) {
    201		if (enable)
    202			omap_cfg_reg(R9_16XX_GPIO18);
    203		else
    204			omap_cfg_reg(R9_16XX_UART2_RX);
    205	}
    206	if (uart3_ck != NULL) {
    207		if (enable)
    208			omap_cfg_reg(L14_16XX_GPIO49);
    209		else
    210			omap_cfg_reg(L14_16XX_UART3_RX);
    211	}
    212}
    213
    214static void __init omap_serial_set_port_wakeup(int gpio_nr)
    215{
    216	int ret;
    217
    218	ret = gpio_request(gpio_nr, "UART wake");
    219	if (ret < 0) {
    220		printk(KERN_ERR "Could not request UART wake GPIO: %i\n",
    221		       gpio_nr);
    222		return;
    223	}
    224	gpio_direction_input(gpio_nr);
    225	ret = request_irq(gpio_to_irq(gpio_nr), &omap_serial_wake_interrupt,
    226			  IRQF_TRIGGER_RISING, "serial wakeup", NULL);
    227	if (ret) {
    228		gpio_free(gpio_nr);
    229		printk(KERN_ERR "No interrupt for UART wake GPIO: %i\n",
    230		       gpio_nr);
    231		return;
    232	}
    233	enable_irq_wake(gpio_to_irq(gpio_nr));
    234}
    235
    236int __init omap_serial_wakeup_init(void)
    237{
    238	if (!cpu_is_omap16xx())
    239		return 0;
    240
    241	if (uart1_ck != NULL)
    242		omap_serial_set_port_wakeup(37);
    243	if (uart2_ck != NULL)
    244		omap_serial_set_port_wakeup(18);
    245	if (uart3_ck != NULL)
    246		omap_serial_set_port_wakeup(49);
    247
    248	return 0;
    249}
    250
    251#endif	/* CONFIG_OMAP_SERIAL_WAKE */
    252
    253static int __init omap_init(void)
    254{
    255	if (!cpu_class_is_omap1())
    256		return -ENODEV;
    257
    258	return platform_device_register(&serial_device);
    259}
    260arch_initcall(omap_init);