Re: [Qemu-devel] [PATCH v5 05/18] qapi: add QMP input visitor

2011-07-12 Thread Michael Roth

On 07/12/2011 08:53 AM, Luiz Capitulino wrote:

On Tue, 12 Jul 2011 08:46:13 -0500
Michael Roth  wrote:


On 07/12/2011 08:16 AM, Luiz Capitulino wrote:

On Mon, 11 Jul 2011 19:05:58 -0500
Michael Roth   wrote:


On 07/07/2011 09:32 AM, Luiz Capitulino wrote:

On Tue,  5 Jul 2011 08:02:32 -0500
Michael Rothwrote:


A type of Visiter class that is used to walk a qobject's
structure and assign each entry to the corresponding native C type.
Command marshaling function will use this to pull out QMP command
parameters recieved over the wire and pass them as native arguments
to the corresponding C functions.

Signed-off-by: Michael Roth
---
Makefile.objs|2 +-
qapi/qmp-input-visitor.c |  264 
++
qapi/qmp-input-visitor.h |   27 +
qerror.h |3 +
4 files changed, 295 insertions(+), 1 deletions(-)
create mode 100644 qapi/qmp-input-visitor.c
create mode 100644 qapi/qmp-input-visitor.h

diff --git a/Makefile.objs b/Makefile.objs
index 0077014..997ecef 100644
--- a/Makefile.objs
+++ b/Makefile.objs
@@ -375,7 +375,7 @@ libcacard-y = cac.o event.o vcard.o vreader.o 
vcard_emul_nss.o vcard_emul_type.o
##
# qapi

-qapi-nested-y = qapi-visit-core.o
+qapi-nested-y = qapi-visit-core.o qmp-input-visitor.o
qapi-obj-y = $(addprefix qapi/, $(qapi-nested-y))

