[libvirt] [PATCH 0/4] vbox: address thread-safety issues.

Dawid Zamirski dzamirski at datto.com
Thu Sep 29 17:36:44 UTC 2016


On Wed, 2016-09-28 at 13:41 -0400, Dawid Zamirski wrote:
> This patch series solves (at least in my testing) vbox driver
> thread-safety issues that were also outlined on libvirt-users ML [1]
> and I was affected with. 

Just to give a more practical context on the issue I'm trying to solve
with this series, given this simple example code:

=======================

#define _GNU_SOURCE
#include <stdlib.h>
#include <unistd.h>
#include <stdio.h>
#include <libvirt/libvirt.h>
#include <libvirt/virterror.h>

const char *xml_tmpl = "<?xml version=\"1.0\"?>"
"<domain type=\"vbox\">"
"    <name>%s</name>"
"    <memory unit=\"MiB\">3072</memory>"
"    <vcpu>2</vcpu>"
"    <os>"
"        <type arch=\"x86_64\">hvm</type>"
"        <boot dev=\"cdrom\"/>"
"        <boot dev=\"hd\"/>"
"    </os>"
"    <features>"
"        <acpi/>"
"        <apic/>"
"        <pae/>"
"    </features>"
"    <cpu mode=\"host-model\"/>"
"    <devices>"
"        <graphics type=\"rdp\" autoport=\"yes\"
multiUser=\"yes\"></graphics>"
"        <video primary=\"yes\">"
"            <model type=\"vbox\" vram=\"24576\" heads=\"1\"></model>"
"        </video>"
"    </devices>"
"</domain>";

int main(int argc, char *argv[]) {
    virConnectPtr conn;
    char *vm_xml;
    int ret = 0;

    if (argc != 2) {
        fprintf(stderr, "Please specify VM name as first argument\n");

        return 1;
    }

    conn = virConnectOpen("vbox:///session");

    if (conn == NULL) {
        fprintf(stderr, "Failed to open connection to
vbox:///session\n");

        return 1;
    } else {
        printf("Connected to vbox successfully...\n");
    }

    printf("Sleeping for 5s...\n");

    sleep(5);
     
    if (asprintf(&vm_xml, xml_tmpl, argv[1]) == -1) {
        fprintf(stderr, "Failed to allocate memory for VM XML
definition string\n");
        ret = 1;

        goto cleanup;
    }

    printf("Defining domain...\n");

    virDomainPtr dom = virDomainDefineXML(conn, vm_xml);

    if (dom == NULL) {
        const char *error = virGetLastErrorMessage();
        fprintf(stderr, "Failed to define domain: %s\n", error);
        ret = 1;

        goto cleanup;
    }

    printf("Domain defined successfully.\n");
    sleep(1);
    printf("Undefining domain...\n");

    if (virDomainUndefine(dom) == -1) {
        const char *error = virGetLastErrorMessage();
        fprintf(stderr, "Failed to undefine domain %s\n", error);
        fprintf(stderr, "This may require cleanup of the VBOX home dir
from stale template files\n");
        ret = 1;

        goto cleanup;
    }

    printf("Domain undefined successfully.\n");

 cleanup:
    printf("Closing vbox connection...\n");
    virConnectClose(conn);

    printf("Done\n");

    free(vm_xml);
    vm_xml = NULL;

    return ret;
}

================================

After compiling (to say, vbox-test):

1. ./vbox-test vm1 # creates/destroys vbox VM named "vm1"
2. while #1 is sleeping, ./vbox-test vm2 # will attempt to do the same
for "vm2" by spawning concurrent vbox connection.
3. result: the 2nd process will segfault libvirtd

with those patches applied both succeed as expected.

Regards,
Dawid




More information about the libvir-list mailing list