示例#1
0
static void qdict_crumple_test_bad_inputs(void)
{
    QDict *src;
    Error *error = NULL;

    src = qdict_new();
    /* rule.0 can't be both a string and a dict */
    qdict_put(src, "rule.0", qstring_from_str("fred"));
    qdict_put(src, "rule.0.policy", qstring_from_str("allow"));

    g_assert(qdict_crumple(src, &error) == NULL);
    g_assert(error != NULL);
    error_free(error);
    error = NULL;
    QDECREF(src);

    src = qdict_new();
    /* rule can't be both a list and a dict */
    qdict_put(src, "rule.0", qstring_from_str("fred"));
    qdict_put(src, "rule.a", qstring_from_str("allow"));

    g_assert(qdict_crumple(src, &error) == NULL);
    g_assert(error != NULL);
    error_free(error);
    error = NULL;
    QDECREF(src);

    src = qdict_new();
    /* The input should be flat, ie no dicts or lists */
    qdict_put(src, "rule.a", qdict_new());
    qdict_put(src, "rule.b", qstring_from_str("allow"));

    g_assert(qdict_crumple(src, &error) == NULL);
    g_assert(error != NULL);
    error_free(error);
    error = NULL;
    QDECREF(src);

    src = qdict_new();
    /* List indexes must not have gaps */
    qdict_put(src, "rule.0", qstring_from_str("deny"));
    qdict_put(src, "rule.3", qstring_from_str("allow"));

    g_assert(qdict_crumple(src, &error) == NULL);
    g_assert(error != NULL);
    error_free(error);
    error = NULL;
    QDECREF(src);

    src = qdict_new();
    /* List indexes must be in %zu format */
    qdict_put(src, "rule.0", qstring_from_str("deny"));
    qdict_put(src, "rule.+1", qstring_from_str("allow"));

    g_assert(qdict_crumple(src, &error) == NULL);
    g_assert(error != NULL);
    error_free(error);
    error = NULL;
    QDECREF(src);
}
示例#2
0
文件: qemu-io.c 项目: Aakriti/qemu
static int openfile(char *name, int flags, int growable, QDict *opts)
{
    Error *local_err = NULL;

    if (qemuio_bs) {
        fprintf(stderr, "file open already, try 'help close'\n");
        return 1;
    }

    if (growable) {
        if (bdrv_file_open(&qemuio_bs, name, NULL, opts, flags, &local_err)) {
            fprintf(stderr, "%s: can't open device %s: %s\n", progname, name,
                    error_get_pretty(local_err));
            error_free(local_err);
            return 1;
        }
    } else {
        qemuio_bs = bdrv_new("hda");

        if (bdrv_open(qemuio_bs, name, opts, flags, NULL, &local_err) < 0) {
            fprintf(stderr, "%s: can't open device %s: %s\n", progname, name,
                    error_get_pretty(local_err));
            error_free(local_err);
            bdrv_unref(qemuio_bs);
            qemuio_bs = NULL;
            return 1;
        }
    }

    return 0;
}
示例#3
0
文件: qemu-sockets.c 项目: m000/panda
static void wait_for_connect(void *opaque)
{
    ConnectState *s = opaque;
    int val = 0, rc = 0;
    socklen_t valsize = sizeof(val);
    bool in_progress;
    Error *err = NULL;

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

    do {
        rc = qemu_getsockopt(s->fd, SOL_SOCKET, SO_ERROR, &val, &valsize);
    } while (rc == -1 && errno == EINTR);

    /* update rc to contain error */
    if (!rc && val) {
        rc = -1;
        errno = val;
    }

    /* connect error */
    if (rc < 0) {
        error_setg_errno(&err, errno, "Error connecting to socket");
        closesocket(s->fd);
        s->fd = rc;
    }

    /* try to connect to the next address on the list */
    if (s->current_addr) {
        while (s->current_addr->ai_next != NULL && s->fd < 0) {
            s->current_addr = s->current_addr->ai_next;
            s->fd = inet_connect_addr(s->current_addr, &in_progress, s, NULL);
            if (s->fd < 0) {
                error_free(err);
                err = NULL;
                error_setg_errno(&err, errno, "Unable to start socket connect");
            }
            /* connect in progress */
            if (in_progress) {
                goto out;
            }
        }

        freeaddrinfo(s->addr_list);
    }

    if (s->callback) {
        s->callback(s->fd, err, s->opaque);
    }
    g_free(s);
out:
    error_free(err);
}
示例#4
0
/* handle requests/control events coming in over the channel */
static void process_event(JSONMessageParser *parser, QList *tokens)
{
    GAState *s = container_of(parser, GAState, parser);
    QObject *obj;
    QDict *qdict;
    Error *err = NULL;
    int ret;

    g_assert(s && parser);

    g_debug("process_event: called");
    obj = json_parser_parse_err(tokens, NULL, &err);
    if (err || !obj || qobject_type(obj) != QTYPE_QDICT) {
        qobject_decref(obj);
        qdict = qdict_new();
        if (!err) {
            g_warning("failed to parse event: unknown error");
            error_set(&err, QERR_JSON_PARSING);
        } else {
            g_warning("failed to parse event: %s", error_get_pretty(err));
        }
        qdict_put_obj(qdict, "error", error_get_qobject(err));
        error_free(err);
    } else {
        qdict = qobject_to_qdict(obj);
    }

    g_assert(qdict);

    /* handle host->guest commands */
    if (qdict_haskey(qdict, "execute")) {
        process_command(s, qdict);
    } else {
        if (!qdict_haskey(qdict, "error")) {
            QDECREF(qdict);
            qdict = qdict_new();
            g_warning("unrecognized payload format");
            error_set(&err, QERR_UNSUPPORTED);
            qdict_put_obj(qdict, "error", error_get_qobject(err));
            error_free(err);
        }
        ret = conn_channel_send_payload(s->conn_channel, QOBJECT(qdict));
        if (ret) {
            g_warning("error sending payload: %s", strerror(ret));
        }
    }

    QDECREF(qdict);
}
示例#5
0
int qmp_marshal_input_query_version(Monitor *mon, const QDict *qdict, QObject **ret)
{
    Error *local_err = NULL;
    Error **errp = &local_err;
    QDict *args = (QDict *)qdict;
    VersionInfo * retval = NULL;
    (void)args;
    if (error_is_set(errp)) {
        goto out;
    }
    retval = qmp_query_version(errp);
    if (!error_is_set(errp)) {
        qmp_marshal_output_query_version(retval, ret, errp);
    }

out:


    if (local_err) {
        qerror_report_err(local_err);
        error_free(local_err);
        return -1;
    }
    return 0;
}
示例#6
0
int qmp_marshal_input_cpu(Monitor *mon, const QDict *qdict, QObject **ret)
{
    Error *local_err = NULL;
    Error **errp = &local_err;
    QDict *args = (QDict *)qdict;
    QmpInputVisitor *mi;
    QapiDeallocVisitor *md;
    Visitor *v;
    int64_t index;

    mi = qmp_input_visitor_new(QOBJECT(args));
    v = qmp_input_get_visitor(mi);
    visit_type_int(v, &index, "index", errp);
    qmp_input_visitor_cleanup(mi);

    if (error_is_set(errp)) {
        goto out;
    }
    qmp_cpu(index, errp);

out:
    md = qapi_dealloc_visitor_new();
    v = qapi_dealloc_get_visitor(md);
    visit_type_int(v, &index, "index", errp);
    qapi_dealloc_visitor_cleanup(md);

    if (local_err) {
        qerror_report_err(local_err);
        error_free(local_err);
        return -1;
    }
    return 0;
}
示例#7
0
static void realize(DeviceState *d, Error **errp)
{
    sPAPRDRConnector *drc = SPAPR_DR_CONNECTOR(d);
    sPAPRDRConnectorClass *drck = SPAPR_DR_CONNECTOR_GET_CLASS(drc);
    Object *root_container;
    char link_name[256];
    gchar *child_name;
    Error *err = NULL;

    DPRINTFN("drc realize: %x", drck->get_index(drc));
    /* NOTE: we do this as part of realize/unrealize due to the fact
     * that the guest will communicate with the DRC via RTAS calls
     * referencing the global DRC index. By unlinking the DRC
     * from DRC_CONTAINER_PATH/<drc_index> we effectively make it
     * inaccessible by the guest, since lookups rely on this path
     * existing in the composition tree
     */
    root_container = container_get(object_get_root(), DRC_CONTAINER_PATH);
    snprintf(link_name, sizeof(link_name), "%x", drck->get_index(drc));
    child_name = object_get_canonical_path_component(OBJECT(drc));
    DPRINTFN("drc child name: %s", child_name);
    object_property_add_alias(root_container, link_name,
                              drc->owner, child_name, &err);
    if (err) {
        error_report("%s", error_get_pretty(err));
        error_free(err);
        object_unref(OBJECT(drc));
    }
    g_free(child_name);
    DPRINTFN("drc realize complete");
}
示例#8
0
文件: spapr_irq.c 项目: aik/qemu
static void spapr_irq_init_xics(sPAPRMachineState *spapr, Error **errp)
{
    MachineState *machine = MACHINE(spapr);
    sPAPRMachineClass *smc = SPAPR_MACHINE_GET_CLASS(spapr);
    int nr_irqs = smc->irq->nr_irqs;
    Error *local_err = NULL;

    if (kvm_enabled()) {
        if (machine_kernel_irqchip_allowed(machine) &&
            !xics_kvm_init(spapr, &local_err)) {
            spapr->icp_type = TYPE_KVM_ICP;
            spapr->ics = spapr_ics_create(spapr, TYPE_ICS_KVM, nr_irqs,
                                          &local_err);
        }
        if (machine_kernel_irqchip_required(machine) && !spapr->ics) {
            error_prepend(&local_err,
                          "kernel_irqchip requested but unavailable: ");
            goto error;
        }
        error_free(local_err);
        local_err = NULL;
    }

    if (!spapr->ics) {
        xics_spapr_init(spapr);
        spapr->icp_type = TYPE_ICP;
        spapr->ics = spapr_ics_create(spapr, TYPE_ICS_SIMPLE, nr_irqs,
                                      &local_err);
    }

error:
    error_propagate(errp, local_err);
}
示例#9
0
文件: hmp.c 项目: JonahAragon/qemu
static void hmp_handle_error(Monitor *mon, Error **errp)
{
    if (error_is_set(errp)) {
        monitor_printf(mon, "%s\n", error_get_pretty(*errp));
        error_free(*errp);
    }
}
示例#10
0
static void vncws_send_handshake_response(VncState *vs, const char* key)
{
    char combined_key[WS_CLIENT_KEY_LEN + WS_GUID_LEN + 1];
    char *accept = NULL, *response = NULL;
    Error *err = NULL;

    g_strlcpy(combined_key, key, WS_CLIENT_KEY_LEN + 1);
    g_strlcat(combined_key, WS_GUID, WS_CLIENT_KEY_LEN + WS_GUID_LEN + 1);

    /* hash and encode it */
    if (qcrypto_hash_base64(QCRYPTO_HASH_ALG_SHA1,
                            combined_key,
                            WS_CLIENT_KEY_LEN + WS_GUID_LEN,
                            &accept,
                            &err) < 0) {
        VNC_DEBUG("Hashing Websocket combined key failed %s\n",
                  error_get_pretty(err));
        error_free(err);
        vnc_client_error(vs);
        return;
    }

    response = g_strdup_printf(WS_HANDSHAKE, accept);
    vnc_client_write_buf(vs, (const uint8_t *)response, strlen(response));

    g_free(accept);
    g_free(response);

    vs->encode_ws = 1;
    vnc_init_state(vs);
}
示例#11
0
/* test generated deallocation on an object whose construction was prematurely
 * terminated due to an error */
