On Wed, Jul 17, 2019 at 10:03:23 -0400, Collin Walling wrote: > Interfaces with QEMU to baseline CPU models. The command takes two > CPU models, A and B, that are given a model name and an optional list > of CPU features. Through the query-cpu-model-baseline command issued > via QMP, a result is produced that contains a new baselined CPU model > that is guaranteed to run on both A and B. > > Signed-off-by: Collin Walling <walling@xxxxxxxxxxxxx> > Reviewed-by: Daniel Henrique Barboza <danielh413@xxxxxxxxx> > --- > src/qemu/qemu_monitor.c | 22 ++++++++++++++++ > src/qemu/qemu_monitor.h | 9 +++++++ > src/qemu/qemu_monitor_json.c | 61 ++++++++++++++++++++++++++++++++++++++++++++ > src/qemu/qemu_monitor_json.h | 10 ++++++++ > 4 files changed, 102 insertions(+) > > diff --git a/src/qemu/qemu_monitor.c b/src/qemu/qemu_monitor.c > index 731be2e..136d3e2 100644 > --- a/src/qemu/qemu_monitor.c > +++ b/src/qemu/qemu_monitor.c > @@ -3648,6 +3648,28 @@ qemuMonitorGetCPUModelExpansion(qemuMonitorPtr mon, > } > > > +int > +qemuMonitorGetCPUModelBaseline(qemuMonitorPtr mon, > + const char *model_a_name, > + int model_a_nprops, > + virCPUFeatureDefPtr model_a_props, > + const char *model_b_name, > + int model_b_nprops, > + virCPUFeatureDefPtr model_b_props, This is a mess. Model name, number of features, and the array of features are all included in a virCPUDef structure. Are you going to call this function from places where you don't actually have virCPUDef? Passing just two virCPUDefPtr cpu1, and virCPUDefPtr cpu2 parameters would be much nicer. > + qemuMonitorCPUModelInfoPtr *model_result) > +{ > + VIR_DEBUG("model_a_name=%s model_a_nprops=%d model_b_name=%s model_b_nprops=%d", > + model_a_name, model_a_nprops, model_b_name, model_b_nprops); > + > + QEMU_CHECK_MONITOR(mon); > + > + return qemuMonitorJSONGetCPUModelBaseline(mon, model_a_name, model_a_nprops, > + model_a_props, model_b_name, > + model_b_nprops, model_b_props, > + model_result); > +} > + > + > void > qemuMonitorCPUModelInfoFree(qemuMonitorCPUModelInfoPtr model_info) > { > diff --git a/src/qemu/qemu_monitor.h b/src/qemu/qemu_monitor.h > index c41428b..4ec74f1 100644 > --- a/src/qemu/qemu_monitor.h > +++ b/src/qemu/qemu_monitor.h > @@ -1084,6 +1084,15 @@ int qemuMonitorGetCPUModelExpansion(qemuMonitorPtr mon, > > void qemuMonitorCPUModelInfoFree(qemuMonitorCPUModelInfoPtr model_info); > > +int qemuMonitorGetCPUModelBaseline(qemuMonitorPtr mon, > + const char *model_a_name, > + int model_a_nprops, > + virCPUFeatureDefPtr model_a_props, > + const char *model_b_name, > + int model_b_nprops, > + virCPUFeatureDefPtr model_b_props, > + qemuMonitorCPUModelInfoPtr *model_result); > + > qemuMonitorCPUModelInfoPtr > qemuMonitorCPUModelInfoCopy(const qemuMonitorCPUModelInfo *orig); > > diff --git a/src/qemu/qemu_monitor_json.c b/src/qemu/qemu_monitor_json.c > index f6bf7f2..b599ee6 100644 > --- a/src/qemu/qemu_monitor_json.c > +++ b/src/qemu/qemu_monitor_json.c > @@ -5814,6 +5814,67 @@ qemuMonitorJSONGetCPUModelExpansion(qemuMonitorPtr mon, > } > > > +int > +qemuMonitorJSONGetCPUModelBaseline(qemuMonitorPtr mon, > + const char *model_a_name, > + int model_a_nprops, > + virCPUFeatureDefPtr model_a_props, > + const char *model_b_name, > + int model_b_nprops, > + virCPUFeatureDefPtr model_b_props, > + qemuMonitorCPUModelInfoPtr *model_result) > +{ > + int ret = -1; > + virJSONValuePtr model_a; > + virJSONValuePtr model_b = NULL; > + virJSONValuePtr cmd = NULL; > + virJSONValuePtr reply = NULL; > + virJSONValuePtr data; > + virJSONValuePtr cpu_model; > + virJSONValuePtr cpu_props = NULL; > + const char *cpu_name = ""; > + qemuMonitorCPUModelInfoPtr baseline = NULL; > + > + if (!(model_a = qemuMonitorJSONMakeCPUModel(model_a_name, model_a_nprops, > + model_a_props, true)) || > + !(model_b = qemuMonitorJSONMakeCPUModel(model_b_name, model_b_nprops, > + model_b_props, true))) > + goto cleanup; > + > + if (!(cmd = qemuMonitorJSONMakeCommand("query-cpu-model-baseline", > + "a:modela", &model_a, > + "a:modelb", &model_b, > + NULL))) > + goto cleanup; > + > + if (qemuMonitorJSONCommand(mon, cmd, &reply) < 0) > + goto cleanup; > + > + if (qemuMonitorJSONCheckReply(cmd, reply, VIR_JSON_TYPE_OBJECT) < 0) > + goto cleanup; > + > + data = virJSONValueObjectGetObject(reply, "return"); > + > + if (qemuMonitorJSONParseCPUModelData(data, &cpu_model, &cpu_props, &cpu_name, > + "query-cpu-model-baseline") < 0) > + goto cleanup; > + > + if (qemuMonitorJSONParseCPUModel(cpu_name, cpu_props, &baseline) < 0) > + goto cleanup; > + > + VIR_STEAL_PTR(*model_result, baseline); > + ret = 0; As already mentioned by Boris, you can return baseline directly and you don't need to worry about freeing it. > + > + cleanup: > + qemuMonitorCPUModelInfoFree(baseline); > + virJSONValueFree(cmd); > + virJSONValueFree(reply); > + virJSONValueFree(model_a); > + virJSONValueFree(model_b); You can declare all four variables as VIR_AUTOPTR(virJSONValue) cmd = NULL; and then you can drop this cleanup section completely by replacing "goto cleanup" with "return -1". > + return ret; > +} > + > + > int qemuMonitorJSONGetCommands(qemuMonitorPtr mon, > char ***commands) > { ... Jirka -- libvir-list mailing list libvir-list@xxxxxxxxxx https://www.redhat.com/mailman/listinfo/libvir-list