1/*
2 * Copyright 2017, Data61
3 * Commonwealth Scientific and Industrial Research Organisation (CSIRO)
4 * ABN 41 687 119 230.
5 *
6 * This software may be distributed and modified according to the terms of
7 * the BSD 2-Clause license. Note that NO WARRANTY is provided.
8 * See "LICENSE_BSD2.txt" for details.
9 *
10 * @TAG(DATA61_BSD)
11 */
12
13/* disabled until someone makes it compile */
14
15#include <platsupport/clock.h>
16#include <platsupport/serial.h>
17#include <utils/util.h>
18#include <string.h>
19
20#include "serial.h"
21#include "mux.h"
22
23#include "../../common.h"
24
25/* TX FIFO IRQ threshold ratio {0..7}.
26 * The absolute value depends on the FIFO size of the individual UART
27 * A high value avoids underruns, but increases IRQ overhead */
28#define FIFO_TXLVL_VAL   2
29
30/* RX FIFO IRQ threshold ratio {0..7}.
31 * The absolute value depends on the FIFO size of the individual UART
32 * A low value avoids overruns, but increases IRQ overhead */
33#define FIFO_RXLVL_VAL   2
34
35/* Timeout on RX {0..15} */
36#define RX_TIMEOUT_VAL   15 /* 8*(N + 1) frames */
37
38#define ULCON       0x0000 /* line control */
39#define UCON        0x0004 /* control */
40#define UFCON       0x0008 /* fifo control */
41#define UMCON       0x000C /* modem control */
42#define UTRSTAT     0x0010 /* TX/RX status */
43#define UERSTAT     0x0014 /* RX error status */
44#define UFRSTAT     0x0018 /* FIFO status */
45#define UMSTAT      0x001C /* modem status */
46#define UTXH        0x0020 /* TX buffer */
47#define URXH        0x0024 /* RX buffer */
48#define UBRDIV      0x0028 /* baud rate divisor */
49#define UFRACVAL    0x002C /* divisor fractional value */
50#define UINTP       0x0030 /* interrupt pending */
51#define UINTSP      0x0034 /* interrupt source pending */
52#define UINTM       0x0038 /* interrupt mask */
53
54/* UTRSTAT */
55#define TRSTAT_RXTIMEOUT      BIT(3)
56#define TRSTAT_TX_EMPTY       BIT(2)
57#define TRSTAT_TXBUF_EMPTY    BIT(1)
58#define TRSTAT_RXBUF_READY    BIT(0)
59
60/* FRSTAT */
61#define FRSTAT_TX_FULL        BIT(24)
62#define FRSTAT_GET_TXFIFO(x)  (((x) >> 16) & 0xff)
63#define FRSTAT_RXFIFO_ERR     BIT(9)
64#define FRSTAT_RXFIFO_FULL    BIT(8)
65#define FRSTAT_GET_RXFIFO(x)  (((x) >>  0) & 0xff)
66
67/* UCON */
68#define CON_MODE_DISABLE      0x0
69#define CON_MODE_POLL         0x1
70#define CON_MODE_DMA          0x2
71#define CON_MODE_MASK         0x3
72#define CON_TXMODE(x)         (CON_MODE_##x << 2)
73#define CON_RXMODE(x)         (CON_MODE_##x << 0)
74#define CON_RX_TIMEOUT(x)     (((x) & 0xf) << 12)
75#define CON_RX_TIMEOUT_MASK   CON_RX_TIMEOUT(0xf)
76#define CON_RX_TIMEOUT_EMPTY  BIT(11)
77#define CON_TXIRQTYPE_LEVEL   BIT(9)
78#define CON_RXIRQTYPE_LEVEL   BIT(8)
79#define CON_RXTIMEOUT_ENABLE  BIT(7)
80#define CON_RXERR_IRQ_EN      BIT(6)
81/* FIFO control */
82#define FIFO_EN               BIT(0)
83#define FIFO_RX_RESET         BIT(1)
84#define FIFO_TX_RESET         BIT(2)
85#define FIFO_TXLVL(x)         ((x) << 8)
86#define FIFO_TXLVL_MASK       FIFO_TXLVL(0x7)
87#define FIFO_RXLVL(x)         ((x) << 4)
88#define FIFO_RXLVL_MASK       FIFO_RXLVL(0x7)
89
90/* INTP, INTSP, INTM */
91#define INT_MODEM BIT(3)
92#define INT_TX    BIT(2)
93#define INT_ERR   BIT(1)
94#define INT_RX    BIT(0)
95
96#define REG_PTR(base, offset)  ((volatile uint32_t *)((char*)(base) + (offset)))
97
98static clk_t *clk;
99
100enum mux_feature uart_mux[] = {
101    [PS_SERIAL0] = MUX_UART0,
102    [PS_SERIAL1] = MUX_UART1,
103    [PS_SERIAL2] = MUX_UART2,
104    [PS_SERIAL3] = MUX_UART3
105};
106
107static const int uart_irqs[][2] = {
108    [PS_SERIAL0] = {EXYNOS_UART0_IRQ, -1},
109    [PS_SERIAL1] = {EXYNOS_UART1_IRQ, -1},
110    [PS_SERIAL2] = {EXYNOS_UART2_IRQ, -1},
111    [PS_SERIAL3] = {EXYNOS_UART3_IRQ, -1}
112};
113
114static const uint32_t uart_paddr[] = {
115    [PS_SERIAL0] = EXYNOS_UART0_PADDR,
116    [PS_SERIAL1] = EXYNOS_UART1_PADDR,
117    [PS_SERIAL2] = EXYNOS_UART2_PADDR,
118    [PS_SERIAL3] = EXYNOS_UART3_PADDR
119};
120
121static const enum clk_id uart_clk[] = {
122    [PS_SERIAL0] = CLK_UART0,
123    [PS_SERIAL1] = CLK_UART1,
124    [PS_SERIAL2] = CLK_UART2,
125    [PS_SERIAL3] = CLK_UART3
126};
127
128#define UART_DEFN(devid) {                     \
129        .id      = PS_SERIAL##devid,           \
130        .paddr   = EXYNOS_UART##devid##_PADDR, \
131        .size    = BIT(12),                    \
132        .irqs    = uart_irqs[devid],           \
133        .init_fn = &uart_init                  \
134    }
135
136static const struct dev_defn dev_defn[] = {
137    UART_DEFN(0),
138    UART_DEFN(1),
139    UART_DEFN(2),
140    UART_DEFN(3),
141};
142
143static int exynos_uart_putchar(ps_chardevice_t *d, int c)
144{
145    if (*REG_PTR(d->vaddr, UFRSTAT) & FRSTAT_TX_FULL) {
146        /* abort: no room in FIFO */
147        return -1;
148    } else {
149        /* Write out the next character. */
150        *REG_PTR(d->vaddr, UTXH) = c;
151        if (c == '\n' && (d->flags & SERIAL_AUTO_CR)) {
152            /* In this case, We should have checked that we had two free bytes in
153             * the FIFO before we submitted the first char, however, the fifo size
154             * would need to be considered and this differs between UARTs.
155             * To keep things simple, we recognise that it is rare for a '\n' to
156             * be sent when there is insufficient FIFO space and accept the
157             * inefficiencies of spinning, waiting for space.
158             */
159            while (exynos_uart_putchar(d, '\r') < 0);
160        }
161        return c;
162    }
163}
164
165static int uart_fill_fifo(ps_chardevice_t *d, const char *data, size_t len)
166{
167    int i;
168    for (i = 0; i < len; i++) {
169        if (exynos_uart_putchar(d, *data++) < 0) {
170            return i;
171        }
172    }
173    return len;
174}
175
176static void uart_drain_tx_fifo(ps_chardevice_t *d)
177{
178    if (d->write_descriptor.data) {
179        exynos_handle_tx_irq(d);
180    }
181}
182
183static ssize_t exynos_uart_write(ps_chardevice_t *d, const void *vdata, size_t count, chardev_callback_t wcb,
184                                 void *token)
185{
186    const char *data = (const char *)vdata;
187    int sent;
188
189    /*
190     * Try to further drain the TX FIFO before writing.
191     * This is a slight optimisation to maximize the amount of
192     * data we can write and possibly free up the write
193     * descriptor (instead of returning failure).
194     */
195    uart_drain_tx_fifo(d);
196
197    if (d->write_descriptor.data) {
198        /* Transaction is already in progress */
199        return -1;
200    }
201    /* Fill the FIFO */
202    sent = uart_fill_fifo(d, data, count);
203    if (wcb) {
204        /* Register the callback */
205        d->write_descriptor.callback = wcb;
206        d->write_descriptor.token = token;
207        d->write_descriptor.bytes_transfered = sent;
208        d->write_descriptor.bytes_requested = count;
209        d->write_descriptor.data = (void *)data + sent;
210        /* Enable TX IRQ */
211        *REG_PTR(d->vaddr, UINTP) = INT_TX;
212        *REG_PTR(d->vaddr, UINTM) &= ~INT_TX;
213    }
214    return sent;
215}
216
217static void uart_handle_tx_irq(ps_chardevice_t *d)
218{
219    int sent;
220    int to_send;
221    /* pipe more data onto the fifo */
222    to_send = d->write_descriptor.bytes_requested - d->write_descriptor.bytes_transfered;
223    sent = uart_fill_fifo(d, d->write_descriptor.data, to_send);
224    d->write_descriptor.bytes_transfered += sent;
225    d->write_descriptor.data += sent;
226
227    /* Check if this transaction is complete */
228    if (d->write_descriptor.bytes_transfered == d->write_descriptor.bytes_requested) {
229        /* Shutdown IRQs */
230        *REG_PTR(d->vaddr, UINTM) |= INT_TX;
231        d->write_descriptor.data = NULL;
232        /* Signal completion */
233        d->write_descriptor.callback(d, CHARDEV_STAT_COMPLETE,
234                                     d->write_descriptor.bytes_transfered,
235                                     d->write_descriptor.token);
236    }
237
238    /* Clear the pending flag, ready for the next IRQ */
239    *REG_PTR(d->vaddr, UINTP) = INT_TX;
240}
241
242static int exynos_uart_getchar(ps_chardevice_t *d)
243{
244    if (*REG_PTR(d->vaddr, UTRSTAT) & TRSTAT_RXBUF_READY) {
245        return *REG_PTR(d->vaddr, URXH);
246    } else {
247        return -1;
248    }
249}
250
251static int uart_read_fifo(ps_chardevice_t *d, char *data, size_t len)
252{
253    int i;
254    for (i = 0; i < len; i++) {
255        int c;
256        c = exynos_uart_getchar(d);
257        if (c < 0) {
258            break;
259        }
260        *data++ = c;
261    }
262    /* Clear the pending flag */
263    *REG_PTR(d->vaddr, UINTP) = INT_RX;
264    return i;
265}
266
267static ssize_t exynos_uart_read(ps_chardevice_t *d, void *vdata, size_t count, chardev_callback_t rcb, void *token)
268{
269    if (d->read_descriptor.data) {
270        /* Transaction is already in progress */
271        return -1;
272    } else if (rcb) {
273        /* We don't want to perform an actual read here as we want the ISR to catch
274         * timeouts appropriately. Just register the callback and wait for the IRQ */
275        d->read_descriptor.callback = rcb;
276        d->read_descriptor.token = token;
277        d->read_descriptor.bytes_transfered = 0;
278        d->read_descriptor.bytes_requested = count;
279        d->read_descriptor.data = (void *)vdata;
280        /* Dont need to enable the RX IRQ because it is always enabled */
281        return 0;
282    } else {
283        /* Read what we can into the buffer and return */
284        return uart_read_fifo(d, (char *)vdata, count);
285    }
286}
287
288static void uart_handle_rx_irq(ps_chardevice_t *d)
289{
290    int timeout;
291    uint32_t v;
292    int read;
293    int to_read;
294    /* If a callback was not registered, simply return. User is expected
295     * to read FIFO data with a call to 'read' */
296    if (d->read_descriptor.data == NULL) {
297        return;
298    }
299    /* Check for timeout */
300    v = *REG_PTR(d->vaddr, UTRSTAT);
301    timeout = v & TRSTAT_RXTIMEOUT;
302    /* Clear timeout condition */
303    *REG_PTR(d->vaddr, UTRSTAT) = v;
304    /* Drain the RX FIFO */
305    to_read = d->read_descriptor.bytes_requested - d->read_descriptor.bytes_transfered;
306    read = uart_read_fifo(d, d->read_descriptor.data, to_read);
307    if (read >= 0) {
308        d->read_descriptor.bytes_transfered += read;
309        d->read_descriptor.data += read;
310    }
311
312    /* Check if this transaction is complete */
313    if (timeout || d->read_descriptor.bytes_transfered == d->read_descriptor.bytes_requested) {
314        d->read_descriptor.data = NULL;
315        /* Signal completion */
316        d->read_descriptor.callback(d, CHARDEV_STAT_COMPLETE,
317                                    d->read_descriptor.bytes_transfered,
318                                    d->read_descriptor.token);
319    }
320    /* Clear the pending flag */
321    *REG_PTR(d->vaddr, UINTP) = INT_RX;
322}
323
324static void uart_flush(ps_chardevice_t *d)
325{
326    while (!(*REG_PTR(d->vaddr, UTRSTAT) & TRSTAT_TX_EMPTY));
327}
328
329int exynos_check_irq(ps_chardevice_t *d)
330{
331    return *REG_PTR(d->vaddr, UINTP);
332}
333
334void exynos_handle_rx_irq(ps_chardevice_t *d)
335{
336    uint32_t sts;
337    sts = *REG_PTR(d->vaddr, UINTP);
338    if (sts & INT_RX) {
339        sts &= ~INT_RX;
340        uart_handle_rx_irq(d);
341    }
342}
343
344void exynos_handle_tx_irq(ps_chardevice_t *d)
345{
346    uint32_t sts;
347    sts = *REG_PTR(d->vaddr, UINTP);
348    if (sts & INT_TX) {
349        sts &= ~INT_TX;
350        uart_handle_tx_irq(d);
351    }
352}
353
354static void uart_handle_irq(ps_chardevice_t *d)
355{
356    uint32_t sts;
357    sts = *REG_PTR(d->vaddr, UINTP);
358    if (sts & INT_TX) {
359        sts &= ~INT_TX;
360        uart_handle_tx_irq(d);
361    }
362    if (sts & INT_RX) {
363        sts &= ~INT_RX;
364        uart_handle_rx_irq(d);
365    }
366    if (sts) {
367        ZF_LOGE("Unhandled IRQ (status 0x%x)\n", sts);
368    }
369}
370
371#define BRDIV_BITS 16
372static int uart_set_baud(const ps_chardevice_t *d, long bps)
373{
374    long div_val, sclk_uart;
375    uint32_t brdiv, brfrac;
376
377    sclk_uart = (clk == NULL) ? UART_DEFAULT_FIN : clk_get_freq(clk);
378    div_val  = sclk_uart / bps - 16;
379    /* Check if we need to scale down the clock */
380    if (div_val / 16 >> BRDIV_BITS > 0) {
381        assert(!"Not implemented");
382        sclk_uart = 0;//clk_set_div(device_data_clk(d), div_val >> BRDIV_BITS);
383        div_val  = sclk_uart / bps;
384        /* Make sure that we have fixed the problem */
385        if (div_val / 16 >> BRDIV_BITS > 0) {
386            return -1;
387        }
388    }
389    brfrac = div_val % 16;
390    brdiv = (div_val / 16) & 0xffff;
391
392    *REG_PTR(d->vaddr, UBRDIV) = brdiv;
393    *REG_PTR(d->vaddr, UFRACVAL) = brfrac;
394    return 0;
395}
396
397static int uart_set_charsize(ps_chardevice_t *d, int char_size)
398{
399    uint32_t v;
400    v = *REG_PTR(d->vaddr, ULCON);
401    v &= ~(0x3 << 0);
402    switch (char_size) {
403    case 5:
404        v |= (0x0 << 0);
405        break;
406    case 6:
407        v |= (BIT(0));
408        break;
409    case 7:
410        v |= (0x2 << 0);
411        break;
412    case 8:
413        v |= (0x3 << 0);
414        break;
415    default :
416        return -1;
417    }
418    *REG_PTR(d->vaddr, ULCON) = v;
419    return 0;
420}
421
422static int uart_set_stop(ps_chardevice_t *d, int stop_bits)
423{
424    uint32_t v;
425    v = *REG_PTR(d->vaddr, ULCON);
426    v &= ~(BIT(2));
427    switch (stop_bits) {
428    case 1:
429        v |= (0x0 << 2);
430        break;
431    case 2:
432        v |= (BIT(2));
433        break;
434    default :
435        return -1;
436    }
437    *REG_PTR(d->vaddr, ULCON) = v;
438    return 0;
439}
440
441static int uart_set_parity(ps_chardevice_t *d, enum serial_parity parity)
442{
443    uint32_t v;
444    v = *REG_PTR(d->vaddr, ULCON);
445    v &= ~(0x7 << 3);
446    switch (parity) {
447    case PARITY_EVEN:
448        v |= (0x5 << 3);
449        break;
450    case PARITY_ODD:
451        v |= (0x4 << 3);
452        break;
453    case PARITY_NONE:
454        v |= (0x0 << 3);
455        break;
456    default :
457        return -1;
458    }
459    *REG_PTR(d->vaddr, ULCON) = v;
460    return 0;
461}
462
463int serial_configure(ps_chardevice_t *d, long bps, int char_size,
464                     enum serial_parity parity, int stop_bits)
465{
466    return uart_set_baud(d, bps)
467           || uart_set_parity(d, parity)
468           || uart_set_charsize(d, char_size)
469           || uart_set_stop(d, stop_bits);
470}
471
472static void mux_uart_init(enum mux_feature feature, mux_sys_t *mux_sys)
473{
474    if (mux_sys_valid(mux_sys)) {
475        if (mux_feature_enable(mux_sys, feature, MUX_DIR_NOT_A_GPIO)) {
476            ZF_LOGE("Failed to initialise MUX for UART\n");
477        }
478    }
479}
480
481static void chardevice_init(ps_chardevice_t *dev, void *vaddr, const int *irqs)
482{
483    assert(dev != NULL);
484    memset(dev, 0, sizeof(*dev));
485    dev->vaddr      = vaddr;
486    dev->read       = &exynos_uart_read;
487    dev->write      = &exynos_uart_write;
488    dev->handle_irq = &uart_handle_irq;
489    dev->irqs       = irqs;
490    dev->flags      = SERIAL_AUTO_CR;
491    /* TODO */
492    dev->clk        = NULL;
493}
494
495int exynos_serial_init(enum chardev_id id, void *vaddr, mux_sys_t *mux_sys,
496                       clk_t *clk_src, ps_chardevice_t *dev)
497{
498    int v;
499    uart_flush(dev);
500
501    if (clk_src != NULL) {
502        clk = clk_src;
503    }
504
505    /* Set character encoding */
506    serial_configure(dev, 115200UL, 8, PARITY_NONE, 1);
507    /* Set FIFO trigger levels */
508    v = FIFO_EN;
509    v |= FIFO_RXLVL(FIFO_RXLVL_VAL);
510    v |= FIFO_TXLVL(FIFO_TXLVL_VAL);
511    *REG_PTR(dev->vaddr, UFCON) = v;
512    /* Configure TX/RX modes and enable TX/RX */
513    v = CON_RX_TIMEOUT(RX_TIMEOUT_VAL) | CON_RXTIMEOUT_ENABLE;
514    v |= (CON_TXMODE(POLL) | CON_RXMODE(POLL));
515    v |= CON_TXIRQTYPE_LEVEL | CON_RXIRQTYPE_LEVEL;
516    *REG_PTR(dev->vaddr, UCON) = v;
517    /* Enable RX IRQ */
518    *REG_PTR(dev->vaddr, UINTM) = ~INT_RX;
519    *REG_PTR(dev->vaddr, UINTP) = INT_RX | INT_TX | INT_ERR | INT_MODEM;
520
521    return 0;
522}
523
524static clk_t *clk_init(enum clk_id clock_id, ps_io_ops_t *ops)
525{
526    assert(ops != NULL);
527    if (clock_sys_valid(&ops->clock_sys)) {
528        return clk_get_clock(&ops->clock_sys, clock_id);
529    }
530    return NULL;
531}
532
533int serial_init(enum chardev_id id, ps_io_ops_t *ops,
534                ps_chardevice_t *dev)
535{
536    void *vaddr;
537    clk_t *clk;
538    vaddr = ps_io_map(&ops->io_mapper, uart_paddr[id], BIT(12), 0, PS_MEM_NORMAL);
539    if (vaddr == NULL) {
540        return -1;
541    }
542    clk = clk_init(uart_clk[id], ops);
543    mux_uart_init(uart_mux[id], (mux_sys_t *)&ops->mux_sys);
544    chardevice_init(dev, vaddr, &uart_irqs[id][0]);
545    dev->id = id;
546    return exynos_serial_init(id, vaddr, &ops->mux_sys, clk, dev);
547}
548
549int uart_init(const struct dev_defn *defn, const ps_io_ops_t *ops, ps_chardevice_t *dev)
550{
551    return serial_init(defn->id, (ps_io_ops_t *)ops, dev);
552}
553
554ps_chardevice_t *ps_cdev_init(enum chardev_id id, const ps_io_ops_t *o, ps_chardevice_t *d)
555{
556    unsigned int i;
557    for (i = 0; i < ARRAY_SIZE(dev_defn); i++) {
558        if (dev_defn[i].id == id) {
559            return (dev_defn[i].init_fn(dev_defn + i, o, d)) ? NULL : d;
560        }
561    }
562    return NULL;
563}
564
565ps_chardevice_t *ps_cdev_static_init(const ps_io_ops_t *o, ps_chardevice_t *d, void *params)
566{
567
568    if (params == NULL) {
569        return NULL;
570    }
571
572    static_serial_params_t *serial_params = (static_serial_params_t *) params;
573    clk_t *clk;
574
575    enum clk_id clock_id = serial_params->clock_id;
576    enum mux_feature uart_mux_feature = serial_params->uart_mux_feature;
577    void *vaddr = serial_params->vaddr;
578    if (vaddr == NULL) {
579        return NULL;
580    }
581    clk = clk_init(clock_id, (ps_io_ops_t *)o);
582    mux_uart_init(uart_mux_feature, (mux_sys_t *) &o->mux_sys);
583    chardevice_init(d, vaddr, NULL);
584    return exynos_serial_init(0, vaddr, (mux_sys_t *) &o->mux_sys, clk, d) ? NULL : d;
585}
586