static void test_dealloc_partial(void)
{
    static const char text[] = "don't leak me";

    UserDefTwo *ud2 = NULL;
    Error *err = NULL;

    /* create partial object */
    {
        QDict *ud2_dict;
        QmpInputVisitor *qiv;

        ud2_dict = qdict_new();
        qdict_put_obj(ud2_dict, "string0", QOBJECT(qstring_from_str(text)));

        qiv = qmp_input_visitor_new(QOBJECT(ud2_dict));
        visit_type_UserDefTwo(qmp_input_get_visitor(qiv), &ud2, NULL, &err);
        qmp_input_visitor_cleanup(qiv);
        QDECREF(ud2_dict);
    }

    /* verify partial success */
    assert(ud2 != NULL);
    assert(ud2->string0 != NULL);
    assert(strcmp(ud2->string0, text) == 0);
    assert(ud2->dict1 == NULL);

    /* confirm & release construction error */
    assert(err != NULL);
    error_free(err);

    /* tear down partial object */
    qapi_free_UserDefTwo(ud2);
}
示例#12
0
static gboolean qio_channel_websock_handshake_send(QIOChannel *ioc,
                                                   GIOCondition condition,
                                                   gpointer user_data)
{
    QIOTask *task = user_data;
    QIOChannelWebsock *wioc = QIO_CHANNEL_WEBSOCK(
        qio_task_get_source(task));
    Error *err = NULL;
    ssize_t ret;

    ret = qio_channel_write(wioc->master,
                            (char *)wioc->encoutput.buffer,
                            wioc->encoutput.offset,
                            &err);

    if (ret < 0) {
        trace_qio_channel_websock_handshake_fail(ioc);
        qio_task_abort(task, err);
        error_free(err);
        return FALSE;
    }

    buffer_advance(&wioc->encoutput, ret);
    if (wioc->encoutput.offset == 0) {
        trace_qio_channel_websock_handshake_complete(ioc);
        qio_task_complete(task);
        return FALSE;
    }
    trace_qio_channel_websock_handshake_pending(ioc, G_IO_OUT);
    return TRUE;
}
示例#13
0
static int pci_device_hot_remove(Monitor *mon, const char *pci_addr)
{
    PCIDevice *d;
    int dom, bus;
    unsigned slot;
    Error *local_err = NULL;

    if (pci_read_devaddr(mon, pci_addr, &dom, &bus, &slot)) {
        return -1;
    }

    d = pci_find_device(pci_find_root_bus(dom), bus, PCI_DEVFN(slot, 0));
    if (!d) {
        monitor_printf(mon, "slot %d empty\n", slot);
        return -1;
    }

    qdev_unplug(&d->qdev, &local_err);
    if (error_is_set(&local_err)) {
        monitor_printf(mon, "%s\n", error_get_pretty(local_err));
        error_free(local_err);
        return -1;
    }

    return 0;
}
示例#14
0
/* Disable dataplane thread during live migration since it does not
 * update the dirty memory bitmap yet.
 */
