X-Git-Url: https://git.proxmox.com/?a=blobdiff_plain;f=accel.c;h=664bb88422a4babeaaa47416d64e8bba6f143172;hb=fb59dabd4fa7e6586824ac3012073b943fc8dc79;hp=3cefd7451ccce84c5f7693b3a5f2ddfaea9884be;hpb=e54adde6154fc86e52abb911e7c0604c9dc7a58a;p=mirror_qemu.git diff --git a/accel.c b/accel.c index 3cefd7451c..664bb88422 100644 --- a/accel.c +++ b/accel.c @@ -23,45 +23,67 @@ * THE SOFTWARE. */ +#include "qemu/osdep.h" #include "sysemu/accel.h" +#include "hw/boards.h" #include "qemu-common.h" #include "sysemu/arch_init.h" #include "sysemu/sysemu.h" #include "sysemu/kvm.h" #include "sysemu/qtest.h" #include "hw/xen/xen.h" +#include "qom/object.h" int tcg_tb_size; static bool tcg_allowed = true; -static int tcg_init(MachineClass *mc) +static int tcg_init(MachineState *ms) { tcg_exec_init(tcg_tb_size * 1024 * 1024); return 0; } -typedef struct AccelType { - const char *opt_name; - const char *name; - int (*available)(void); - int (*init)(MachineClass *mc); - bool *allowed; -} AccelType; - -static AccelType accel_list[] = { - { "tcg", "tcg", tcg_available, tcg_init, &tcg_allowed }, - { "xen", "Xen", xen_available, xen_init, &xen_allowed }, - { "kvm", "KVM", kvm_available, kvm_init, &kvm_allowed }, - { "qtest", "QTest", qtest_available, qtest_init_accel, &qtest_allowed }, +static const TypeInfo accel_type = { + .name = TYPE_ACCEL, + .parent = TYPE_OBJECT, + .class_size = sizeof(AccelClass), + .instance_size = sizeof(AccelState), }; -int configure_accelerator(MachineClass *mc) +/* Lookup AccelClass from opt_name. Returns NULL if not found */ +static AccelClass *accel_find(const char *opt_name) +{ + char *class_name = g_strdup_printf(ACCEL_CLASS_NAME("%s"), opt_name); + AccelClass *ac = ACCEL_CLASS(object_class_by_name(class_name)); + g_free(class_name); + return ac; +} + +static int accel_init_machine(AccelClass *acc, MachineState *ms) +{ + ObjectClass *oc = OBJECT_CLASS(acc); + const char *cname = object_class_get_name(oc); + AccelState *accel = ACCEL(object_new(cname)); + int ret; + ms->accelerator = accel; + *(acc->allowed) = true; + ret = acc->init_machine(ms); + if (ret < 0) { + ms->accelerator = NULL; + *(acc->allowed) = false; + object_unref(OBJECT(accel)); + } + return ret; +} + +void configure_accelerator(MachineState *ms) { const char *p; char buf[10]; - int i, ret; + int ret; bool accel_initialised = false; bool init_failed = false; + AccelClass *acc = NULL; p = qemu_opt_get(qemu_get_machine_opts(), "accel"); if (p == NULL) { @@ -74,29 +96,24 @@ int configure_accelerator(MachineClass *mc) p++; } p = get_opt_name(buf, sizeof(buf), p, ':'); - for (i = 0; i < ARRAY_SIZE(accel_list); i++) { - if (strcmp(accel_list[i].opt_name, buf) == 0) { - if (!accel_list[i].available()) { - printf("%s not supported for this target\n", - accel_list[i].name); - break; - } - *(accel_list[i].allowed) = true; - ret = accel_list[i].init(mc); - if (ret < 0) { - init_failed = true; - fprintf(stderr, "failed to initialize %s: %s\n", - accel_list[i].name, - strerror(-ret)); - *(accel_list[i].allowed) = false; - } else { - accel_initialised = true; - } - break; - } + acc = accel_find(buf); + if (!acc) { + fprintf(stderr, "\"%s\" accelerator not found.\n", buf); + continue; } - if (i == ARRAY_SIZE(accel_list)) { - fprintf(stderr, "\"%s\" accelerator does not exist.\n", buf); + if (acc->available && !acc->available()) { + printf("%s not supported for this target\n", + acc->name); + continue; + } + ret = accel_init_machine(acc, ms); + if (ret < 0) { + init_failed = true; + fprintf(stderr, "failed to initialize %s: %s\n", + acc->name, + strerror(-ret)); + } else { + accel_initialised = true; } } @@ -108,8 +125,31 @@ int configure_accelerator(MachineClass *mc) } if (init_failed) { - fprintf(stderr, "Back to %s accelerator.\n", accel_list[i].name); + fprintf(stderr, "Back to %s accelerator.\n", acc->name); } +} - return !accel_initialised; + +static void tcg_accel_class_init(ObjectClass *oc, void *data) +{ + AccelClass *ac = ACCEL_CLASS(oc); + ac->name = "tcg"; + ac->init_machine = tcg_init; + ac->allowed = &tcg_allowed; } + +#define TYPE_TCG_ACCEL ACCEL_CLASS_NAME("tcg") + +static const TypeInfo tcg_accel_type = { + .name = TYPE_TCG_ACCEL, + .parent = TYPE_ACCEL, + .class_init = tcg_accel_class_init, +}; + +static void register_accel_types(void) +{ + type_register_static(&accel_type); + type_register_static(&tcg_accel_type); +} + +type_init(register_accel_types);