/*
 * IMX31 UARTS
 *
 * Copyright (c) 2008 OKL
 * Originally Written by Hans Jiang
 * Copyright (c) 2011 NICTA Pty Ltd.
 *
 * This work is licensed under the terms of the GNU GPL, version 2 or later.
 * See the COPYING file in the top-level directory.
 *
 * This is a `bare-bones' implementation of the IMX series serial ports.
 * TODO:
 *  -- implement FIFOs.  The real hardware has 32 word transmit
 *                       and receive FIFOs; we currently use a 1-char buffer
 *  -- implement DMA
 *  -- implement BAUD-rate and modem lines, for when the backend
 *     is a real serial device.
 */

#include "hw/hw.h"
#include "hw/sysbus.h"
#include "sysemu/sysemu.h"
#include "sysemu/char.h"
#include "hw/arm/imx.h"

//#define DEBUG_SERIAL 1
#ifdef DEBUG_SERIAL
#define DPRINTF(fmt, args...) \
do { printf("imx_serial: " fmt , ##args); } while (0)
#else
#define DPRINTF(fmt, args...) do {} while (0)
#endif

/*
 * Define to 1 for messages about attempts to
 * access unimplemented registers or similar.
 */
//#define DEBUG_IMPLEMENTATION 1
#ifdef DEBUG_IMPLEMENTATION
#  define IPRINTF(fmt, args...) \
    do  { fprintf(stderr, "imx_serial: " fmt, ##args); } while (0)
#else
#  define IPRINTF(fmt, args...) do {} while (0)
#endif

typedef struct {
    SysBusDevice busdev;
    MemoryRegion iomem;
    int32_t readbuff;

    uint32_t usr1;
    uint32_t usr2;
    uint32_t ucr1;
    uint32_t ucr2;
    uint32_t uts1;

    /*
     * The registers below are implemented just so that the
     * guest OS sees what it has written
     */
    uint32_t onems;
    uint32_t ufcr;
    uint32_t ubmr;
    uint32_t ubrc;
    uint32_t ucr3;

    qemu_irq irq;
    CharDriverState *chr;
} IMXSerialState;

static const VMStateDescription vmstate_imx_serial = {
    .name = "imx-serial",
    .version_id = 1,
    .minimum_version_id = 1,
    .minimum_version_id_old = 1,
    .fields = (VMStateField[]) {
        VMSTATE_INT32(readbuff, IMXSerialState),
        VMSTATE_UINT32(usr1, IMXSerialState),
        VMSTATE_UINT32(usr2, IMXSerialState),
        VMSTATE_UINT32(ucr1, IMXSerialState),
        VMSTATE_UINT32(uts1, IMXSerialState),
        VMSTATE_UINT32(onems, IMXSerialState),
        VMSTATE_UINT32(ufcr, IMXSerialState),
        VMSTATE_UINT32(ubmr, IMXSerialState),
        VMSTATE_UINT32(ubrc, IMXSerialState),
        VMSTATE_UINT32(ucr3, IMXSerialState),
        VMSTATE_END_OF_LIST()
    },
};


#define URXD_CHARRDY    (1<<15)   /* character read is valid */
#define URXD_ERR        (1<<14)   /* Character has error */
#define URXD_BRK        (1<<11)   /* Break received */

#define USR1_PARTYER    (1<<15)   /* Parity Error */
#define USR1_RTSS       (1<<14)   /* RTS pin status */
#define USR1_TRDY       (1<<13)   /* Tx ready */
#define USR1_RTSD       (1<<12)   /* RTS delta: pin changed state */
#define USR1_ESCF       (1<<11)   /* Escape sequence interrupt */
#define USR1_FRAMERR    (1<<10)   /* Framing error  */
#define USR1_RRDY       (1<<9)    /* receiver ready */
#define USR1_AGTIM      (1<<8)    /* Aging timer interrupt */
#define USR1_DTRD       (1<<7)    /* DTR changed */
#define USR1_RXDS       (1<<6)    /* Receiver is idle */
#define USR1_AIRINT     (1<<5)    /* Aysnch IR interrupt */
#define USR1_AWAKE      (1<<4)    /* Falling edge detected on RXd pin */

#define USR2_ADET       (1<<15)   /* Autobaud complete */
#define USR2_TXFE       (1<<14)   /* Transmit FIFO empty */
#define USR2_DTRF       (1<<13)   /* DTR/DSR transition */
#define USR2_IDLE       (1<<12)   /* UART has been idle for too long */
#define USR2_ACST       (1<<11)   /* Autobaud counter stopped */
#define USR2_RIDELT     (1<<10)   /* Ring Indicator delta */
#define USR2_RIIN       (1<<9)    /* Ring Indicator Input */
#define USR2_IRINT      (1<<8)    /* Serial Infrared Interrupt */
#define USR2_WAKE       (1<<7)    /* Start bit detected */
#define USR2_DCDDELT    (1<<6)    /* Data Carrier Detect delta */
#define USR2_DCDIN      (1<<5)    /* Data Carrier Detect Input */
#define USR2_RTSF       (1<<4)    /* RTS transition */
#define USR2_TXDC       (1<<3)    /* Transmission complete */
#define USR2_BRCD       (1<<2)    /* Break condition detected */
#define USR2_ORE        (1<<1)    /* Overrun error */
#define USR2_RDR        (1<<0)    /* Receive data ready */

#define UCR1_TRDYEN     (1<<13)   /* Tx Ready Interrupt Enable */
#define UCR1_RRDYEN     (1<<9)    /* Rx Ready Interrupt Enable */
#define UCR1_TXMPTYEN   (1<<6)    /* Tx Empty Interrupt Enable */
#define UCR1_UARTEN     (1<<0)    /* UART Enable */

#define UCR2_TXEN       (1<<2)    /* Transmitter enable */
#define UCR2_RXEN       (1<<1)    /* Receiver enable */
#define UCR2_SRST       (1<<0)    /* Reset complete */

#define UTS1_TXEMPTY    (1<<6)
#define UTS1_RXEMPTY    (1<<5)
#define UTS1_TXFULL     (1<<4)
#define UTS1_RXFULL     (1<<3)

static void imx_update(IMXSerialState *s)
{
    uint32_t flags;

    flags = (s->usr1 & s->ucr1) & (USR1_TRDY|USR1_RRDY);
    if (!(s->ucr1 & UCR1_TXMPTYEN)) {
        flags &= ~USR1_TRDY;
    }

    qemu_set_irq(s->irq, !!flags);
}

static void imx_serial_reset(IMXSerialState *s)
{

    s->usr1 = USR1_TRDY | USR1_RXDS;
    /*
     * Fake attachment of a terminal: assert RTS.
     */
    s->usr1 |= USR1_RTSS;
    s->usr2 = USR2_TXFE | USR2_TXDC | USR2_DCDIN;
    s->uts1 = UTS1_RXEMPTY | UTS1_TXEMPTY;
    s->ucr1 = 0;
    s->ucr2 = UCR2_SRST;
    s->ucr3 = 0x700;
    s->ubmr = 0;
    s->ubrc = 4;
    s->readbuff = URXD_ERR;
}

static void imx_serial_reset_at_boot(DeviceState *dev)
{
    IMXSerialState *s = container_of(dev, IMXSerialState, busdev.qdev);

    imx_serial_reset(s);

    /*
     * enable the uart on boot, so messages from the linux decompresser
     * are visible.  On real hardware this is done by the boot rom
     * before anything else is loaded.
     */
    s->ucr1 = UCR1_UARTEN;
    s->ucr2 = UCR2_TXEN;

}

static uint64_t imx_serial_read(void *opaque, hwaddr offset,
                                unsigned size)
{
    IMXSerialState *s = (IMXSerialState *)opaque;
    uint32_t c;

    DPRINTF("read(offset=%x)\n", offset >> 2);
    switch (offset >> 2) {
    case 0x0: /* URXD */
        c = s->readbuff;
        if (!(s->uts1 & UTS1_RXEMPTY)) {
            /* Character is valid */
            c |= URXD_CHARRDY;
            s->usr1 &= ~USR1_RRDY;
            s->usr2 &= ~USR2_RDR;
            s->uts1 |= UTS1_RXEMPTY;
            imx_update(s);
            qemu_chr_accept_input(s->chr);
        }
        return c;

    case 0x20: /* UCR1 */
        return s->ucr1;

    case 0x21: /* UCR2 */
        return s->ucr2;

    case 0x25: /* USR1 */
        return s->usr1;

    case 0x26: /* USR2 */
        return s->usr2;

    case 0x2A: /* BRM Modulator */
        return s->ubmr;

    case 0x2B: /* Baud Rate Count */
        return s->ubrc;

    case 0x2d: /* Test register */
        return s->uts1;

    case 0x24: /* UFCR */
        return s->ufcr;

    case 0x2c:
        return s->onems;

    case 0x22: /* UCR3 */
        return s->ucr3;

    case 0x23: /* UCR4 */
    case 0x29: /* BRM Incremental */
        return 0x0; /* TODO */

    default:
        IPRINTF("imx_serial_read: bad offset: 0x%x\n", (int)offset);
        return 0;
    }
}

static void imx_serial_write(void *opaque, hwaddr offset,
                      uint64_t value, unsigned size)
{
    IMXSerialState *s = (IMXSerialState *)opaque;
    unsigned char ch;

    DPRINTF("write(offset=%x, value = %x) to %s\n",
            offset >> 2,
            (unsigned int)value, s->chr ? s->chr->label : "NODEV");

    switch (offset >> 2) {
    case 0x10: /* UTXD */
        ch = value;
        if (s->ucr2 & UCR2_TXEN) {
            if (s->chr) {
                qemu_chr_fe_write(s->chr, &ch, 1);
            }
            s->usr1 &= ~USR1_TRDY;
            imx_update(s);
            s->usr1 |= USR1_TRDY;
            imx_update(s);
        }
        break;

    case 0x20: /* UCR1 */
        s->ucr1 = value & 0xffff;
        DPRINTF("write(ucr1=%x)\n", (unsigned int)value);
        imx_update(s);
        break;

    case 0x21: /* UCR2 */
        /*
         * Only a few bits in control register 2 are implemented as yet.
         * If it's intended to use a real serial device as a back-end, this
         * register will have to be implemented more fully.
         */
        if (!(value & UCR2_SRST)) {
            imx_serial_reset(s);
            imx_update(s);
            value |= UCR2_SRST;
        }
        if (value & UCR2_RXEN) {
            if (!(s->ucr2 & UCR2_RXEN)) {
                qemu_chr_accept_input(s->chr);
            }
        }
        s->ucr2 = value & 0xffff;
        break;

    case 0x25: /* USR1 */
        value &= USR1_AWAKE | USR1_AIRINT | USR1_DTRD | USR1_AGTIM |
            USR1_FRAMERR | USR1_ESCF | USR1_RTSD | USR1_PARTYER;
        s->usr1 &= ~value;
        break;

    case 0x26: /* USR2 */
       /*
        * Writing 1 to some bits clears them; all other
        * values are ignored
        */
        value &= USR2_ADET | USR2_DTRF | USR2_IDLE | USR2_ACST |
            USR2_RIDELT | USR2_IRINT | USR2_WAKE |
            USR2_DCDDELT | USR2_RTSF | USR2_BRCD | USR2_ORE;
        s->usr2 &= ~value;
        break;

        /*
         * Linux expects to see what it writes to these registers
         * We don't currently alter the baud rate
         */
    case 0x29: /* UBIR */
        s->ubrc = value & 0xffff;
        break;

    case 0x2a: /* UBMR */
        s->ubmr = value & 0xffff;
        break;

    case 0x2c: /* One ms reg */
        s->onems = value & 0xffff;
        break;

    case 0x24: /* FIFO control register */
        s->ufcr = value & 0xffff;
        break;

    case 0x22: /* UCR3 */
        s->ucr3 = value & 0xffff;
        break;

    case 0x2d: /* UTS1 */
    case 0x23: /* UCR4 */
        IPRINTF("Unimplemented Register %x written to\n", offset >> 2);
        /* TODO */
        break;

    default:
        IPRINTF("imx_serial_write: Bad offset 0x%x\n", (int)offset);
    }
}

static int imx_can_receive(void *opaque)
{
    IMXSerialState *s = (IMXSerialState *)opaque;
    return !(s->usr1 & USR1_RRDY);
}

static void imx_put_data(void *opaque, uint32_t value)
{
    IMXSerialState *s = (IMXSerialState *)opaque;
    DPRINTF("received char\n");
    s->usr1 |= USR1_RRDY;
    s->usr2 |= USR2_RDR;
    s->uts1 &= ~UTS1_RXEMPTY;
    s->readbuff = value;
    imx_update(s);
}

static void imx_receive(void *opaque, const uint8_t *buf, int size)
{
    imx_put_data(opaque, *buf);
}

static void imx_event(void *opaque, int event)
{
    if (event == CHR_EVENT_BREAK) {
        imx_put_data(opaque, URXD_BRK);
    }
}


static const struct MemoryRegionOps imx_serial_ops = {
    .read = imx_serial_read,
    .write = imx_serial_write,
    .endianness = DEVICE_NATIVE_ENDIAN,
};

static int imx_serial_init(SysBusDevice *dev)
{
    IMXSerialState *s = FROM_SYSBUS(IMXSerialState, dev);


    memory_region_init_io(&s->iomem, OBJECT(s), &imx_serial_ops, s,
                          "imx-serial", 0x1000);
    sysbus_init_mmio(dev, &s->iomem);
    sysbus_init_irq(dev, &s->irq);

    if (s->chr) {
        qemu_chr_add_handlers(s->chr, imx_can_receive, imx_receive,
                              imx_event, s);
    } else {
        DPRINTF("No char dev for uart at 0x%lx\n",
                (unsigned long)s->iomem.ram_addr);
    }

    return 0;
}

void imx_serial_create(int uart, const hwaddr addr, qemu_irq irq)
{
    DeviceState *dev;
    SysBusDevice *bus;
    CharDriverState *chr;
    const char chr_name[] = "serial";
    char label[ARRAY_SIZE(chr_name) + 1];

    dev = qdev_create(NULL, "imx-serial");

    if (uart >= MAX_SERIAL_PORTS) {
        hw_error("Cannot assign uart %d: QEMU supports only %d ports\n",
                 uart, MAX_SERIAL_PORTS);
    }
    chr = serial_hds[uart];
    if (!chr) {
        snprintf(label, ARRAY_SIZE(label), "%s%d", chr_name, uart);
        chr = qemu_chr_new(label, "null", NULL);
        if (!(chr)) {
            hw_error("Can't assign serial port to imx-uart%d.\n", uart);
        }
    }

    qdev_prop_set_chr(dev, "chardev", chr);
    bus = SYS_BUS_DEVICE(dev);
    qdev_init_nofail(dev);
    if (addr != (hwaddr)-1) {
        sysbus_mmio_map(bus, 0, addr);
    }
    sysbus_connect_irq(bus, 0, irq);

}


static Property imx32_serial_properties[] = {
    DEFINE_PROP_CHR("chardev", IMXSerialState, chr),
    DEFINE_PROP_END_OF_LIST(),
};

static void imx_serial_class_init(ObjectClass *klass, void *data)
{
    DeviceClass *dc = DEVICE_CLASS(klass);
    SysBusDeviceClass *k = SYS_BUS_DEVICE_CLASS(klass);

    k->init = imx_serial_init;
    dc->vmsd = &vmstate_imx_serial;
    dc->reset = imx_serial_reset_at_boot;
    dc->desc = "i.MX series UART";
    dc->props = imx32_serial_properties;
}

static const TypeInfo imx_serial_info = {
    .name = "imx-serial",
    .parent = TYPE_SYS_BUS_DEVICE,
    .instance_size = sizeof(IMXSerialState),
    .class_init = imx_serial_class_init,
};

static void imx_serial_register_types(void)
{
    type_register_static(&imx_serial_info);
}

type_init(imx_serial_register_types)