vl.o: QEMU_CFLAGS+=$(GPROF_CFLAGS)
diff --git a/qapi/qmp-input-visitor.c b/qapi/qmp-input-visitor.c
new file mode 100644
index 000..80912bb
--- /dev/null
+++ b/qapi/qmp-input-visitor.c
@@ -0,0 +1,264 @@
+/*
+ * Input Visitor
+ *
+ * Copyright IBM, Corp. 2011
+ *
+ * Authors:
+ *  Anthony Liguori
+ *
+ * This work is licensed under the terms of the GNU LGPL, version 2.1 or later.
+ * See the COPYING.LIB file in the top-level directory.
+ *
+ */
+
+#include "qmp-input-visitor.h"
+#include "qemu-queue.h"
+#include "qemu-common.h"
+#include "qemu-objects.h"
+#include "qerror.h"
+
+#define QIV_STACK_SIZE 1024
+
+typedef struct StackObject
+{
+const QObject *obj;
+const  QListEntry *entry;
+} StackObject;
+
+struct QmpInputVisitor
+{
+Visitor visitor;
+const QObject *obj;
+StackObject stack[QIV_STACK_SIZE];
+int nb_stack;
+};
+
+static QmpInputVisitor *to_qiv(Visitor *v)
+{
+return container_of(v, QmpInputVisitor, visitor);
+}
+
+static const QObject *qmp_input_get_object(QmpInputVisitor *qiv, const char 
*name)
+{
+const QObject *qobj;
+
+if (qiv->nb_stack == 0) {
+qobj = qiv->obj;
+} else {
+qobj = qiv->stack[qiv->nb_stack - 1].obj;
+}
+
+if (name&&qobject_type(qobj) == QTYPE_QDICT) {
+return qdict_get(qobject_to_qdict(qobj), name);
+} else if (qiv->nb_stack>0&&qobject_type(qobj) == QTYPE_QLIST) {
+return qlist_entry_obj(qiv->stack[qiv->nb_stack - 1].entry);
+}
+
+return qobj;
+}
+
+static void qmp_input_push(QmpInputVisitor *qiv, const QObject *obj, Error 
**errp)
+{
+qiv->stack[qiv->nb_stack].obj = obj;
+if (qobject_type(obj) == QTYPE_QLIST) {
+qiv->stack[qiv->nb_stack].entry = qlist_first(qobject_to_qlist(obj));
+}
+qiv->nb_stack++;
+
+if (qiv->nb_stack>= QIV_STACK_SIZE) {
+error_set(errp, QERR_BUFFER_OVERRUN);
+return;
+}
+}
+
+static void qmp_input_pop(QmpInputVisitor *qiv, Error **errp)
+{
+qiv->nb_stack--;
+if (qiv->nb_stack<0) {
+error_set(errp, QERR_BUFFER_OVERRUN);
+return;
+}
+}
+
+static void qmp_input_start_struct(Visitor *v, void **obj, const char *kind, 
const char *name, size_t size, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+const QObject *qobj = qmp_input_get_object(qiv, name);
+
+if (!qobj || qobject_type(qobj) != QTYPE_QDICT) {
+error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
"QDict");
+return;
+}
+
+qmp_input_push(qiv, qobj, errp);
+if (error_is_set(errp)) {
+return;
+}
+
+if (obj) {
+*obj = qemu_mallocz(size);
+}
+}
+
+static void qmp_input_end_struct(Visitor *v, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+
+qmp_input_pop(qiv, errp);
+}
+
+static void qmp_input_start_list(Visitor *v, const char *name, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+const QObject *qobj = qmp_input_get_object(qiv, name);
+
+if (!qobj || qobject_type(qobj) != QTYPE_QLIST) {
+error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
"list");
+return;
+}
+
+qmp_input_push(qiv, qobj, errp);
+}
+
+static GenericList *qmp_input_next_list(Visitor *v, GenericList **list, Error 
**errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+GenericList *entry;
+StackObject *so =&qiv->stack[qiv->nb_stack - 1];
+
+if (so->entry == NULL) {
+return NULL;
+}
+
+entry = qemu_mallocz(sizeof(*entry));
+if (*list) {
+so->ent

Re: [Qemu-devel] [PATCH v5 05/18] qapi: add QMP input visitor

2011-07-12 Thread Luiz Capitulino
On Tue, 12 Jul 2011 08:46:13 -0500
Michael Roth  wrote:

> On 07/12/2011 08:16 AM, Luiz Capitulino wrote:
> > On Mon, 11 Jul 2011 19:05:58 -0500
> > Michael Roth  wrote:
> >
> >> On 07/07/2011 09:32 AM, Luiz Capitulino wrote:
> >>> On Tue,  5 Jul 2011 08:02:32 -0500
> >>> Michael Roth   wrote:
> >>>
>  A type of Visiter class that is used to walk a qobject's
>  structure and assign each entry to the corresponding native C type.
>  Command marshaling function will use this to pull out QMP command
>  parameters recieved over the wire and pass them as native arguments
>  to the corresponding C functions.
> 
>  Signed-off-by: Michael Roth
>  ---
> Makefile.objs|2 +-
> qapi/qmp-input-visitor.c |  264 
>  ++
> qapi/qmp-input-visitor.h |   27 +
> qerror.h |3 +
> 4 files changed, 295 insertions(+), 1 deletions(-)
> create mode 100644 qapi/qmp-input-visitor.c
> create mode 100644 qapi/qmp-input-visitor.h
> 
>  diff --git a/Makefile.objs b/Makefile.objs
>  index 0077014..997ecef 100644
>  --- a/Makefile.objs
>  +++ b/Makefile.objs
>  @@ -375,7 +375,7 @@ libcacard-y = cac.o event.o vcard.o vreader.o 
>  vcard_emul_nss.o vcard_emul_type.o
> ##
> # qapi
> 
>  -qapi-nested-y = qapi-visit-core.o
>  +qapi-nested-y = qapi-visit-core.o qmp-input-visitor.o
> qapi-obj-y = $(addprefix qapi/, $(qapi-nested-y))
> 
> vl.o: QEMU_CFLAGS+=$(GPROF_CFLAGS)
>  diff --git a/qapi/qmp-input-visitor.c b/qapi/qmp-input-visitor.c
>  new file mode 100644
>  index 000..80912bb
>  --- /dev/null
>  +++ b/qapi/qmp-input-visitor.c
>  @@ -0,0 +1,264 @@
>  +/*
>  + * Input Visitor
>  + *
>  + * Copyright IBM, Corp. 2011
>  + *
>  + * Authors:
>  + *  Anthony Liguori
>  + *
>  + * This work is licensed under the terms of the GNU LGPL, version 2.1 
>  or later.
>  + * See the COPYING.LIB file in the top-level directory.
>  + *
>  + */
>  +
>  +#include "qmp-input-visitor.h"
>  +#include "qemu-queue.h"
>  +#include "qemu-common.h"
>  +#include "qemu-objects.h"
>  +#include "qerror.h"
>  +
>  +#define QIV_STACK_SIZE 1024
>  +
>  +typedef struct StackObject
>  +{
>  +const QObject *obj;
>  +const  QListEntry *entry;
>  +} StackObject;
>  +
>  +struct QmpInputVisitor
>  +{
>  +Visitor visitor;
>  +const QObject *obj;
>  +StackObject stack[QIV_STACK_SIZE];
>  +int nb_stack;
>  +};
>  +
>  +static QmpInputVisitor *to_qiv(Visitor *v)
>  +{
>  +return container_of(v, QmpInputVisitor, visitor);
>  +}
>  +
>  +static const QObject *qmp_input_get_object(QmpInputVisitor *qiv, const 
>  char *name)
>  +{
>  +const QObject *qobj;
>  +
>  +if (qiv->nb_stack == 0) {
>  +qobj = qiv->obj;
>  +} else {
>  +qobj = qiv->stack[qiv->nb_stack - 1].obj;
>  +}
>  +
>  +if (name&&   qobject_type(qobj) == QTYPE_QDICT) {
>  +return qdict_get(qobject_to_qdict(qobj), name);
>  +} else if (qiv->nb_stack>   0&&   qobject_type(qobj) == 
>  QTYPE_QLIST) {
>  +return qlist_entry_obj(qiv->stack[qiv->nb_stack - 1].entry);
>  +}
>  +
>  +return qobj;
>  +}
>  +
>  +static void qmp_input_push(QmpInputVisitor *qiv, const QObject *obj, 
>  Error **errp)
>  +{
>  +qiv->stack[qiv->nb_stack].obj = obj;
>  +if (qobject_type(obj) == QTYPE_QLIST) {
>  +qiv->stack[qiv->nb_stack].entry = 
>  qlist_first(qobject_to_qlist(obj));
>  +}
>  +qiv->nb_stack++;
>  +
>  +if (qiv->nb_stack>= QIV_STACK_SIZE) {
>  +error_set(errp, QERR_BUFFER_OVERRUN);
>  +return;
>  +}
>  +}
>  +
>  +static void qmp_input_pop(QmpInputVisitor *qiv, Error **errp)
>  +{
>  +qiv->nb_stack--;
>  +if (qiv->nb_stack<   0) {
>  +error_set(errp, QERR_BUFFER_OVERRUN);
>  +return;
>  +}
>  +}
>  +
>  +static void qmp_input_start_struct(Visitor *v, void **obj, const char 
>  *kind, const char *name, size_t size, Error **errp)
>  +{
>  +QmpInputVisitor *qiv = to_qiv(v);
>  +const QObject *qobj = qmp_input_get_object(qiv, name);
>  +
>  +if (!qobj || qobject_type(qobj) != QTYPE_QDICT) {
>  +error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : 
>  "null", "QDict");
>  +return;
>  +}
>  +
>  +qmp_input_push(qiv, qobj, errp);
>  +if (error_is_set(errp)) {
>  +return;
>  +}
> >>

Re: [Qemu-devel] [PATCH v5 05/18] qapi: add QMP input visitor

2011-07-12 Thread Michael Roth

On 07/12/2011 08:16 AM, Luiz Capitulino wrote:

On Mon, 11 Jul 2011 19:05:58 -0500
Michael Roth  wrote:


On 07/07/2011 09:32 AM, Luiz Capitulino wrote:

On Tue,  5 Jul 2011 08:02:32 -0500
Michael Roth   wrote:


A type of Visiter class that is used to walk a qobject's
structure and assign each entry to the corresponding native C type.
Command marshaling function will use this to pull out QMP command
parameters recieved over the wire and pass them as native arguments
to the corresponding C functions.

Signed-off-by: Michael Roth
---
   Makefile.objs|2 +-
   qapi/qmp-input-visitor.c |  264 
++
   qapi/qmp-input-visitor.h |   27 +
   qerror.h |3 +
   4 files changed, 295 insertions(+), 1 deletions(-)
   create mode 100644 qapi/qmp-input-visitor.c
   create mode 100644 qapi/qmp-input-visitor.h

diff --git a/Makefile.objs b/Makefile.objs
index 0077014..997ecef 100644
--- a/Makefile.objs
+++ b/Makefile.objs
@@ -375,7 +375,7 @@ libcacard-y = cac.o event.o vcard.o vreader.o 
vcard_emul_nss.o vcard_emul_type.o
   ##
   # qapi

-qapi-nested-y = qapi-visit-core.o
+qapi-nested-y = qapi-visit-core.o qmp-input-visitor.o
   qapi-obj-y = $(addprefix qapi/, $(qapi-nested-y))

   vl.o: QEMU_CFLAGS+=$(GPROF_CFLAGS)
diff --git a/qapi/qmp-input-visitor.c b/qapi/qmp-input-visitor.c
new file mode 100644
index 000..80912bb
--- /dev/null
+++ b/qapi/qmp-input-visitor.c
@@ -0,0 +1,264 @@
+/*
+ * Input Visitor
+ *
+ * Copyright IBM, Corp. 2011
+ *
+ * Authors:
+ *  Anthony Liguori
+ *
+ * This work is licensed under the terms of the GNU LGPL, version 2.1 or later.
+ * See the COPYING.LIB file in the top-level directory.
+ *
+ */
+
+#include "qmp-input-visitor.h"
+#include "qemu-queue.h"
+#include "qemu-common.h"
+#include "qemu-objects.h"
+#include "qerror.h"
+
+#define QIV_STACK_SIZE 1024
+
+typedef struct StackObject
+{
+const QObject *obj;
+const  QListEntry *entry;
+} StackObject;
+
+struct QmpInputVisitor
+{
+Visitor visitor;
+const QObject *obj;
+StackObject stack[QIV_STACK_SIZE];
+int nb_stack;
+};
+
+static QmpInputVisitor *to_qiv(Visitor *v)
+{
+return container_of(v, QmpInputVisitor, visitor);
+}
+
+static const QObject *qmp_input_get_object(QmpInputVisitor *qiv, const char 
*name)
+{
+const QObject *qobj;
+
+if (qiv->nb_stack == 0) {
+qobj = qiv->obj;
+} else {
+qobj = qiv->stack[qiv->nb_stack - 1].obj;
+}
+
+if (name&&   qobject_type(qobj) == QTYPE_QDICT) {
+return qdict_get(qobject_to_qdict(qobj), name);
+} else if (qiv->nb_stack>   0&&   qobject_type(qobj) == QTYPE_QLIST) {
+return qlist_entry_obj(qiv->stack[qiv->nb_stack - 1].entry);
+}
+
+return qobj;
+}
+
+static void qmp_input_push(QmpInputVisitor *qiv, const QObject *obj, Error 
**errp)
+{
+qiv->stack[qiv->nb_stack].obj = obj;
+if (qobject_type(obj) == QTYPE_QLIST) {
+qiv->stack[qiv->nb_stack].entry = qlist_first(qobject_to_qlist(obj));
+}
+qiv->nb_stack++;
+
+if (qiv->nb_stack>= QIV_STACK_SIZE) {
+error_set(errp, QERR_BUFFER_OVERRUN);
+return;
+}
+}
+
+static void qmp_input_pop(QmpInputVisitor *qiv, Error **errp)
+{
+qiv->nb_stack--;
+if (qiv->nb_stack<   0) {
+error_set(errp, QERR_BUFFER_OVERRUN);
+return;
+}
+}
+
+static void qmp_input_start_struct(Visitor *v, void **obj, const char *kind, 
const char *name, size_t size, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+const QObject *qobj = qmp_input_get_object(qiv, name);
+
+if (!qobj || qobject_type(qobj) != QTYPE_QDICT) {
+error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
"QDict");
+return;
+}
+
+qmp_input_push(qiv, qobj, errp);
+if (error_is_set(errp)) {
+return;
+}
+
+if (obj) {
+*obj = qemu_mallocz(size);
+}
+}
+
+static void qmp_input_end_struct(Visitor *v, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+
+qmp_input_pop(qiv, errp);
+}
+
+static void qmp_input_start_list(Visitor *v, const char *name, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+const QObject *qobj = qmp_input_get_object(qiv, name);
+
+if (!qobj || qobject_type(qobj) != QTYPE_QLIST) {
+error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
"list");
+return;
+}
+
+qmp_input_push(qiv, qobj, errp);
+}
+
+static GenericList *qmp_input_next_list(Visitor *v, GenericList **list, Error 
**errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+GenericList *entry;
+StackObject *so =&qiv->stack[qiv->nb_stack - 1];
+
+if (so->entry == NULL) {
+return NULL;
+}
+
+entry = qemu_mallocz(sizeof(*entry));
+if (*list) {
+so->entry = qlist_next(so->entry);
+if (so->entry == NULL) {
+qemu_free(entry);
+return NULL;
+   

Re: [Qemu-devel] [PATCH v5 05/18] qapi: add QMP input visitor

2011-07-12 Thread Luiz Capitulino
On Mon, 11 Jul 2011 19:05:58 -0500
Michael Roth  wrote:

> On 07/07/2011 09:32 AM, Luiz Capitulino wrote:
> > On Tue,  5 Jul 2011 08:02:32 -0500
> > Michael Roth  wrote:
> >
> >> A type of Visiter class that is used to walk a qobject's
> >> structure and assign each entry to the corresponding native C type.
> >> Command marshaling function will use this to pull out QMP command
> >> parameters recieved over the wire and pass them as native arguments
> >> to the corresponding C functions.
> >>
> >> Signed-off-by: Michael Roth
> >> ---
> >>   Makefile.objs|2 +-
> >>   qapi/qmp-input-visitor.c |  264 
> >> ++
> >>   qapi/qmp-input-visitor.h |   27 +
> >>   qerror.h |3 +
> >>   4 files changed, 295 insertions(+), 1 deletions(-)
> >>   create mode 100644 qapi/qmp-input-visitor.c
> >>   create mode 100644 qapi/qmp-input-visitor.h
> >>
> >> diff --git a/Makefile.objs b/Makefile.objs
> >> index 0077014..997ecef 100644
> >> --- a/Makefile.objs
> >> +++ b/Makefile.objs
> >> @@ -375,7 +375,7 @@ libcacard-y = cac.o event.o vcard.o vreader.o 
> >> vcard_emul_nss.o vcard_emul_type.o
> >>   ##
> >>   # qapi
> >>
> >> -qapi-nested-y = qapi-visit-core.o
> >> +qapi-nested-y = qapi-visit-core.o qmp-input-visitor.o
> >>   qapi-obj-y = $(addprefix qapi/, $(qapi-nested-y))
> >>
> >>   vl.o: QEMU_CFLAGS+=$(GPROF_CFLAGS)
> >> diff --git a/qapi/qmp-input-visitor.c b/qapi/qmp-input-visitor.c
> >> new file mode 100644
> >> index 000..80912bb
> >> --- /dev/null
> >> +++ b/qapi/qmp-input-visitor.c
> >> @@ -0,0 +1,264 @@
> >> +/*
> >> + * Input Visitor
> >> + *
> >> + * Copyright IBM, Corp. 2011
> >> + *
> >> + * Authors:
> >> + *  Anthony Liguori
> >> + *
> >> + * This work is licensed under the terms of the GNU LGPL, version 2.1 or 
> >> later.
> >> + * See the COPYING.LIB file in the top-level directory.
> >> + *
> >> + */
> >> +
> >> +#include "qmp-input-visitor.h"
> >> +#include "qemu-queue.h"
> >> +#include "qemu-common.h"
> >> +#include "qemu-objects.h"
> >> +#include "qerror.h"
> >> +
> >> +#define QIV_STACK_SIZE 1024
> >> +
> >> +typedef struct StackObject
> >> +{
> >> +const QObject *obj;
> >> +const  QListEntry *entry;
> >> +} StackObject;
> >> +
> >> +struct QmpInputVisitor
> >> +{
> >> +Visitor visitor;
> >> +const QObject *obj;
> >> +StackObject stack[QIV_STACK_SIZE];
> >> +int nb_stack;
> >> +};
> >> +
> >> +static QmpInputVisitor *to_qiv(Visitor *v)
> >> +{
> >> +return container_of(v, QmpInputVisitor, visitor);
> >> +}
> >> +
> >> +static const QObject *qmp_input_get_object(QmpInputVisitor *qiv, const 
> >> char *name)
> >> +{
> >> +const QObject *qobj;
> >> +
> >> +if (qiv->nb_stack == 0) {
> >> +qobj = qiv->obj;
> >> +} else {
> >> +qobj = qiv->stack[qiv->nb_stack - 1].obj;
> >> +}
> >> +
> >> +if (name&&  qobject_type(qobj) == QTYPE_QDICT) {
> >> +return qdict_get(qobject_to_qdict(qobj), name);
> >> +} else if (qiv->nb_stack>  0&&  qobject_type(qobj) == QTYPE_QLIST) {
> >> +return qlist_entry_obj(qiv->stack[qiv->nb_stack - 1].entry);
> >> +}
> >> +
> >> +return qobj;
> >> +}
> >> +
> >> +static void qmp_input_push(QmpInputVisitor *qiv, const QObject *obj, 
> >> Error **errp)
> >> +{
> >> +qiv->stack[qiv->nb_stack].obj = obj;
> >> +if (qobject_type(obj) == QTYPE_QLIST) {
> >> +qiv->stack[qiv->nb_stack].entry = 
> >> qlist_first(qobject_to_qlist(obj));
> >> +}
> >> +qiv->nb_stack++;
> >> +
> >> +if (qiv->nb_stack>= QIV_STACK_SIZE) {
> >> +error_set(errp, QERR_BUFFER_OVERRUN);
> >> +return;
> >> +}
> >> +}
> >> +
> >> +static void qmp_input_pop(QmpInputVisitor *qiv, Error **errp)
> >> +{
> >> +qiv->nb_stack--;
> >> +if (qiv->nb_stack<  0) {
> >> +error_set(errp, QERR_BUFFER_OVERRUN);
> >> +return;
> >> +}
> >> +}
> >> +
> >> +static void qmp_input_start_struct(Visitor *v, void **obj, const char 
> >> *kind, const char *name, size_t size, Error **errp)
> >> +{
> >> +QmpInputVisitor *qiv = to_qiv(v);
> >> +const QObject *qobj = qmp_input_get_object(qiv, name);
> >> +
> >> +if (!qobj || qobject_type(qobj) != QTYPE_QDICT) {
> >> +error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : 
> >> "null", "QDict");
> >> +return;
> >> +}
> >> +
> >> +qmp_input_push(qiv, qobj, errp);
> >> +if (error_is_set(errp)) {
> >> +return;
> >> +}
> >> +
> >> +if (obj) {
> >> +*obj = qemu_mallocz(size);
> >> +}
> >> +}
> >> +
> >> +static void qmp_input_end_struct(Visitor *v, Error **errp)
> >> +{
> >> +QmpInputVisitor *qiv = to_qiv(v);
> >> +
> >> +qmp_input_pop(qiv, errp);
> >> +}
> >> +
> >> +static void qmp_input_start_list(Visitor *v, const char *name, Error 
> >> **errp)
> >> +{
> >> +QmpInputVisitor *qiv = to_qiv(v);
> >> +const QObj

Re: [Qemu-devel] [PATCH v5 05/18] qapi: add QMP input visitor

2011-07-11 Thread Michael Roth

On 07/07/2011 09:32 AM, Luiz Capitulino wrote:

On Tue,  5 Jul 2011 08:02:32 -0500
Michael Roth  wrote:


A type of Visiter class that is used to walk a qobject's
structure and assign each entry to the corresponding native C type.
Command marshaling function will use this to pull out QMP command
parameters recieved over the wire and pass them as native arguments
to the corresponding C functions.

Signed-off-by: Michael Roth
---
  Makefile.objs|2 +-
  qapi/qmp-input-visitor.c |  264 ++
  qapi/qmp-input-visitor.h |   27 +
  qerror.h |3 +
  4 files changed, 295 insertions(+), 1 deletions(-)
  create mode 100644 qapi/qmp-input-visitor.c
  create mode 100644 qapi/qmp-input-visitor.h

diff --git a/Makefile.objs b/Makefile.objs
index 0077014..997ecef 100644
--- a/Makefile.objs
+++ b/Makefile.objs
@@ -375,7 +375,7 @@ libcacard-y = cac.o event.o vcard.o vreader.o 
vcard_emul_nss.o vcard_emul_type.o
  ##
  # qapi

-qapi-nested-y = qapi-visit-core.o
+qapi-nested-y = qapi-visit-core.o qmp-input-visitor.o
  qapi-obj-y = $(addprefix qapi/, $(qapi-nested-y))

  vl.o: QEMU_CFLAGS+=$(GPROF_CFLAGS)
diff --git a/qapi/qmp-input-visitor.c b/qapi/qmp-input-visitor.c
new file mode 100644
index 000..80912bb
--- /dev/null
+++ b/qapi/qmp-input-visitor.c
@@ -0,0 +1,264 @@
+/*
+ * Input Visitor
+ *
+ * Copyright IBM, Corp. 2011
+ *
+ * Authors:
+ *  Anthony Liguori
+ *
+ * This work is licensed under the terms of the GNU LGPL, version 2.1 or later.
+ * See the COPYING.LIB file in the top-level directory.
+ *
+ */
+
+#include "qmp-input-visitor.h"
+#include "qemu-queue.h"
+#include "qemu-common.h"
+#include "qemu-objects.h"
+#include "qerror.h"
+
+#define QIV_STACK_SIZE 1024
+
+typedef struct StackObject
+{
+const QObject *obj;
+const  QListEntry *entry;
+} StackObject;
+
+struct QmpInputVisitor
+{
+Visitor visitor;
+const QObject *obj;
+StackObject stack[QIV_STACK_SIZE];
+int nb_stack;
+};
+
+static QmpInputVisitor *to_qiv(Visitor *v)
+{
+return container_of(v, QmpInputVisitor, visitor);
+}
+
+static const QObject *qmp_input_get_object(QmpInputVisitor *qiv, const char 
*name)
+{
+const QObject *qobj;
+
+if (qiv->nb_stack == 0) {
+qobj = qiv->obj;
+} else {
+qobj = qiv->stack[qiv->nb_stack - 1].obj;
+}
+
+if (name&&  qobject_type(qobj) == QTYPE_QDICT) {
+return qdict_get(qobject_to_qdict(qobj), name);
+} else if (qiv->nb_stack>  0&&  qobject_type(qobj) == QTYPE_QLIST) {
+return qlist_entry_obj(qiv->stack[qiv->nb_stack - 1].entry);
+}
+
+return qobj;
+}
+
+static void qmp_input_push(QmpInputVisitor *qiv, const QObject *obj, Error 
**errp)
+{
+qiv->stack[qiv->nb_stack].obj = obj;
+if (qobject_type(obj) == QTYPE_QLIST) {
+qiv->stack[qiv->nb_stack].entry = qlist_first(qobject_to_qlist(obj));
+}
+qiv->nb_stack++;
+
+if (qiv->nb_stack>= QIV_STACK_SIZE) {
+error_set(errp, QERR_BUFFER_OVERRUN);
+return;
+}
+}
+
+static void qmp_input_pop(QmpInputVisitor *qiv, Error **errp)
+{
+qiv->nb_stack--;
+if (qiv->nb_stack<  0) {
+error_set(errp, QERR_BUFFER_OVERRUN);
+return;
+}
+}
+
+static void qmp_input_start_struct(Visitor *v, void **obj, const char *kind, 
const char *name, size_t size, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+const QObject *qobj = qmp_input_get_object(qiv, name);
+
+if (!qobj || qobject_type(qobj) != QTYPE_QDICT) {
+error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
"QDict");
+return;
+}
+
+qmp_input_push(qiv, qobj, errp);
+if (error_is_set(errp)) {
+return;
+}
+
+if (obj) {
+*obj = qemu_mallocz(size);
+}
+}
+
+static void qmp_input_end_struct(Visitor *v, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+
+qmp_input_pop(qiv, errp);
+}
+
+static void qmp_input_start_list(Visitor *v, const char *name, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+const QObject *qobj = qmp_input_get_object(qiv, name);
+
+if (!qobj || qobject_type(qobj) != QTYPE_QLIST) {
+error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
"list");
+return;
+}
+
+qmp_input_push(qiv, qobj, errp);
+}
+
+static GenericList *qmp_input_next_list(Visitor *v, GenericList **list, Error 
**errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+GenericList *entry;
+StackObject *so =&qiv->stack[qiv->nb_stack - 1];
+
+if (so->entry == NULL) {
+return NULL;
+}
+
+entry = qemu_mallocz(sizeof(*entry));
+if (*list) {
+so->entry = qlist_next(so->entry);
+if (so->entry == NULL) {
+qemu_free(entry);
+return NULL;
+}
+(*list)->next = entry;
+}
+*list = entry;
+
+
+return entry;
+}
+
+static void qmp_input_end_li

Re: [Qemu-devel] [PATCH v5 05/18] qapi: add QMP input visitor

2011-07-07 Thread Luiz Capitulino
On Tue,  5 Jul 2011 08:02:32 -0500
Michael Roth  wrote:

> A type of Visiter class that is used to walk a qobject's
> structure and assign each entry to the corresponding native C type.
> Command marshaling function will use this to pull out QMP command
> parameters recieved over the wire and pass them as native arguments
> to the corresponding C functions.
> 
> Signed-off-by: Michael Roth 
> ---
>  Makefile.objs|2 +-
>  qapi/qmp-input-visitor.c |  264 
> ++
>  qapi/qmp-input-visitor.h |   27 +
>  qerror.h |3 +
>  4 files changed, 295 insertions(+), 1 deletions(-)
>  create mode 100644 qapi/qmp-input-visitor.c
>  create mode 100644 qapi/qmp-input-visitor.h
> 
> diff --git a/Makefile.objs b/Makefile.objs
> index 0077014..997ecef 100644
> --- a/Makefile.objs
> +++ b/Makefile.objs
> @@ -375,7 +375,7 @@ libcacard-y = cac.o event.o vcard.o vreader.o 
> vcard_emul_nss.o vcard_emul_type.o
>  ##
>  # qapi
>  
> -qapi-nested-y = qapi-visit-core.o
> +qapi-nested-y = qapi-visit-core.o qmp-input-visitor.o
>  qapi-obj-y = $(addprefix qapi/, $(qapi-nested-y))
>  
>  vl.o: QEMU_CFLAGS+=$(GPROF_CFLAGS)
> diff --git a/qapi/qmp-input-visitor.c b/qapi/qmp-input-visitor.c
> new file mode 100644
> index 000..80912bb
> --- /dev/null
> +++ b/qapi/qmp-input-visitor.c
> @@ -0,0 +1,264 @@
> +/*
> + * Input Visitor
> + *
> + * Copyright IBM, Corp. 2011
> + *
> + * Authors:
> + *  Anthony Liguori   
> + *
> + * This work is licensed under the terms of the GNU LGPL, version 2.1 or 
> later.
> + * See the COPYING.LIB file in the top-level directory.
> + *
> + */
> +
> +#include "qmp-input-visitor.h"
> +#include "qemu-queue.h"
> +#include "qemu-common.h"
> +#include "qemu-objects.h"
> +#include "qerror.h"
> +
> +#define QIV_STACK_SIZE 1024
> +
> +typedef struct StackObject
> +{
> +const QObject *obj;
> +const  QListEntry *entry;
> +} StackObject;
> +
> +struct QmpInputVisitor
> +{
> +Visitor visitor;
> +const QObject *obj;
> +StackObject stack[QIV_STACK_SIZE];
> +int nb_stack;
> +};
> +
> +static QmpInputVisitor *to_qiv(Visitor *v)
> +{
> +return container_of(v, QmpInputVisitor, visitor);
> +}
> +
> +static const QObject *qmp_input_get_object(QmpInputVisitor *qiv, const char 
> *name)
> +{
> +const QObject *qobj;
> +
> +if (qiv->nb_stack == 0) {
> +qobj = qiv->obj;
> +} else {
> +qobj = qiv->stack[qiv->nb_stack - 1].obj;
> +}
> +
> +if (name && qobject_type(qobj) == QTYPE_QDICT) {
> +return qdict_get(qobject_to_qdict(qobj), name);
> +} else if (qiv->nb_stack > 0 && qobject_type(qobj) == QTYPE_QLIST) {
> +return qlist_entry_obj(qiv->stack[qiv->nb_stack - 1].entry);
> +}
> +
> +return qobj;
> +}
> +
> +static void qmp_input_push(QmpInputVisitor *qiv, const QObject *obj, Error 
> **errp)
> +{
> +qiv->stack[qiv->nb_stack].obj = obj;
> +if (qobject_type(obj) == QTYPE_QLIST) {
> +qiv->stack[qiv->nb_stack].entry = qlist_first(qobject_to_qlist(obj));
> +}
> +qiv->nb_stack++;
> +
> +if (qiv->nb_stack >= QIV_STACK_SIZE) {
> +error_set(errp, QERR_BUFFER_OVERRUN);
> +return;
> +}
> +}
> +
> +static void qmp_input_pop(QmpInputVisitor *qiv, Error **errp)
> +{
> +qiv->nb_stack--;
> +if (qiv->nb_stack < 0) {
> +error_set(errp, QERR_BUFFER_OVERRUN);
> +return;
> +}
> +}
> +
> +static void qmp_input_start_struct(Visitor *v, void **obj, const char *kind, 
> const char *name, size_t size, Error **errp)
> +{
> +QmpInputVisitor *qiv = to_qiv(v);
> +const QObject *qobj = qmp_input_get_object(qiv, name);
> +
> +if (!qobj || qobject_type(qobj) != QTYPE_QDICT) {
> +error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
> "QDict");
> +return;
> +}
> +
> +qmp_input_push(qiv, qobj, errp);
> +if (error_is_set(errp)) {
> +return;
> +}
> +
> +if (obj) {
> +*obj = qemu_mallocz(size);
> +}
> +}
> +
> +static void qmp_input_end_struct(Visitor *v, Error **errp)
> +{
> +QmpInputVisitor *qiv = to_qiv(v);
> +
> +qmp_input_pop(qiv, errp);
> +}
> +
> +static void qmp_input_start_list(Visitor *v, const char *name, Error **errp)
> +{
> +QmpInputVisitor *qiv = to_qiv(v);
> +const QObject *qobj = qmp_input_get_object(qiv, name);
> +
> +if (!qobj || qobject_type(qobj) != QTYPE_QLIST) {
> +error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
> "list");
> +return;
> +}
> +
> +qmp_input_push(qiv, qobj, errp);
> +}
> +
> +static GenericList *qmp_input_next_list(Visitor *v, GenericList **list, 
> Error **errp)
> +{
> +QmpInputVisitor *qiv = to_qiv(v);
> +GenericList *entry;
> +StackObject *so = &qiv->stack[qiv->nb_stack - 1];
> +
> +if (so->entry == NULL) {
> +return NULL;
> +}
> +
> +entry = qemu_ma

Re: [Qemu-devel] [PATCH v5 05/18] qapi: add QMP input visitor

2011-07-07 Thread Michael Roth

On 07/07/2011 09:32 AM, Luiz Capitulino wrote:

On Tue,  5 Jul 2011 08:02:32 -0500
Michael Roth  wrote:


A type of Visiter class that is used to walk a qobject's
structure and assign each entry to the corresponding native C type.
Command marshaling function will use this to pull out QMP command
parameters recieved over the wire and pass them as native arguments
to the corresponding C functions.

Signed-off-by: Michael Roth
---
  Makefile.objs|2 +-
  qapi/qmp-input-visitor.c |  264 ++
  qapi/qmp-input-visitor.h |   27 +
  qerror.h |3 +
  4 files changed, 295 insertions(+), 1 deletions(-)
  create mode 100644 qapi/qmp-input-visitor.c
  create mode 100644 qapi/qmp-input-visitor.h

diff --git a/Makefile.objs b/Makefile.objs
index 0077014..997ecef 100644
--- a/Makefile.objs
+++ b/Makefile.objs
@@ -375,7 +375,7 @@ libcacard-y = cac.o event.o vcard.o vreader.o 
vcard_emul_nss.o vcard_emul_type.o
  ##
  # qapi

-qapi-nested-y = qapi-visit-core.o
+qapi-nested-y = qapi-visit-core.o qmp-input-visitor.o
  qapi-obj-y = $(addprefix qapi/, $(qapi-nested-y))

  vl.o: QEMU_CFLAGS+=$(GPROF_CFLAGS)
diff --git a/qapi/qmp-input-visitor.c b/qapi/qmp-input-visitor.c
new file mode 100644
index 000..80912bb
--- /dev/null
+++ b/qapi/qmp-input-visitor.c
@@ -0,0 +1,264 @@
+/*
+ * Input Visitor
+ *
+ * Copyright IBM, Corp. 2011
+ *
+ * Authors:
+ *  Anthony Liguori
+ *
+ * This work is licensed under the terms of the GNU LGPL, version 2.1 or later.
+ * See the COPYING.LIB file in the top-level directory.
+ *
+ */
+
+#include "qmp-input-visitor.h"
+#include "qemu-queue.h"
+#include "qemu-common.h"
+#include "qemu-objects.h"
+#include "qerror.h"
+
+#define QIV_STACK_SIZE 1024
+
+typedef struct StackObject
+{
+const QObject *obj;
+const  QListEntry *entry;
+} StackObject;
+
+struct QmpInputVisitor
+{
+Visitor visitor;
+const QObject *obj;
+StackObject stack[QIV_STACK_SIZE];
+int nb_stack;
+};
+
+static QmpInputVisitor *to_qiv(Visitor *v)
+{
+return container_of(v, QmpInputVisitor, visitor);
+}
+
+static const QObject *qmp_input_get_object(QmpInputVisitor *qiv, const char 
*name)
+{
+const QObject *qobj;
+
+if (qiv->nb_stack == 0) {
+qobj = qiv->obj;
+} else {
+qobj = qiv->stack[qiv->nb_stack - 1].obj;
+}
+
+if (name&&  qobject_type(qobj) == QTYPE_QDICT) {
+return qdict_get(qobject_to_qdict(qobj), name);
+} else if (qiv->nb_stack>  0&&  qobject_type(qobj) == QTYPE_QLIST) {
+return qlist_entry_obj(qiv->stack[qiv->nb_stack - 1].entry);
+}
+
+return qobj;
+}
+
+static void qmp_input_push(QmpInputVisitor *qiv, const QObject *obj, Error 
**errp)
+{
+qiv->stack[qiv->nb_stack].obj = obj;
+if (qobject_type(obj) == QTYPE_QLIST) {
+qiv->stack[qiv->nb_stack].entry = qlist_first(qobject_to_qlist(obj));
+}
+qiv->nb_stack++;
+
+if (qiv->nb_stack>= QIV_STACK_SIZE) {
+error_set(errp, QERR_BUFFER_OVERRUN);
+return;
+}
+}
+
+static void qmp_input_pop(QmpInputVisitor *qiv, Error **errp)
+{
+qiv->nb_stack--;
+if (qiv->nb_stack<  0) {
+error_set(errp, QERR_BUFFER_OVERRUN);
+return;
+}
+}
+
+static void qmp_input_start_struct(Visitor *v, void **obj, const char *kind, 
const char *name, size_t size, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+const QObject *qobj = qmp_input_get_object(qiv, name);
+
+if (!qobj || qobject_type(qobj) != QTYPE_QDICT) {
+error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
"QDict");
+return;
+}
+
+qmp_input_push(qiv, qobj, errp);
+if (error_is_set(errp)) {
+return;
+}
+
+if (obj) {
+*obj = qemu_mallocz(size);
+}
+}
+
+static void qmp_input_end_struct(Visitor *v, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+
+qmp_input_pop(qiv, errp);
+}
+
+static void qmp_input_start_list(Visitor *v, const char *name, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+const QObject *qobj = qmp_input_get_object(qiv, name);
+
+if (!qobj || qobject_type(qobj) != QTYPE_QLIST) {
+error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
"list");
+return;
+}
+
+qmp_input_push(qiv, qobj, errp);
+}
+
+static GenericList *qmp_input_next_list(Visitor *v, GenericList **list, Error 
**errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+GenericList *entry;
+StackObject *so =&qiv->stack[qiv->nb_stack - 1];
+
+if (so->entry == NULL) {
+return NULL;
+}
+
+entry = qemu_mallocz(sizeof(*entry));
+if (*list) {
+so->entry = qlist_next(so->entry);
+if (so->entry == NULL) {
+qemu_free(entry);
+return NULL;
+}
+(*list)->next = entry;
+}
+*list = entry;
+
+
+return entry;
+}
+
+static void qmp_input_end_li

