From patchwork Wed May 7 09:54:12 2014 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Chunyan Liu X-Patchwork-Id: 346462 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id E4B461401FA for ; Wed, 7 May 2014 19:59:01 +1000 (EST) Received: from localhost ([::1]:39805 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1Whyct-0001NN-SG for incoming@patchwork.ozlabs.org; Wed, 07 May 2014 05:58:59 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:40353) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1WhyZK-00032E-Bo for qemu-devel@nongnu.org; Wed, 07 May 2014 05:55:23 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1WhyZ9-0002SN-Ui for qemu-devel@nongnu.org; Wed, 07 May 2014 05:55:18 -0400 Received: from victor.provo.novell.com ([137.65.250.26]:59745) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1WhyZ9-0002Rf-IK for qemu-devel@nongnu.org; Wed, 07 May 2014 05:55:07 -0400 Received: from linux-cyliu.lab.bej.apac.novell.com (prv-ext-foundry1int.gns.novell.com [137.65.251.240]) by victor.provo.novell.com with ESMTP (NOT encrypted); Wed, 07 May 2014 03:55:03 -0600 From: Chunyan Liu To: qemu-devel@nongnu.org Date: Wed, 7 May 2014 17:54:12 +0800 Message-Id: <1399456476-10786-10-git-send-email-cyliu@suse.com> X-Mailer: git-send-email 1.7.12.4 In-Reply-To: <1399456476-10786-1-git-send-email-cyliu@suse.com> References: <1399456476-10786-1-git-send-email-cyliu@suse.com> X-detected-operating-system: by eggs.gnu.org: GNU/Linux 3.x X-Received-From: 137.65.250.26 Cc: l@dorileo.org, stefanha@redhat.com Subject: [Qemu-devel] [PATCH v27 09/33] QemuOpts: add conversion between QEMUOptionParameter to QemuOpts X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Add two temp conversion functions between QEMUOptionParameter to QemuOpts, so that next patch can use it. It will simplify later patch for easier review. And will be finally removed after all backend drivers switch to QemuOpts. Reviewed-by: Stefan Hajnoczi Reviewed-by: Eric Blake Reviewed-by: Leandro Dorileo Signed-off-by: Chunyan Liu --- include/qemu/option.h | 9 +++ util/qemu-option.c | 153 ++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 162 insertions(+) diff --git a/include/qemu/option.h b/include/qemu/option.h index fbf5dc2..e98e8ef 100644 --- a/include/qemu/option.h +++ b/include/qemu/option.h @@ -103,6 +103,12 @@ typedef struct QemuOptDesc { } QemuOptDesc; struct QemuOptsList { + /* FIXME: Temp used for QEMUOptionParamter->QemuOpts conversion to + * indicate the need to free memory. Will remove after all drivers + * switch to QemuOpts. + */ + bool allocated; + const char *name; const char *implied_opt_name; bool merge_lists; /* Merge multiple uses of option into a single list? */ @@ -167,5 +173,8 @@ void qemu_opts_print(QemuOpts *opts); int qemu_opts_foreach(QemuOptsList *list, qemu_opts_loopfunc func, void *opaque, int abort_on_failure); void qemu_opts_print_help(QemuOptsList *list); +void qemu_opts_free(QemuOptsList *list); +QEMUOptionParameter *opts_to_params(QemuOpts *opts); +QemuOptsList *params_to_opts(QEMUOptionParameter *list); #endif diff --git a/util/qemu-option.c b/util/qemu-option.c index adb7c3c..93ffcd5 100644 --- a/util/qemu-option.c +++ b/util/qemu-option.c @@ -1345,3 +1345,156 @@ int qemu_opts_foreach(QemuOptsList *list, qemu_opts_loopfunc func, void *opaque, loc_pop(&loc); return rc; } + +static size_t count_opts_list(QemuOptsList *list) +{ + QemuOptDesc *desc = NULL; + size_t num_opts = 0; + + if (!list) { + return 0; + } + + desc = list->desc; + while (desc && desc->name) { + num_opts++; + desc++; + } + + return num_opts; +} + +/* Convert QEMUOptionParameter to QemuOpts + * FIXME: this function will be removed after all drivers + * switch to QemuOpts + */ +QemuOptsList *params_to_opts(QEMUOptionParameter *list) +{ + QemuOptsList *opts = NULL; + size_t num_opts, i = 0; + + if (!list) { + return NULL; + } + + num_opts = count_option_parameters(list); + opts = g_malloc0(sizeof(QemuOptsList) + + (num_opts + 1) * sizeof(QemuOptDesc)); + QTAILQ_INIT(&opts->head); + /* (const char *) members will point to malloced space and need to free */ + opts->allocated = true; + + while (list && list->name) { + opts->desc[i].name = g_strdup(list->name); + opts->desc[i].help = g_strdup(list->help); + switch (list->type) { + case OPT_FLAG: + opts->desc[i].type = QEMU_OPT_BOOL; + opts->desc[i].def_value_str = + g_strdup(list->value.n ? "on" : "off"); + break; + + case OPT_NUMBER: + opts->desc[i].type = QEMU_OPT_NUMBER; + if (list->value.n) { + opts->desc[i].def_value_str = + g_strdup_printf("%" PRIu64, list->value.n); + } + break; + + case OPT_SIZE: + opts->desc[i].type = QEMU_OPT_SIZE; + if (list->value.n) { + opts->desc[i].def_value_str = + g_strdup_printf("%" PRIu64, list->value.n); + } + break; + + case OPT_STRING: + opts->desc[i].type = QEMU_OPT_STRING; + opts->desc[i].def_value_str = g_strdup(list->value.s); + break; + } + + i++; + list++; + } + + return opts; +} + +/* convert QemuOpts to QEMUOptionParameter + * Note: result QEMUOptionParameter has shorter lifetime than + * input QemuOpts. + * FIXME: this function will be removed after all drivers + * switch to QemuOpts + */ +QEMUOptionParameter *opts_to_params(QemuOpts *opts) +{ + QEMUOptionParameter *dest = NULL; + QemuOptDesc *desc; + size_t num_opts, i = 0; + const char *tmp; + + if (!opts || !opts->list || !opts->list->desc) { + return NULL; + } + assert(!opts_accepts_any(opts)); + + num_opts = count_opts_list(opts->list); + dest = g_malloc0((num_opts + 1) * sizeof(QEMUOptionParameter)); + + desc = opts->list->desc; + while (desc && desc->name) { + dest[i].name = desc->name; + dest[i].help = desc->help; + dest[i].assigned = qemu_opt_find(opts, desc->name) ? true : false; + switch (desc->type) { + case QEMU_OPT_STRING: + dest[i].type = OPT_STRING; + tmp = qemu_opt_get(opts, desc->name); + dest[i].value.s = g_strdup(tmp); + break; + + case QEMU_OPT_BOOL: + dest[i].type = OPT_FLAG; + dest[i].value.n = qemu_opt_get_bool(opts, desc->name, 0) ? 1 : 0; + break; + + case QEMU_OPT_NUMBER: + dest[i].type = OPT_NUMBER; + dest[i].value.n = qemu_opt_get_number(opts, desc->name, 0); + break; + + case QEMU_OPT_SIZE: + dest[i].type = OPT_SIZE; + dest[i].value.n = qemu_opt_get_size(opts, desc->name, 0); + break; + } + + i++; + desc++; + } + + return dest; +} + +void qemu_opts_free(QemuOptsList *list) +{ + /* List members point to new malloced space and need to be freed. + * FIXME: + * Introduced for QEMUOptionParamter->QemuOpts conversion. + * Will remove after all drivers switch to QemuOpts. + */ + if (list && list->allocated) { + QemuOptDesc *desc = list->desc; + while (desc && desc->name) { + g_free((char *)desc->name); + g_free((char *)desc->help); + g_free((char *)desc->def_value_str); + desc++; + } + } + + g_free(list); +}