static void virtio_blk_migration_state_changed(Notifier *notifier, void *data)
{
    VirtIOBlock *s = container_of(notifier, VirtIOBlock,
                                  migration_state_notifier);
    MigrationState *mig = data;
    Error *err = NULL;

    if (migration_in_setup(mig)) {
        if (!s->dataplane) {
            return;
        }
        virtio_blk_data_plane_destroy(s->dataplane);
        s->dataplane = NULL;
    } else if (migration_has_finished(mig) ||
               migration_has_failed(mig)) {
        if (s->dataplane) {
            return;
        }
        bdrv_drain_all(); /* complete in-flight non-dataplane requests */
        virtio_blk_data_plane_create(VIRTIO_DEVICE(s), &s->blk,
                                     &s->dataplane, &err);
        if (err != NULL) {
            error_report("%s", error_get_pretty(err));
            error_free(err);
        }
    }
}
示例#15
0
void vncws_tls_handshake_io(void *opaque)
{
    VncState *vs = (VncState *)opaque;
    Error *err = NULL;

    vs->tls = qcrypto_tls_session_new(vs->vd->tlscreds,
                                      NULL,
                                      vs->vd->tlsaclname,
                                      QCRYPTO_TLS_CREDS_ENDPOINT_SERVER,
                                      &err);
    if (!vs->tls) {
        VNC_DEBUG("Failed to setup TLS %s\n",
                  error_get_pretty(err));
        error_free(err);
        vnc_client_error(vs);
        return;
    }

    qcrypto_tls_session_set_callbacks(vs->tls,
                                      vnc_tls_push,
                                      vnc_tls_pull,
                                      vs);

    VNC_DEBUG("Start TLS WS handshake process\n");
    vncws_start_tls_handshake(vs);
}
示例#16
0
static gboolean qio_channel_websock_handshake_io(QIOChannel *ioc,
                                                 GIOCondition condition,
                                                 gpointer user_data)
{
    QIOTask *task = user_data;
    QIOChannelWebsock *wioc = QIO_CHANNEL_WEBSOCK(
        qio_task_get_source(task));
    Error *err = NULL;
    int ret;

    ret = qio_channel_websock_handshake_read(wioc, &err);
    if (ret < 0) {
        trace_qio_channel_websock_handshake_fail(ioc);
        qio_task_abort(task, err);
        error_free(err);
        return FALSE;
    }
    if (ret == 0) {
        trace_qio_channel_websock_handshake_pending(ioc, G_IO_IN);
        /* need more data still */
        return TRUE;
    }

    object_ref(OBJECT(task));
    trace_qio_channel_websock_handshake_reply(ioc);
    qio_channel_add_watch(
        wioc->master,
        G_IO_OUT,
        qio_channel_websock_handshake_send,
        task,
        (GDestroyNotify)object_unref);
    return FALSE;
}
示例#17
0
文件: error.c 项目: Perelandric/ponyc
void errorframe_discard(errorframe_t* frame)
{
  pony_assert(frame != NULL);

  error_free(*frame);
  *frame = NULL;
}
示例#18
0
static int pci_device_hot_remove(Monitor *mon, const char *pci_addr)
{
    PCIBus *root = pci_find_primary_bus();
    PCIDevice *d;
    int bus;
    unsigned slot;
    Error *local_err = NULL;

    if (!root) {
        monitor_printf(mon, "no primary PCI bus (if there are multiple"
                       " PCI roots, you must use device_del instead)");
        return -1;
    }

    if (pci_read_devaddr(mon, pci_addr, &bus, &slot)) {
        return -1;
    }

    d = pci_find_device(root, bus, PCI_DEVFN(slot, 0));
    if (!d) {
        monitor_printf(mon, "slot %d empty\n", slot);
        return -1;
    }

    qdev_unplug(&d->qdev, &local_err);
    if (error_is_set(&local_err)) {
        monitor_printf(mon, "%s\n", error_get_pretty(local_err));
        error_free(local_err);
        return -1;
    }

    return 0;
}
示例#19
0
/**
 * Create a socket and connect it to an address.
 *
 * @saddr: Inet socket address specification
 * @errp: set on error
 *
 * Returns: -1 on error, file descriptor on success.
 */