[Qemu-devel] [PATCH v5 05/18] qapi: add QMP input visitor

2011-07-05 Thread Michael Roth
A type of Visiter class that is used to walk a qobject's
structure and assign each entry to the corresponding native C type.
Command marshaling function will use this to pull out QMP command
parameters recieved over the wire and pass them as native arguments
to the corresponding C functions.

Signed-off-by: Michael Roth 
---
 Makefile.objs|2 +-
 qapi/qmp-input-visitor.c |  264 ++
 qapi/qmp-input-visitor.h |   27 +
 qerror.h |3 +
 4 files changed, 295 insertions(+), 1 deletions(-)
 create mode 100644 qapi/qmp-input-visitor.c
 create mode 100644 qapi/qmp-input-visitor.h

diff --git a/Makefile.objs b/Makefile.objs
index 0077014..997ecef 100644
--- a/Makefile.objs
+++ b/Makefile.objs
@@ -375,7 +375,7 @@ libcacard-y = cac.o event.o vcard.o vreader.o 
vcard_emul_nss.o vcard_emul_type.o
 ##
 # qapi
 
-qapi-nested-y = qapi-visit-core.o
+qapi-nested-y = qapi-visit-core.o qmp-input-visitor.o
 qapi-obj-y = $(addprefix qapi/, $(qapi-nested-y))
 
 vl.o: QEMU_CFLAGS+=$(GPROF_CFLAGS)
