/*
 * QEMU PowerPC E500 embedded processors pci controller emulation
 *
 * Copyright (C) 2009 Freescale Semiconductor, Inc. All rights reserved.
 *
 * Author: Yu Liu,     <yu.liu@freescale.com>
 *
 * This file is derived from hw/ppc4xx_pci.c,
 * the copyright for that material belongs to the original owners.
 *
 * This 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.
 */

#include "hw.h"
#include "ppc.h"
#include "ppce500.h"
typedef target_phys_addr_t pci_addr_t;
#include "pci.h"
#include "pci_host.h"
#include "bswap.h"
#include "qemu-log.h"

#ifdef DEBUG_PCI
#define pci_debug(fmt, ...) fprintf(stderr, fmt, ## __VA_ARGS__)
#else
#define pci_debug(fmt, ...)
#endif

#define PCIE500_CFGADDR       0x0
#define PCIE500_CFGDATA       0x4
#define PCIE500_REG_BASE      0xC00
#define PCIE500_REG_SIZE      (0x1000 - PCIE500_REG_BASE)

#define PPCE500_PCI_CONFIG_ADDR         0x0
#define PPCE500_PCI_CONFIG_DATA         0x4
#define PPCE500_PCI_INTACK              0x8

#define PPCE500_PCI_OW1                 (0xC20 - PCIE500_REG_BASE)
#define PPCE500_PCI_OW2                 (0xC40 - PCIE500_REG_BASE)
#define PPCE500_PCI_OW3                 (0xC60 - PCIE500_REG_BASE)
#define PPCE500_PCI_OW4                 (0xC80 - PCIE500_REG_BASE)
#define PPCE500_PCI_IW3                 (0xDA0 - PCIE500_REG_BASE)
#define PPCE500_PCI_IW2                 (0xDC0 - PCIE500_REG_BASE)
#define PPCE500_PCI_IW1                 (0xDE0 - PCIE500_REG_BASE)

#define PPCE500_PCI_GASKET_TIMR         (0xE20 - PCIE500_REG_BASE)

#define PCI_POTAR               0x0
#define PCI_POTEAR              0x4
#define PCI_POWBAR              0x8
#define PCI_POWAR               0x10

#define PCI_PITAR               0x0
#define PCI_PIWBAR              0x8
#define PCI_PIWBEAR             0xC
#define PCI_PIWAR               0x10

#define PPCE500_PCI_NR_POBS     5
#define PPCE500_PCI_NR_PIBS     3

struct  pci_outbound {
    uint32_t potar;
    uint32_t potear;
    uint32_t powbar;
    uint32_t powar;
};

struct pci_inbound {
    uint32_t pitar;
    uint32_t piwbar;
    uint32_t piwbear;
    uint32_t piwar;
};

struct PPCE500PCIState {
    struct pci_outbound pob[PPCE500_PCI_NR_POBS];
    struct pci_inbound pib[PPCE500_PCI_NR_PIBS];
    uint32_t gasket_time;
    PCIHostState pci_state;
    PCIDevice *pci_dev;
};

typedef struct PPCE500PCIState PPCE500PCIState;

static uint32_t pcie500_cfgaddr_readl(void *opaque, target_phys_addr_t addr)
{
    PPCE500PCIState *pci = opaque;

    pci_debug("%s: (addr:" TARGET_FMT_plx ") -> value:%x\n", __func__, addr,
              pci->pci_state.config_reg);
    return pci->pci_state.config_reg;
}

static CPUReadMemoryFunc *pcie500_cfgaddr_read[] = {
    &pcie500_cfgaddr_readl,
    &pcie500_cfgaddr_readl,
    &pcie500_cfgaddr_readl,
};

static void pcie500_cfgaddr_writel(void *opaque, target_phys_addr_t addr,
                                  uint32_t value)
{
    PPCE500PCIState *controller = opaque;

    pci_debug("%s: value:%x -> (addr:" TARGET_FMT_plx ")\n", __func__, value,
              addr);
    controller->pci_state.config_reg = value & ~0x3;
}

static CPUWriteMemoryFunc *pcie500_cfgaddr_write[] = {
    &pcie500_cfgaddr_writel,
    &pcie500_cfgaddr_writel,
    &pcie500_cfgaddr_writel,
};

static CPUReadMemoryFunc *pcie500_cfgdata_read[] = {
    &pci_host_data_readb,
    &pci_host_data_readw,
    &pci_host_data_readl,
};

