/*
 * i.MX Fast Ethernet Controller emulation.
 *
 * Copyright (c) 2013 Jean-Christophe Dubois. <jcd@tribudubois.net>
 *
 * Based on Coldfire Fast Ethernet Controller emulation.
 *
 * Copyright (c) 2007 CodeSourcery.
 *
 *  This program is free software; you can redistribute it and/or modify it
 *  under the terms of the GNU General Public License as published by the
 *  Free Software Foundation; either version 2 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful, but WITHOUT
 *  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 *  FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
 *  for more details.
 *
 *  You should have received a copy of the GNU General Public License along
 *  with this program; if not, see <http://www.gnu.org/licenses/>.
 */

#include "hw/net/imx_fec.h"
#include "sysemu/dma.h"

/* For crc32 */
#include <zlib.h>

#ifndef IMX_FEC_DEBUG
#define IMX_FEC_DEBUG          0
#endif

#ifndef IMX_PHY_DEBUG
#define IMX_PHY_DEBUG          0
#endif

#if IMX_FEC_DEBUG
#define FEC_PRINTF(fmt, ...) \
    do { fprintf(stderr, "%s[%s]: " fmt , TYPE_IMX_FEC, __func__, \
                 ## __VA_ARGS__); \
    } while (0)
#else
#define FEC_PRINTF(fmt, ...) do {} while (0)
#endif

#if IMX_PHY_DEBUG
#define PHY_PRINTF(fmt, ...) \
    do { fprintf(stderr, "%s.phy[%s]: " fmt , TYPE_IMX_FEC, __func__, \
                 ## __VA_ARGS__); \
    } while (0)
#else
#define PHY_PRINTF(fmt, ...) do {} while (0)
#endif

static const VMStateDescription vmstate_imx_fec = {
    .name = TYPE_IMX_FEC,
    .version_id = 1,
    .minimum_version_id = 1,
    .fields = (VMStateField[]) {
        VMSTATE_UINT32(irq_state, IMXFECState),
        VMSTATE_UINT32(eir, IMXFECState),
        VMSTATE_UINT32(eimr, IMXFECState),
        VMSTATE_UINT32(rx_enabled, IMXFECState),
        VMSTATE_UINT32(rx_descriptor, IMXFECState),
        VMSTATE_UINT32(tx_descriptor, IMXFECState),
        VMSTATE_UINT32(ecr, IMXFECState),
        VMSTATE_UINT32(mmfr, IMXFECState),
        VMSTATE_UINT32(mscr, IMXFECState),
        VMSTATE_UINT32(mibc, IMXFECState),
        VMSTATE_UINT32(rcr, IMXFECState),
        VMSTATE_UINT32(tcr, IMXFECState),
        VMSTATE_UINT32(tfwr, IMXFECState),
        VMSTATE_UINT32(frsr, IMXFECState),
        VMSTATE_UINT32(erdsr, IMXFECState),
        VMSTATE_UINT32(etdsr, IMXFECState),
        VMSTATE_UINT32(emrbr, IMXFECState),
        VMSTATE_UINT32(miigsk_cfgr, IMXFECState),
        VMSTATE_UINT32(miigsk_enr, IMXFECState),

        VMSTATE_UINT32(phy_status, IMXFECState),
        VMSTATE_UINT32(phy_control, IMXFECState),
        VMSTATE_UINT32(phy_advertise, IMXFECState),
        VMSTATE_UINT32(phy_int, IMXFECState),
        VMSTATE_UINT32(phy_int_mask, IMXFECState),
        VMSTATE_END_OF_LIST()
    }
};

#define PHY_INT_ENERGYON            (1 << 7)
#define PHY_INT_AUTONEG_COMPLETE    (1 << 6)
#define PHY_INT_FAULT               (1 << 5)
#define PHY_INT_DOWN                (1 << 4)
#define PHY_INT_AUTONEG_LP          (1 << 3)
#define PHY_INT_PARFAULT            (1 << 2)
#define PHY_INT_AUTONEG_PAGE        (1 << 1)

static void imx_fec_update(IMXFECState *s);

/*
 * The MII phy could raise a GPIO to the processor which in turn
 * could be handled as an interrpt by the OS.
 * For now we don't handle any GPIO/interrupt line, so the OS will
 * have to poll for the PHY status.
 */
static void phy_update_irq(IMXFECState *s)
{
    imx_fec_update(s);
}

static void phy_update_link(IMXFECState *s)
{
    /* Autonegotiation status mirrors link status.  */
    if (qemu_get_queue(s->nic)->link_down) {
        PHY_PRINTF("link is down\n");
        s->phy_status &= ~0x0024;
        s->phy_int |= PHY_INT_DOWN;
    } else {
        PHY_PRINTF("link is up\n");
        s->phy_status |= 0x0024;
        s->phy_int |= PHY_INT_ENERGYON;
        s->phy_int |= PHY_INT_AUTONEG_COMPLETE;
    }
    phy_update_irq(s);
}

static void imx_fec_set_link(NetClientState *nc)
{
    phy_update_link(IMX_FEC(qemu_get_nic_opaque(nc)));
}

static void phy_reset(IMXFECState *s)
{
    s->phy_status = 0x7809;
    s->phy_control = 0x3000;
    s->phy_advertise = 0x01e1;
    s->phy_int_mask = 0;
    s->phy_int = 0;
    phy_update_link(s);
}

static uint32_t do_phy_read(IMXFECState *s, int reg)
{
    uint32_t val;

    if (reg > 31) {
        /* we only advertise one phy */
        return 0;
    }

    switch (reg) {
    case 0:     /* Basic Control */
        val = s->phy_control;
        break;
    case 1:     /* Basic Status */
        val = s->phy_status;
        break;
    case 2:     /* ID1 */
        val = 0x0007;
        break;
    case 3:     /* ID2 */
        val = 0xc0d1;
        break;
    case 4:     /* Auto-neg advertisement */
        val = s->phy_advertise;
        break;
    case 5:     /* Auto-neg Link Partner Ability */
        val = 0x0f71;
        break;
    case 6:     /* Auto-neg Expansion */
        val = 1;
        break;
    case 29:    /* Interrupt source.  */
        val = s->phy_int;
        s->phy_int = 0;
        phy_update_irq(s);
        break;
    case 30:    /* Interrupt mask */
        val = s->phy_int_mask;
        break;
    case 17:
    case 18:
    case 27:
    case 31:
        qemu_log_mask(LOG_UNIMP, "%s.phy[%s]: reg %d not implemented\n",
                      TYPE_IMX_FEC, __func__, reg);
        val = 0;
        break;
    default:
        qemu_log_mask(LOG_GUEST_ERROR, "%s[%s]: Bad address at offset %d\n",
                      TYPE_IMX_FEC, __func__, reg);
        val = 0;
        break;
    }

    PHY_PRINTF("read 0x%04x @ %d\n", val, reg);

    return val;
}

static void do_phy_write(IMXFECState *s, int reg, uint32_t val)
{
    PHY_PRINTF("write 0x%04x @ %d\n", val, reg);

    if (reg > 31) {
        /* we only advertise one phy */
        return;
    }

    switch (reg) {
    case 0:     /* Basic Control */
        if (val & 0x8000) {
            phy_reset(s);
        } else {
            s->phy_control = val & 0x7980;
            /* Complete autonegotiation immediately.  */
            if (val & 0x1000) {
                s->phy_status |= 0x0020;
            }
        }
        break;
    case 4:     /* Auto-neg advertisement */
        s->phy_advertise = (val & 0x2d7f) | 0x80;
        break;
    case 30:    /* Interrupt mask */
        s->phy_int_mask = val & 0xff;
        phy_update_irq(s);
        break;
    case 17:
    case 18:
    case 27:
    case 31:
        qemu_log_mask(LOG_UNIMP, "%s.phy[%s]: reg %d not implemented\n",
                      TYPE_IMX_FEC, __func__, reg);
        break;
    default:
        qemu_log_mask(LOG_GUEST_ERROR, "%s.phy[%s]: Bad address at offset %d\n",
                      TYPE_IMX_FEC, __func__, reg);
        break;
    }
}

static void imx_fec_read_bd(IMXFECBufDesc *bd, dma_addr_t addr)
{
    dma_memory_read(&address_space_memory, addr, bd, sizeof(*bd));
}

static void imx_fec_write_bd(IMXFECBufDesc *bd, dma_addr_t addr)
{
    dma_memory_write(&address_space_memory, addr, bd, sizeof(*bd));
}

static void imx_fec_update(IMXFECState *s)
{
    uint32_t active;
    uint32_t changed;

    active = s->eir & s->eimr;
    changed = active ^ s->irq_state;
    if (changed) {
        qemu_set_irq(s->irq, active);
    }
    s->irq_state = active;
}

static void imx_fec_do_tx(IMXFECState *s)
{
    int frame_size = 0;
    uint8_t frame[FEC_MAX_FRAME_SIZE];
    uint8_t *ptr = frame;
    uint32_t addr = s->tx_descriptor;

    while (1) {
        IMXFECBufDesc bd;
        int len;

        imx_fec_read_bd(&bd, addr);
        FEC_PRINTF("tx_bd %x flags %04x len %d data %08x\n",
                   addr, bd.flags, bd.length, bd.data);
        if ((bd.flags & FEC_BD_R) == 0) {
            /* Run out of descriptors to transmit.  */
            break;
        }
        len = bd.length;
        if (frame_size + len > FEC_MAX_FRAME_SIZE) {
            len = FEC_MAX_FRAME_SIZE - frame_size;
            s->eir |= FEC_INT_BABT;
        }
        dma_memory_read(&address_space_memory, bd.data, ptr, len);
        ptr += len;
        frame_size += len;
        if (bd.flags & FEC_BD_L) {
            /* Last buffer in frame.  */
            qemu_send_packet(qemu_get_queue(s->nic), frame, len);
            ptr = frame;
            frame_size = 0;
            s->eir |= FEC_INT_TXF;
        }
        s->eir |= FEC_INT_TXB;
        bd.flags &= ~FEC_BD_R;
        /* Write back the modified descriptor.  */
        imx_fec_write_bd(&bd, addr);
        /* Advance to the next descriptor.  */
        if ((bd.flags & FEC_BD_W) != 0) {
            addr = s->etdsr;
        } else {
            addr += 8;
        }
    }

    s->tx_descriptor = addr;

    imx_fec_update(s);
}

static void imx_fec_enable_rx(IMXFECState *s)
{
    IMXFECBufDesc bd;
    uint32_t tmp;

    imx_fec_read_bd(&bd, s->rx_descriptor);

    tmp = ((bd.flags & FEC_BD_E) != 0);

    if (!tmp) {
        FEC_PRINTF("RX buffer full\n");
    } else if (!s->rx_enabled) {
        qemu_flush_queued_packets(qemu_get_queue(s->nic));
    }

    s->rx_enabled = tmp;
}

static void imx_fec_reset(DeviceState *d)
{
    IMXFECState *s = IMX_FEC(d);

    /* Reset the FEC */
    s->eir = 0;
    s->eimr = 0;
    s->rx_enabled = 0;
    s->ecr = 0;
    s->mscr = 0;
    s->mibc = 0xc0000000;
    s->rcr = 0x05ee0001;
    s->tcr = 0;
    s->tfwr = 0;
    s->frsr = 0x500;
    s->miigsk_cfgr = 0;
    s->miigsk_enr = 0x6;

    /* We also reset the PHY */
    phy_reset(s);
}

static uint64_t imx_fec_read(void *opaque, hwaddr addr, unsigned size)
{
    IMXFECState *s = IMX_FEC(opaque);

    FEC_PRINTF("reading from @ 0x%03x\n", (int)addr);

    switch (addr & 0x3ff) {
    case 0x004:
        return s->eir;
    case 0x008:
        return s->eimr;
    case 0x010:
        return s->rx_enabled ? (1 << 24) : 0;   /* RDAR */
    case 0x014:
        return 0;   /* TDAR */
    case 0x024:
        return s->ecr;
    case 0x040:
        return s->mmfr;
    case 0x044:
        return s->mscr;
    case 0x064:
        return s->mibc; /* MIBC */
    case 0x084:
        return s->rcr;
    case 0x0c4:
        return s->tcr;
    case 0x0e4:     /* PALR */
        return (s->conf.macaddr.a[0] << 24)
               | (s->conf.macaddr.a[1] << 16)
               | (s->conf.macaddr.a[2] << 8)
               | s->conf.macaddr.a[3];
        break;
    case 0x0e8:     /* PAUR */
        return (s->conf.macaddr.a[4] << 24)
               | (s->conf.macaddr.a[5] << 16)
               | 0x8808;
    case 0x0ec:
        return 0x10000; /* OPD */
    case 0x118:
        return 0;
    case 0x11c:
        return 0;
    case 0x120:
        return 0;
    case 0x124:
        return 0;
    case 0x144:
        return s->tfwr;
    case 0x14c:
        return 0x600;
    case 0x150:
        return s->frsr;
    case 0x180:
        return s->erdsr;
    case 0x184:
        return s->etdsr;
    case 0x188:
        return s->emrbr;
    case 0x300:
        return s->miigsk_cfgr;
    case 0x308:
        return s->miigsk_enr;
    default:
        qemu_log_mask(LOG_GUEST_ERROR, "%s[%s]: Bad address at offset %d\n",
                      TYPE_IMX_FEC, __func__, (int)addr);
        return 0;
    }
}

static void imx_fec_write(void *opaque, hwaddr addr,
                          uint64_t value, unsigned size)
{
    IMXFECState *s = IMX_FEC(opaque);

    FEC_PRINTF("writing 0x%08x @ 0x%03x\n", (int)value, (int)addr);

    switch (addr & 0x3ff) {
    case 0x004: /* EIR */
        s->eir &= ~value;
        break;
    case 0x008: /* EIMR */
        s->eimr = value;
        break;
    case 0x010: /* RDAR */
        if ((s->ecr & FEC_EN) && !s->rx_enabled) {
            imx_fec_enable_rx(s);
        }
        break;
    case 0x014: /* TDAR */
        if (s->ecr & FEC_EN) {
            imx_fec_do_tx(s);
        }
        break;
    case 0x024: /* ECR */
        s->ecr = value;
        if (value & FEC_RESET) {
            imx_fec_reset(DEVICE(s));
        }
        if ((s->ecr & FEC_EN) == 0) {
            s->rx_enabled = 0;
        }
        break;
    case 0x040: /* MMFR */
        /* store the value */
        s->mmfr = value;
        if (extract32(value, 28, 1)) {
            do_phy_write(s, extract32(value, 18, 9), extract32(value, 0, 16));
        } else {
            s->mmfr = do_phy_read(s, extract32(value, 18, 9));
        }
        /* raise the interrupt as the PHY operation is done */
        s->eir |= FEC_INT_MII;
        break;
    case 0x044: /* MSCR */
        s->mscr = value & 0xfe;
        break;
    case 0x064: /* MIBC */
        /* TODO: Implement MIB.  */
        s->mibc = (value & 0x80000000) ? 0xc0000000 : 0;
        break;
    case 0x084: /* RCR */
        s->rcr = value & 0x07ff003f;
        /* TODO: Implement LOOP mode.  */
        break;
    case 0x0c4: /* TCR */
        /* We transmit immediately, so raise GRA immediately.  */
        s->tcr = value;
        if (value & 1) {
            s->eir |= FEC_INT_GRA;
        }
        break;
    case 0x0e4: /* PALR */
        s->conf.macaddr.a[0] = value >> 24;
        s->conf.macaddr.a[1] = value >> 16;
        s->conf.macaddr.a[2] = value >> 8;
        s->conf.macaddr.a[3] = value;
        break;
    case 0x0e8: /* PAUR */
        s->conf.macaddr.a[4] = value >> 24;
        s->conf.macaddr.a[5] = value >> 16;
        break;
    case 0x0ec: /* OPDR */
        break;
    case 0x118: /* IAUR */
    case 0x11c: /* IALR */
    case 0x120: /* GAUR */
    case 0x124: /* GALR */
        /* TODO: implement MAC hash filtering.  */
        break;
    case 0x144: /* TFWR */
        s->tfwr = value & 3;
        break;
    case 0x14c: /* FRBR */
        /* FRBR writes ignored.  */
        break;
    case 0x150: /* FRSR */
        s->frsr = (value & 0x3fc) | 0x400;
        break;
    case 0x180: /* ERDSR */
        s->erdsr = value & ~3;
        s->rx_descriptor = s->erdsr;
        break;
    case 0x184: /* ETDSR */
        s->etdsr = value & ~3;
        s->tx_descriptor = s->etdsr;
        break;
    case 0x188: /* EMRBR */
        s->emrbr = value & 0x7f0;
        break;
    case 0x300: /* MIIGSK_CFGR */
        s->miigsk_cfgr = value & 0x53;
        break;
    case 0x308: /* MIIGSK_ENR */
        s->miigsk_enr = (value & 0x2) ? 0x6 : 0;
        break;
    default:
        qemu_log_mask(LOG_GUEST_ERROR, "%s[%s]: Bad address at offset %d\n",
                      TYPE_IMX_FEC, __func__, (int)addr);
        break;
    }

    imx_fec_update(s);
}

static int imx_fec_can_receive(NetClientState *nc)
{
    IMXFECState *s = IMX_FEC(qemu_get_nic_opaque(nc));

    return s->rx_enabled;
}

static ssize_t imx_fec_receive(NetClientState *nc, const uint8_t *buf,
                               size_t len)
{
    IMXFECState *s = IMX_FEC(qemu_get_nic_opaque(nc));
    IMXFECBufDesc bd;
    uint32_t flags = 0;
    uint32_t addr;
    uint32_t crc;
    uint32_t buf_addr;
    uint8_t *crc_ptr;
    unsigned int buf_len;
    size_t size = len;

    FEC_PRINTF("len %d\n", (int)size);

    if (!s->rx_enabled) {
        qemu_log_mask(LOG_GUEST_ERROR, "%s[%s]: Unexpected packet\n",
                      TYPE_IMX_FEC, __func__);
        return 0;
    }

    /* 4 bytes for the CRC.  */
    size += 4;
    crc = cpu_to_be32(crc32(~0, buf, size));
    crc_ptr = (uint8_t *) &crc;

    /* Huge frames are truncted.  */
    if (size > FEC_MAX_FRAME_SIZE) {
        size = FEC_MAX_FRAME_SIZE;
        flags |= FEC_BD_TR | FEC_BD_LG;
    }

    /* Frames larger than the user limit just set error flags.  */
    if (size > (s->rcr >> 16)) {
        flags |= FEC_BD_LG;
    }

    addr = s->rx_descriptor;
    while (size > 0) {
        imx_fec_read_bd(&bd, addr);
        if ((bd.flags & FEC_BD_E) == 0) {
            /* No descriptors available.  Bail out.  */
            /*
             * FIXME: This is wrong. We should probably either
             * save the remainder for when more RX buffers are
             * available, or flag an error.
             */
            qemu_log_mask(LOG_GUEST_ERROR, "%s[%s]: Lost end of frame\n",
                          TYPE_IMX_FEC, __func__);
            break;
        }
        buf_len = (size <= s->emrbr) ? size : s->emrbr;
        bd.length = buf_len;
        size -= buf_len;
        FEC_PRINTF("rx_bd %x length %d\n", addr, bd.length);
        /* The last 4 bytes are the CRC.  */
        if (size < 4) {
            buf_len += size - 4;
        }
        buf_addr = bd.data;
        dma_memory_write(&address_space_memory, buf_addr, buf, buf_len);
        buf += buf_len;
        if (size < 4) {
            dma_memory_write(&address_space_memory, buf_addr + buf_len,
                             crc_ptr, 4 - size);
            crc_ptr += 4 - size;
        }
        bd.flags &= ~FEC_BD_E;
        if (size == 0) {
            /* Last buffer in frame.  */
            bd.flags |= flags | FEC_BD_L;
            FEC_PRINTF("rx frame flags %04x\n", bd.flags);
            s->eir |= FEC_INT_RXF;
        } else {
            s->eir |= FEC_INT_RXB;
        }
        imx_fec_write_bd(&bd, addr);
        /* Advance to the next descriptor.  */
        if ((bd.flags & FEC_BD_W) != 0) {
            addr = s->erdsr;
        } else {
            addr += 8;
        }
    }
    s->rx_descriptor = addr;
    imx_fec_enable_rx(s);
    imx_fec_update(s);
    return len;
}

static const MemoryRegionOps imx_fec_ops = {
    .read = imx_fec_read,
    .write = imx_fec_write,
    .valid.min_access_size = 4,
    .valid.max_access_size = 4,
    .endianness = DEVICE_NATIVE_ENDIAN,
};

static void imx_fec_cleanup(NetClientState *nc)
{
    IMXFECState *s = IMX_FEC(qemu_get_nic_opaque(nc));

    s->nic = NULL;
}

static NetClientInfo net_imx_fec_info = {
    .type = NET_CLIENT_OPTIONS_KIND_NIC,
    .size = sizeof(NICState),
    .can_receive = imx_fec_can_receive,
    .receive = imx_fec_receive,
    .cleanup = imx_fec_cleanup,
    .link_status_changed = imx_fec_set_link,
};


static void imx_fec_realize(DeviceState *dev, Error **errp)
{
    IMXFECState *s = IMX_FEC(dev);
    SysBusDevice *sbd = SYS_BUS_DEVICE(dev);

    memory_region_init_io(&s->iomem, OBJECT(dev), &imx_fec_ops, s,
                          TYPE_IMX_FEC, 0x400);
    sysbus_init_mmio(sbd, &s->iomem);
    sysbus_init_irq(sbd, &s->irq);
    qemu_macaddr_default_if_unset(&s->conf.macaddr);

    s->conf.peers.ncs[0] = nd_table[0].netdev;

    s->nic = qemu_new_nic(&net_imx_fec_info, &s->conf,
                          object_get_typename(OBJECT(dev)), DEVICE(dev)->id,
                          s);
    qemu_format_nic_info_str(qemu_get_queue(s->nic), s->conf.macaddr.a);
}

static Property imx_fec_properties[] = {
    DEFINE_NIC_PROPERTIES(IMXFECState, conf),
    DEFINE_PROP_END_OF_LIST(),
};

static void imx_fec_class_init(ObjectClass *klass, void *data)
{
    DeviceClass *dc = DEVICE_CLASS(klass);

    dc->vmsd = &vmstate_imx_fec;
    dc->reset = imx_fec_reset;
    dc->props = imx_fec_properties;
    dc->realize = imx_fec_realize;
}

static const TypeInfo imx_fec_info = {
    .name = TYPE_IMX_FEC,
    .parent = TYPE_SYS_BUS_DEVICE,
    .instance_size = sizeof(IMXFECState),
    .class_init = imx_fec_class_init,
};

static void imx_fec_register_types(void)
{
    type_register_static(&imx_fec_info);
}

type_init(imx_fec_register_types)
