/*
 * Block protocol for block driver correctness testing
 *
 * Copyright (C) 2010 IBM, Corp.
 *
 * 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/osdep.h"
#include "qapi/error.h"
#include "qemu/sockets.h" /* for EINPROGRESS on Windows */
#include "block/block-io.h"
#include "block/block_int.h"
#include "qobject/qdict.h"
#include "qobject/qstring.h"
#include "qemu/cutils.h"
#include "qemu/module.h"
#include "qemu/option.h"
#include "qemu/memalign.h"

typedef struct {
    BdrvChild *test_file;
} BDRVBlkverifyState;

typedef struct BlkverifyRequest {
    Coroutine *co;
    BlockDriverState *bs;

    /* Request metadata */
    bool is_write;
    uint64_t offset;
    uint64_t bytes;
    int flags;

    int GRAPH_RDLOCK_PTR (*request_fn)(
        BdrvChild *, int64_t, int64_t, QEMUIOVector *, BdrvRequestFlags);

    int ret;                    /* test image result */
    int raw_ret;                /* raw image result */

    unsigned int done;          /* completion counter */

    QEMUIOVector *qiov;         /* user I/O vector */
    QEMUIOVector *raw_qiov;     /* cloned I/O vector for raw file */
} BlkverifyRequest;

static void G_GNUC_PRINTF(2, 3) blkverify_err(BlkverifyRequest *r,
                                             const char *fmt, ...)
{
    va_list ap;

    va_start(ap, fmt);
    fprintf(stderr, "blkverify: %s offset=%" PRId64 " bytes=%" PRId64 " ",
            r->is_write ? "write" : "read", r->offset, r->bytes);
    vfprintf(stderr, fmt, ap);
    fprintf(stderr, "\n");
    va_end(ap);
    exit(1);
}

/* Valid blkverify filenames look like blkverify:path/to/raw_image:path/to/image */
static void blkverify_parse_filename(const char *filename, QDict *options,
                                     Error **errp)
{
    const char *c;
    QString *raw_path;


    /* Parse the blkverify: prefix */
    if (!strstart(filename, "blkverify:", &filename)) {
        /* There was no prefix; therefore, all options have to be already
           present in the QDict (except for the filename) */
        qdict_put_str(options, "x-image", filename);
        return;
    }

    /* Parse the raw image filename */
    c = strchr(filename, ':');
    if (c == NULL) {
        error_setg(errp, "blkverify requires raw copy and original image path");
        return;
    }

    /* TODO Implement option pass-through and set raw.filename here */
    raw_path = qstring_from_substr(filename, 0, c - filename);
    qdict_put(options, "x-raw", raw_path);

    /* TODO Allow multi-level nesting and set file.filename here */
    filename = c + 1;
    qdict_put_str(options, "x-image", filename);
}

static QemuOptsList runtime_opts = {
    .name = "blkverify",
    .head = QTAILQ_HEAD_INITIALIZER(runtime_opts.head),
    .desc = {
        {
            .name = "x-raw",
            .type = QEMU_OPT_STRING,
            .help = "[internal use only, will be removed]",
        },
        {
            .name = "x-image",
            .type = QEMU_OPT_STRING,
            .help = "[internal use only, will be removed]",
        },
        { /* end of list */ }
    },
};

static int blkverify_open(BlockDriverState *bs, QDict *options, int flags,
                          Error **errp)
{
    BDRVBlkverifyState *s = bs->opaque;
    QemuOpts *opts;
    int ret;

    opts = qemu_opts_create(&runtime_opts, NULL, 0, &error_abort);
    if (!qemu_opts_absorb_qdict(opts, options, errp)) {
        ret = -EINVAL;
        goto fail;
    }

    /* Open the raw file */
    ret = bdrv_open_file_child(qemu_opt_get(opts, "x-raw"), options, "raw",
                               bs, errp);
    if (ret < 0) {
        goto fail;
    }

    /* Open the test file */
    s->test_file = bdrv_open_child(qemu_opt_get(opts, "x-image"), options,
                                   "test", bs, &child_of_bds, BDRV_CHILD_DATA,
                                   false, errp);
    if (!s->test_file) {
        ret = -EINVAL;
        goto fail;
    }

    bs->supported_write_flags = BDRV_REQ_WRITE_UNCHANGED;
    bs->supported_zero_flags = BDRV_REQ_WRITE_UNCHANGED;

    ret = 0;
fail:
    qemu_opts_del(opts);
    return ret;
}

static void blkverify_close(BlockDriverState *bs)
{
    BDRVBlkverifyState *s = bs->opaque;

    bdrv_graph_wrlock_drained();
    bdrv_unref_child(bs, s->test_file);
    s->test_file = NULL;
    bdrv_graph_wrunlock();
}

static int64_t coroutine_fn GRAPH_RDLOCK
blkverify_co_getlength(BlockDriverState *bs)
{
    BDRVBlkverifyState *s = bs->opaque;

    return bdrv_co_getlength(s->test_file->bs);
}

static void coroutine_fn blkverify_do_test_req(void *opaque)
{
    BlkverifyRequest *r = opaque;
    BDRVBlkverifyState *s = r->bs->opaque;

    bdrv_graph_co_rdlock();
    r->ret = r->request_fn(s->test_file, r->offset, r->bytes, r->qiov,
                           r->flags);
    bdrv_graph_co_rdunlock();

    r->done++;
    qemu_coroutine_enter_if_inactive(r->co);
}

static void coroutine_fn blkverify_do_raw_req(void *opaque)
{
    BlkverifyRequest *r = opaque;

    bdrv_graph_co_rdlock();
    r->raw_ret = r->request_fn(r->bs->file, r->offset, r->bytes, r->raw_qiov,
                               r->flags);
    bdrv_graph_co_rdunlock();

    r->done++;
    qemu_coroutine_enter_if_inactive(r->co);
}