static CPUWriteMemoryFunc *pcie500_cfgdata_write[] = {
    &pci_host_data_writeb,
    &pci_host_data_writew,
    &pci_host_data_writel,
};

static uint32_t pci_reg_read4(void *opaque, target_phys_addr_t addr)
{
    PPCE500PCIState *pci = opaque;
    unsigned long win;
    uint32_t value = 0;

    win = addr & 0xfe0;

    switch (win) {
    case PPCE500_PCI_OW1:
    case PPCE500_PCI_OW2:
    case PPCE500_PCI_OW3:
    case PPCE500_PCI_OW4:
        switch (addr & 0xC) {
        case PCI_POTAR: value = pci->pob[(addr >> 5) & 0x7].potar; break;
        case PCI_POTEAR: value = pci->pob[(addr >> 5) & 0x7].potear; break;
        case PCI_POWBAR: value = pci->pob[(addr >> 5) & 0x7].powbar; break;
        case PCI_POWAR: value = pci->pob[(addr >> 5) & 0x7].powar; break;
        default: break;
        }
        break;

    case PPCE500_PCI_IW3:
    case PPCE500_PCI_IW2:
    case PPCE500_PCI_IW1:
        switch (addr & 0xC) {
        case PCI_PITAR: value = pci->pib[(addr >> 5) & 0x3].pitar; break;
        case PCI_PIWBAR: value = pci->pib[(addr >> 5) & 0x3].piwbar; break;
        case PCI_PIWBEAR: value = pci->pib[(addr >> 5) & 0x3].piwbear; break;
        case PCI_PIWAR: value = pci->pib[(addr >> 5) & 0x3].piwar; break;
        default: break;
        };
        break;

    case PPCE500_PCI_GASKET_TIMR:
        value = pci->gasket_time;
        break;

    default:
        break;
    }

    pci_debug("%s: win:%lx(addr:" TARGET_FMT_plx ") -> value:%x\n", __func__,
              win, addr, value);
    return value;
}

static CPUReadMemoryFunc *e500_pci_reg_read[] = {
    &pci_reg_read4,
    &pci_reg_read4,
    &pci_reg_read4,
};

static void pci_reg_write4(void *opaque, target_phys_addr_t addr,
                               uint32_t value)
{
    PPCE500PCIState *pci = opaque;
    unsigned long win;

    win = addr & 0xfe0;

    pci_debug("%s: value:%x -> win:%lx(addr:" TARGET_FMT_plx ")\n",
              __func__, value, win, addr);

    switch (win) {
    case PPCE500_PCI_OW1:
    case PPCE500_PCI_OW2:
    case PPCE500_PCI_OW3:
    case PPCE500_PCI_OW4:
        switch (addr & 0xC) {
        case PCI_POTAR: pci->pob[(addr >> 5) & 0x7].potar = value; break;
        case PCI_POTEAR: pci->pob[(addr >> 5) & 0x7].potear = value; break;
        case PCI_POWBAR: pci->pob[(addr >> 5) & 0x7].powbar = value; break;
        case PCI_POWAR: pci->pob[(addr >> 5) & 0x7].powar = value; break;
        default: break;
        };
        break;

    case PPCE500_PCI_IW3:
    case PPCE500_PCI_IW2:
    case PPCE500_PCI_IW1:
        switch (addr & 0xC) {
        case PCI_PITAR: pci->pib[(addr >> 5) & 0x3].pitar = value; break;
        case PCI_PIWBAR: pci->pib[(addr >> 5) & 0x3].piwbar = value; break;
        case PCI_PIWBEAR: pci->pib[(addr >> 5) & 0x3].piwbear = value; break;
        case PCI_PIWAR: pci->pib[(addr >> 5) & 0x3].piwar = value; break;
        default: break;
        };
        break;

    case PPCE500_PCI_GASKET_TIMR:
        pci->gasket_time = value;
        break;

    default:
        break;
    };
}

static CPUWriteMemoryFunc *e500_pci_reg_write[] = {
    &pci_reg_write4,
    &pci_reg_write4,
    &pci_reg_write4,
};

static int mpc85xx_pci_map_irq(PCIDevice *pci_dev, int irq_num)
{
    int devno = pci_dev->devfn >> 3, ret = 0;

    switch (devno) {
        /* Two PCI slot */
        case 0x11:
        case 0x12:
            ret = (irq_num + devno - 0x10) % 4;
            break;
        default:
            printf("Error:%s:unknow dev number\n", __func__);
    }

    pci_debug("%s: devfn %x irq %d -> %d  devno:%x\n", __func__,
           pci_dev->devfn, irq_num, ret, devno);

    return ret;
}

