1 // SPDX-License-Identifier: GPL-2.0+
2 /*
3  * Copyright (C) 2015 Masahiro Yamada <yamada.masahiro@socionext.com>
4  */
5 
6 #include <linux/clk.h>
7 #include <linux/console.h>
8 #include <linux/io.h>
9 #include <linux/module.h>
10 #include <linux/of.h>
11 #include <linux/platform_device.h>
12 
13 #include "8250.h"
14 
15 /* Most (but not all) of UniPhier UART devices have 64-depth FIFO. */
16 #define UNIPHIER_UART_DEFAULT_FIFO_SIZE	64
17 
18 /*
19  * This hardware is similar to 8250, but its register map is a bit different:
20  *   - MMIO32 (regshift = 2)
21  *   - FCR is not at 2, but 3
22  *   - LCR and MCR are not at 3 and 4, they share 4
23  *   - No SCR (Instead, CHAR can be used as a scratch register)
24  *   - Divisor latch at 9, no divisor latch access bit
25  */
26 
27 #define UNIPHIER_UART_REGSHIFT		2
28 
29 /* bit[15:8] = CHAR, bit[7:0] = FCR */
30 #define UNIPHIER_UART_CHAR_FCR		(3 << (UNIPHIER_UART_REGSHIFT))
31 /* bit[15:8] = LCR, bit[7:0] = MCR */
32 #define UNIPHIER_UART_LCR_MCR		(4 << (UNIPHIER_UART_REGSHIFT))
33 /* Divisor Latch Register */
34 #define UNIPHIER_UART_DLR		(9 << (UNIPHIER_UART_REGSHIFT))
35 
36 struct uniphier8250_priv {
37 	int line;
38 	struct clk *clk;
39 	spinlock_t atomic_write_lock;
40 };
41 
42 #ifdef CONFIG_SERIAL_8250_CONSOLE
uniphier_early_console_setup(struct earlycon_device * device,const char * options)43 static int __init uniphier_early_console_setup(struct earlycon_device *device,
44 					       const char *options)
45 {
46 	if (!device->port.membase)
47 		return -ENODEV;
48 
49 	/* This hardware always expects MMIO32 register interface. */
50 	device->port.iotype = UPIO_MEM32;
51 	device->port.regshift = UNIPHIER_UART_REGSHIFT;
52 
53 	/*
54 	 * Do not touch the divisor register in early_serial8250_setup();
55 	 * we assume it has been initialized by a boot loader.
56 	 */
57 	device->baud = 0;
58 
59 	return early_serial8250_setup(device, options);
60 }
61 OF_EARLYCON_DECLARE(uniphier, "socionext,uniphier-uart",
62 		    uniphier_early_console_setup);
63 #endif
64 
65 /*
66  * The register map is slightly different from that of 8250.
67  * IO callbacks must be overridden for correct access to FCR, LCR, MCR and SCR.
68  */
uniphier_serial_in(struct uart_port * p,int offset)69 static unsigned int uniphier_serial_in(struct uart_port *p, int offset)
70 {
71 	unsigned int valshift = 0;
72 
73 	switch (offset) {
74 	case UART_SCR:
75 		/* No SCR for this hardware.  Use CHAR as a scratch register */
76 		valshift = 8;
77 		offset = UNIPHIER_UART_CHAR_FCR;
78 		break;
79 	case UART_LCR:
80 		valshift = 8;
81 		/* fall through */
82 	case UART_MCR:
83 		offset = UNIPHIER_UART_LCR_MCR;
84 		break;
85 	default:
86 		offset <<= UNIPHIER_UART_REGSHIFT;
87 		break;
88 	}
89 
90 	/*
91 	 * The return value must be masked with 0xff because some registers
92 	 * share the same offset that must be accessed by 32-bit write/read.
93 	 * 8 or 16 bit access to this hardware result in unexpected behavior.
94 	 */
95 	return (readl(p->membase + offset) >> valshift) & 0xff;
96 }
97 
uniphier_serial_out(struct uart_port * p,int offset,int value)98 static void uniphier_serial_out(struct uart_port *p, int offset, int value)
99 {
100 	unsigned int valshift = 0;
101 	bool normal = false;
102 
103 	switch (offset) {
104 	case UART_SCR:
105 		/* No SCR for this hardware.  Use CHAR as a scratch register */
106 		valshift = 8;
107 		/* fall through */
108 	case UART_FCR:
109 		offset = UNIPHIER_UART_CHAR_FCR;
110 		break;
111 	case UART_LCR:
112 		valshift = 8;
113 		/* Divisor latch access bit does not exist. */
114 		value &= ~UART_LCR_DLAB;
115 		/* fall through */
116 	case UART_MCR:
117 		offset = UNIPHIER_UART_LCR_MCR;
118 		break;
119 	default:
120 		offset <<= UNIPHIER_UART_REGSHIFT;
121 		normal = true;
122 		break;
123 	}
124 
125 	if (normal) {
126 		writel(value, p->membase + offset);
127 	} else {
128 		/*
129 		 * Special case: two registers share the same address that
130 		 * must be 32-bit accessed.  As this is not longer atomic safe,
131 		 * take a lock just in case.
132 		 */
133 		struct uniphier8250_priv *priv = p->private_data;
134 		unsigned long flags;
135 		u32 tmp;
136 
137 		spin_lock_irqsave(&priv->atomic_write_lock, flags);
138 		tmp = readl(p->membase + offset);
139 		tmp &= ~(0xff << valshift);
140 		tmp |= value << valshift;
141 		writel(tmp, p->membase + offset);
142 		spin_unlock_irqrestore(&priv->atomic_write_lock, flags);
143 	}
144 }
145 
146 /*
147  * This hardware does not have the divisor latch access bit.
148  * The divisor latch register exists at different address.
149  * Override dl_read/write callbacks.
150  */
uniphier_serial_dl_read(struct uart_8250_port * up)151 static int uniphier_serial_dl_read(struct uart_8250_port *up)
152 {
153 	return readl(up->port.membase + UNIPHIER_UART_DLR);
154 }
155 
uniphier_serial_dl_write(struct uart_8250_port * up,int value)156 static void uniphier_serial_dl_write(struct uart_8250_port *up, int value)
157 {
158 	writel(value, up->port.membase + UNIPHIER_UART_DLR);
159 }
160 
uniphier_of_serial_setup(struct device * dev,struct uart_port * port,struct uniphier8250_priv * priv)161 static int uniphier_of_serial_setup(struct device *dev, struct uart_port *port,
162 				    struct uniphier8250_priv *priv)
163 {
164 	int ret;
165 	u32 prop;
166 	struct device_node *np = dev->of_node;
167 
168 	ret = of_alias_get_id(np, "serial");
169 	if (ret < 0) {
170 		dev_err(dev, "failed to get alias id\n");
171 		return ret;
172 	}
173 	port->line = ret;
174 
175 	/* Get clk rate through clk driver */
176 	priv->clk = devm_clk_get(dev, NULL);
177 	if (IS_ERR(priv->clk)) {
178 		dev_err(dev, "failed to get clock\n");
179 		return PTR_ERR(priv->clk);
180 	}
181 
182 	ret = clk_prepare_enable(priv->clk);
183 	if (ret < 0)
184 		return ret;
185 
186 	port->uartclk = clk_get_rate(priv->clk);
187 
188 	/* Check for fifo size */
189 	if (of_property_read_u32(np, "fifo-size", &prop) == 0)
190 		port->fifosize = prop;
191 	else
192 		port->fifosize = UNIPHIER_UART_DEFAULT_FIFO_SIZE;
193 
194 	return 0;
195 }
196 
uniphier_uart_probe(struct platform_device * pdev)197 static int uniphier_uart_probe(struct platform_device *pdev)
198 {
199 	struct device *dev = &pdev->dev;
200 	struct uart_8250_port up;
201 	struct uniphier8250_priv *priv;
202 	struct resource *regs;
203 	void __iomem *membase;
204 	int irq;
205 	int ret;
206 
207 	regs = platform_get_resource(pdev, IORESOURCE_MEM, 0);
208 	if (!regs) {
209 		dev_err(dev, "failed to get memory resource\n");
210 		return -EINVAL;
211 	}
212 
213 	membase = devm_ioremap(dev, regs->start, resource_size(regs));
214 	if (!membase)
215 		return -ENOMEM;
216 
217 	irq = platform_get_irq(pdev, 0);
218 	if (irq < 0) {
219 		dev_err(dev, "failed to get IRQ number\n");
220 		return irq;
221 	}
222 
223 	priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL);
224 	if (!priv)
225 		return -ENOMEM;
226 
227 	memset(&up, 0, sizeof(up));
228 
229 	ret = uniphier_of_serial_setup(dev, &up.port, priv);
230 	if (ret < 0)
231 		return ret;
232 
233 	spin_lock_init(&priv->atomic_write_lock);
234 
235 	up.port.dev = dev;
236 	up.port.private_data = priv;
237 	up.port.mapbase = regs->start;
238 	up.port.mapsize = resource_size(regs);
239 	up.port.membase = membase;
240 	up.port.irq = irq;
241 
242 	up.port.type = PORT_16550A;
243 	up.port.iotype = UPIO_MEM32;
244 	up.port.regshift = UNIPHIER_UART_REGSHIFT;
245 	up.port.flags = UPF_FIXED_PORT | UPF_FIXED_TYPE;
246 	up.capabilities = UART_CAP_FIFO;
247 
248 	up.port.serial_in = uniphier_serial_in;
249 	up.port.serial_out = uniphier_serial_out;
250 	up.dl_read = uniphier_serial_dl_read;
251 	up.dl_write = uniphier_serial_dl_write;
252 
253 	ret = serial8250_register_8250_port(&up);
254 	if (ret < 0) {
255 		dev_err(dev, "failed to register 8250 port\n");
256 		clk_disable_unprepare(priv->clk);
257 		return ret;
258 	}
259 	priv->line = ret;
260 
261 	platform_set_drvdata(pdev, priv);
262 
263 	return 0;
264 }
265 
uniphier_uart_remove(struct platform_device * pdev)266 static int uniphier_uart_remove(struct platform_device *pdev)
267 {
268 	struct uniphier8250_priv *priv = platform_get_drvdata(pdev);
269 
270 	serial8250_unregister_port(priv->line);
271 	clk_disable_unprepare(priv->clk);
272 
273 	return 0;
274 }
275 
uniphier_uart_suspend(struct device * dev)276 static int __maybe_unused uniphier_uart_suspend(struct device *dev)
277 {
278 	struct uniphier8250_priv *priv = dev_get_drvdata(dev);
279 	struct uart_8250_port *up = serial8250_get_port(priv->line);
280 
281 	serial8250_suspend_port(priv->line);
282 
283 	if (!uart_console(&up->port) || console_suspend_enabled)
284 		clk_disable_unprepare(priv->clk);
285 
286 	return 0;
287 }
288 
uniphier_uart_resume(struct device * dev)289 static int __maybe_unused uniphier_uart_resume(struct device *dev)
290 {
291 	struct uniphier8250_priv *priv = dev_get_drvdata(dev);
292 	struct uart_8250_port *up = serial8250_get_port(priv->line);
293 	int ret;
294 
295 	if (!uart_console(&up->port) || console_suspend_enabled) {
296 		ret = clk_prepare_enable(priv->clk);
297 		if (ret)
298 			return ret;
299 	}
300 
301 	serial8250_resume_port(priv->line);
302 
303 	return 0;
304 }
305 
306 static const struct dev_pm_ops uniphier_uart_pm_ops = {
307 	SET_SYSTEM_SLEEP_PM_OPS(uniphier_uart_suspend, uniphier_uart_resume)
308 };
309 
310 static const struct of_device_id uniphier_uart_match[] = {
311 	{ .compatible = "socionext,uniphier-uart" },
312 	{ /* sentinel */ }
313 };
314 MODULE_DEVICE_TABLE(of, uniphier_uart_match);
315 
316 static struct platform_driver uniphier_uart_platform_driver = {
317 	.probe		= uniphier_uart_probe,
318 	.remove		= uniphier_uart_remove,
319 	.driver = {
320 		.name	= "uniphier-uart",
321 		.of_match_table = uniphier_uart_match,
322 		.pm = &uniphier_uart_pm_ops,
323 	},
324 };
325 module_platform_driver(uniphier_uart_platform_driver);
326 
327 MODULE_AUTHOR("Masahiro Yamada <yamada.masahiro@socionext.com>");
328 MODULE_DESCRIPTION("UniPhier UART driver");
329 MODULE_LICENSE("GPL");
330