/*
 * QEMU GRLIB Components
 *
 * Copyright (c) 2010-2011 AdaCore
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in
 * all copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
 * THE SOFTWARE.
 */

#ifndef _GRLIB_H_
#define _GRLIB_H_

#include "qdev.h"
#include "sysbus.h"

/* Emulation of GrLib device is base on the GRLIB IP Core User's Manual:
 * http://www.gaisler.com/products/grlib/grip.pdf
 */

/* IRQMP */

typedef void (*set_pil_in_fn) (void *opaque, uint32_t pil_in);

void grlib_irqmp_set_irq(void *opaque, int irq, int level);

void grlib_irqmp_ack(DeviceState *dev, int intno);

static inline
DeviceState *grlib_irqmp_create(target_phys_addr_t   base,
                                CPUSPARCState            *env,
                                qemu_irq           **cpu_irqs,
                                uint32_t             nr_irqs,
                                set_pil_in_fn        set_pil_in)
{
    DeviceState *dev;

    assert(cpu_irqs != NULL);

    dev = qdev_create(NULL, "grlib,irqmp");
    qdev_prop_set_ptr(dev, "set_pil_in", set_pil_in);
    qdev_prop_set_ptr(dev, "set_pil_in_opaque", env);

    if (qdev_init(dev)) {
        return NULL;
    }

    env->irq_manager = dev;

    sysbus_mmio_map(sysbus_from_qdev(dev), 0, base);

    *cpu_irqs = qemu_allocate_irqs(grlib_irqmp_set_irq,
                                   dev,
                                   nr_irqs);

    return dev;
}

/* GPTimer */

static inline
DeviceState *grlib_gptimer_create(target_phys_addr_t  base,
                                  uint32_t            nr_timers,
                                  uint32_t            freq,
                                  qemu_irq           *cpu_irqs,
                                  int                 base_irq)
{
    DeviceState *dev;
    int i;

    dev = qdev_create(NULL, "grlib,gptimer");
    qdev_prop_set_uint32(dev, "nr-timers", nr_timers);
    qdev_prop_set_uint32(dev, "frequency", freq);
    qdev_prop_set_uint32(dev, "irq-line", base_irq);

    if (qdev_init(dev)) {
        return NULL;
    }

    sysbus_mmio_map(sysbus_from_qdev(dev), 0, base);

    for (i = 0; i < nr_timers; i++) {
        sysbus_connect_irq(sysbus_from_qdev(dev), i, cpu_irqs[base_irq + i]);
    }

    return dev;
}

/* APB UART */

static inline
DeviceState *grlib_apbuart_create(target_phys_addr_t  base,
                                  CharDriverState    *serial,
                                  qemu_irq            irq)
{
    DeviceState *dev;

    dev = qdev_create(NULL, "grlib,apbuart");
    qdev_prop_set_chr(dev, "chrdev", serial);

    if (qdev_init(dev)) {
        return NULL;
    }

    sysbus_mmio_map(sysbus_from_qdev(dev), 0, base);

    sysbus_connect_irq(sysbus_from_qdev(dev), 0, irq);

    return dev;
}

#endif /* ! _GRLIB_H_ */