static void mpc85xx_pci_set_irq(qemu_irq *pic, int irq_num, int level)
{
    pci_debug("%s: PCI irq %d, level:%d\n", __func__, irq_num, level);

    qemu_set_irq(pic[irq_num], level);
}

static void ppce500_pci_save(QEMUFile *f, void *opaque)
{
    PPCE500PCIState *controller = opaque;
    int i;

    pci_device_save(controller->pci_dev, f);

    for (i = 0; i < PPCE500_PCI_NR_POBS; i++) {
        qemu_put_be32s(f, &controller->pob[i].potar);
        qemu_put_be32s(f, &controller->pob[i].potear);
        qemu_put_be32s(f, &controller->pob[i].powbar);
        qemu_put_be32s(f, &controller->pob[i].powar);
    }

    for (i = 0; i < PPCE500_PCI_NR_PIBS; i++) {
        qemu_put_be32s(f, &controller->pib[i].pitar);
        qemu_put_be32s(f, &controller->pib[i].piwbar);
        qemu_put_be32s(f, &controller->pib[i].piwbear);
        qemu_put_be32s(f, &controller->pib[i].piwar);
    }
    qemu_put_be32s(f, &controller->gasket_time);
}

static int ppce500_pci_load(QEMUFile *f, void *opaque, int version_id)
{
    PPCE500PCIState *controller = opaque;
    int i;

    if (version_id != 1)
        return -EINVAL;

    pci_device_load(controller->pci_dev, f);

    for (i = 0; i < PPCE500_PCI_NR_POBS; i++) {
        qemu_get_be32s(f, &controller->pob[i].potar);
        qemu_get_be32s(f, &controller->pob[i].potear);
        qemu_get_be32s(f, &controller->pob[i].powbar);
        qemu_get_be32s(f, &controller->pob[i].powar);
    }

    for (i = 0; i < PPCE500_PCI_NR_PIBS; i++) {
        qemu_get_be32s(f, &controller->pib[i].pitar);
        qemu_get_be32s(f, &controller->pib[i].piwbar);
        qemu_get_be32s(f, &controller->pib[i].piwbear);
        qemu_get_be32s(f, &controller->pib[i].piwar);
    }
    qemu_get_be32s(f, &controller->gasket_time);

    return 0;
}

PCIBus *ppce500_pci_init(qemu_irq pci_irqs[4], target_phys_addr_t registers)
{
    PPCE500PCIState *controller;
    PCIDevice *d;
    int index;
    static int ppce500_pci_id;

    controller = qemu_mallocz(sizeof(PPCE500PCIState));

    controller->pci_state.bus = pci_register_bus(NULL, "pci",
                                                 mpc85xx_pci_set_irq,
                                                 mpc85xx_pci_map_irq,
                                                 pci_irqs, 0x88, 4);
    d = pci_register_device(controller->pci_state.bus,
                            "host bridge", sizeof(PCIDevice),
                            0, NULL, NULL);

    pci_config_set_vendor_id(d->config, PCI_VENDOR_ID_FREESCALE);
    pci_config_set_device_id(d->config, PCI_DEVICE_ID_MPC8533E);
    pci_config_set_class(d->config, PCI_CLASS_PROCESSOR_POWERPC);

    controller->pci_dev = d;

    /* CFGADDR */
    index = cpu_register_io_memory(pcie500_cfgaddr_read,
                                   pcie500_cfgaddr_write, controller);
    if (index < 0)
        goto free;
    cpu_register_physical_memory(registers + PCIE500_CFGADDR, 4, index);

    /* CFGDATA */
    index = cpu_register_io_memory(pcie500_cfgdata_read,
                                   pcie500_cfgdata_write,
                                   &controller->pci_state);
    if (index < 0)
        goto free;
    cpu_register_physical_memory(registers + PCIE500_CFGDATA, 4, index);

    index = cpu_register_io_memory(e500_pci_reg_read,
                                   e500_pci_reg_write, controller);
    if (index < 0)
        goto free;
    cpu_register_physical_memory(registers + PCIE500_REG_BASE,
                                   PCIE500_REG_SIZE, index);

    /* XXX load/save code not tested. */
    register_savevm("ppce500_pci", ppce500_pci_id++, 1,
                    ppce500_pci_save, ppce500_pci_load, controller);

    return controller->pci_state.bus;

free:
    printf("%s error\n", __func__);
    qemu_free(controller);
    return NULL;
}