int inet_connect_saddr(InetSocketAddress *saddr, Error **errp)
{
    Error *local_err = NULL;
    struct addrinfo *res, *e;
    int sock = -1;

    res = inet_parse_connect_saddr(saddr, errp);
    if (!res) {
        return -1;
    }

    for (e = res; e != NULL; e = e->ai_next) {
        error_free(local_err);
        local_err = NULL;
        sock = inet_connect_addr(e, &local_err);
        if (sock >= 0) {
            break;
        }
    }

    if (sock < 0) {
        error_propagate(errp, local_err);
    }

    freeaddrinfo(res);
    return sock;
}
示例#20
0
static int raw_open_common(BlockDriverState *bs, QDict *options,
                           int bdrv_flags, int open_flags)
{
    BDRVRawState *s = bs->opaque;
    QemuOpts *opts;
    Error *local_err = NULL;
    const char *filename;
    int fd, ret;

    opts = qemu_opts_create_nofail(&raw_runtime_opts);
    qemu_opts_absorb_qdict(opts, options, &local_err);
    if (error_is_set(&local_err)) {
        qerror_report_err(local_err);
        error_free(local_err);
        ret = -EINVAL;
        goto fail;
    }

    filename = qemu_opt_get(opts, "filename");

    ret = raw_normalize_devicepath(&filename);
    if (ret != 0) {
        goto fail;
    }

    s->open_flags = open_flags;
    raw_parse_flags(bdrv_flags, &s->open_flags);

    s->fd = -1;
    fd = qemu_open(filename, s->open_flags, 0644);
    if (fd < 0) {
        ret = -errno;
        if (ret == -EROFS) {
            ret = -EACCES;
        }
        goto fail;
    }
    s->fd = fd;

#ifdef CONFIG_LINUX_AIO
    if (raw_set_aio(&s->aio_ctx, &s->use_aio, bdrv_flags)) {
        qemu_close(fd);
        ret = -errno;
        goto fail;
    }
#endif

    s->has_discard = 1;
#ifdef CONFIG_XFS
    if (platform_test_xfs_fd(s->fd)) {
        s->is_xfs = 1;
    }
#endif

    ret = 0;
fail:
    qemu_opts_del(opts);
    return ret;
}
示例#21
0
void error_propagate(Error **dst_err, Error *local_err)
{
    if (dst_err && !*dst_err) {
        *dst_err = local_err;
    } else if (local_err) {
        error_free(local_err);
    }
}
示例#22
0
文件: error.c 项目: JeremyAgost/qemu
void error_report_err(Error *err)
{
    error_report("%s", error_get_pretty(err));
    if (err->hint) {
        error_printf_unless_qmp("%s", err->hint->str);
    }
    error_free(err);
}
示例#23
0
static void data_plane_remove_op_blockers(VirtIOBlockDataPlane *s)
{
    if (s->blocker) {
        blk_op_unblock_all(s->conf->conf.blk, s->blocker);
        error_free(s->blocker);
        s->blocker = NULL;
    }
}
示例#24
0
文件: ssh.c 项目: 01org/KVMGT-qemu
static int ssh_create(const char *filename, QEMUOptionParameter *options)
{
    int r, ret;
    Error *local_err = NULL;
    int64_t total_size = 0;
    QDict *uri_options = NULL;
    BDRVSSHState s;
    ssize_t r2;
    char c[1] = { '\0' };

    ssh_state_init(&s);

    /* Get desired file size. */
    while (options && options->name) {
        if (!strcmp(options->name, BLOCK_OPT_SIZE)) {
            total_size = options->value.n;
        }
        options++;
    }
    DPRINTF("total_size=%" PRIi64, total_size);

    uri_options = qdict_new();
    r = parse_uri(filename, uri_options, &local_err);
    if (r < 0) {
        qerror_report_err(local_err);
        error_free(local_err);
        ret = r;
        goto out;
    }

    r = connect_to_ssh(&s, uri_options,
                       LIBSSH2_FXF_READ|LIBSSH2_FXF_WRITE|
                       LIBSSH2_FXF_CREAT|LIBSSH2_FXF_TRUNC, 0644);
    if (r < 0) {
        ret = r;
        goto out;
    }

    if (total_size > 0) {
        libssh2_sftp_seek64(s.sftp_handle, total_size-1);
        r2 = libssh2_sftp_write(s.sftp_handle, c, 1);
        if (r2 < 0) {
            sftp_error_report(&s, "truncate failed");
            ret = -EINVAL;
            goto out;
        }
        s.attrs.filesize = total_size;
    }

    ret = 0;

 out:
    ssh_state_free(&s);
    if (uri_options != NULL) {
        QDECREF(uri_options);
    }
    return ret;
}
示例#25
0
文件: main.c 项目: JunaidLoonat/qemu
/* handle requests/control events coming in over the channel */
static void process_event(JSONMessageParser *parser, GQueue *tokens)
{
    GAState *s = container_of(parser, GAState, parser);
    QDict *qdict;
    Error *err = NULL;
    int ret;

    g_assert(s && parser);

    g_debug("process_event: called");
    qdict = qobject_to_qdict(json_parser_parse_err(tokens, NULL, &err));
    if (err || !qdict) {
        QDECREF(qdict);
        qdict = qdict_new();
        if (!err) {
            g_warning("failed to parse event: unknown error");
            error_setg(&err, QERR_JSON_PARSING);
        } else {
            g_warning("failed to parse event: %s", error_get_pretty(err));
        }
        qdict_put_obj(qdict, "error", qmp_build_error_object(err));
        error_free(err);
    }

    /* handle host->guest commands */
    if (qdict_haskey(qdict, "execute")) {
        process_command(s, qdict);
    } else {
        if (!qdict_haskey(qdict, "error")) {
            QDECREF(qdict);
            qdict = qdict_new();
            g_warning("unrecognized payload format");
            error_setg(&err, QERR_UNSUPPORTED);
            qdict_put_obj(qdict, "error", qmp_build_error_object(err));
            error_free(err);
        }
        ret = send_response(s, QOBJECT(qdict));
        if (ret < 0) {
            g_warning("error sending error response: %s", strerror(-ret));
        }
    }

    QDECREF(qdict);
}
示例#26
0
文件: common.c 项目: AmesianX/panda
ssize_t nbd_wr_syncv(QIOChannel *ioc,
                     struct iovec *iov,
                     size_t niov,
                     size_t length,
                     bool do_read)
{
    ssize_t done = 0;
    Error *local_err = NULL;
    struct iovec *local_iov = g_new(struct iovec, niov);
    struct iovec *local_iov_head = local_iov;
    unsigned int nlocal_iov = niov;

    nlocal_iov = iov_copy(local_iov, nlocal_iov, iov, niov, 0, length);

    while (nlocal_iov > 0) {
        ssize_t len;
        if (do_read) {
            len = qio_channel_readv(ioc, local_iov, nlocal_iov, &local_err);
        } else {
            len = qio_channel_writev(ioc, local_iov, nlocal_iov, &local_err);
        }
        if (len == QIO_CHANNEL_ERR_BLOCK) {
            if (qemu_in_coroutine()) {
                /* XXX figure out if we can create a variant on
                 * qio_channel_yield() that works with AIO contexts
                 * and consider using that in this branch */
                qemu_coroutine_yield();
            } else if (done) {
                /* XXX this is needed by nbd_reply_ready.  */
                qio_channel_wait(ioc,
                                 do_read ? G_IO_IN : G_IO_OUT);
            } else {
                return -EAGAIN;
            }
            continue;
        }
        if (len < 0) {
            TRACE("I/O error: %s", error_get_pretty(local_err));
            error_free(local_err);
            /* XXX handle Error objects */
            done = -EIO;
            goto cleanup;
        }

        if (do_read && len == 0) {
            break;
        }

        iov_discard_front(&local_iov, &nlocal_iov, len);
        done += len;
    }

 cleanup:
    g_free(local_iov_head);
    return done;
}
示例#27
0
文件: vhdx.c 项目: binghamton/qemu
static void vhdx_close(BlockDriverState *bs)
{
    BDRVVHDXState *s = bs->opaque;
    qemu_vfree(s->headers[0]);
    qemu_vfree(s->headers[1]);
    qemu_vfree(s->bat);
    qemu_vfree(s->parent_entries);
    migrate_del_blocker(s->migration_blocker);
    error_free(s->migration_blocker);
}
示例#28
0
void block_job_release(BlockDriverState *bs)
{
    BlockJob *job = bs->job;

    bs->job = NULL;
    bdrv_op_unblock_all(bs, job->blocker);
    error_free(job->blocker);
    g_free(job->id);
    g_free(job);
}
示例#29
0
QDict *qmp_error_response(Error *err)
{
    QDict *rsp;

    rsp = qdict_from_jsonf_nofail("{ 'error': { 'class': %s, 'desc': %s } }",
                                  QapiErrorClass_str(error_get_class(err)),
                                  error_get_pretty(err));
    error_free(err);
    return rsp;
}
示例#30
0
int whpx_init_vcpu(CPUState *cpu)
{
    HRESULT hr;
    struct whpx_state *whpx = &whpx_global;
    struct whpx_vcpu *vcpu;
    Error *local_error = NULL;

    /* Add migration blockers for all unsupported features of the
     * Windows Hypervisor Platform
     */
    if (whpx_migration_blocker == NULL) {
        error_setg(&whpx_migration_blocker,
               "State blocked due to non-migratable CPUID feature support,"
               "dirty memory tracking support, and XSAVE/XRSTOR support");

        (void)migrate_add_blocker(whpx_migration_blocker, &local_error);
        if (local_error) {
            error_report_err(local_error);
            error_free(whpx_migration_blocker);
            migrate_del_blocker(whpx_migration_blocker);
            return -EINVAL;
        }
    }

    vcpu = g_malloc0(sizeof(struct whpx_vcpu));

    if (!vcpu) {
        error_report("WHPX: Failed to allocte VCPU context.");
        return -ENOMEM;
    }

    hr = WHvEmulatorCreateEmulator(&whpx_emu_callbacks, &vcpu->emulator);
    if (FAILED(hr)) {
        error_report("WHPX: Failed to setup instruction completion support,"
                     " hr=%08lx", hr);
        g_free(vcpu);
        return -EINVAL;
    }

    hr = WHvCreateVirtualProcessor(whpx->partition, cpu->cpu_index, 0);
    if (FAILED(hr)) {
        error_report("WHPX: Failed to create a virtual processor,"
                     " hr=%08lx", hr);
        WHvEmulatorDestroyEmulator(vcpu->emulator);
        g_free(vcpu);
        return -EINVAL;
    }

    vcpu->interruptable = true;

    cpu->vcpu_dirty = true;
    cpu->hax_vcpu = (struct hax_vcpu_state *)vcpu;

    return 0;
}