/*
 *  IOAPIC emulation logic - common bits of emulated and KVM kernel model
 *
 *  Copyright (c) 2004-2005 Fabrice Bellard
 *  Copyright (c) 2009      Xiantao Zhang, Intel
 *  Copyright (c) 2011      Jan Kiszka, Siemens AG
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2 of the License, or (at your option) any later version.
 *
 * This library 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
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, see <http://www.gnu.org/licenses/>.
 */

#include "qemu/osdep.h"
#include "qapi/error.h"
#include "monitor/monitor.h"
#include "hw/i386/ioapic.h"
#include "hw/i386/ioapic_internal.h"
#include "hw/sysbus.h"

/* ioapic_no count start from 0 to MAX_IOAPICS,
 * remove as static variable from ioapic_common_init.
 * now as a global variable, let child to increase the counter
 * then we can drop the 'instance_no' argument
 * and convert to our QOM's realize function
 */
int ioapic_no;

static void ioapic_irr_dump(Monitor *mon, const char *name, uint32_t bitmap)
{
    int i;

    monitor_printf(mon, "%-10s ", name);
    if (bitmap == 0) {
        monitor_printf(mon, "(none)\n");
        return;
    }
    for (i = 0; i < IOAPIC_NUM_PINS; i++) {
        if (bitmap & (1 << i)) {
            monitor_printf(mon, "%-2u ", i);
        }
    }
    monitor_printf(mon, "\n");
}

void ioapic_print_redtbl(Monitor *mon, IOAPICCommonState *s)
{
    static const char *delm_str[] = {
        "fixed", "lowest", "SMI", "...", "NMI", "INIT", "...", "extINT"};
    uint32_t remote_irr = 0;
    int i;

    monitor_printf(mon, "ioapic ver=0x%x id=0x%02x sel=0x%02x",
                   s->version, s->id, s->ioregsel);
    if (s->ioregsel) {
        monitor_printf(mon, " (redir[%u])\n",
                       (s->ioregsel - IOAPIC_REG_REDTBL_BASE) >> 1);
    } else {
        monitor_printf(mon, "\n");
    }
    for (i = 0; i < IOAPIC_NUM_PINS; i++) {
        uint64_t entry = s->ioredtbl[i];
        uint32_t delm = (uint32_t)((entry & IOAPIC_LVT_DELIV_MODE) >>
                                   IOAPIC_LVT_DELIV_MODE_SHIFT);
        monitor_printf(mon, "pin %-2u 0x%016"PRIx64" dest=%"PRIx64
                       " vec=%-3"PRIu64" %s %-5s %-6s %-6s %s\n",
                       i, entry,
                       (entry >> IOAPIC_LVT_DEST_SHIFT) &
                            (entry & IOAPIC_LVT_DEST_MODE ? 0xff : 0xf),
                       entry & IOAPIC_VECTOR_MASK,
                       entry & IOAPIC_LVT_POLARITY ? "active-lo" : "active-hi",
                       entry & IOAPIC_LVT_TRIGGER_MODE ? "level" : "edge",
                       entry & IOAPIC_LVT_MASKED ? "masked" : "",
                       delm_str[delm],
                       entry & IOAPIC_LVT_DEST_MODE ? "logical" : "physical");

        remote_irr |= entry & IOAPIC_LVT_TRIGGER_MODE ?
                        (entry & IOAPIC_LVT_REMOTE_IRR ? (1 << i) : 0) : 0;
    }
    ioapic_irr_dump(mon, "IRR", s->irr);
    ioapic_irr_dump(mon, "Remote IRR", remote_irr);
}

void ioapic_reset_common(DeviceState *dev)
{
    IOAPICCommonState *s = IOAPIC_COMMON(dev);
    int i;

    s->id = 0;
    s->ioregsel = 0;
    s->irr = 0;
    for (i = 0; i < IOAPIC_NUM_PINS; i++) {
        s->ioredtbl[i] = 1 << IOAPIC_LVT_MASKED_SHIFT;
    }
}

static void ioapic_dispatch_pre_save(void *opaque)
{
    IOAPICCommonState *s = IOAPIC_COMMON(opaque);
    IOAPICCommonClass *info = IOAPIC_COMMON_GET_CLASS(s);

    if (info->pre_save) {
        info->pre_save(s);
    }
}

static int ioapic_dispatch_post_load(void *opaque, int version_id)
{
    IOAPICCommonState *s = IOAPIC_COMMON(opaque);
    IOAPICCommonClass *info = IOAPIC_COMMON_GET_CLASS(s);

    if (info->post_load) {
        info->post_load(s);
    }
    return 0;
}

static void ioapic_common_realize(DeviceState *dev, Error **errp)
{
    IOAPICCommonState *s = IOAPIC_COMMON(dev);
    IOAPICCommonClass *info;

    if (ioapic_no >= MAX_IOAPICS) {
        error_setg(errp, "Only %d ioapics allowed", MAX_IOAPICS);
        return;
    }

    info = IOAPIC_COMMON_GET_CLASS(s);
    info->realize(dev, errp);

    sysbus_init_mmio(SYS_BUS_DEVICE(s), &s->io_memory);
    ioapic_no++;
}

static const VMStateDescription vmstate_ioapic_common = {
    .name = "ioapic",
    .version_id = 3,
    .minimum_version_id = 1,
    .pre_save = ioapic_dispatch_pre_save,
    .post_load = ioapic_dispatch_post_load,
    .fields = (VMStateField[]) {
        VMSTATE_UINT8(id, IOAPICCommonState),
        VMSTATE_UINT8(ioregsel, IOAPICCommonState),
        VMSTATE_UNUSED_V(2, 8), /* to account for qemu-kvm's v2 format */
        VMSTATE_UINT32_V(irr, IOAPICCommonState, 2),
        VMSTATE_UINT64_ARRAY(ioredtbl, IOAPICCommonState, IOAPIC_NUM_PINS),
        VMSTATE_END_OF_LIST()
    }
};

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

    dc->realize = ioapic_common_realize;
    dc->vmsd = &vmstate_ioapic_common;
}

static const TypeInfo ioapic_common_type = {
    .name = TYPE_IOAPIC_COMMON,
    .parent = TYPE_SYS_BUS_DEVICE,
    .instance_size = sizeof(IOAPICCommonState),
    .class_size = sizeof(IOAPICCommonClass),
    .class_init = ioapic_common_class_init,
    .abstract = true,
};

static void ioapic_common_register_types(void)
{
    type_register_static(&ioapic_common_type);
}

type_init(ioapic_common_register_types)
