1 /* uart_xlnx_ps.c - Xilinx Zynq family serial driver */
2 
3 /*
4  * Copyright (c) 2018 Xilinx, Inc.
5  *
6  * SPDX-License-Identifier: Apache-2.0
7  */
8 
9 #define DT_DRV_COMPAT xlnx_xuartps
10 
11 /**
12  * @brief Xilinx Zynq Family Serial Driver
13  *
14  * This is the driver for the Xilinx Zynq family cadence serial device.
15  *
16  * Before individual UART port can be used, uart_xlnx_ps_init() has to be
17  * called to setup the port.
18  *
19  * - the following macro for the number of bytes between register addresses:
20  *
21  *  UART_REG_ADDR_INTERVAL
22  */
23 
24 #include <errno.h>
25 #include <zephyr/kernel.h>
26 #include <zephyr/arch/cpu.h>
27 #include <zephyr/types.h>
28 #include <soc.h>
29 
30 #include <zephyr/init.h>
31 #include <zephyr/toolchain.h>
32 #include <zephyr/linker/sections.h>
33 #include <zephyr/drivers/uart.h>
34 #include <zephyr/sys/sys_io.h>
35 #include <zephyr/irq.h>
36 
37 #ifdef CONFIG_PINCTRL
38 #include <zephyr/drivers/pinctrl.h>
39 #endif
40 
41 /* For all register offsets and bits / bit masks:
42  * Comp. Xilinx Zynq-7000 Technical Reference Manual (ug585), chap. B.33
43  */
44 
45 /* Register offsets within the UART device's register space */
46 #define XUARTPS_CR_OFFSET	0x0000U  /**< Control Register [8:0] */
47 #define XUARTPS_MR_OFFSET	0x0004U  /**< Mode Register [9:0] */
48 #define XUARTPS_IER_OFFSET	0x0008U  /**< Interrupt Enable [12:0] */
49 #define XUARTPS_IDR_OFFSET	0x000CU  /**< Interrupt Disable [12:0] */
50 #define XUARTPS_IMR_OFFSET	0x0010U  /**< Interrupt Mask [12:0] */
51 #define XUARTPS_ISR_OFFSET	0x0014U  /**< Interrupt Status [12:0]*/
52 #define XUARTPS_BAUDGEN_OFFSET	0x0018U  /**< Baud Rate Generator [15:0] */
53 #define XUARTPS_RXTOUT_OFFSET	0x001CU  /**< RX Timeout [7:0] */
54 #define XUARTPS_RXWM_OFFSET	0x0020U  /**< RX FIFO Trigger Level [5:0] */
55 #define XUARTPS_MODEMCR_OFFSET	0x0024U  /**< Modem Control [5:0] */
56 #define XUARTPS_MODEMSR_OFFSET	0x0028U  /**< Modem Status [8:0] */
57 #define XUARTPS_SR_OFFSET	0x002CU  /**< Channel Status [14:0] */
58 #define XUARTPS_FIFO_OFFSET	0x0030U  /**< FIFO [7:0] */
59 #define XUARTPS_BAUDDIV_OFFSET	0x0034U  /**< Baud Rate Divider [7:0] */
60 #define XUARTPS_FLOWDEL_OFFSET	0x0038U  /**< Flow Delay [5:0] */
61 #define XUARTPS_TXWM_OFFSET	0x0044U  /**< TX FIFO Trigger Level [5:0] */
62 #define XUARTPS_RXBS_OFFSET	0x0048U  /**< RX FIFO Byte Status [11:0] */
63 
64 /* Control Register Bits Definition */
65 #define XUARTPS_CR_STOPBRK	0x00000100U  /**< Stop transmission of break */
66 #define XUARTPS_CR_STARTBRK	0x00000080U  /**< Set break */
67 #define XUARTPS_CR_TORST	0x00000040U  /**< RX timeout counter restart */
68 #define XUARTPS_CR_TX_DIS	0x00000020U  /**< TX disabled. */
69 #define XUARTPS_CR_TX_EN	0x00000010U  /**< TX enabled */
70 #define XUARTPS_CR_RX_DIS	0x00000008U  /**< RX disabled. */
71 #define XUARTPS_CR_RX_EN	0x00000004U  /**< RX enabled */
72 #define XUARTPS_CR_EN_DIS_MASK	0x0000003CU  /**< Enable/disable Mask */
73 #define XUARTPS_CR_TXRST	0x00000002U  /**< TX logic reset */
74 #define XUARTPS_CR_RXRST	0x00000001U  /**< RX logic reset */
75 
76 /* Mode Register Bits Definition */
77 #define XUARTPS_MR_CCLK			0x00000400U /**< Input clock select */
78 #define XUARTPS_MR_CHMODE_R_LOOP	0x00000300U /**< Remote loopback mode */
79 #define XUARTPS_MR_CHMODE_L_LOOP	0x00000200U /**< Local loopback mode */
80 #define XUARTPS_MR_CHMODE_ECHO		0x00000100U /**< Auto echo mode */
81 #define XUARTPS_MR_CHMODE_NORM		0x00000000U /**< Normal mode */
82 #define XUARTPS_MR_CHMODE_SHIFT		8U  /**< Mode shift */
83 #define XUARTPS_MR_CHMODE_MASK		0x00000300U /**< Mode mask */
84 #define XUARTPS_MR_STOPMODE_2_BIT	0x00000080U /**< 2 stop bits */
85 #define XUARTPS_MR_STOPMODE_1_5_BIT	0x00000040U /**< 1.5 stop bits */
86 #define XUARTPS_MR_STOPMODE_1_BIT	0x00000000U /**< 1 stop bit */
87 #define XUARTPS_MR_STOPMODE_SHIFT	6U  /**< Stop bits shift */
88 #define XUARTPS_MR_STOPMODE_MASK	0x000000A0U /**< Stop bits mask */
89 #define XUARTPS_MR_PARITY_NONE		0x00000020U /**< No parity mode */
90 #define XUARTPS_MR_PARITY_MARK		0x00000018U /**< Mark parity mode */
91 #define XUARTPS_MR_PARITY_SPACE		0x00000010U /**< Space parity mode */
92 #define XUARTPS_MR_PARITY_ODD		0x00000008U /**< Odd parity mode */
93 #define XUARTPS_MR_PARITY_EVEN		0x00000000U /**< Even parity mode */
94 #define XUARTPS_MR_PARITY_SHIFT		3U  /**< Parity setting shift */
95 #define XUARTPS_MR_PARITY_MASK		0x00000038U /**< Parity mask */
96 #define XUARTPS_MR_CHARLEN_6_BIT	0x00000006U /**< 6 bits data */
97 #define XUARTPS_MR_CHARLEN_7_BIT	0x00000004U /**< 7 bits data */
98 #define XUARTPS_MR_CHARLEN_8_BIT	0x00000000U /**< 8 bits data */
99 #define XUARTPS_MR_CHARLEN_SHIFT	1U  /**< Data Length shift */
100 #define XUARTPS_MR_CHARLEN_MASK		0x00000006U /**< Data length mask */
101 #define XUARTPS_MR_CLKSEL		0x00000001U /**< Input clock select */
102 
103 /* Interrupt Register Bits Definition */
104 #define XUARTPS_IXR_RBRK	0x00002000U /**< Rx FIFO break detect interrupt */
105 #define XUARTPS_IXR_TOVR	0x00001000U /**< Tx FIFO Overflow interrupt */
106 #define XUARTPS_IXR_TNFUL	0x00000800U /**< Tx FIFO Nearly Full interrupt */
107 #define XUARTPS_IXR_TTRIG	0x00000400U /**< Tx Trig interrupt */
108 #define XUARTPS_IXR_DMS		0x00000200U /**< Modem status change interrupt */
109 #define XUARTPS_IXR_TOUT	0x00000100U /**< Timeout error interrupt */
110 #define XUARTPS_IXR_PARITY	0x00000080U /**< Parity error interrupt */
111 #define XUARTPS_IXR_FRAMING	0x00000040U /**< Framing error interrupt */
112 #define XUARTPS_IXR_RXOVR	0x00000020U /**< Overrun error interrupt */
113 #define XUARTPS_IXR_TXFULL	0x00000010U /**< TX FIFO full interrupt. */
114 #define XUARTPS_IXR_TXEMPTY	0x00000008U /**< TX FIFO empty interrupt. */
115 #define XUARTPS_IXR_RXFULL	0x00000004U /**< RX FIFO full interrupt. */
116 #define XUARTPS_IXR_RXEMPTY	0x00000002U /**< RX FIFO empty interrupt. */
117 #define XUARTPS_IXR_RTRIG	0x00000001U /**< RX FIFO trigger interrupt. */
118 #define XUARTPS_IXR_MASK	0x00003FFFU /**< Valid bit mask */
119 
120 /* Modem Control Register Bits Definition */
121 #define XUARTPS_MODEMCR_FCM_RTS_CTS	0x00000020 /**< RTS/CTS hardware flow control. */
122 #define XUARTPS_MODEMCR_FCM_NONE	0x00000000 /**< No hardware flow control. */
123 #define XUARTPS_MODEMCR_FCM_MASK	0x00000020 /**< Hardware flow control mask. */
124 #define XUARTPS_MODEMCR_RTS_SHIFT	1U         /**< RTS bit shift */
125 #define XUARTPS_MODEMCR_DTR_SHIFT	0U         /**< DTR bit shift */
126 
127 /* Channel Status Register */
128 #define XUARTPS_SR_TNFUL	0x00004000U /**< TX FIFO Nearly Full Status */
129 #define XUARTPS_SR_TTRIG	0x00002000U /**< TX FIFO Trigger Status */
130 #define XUARTPS_SR_FLOWDEL	0x00001000U /**< RX FIFO fill over flow delay */
131 #define XUARTPS_SR_TACTIVE	0x00000800U /**< TX active */
132 #define XUARTPS_SR_RACTIVE	0x00000400U /**< RX active */
133 #define XUARTPS_SR_TXFULL	0x00000010U /**< TX FIFO full */
134 #define XUARTPS_SR_TXEMPTY	0x00000008U /**< TX FIFO empty */
135 #define XUARTPS_SR_RXFULL	0x00000004U /**< RX FIFO full */
136 #define XUARTPS_SR_RXEMPTY	0x00000002U /**< RX FIFO empty */
137 #define XUARTPS_SR_RTRIG	0x00000001U /**< RX FIFO fill over trigger */
138 
139 /** Device configuration structure */
140 struct uart_xlnx_ps_dev_config {
141 	DEVICE_MMIO_ROM;
142 	uint32_t sys_clk_freq;
143 #ifdef CONFIG_UART_INTERRUPT_DRIVEN
144 	uart_irq_config_func_t irq_config_func;
145 #endif
146 #ifdef CONFIG_PINCTRL
147 	const struct pinctrl_dev_config *pincfg;
148 #endif
149 	uint32_t baud_rate;
150 };
151 
152 /** Device data structure */
153 struct uart_xlnx_ps_dev_data_t {
154 	DEVICE_MMIO_RAM;
155 	uint32_t parity;
156 	uint32_t stopbits;
157 	uint32_t databits;
158 	uint32_t flowctrl;
159 
160 #ifdef CONFIG_UART_INTERRUPT_DRIVEN
161 	uart_irq_callback_user_data_t user_cb;
162 	void *user_data;
163 #endif
164 };
165 
166 /**
167  * @brief Disables the UART's RX and TX function.
168  *
169  * Writes 'Disable RX' and 'Disable TX' command bits into the respective
170  * UART's Command Register, thus disabling the operation of the UART.
171  *
172  * While writing the disable command bits, the opposing enable command
173  * bits, which are set when enabling the UART, are cleared.
174  *
175  * This function must be called before any configuration parameters
176  * of the UART are modified at run-time.
177  *
178  * @param reg_base Base address of the respective UART's register space.
179  */
xlnx_ps_disable_uart(uintptr_t reg_base)180 static void xlnx_ps_disable_uart(uintptr_t reg_base)
181 {
182 	uint32_t reg_val = sys_read32(reg_base + XUARTPS_CR_OFFSET);
183 
184 	reg_val &= (~XUARTPS_CR_EN_DIS_MASK);
185 	/* Set control register bits [5]: TX_DIS and [3]: RX_DIS */
186 	reg_val |= XUARTPS_CR_TX_DIS | XUARTPS_CR_RX_DIS;
187 	sys_write32(reg_val, reg_base + XUARTPS_CR_OFFSET);
188 }
189 
190 /**
191  * @brief Enables the UART's RX and TX function.
192  *
193  * Writes 'Enable RX' and 'Enable TX' command bits into the respective
194  * UART's Command Register, thus enabling the operation of the UART.
195  *
196  * While writing the enable command bits, the opposing disable command
197  * bits, which are set when disabling the UART, are cleared.
198  *
199  * This function must not be called while any configuration parameters
200  * of the UART are being modified at run-time.
201  *
202  * @param reg_base Base address of the respective UART's register space.
203  */
xlnx_ps_enable_uart(uintptr_t reg_base)204 static void xlnx_ps_enable_uart(uintptr_t reg_base)
205 {
206 	uint32_t reg_val = sys_read32(reg_base + XUARTPS_CR_OFFSET);
207 
208 	reg_val &= (~XUARTPS_CR_EN_DIS_MASK);
209 	/* Set control register bits [4]: TX_EN and [2]: RX_EN */
210 	reg_val |= XUARTPS_CR_TX_EN | XUARTPS_CR_RX_EN;
211 	sys_write32(reg_val, reg_base + XUARTPS_CR_OFFSET);
212 }
213 
214 /**
215  * @brief Calculates and sets the values of the BAUDDIV and BAUDGEN registers.
216  *
217  * Calculates and sets the values of the BAUDDIV and BAUDGEN registers, which
218  * determine the prescaler applied to the clock driving the UART, based on
219  * the target baud rate, which is provided as a decimal value.
220  *
221  * The calculation of the values to be written to the BAUDDIV and BAUDGEN
222  * registers is described in the Zynq-7000 TRM, chapter 19.2.3 'Baud Rate
223  * Generator'.
224  *
225  * @param dev UART device struct
226  * @param baud_rate The desired baud rate as a decimal value
227  */
set_baudrate(const struct device * dev,uint32_t baud_rate)228 static void set_baudrate(const struct device *dev, uint32_t baud_rate)
229 {
230 	const struct uart_xlnx_ps_dev_config *dev_cfg = dev->config;
231 	uint32_t baud = dev_cfg->baud_rate;
232 	uint32_t clk_freq = dev_cfg->sys_clk_freq;
233 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
234 	uint32_t divisor, generator;
235 
236 	/* Calculate divisor and baud rate generator value */
237 	if ((baud != 0) && (clk_freq != 0)) {
238 		/* Covering case where input clock is so slow */
239 		if (clk_freq < 1000000U && baud > 4800U) {
240 			baud = 4800;
241 		}
242 
243 		for (divisor = 4; divisor < 255; divisor++) {
244 			uint32_t tmpbaud, bauderr;
245 
246 			generator = clk_freq / (baud * (divisor + 1));
247 			if (generator < 2 || generator > 65535) {
248 				continue;
249 			}
250 			tmpbaud = clk_freq / (generator * (divisor + 1));
251 
252 			if (baud > tmpbaud) {
253 				bauderr = baud - tmpbaud;
254 			} else {
255 				bauderr = tmpbaud - baud;
256 			}
257 			if (((bauderr * 100) / baud) < 3) {
258 				break;
259 			}
260 		}
261 
262 		/*
263 		 * Set baud rate divisor and generator.
264 		 * -> This function is always called from a context in which
265 		 * the receiver/transmitter is disabled, the baud rate can
266 		 * be changed safely at this time.
267 		 */
268 		sys_write32(divisor, reg_base + XUARTPS_BAUDDIV_OFFSET);
269 		sys_write32(generator, reg_base + XUARTPS_BAUDGEN_OFFSET);
270 	}
271 }
272 
273 /**
274  * @brief Initialize individual UART port
275  *
276  * This routine is called to reset the chip in a quiescent state.
277  *
278  * @param dev UART device struct
279  *
280  * @return 0 if successful, failed otherwise
281  */
uart_xlnx_ps_init(const struct device * dev)282 static int uart_xlnx_ps_init(const struct device *dev)
283 {
284 	const struct uart_xlnx_ps_dev_config *dev_cfg = dev->config;
285 	uint32_t reg_val;
286 #ifdef CONFIG_PINCTRL
287 	int err;
288 #endif
289 
290 	DEVICE_MMIO_MAP(dev, K_MEM_CACHE_NONE);
291 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
292 
293 	/* Disable RX/TX before changing any configuration data */
294 	xlnx_ps_disable_uart(reg_base);
295 
296 #ifdef CONFIG_PINCTRL
297 	err = pinctrl_apply_state(dev_cfg->pincfg, PINCTRL_STATE_DEFAULT);
298 	if (err < 0) {
299 		return err;
300 	}
301 #endif
302 
303 	/* Set initial character length / start/stop bit / parity configuration */
304 	reg_val = sys_read32(reg_base + XUARTPS_MR_OFFSET);
305 	reg_val &= (~(XUARTPS_MR_CHARLEN_MASK | XUARTPS_MR_STOPMODE_MASK |
306 		    XUARTPS_MR_PARITY_MASK));
307 	reg_val |= XUARTPS_MR_CHARLEN_8_BIT | XUARTPS_MR_STOPMODE_1_BIT |
308 		   XUARTPS_MR_PARITY_NONE;
309 	sys_write32(reg_val, reg_base + XUARTPS_MR_OFFSET);
310 
311 	/* Set RX FIFO trigger at 1 data bytes. */
312 	sys_write32(0x01U, reg_base + XUARTPS_RXWM_OFFSET);
313 
314 	/* Disable all interrupts, polling mode is default */
315 	sys_write32(XUARTPS_IXR_MASK, reg_base + XUARTPS_IDR_OFFSET);
316 
317 	/* Set the baud rate */
318 	set_baudrate(dev, dev_cfg->baud_rate);
319 
320 #ifdef CONFIG_UART_INTERRUPT_DRIVEN
321 
322 	/* Clear any pending interrupt flags */
323 	sys_write32(XUARTPS_IXR_MASK, reg_base + XUARTPS_ISR_OFFSET);
324 
325 	/* Attach to & unmask the corresponding interrupt vector */
326 	dev_cfg->irq_config_func(dev);
327 
328 #endif
329 
330 	xlnx_ps_enable_uart(reg_base);
331 
332 	return 0;
333 }
334 
335 /**
336  * @brief Poll the device for input.
337  *
338  * @param dev UART device struct
339  * @param c Pointer to character
340  *
341  * @return 0 if a character arrived, -1 if the input buffer if empty.
342  */
uart_xlnx_ps_poll_in(const struct device * dev,unsigned char * c)343 static int uart_xlnx_ps_poll_in(const struct device *dev, unsigned char *c)
344 {
345 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
346 	uint32_t reg_val = sys_read32(reg_base + XUARTPS_SR_OFFSET);
347 
348 	if ((reg_val & XUARTPS_SR_RXEMPTY) == 0) {
349 		*c = (unsigned char)sys_read32(reg_base + XUARTPS_FIFO_OFFSET);
350 		return 0;
351 	} else {
352 		return -1;
353 	}
354 }
355 
356 /**
357  * @brief Output a character in polled mode.
358  *
359  * Checks if the transmitter is empty. If empty, a character is written to
360  * the data register.
361  *
362  * If the hardware flow control is enabled then the handshake signal CTS has to
363  * be asserted in order to send a character.
364  *
365  * @param dev UART device struct
366  * @param c Character to send
367  *
368  * @return Sent character
369  */
uart_xlnx_ps_poll_out(const struct device * dev,unsigned char c)370 static void uart_xlnx_ps_poll_out(const struct device *dev, unsigned char c)
371 {
372 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
373 	uint32_t reg_val;
374 
375 	/* wait for transmitter to ready to accept a character */
376 	do {
377 		reg_val = sys_read32(reg_base + XUARTPS_SR_OFFSET);
378 	} while ((reg_val & XUARTPS_SR_TXEMPTY) == 0);
379 
380 	sys_write32((uint32_t)(c & 0xFF), reg_base + XUARTPS_FIFO_OFFSET);
381 
382 	do {
383 		reg_val = sys_read32(reg_base + XUARTPS_SR_OFFSET);
384 	} while ((reg_val & XUARTPS_SR_TXEMPTY) == 0);
385 }
386 
387 /**
388  * @brief Converts a parity enum value to a Mode Register bit mask.
389  *
390  * Converts a value of an enumeration type provided by the driver
391  * framework for the configuration of the UART's parity setting
392  * into a bit mask within the Mode Register.
393  *
394  * It is assumed that the Mode Register contents that are being
395  * modified within this function come with the bits modified by
396  * this function already masked out by the caller.
397  *
398  * @param mode_reg Pointer to the Mode Register contents to which
399  *                 the parity configuration shall be added.
400  * @param parity   Enumeration value to be converted to a bit mask.
401  *
402  * @return Indication of success, always true for this function
403  *         as all parity modes supported by the API are also supported
404  *         by the hardware.
405  */
uart_xlnx_ps_cfg2ll_parity(uint32_t * mode_reg,enum uart_config_parity parity)406 static inline bool uart_xlnx_ps_cfg2ll_parity(
407 	uint32_t *mode_reg,
408 	enum uart_config_parity parity)
409 {
410 	/*
411 	 * Translate the new parity configuration to the mode register's
412 	 * bits [5..3] (PAR):
413 	 *  000b : even
414 	 *  001b : odd
415 	 *  010b : space
416 	 *  011b : mark
417 	 *  1xxb : none
418 	 */
419 
420 	switch (parity) {
421 	default:
422 	case UART_CFG_PARITY_EVEN:
423 		*mode_reg |= XUARTPS_MR_PARITY_EVEN;
424 		break;
425 	case UART_CFG_PARITY_ODD:
426 		*mode_reg |= XUARTPS_MR_PARITY_ODD;
427 		break;
428 	case UART_CFG_PARITY_SPACE:
429 		*mode_reg |= XUARTPS_MR_PARITY_SPACE;
430 		break;
431 	case UART_CFG_PARITY_MARK:
432 		*mode_reg |= XUARTPS_MR_PARITY_MARK;
433 		break;
434 	case UART_CFG_PARITY_NONE:
435 		*mode_reg |= XUARTPS_MR_PARITY_NONE;
436 		break;
437 	}
438 
439 	return true;
440 }
441 
442 /**
443  * @brief Converts a stop bit enum value to a Mode Register bit mask.
444  *
445  * Converts a value of an enumeration type provided by the driver
446  * framework for the configuration of the UART's stop bit setting
447  * into a bit mask within the Mode Register.
448  *
449  * It is assumed that the Mode Register contents that are being
450  * modified within this function come with the bits modified by
451  * this function already masked out by the caller.
452  *
453  * @param mode_reg Pointer to the Mode Register contents to which
454  *                 the stop bit configuration shall be added.
455  * @param stopbits Enumeration value to be converted to a bit mask.
456  *
457  * @return Indication of success or failure in case of an unsupported
458  *         stop bit configuration being provided by the caller.
459  */
uart_xlnx_ps_cfg2ll_stopbits(uint32_t * mode_reg,enum uart_config_stop_bits stopbits)460 static inline bool uart_xlnx_ps_cfg2ll_stopbits(
461 	uint32_t *mode_reg,
462 	enum uart_config_stop_bits stopbits)
463 {
464 	/*
465 	 * Translate the new stop bit configuration to the mode register's
466 	 * bits [7..6] (NBSTOP):
467 	 *  00b : 1 stop bit
468 	 *  01b : 1.5 stop bits
469 	 *  10b : 2 stop bits
470 	 *  11b : reserved
471 	 */
472 
473 	switch (stopbits) {
474 	case UART_CFG_STOP_BITS_0_5:
475 		/* Controller doesn't support 0.5 stop bits */
476 		return false;
477 	default:
478 	case UART_CFG_STOP_BITS_1:
479 		*mode_reg |= XUARTPS_MR_STOPMODE_1_BIT;
480 		break;
481 	case UART_CFG_STOP_BITS_1_5:
482 		*mode_reg |= XUARTPS_MR_STOPMODE_1_5_BIT;
483 		break;
484 	case UART_CFG_STOP_BITS_2:
485 		*mode_reg |= XUARTPS_MR_STOPMODE_2_BIT;
486 		break;
487 	}
488 
489 	return true;
490 }
491 
492 /**
493  * @brief Converts a data bit enum value to a Mode Register bit mask.
494  *
495  * Converts a value of an enumeration type provided by the driver
496  * framework for the configuration of the UART's data bit setting
497  * into a bit mask within the Mode Register.
498  *
499  * It is assumed that the Mode Register contents that are being
500  * modified within this function come with the bits modified by
501  * this function already masked out by the caller.
502  *
503  * @param mode_reg Pointer to the Mode Register contents to which
504  *                 the data bit configuration shall be added.
505  * @param databits Enumeration value to be converted to a bit mask.
506  *
507  * @return Indication of success or failure in case of an unsupported
508  *         data bit configuration being provided by the caller.
509  */
uart_xlnx_ps_cfg2ll_databits(uint32_t * mode_reg,enum uart_config_data_bits databits)510 static inline bool uart_xlnx_ps_cfg2ll_databits(
511 	uint32_t *mode_reg,
512 	enum uart_config_data_bits databits)
513 {
514 	/*
515 	 * Translate the new data bit configuration to the mode register's
516 	 * bits [2..1] (CHRL):
517 	 *  0xb : 8 data bits
518 	 *  10b : 7 data bits
519 	 *  11b : 6 data bits
520 	 */
521 
522 	switch (databits) {
523 	case UART_CFG_DATA_BITS_5:
524 	case UART_CFG_DATA_BITS_9:
525 		/* Controller doesn't support 5 or 9 data bits */
526 		return false;
527 	default:
528 	case UART_CFG_DATA_BITS_8:
529 		*mode_reg |= XUARTPS_MR_CHARLEN_8_BIT;
530 		break;
531 	case UART_CFG_DATA_BITS_7:
532 		*mode_reg |= XUARTPS_MR_CHARLEN_7_BIT;
533 		break;
534 	case UART_CFG_DATA_BITS_6:
535 		*mode_reg |= XUARTPS_MR_CHARLEN_6_BIT;
536 		break;
537 	}
538 
539 	return true;
540 }
541 
542 /**
543  * @brief Converts a flow control enum value to a Modem Control
544  *        Register bit mask.
545  *
546  * Converts a value of an enumeration type provided by the driver
547  * framework for the configuration of the UART's flow control
548  * setting into a bit mask within the Modem Control Register.
549  *
550  * It is assumed that the Modem Control Register contents that are
551  * being modified within this function come with the bits modified
552  * by this function already masked out by the caller.
553  *
554  * @param modemcr_reg Pointer to the Modem Control Register contents
555  *                    to which the flow control configuration shall
556  *                    be added.
557  * @param hwctrl Enumeration value to be converted to a bit mask.
558  *
559  * @return Indication of success or failure in case of an unsupported
560  *         flow control configuration being provided by the caller.
561  */
uart_xlnx_ps_cfg2ll_hwctrl(uint32_t * modemcr_reg,enum uart_config_flow_control hwctrl)562 static inline bool uart_xlnx_ps_cfg2ll_hwctrl(
563 	uint32_t *modemcr_reg,
564 	enum uart_config_flow_control hwctrl)
565 {
566 	/*
567 	 * Translate the new flow control configuration to the modem
568 	 * control register's bit [5] (FCM):
569 	 *  0b : no flow control
570 	 *  1b : RTS/CTS
571 	 */
572 
573 	if (hwctrl == UART_CFG_FLOW_CTRL_RTS_CTS) {
574 		*modemcr_reg |= XUARTPS_MODEMCR_FCM_RTS_CTS;
575 	} else if (hwctrl ==  UART_CFG_FLOW_CTRL_NONE) {
576 		*modemcr_reg |= XUARTPS_MODEMCR_FCM_NONE;
577 	} else {
578 		/* Only no flow control or RTS/CTS is supported. */
579 		return false;
580 	}
581 
582 	return true;
583 }
584 
585 #ifdef CONFIG_UART_USE_RUNTIME_CONFIGURE
586 /**
587  * @brief Configures the UART device at run-time.
588  *
589  * Configures the UART device at run-time according to the
590  * configuration data provided by the caller.
591  *
592  * @param dev UART device struct
593  * @param cfg The configuration parameters to be applied.
594  *
595  * @return 0 if the configuration completed successfully, ENOTSUP
596  *         error if an unsupported configuration parameter is detected.
597  */
uart_xlnx_ps_configure(const struct device * dev,const struct uart_config * cfg)598 static int uart_xlnx_ps_configure(const struct device *dev,
599 				  const struct uart_config *cfg)
600 {
601 	struct uart_xlnx_ps_dev_config *dev_cfg =
602 	(struct uart_xlnx_ps_dev_config *)dev->config;
603 
604 	uintptr_t reg_base   = DEVICE_MMIO_GET(dev);
605 	uint32_t mode_reg    = 0;
606 	uint32_t modemcr_reg = 0;
607 
608 	/* Read the current mode register & modem control register values */
609 	mode_reg    = sys_read32(reg_base + XUARTPS_MR_OFFSET);
610 	modemcr_reg = sys_read32(reg_base + XUARTPS_MODEMCR_OFFSET);
611 
612 	/* Mask out all items that might be re-configured */
613 	mode_reg    &= (~XUARTPS_MR_PARITY_MASK);
614 	mode_reg    &= (~XUARTPS_MR_STOPMODE_MASK);
615 	mode_reg    &= (~XUARTPS_MR_CHARLEN_MASK);
616 	modemcr_reg &= (~XUARTPS_MODEMCR_FCM_MASK);
617 
618 	/* Assemble the updated registers, validity checks contained within */
619 	if ((!uart_xlnx_ps_cfg2ll_parity(&mode_reg, cfg->parity)) ||
620 		(!uart_xlnx_ps_cfg2ll_stopbits(&mode_reg, cfg->stop_bits)) ||
621 		(!uart_xlnx_ps_cfg2ll_databits(&mode_reg, cfg->data_bits)) ||
622 		(!uart_xlnx_ps_cfg2ll_hwctrl(&modemcr_reg, cfg->flow_ctrl))) {
623 		return -ENOTSUP;
624 	}
625 
626 	/* Disable the controller before modifying any config registers */
627 	xlnx_ps_disable_uart(reg_base);
628 
629 	/* Set the baud rate */
630 	set_baudrate(dev, cfg->baudrate);
631 	dev_cfg->baud_rate = cfg->baudrate;
632 
633 	/* Write the two control registers */
634 	sys_write32(mode_reg,    reg_base + XUARTPS_MR_OFFSET);
635 	sys_write32(modemcr_reg, reg_base + XUARTPS_MODEMCR_OFFSET);
636 
637 	/* Re-enable the controller */
638 	xlnx_ps_enable_uart(reg_base);
639 
640 	return 0;
641 };
642 #endif /* CONFIG_UART_USE_RUNTIME_CONFIGURE */
643 
644 /**
645  * @brief Converts a Mode Register bit mask to a parity configuration
646  *        enum value.
647  *
648  * Converts a bit mask representing the UART's parity setting within
649  * the UART's Mode Register into a value of an enumeration type provided
650  * by the UART driver API.
651  *
652  * @param mode_reg The current Mode Register contents from which the
653  *                 parity setting shall be extracted.
654  *
655  * @return The current parity setting mapped to the UART driver API's
656  *         enum type.
657  */
uart_xlnx_ps_ll2cfg_parity(uint32_t mode_reg)658 static inline enum uart_config_parity uart_xlnx_ps_ll2cfg_parity(
659 	uint32_t mode_reg)
660 {
661 	/*
662 	 * Obtain the current parity configuration from the mode register's
663 	 * bits [5..3] (PAR):
664 	 *  000b : even -> reset value
665 	 *  001b : odd
666 	 *  010b : space
667 	 *  011b : mark
668 	 *  1xxb : none
669 	 */
670 
671 	switch ((mode_reg & XUARTPS_MR_PARITY_MASK)) {
672 	case XUARTPS_MR_PARITY_EVEN:
673 	default:
674 		return UART_CFG_PARITY_EVEN;
675 	case XUARTPS_MR_PARITY_ODD:
676 		return UART_CFG_PARITY_ODD;
677 	case XUARTPS_MR_PARITY_SPACE:
678 		return UART_CFG_PARITY_SPACE;
679 	case XUARTPS_MR_PARITY_MARK:
680 		return UART_CFG_PARITY_MARK;
681 	case XUARTPS_MR_PARITY_NONE:
682 		return UART_CFG_PARITY_NONE;
683 	}
684 }
685 
686 /**
687  * @brief Converts a Mode Register bit mask to a stop bit configuration
688  *        enum value.
689  *
690  * Converts a bit mask representing the UART's stop bit setting within
691  * the UART's Mode Register into a value of an enumeration type provided
692  * by the UART driver API.
693  *
694  * @param mode_reg The current Mode Register contents from which the
695  *                 stop bit setting shall be extracted.
696  *
697  * @return The current stop bit setting mapped to the UART driver API's
698  *         enum type.
699  */
uart_xlnx_ps_ll2cfg_stopbits(uint32_t mode_reg)700 static inline enum uart_config_stop_bits uart_xlnx_ps_ll2cfg_stopbits(
701 	uint32_t mode_reg)
702 {
703 	/*
704 	 * Obtain the current stop bit configuration from the mode register's
705 	 * bits [7..6] (NBSTOP):
706 	 *  00b : 1 stop bit -> reset value
707 	 *  01b : 1.5 stop bits
708 	 *  10b : 2 stop bits
709 	 *  11b : reserved
710 	 */
711 
712 	switch ((mode_reg & XUARTPS_MR_STOPMODE_MASK)) {
713 	case XUARTPS_MR_STOPMODE_1_BIT:
714 	default:
715 		return UART_CFG_STOP_BITS_1;
716 	case XUARTPS_MR_STOPMODE_1_5_BIT:
717 		return UART_CFG_STOP_BITS_1_5;
718 	case XUARTPS_MR_STOPMODE_2_BIT:
719 		return UART_CFG_STOP_BITS_2;
720 	}
721 }
722 
723 /**
724  * @brief Converts a Mode Register bit mask to a data bit configuration
725  *        enum value.
726  *
727  * Converts a bit mask representing the UART's data bit setting within
728  * the UART's Mode Register into a value of an enumeration type provided
729  * by the UART driver API.
730  *
731  * @param mode_reg The current Mode Register contents from which the
732  *                 data bit setting shall be extracted.
733  *
734  * @return The current data bit setting mapped to the UART driver API's
735  *         enum type.
736  */
uart_xlnx_ps_ll2cfg_databits(uint32_t mode_reg)737 static inline enum uart_config_data_bits uart_xlnx_ps_ll2cfg_databits(
738 	uint32_t mode_reg)
739 {
740 	/*
741 	 * Obtain the current data bit configuration from the mode register's
742 	 * bits [2..1] (CHRL):
743 	 *  0xb : 8 data bits -> reset value
744 	 *  10b : 7 data bits
745 	 *  11b : 6 data bits
746 	 */
747 
748 	switch ((mode_reg & XUARTPS_MR_CHARLEN_MASK)) {
749 	case XUARTPS_MR_CHARLEN_8_BIT:
750 	default:
751 		return UART_CFG_DATA_BITS_8;
752 	case XUARTPS_MR_CHARLEN_7_BIT:
753 		return UART_CFG_DATA_BITS_7;
754 	case XUARTPS_MR_CHARLEN_6_BIT:
755 		return UART_CFG_DATA_BITS_6;
756 	}
757 }
758 
759 /**
760  * @brief Converts a Modem Control Register bit mask to a flow control
761  *        configuration enum value.
762  *
763  * Converts a bit mask representing the UART's flow control setting within
764  * the UART's Modem Control Register into a value of an enumeration type
765  * provided by the UART driver API.
766  *
767  * @param modemcr_reg The current Modem Control Register contents from
768  *                    which the parity setting shall be extracted.
769  *
770  * @return The current flow control setting mapped to the UART driver API's
771  *         enum type.
772  */
uart_xlnx_ps_ll2cfg_hwctrl(uint32_t modemcr_reg)773 static inline enum uart_config_flow_control uart_xlnx_ps_ll2cfg_hwctrl(
774 	uint32_t modemcr_reg)
775 {
776 	/*
777 	 * Obtain the current flow control configuration from the modem
778 	 * control register's bit [5] (FCM):
779 	 *  0b : no flow control -> reset value
780 	 *  1b : RTS/CTS
781 	 */
782 
783 	if ((modemcr_reg & XUARTPS_MODEMCR_FCM_MASK)
784 		== XUARTPS_MODEMCR_FCM_RTS_CTS) {
785 		return UART_CFG_FLOW_CTRL_RTS_CTS;
786 	}
787 
788 	return UART_CFG_FLOW_CTRL_NONE;
789 }
790 
791 #ifdef CONFIG_UART_USE_RUNTIME_CONFIGURE
792 /**
793  * @brief Returns the current configuration of the UART at run-time.
794  *
795  * Returns the current configuration of the UART at run-time by obtaining
796  * the current configuration from the UART's Mode and Modem Control Registers
797  * (exception: baud rate).
798  *
799  * @param dev UART device struct
800  * @param cfg Pointer to the data structure to which the current configuration
801  *            shall be written.
802  *
803  * @return always 0.
804  */
uart_xlnx_ps_config_get(const struct device * dev,struct uart_config * cfg)805 static int uart_xlnx_ps_config_get(const struct device *dev,
806 				   struct uart_config *cfg)
807 {
808 	const struct uart_xlnx_ps_dev_config *dev_cfg = dev->config;
809 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
810 
811 	/*
812 	 * Read the Mode & Modem control registers - they contain
813 	 * the current data / stop bit and parity settings (Mode
814 	 * Register) and the current flow control setting (Modem
815 	 * Control register).
816 	 */
817 	uint32_t mode_reg    = sys_read32(reg_base + XUARTPS_MR_OFFSET);
818 	uint32_t modemcr_reg = sys_read32(reg_base + XUARTPS_MODEMCR_OFFSET);
819 
820 	cfg->baudrate  = dev_cfg->baud_rate;
821 	cfg->parity    = uart_xlnx_ps_ll2cfg_parity(mode_reg);
822 	cfg->stop_bits = uart_xlnx_ps_ll2cfg_stopbits(mode_reg);
823 	cfg->data_bits = uart_xlnx_ps_ll2cfg_databits(mode_reg);
824 	cfg->flow_ctrl = uart_xlnx_ps_ll2cfg_hwctrl(modemcr_reg);
825 
826 	return 0;
827 }
828 #endif /* CONFIG_UART_USE_RUNTIME_CONFIGURE */
829 
830 #if CONFIG_UART_INTERRUPT_DRIVEN
831 
832 /**
833  * @brief Fill FIFO with data
834  *
835  * @param dev UART device struct
836  * @param tx_data Data to transmit
837  * @param size Number of bytes to send
838  *
839  * @return Number of bytes sent
840  */
uart_xlnx_ps_fifo_fill(const struct device * dev,const uint8_t * tx_data,int size)841 static int uart_xlnx_ps_fifo_fill(const struct device *dev,
842 				  const uint8_t *tx_data,
843 				  int size)
844 {
845 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
846 	uint32_t data_iter = 0;
847 
848 	sys_write32(XUARTPS_IXR_TXEMPTY, reg_base + XUARTPS_IDR_OFFSET);
849 	while (size--) {
850 		while ((sys_read32(reg_base + XUARTPS_SR_OFFSET) & XUARTPS_SR_TXFULL) != 0) {
851 		}
852 		sys_write32((uint32_t)tx_data[data_iter++], reg_base + XUARTPS_FIFO_OFFSET);
853 	}
854 	sys_write32(XUARTPS_IXR_TXEMPTY, reg_base + XUARTPS_IER_OFFSET);
855 
856 	return data_iter;
857 }
858 
859 /**
860  * @brief Read data from FIFO
861  *
862  * @param dev UART device struct
863  * @param rxData Data container
864  * @param size Container size
865  *
866  * @return Number of bytes read
867  */
uart_xlnx_ps_fifo_read(const struct device * dev,uint8_t * rx_data,const int size)868 static int uart_xlnx_ps_fifo_read(const struct device *dev, uint8_t *rx_data,
869 				  const int size)
870 {
871 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
872 	uint32_t reg_val = sys_read32(reg_base + XUARTPS_SR_OFFSET);
873 	int inum = 0;
874 
875 	while (inum < size && (reg_val & XUARTPS_SR_RXEMPTY) == 0) {
876 		rx_data[inum] = (uint8_t)sys_read32(reg_base
877 				+ XUARTPS_FIFO_OFFSET);
878 		inum++;
879 		reg_val = sys_read32(reg_base + XUARTPS_SR_OFFSET);
880 	}
881 
882 	return inum;
883 }
884 
885 /**
886  * @brief Enable TX interrupt in IER
887  *
888  * @param dev UART device struct
889  */
uart_xlnx_ps_irq_tx_enable(const struct device * dev)890 static void uart_xlnx_ps_irq_tx_enable(const struct device *dev)
891 {
892 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
893 
894 	sys_write32(
895 		(XUARTPS_IXR_TTRIG | XUARTPS_IXR_TXEMPTY),
896 		reg_base + XUARTPS_IER_OFFSET);
897 }
898 
899 /**
900  * @brief Disable TX interrupt in IER
901  *
902  * @param dev UART device struct
903  */
uart_xlnx_ps_irq_tx_disable(const struct device * dev)904 static void uart_xlnx_ps_irq_tx_disable(const struct device *dev)
905 {
906 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
907 
908 	sys_write32(
909 		(XUARTPS_IXR_TTRIG | XUARTPS_IXR_TXEMPTY),
910 		reg_base + XUARTPS_IDR_OFFSET);
911 }
912 
913 /**
914  * @brief Check if Tx IRQ has been raised
915  *
916  * @param dev UART device struct
917  *
918  * @return 1 if an IRQ is ready, 0 otherwise
919  */
uart_xlnx_ps_irq_tx_ready(const struct device * dev)920 static int uart_xlnx_ps_irq_tx_ready(const struct device *dev)
921 {
922 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
923 	uint32_t reg_val = sys_read32(reg_base + XUARTPS_SR_OFFSET);
924 
925 	if ((reg_val & (XUARTPS_SR_TTRIG | XUARTPS_SR_TXEMPTY)) == 0) {
926 		return 0;
927 	} else {
928 		return 1;
929 	}
930 }
931 
932 /**
933  * @brief Check if nothing remains to be transmitted
934  *
935  * @param dev UART device struct
936  *
937  * @return 1 if nothing remains to be transmitted, 0 otherwise
938  */
uart_xlnx_ps_irq_tx_complete(const struct device * dev)939 static int uart_xlnx_ps_irq_tx_complete(const struct device *dev)
940 {
941 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
942 	uint32_t reg_val = sys_read32(reg_base + XUARTPS_SR_OFFSET);
943 
944 	if ((reg_val & XUARTPS_SR_TXEMPTY) == 0) {
945 		return 0;
946 	} else {
947 		return 1;
948 	}
949 }
950 
951 /**
952  * @brief Enable RX interrupt in IER
953  *
954  * @param dev UART device struct
955  */
uart_xlnx_ps_irq_rx_enable(const struct device * dev)956 static void uart_xlnx_ps_irq_rx_enable(const struct device *dev)
957 {
958 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
959 
960 	sys_write32(XUARTPS_IXR_RTRIG, reg_base + XUARTPS_IER_OFFSET);
961 }
962 
963 /**
964  * @brief Disable RX interrupt in IER
965  *
966  * @param dev UART device struct
967  */
uart_xlnx_ps_irq_rx_disable(const struct device * dev)968 static void uart_xlnx_ps_irq_rx_disable(const struct device *dev)
969 {
970 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
971 
972 	sys_write32(XUARTPS_IXR_RTRIG, reg_base + XUARTPS_IDR_OFFSET);
973 }
974 
975 /**
976  * @brief Check if Rx IRQ has been raised
977  *
978  * @param dev UART device struct
979  *
980  * @return 1 if an IRQ is ready, 0 otherwise
981  */
uart_xlnx_ps_irq_rx_ready(const struct device * dev)982 static int uart_xlnx_ps_irq_rx_ready(const struct device *dev)
983 {
984 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
985 	uint32_t reg_val = sys_read32(reg_base + XUARTPS_ISR_OFFSET);
986 
987 	if ((reg_val & XUARTPS_IXR_RTRIG) == 0) {
988 		return 0;
989 	} else {
990 		sys_write32(XUARTPS_IXR_RTRIG, reg_base + XUARTPS_ISR_OFFSET);
991 		return 1;
992 	}
993 }
994 
995 /**
996  * @brief Enable error interrupt in IER
997  *
998  * @param dev UART device struct
999  */
uart_xlnx_ps_irq_err_enable(const struct device * dev)1000 static void uart_xlnx_ps_irq_err_enable(const struct device *dev)
1001 {
1002 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
1003 
1004 	sys_write32(
1005 		  XUARTPS_IXR_TOVR    /* [12] Transmitter FIFO Overflow */
1006 		| XUARTPS_IXR_TOUT    /* [8]  Receiver Timerout */
1007 		| XUARTPS_IXR_PARITY  /* [7]  Parity Error */
1008 		| XUARTPS_IXR_FRAMING /* [6]  Receiver Framing Error */
1009 		| XUARTPS_IXR_RXOVR,  /* [5]  Receiver Overflow Error */
1010 	    reg_base + XUARTPS_IER_OFFSET);
1011 }
1012 
1013 /**
1014  * @brief Disable error interrupt in IER
1015  *
1016  * @param dev UART device struct
1017  *
1018  * @return 1 if an IRQ is ready, 0 otherwise
1019  */
uart_xlnx_ps_irq_err_disable(const struct device * dev)1020 static void uart_xlnx_ps_irq_err_disable(const struct device *dev)
1021 {
1022 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
1023 
1024 	sys_write32(
1025 		  XUARTPS_IXR_TOVR    /* [12] Transmitter FIFO Overflow */
1026 		| XUARTPS_IXR_TOUT    /* [8]  Receiver Timerout */
1027 		| XUARTPS_IXR_PARITY  /* [7]  Parity Error */
1028 		| XUARTPS_IXR_FRAMING /* [6]  Receiver Framing Error */
1029 		| XUARTPS_IXR_RXOVR,  /* [5]  Receiver Overflow Error */
1030 	    reg_base + XUARTPS_IDR_OFFSET);
1031 }
1032 
1033 /**
1034  * @brief Check if any IRQ is pending
1035  *
1036  * @param dev UART device struct
1037  *
1038  * @return 1 if an IRQ is pending, 0 otherwise
1039  */
uart_xlnx_ps_irq_is_pending(const struct device * dev)1040 static int uart_xlnx_ps_irq_is_pending(const struct device *dev)
1041 {
1042 	uintptr_t reg_base = DEVICE_MMIO_GET(dev);
1043 	uint32_t reg_imr = sys_read32(reg_base + XUARTPS_IMR_OFFSET);
1044 	uint32_t reg_isr = sys_read32(reg_base + XUARTPS_ISR_OFFSET);
1045 
1046 	if ((reg_imr & reg_isr) != 0) {
1047 		return 1;
1048 	} else {
1049 		return 0;
1050 	}
1051 }
1052 
1053 /**
1054  * @brief Update cached contents of IIR
1055  *
1056  * @param dev UART device struct
1057  *
1058  * @return Always 1
1059  */
uart_xlnx_ps_irq_update(const struct device * dev)1060 static int uart_xlnx_ps_irq_update(const struct device *dev)
1061 {
1062 	ARG_UNUSED(dev);
1063 	return 1;
1064 }
1065 
1066 /**
1067  * @brief Set the callback function pointer for IRQ.
1068  *
1069  * @param dev UART device struct
1070  * @param cb Callback function pointer.
1071  */
uart_xlnx_ps_irq_callback_set(const struct device * dev,uart_irq_callback_user_data_t cb,void * cb_data)1072 static void uart_xlnx_ps_irq_callback_set(const struct device *dev,
1073 					    uart_irq_callback_user_data_t cb,
1074 					    void *cb_data)
1075 {
1076 	struct uart_xlnx_ps_dev_data_t *dev_data = dev->data;
1077 
1078 	dev_data->user_cb = cb;
1079 	dev_data->user_data = cb_data;
1080 }
1081 
1082 /**
1083  * @brief Interrupt ce routine.
1084  *
1085  * This simply calls the callback function, if one exists.
1086  *
1087  * @param arg Argument to ISR.
1088  */
uart_xlnx_ps_isr(const struct device * dev)1089 static void uart_xlnx_ps_isr(const struct device *dev)
1090 {
1091 	const struct uart_xlnx_ps_dev_data_t *data = dev->data;
1092 
1093 	if (data->user_cb) {
1094 		data->user_cb(dev, data->user_data);
1095 	}
1096 }
1097 #endif /* CONFIG_UART_INTERRUPT_DRIVEN */
1098 
1099 static const struct uart_driver_api uart_xlnx_ps_driver_api = {
1100 	.poll_in = uart_xlnx_ps_poll_in,
1101 	.poll_out = uart_xlnx_ps_poll_out,
1102 #ifdef CONFIG_UART_USE_RUNTIME_CONFIGURE
1103 	.configure = uart_xlnx_ps_configure,
1104 	.config_get = uart_xlnx_ps_config_get,
1105 #endif
1106 #ifdef CONFIG_UART_INTERRUPT_DRIVEN
1107 	.fifo_fill = uart_xlnx_ps_fifo_fill,
1108 	.fifo_read = uart_xlnx_ps_fifo_read,
1109 	.irq_tx_enable = uart_xlnx_ps_irq_tx_enable,
1110 	.irq_tx_disable = uart_xlnx_ps_irq_tx_disable,
1111 	.irq_tx_ready = uart_xlnx_ps_irq_tx_ready,
1112 	.irq_tx_complete = uart_xlnx_ps_irq_tx_complete,
1113 	.irq_rx_enable = uart_xlnx_ps_irq_rx_enable,
1114 	.irq_rx_disable = uart_xlnx_ps_irq_rx_disable,
1115 	.irq_rx_ready = uart_xlnx_ps_irq_rx_ready,
1116 	.irq_err_enable = uart_xlnx_ps_irq_err_enable,
1117 	.irq_err_disable = uart_xlnx_ps_irq_err_disable,
1118 	.irq_is_pending = uart_xlnx_ps_irq_is_pending,
1119 	.irq_update = uart_xlnx_ps_irq_update,
1120 	.irq_callback_set = uart_xlnx_ps_irq_callback_set,
1121 #endif
1122 };
1123 
1124 #ifdef CONFIG_UART_INTERRUPT_DRIVEN
1125 
1126 #define UART_XLNX_PS_IRQ_CONF_FUNC_SET(port) \
1127 	.irq_config_func = uart_xlnx_ps_irq_config_##port,
1128 
1129 #define UART_XLNX_PS_IRQ_CONF_FUNC(port) \
1130 static void uart_xlnx_ps_irq_config_##port(const struct device *dev) \
1131 { \
1132 	IRQ_CONNECT(DT_INST_IRQN(port), \
1133 	DT_INST_IRQ(port, priority), \
1134 	uart_xlnx_ps_isr, DEVICE_DT_INST_GET(port), \
1135 	0); \
1136 	irq_enable(DT_INST_IRQN(port)); \
1137 }
1138 
1139 #else
1140 
1141 #define UART_XLNX_PS_IRQ_CONF_FUNC_SET(port)
1142 #define UART_XLNX_PS_IRQ_CONF_FUNC(port)
1143 
1144 #endif /*CONFIG_UART_INTERRUPT_DRIVEN */
1145 
1146 #define UART_XLNX_PS_DEV_DATA(port) \
1147 static struct uart_xlnx_ps_dev_data_t uart_xlnx_ps_dev_data_##port
1148 
1149 #if CONFIG_PINCTRL
1150 #define UART_XLNX_PS_PINCTRL_DEFINE(port) PINCTRL_DT_INST_DEFINE(port);
1151 #define UART_XLNX_PS_PINCTRL_INIT(port) .pincfg = PINCTRL_DT_INST_DEV_CONFIG_GET(port),
1152 #else
1153 #define UART_XLNX_PS_PINCTRL_DEFINE(port)
1154 #define UART_XLNX_PS_PINCTRL_INIT(port)
1155 #endif /* CONFIG_PINCTRL */
1156 
1157 #define UART_XLNX_PS_DEV_CFG(port) \
1158 static struct uart_xlnx_ps_dev_config uart_xlnx_ps_dev_cfg_##port = { \
1159 	DEVICE_MMIO_ROM_INIT(DT_DRV_INST(port)), \
1160 	.sys_clk_freq = DT_INST_PROP(port, clock_frequency), \
1161 	.baud_rate = DT_INST_PROP(port, current_speed), \
1162 	UART_XLNX_PS_IRQ_CONF_FUNC_SET(port) \
1163 	UART_XLNX_PS_PINCTRL_INIT(port) \
1164 }
1165 
1166 #define UART_XLNX_PS_INIT(port) \
1167 DEVICE_DT_INST_DEFINE(port, \
1168 	uart_xlnx_ps_init, \
1169 	NULL, \
1170 	&uart_xlnx_ps_dev_data_##port, \
1171 	&uart_xlnx_ps_dev_cfg_##port, \
1172 	PRE_KERNEL_1, CONFIG_SERIAL_INIT_PRIORITY, \
1173 	&uart_xlnx_ps_driver_api)
1174 
1175 #define UART_XLNX_INSTANTIATE(inst)		\
1176 	UART_XLNX_PS_PINCTRL_DEFINE(inst)	\
1177 	UART_XLNX_PS_IRQ_CONF_FUNC(inst);	\
1178 	UART_XLNX_PS_DEV_DATA(inst);		\
1179 	UART_XLNX_PS_DEV_CFG(inst);		\
1180 	UART_XLNX_PS_INIT(inst);
1181 
1182 DT_INST_FOREACH_STATUS_OKAY(UART_XLNX_INSTANTIATE)
1183