/*
 * QEMU Random Number Generator Backend
 *
 * Copyright IBM, Corp. 2012
 *
 * Authors:
 *  Anthony Liguori   <aliguori@us.ibm.com>
 *
 * This work is licensed under the terms of the GNU GPL, version 2 or later.
 * See the COPYING file in the top-level directory.
 */

#include "qemu/rng-random.h"
#include "qemu/rng.h"
#include "qapi/qmp/qerror.h"
#include "qemu/main-loop.h"

struct RndRandom
{
    RngBackend parent;

    int fd;
    char *filename;

    EntropyReceiveFunc *receive_func;
    void *opaque;
    size_t size;
};

/**
 * A simple and incomplete backend to request entropy from /dev/random.
 *
 * This backend exposes an additional "filename" property that can be used to
 * set the filename to use to open the backend.
 */

static void entropy_available(void *opaque)
{
    RndRandom *s = RNG_RANDOM(opaque);
    uint8_t buffer[s->size];
    ssize_t len;

    len = read(s->fd, buffer, s->size);
    g_assert(len != -1);

    s->receive_func(s->opaque, buffer, len);
    s->receive_func = NULL;

    qemu_set_fd_handler(s->fd, NULL, NULL, NULL);
}

static void rng_random_request_entropy(RngBackend *b, size_t size,
                                        EntropyReceiveFunc *receive_entropy,
                                        void *opaque)
{
    RndRandom *s = RNG_RANDOM(b);

    if (s->receive_func) {
        s->receive_func(s->opaque, NULL, 0);
    }

    s->receive_func = receive_entropy;
    s->opaque = opaque;
    s->size = size;

    qemu_set_fd_handler(s->fd, entropy_available, NULL, s);
}

static void rng_random_opened(RngBackend *b, Error **errp)
{
    RndRandom *s = RNG_RANDOM(b);

    if (s->filename == NULL) {
        error_set(errp, QERR_INVALID_PARAMETER_VALUE,
                  "filename", "a valid filename");
    } else {
        s->fd = qemu_open(s->filename, O_RDONLY | O_NONBLOCK);

        if (s->fd == -1) {
            error_set(errp, QERR_OPEN_FILE_FAILED, s->filename);
        }
    }
}

static char *rng_random_get_filename(Object *obj, Error **errp)
{
    RndRandom *s = RNG_RANDOM(obj);

    if (s->filename) {
        return g_strdup(s->filename);
    }

    return NULL;
}

static void rng_random_set_filename(Object *obj, const char *filename,
                                 Error **errp)
{
    RngBackend *b = RNG_BACKEND(obj);
    RndRandom *s = RNG_RANDOM(obj);

    if (b->opened) {
        error_set(errp, QERR_PERMISSION_DENIED);
        return;
    }

    if (s->filename) {
        g_free(s->filename);
    }

    s->filename = g_strdup(filename);
}

static void rng_random_init(Object *obj)
{
    RndRandom *s = RNG_RANDOM(obj);

    object_property_add_str(obj, "filename",
                            rng_random_get_filename,
                            rng_random_set_filename,
                            NULL);

    s->filename = g_strdup("/dev/random");
}

static void rng_random_finalize(Object *obj)
{
    RndRandom *s = RNG_RANDOM(obj);

    qemu_set_fd_handler(s->fd, NULL, NULL, NULL);

    if (s->fd != -1) {
        qemu_close(s->fd);
    }

    g_free(s->filename);
}

static void rng_random_class_init(ObjectClass *klass, void *data)
{
    RngBackendClass *rbc = RNG_BACKEND_CLASS(klass);

    rbc->request_entropy = rng_random_request_entropy;
    rbc->opened = rng_random_opened;
}

static const TypeInfo rng_random_info = {
    .name = TYPE_RNG_RANDOM,
    .parent = TYPE_RNG_BACKEND,
    .instance_size = sizeof(RndRandom),
    .class_init = rng_random_class_init,
    .instance_init = rng_random_init,
    .instance_finalize = rng_random_finalize,
};

static void register_types(void)
{
    type_register_static(&rng_random_info);
}

type_init(register_types);