static int coroutine_fn GRAPH_RDLOCK
blkverify_co_prwv(BlockDriverState *bs, BlkverifyRequest *r, uint64_t offset,
                  uint64_t bytes, QEMUIOVector *qiov, QEMUIOVector *raw_qiov,
                  int flags, bool is_write)
{
    Coroutine *co_a, *co_b;

    *r = (BlkverifyRequest) {
        .co         = qemu_coroutine_self(),
        .bs         = bs,
        .offset     = offset,
        .bytes      = bytes,
        .qiov       = qiov,
        .raw_qiov   = raw_qiov,
        .flags      = flags,
        .is_write   = is_write,
        .request_fn = is_write ? bdrv_co_pwritev : bdrv_co_preadv,
    };

    co_a = qemu_coroutine_create(blkverify_do_test_req, r);
    co_b = qemu_coroutine_create(blkverify_do_raw_req, r);

    qemu_coroutine_enter(co_a);
    qemu_coroutine_enter(co_b);

    while (r->done < 2) {
        qemu_coroutine_yield();
    }

    if (r->ret != r->raw_ret) {
        blkverify_err(r, "return value mismatch %d != %d", r->ret, r->raw_ret);
    }

    return r->ret;
}

static int coroutine_fn GRAPH_RDLOCK
blkverify_co_preadv(BlockDriverState *bs, int64_t offset, int64_t bytes,
                    QEMUIOVector *qiov, BdrvRequestFlags flags)
{
    BlkverifyRequest r;
    QEMUIOVector raw_qiov;
    void *buf;
    ssize_t cmp_offset;
    int ret;

    buf = qemu_blockalign(bs->file->bs, qiov->size);
    qemu_iovec_init(&raw_qiov, qiov->niov);
    qemu_iovec_clone(&raw_qiov, qiov, buf);

    ret = blkverify_co_prwv(bs, &r, offset, bytes, qiov, &raw_qiov,
                            flags & ~BDRV_REQ_REGISTERED_BUF, false);

    cmp_offset = qemu_iovec_compare(qiov, &raw_qiov);
    if (cmp_offset != -1) {
        blkverify_err(&r, "contents mismatch at offset %" PRId64,
                      offset + cmp_offset);
    }

    qemu_iovec_destroy(&raw_qiov);
    qemu_vfree(buf);

    return ret;
}

static int coroutine_fn GRAPH_RDLOCK
blkverify_co_pwritev(BlockDriverState *bs, int64_t offset, int64_t bytes,
                     QEMUIOVector *qiov, BdrvRequestFlags flags)
{
    BlkverifyRequest r;
    return blkverify_co_prwv(bs, &r, offset, bytes, qiov, qiov, flags, true);
}

static int coroutine_fn GRAPH_RDLOCK blkverify_co_flush(BlockDriverState *bs)
{
    BDRVBlkverifyState *s = bs->opaque;

    /* Only flush test file, the raw file is not important */
    return bdrv_co_flush(s->test_file->bs);
}

static bool GRAPH_RDLOCK
blkverify_recurse_can_replace(BlockDriverState *bs,
                              BlockDriverState *to_replace)
{
    BDRVBlkverifyState *s = bs->opaque;

    /*
     * blkverify quits the whole qemu process if there is a mismatch
     * between bs->file->bs and s->test_file->bs.  Therefore, we know
     * know that both must match bs and we can recurse down to either.
     */
    return bdrv_recurse_can_replace(bs->file->bs, to_replace) ||
           bdrv_recurse_can_replace(s->test_file->bs, to_replace);
}

static void GRAPH_RDLOCK blkverify_refresh_filename(BlockDriverState *bs)
{
    BDRVBlkverifyState *s = bs->opaque;

    if (bs->file->bs->exact_filename[0]
        && s->test_file->bs->exact_filename[0])
    {
        int ret = snprintf(bs->exact_filename, sizeof(bs->exact_filename),
                           "blkverify:%s:%s",
                           bs->file->bs->exact_filename,
                           s->test_file->bs->exact_filename);
        if (ret >= sizeof(bs->exact_filename)) {
            /* An overflow makes the filename unusable, so do not report any */
            bs->exact_filename[0] = 0;
        }
    }
}

static char *blkverify_dirname(BlockDriverState *bs, Error **errp)
{
    /* In general, there are two BDSs with different dirnames below this one;
     * so there is no unique dirname we could return (unless both are equal by
     * chance). Therefore, to be consistent, just always return NULL. */
    error_setg(errp, "Cannot generate a base directory for blkverify nodes");
    return NULL;
}

static BlockDriver bdrv_blkverify = {
    .format_name                      = "blkverify",
    .protocol_name                    = "blkverify",
    .instance_size                    = sizeof(BDRVBlkverifyState),

    .bdrv_parse_filename              = blkverify_parse_filename,
    .bdrv_open                        = blkverify_open,
    .bdrv_close                       = blkverify_close,
    .bdrv_child_perm                  = bdrv_default_perms,
    .bdrv_co_getlength                = blkverify_co_getlength,
    .bdrv_refresh_filename            = blkverify_refresh_filename,
    .bdrv_dirname                     = blkverify_dirname,

    .bdrv_co_preadv                   = blkverify_co_preadv,
    .bdrv_co_pwritev                  = blkverify_co_pwritev,
    .bdrv_co_flush                    = blkverify_co_flush,

    .is_filter                        = true,
    .bdrv_recurse_can_replace         = blkverify_recurse_can_replace,
};

static void bdrv_blkverify_init(void)
{
    bdrv_register(&bdrv_blkverify);
}

block_init(bdrv_blkverify_init);