diff --git a/qapi/qmp-input-visitor.c b/qapi/qmp-input-visitor.c
new file mode 100644
index 000..80912bb
--- /dev/null
+++ b/qapi/qmp-input-visitor.c
@@ -0,0 +1,264 @@
+/*
+ * Input Visitor
+ *
+ * Copyright IBM, Corp. 2011
+ *
+ * Authors:
+ *  Anthony Liguori   
+ *
+ * This work is licensed under the terms of the GNU LGPL, version 2.1 or later.
+ * See the COPYING.LIB file in the top-level directory.
+ *
+ */
+
+#include "qmp-input-visitor.h"
+#include "qemu-queue.h"
+#include "qemu-common.h"
+#include "qemu-objects.h"
+#include "qerror.h"
+
+#define QIV_STACK_SIZE 1024
+
+typedef struct StackObject
+{
+const QObject *obj;
+const  QListEntry *entry;
+} StackObject;
+
+struct QmpInputVisitor
+{
+Visitor visitor;
+const QObject *obj;
+StackObject stack[QIV_STACK_SIZE];
+int nb_stack;
+};
+
+static QmpInputVisitor *to_qiv(Visitor *v)
+{
+return container_of(v, QmpInputVisitor, visitor);
+}
+
+static const QObject *qmp_input_get_object(QmpInputVisitor *qiv, const char 
*name)
+{
+const QObject *qobj;
+
+if (qiv->nb_stack == 0) {
+qobj = qiv->obj;
+} else {
+qobj = qiv->stack[qiv->nb_stack - 1].obj;
+}
+
+if (name && qobject_type(qobj) == QTYPE_QDICT) {
+return qdict_get(qobject_to_qdict(qobj), name);
+} else if (qiv->nb_stack > 0 && qobject_type(qobj) == QTYPE_QLIST) {
+return qlist_entry_obj(qiv->stack[qiv->nb_stack - 1].entry);
+}
+
+return qobj;
+}
+
+static void qmp_input_push(QmpInputVisitor *qiv, const QObject *obj, Error 
**errp)
+{
+qiv->stack[qiv->nb_stack].obj = obj;
+if (qobject_type(obj) == QTYPE_QLIST) {
+qiv->stack[qiv->nb_stack].entry = qlist_first(qobject_to_qlist(obj));
+}
+qiv->nb_stack++;
+
+if (qiv->nb_stack >= QIV_STACK_SIZE) {
+error_set(errp, QERR_BUFFER_OVERRUN);
+return;
+}
+}
+
+static void qmp_input_pop(QmpInputVisitor *qiv, Error **errp)
+{
+qiv->nb_stack--;
+if (qiv->nb_stack < 0) {
+error_set(errp, QERR_BUFFER_OVERRUN);
+return;
+}
+}
+
+static void qmp_input_start_struct(Visitor *v, void **obj, const char *kind, 
const char *name, size_t size, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+const QObject *qobj = qmp_input_get_object(qiv, name);
+
+if (!qobj || qobject_type(qobj) != QTYPE_QDICT) {
+error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
"QDict");
+return;
+}
+
+qmp_input_push(qiv, qobj, errp);
+if (error_is_set(errp)) {
+return;
+}
+
+if (obj) {
+*obj = qemu_mallocz(size);
+}
+}
+
+static void qmp_input_end_struct(Visitor *v, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+
+qmp_input_pop(qiv, errp);
+}
+
+static void qmp_input_start_list(Visitor *v, const char *name, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+const QObject *qobj = qmp_input_get_object(qiv, name);
+
+if (!qobj || qobject_type(qobj) != QTYPE_QLIST) {
+error_set(errp, QERR_INVALID_PARAMETER_TYPE, name ? name : "null", 
"list");
+return;
+}
+
+qmp_input_push(qiv, qobj, errp);
+}
+
+static GenericList *qmp_input_next_list(Visitor *v, GenericList **list, Error 
**errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+GenericList *entry;
+StackObject *so = &qiv->stack[qiv->nb_stack - 1];
+
+if (so->entry == NULL) {
+return NULL;
+}
+
+entry = qemu_mallocz(sizeof(*entry));
+if (*list) {
+so->entry = qlist_next(so->entry);
+if (so->entry == NULL) {
+qemu_free(entry);
+return NULL;
+}
+(*list)->next = entry;
+}
+*list = entry;
+
+
+return entry;
+}
+
+static void qmp_input_end_list(Visitor *v, Error **errp)
+{
+QmpInputVisitor *qiv = to_qiv(v);
+
+qmp_input_pop(qiv, errp);
+}
+
+