All of lore.kernel.org
 help / color / mirror / Atom feed
* [Qemu-devel] [PATCH v2 00/35]: add new error format
@ 2012-08-07 15:53 Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 01/35] monitor: drop unused monitor debug code Luiz Capitulino
                   ` (34 more replies)
  0 siblings, 35 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

v2

 o rebase on top of master
 o fix linux-user build breakage
 o maintain DeviceEncrypted error and let hmp_change() use it
 o drop patch that changed inet_connect() and inet_connect_opts()
   to return -errno
 o Simplified tcp_start_outgoing_migration() error handling
 o use g_strdup_vprintf() (instead of vsnprintf() plus g_strdup())
 o drop errors from command's documentation in qapi-schema.json
 o update docs/writing-qmp-commands.txt

This series implements the 'Plan for error handling in QMP' as described
by Anthony in this email:

    http://lists.gnu.org/archive/html/qemu-devel/2012-07/msg03764.html

Basically, this replaces almost all error classes by GenericError (the
exception are a few error classes used by libvirt) and drops the error
data memeber. This also adds a free form string to error_set().

On the wire, we go from:

    { "error": { "class": "DeviceNotRemovable",
                 "data": { "device": "virtio0" },
                 "desc": "Device 'virtio0' is not removable" } }

to:

     { "error": { "class": "GenericError",
                  "desc": "Device 'virtio0' is not removable" } }

Internally, we go from:

  void error_set(Error **err, const char *fmt, ...);

to:

  void error_set(Error **err, ErrorClass err_class, const char *fmt, ...);

 Makefile.objs                 |   1 +
 QMP/qmp-spec.txt              |  10 +-
 block.c                       |   1 +
 block_int.h                   |   1 +
 configure                     |  10 -
 docs/writing-qmp-commands.txt |  47 ++--
 error.c                       |  93 +-------
 error.h                       |  34 +--
 error_int.h                   |  29 ---
 hmp.c                         |  75 +++---
 hmp.h                         |   1 +
 migration-tcp.c               |  22 +-
 monitor.c                     |  83 ++-----
 nbd.c                         |   2 +-
 qapi-schema.json              |  93 +++-----
 qapi/qmp-core.h               |   1 +
 qapi/qmp-dispatch.c           |  11 +-
 qemu-char.c                   |   2 +-
 qemu-ga.c                     |   5 +-
 qemu-sockets.c                |  14 +-
 qemu_socket.h                 |   4 +-
 qerror.c                      | 516 ++----------------------------------------
 qerror.h                      | 168 ++++++--------
 qmp-commands.hx               |   4 +-
 scripts/qapi-types.py         |  17 +-
 ui/vnc.c                      |   2 +-
 26 files changed, 272 insertions(+), 974 deletions(-)

^ permalink raw reply	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 01/35] monitor: drop unused monitor debug code
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 02/35] qerror: QERR_AMBIGUOUS_PATH: drop %(object) from human msg Luiz Capitulino
                   ` (33 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

In the old QMP days, this code was used to find out QMP commands that
might be calling monitor_printf() down its call chain.

This is almost impossible to happen today, because the qapi converted
commands don't even have a monitor object. Besides, it's been more than
a year since I used this last time.

Let's just drop it.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 configure | 10 ----------
 monitor.c | 65 ---------------------------------------------------------------
 2 files changed, 75 deletions(-)

diff --git a/configure b/configure
index 280726c..030d137 100755
--- a/configure
+++ b/configure
@@ -147,7 +147,6 @@ vhost_net="no"
 kvm="no"
 gprof="no"
 debug_tcg="no"
-debug_mon="no"
 debug="no"
 strip_opt="yes"
 tcg_interpreter="no"
@@ -633,14 +632,9 @@ for opt do
   ;;
   --disable-debug-tcg) debug_tcg="no"
   ;;
-  --enable-debug-mon) debug_mon="yes"
-  ;;
-  --disable-debug-mon) debug_mon="no"
-  ;;
   --enable-debug)
       # Enable debugging options that aren't excessively noisy
       debug_tcg="yes"
-      debug_mon="yes"
       debug="yes"
       strip_opt="no"
   ;;
@@ -3039,7 +3033,6 @@ echo "host CPU          $cpu"
 echo "host big endian   $bigendian"
 echo "target list       $target_list"
 echo "tcg debug enabled $debug_tcg"
-echo "Mon debug enabled $debug_mon"
 echo "gprof enabled     $gprof"
 echo "sparse enabled    $sparse"
 echo "strip binaries    $strip_opt"
@@ -3132,9 +3125,6 @@ echo "ARCH=$ARCH" >> $config_host_mak
 if test "$debug_tcg" = "yes" ; then
   echo "CONFIG_DEBUG_TCG=y" >> $config_host_mak
 fi
-if test "$debug_mon" = "yes" ; then
-  echo "CONFIG_DEBUG_MONITOR=y" >> $config_host_mak
-fi
 if test "$debug" = "yes" ; then
   echo "CONFIG_DEBUG_EXEC=y" >> $config_host_mak
 fi
diff --git a/monitor.c b/monitor.c
index 49dccfe..aa57167 100644
--- a/monitor.c
+++ b/monitor.c
@@ -172,41 +172,11 @@ struct Monitor {
     CPUArchState *mon_cpu;
     BlockDriverCompletionFunc *password_completion_cb;
     void *password_opaque;
-#ifdef CONFIG_DEBUG_MONITOR
-    int print_calls_nr;
-#endif
     QError *error;
     QLIST_HEAD(,mon_fd_t) fds;
     QLIST_ENTRY(Monitor) entry;
 };
 
-#ifdef CONFIG_DEBUG_MONITOR
-#define MON_DEBUG(fmt, ...) do {    \
-    fprintf(stderr, "Monitor: ");       \
-    fprintf(stderr, fmt, ## __VA_ARGS__); } while (0)
-
-static inline void mon_print_count_inc(Monitor *mon)
-{
-    mon->print_calls_nr++;
-}
-
-static inline void mon_print_count_init(Monitor *mon)
-{
-    mon->print_calls_nr = 0;
-}
-
-static inline int mon_print_count_get(const Monitor *mon)
-{
-    return mon->print_calls_nr;
-}
-
-#else /* !CONFIG_DEBUG_MONITOR */
-#define MON_DEBUG(fmt, ...) do { } while (0)
-static inline void mon_print_count_inc(Monitor *mon) { }
-static inline void mon_print_count_init(Monitor *mon) { }
-static inline int mon_print_count_get(const Monitor *mon) { return 0; }
-#endif /* CONFIG_DEBUG_MONITOR */
-
 /* QMP checker flags */
 #define QMP_ACCEPT_UNKNOWNS 1
 
@@ -299,8 +269,6 @@ void monitor_vprintf(Monitor *mon, const char *fmt, va_list ap)
     if (!mon)
         return;
 
-    mon_print_count_inc(mon);
-
     if (monitor_ctrl_mode(mon)) {
         return;
     }
@@ -3860,8 +3828,6 @@ void monitor_set_error(Monitor *mon, QError *qerror)
     if (!mon->error) {
         mon->error = qerror;
     } else {
-        MON_DEBUG("Additional error report at %s:%d\n",
-                  qerror->file, qerror->linenr);
         QDECREF(qerror);
     }
 }
@@ -3875,36 +3841,7 @@ static void handler_audit(Monitor *mon, const mon_cmd_t *cmd, int ret)
          * Action: Report an internal error to the client if in QMP.
          */
         qerror_report(QERR_UNDEFINED_ERROR);
-        MON_DEBUG("command '%s' returned failure but did not pass an error\n",
-                  cmd->name);
     }
-
-#ifdef CONFIG_DEBUG_MONITOR
-    if (!ret && monitor_has_error(mon)) {
-        /*
-         * If it returns success, it must not have passed an error.
-         *
-         * Action: Report the passed error to the client.
-         */
-        MON_DEBUG("command '%s' returned success but passed an error\n",
-                  cmd->name);
-    }
-
-    if (mon_print_count_get(mon) > 0 && strcmp(cmd->name, "info") != 0) {
-        /*
-         * Handlers should not call Monitor print functions.
-         *
-         * Action: Ignore them in QMP.
-         *
-         * (XXX: we don't check any 'info' or 'query' command here
-         * because the user print function _is_ called by do_info(), hence
-         * we will trigger this check. This problem will go away when we
-         * make 'query' commands real and kill do_info())
-         */
-        MON_DEBUG("command '%s' called print functions %d time(s)\n",
-                  cmd->name, mon_print_count_get(mon));
-    }
-#endif
 }
 
 static void handle_user_command(Monitor *mon, const char *cmdline)
@@ -4433,8 +4370,6 @@ static void qmp_call_cmd(Monitor *mon, const mon_cmd_t *cmd,
     int ret;
     QObject *data = NULL;
 
-    mon_print_count_init(mon);
-
     ret = cmd->mhandler.cmd_new(mon, params, &data);
     handler_audit(mon, cmd, ret);
     monitor_protocol_emitter(mon, data);
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 02/35] qerror: QERR_AMBIGUOUS_PATH: drop %(object) from human msg
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 01/35] monitor: drop unused monitor debug code Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 03/35] qerror: QERR_DEVICE_ENCRYPTED: change error message Luiz Capitulino
                   ` (32 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Actually, renames it to 'object'. This must be what the original author
meant to write, as there's no 'object' in the error's data member.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qerror.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/qerror.c b/qerror.c
index 92c4eff..082de98 100644
--- a/qerror.c
+++ b/qerror.c
@@ -49,7 +49,7 @@ static const QErrorStringTable qerror_table[] = {
     },
     {
         .error_fmt = QERR_AMBIGUOUS_PATH,
-        .desc      = "Path '%(path)' does not uniquely identify a %(object)"
+        .desc      = "Path '%(path)' does not uniquely identify an object"
     },
     {
         .error_fmt = QERR_BAD_BUS_FOR_DEVICE,
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 03/35] qerror: QERR_DEVICE_ENCRYPTED: change error message
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 01/35] monitor: drop unused monitor debug code Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 02/35] qerror: QERR_AMBIGUOUS_PATH: drop %(object) from human msg Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 04/35] qerror: reduce public exposure Luiz Capitulino
                   ` (31 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Match what HMP commands print on DeviceEncrypted errors.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qerror.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/qerror.c b/qerror.c
index 082de98..de0a79e 100644
--- a/qerror.c
+++ b/qerror.c
@@ -81,7 +81,7 @@ static const QErrorStringTable qerror_table[] = {
     },
     {
         .error_fmt = QERR_DEVICE_ENCRYPTED,
-        .desc      = "Device '%(device)' is encrypted",
+        .desc      = "'%(device)' (%(filename)) is encrypted",
     },
     {
         .error_fmt = QERR_DEVICE_FEATURE_BLOCKS_MIGRATION,
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 04/35] qerror: reduce public exposure
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (2 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 03/35] qerror: QERR_DEVICE_ENCRYPTED: change error message Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 05/35] qerror: drop qerror_abort() Luiz Capitulino
                   ` (30 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

qerror will be dropped in a near future, let's reduce its public
exposure by making functions only used in qerror.c static.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qerror.c | 10 +++++-----
 qerror.h |  5 -----
 2 files changed, 5 insertions(+), 10 deletions(-)

diff --git a/qerror.c b/qerror.c
index de0a79e..bfb875a 100644
--- a/qerror.c
+++ b/qerror.c
@@ -336,7 +336,7 @@ static const QErrorStringTable qerror_table[] = {
  *
  * Return strong reference.
  */
-QError *qerror_new(void)
+static QError *qerror_new(void)
 {
     QError *qerr;
 
@@ -424,8 +424,8 @@ static void qerror_set_desc(QError *qerr, const char *fmt)
  *
  * Return strong reference.
  */
-QError *qerror_from_info(const char *file, int linenr, const char *func,
-                         const char *fmt, va_list *va)
+static QError *qerror_from_info(const char *file, int linenr, const char *func,
+                                const char *fmt, va_list *va)
 {
     QError *qerr;
 
@@ -549,7 +549,7 @@ QString *qerror_human(const QError *qerror)
  * it uses error_report() for this, so that the output is routed to the right
  * place (ie. stderr or Monitor's device).
  */
-void qerror_print(QError *qerror)
+static void qerror_print(QError *qerror)
 {
     QString *qstring = qerror_human(qerror);
     loc_push_restore(&qerror->loc);
@@ -620,7 +620,7 @@ void assert_no_error(Error *err)
 /**
  * qobject_to_qerror(): Convert a QObject into a QError
  */
-QError *qobject_to_qerror(const QObject *obj)
+static QError *qobject_to_qerror(const QObject *obj)
 {
     if (qobject_type(obj) != QTYPE_QERROR) {
         return NULL;
diff --git a/qerror.h b/qerror.h
index b4c8758..fe8870c 100644
--- a/qerror.h
+++ b/qerror.h
@@ -33,11 +33,7 @@ typedef struct QError {
     const QErrorStringTable *entry;
 } QError;
 
-QError *qerror_new(void);
-QError *qerror_from_info(const char *file, int linenr, const char *func,
-                         const char *fmt, va_list *va) GCC_FMT_ATTR(4, 0);
 QString *qerror_human(const QError *qerror);
-void qerror_print(QError *qerror);
 void qerror_report_internal(const char *file, int linenr, const char *func,
                             const char *fmt, ...) GCC_FMT_ATTR(4, 5);
 void qerror_report_err(Error *err);
@@ -45,7 +41,6 @@ void assert_no_error(Error *err);
 QString *qerror_format(const char *fmt, QDict *error);
 #define qerror_report(fmt, ...) \
     qerror_report_internal(__FILE__, __LINE__, __func__, fmt, ## __VA_ARGS__)
-QError *qobject_to_qerror(const QObject *obj);
 
 /*
  * QError class list
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 05/35] qerror: drop qerror_abort()
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (3 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 04/35] qerror: reduce public exposure Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 06/35] qerror: avoid passing qerr pointer Luiz Capitulino
                   ` (29 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

qerror_abort() depends on the 'file', 'func' and 'linenr' members of
QError. However, these members are going to be dropped by the next
commit, so let's drop qerror_abort() in favor of printing an error
message to stderr plus a call to abort().

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qerror.c | 41 ++++++++++++++---------------------------
 1 file changed, 14 insertions(+), 27 deletions(-)

diff --git a/qerror.c b/qerror.c
index bfb875a..7cb7c12 100644
--- a/qerror.c
+++ b/qerror.c
@@ -346,22 +346,6 @@ static QError *qerror_new(void)
     return qerr;
 }
 
-static void GCC_FMT_ATTR(2, 3) qerror_abort(const QError *qerr,
-                                            const char *fmt, ...)
-{
-    va_list ap;
-
-    fprintf(stderr, "qerror: bad call in function '%s':\n", qerr->func);
-    fprintf(stderr, "qerror: -> ");
-
-    va_start(ap, fmt);
-    vfprintf(stderr, fmt, ap);
-    va_end(ap);
-
-    fprintf(stderr, "\nqerror: call at %s:%d\n", qerr->file, qerr->linenr);
-    abort();
-}
-
 static void GCC_FMT_ATTR(2, 0) qerror_set_data(QError *qerr,
                                                const char *fmt, va_list *va)
 {
@@ -369,28 +353,34 @@ static void GCC_FMT_ATTR(2, 0) qerror_set_data(QError *qerr,
 
     obj = qobject_from_jsonv(fmt, va);
     if (!obj) {
-        qerror_abort(qerr, "invalid format '%s'", fmt);
+        fprintf(stderr, "invalid json in error dict '%s'\n", fmt);
+        abort();
     }
     if (qobject_type(obj) != QTYPE_QDICT) {
-        qerror_abort(qerr, "error format is not a QDict '%s'", fmt);
+        fprintf(stderr, "error is not a dict '%s'\n", fmt);
+        abort();
     }
 
     qerr->error = qobject_to_qdict(obj);
 
     obj = qdict_get(qerr->error, "class");
     if (!obj) {
-        qerror_abort(qerr, "missing 'class' key in '%s'", fmt);
+        fprintf(stderr, "missing 'class' key in '%s'\n", fmt);
+        abort();
     }
     if (qobject_type(obj) != QTYPE_QSTRING) {
-        qerror_abort(qerr, "'class' key value should be a QString");
+        fprintf(stderr, "'class' key value should be a string in '%s'\n", fmt);
+        abort();
     }
     
     obj = qdict_get(qerr->error, "data");
     if (!obj) {
-        qerror_abort(qerr, "missing 'data' key in '%s'", fmt);
+        fprintf(stderr, "missing 'data' key in '%s'\n", fmt);
+        abort();
     }
     if (qobject_type(obj) != QTYPE_QDICT) {
-        qerror_abort(qerr, "'data' key value should be a QDICT");
+        fprintf(stderr, "'data' key value should be a dict in '%s'\n", fmt);
+        abort();
     }
 }
 
@@ -407,7 +397,8 @@ static void qerror_set_desc(QError *qerr, const char *fmt)
         }
     }
 
-    qerror_abort(qerr, "error format '%s' not found", fmt);
+    fprintf(stderr, "error format '%s' not found\n", fmt);
+    abort();
 }
 
 /**
@@ -435,10 +426,6 @@ static QError *qerror_from_info(const char *file, int linenr, const char *func,
     qerr->file = file;
     qerr->func = func;
 
-    if (!fmt) {
-        qerror_abort(qerr, "QDict not specified");
-    }
-
     qerror_set_data(qerr, fmt, va);
     qerror_set_desc(qerr, fmt);
 
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 06/35] qerror: avoid passing qerr pointer
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (4 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 05/35] qerror: drop qerror_abort() Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 07/35] qerror: QError: drop file, linenr, func Luiz Capitulino
                   ` (28 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Helps dropping/modifying qerror functions.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qerror.c | 24 ++++++++++++------------
 1 file changed, 12 insertions(+), 12 deletions(-)

diff --git a/qerror.c b/qerror.c
index 7cb7c12..e717496 100644
--- a/qerror.c
+++ b/qerror.c
@@ -346,10 +346,10 @@ static QError *qerror_new(void)
     return qerr;
 }
 
-static void GCC_FMT_ATTR(2, 0) qerror_set_data(QError *qerr,
-                                               const char *fmt, va_list *va)
+static QDict *error_obj_from_fmt_no_fail(const char *fmt, va_list *va)
 {
     QObject *obj;
+    QDict *ret;
 
     obj = qobject_from_jsonv(fmt, va);
     if (!obj) {
@@ -361,9 +361,8 @@ static void GCC_FMT_ATTR(2, 0) qerror_set_data(QError *qerr,
         abort();
     }
 
-    qerr->error = qobject_to_qdict(obj);
-
-    obj = qdict_get(qerr->error, "class");
+    ret = qobject_to_qdict(obj);
+    obj = qdict_get(ret, "class");
     if (!obj) {
         fprintf(stderr, "missing 'class' key in '%s'\n", fmt);
         abort();
@@ -372,8 +371,8 @@ static void GCC_FMT_ATTR(2, 0) qerror_set_data(QError *qerr,
         fprintf(stderr, "'class' key value should be a string in '%s'\n", fmt);
         abort();
     }
-    
-    obj = qdict_get(qerr->error, "data");
+
+    obj = qdict_get(ret, "data");
     if (!obj) {
         fprintf(stderr, "missing 'data' key in '%s'\n", fmt);
         abort();
@@ -382,9 +381,11 @@ static void GCC_FMT_ATTR(2, 0) qerror_set_data(QError *qerr,
         fprintf(stderr, "'data' key value should be a dict in '%s'\n", fmt);
         abort();
     }
+
+    return ret;
 }
 
-static void qerror_set_desc(QError *qerr, const char *fmt)
+static const QErrorStringTable *get_desc_no_fail(const char *fmt)
 {
     int i;
 
@@ -392,8 +393,7 @@ static void qerror_set_desc(QError *qerr, const char *fmt)
 
     for (i = 0; qerror_table[i].error_fmt; i++) {
         if (strcmp(qerror_table[i].error_fmt, fmt) == 0) {
-            qerr->entry = &qerror_table[i];
-            return;
+            return &qerror_table[i];
         }
     }
 
@@ -426,8 +426,8 @@ static QError *qerror_from_info(const char *file, int linenr, const char *func,
     qerr->file = file;
     qerr->func = func;
 
-    qerror_set_data(qerr, fmt, va);
-    qerror_set_desc(qerr, fmt);
+    qerr->error = error_obj_from_fmt_no_fail(fmt, va);
+    qerr->entry = get_desc_no_fail(fmt);
 
     return qerr;
 }
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 07/35] qerror: QError: drop file, linenr, func
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (5 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 06/35] qerror: avoid passing qerr pointer Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 08/35] qerror: qerror_format(): return an allocated string Luiz Capitulino
                   ` (27 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

They have never been fully used and conflict with future error
improvements.

Also makes qerror_report() a proper function, as there's no point
in having it as a macro anymore.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qerror.c | 20 +++-----------------
 qerror.h |  8 +-------
 2 files changed, 4 insertions(+), 24 deletions(-)

diff --git a/qerror.c b/qerror.c
index e717496..6f9f49c 100644
--- a/qerror.c
+++ b/qerror.c
@@ -404,27 +404,14 @@ static const QErrorStringTable *get_desc_no_fail(const char *fmt)
 /**
  * qerror_from_info(): Create a new QError from error information
  *
- * The information consists of:
- *
- * - file   the file name of where the error occurred
- * - linenr the line number of where the error occurred
- * - func   the function name of where the error occurred
- * - fmt    JSON printf-like dictionary, there must exist keys 'class' and
- *          'data'
- * - va     va_list of all arguments specified by fmt
- *
  * Return strong reference.
  */
-static QError *qerror_from_info(const char *file, int linenr, const char *func,
-                                const char *fmt, va_list *va)
+static QError *qerror_from_info(const char *fmt, va_list *va)
 {
     QError *qerr;
 
     qerr = qerror_new();
     loc_save(&qerr->loc);
-    qerr->linenr = linenr;
-    qerr->file = file;
-    qerr->func = func;
 
     qerr->error = error_obj_from_fmt_no_fail(fmt, va);
     qerr->entry = get_desc_no_fail(fmt);
@@ -545,14 +532,13 @@ static void qerror_print(QError *qerror)
     QDECREF(qstring);
 }
 
-void qerror_report_internal(const char *file, int linenr, const char *func,
-                            const char *fmt, ...)
+void qerror_report(const char *fmt, ...)
 {
     va_list va;
     QError *qerror;
 
     va_start(va, fmt);
-    qerror = qerror_from_info(file, linenr, func, fmt, &va);
+    qerror = qerror_from_info(fmt, &va);
     va_end(va);
 
     if (monitor_cur_is_qmp()) {
diff --git a/qerror.h b/qerror.h
index fe8870c..3c0b14c 100644
--- a/qerror.h
+++ b/qerror.h
@@ -27,20 +27,14 @@ typedef struct QError {
     QObject_HEAD;
     QDict *error;
     Location loc;
-    int linenr;
-    const char *file;
-    const char *func;
     const QErrorStringTable *entry;
 } QError;
 
 QString *qerror_human(const QError *qerror);
-void qerror_report_internal(const char *file, int linenr, const char *func,
-                            const char *fmt, ...) GCC_FMT_ATTR(4, 5);
+void qerror_report(const char *fmt, ...) GCC_FMT_ATTR(1, 2);
 void qerror_report_err(Error *err);
 void assert_no_error(Error *err);
 QString *qerror_format(const char *fmt, QDict *error);
-#define qerror_report(fmt, ...) \
-    qerror_report_internal(__FILE__, __LINE__, __func__, fmt, ## __VA_ARGS__)
 
 /*
  * QError class list
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 08/35] qerror: qerror_format(): return an allocated string
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (6 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 07/35] qerror: QError: drop file, linenr, func Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 09/35] qerror: don't delay error message construction Luiz Capitulino
                   ` (26 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Simplifies current and future users.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 error.c  |  5 +----
 qerror.c | 10 ++++++++--
 qerror.h |  2 +-
 3 files changed, 10 insertions(+), 7 deletions(-)

diff --git a/error.c b/error.c
index 58f55a0..3a62592 100644
--- a/error.c
+++ b/error.c
@@ -65,10 +65,7 @@ bool error_is_set(Error **errp)
 const char *error_get_pretty(Error *err)
 {
     if (err->msg == NULL) {
-        QString *str;
-        str = qerror_format(err->fmt, err->obj);
-        err->msg = g_strdup(qstring_get_str(str));
-        QDECREF(str);
+        err->msg = qerror_format(err->fmt, err->obj);
     }
 
     return err->msg;
diff --git a/qerror.c b/qerror.c
index 6f9f49c..d073ed7 100644
--- a/qerror.c
+++ b/qerror.c
@@ -493,9 +493,11 @@ static QString *qerror_format_desc(QDict *error,
     return qstring;
 }
 
-QString *qerror_format(const char *fmt, QDict *error)
+char *qerror_format(const char *fmt, QDict *error)
 {
     const QErrorStringTable *entry = NULL;
+    QString *qstr;
+    char *ret;
     int i;
 
     for (i = 0; qerror_table[i].error_fmt; i++) {
@@ -505,7 +507,11 @@ QString *qerror_format(const char *fmt, QDict *error)
         }
     }
 
-    return qerror_format_desc(error, entry);
+    qstr = qerror_format_desc(error, entry);
+    ret = g_strdup(qstring_get_str(qstr));
+    QDECREF(qstr);
+
+    return ret;
 }
 
 /**
diff --git a/qerror.h b/qerror.h
index 3c0b14c..aec76b2 100644
--- a/qerror.h
+++ b/qerror.h
@@ -34,7 +34,7 @@ QString *qerror_human(const QError *qerror);
 void qerror_report(const char *fmt, ...) GCC_FMT_ATTR(1, 2);
 void qerror_report_err(Error *err);
 void assert_no_error(Error *err);
-QString *qerror_format(const char *fmt, QDict *error);
+char *qerror_format(const char *fmt, QDict *error);
 
 /*
  * QError class list
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 09/35] qerror: don't delay error message construction
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (7 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 08/35] qerror: qerror_format(): return an allocated string Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 10/35] error: " Luiz Capitulino
                   ` (25 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Today, the error message is only constructed when it's used. This commit
changes qerror to construct the error message when the error object is
built (ie. when the error is reported).

This eliminates the need of storing a pointer to qerror_table[], which
will be dropped soon, and also simplifies the code.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qerror.c | 29 ++++-------------------------
 qerror.h |  2 +-
 2 files changed, 5 insertions(+), 26 deletions(-)

diff --git a/qerror.c b/qerror.c
index d073ed7..a254f88 100644
--- a/qerror.c
+++ b/qerror.c
@@ -385,22 +385,6 @@ static QDict *error_obj_from_fmt_no_fail(const char *fmt, va_list *va)
     return ret;
 }
 
-static const QErrorStringTable *get_desc_no_fail(const char *fmt)
-{
-    int i;
-
-    // FIXME: inefficient loop
-
-    for (i = 0; qerror_table[i].error_fmt; i++) {
-        if (strcmp(qerror_table[i].error_fmt, fmt) == 0) {
-            return &qerror_table[i];
-        }
-    }
-
-    fprintf(stderr, "error format '%s' not found\n", fmt);
-    abort();
-}
-
 /**
  * qerror_from_info(): Create a new QError from error information
  *
@@ -414,7 +398,7 @@ static QError *qerror_from_info(const char *fmt, va_list *va)
     loc_save(&qerr->loc);
 
     qerr->error = error_obj_from_fmt_no_fail(fmt, va);
-    qerr->entry = get_desc_no_fail(fmt);
+    qerr->err_msg = qerror_format(fmt, qerr->error);
 
     return qerr;
 }
@@ -519,7 +503,7 @@ char *qerror_format(const char *fmt, QDict *error)
  */
 QString *qerror_human(const QError *qerror)
 {
-    return qerror_format_desc(qerror->error, qerror->entry);
+    return qstring_from_str(qerror->err_msg);
 }
 
 /**
@@ -566,19 +550,13 @@ struct Error
 void qerror_report_err(Error *err)
 {
     QError *qerr;
-    int i;
 
     qerr = qerror_new();
     loc_save(&qerr->loc);
     QINCREF(err->obj);
     qerr->error = err->obj;
 
-    for (i = 0; qerror_table[i].error_fmt; i++) {
-        if (strcmp(qerror_table[i].error_fmt, err->fmt) == 0) {
-            qerr->entry = &qerror_table[i];
-            break;
-        }
-    }
+    qerr->err_msg = qerror_format(err->fmt, qerr->error);
 
     if (monitor_cur_is_qmp()) {
         monitor_set_error(cur_mon, qerr);
@@ -619,5 +597,6 @@ static void qerror_destroy_obj(QObject *obj)
     qerr = qobject_to_qerror(obj);
 
     QDECREF(qerr->error);
+    g_free(qerr->err_msg);
     g_free(qerr);
 }
diff --git a/qerror.h b/qerror.h
index aec76b2..de8497d 100644
--- a/qerror.h
+++ b/qerror.h
@@ -27,7 +27,7 @@ typedef struct QError {
     QObject_HEAD;
     QDict *error;
     Location loc;
-    const QErrorStringTable *entry;
+    char *err_msg;
 } QError;
 
 QString *qerror_human(const QError *qerror);
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 10/35] error: don't delay error message construction
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (8 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 09/35] qerror: don't delay error message construction Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 11/35] qmp: query-block: add 'valid_encryption_key' field Luiz Capitulino
                   ` (24 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Today, the error message is only constructed when it's used. This commit
changes that to construct the error message when the error object is
built (ie. when the error is reported).

This simplifies the Error object.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 error.c  | 8 +-------
 qerror.c | 4 +---
 2 files changed, 2 insertions(+), 10 deletions(-)

diff --git a/error.c b/error.c
index 3a62592..2ade99b 100644
--- a/error.c
+++ b/error.c
@@ -20,7 +20,6 @@
 struct Error
 {
     QDict *obj;
-    const char *fmt;
     char *msg;
 };
 
@@ -39,7 +38,7 @@ void error_set(Error **errp, const char *fmt, ...)
     va_start(ap, fmt);
     err->obj = qobject_to_qdict(qobject_from_jsonv(fmt, &ap));
     va_end(ap);
-    err->fmt = fmt;
+    err->msg = qerror_format(fmt, err->obj);
 
     *errp = err;
 }
@@ -50,7 +49,6 @@ Error *error_copy(const Error *err)
 
     err_new = g_malloc0(sizeof(*err));
     err_new->msg = g_strdup(err->msg);
-    err_new->fmt = err->fmt;
     err_new->obj = err->obj;
     QINCREF(err_new->obj);
 
@@ -64,10 +62,6 @@ bool error_is_set(Error **errp)
 
 const char *error_get_pretty(Error *err)
 {
-    if (err->msg == NULL) {
-        err->msg = qerror_format(err->fmt, err->obj);
-    }
-
     return err->msg;
 }
 
diff --git a/qerror.c b/qerror.c
index a254f88..5d38428 100644
--- a/qerror.c
+++ b/qerror.c
@@ -543,7 +543,6 @@ void qerror_report(const char *fmt, ...)
 struct Error
 {
     QDict *obj;
-    const char *fmt;
     char *msg;
 };
 
@@ -555,8 +554,7 @@ void qerror_report_err(Error *err)
     loc_save(&qerr->loc);
     QINCREF(err->obj);
     qerr->error = err->obj;
-
-    qerr->err_msg = qerror_format(err->fmt, qerr->error);
+    qerr->err_msg = g_strdup(err->msg);
 
     if (monitor_cur_is_qmp()) {
         monitor_set_error(cur_mon, qerr);
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 11/35] qmp: query-block: add 'valid_encryption_key' field
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (9 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 10/35] error: " Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 12/35] hmp: hmp_cont(): don't rely on QERR_DEVICE_ENCRYPTED Luiz Capitulino
                   ` (23 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 block.c          | 1 +
 qapi-schema.json | 8 +++++---
 2 files changed, 6 insertions(+), 3 deletions(-)

diff --git a/block.c b/block.c
index 24323c1..59f6dd8 100644
--- a/block.c
+++ b/block.c
@@ -2445,6 +2445,7 @@ BlockInfoList *qmp_query_block(Error **errp)
             info->value->inserted->ro = bs->read_only;
             info->value->inserted->drv = g_strdup(bs->drv->format_name);
             info->value->inserted->encrypted = bs->encrypted;
+            info->value->inserted->valid_encryption_key = bs->valid_key;
             if (bs->backing_file[0]) {
                 info->value->inserted->has_backing_file = true;
                 info->value->inserted->backing_file = g_strdup(bs->backing_file);
diff --git a/qapi-schema.json b/qapi-schema.json
index cddf63a..5805f74 100644
--- a/qapi-schema.json
+++ b/qapi-schema.json
@@ -402,6 +402,8 @@
 #
 # @encrypted: true if the backing device is encrypted
 #
+# @valid_encryption_key: true if a valid encryption key has been set
+#
 # @bps: total throughput limit in bytes per second is specified
 #
 # @bps_rd: read throughput limit in bytes per second is specified
@@ -421,9 +423,9 @@
 { 'type': 'BlockDeviceInfo',
   'data': { 'file': 'str', 'ro': 'bool', 'drv': 'str',
             '*backing_file': 'str', 'backing_file_depth': 'int',
-            'encrypted': 'bool', 'bps': 'int', 'bps_rd': 'int',
-            'bps_wr': 'int', 'iops': 'int', 'iops_rd': 'int',
-            'iops_wr': 'int'} }
+            'encrypted': 'bool', 'valid_encryption_key': 'bool',
+            'bps': 'int', 'bps_rd': 'int', 'bps_wr': 'int',
+            'iops': 'int', 'iops_rd': 'int', 'iops_wr': 'int'} }
 
 ##
 # @BlockDeviceIoStatus:
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 12/35] hmp: hmp_cont(): don't rely on QERR_DEVICE_ENCRYPTED
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (10 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 11/35] qmp: query-block: add 'valid_encryption_key' field Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-10  8:43   ` Markus Armbruster
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 13/35] hmp_change(): don't access DeviceEncrypted's data Luiz Capitulino
                   ` (22 subsequent siblings)
  34 siblings, 1 reply; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

This commit changes hmp_cont() to loop through all block devices
and proactively set an encryption key for any encrypted device
without a valid one.

This change is needed because QERR_DEVICE_ENCRYPTED is going to be
dropped by a future commit.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 hmp.c | 43 +++++++++++++++++++++++++------------------
 1 file changed, 25 insertions(+), 18 deletions(-)

diff --git a/hmp.c b/hmp.c
index 25688ab..bfcc032 100644
--- a/hmp.c
+++ b/hmp.c
@@ -612,34 +612,41 @@ void hmp_pmemsave(Monitor *mon, const QDict *qdict)
 
 static void hmp_cont_cb(void *opaque, int err)
 {
-    Monitor *mon = opaque;
-
     if (!err) {
-        hmp_cont(mon, NULL);
+        qmp_cont(NULL);
     }
 }
 
-void hmp_cont(Monitor *mon, const QDict *qdict)
+static bool blockinfo_is_encrypted(const BlockInfo *bdev)
 {
-    Error *errp = NULL;
-
-    qmp_cont(&errp);
-    if (error_is_set(&errp)) {
-        if (error_is_type(errp, QERR_DEVICE_ENCRYPTED)) {
-            const char *device;
+    return (bdev->inserted && bdev->inserted->encrypted);
+}
 
-            /* The device is encrypted. Ask the user for the password
-               and retry */
+static bool blockinfo_key_is_set(const BlockInfo *bdev)
+{
+    return (bdev->inserted && bdev->inserted->valid_encryption_key);
+}
 
-            device = error_get_field(errp, "device");
-            assert(device != NULL);
+void hmp_cont(Monitor *mon, const QDict *qdict)
+{
+    BlockInfoList *bdev_list, *bdev;
+    Error *errp = NULL;
 
-            monitor_read_block_device_key(mon, device, hmp_cont_cb, mon);
-            error_free(errp);
-            return;
+    bdev_list = qmp_query_block(NULL);
+    for (bdev = bdev_list; bdev; bdev = bdev->next) {
+        if (blockinfo_is_encrypted(bdev->value) &&
+            !blockinfo_key_is_set(bdev->value)) {
+                monitor_read_block_device_key(mon, bdev->value->device,
+                                              hmp_cont_cb, NULL);
+                goto out;
         }
-        hmp_handle_error(mon, &errp);
     }
+
+    qmp_cont(&errp);
+    hmp_handle_error(mon, &errp);
+
+out:
+    qapi_free_BlockInfoList(bdev_list);
 }
 
 void hmp_system_wakeup(Monitor *mon, const QDict *qdict)
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 13/35] hmp_change(): don't access DeviceEncrypted's data
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (11 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 12/35] hmp: hmp_cont(): don't rely on QERR_DEVICE_ENCRYPTED Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-10  9:02   ` Markus Armbruster
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 14/35] net: inet_connect(), inet_connect_opts(): add in_progress argument Luiz Capitulino
                   ` (21 subsequent siblings)
  34 siblings, 1 reply; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

It's not needed. The device name is already known and
monitor_read_block_device_key() knows how to do the rest. This overly
simplifies hmp_change().

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 hmp.c | 29 ++---------------------------
 1 file changed, 2 insertions(+), 27 deletions(-)

diff --git a/hmp.c b/hmp.c
index bfcc032..3a9688d 100644
--- a/hmp.c
+++ b/hmp.c
@@ -782,22 +782,6 @@ static void hmp_change_read_arg(Monitor *mon, const char *password,
     monitor_read_command(mon, 1);
 }
 
-static void cb_hmp_change_bdrv_pwd(Monitor *mon, const char *password,
-                                   void *opaque)
-{
-    Error *encryption_err = opaque;
-    Error *err = NULL;
-    const char *device;
-
-    device = error_get_field(encryption_err, "device");
-
-    qmp_block_passwd(device, password, &err);
-    hmp_handle_error(mon, &err);
-    error_free(encryption_err);
-
-    monitor_read_command(mon, 1);
-}
-
 void hmp_change(Monitor *mon, const QDict *qdict)
 {
     const char *device = qdict_get_str(qdict, "device");
@@ -816,17 +800,8 @@ void hmp_change(Monitor *mon, const QDict *qdict)
 
     qmp_change(device, target, !!arg, arg, &err);
     if (error_is_type(err, QERR_DEVICE_ENCRYPTED)) {
-        monitor_printf(mon, "%s (%s) is encrypted.\n",
-                       error_get_field(err, "device"),
-                       error_get_field(err, "filename"));
-        if (!monitor_get_rs(mon)) {
-            monitor_printf(mon,
-                    "terminal does not support password prompting\n");
-            error_free(err);
-            return;
-        }
-        readline_start(monitor_get_rs(mon), "Password: ", 1,
-                       cb_hmp_change_bdrv_pwd, err);
+        error_free(err);
+        monitor_read_block_device_key(mon, device, NULL, NULL);
         return;
     }
     hmp_handle_error(mon, &err);
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 14/35] net: inet_connect(), inet_connect_opts(): add in_progress argument
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (12 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 13/35] hmp_change(): don't access DeviceEncrypted's data Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-10  9:07   ` Markus Armbruster
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 15/35] migration: don't rely on any QERR_SOCKET_* Luiz Capitulino
                   ` (20 subsequent siblings)
  34 siblings, 1 reply; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

It's used to indicate the special case where a valid file-descriptor
is returned (ie. success) but the connection can't be completed
w/o blocking.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 migration-tcp.c |  2 +-
 nbd.c           |  2 +-
 qemu-char.c     |  2 +-
 qemu-sockets.c  | 14 +++++++++++---
 qemu_socket.h   |  4 ++--
 ui/vnc.c        |  2 +-
 6 files changed, 17 insertions(+), 9 deletions(-)

diff --git a/migration-tcp.c b/migration-tcp.c
index 440804d..18944a4 100644
--- a/migration-tcp.c
+++ b/migration-tcp.c
@@ -86,7 +86,7 @@ int tcp_start_outgoing_migration(MigrationState *s, const char *host_port,
     s->write = socket_write;
     s->close = tcp_close;
 
-    s->fd = inet_connect(host_port, false, errp);
+    s->fd = inet_connect(host_port, false, NULL, errp);
 
     if (!error_is_set(errp)) {
         migrate_fd_connect(s);
diff --git a/nbd.c b/nbd.c
index dc0adf9..0dd60c5 100644
--- a/nbd.c
+++ b/nbd.c
@@ -162,7 +162,7 @@ int tcp_socket_outgoing(const char *address, uint16_t port)
 
 int tcp_socket_outgoing_spec(const char *address_and_port)
 {
-    return inet_connect(address_and_port, true, NULL);
+    return inet_connect(address_and_port, true, NULL, NULL);
 }
 
 int tcp_socket_incoming(const char *address, uint16_t port)
diff --git a/qemu-char.c b/qemu-char.c
index c2aaaee..382c71e 100644
--- a/qemu-char.c
+++ b/qemu-char.c
@@ -2446,7 +2446,7 @@ static CharDriverState *qemu_chr_open_socket(QemuOpts *opts)
         if (is_listen) {
             fd = inet_listen_opts(opts, 0, NULL);
         } else {
-            fd = inet_connect_opts(opts, NULL);
+            fd = inet_connect_opts(opts, NULL, NULL);
         }
     }
     if (fd < 0) {
diff --git a/qemu-sockets.c b/qemu-sockets.c
index beb2bb6..9cb47d4 100644
--- a/qemu-sockets.c
+++ b/qemu-sockets.c
@@ -209,7 +209,7 @@ listen:
     return slisten;
 }
 
-int inet_connect_opts(QemuOpts *opts, Error **errp)
+int inet_connect_opts(QemuOpts *opts, bool *in_progress, Error **errp)
 {
     struct addrinfo ai,*res,*e;
     const char *addr;
@@ -224,6 +224,10 @@ int inet_connect_opts(QemuOpts *opts, Error **errp)
     ai.ai_family = PF_UNSPEC;
     ai.ai_socktype = SOCK_STREAM;
 
+    if (in_progress) {
+        *in_progress = false;
+    }
+
     addr = qemu_opt_get(opts, "host");
     port = qemu_opt_get(opts, "port");
     block = qemu_opt_get_bool(opts, "block", 0);
@@ -277,6 +281,10 @@ int inet_connect_opts(QemuOpts *opts, Error **errp)
   #else
         if (!block && (rc == -EINPROGRESS)) {
   #endif
+            if (in_progress) {
+                *in_progress = true;
+            }
+
             error_set(errp, QERR_SOCKET_CONNECT_IN_PROGRESS);
         } else if (rc < 0) {
             if (NULL == e->ai_next)
@@ -487,7 +495,7 @@ int inet_listen(const char *str, char *ostr, int olen,
     return sock;
 }
 
-int inet_connect(const char *str, bool block, Error **errp)
+int inet_connect(const char *str, bool block, bool *in_progress, Error **errp)
 {
     QemuOpts *opts;
     int sock = -1;
@@ -497,7 +505,7 @@ int inet_connect(const char *str, bool block, Error **errp)
         if (block) {
             qemu_opt_set(opts, "block", "on");
         }
-        sock = inet_connect_opts(opts, errp);
+        sock = inet_connect_opts(opts, in_progress, errp);
     } else {
         error_set(errp, QERR_SOCKET_CREATE_FAILED);
     }
diff --git a/qemu_socket.h b/qemu_socket.h
index 4689ff3..30ae6af 100644
--- a/qemu_socket.h
+++ b/qemu_socket.h
@@ -42,8 +42,8 @@ int send_all(int fd, const void *buf, int len1);
 int inet_listen_opts(QemuOpts *opts, int port_offset, Error **errp);
 int inet_listen(const char *str, char *ostr, int olen,
                 int socktype, int port_offset, Error **errp);
-int inet_connect_opts(QemuOpts *opts, Error **errp);
-int inet_connect(const char *str, bool block, Error **errp);
+int inet_connect_opts(QemuOpts *opts, bool *in_progress, Error **errp);
+int inet_connect(const char *str, bool block, bool *in_progress, Error **errp);
 int inet_dgram_opts(QemuOpts *opts);
 const char *inet_strfamily(int family);
 
diff --git a/ui/vnc.c b/ui/vnc.c
index 312ad7f..385e345 100644
--- a/ui/vnc.c
+++ b/ui/vnc.c
@@ -3061,7 +3061,7 @@ int vnc_display_open(DisplayState *ds, const char *display)
         if (strncmp(display, "unix:", 5) == 0)
             vs->lsock = unix_connect(display+5);
         else
-            vs->lsock = inet_connect(display, true, NULL);
+            vs->lsock = inet_connect(display, true, NULL, NULL);
         if (-1 == vs->lsock) {
             g_free(vs->display);
             vs->display = NULL;
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 15/35] migration: don't rely on any QERR_SOCKET_*
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (13 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 14/35] net: inet_connect(), inet_connect_opts(): add in_progress argument Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-10  9:13   ` Markus Armbruster
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 16/35] qerror: drop QERR_SOCKET_CONNECT_IN_PROGRESS Luiz Capitulino
                   ` (19 subsequent siblings)
  34 siblings, 1 reply; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Use the in_progress argument for QERR_SOCKET_CONNECT_IN_PROGRESS. The
other errors are handled the same by checking if the error is set and
then calling migrate_fd_error() if it's.

It's also necessary to change inet_connect_opts() not to set
QERR_SOCKET_CONNECT_IN_PROGRESS. This error is only used by
tcp_start_outgoing_migration() and not changing it along with the
usage of in_progress would break migration.

Furthermore this commit fixes a bug. Today, there's a spurious error
report when migration succeeds:

(qemu) migrate tcp:0:4444
migrate: Connection can not be completed immediately
(qemu)

After this commit no spurious error is reported anymore.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 migration-tcp.c | 22 ++++++++--------------
 qemu-sockets.c  |  2 --
 2 files changed, 8 insertions(+), 16 deletions(-)

diff --git a/migration-tcp.c b/migration-tcp.c
index 18944a4..40c277f 100644
--- a/migration-tcp.c
+++ b/migration-tcp.c
@@ -82,27 +82,21 @@ static void tcp_wait_for_connect(void *opaque)
 int tcp_start_outgoing_migration(MigrationState *s, const char *host_port,
                                  Error **errp)
 {
+    bool in_progress;
+
     s->get_error = socket_errno;
     s->write = socket_write;
     s->close = tcp_close;
 
-    s->fd = inet_connect(host_port, false, NULL, errp);
-
-    if (!error_is_set(errp)) {
-        migrate_fd_connect(s);
-    } else if (error_is_type(*errp, QERR_SOCKET_CONNECT_IN_PROGRESS)) {
-        DPRINTF("connect in progress\n");
-        qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
-    } else if (error_is_type(*errp, QERR_SOCKET_CREATE_FAILED)) {
-        DPRINTF("connect failed\n");
-        return -1;
-    } else if (error_is_type(*errp, QERR_SOCKET_CONNECT_FAILED)) {
-        DPRINTF("connect failed\n");
+    s->fd = inet_connect(host_port, false, &in_progress, errp);
+    if (error_is_set(errp)) {
         migrate_fd_error(s);
         return -1;
+    } else if (in_progress) {
+        DPRINTF("connect in progress\n");
+        qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
     } else {
-        DPRINTF("unknown error\n");
-        return -1;
+        migrate_fd_connect(s);
     }
 
     return 0;
diff --git a/qemu-sockets.c b/qemu-sockets.c
index 9cb47d4..361d890 100644
--- a/qemu-sockets.c
+++ b/qemu-sockets.c
@@ -284,8 +284,6 @@ int inet_connect_opts(QemuOpts *opts, bool *in_progress, Error **errp)
             if (in_progress) {
                 *in_progress = true;
             }
-
-            error_set(errp, QERR_SOCKET_CONNECT_IN_PROGRESS);
         } else if (rc < 0) {
             if (NULL == e->ai_next)
                 fprintf(stderr, "%s: connect(%s,%s,%s,%s): %s\n", __FUNCTION__,
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 16/35] qerror: drop QERR_SOCKET_CONNECT_IN_PROGRESS
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (14 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 15/35] migration: don't rely on any QERR_SOCKET_* Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 17/35] block: block_int: include qerror.h Luiz Capitulino
                   ` (18 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Unused since last commit.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qerror.c | 4 ----
 qerror.h | 3 ---
 2 files changed, 7 deletions(-)

diff --git a/qerror.c b/qerror.c
index 5d38428..452ec69 100644
--- a/qerror.c
+++ b/qerror.c
@@ -309,10 +309,6 @@ static const QErrorStringTable qerror_table[] = {
         .desc      = "Could not start VNC server on %(target)",
     },
     {
-        .error_fmt = QERR_SOCKET_CONNECT_IN_PROGRESS,
-        .desc      = "Connection can not be completed immediately",
-    },
-    {
         .error_fmt = QERR_SOCKET_CONNECT_FAILED,
         .desc      = "Failed to connect to socket",
     },
diff --git a/qerror.h b/qerror.h
index de8497d..52ce58d 100644
--- a/qerror.h
+++ b/qerror.h
@@ -240,9 +240,6 @@ char *qerror_format(const char *fmt, QDict *error);
 #define QERR_VNC_SERVER_FAILED \
     "{ 'class': 'VNCServerFailed', 'data': { 'target': %s } }"
 
-#define QERR_SOCKET_CONNECT_IN_PROGRESS \
-    "{ 'class': 'SockConnectInprogress', 'data': {} }"
-
 #define QERR_SOCKET_CONNECT_FAILED \
     "{ 'class': 'SockConnectFailed', 'data': {} }"
 
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 17/35] block: block_int: include qerror.h
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (15 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 16/35] qerror: drop QERR_SOCKET_CONNECT_IN_PROGRESS Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 18/35] hmp: hmp.h: include qdict.h Luiz Capitulino
                   ` (17 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Several block/ files are relying on qerror.h being provided by
qapi-types.h. Fix this, as a future commit will change qapi-types.h
not to provide qerror.h.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 block_int.h | 1 +
 1 file changed, 1 insertion(+)

diff --git a/block_int.h b/block_int.h
index d72317f..00892e8 100644
--- a/block_int.h
+++ b/block_int.h
@@ -30,6 +30,7 @@
 #include "qemu-coroutine.h"
 #include "qemu-timer.h"
 #include "qapi-types.h"
+#include "qerror.h"
 
 #define BLOCK_FLAG_ENCRYPT	1
 #define BLOCK_FLAG_COMPAT6	4
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 18/35] hmp: hmp.h: include qdict.h
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (16 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 17/35] block: block_int: include qerror.h Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 19/35] qapi: qapi-types.h: don't include qapi/qapi-types-core.h Luiz Capitulino
                   ` (16 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

hmp.h is relying on qdict.h being provided by qapi-types.h. Fix this,
as a future commit will change qapi-types.h not to provide qdict.h.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 hmp.h | 1 +
 1 file changed, 1 insertion(+)

diff --git a/hmp.h b/hmp.h
index 8d2b0d7..3275522 100644
--- a/hmp.h
+++ b/hmp.h
@@ -16,6 +16,7 @@
 
 #include "qemu-common.h"
 #include "qapi-types.h"
+#include "qdict.h"
 
 void hmp_info_name(Monitor *mon);
 void hmp_info_version(Monitor *mon);
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 19/35] qapi: qapi-types.h: don't include qapi/qapi-types-core.h
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (17 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 18/35] hmp: hmp.h: include qdict.h Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 20/35] qapi: generate correct enum names for camel case enums Luiz Capitulino
                   ` (15 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

qapi-types.h needs only qemu-common.h. Including qapi-types-core.h
causes problems when qerror.h or error.h includes qapi-types.h.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 scripts/qapi-types.py | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/scripts/qapi-types.py b/scripts/qapi-types.py
index 4a734f5..3ed9f04 100644
--- a/scripts/qapi-types.py
+++ b/scripts/qapi-types.py
@@ -253,7 +253,8 @@ fdecl.write(mcgen('''
 #ifndef %(guard)s
 #define %(guard)s
 
-#include "qapi/qapi-types-core.h"
+#include "qemu-common.h"
+
 ''',
                   guard=guardname(h_file)))
 
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 20/35] qapi: generate correct enum names for camel case enums
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (18 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 19/35] qapi: qapi-types.h: don't include qapi/qapi-types-core.h Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 21/35] qapi: don't convert enum strings to lowercase Luiz Capitulino
                   ` (14 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

An enum like GenericError in the schema, should generate
GENERIC_ERROR and not GENERICERROR.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 scripts/qapi-types.py | 12 +++++++++++-
 1 file changed, 11 insertions(+), 1 deletion(-)

diff --git a/scripts/qapi-types.py b/scripts/qapi-types.py
index 3ed9f04..9b7da96 100644
--- a/scripts/qapi-types.py
+++ b/scripts/qapi-types.py
@@ -79,6 +79,16 @@ const char *%(name)s_lookup[] = {
 ''')
     return ret
 
+def generate_enum_name(name):
+    if name.isupper():
+        return c_fun(name)
+    new_name = ''
+    for c in c_fun(name):
+        if c.isupper():
+            new_name += '_'
+        new_name += c
+    return new_name.lstrip('_').upper()
+
 def generate_enum(name, values):
     lookup_decl = mcgen('''
 extern const char *%(name)s_lookup[];
@@ -100,7 +110,7 @@ typedef enum %(name)s
     %(abbrev)s_%(value)s = %(i)d,
 ''',
                      abbrev=de_camel_case(name).upper(),
-                     value=c_fun(value).upper(),
+                     value=generate_enum_name(value),
                      i=i)
         i += 1
 
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 21/35] qapi: don't convert enum strings to lowercase
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (19 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 20/35] qapi: generate correct enum names for camel case enums Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 22/35] qapi-schema: add ErrorClass enum Luiz Capitulino
                   ` (13 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Next commit will introduce enum strings in camel case.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 scripts/qapi-types.py | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/scripts/qapi-types.py b/scripts/qapi-types.py
index 9b7da96..cf601ae 100644
--- a/scripts/qapi-types.py
+++ b/scripts/qapi-types.py
@@ -70,7 +70,7 @@ const char *%(name)s_lookup[] = {
         ret += mcgen('''
     "%(value)s",
 ''',
-                     value=value.lower())
+                     value=value)
 
     ret += mcgen('''
     NULL,
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 22/35] qapi-schema: add ErrorClass enum
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (20 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 21/35] qapi: don't convert enum strings to lowercase Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 23/35] qerror: qerror_table: don't use C99 struct initializers Luiz Capitulino
                   ` (12 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qapi-schema.json | 30 ++++++++++++++++++++++++++++++
 1 file changed, 30 insertions(+)

diff --git a/qapi-schema.json b/qapi-schema.json
index 5805f74..8f670f3 100644
--- a/qapi-schema.json
+++ b/qapi-schema.json
@@ -3,6 +3,36 @@
 # QAPI Schema
 
 ##
+# @ErrorClass
+#
+# QEMU error classes
+#
+# @GenericError: this is used for errors that don't require a specific error
+#                class. This should be the default case for most errors
+#
+# @CommandNotFound: the requested command has not been found
+#
+# @DeviceEncrypted: the requested operation can't be fulfilled because the
+#                   selected device is encrypted
+#
+# @DeviceNotActive: a device has failed to be become active
+#
+# @DeviceNotFound: the requested device has not been found
+#
+# @KVMMissingCap: the requested operation can't be fulfilled because a
+#                 required KVM capability is missing
+#
+# @MigrationExpected: the requested operation can't be fulfilled because a
+#                     migration process is expected
+#
+# Since: 1.2
+##
+{ 'enum': 'ErrorClass',
+  'data': [ 'GenericError', 'CommandNotFound', 'DeviceEncrypted',
+            'DeviceNotActive', 'DeviceNotFound', 'KVMMissingCap',
+            'MigrationExpected' ] }
+
+##
 # @NameInfo:
 #
 # Guest name information.
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 23/35] qerror: qerror_table: don't use C99 struct initializers
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (21 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 22/35] qapi-schema: add ErrorClass enum Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 24/35] error, qerror: add ErrorClass argument to error functions Luiz Capitulino
                   ` (11 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

This allows for changing QERR_ macros to initialize two struct members
at the same time. See next commit for more details.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qerror.c | 276 +++++++++++++++++++++++++++++++--------------------------------
 qerror.h |   2 +-
 2 files changed, 139 insertions(+), 139 deletions(-)

diff --git a/qerror.c b/qerror.c
index 452ec69..ff460b0 100644
--- a/qerror.c
+++ b/qerror.c
@@ -44,285 +44,285 @@ static const QType qerror_type = {
  */
 static const QErrorStringTable qerror_table[] = {
     {
-        .error_fmt = QERR_ADD_CLIENT_FAILED,
-        .desc      = "Could not add client",
+         QERR_ADD_CLIENT_FAILED,
+         "Could not add client",
     },
     {
-        .error_fmt = QERR_AMBIGUOUS_PATH,
-        .desc      = "Path '%(path)' does not uniquely identify an object"
+         QERR_AMBIGUOUS_PATH,
+         "Path '%(path)' does not uniquely identify an object"
     },
     {
-        .error_fmt = QERR_BAD_BUS_FOR_DEVICE,
-        .desc      = "Device '%(device)' can't go on a %(bad_bus_type) bus",
+         QERR_BAD_BUS_FOR_DEVICE,
+         "Device '%(device)' can't go on a %(bad_bus_type) bus",
     },
     {
-        .error_fmt = QERR_BASE_NOT_FOUND,
-        .desc      = "Base '%(base)' not found",
+         QERR_BASE_NOT_FOUND,
+         "Base '%(base)' not found",
     },
     {
-        .error_fmt = QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED,
-        .desc      = "Block format '%(format)' used by device '%(name)' does not support feature '%(feature)'",
+         QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED,
+         "Block format '%(format)' used by device '%(name)' does not support feature '%(feature)'",
     },
     {
-        .error_fmt = QERR_BUS_NO_HOTPLUG,
-        .desc      = "Bus '%(bus)' does not support hotplugging",
+         QERR_BUS_NO_HOTPLUG,
+         "Bus '%(bus)' does not support hotplugging",
     },
     {
-        .error_fmt = QERR_BUS_NOT_FOUND,
-        .desc      = "Bus '%(bus)' not found",
+         QERR_BUS_NOT_FOUND,
+         "Bus '%(bus)' not found",
     },
     {
-        .error_fmt = QERR_COMMAND_DISABLED,
-        .desc      = "The command %(name) has been disabled for this instance",
+         QERR_COMMAND_DISABLED,
+         "The command %(name) has been disabled for this instance",
     },
     {
-        .error_fmt = QERR_COMMAND_NOT_FOUND,
-        .desc      = "The command %(name) has not been found",
+         QERR_COMMAND_NOT_FOUND,
+         "The command %(name) has not been found",
     },
     {
-        .error_fmt = QERR_DEVICE_ENCRYPTED,
-        .desc      = "'%(device)' (%(filename)) is encrypted",
+         QERR_DEVICE_ENCRYPTED,
+         "'%(device)' (%(filename)) is encrypted",
     },
     {
-        .error_fmt = QERR_DEVICE_FEATURE_BLOCKS_MIGRATION,
-        .desc      = "Migration is disabled when using feature '%(feature)' in device '%(device)'",
+         QERR_DEVICE_FEATURE_BLOCKS_MIGRATION,
+         "Migration is disabled when using feature '%(feature)' in device '%(device)'",
     },
     {
-        .error_fmt = QERR_DEVICE_HAS_NO_MEDIUM,
-        .desc      = "Device '%(device)' has no medium",
+         QERR_DEVICE_HAS_NO_MEDIUM,
+         "Device '%(device)' has no medium",
     },
     {
-        .error_fmt = QERR_DEVICE_INIT_FAILED,
-        .desc      = "Device '%(device)' could not be initialized",
+         QERR_DEVICE_INIT_FAILED,
+         "Device '%(device)' could not be initialized",
     },
     {
-        .error_fmt = QERR_DEVICE_IN_USE,
-        .desc      = "Device '%(device)' is in use",
+         QERR_DEVICE_IN_USE,
+         "Device '%(device)' is in use",
     },
     {
-        .error_fmt = QERR_DEVICE_IS_READ_ONLY,
-        .desc      = "Device '%(device)' is read only",
+         QERR_DEVICE_IS_READ_ONLY,
+         "Device '%(device)' is read only",
     },
     {
-        .error_fmt = QERR_DEVICE_LOCKED,
-        .desc      = "Device '%(device)' is locked",
+         QERR_DEVICE_LOCKED,
+         "Device '%(device)' is locked",
     },
     {
-        .error_fmt = QERR_DEVICE_MULTIPLE_BUSSES,
-        .desc      = "Device '%(device)' has multiple child busses",
+         QERR_DEVICE_MULTIPLE_BUSSES,
+         "Device '%(device)' has multiple child busses",
     },
     {
-        .error_fmt = QERR_DEVICE_NO_BUS,
-        .desc      = "Device '%(device)' has no child bus",
+         QERR_DEVICE_NO_BUS,
+         "Device '%(device)' has no child bus",
     },
     {
-        .error_fmt = QERR_DEVICE_NO_HOTPLUG,
-        .desc      = "Device '%(device)' does not support hotplugging",
+         QERR_DEVICE_NO_HOTPLUG,
+         "Device '%(device)' does not support hotplugging",
     },
     {
-        .error_fmt = QERR_DEVICE_NOT_ACTIVE,
-        .desc      = "Device '%(device)' has not been activated",
+         QERR_DEVICE_NOT_ACTIVE,
+         "Device '%(device)' has not been activated",
     },
     {
-        .error_fmt = QERR_DEVICE_NOT_ENCRYPTED,
-        .desc      = "Device '%(device)' is not encrypted",
+         QERR_DEVICE_NOT_ENCRYPTED,
+         "Device '%(device)' is not encrypted",
     },
     {
-        .error_fmt = QERR_DEVICE_NOT_FOUND,
-        .desc      = "Device '%(device)' not found",
+         QERR_DEVICE_NOT_FOUND,
+         "Device '%(device)' not found",
     },
     {
-        .error_fmt = QERR_DEVICE_NOT_REMOVABLE,
-        .desc      = "Device '%(device)' is not removable",
+         QERR_DEVICE_NOT_REMOVABLE,
+         "Device '%(device)' is not removable",
     },
     {
-        .error_fmt = QERR_DUPLICATE_ID,
-        .desc      = "Duplicate ID '%(id)' for %(object)",
+         QERR_DUPLICATE_ID,
+         "Duplicate ID '%(id)' for %(object)",
     },
     {
-        .error_fmt = QERR_FD_NOT_FOUND,
-        .desc      = "File descriptor named '%(name)' not found",
+         QERR_FD_NOT_FOUND,
+         "File descriptor named '%(name)' not found",
     },
     {
-        .error_fmt = QERR_FD_NOT_SUPPLIED,
-        .desc      = "No file descriptor supplied via SCM_RIGHTS",
+         QERR_FD_NOT_SUPPLIED,
+         "No file descriptor supplied via SCM_RIGHTS",
     },
     {
-        .error_fmt = QERR_FEATURE_DISABLED,
-        .desc      = "The feature '%(name)' is not enabled",
+         QERR_FEATURE_DISABLED,
+         "The feature '%(name)' is not enabled",
     },
     {
-        .error_fmt = QERR_INVALID_BLOCK_FORMAT,
-        .desc      = "Invalid block format '%(name)'",
+         QERR_INVALID_BLOCK_FORMAT,
+         "Invalid block format '%(name)'",
     },
     {
-        .error_fmt = QERR_INVALID_OPTION_GROUP,
-        .desc      = "There is no option group '%(group)'",
+         QERR_INVALID_OPTION_GROUP,
+         "There is no option group '%(group)'",
     },
     {
-        .error_fmt = QERR_INVALID_PARAMETER,
-        .desc      = "Invalid parameter '%(name)'",
+         QERR_INVALID_PARAMETER,
+         "Invalid parameter '%(name)'",
     },
     {
-        .error_fmt = QERR_INVALID_PARAMETER_COMBINATION,
-        .desc      = "Invalid parameter combination",
+         QERR_INVALID_PARAMETER_COMBINATION,
+         "Invalid parameter combination",
     },
     {
-        .error_fmt = QERR_INVALID_PARAMETER_TYPE,
-        .desc      = "Invalid parameter type for '%(name)', expected: %(expected)",
+         QERR_INVALID_PARAMETER_TYPE,
+         "Invalid parameter type for '%(name)', expected: %(expected)",
     },
     {
-        .error_fmt = QERR_INVALID_PARAMETER_VALUE,
-        .desc      = "Parameter '%(name)' expects %(expected)",
+         QERR_INVALID_PARAMETER_VALUE,
+         "Parameter '%(name)' expects %(expected)",
     },
     {
-        .error_fmt = QERR_INVALID_PASSWORD,
-        .desc      = "Password incorrect",
+         QERR_INVALID_PASSWORD,
+         "Password incorrect",
     },
     {
-        .error_fmt = QERR_IO_ERROR,
-        .desc      = "An IO error has occurred",
+         QERR_IO_ERROR,
+         "An IO error has occurred",
     },
     {
-        .error_fmt = QERR_JSON_PARSE_ERROR,
-        .desc      = "JSON parse error, %(message)",
+         QERR_JSON_PARSE_ERROR,
+         "JSON parse error, %(message)",
 
     },
     {
-        .error_fmt = QERR_JSON_PARSING,
-        .desc      = "Invalid JSON syntax",
+         QERR_JSON_PARSING,
+         "Invalid JSON syntax",
     },
     {
-        .error_fmt = QERR_KVM_MISSING_CAP,
-        .desc      = "Using KVM without %(capability), %(feature) unavailable",
+         QERR_KVM_MISSING_CAP,
+         "Using KVM without %(capability), %(feature) unavailable",
     },
     {
-        .error_fmt = QERR_MIGRATION_ACTIVE,
-        .desc      = "There's a migration process in progress",
+         QERR_MIGRATION_ACTIVE,
+         "There's a migration process in progress",
     },
     {
-        .error_fmt = QERR_MIGRATION_NOT_SUPPORTED,
-        .desc      = "State blocked by non-migratable device '%(device)'",
+         QERR_MIGRATION_NOT_SUPPORTED,
+         "State blocked by non-migratable device '%(device)'",
     },
     {
-        .error_fmt = QERR_MIGRATION_EXPECTED,
-        .desc      = "An incoming migration is expected before this command can be executed",
+         QERR_MIGRATION_EXPECTED,
+         "An incoming migration is expected before this command can be executed",
     },
     {
-        .error_fmt = QERR_MISSING_PARAMETER,
-        .desc      = "Parameter '%(name)' is missing",
+         QERR_MISSING_PARAMETER,
+         "Parameter '%(name)' is missing",
     },
     {
-        .error_fmt = QERR_NO_BUS_FOR_DEVICE,
-        .desc      = "No '%(bus)' bus found for device '%(device)'",
+         QERR_NO_BUS_FOR_DEVICE,
+         "No '%(bus)' bus found for device '%(device)'",
     },
     {
-        .error_fmt = QERR_NOT_SUPPORTED,
-        .desc      = "Not supported",
+         QERR_NOT_SUPPORTED,
+         "Not supported",
     },
     {
-        .error_fmt = QERR_OPEN_FILE_FAILED,
-        .desc      = "Could not open '%(filename)'",
+         QERR_OPEN_FILE_FAILED,
+         "Could not open '%(filename)'",
     },
     {
-        .error_fmt = QERR_PERMISSION_DENIED,
-        .desc      = "Insufficient permission to perform this operation",
+         QERR_PERMISSION_DENIED,
+         "Insufficient permission to perform this operation",
     },
     {
-        .error_fmt = QERR_PROPERTY_NOT_FOUND,
-        .desc      = "Property '%(device).%(property)' not found",
+         QERR_PROPERTY_NOT_FOUND,
+         "Property '%(device).%(property)' not found",
     },
     {
-        .error_fmt = QERR_PROPERTY_VALUE_BAD,
-        .desc      = "Property '%(device).%(property)' doesn't take value '%(value)'",
+         QERR_PROPERTY_VALUE_BAD,
+         "Property '%(device).%(property)' doesn't take value '%(value)'",
     },
     {
-        .error_fmt = QERR_PROPERTY_VALUE_IN_USE,
-        .desc      = "Property '%(device).%(property)' can't take value '%(value)', it's in use",
+         QERR_PROPERTY_VALUE_IN_USE,
+         "Property '%(device).%(property)' can't take value '%(value)', it's in use",
     },
     {
-        .error_fmt = QERR_PROPERTY_VALUE_NOT_FOUND,
-        .desc      = "Property '%(device).%(property)' can't find value '%(value)'",
+         QERR_PROPERTY_VALUE_NOT_FOUND,
+         "Property '%(device).%(property)' can't find value '%(value)'",
     },
     {
-        .error_fmt = QERR_PROPERTY_VALUE_NOT_POWER_OF_2,
-        .desc      = "Property '%(device).%(property)' doesn't take "
+         QERR_PROPERTY_VALUE_NOT_POWER_OF_2,
+         "Property '%(device).%(property)' doesn't take "
                      "value '%(value)', it's not a power of 2",
     },
     {
-        .error_fmt = QERR_PROPERTY_VALUE_OUT_OF_RANGE,
-        .desc      = "Property '%(device).%(property)' doesn't take "
+         QERR_PROPERTY_VALUE_OUT_OF_RANGE,
+         "Property '%(device).%(property)' doesn't take "
                      "value %(value) (minimum: %(min), maximum: %(max))",
     },
     {
-        .error_fmt = QERR_QGA_COMMAND_FAILED,
-        .desc      = "Guest agent command failed, error was '%(message)'",
+         QERR_QGA_COMMAND_FAILED,
+         "Guest agent command failed, error was '%(message)'",
     },
     {
-        .error_fmt = QERR_QGA_LOGGING_FAILED,
-        .desc      = "Guest agent failed to log non-optional log statement",
+         QERR_QGA_LOGGING_FAILED,
+         "Guest agent failed to log non-optional log statement",
     },
     {
-        .error_fmt = QERR_QMP_BAD_INPUT_OBJECT,
-        .desc      = "Expected '%(expected)' in QMP input",
+         QERR_QMP_BAD_INPUT_OBJECT,
+         "Expected '%(expected)' in QMP input",
     },
     {
-        .error_fmt = QERR_QMP_BAD_INPUT_OBJECT_MEMBER,
-        .desc      = "QMP input object member '%(member)' expects '%(expected)'",
+         QERR_QMP_BAD_INPUT_OBJECT_MEMBER,
+         "QMP input object member '%(member)' expects '%(expected)'",
     },
     {
-        .error_fmt = QERR_QMP_EXTRA_MEMBER,
-        .desc      = "QMP input object member '%(member)' is unexpected",
+         QERR_QMP_EXTRA_MEMBER,
+         "QMP input object member '%(member)' is unexpected",
     },
     {
-        .error_fmt = QERR_RESET_REQUIRED,
-        .desc      = "Resetting the Virtual Machine is required",
+         QERR_RESET_REQUIRED,
+         "Resetting the Virtual Machine is required",
     },
     {
-        .error_fmt = QERR_SET_PASSWD_FAILED,
-        .desc      = "Could not set password",
+         QERR_SET_PASSWD_FAILED,
+         "Could not set password",
     },
     {
-        .error_fmt = QERR_TOO_MANY_FILES,
-        .desc      = "Too many open files",
+         QERR_TOO_MANY_FILES,
+         "Too many open files",
     },
     {
-        .error_fmt = QERR_UNDEFINED_ERROR,
-        .desc      = "An undefined error has occurred",
+         QERR_UNDEFINED_ERROR,
+         "An undefined error has occurred",
     },
     {
-        .error_fmt = QERR_UNKNOWN_BLOCK_FORMAT_FEATURE,
-        .desc      = "'%(device)' uses a %(format) feature which is not "
+         QERR_UNKNOWN_BLOCK_FORMAT_FEATURE,
+         "'%(device)' uses a %(format) feature which is not "
                      "supported by this qemu version: %(feature)",
     },
     {
-        .error_fmt = QERR_UNSUPPORTED,
-        .desc      = "this feature or command is not currently supported",
+         QERR_UNSUPPORTED,
+         "this feature or command is not currently supported",
     },
     {
-        .error_fmt = QERR_VIRTFS_FEATURE_BLOCKS_MIGRATION,
-        .desc      = "Migration is disabled when VirtFS export path '%(path)' "
+         QERR_VIRTFS_FEATURE_BLOCKS_MIGRATION,
+         "Migration is disabled when VirtFS export path '%(path)' "
                      "is mounted in the guest using mount_tag '%(tag)'",
     },
     {
-        .error_fmt = QERR_VNC_SERVER_FAILED,
-        .desc      = "Could not start VNC server on %(target)",
+         QERR_VNC_SERVER_FAILED,
+         "Could not start VNC server on %(target)",
     },
     {
-        .error_fmt = QERR_SOCKET_CONNECT_FAILED,
-        .desc      = "Failed to connect to socket",
+         QERR_SOCKET_CONNECT_FAILED,
+         "Failed to connect to socket",
     },
     {
-        .error_fmt = QERR_SOCKET_LISTEN_FAILED,
-        .desc      = "Failed to set socket to listening mode",
+         QERR_SOCKET_LISTEN_FAILED,
+         "Failed to set socket to listening mode",
     },
     {
-        .error_fmt = QERR_SOCKET_BIND_FAILED,
-        .desc      = "Failed to bind socket",
+         QERR_SOCKET_BIND_FAILED,
+         "Failed to bind socket",
     },
     {
-        .error_fmt = QERR_SOCKET_CREATE_FAILED,
-        .desc      = "Failed to create socket",
+         QERR_SOCKET_CREATE_FAILED,
+         "Failed to create socket",
     },
     {}
 };
diff --git a/qerror.h b/qerror.h
index 52ce58d..2e6a49d 100644
--- a/qerror.h
+++ b/qerror.h
@@ -19,8 +19,8 @@
 #include <stdarg.h>
 
 typedef struct QErrorStringTable {
-    const char *desc;
     const char *error_fmt;
+    const char *desc;
 } QErrorStringTable;
 
 typedef struct QError {
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 24/35] error, qerror: add ErrorClass argument to error functions
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (22 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 23/35] qerror: qerror_table: don't use C99 struct initializers Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 25/35] qerror: add proper ErrorClass value for QERR_ macros Luiz Capitulino
                   ` (10 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

The new argument is added to functions qerror_report() and error_set().
It's stored in Error and QError. qerror_report_err() is also updated to
take care of it.

The QERR_ macros are changed to contain a place holder value for the
new argument, so that the value is used on all current calls to
qerror_report() and error_set() (and also to initialize qerror_table[]).

Next commit will update the QERR_ macros with a proper ErrorClass
value.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 error.c  |   8 +++-
 error.h  |   5 ++-
 qerror.c |  10 +++--
 qerror.h | 145 ++++++++++++++++++++++++++++++++-------------------------------
 4 files changed, 90 insertions(+), 78 deletions(-)

diff --git a/error.c b/error.c
index 2ade99b..648706a 100644
--- a/error.c
+++ b/error.c
@@ -14,6 +14,7 @@
 #include "error.h"
 #include "qjson.h"
 #include "qdict.h"
+#include "qapi-types.h"
 #include "error_int.h"
 #include "qerror.h"
 
@@ -21,9 +22,10 @@ struct Error
 {
     QDict *obj;
     char *msg;
+    ErrorClass err_class;
 };
 
-void error_set(Error **errp, const char *fmt, ...)
+void error_set(Error **errp, ErrorClass err_class, const char *fmt, ...)
 {
     Error *err;
     va_list ap;
@@ -39,6 +41,7 @@ void error_set(Error **errp, const char *fmt, ...)
     err->obj = qobject_to_qdict(qobject_from_jsonv(fmt, &ap));
     va_end(ap);
     err->msg = qerror_format(fmt, err->obj);
+    err->err_class = err_class;
 
     *errp = err;
 }
@@ -49,6 +52,7 @@ Error *error_copy(const Error *err)
 
     err_new = g_malloc0(sizeof(*err));
     err_new->msg = g_strdup(err->msg);
+    err_new->err_class = err->err_class;
     err_new->obj = err->obj;
     QINCREF(err_new->obj);
 
@@ -97,7 +101,7 @@ void error_free(Error *err)
     }
 }
 
-bool error_is_type(Error *err, const char *fmt)
+bool error_is_type(Error *err, ErrorClass err_class, const char *fmt)
 {
     const char *error_class;
     char *ptr;
diff --git a/error.h b/error.h
index 3d9d96d..9678752 100644
--- a/error.h
+++ b/error.h
@@ -13,6 +13,7 @@
 #define ERROR_H
 
 #include "compiler.h"
+#include "qapi-types.h"
 #include <stdbool.h>
 
 /**
@@ -26,7 +27,7 @@ typedef struct Error Error;
  * Currently, qerror.h defines these error formats.  This function is not
  * meant to be used outside of QEMU.
  */
-void error_set(Error **err, const char *fmt, ...) GCC_FMT_ATTR(2, 3);
+void error_set(Error **err, ErrorClass err_class, const char *fmt, ...) GCC_FMT_ATTR(3, 4);
 
 /**
  * Returns true if an indirect pointer to an error is pointing to a valid
@@ -70,6 +71,6 @@ void error_free(Error *err);
  * Determine if an error is of a speific type (based on the qerror format).
  * Non-QEMU users should get the `class' field to identify the error type.
  */
-bool error_is_type(Error *err, const char *fmt);
+bool error_is_type(Error *err, ErrorClass err_class, const char *fmt);
 
 #endif
diff --git a/qerror.c b/qerror.c
index ff460b0..0bf8aec 100644
--- a/qerror.c
+++ b/qerror.c
@@ -386,13 +386,15 @@ static QDict *error_obj_from_fmt_no_fail(const char *fmt, va_list *va)
  *
  * Return strong reference.
  */
-static QError *qerror_from_info(const char *fmt, va_list *va)
+static QError *qerror_from_info(ErrorClass err_class, const char *fmt,
+                                va_list *va)
 {
     QError *qerr;
 
     qerr = qerror_new();
     loc_save(&qerr->loc);
 
+    qerr->err_class = err_class;
     qerr->error = error_obj_from_fmt_no_fail(fmt, va);
     qerr->err_msg = qerror_format(fmt, qerr->error);
 
@@ -518,13 +520,13 @@ static void qerror_print(QError *qerror)
     QDECREF(qstring);
 }
 
-void qerror_report(const char *fmt, ...)
+void qerror_report(ErrorClass eclass, const char *fmt, ...)
 {
     va_list va;
     QError *qerror;
 
     va_start(va, fmt);
-    qerror = qerror_from_info(fmt, &va);
+    qerror = qerror_from_info(eclass, fmt, &va);
     va_end(va);
 
     if (monitor_cur_is_qmp()) {
@@ -540,6 +542,7 @@ struct Error
 {
     QDict *obj;
     char *msg;
+    ErrorClass err_class;
 };
 
 void qerror_report_err(Error *err)
@@ -551,6 +554,7 @@ void qerror_report_err(Error *err)
     QINCREF(err->obj);
     qerr->error = err->obj;
     qerr->err_msg = g_strdup(err->msg);
+    qerr->err_class = err->err_class;
 
     if (monitor_cur_is_qmp()) {
         monitor_set_error(cur_mon, qerr);
diff --git a/qerror.h b/qerror.h
index 2e6a49d..bcc93f8 100644
--- a/qerror.h
+++ b/qerror.h
@@ -16,9 +16,11 @@
 #include "qstring.h"
 #include "qemu-error.h"
 #include "error.h"
+#include "qapi-types.h"
 #include <stdarg.h>
 
 typedef struct QErrorStringTable {
+    ErrorClass err_class;
     const char *error_fmt;
     const char *desc;
 } QErrorStringTable;
@@ -28,10 +30,11 @@ typedef struct QError {
     QDict *error;
     Location loc;
     char *err_msg;
+    ErrorClass err_class;
 } QError;
 
 QString *qerror_human(const QError *qerror);
-void qerror_report(const char *fmt, ...) GCC_FMT_ATTR(1, 2);
+void qerror_report(ErrorClass err_class, const char *fmt, ...) GCC_FMT_ATTR(2, 3);
 void qerror_report_err(Error *err);
 void assert_no_error(Error *err);
 char *qerror_format(const char *fmt, QDict *error);
@@ -42,214 +45,214 @@ char *qerror_format(const char *fmt, QDict *error);
  * Use scripts/check-qerror.sh to check.
  */
 #define QERR_ADD_CLIENT_FAILED \
-    "{ 'class': 'AddClientFailed', 'data': {} }"
+    -1, "{ 'class': 'AddClientFailed', 'data': {} }"
 
 #define QERR_AMBIGUOUS_PATH \
-    "{ 'class': 'AmbiguousPath', 'data': { 'path': %s } }"
+    -1, "{ 'class': 'AmbiguousPath', 'data': { 'path': %s } }"
 
 #define QERR_BAD_BUS_FOR_DEVICE \
-    "{ 'class': 'BadBusForDevice', 'data': { 'device': %s, 'bad_bus_type': %s } }"
+    -1, "{ 'class': 'BadBusForDevice', 'data': { 'device': %s, 'bad_bus_type': %s } }"
 
 #define QERR_BASE_NOT_FOUND \
-    "{ 'class': 'BaseNotFound', 'data': { 'base': %s } }"
+    -1, "{ 'class': 'BaseNotFound', 'data': { 'base': %s } }"
 
 #define QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED \
-    "{ 'class': 'BlockFormatFeatureNotSupported', 'data': { 'format': %s, 'name': %s, 'feature': %s } }"
+    -1, "{ 'class': 'BlockFormatFeatureNotSupported', 'data': { 'format': %s, 'name': %s, 'feature': %s } }"
 
 #define QERR_BUFFER_OVERRUN \
-    "{ 'class': 'BufferOverrun', 'data': {} }"
+    -1, "{ 'class': 'BufferOverrun', 'data': {} }"
 
 #define QERR_BUS_NO_HOTPLUG \
-    "{ 'class': 'BusNoHotplug', 'data': { 'bus': %s } }"
+    -1, "{ 'class': 'BusNoHotplug', 'data': { 'bus': %s } }"
 
 #define QERR_BUS_NOT_FOUND \
-    "{ 'class': 'BusNotFound', 'data': { 'bus': %s } }"
+    -1, "{ 'class': 'BusNotFound', 'data': { 'bus': %s } }"
 
 #define QERR_COMMAND_DISABLED \
-    "{ 'class': 'CommandDisabled', 'data': { 'name': %s } }"
+    -1, "{ 'class': 'CommandDisabled', 'data': { 'name': %s } }"
 
 #define QERR_COMMAND_NOT_FOUND \
-    "{ 'class': 'CommandNotFound', 'data': { 'name': %s } }"
+    -1, "{ 'class': 'CommandNotFound', 'data': { 'name': %s } }"
 
 #define QERR_DEVICE_ENCRYPTED \
-    "{ 'class': 'DeviceEncrypted', 'data': { 'device': %s, 'filename': %s } }"
+    -1, "{ 'class': 'DeviceEncrypted', 'data': { 'device': %s, 'filename': %s } }"
 
 #define QERR_DEVICE_FEATURE_BLOCKS_MIGRATION \
-    "{ 'class': 'DeviceFeatureBlocksMigration', 'data': { 'device': %s, 'feature': %s } }"
+    -1, "{ 'class': 'DeviceFeatureBlocksMigration', 'data': { 'device': %s, 'feature': %s } }"
 
 #define QERR_DEVICE_HAS_NO_MEDIUM \
-    "{ 'class': 'DeviceHasNoMedium', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceHasNoMedium', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_INIT_FAILED \
-    "{ 'class': 'DeviceInitFailed', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceInitFailed', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_IN_USE \
-    "{ 'class': 'DeviceInUse', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceInUse', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_IS_READ_ONLY \
-    "{ 'class': 'DeviceIsReadOnly', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceIsReadOnly', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_LOCKED \
-    "{ 'class': 'DeviceLocked', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceLocked', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_MULTIPLE_BUSSES \
-    "{ 'class': 'DeviceMultipleBusses', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceMultipleBusses', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NO_BUS \
-    "{ 'class': 'DeviceNoBus', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceNoBus', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NO_HOTPLUG \
-    "{ 'class': 'DeviceNoHotplug', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceNoHotplug', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NOT_ACTIVE \
-    "{ 'class': 'DeviceNotActive', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceNotActive', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NOT_ENCRYPTED \
-    "{ 'class': 'DeviceNotEncrypted', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceNotEncrypted', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NOT_FOUND \
-    "{ 'class': 'DeviceNotFound', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceNotFound', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NOT_REMOVABLE \
-    "{ 'class': 'DeviceNotRemovable', 'data': { 'device': %s } }"
+    -1, "{ 'class': 'DeviceNotRemovable', 'data': { 'device': %s } }"
 
 #define QERR_DUPLICATE_ID \
-    "{ 'class': 'DuplicateId', 'data': { 'id': %s, 'object': %s } }"
+    -1, "{ 'class': 'DuplicateId', 'data': { 'id': %s, 'object': %s } }"
 
 #define QERR_FD_NOT_FOUND \
-    "{ 'class': 'FdNotFound', 'data': { 'name': %s } }"
+    -1, "{ 'class': 'FdNotFound', 'data': { 'name': %s } }"
 
 #define QERR_FD_NOT_SUPPLIED \
-    "{ 'class': 'FdNotSupplied', 'data': {} }"
+    -1, "{ 'class': 'FdNotSupplied', 'data': {} }"
 
 #define QERR_FEATURE_DISABLED \
-    "{ 'class': 'FeatureDisabled', 'data': { 'name': %s } }"
+    -1, "{ 'class': 'FeatureDisabled', 'data': { 'name': %s } }"
 
 #define QERR_INVALID_BLOCK_FORMAT \
-    "{ 'class': 'InvalidBlockFormat', 'data': { 'name': %s } }"
+    -1, "{ 'class': 'InvalidBlockFormat', 'data': { 'name': %s } }"
 
 #define QERR_INVALID_OPTION_GROUP \
-    "{ 'class': 'InvalidOptionGroup', 'data': { 'group': %s } }"
+    -1, "{ 'class': 'InvalidOptionGroup', 'data': { 'group': %s } }"
 
 #define QERR_INVALID_PARAMETER \
-    "{ 'class': 'InvalidParameter', 'data': { 'name': %s } }"
+    -1, "{ 'class': 'InvalidParameter', 'data': { 'name': %s } }"
 
 #define QERR_INVALID_PARAMETER_COMBINATION \
-    "{ 'class': 'InvalidParameterCombination', 'data': {} }"
+    -1, "{ 'class': 'InvalidParameterCombination', 'data': {} }"
 
 #define QERR_INVALID_PARAMETER_TYPE \
-    "{ 'class': 'InvalidParameterType', 'data': { 'name': %s,'expected': %s } }"
+    -1, "{ 'class': 'InvalidParameterType', 'data': { 'name': %s,'expected': %s } }"
 
 #define QERR_INVALID_PARAMETER_VALUE \
-    "{ 'class': 'InvalidParameterValue', 'data': { 'name': %s, 'expected': %s } }"
+    -1, "{ 'class': 'InvalidParameterValue', 'data': { 'name': %s, 'expected': %s } }"
 
 #define QERR_INVALID_PASSWORD \
-    "{ 'class': 'InvalidPassword', 'data': {} }"
+    -1, "{ 'class': 'InvalidPassword', 'data': {} }"
 
 #define QERR_IO_ERROR \
-    "{ 'class': 'IOError', 'data': {} }"
+    -1, "{ 'class': 'IOError', 'data': {} }"
 
 #define QERR_JSON_PARSE_ERROR \
-    "{ 'class': 'JSONParseError', 'data': { 'message': %s } }"
+    -1, "{ 'class': 'JSONParseError', 'data': { 'message': %s } }"
 
 #define QERR_JSON_PARSING \
-    "{ 'class': 'JSONParsing', 'data': {} }"
+    -1, "{ 'class': 'JSONParsing', 'data': {} }"
 
 #define QERR_KVM_MISSING_CAP \
-    "{ 'class': 'KVMMissingCap', 'data': { 'capability': %s, 'feature': %s } }"
+    -1, "{ 'class': 'KVMMissingCap', 'data': { 'capability': %s, 'feature': %s } }"
 
 #define QERR_MIGRATION_ACTIVE \
-    "{ 'class': 'MigrationActive', 'data': {} }"
+    -1, "{ 'class': 'MigrationActive', 'data': {} }"
 
 #define QERR_MIGRATION_NOT_SUPPORTED \
-    "{ 'class': 'MigrationNotSupported', 'data': {'device': %s} }"
+    -1, "{ 'class': 'MigrationNotSupported', 'data': {'device': %s} }"
 
 #define QERR_MIGRATION_EXPECTED \
-    "{ 'class': 'MigrationExpected', 'data': {} }"
+    -1, "{ 'class': 'MigrationExpected', 'data': {} }"
 
 #define QERR_MISSING_PARAMETER \
-    "{ 'class': 'MissingParameter', 'data': { 'name': %s } }"
+    -1, "{ 'class': 'MissingParameter', 'data': { 'name': %s } }"
 
 #define QERR_NO_BUS_FOR_DEVICE \
-    "{ 'class': 'NoBusForDevice', 'data': { 'device': %s, 'bus': %s } }"
+    -1, "{ 'class': 'NoBusForDevice', 'data': { 'device': %s, 'bus': %s } }"
 
 #define QERR_NOT_SUPPORTED \
-    "{ 'class': 'NotSupported', 'data': {} }"
+    -1, "{ 'class': 'NotSupported', 'data': {} }"
 
 #define QERR_OPEN_FILE_FAILED \
-    "{ 'class': 'OpenFileFailed', 'data': { 'filename': %s } }"
+    -1, "{ 'class': 'OpenFileFailed', 'data': { 'filename': %s } }"
 
 #define QERR_PERMISSION_DENIED \
-    "{ 'class': 'PermissionDenied', 'data': {} }"
+    -1, "{ 'class': 'PermissionDenied', 'data': {} }"
 
 #define QERR_PROPERTY_NOT_FOUND \
-    "{ 'class': 'PropertyNotFound', 'data': { 'device': %s, 'property': %s } }"
+    -1, "{ 'class': 'PropertyNotFound', 'data': { 'device': %s, 'property': %s } }"
 
 #define QERR_PROPERTY_VALUE_BAD \
-    "{ 'class': 'PropertyValueBad', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
+    -1, "{ 'class': 'PropertyValueBad', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
 
 #define QERR_PROPERTY_VALUE_IN_USE \
-    "{ 'class': 'PropertyValueInUse', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
+    -1, "{ 'class': 'PropertyValueInUse', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
 
 #define QERR_PROPERTY_VALUE_NOT_FOUND \
-    "{ 'class': 'PropertyValueNotFound', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
+    -1, "{ 'class': 'PropertyValueNotFound', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
 
 #define QERR_PROPERTY_VALUE_NOT_POWER_OF_2 \
-    "{ 'class': 'PropertyValueNotPowerOf2', 'data': { " \
+    -1, "{ 'class': 'PropertyValueNotPowerOf2', 'data': { " \
     "'device': %s, 'property': %s, 'value': %"PRId64" } }"
 
 #define QERR_PROPERTY_VALUE_OUT_OF_RANGE \
-    "{ 'class': 'PropertyValueOutOfRange', 'data': { 'device': %s, 'property': %s, 'value': %"PRId64", 'min': %"PRId64", 'max': %"PRId64" } }"
+    -1, "{ 'class': 'PropertyValueOutOfRange', 'data': { 'device': %s, 'property': %s, 'value': %"PRId64", 'min': %"PRId64", 'max': %"PRId64" } }"
 
 #define QERR_QGA_COMMAND_FAILED \
-    "{ 'class': 'QgaCommandFailed', 'data': { 'message': %s } }"
+    -1, "{ 'class': 'QgaCommandFailed', 'data': { 'message': %s } }"
 
 #define QERR_QGA_LOGGING_FAILED \
-    "{ 'class': 'QgaLoggingFailed', 'data': {} }"
+    -1, "{ 'class': 'QgaLoggingFailed', 'data': {} }"
 
 #define QERR_QMP_BAD_INPUT_OBJECT \
-    "{ 'class': 'QMPBadInputObject', 'data': { 'expected': %s } }"
+    -1, "{ 'class': 'QMPBadInputObject', 'data': { 'expected': %s } }"
 
 #define QERR_QMP_BAD_INPUT_OBJECT_MEMBER \
-    "{ 'class': 'QMPBadInputObjectMember', 'data': { 'member': %s, 'expected': %s } }"
+    -1, "{ 'class': 'QMPBadInputObjectMember', 'data': { 'member': %s, 'expected': %s } }"
 
 #define QERR_QMP_EXTRA_MEMBER \
-    "{ 'class': 'QMPExtraInputObjectMember', 'data': { 'member': %s } }"
+    -1, "{ 'class': 'QMPExtraInputObjectMember', 'data': { 'member': %s } }"
 
 #define QERR_RESET_REQUIRED \
-    "{ 'class': 'ResetRequired', 'data': {} }"
+    -1, "{ 'class': 'ResetRequired', 'data': {} }"
 
 #define QERR_SET_PASSWD_FAILED \
-    "{ 'class': 'SetPasswdFailed', 'data': {} }"
+    -1, "{ 'class': 'SetPasswdFailed', 'data': {} }"
 
 #define QERR_TOO_MANY_FILES \
-    "{ 'class': 'TooManyFiles', 'data': {} }"
+    -1, "{ 'class': 'TooManyFiles', 'data': {} }"
 
 #define QERR_UNDEFINED_ERROR \
-    "{ 'class': 'UndefinedError', 'data': {} }"
+    -1, "{ 'class': 'UndefinedError', 'data': {} }"
 
 #define QERR_UNKNOWN_BLOCK_FORMAT_FEATURE \
-    "{ 'class': 'UnknownBlockFormatFeature', 'data': { 'device': %s, 'format': %s, 'feature': %s } }"
+    -1, "{ 'class': 'UnknownBlockFormatFeature', 'data': { 'device': %s, 'format': %s, 'feature': %s } }"
 
 #define QERR_UNSUPPORTED \
-    "{ 'class': 'Unsupported', 'data': {} }"
+    -1, "{ 'class': 'Unsupported', 'data': {} }"
 
 #define QERR_VIRTFS_FEATURE_BLOCKS_MIGRATION \
-    "{ 'class': 'VirtFSFeatureBlocksMigration', 'data': { 'path': %s, 'tag': %s } }"
+    -1, "{ 'class': 'VirtFSFeatureBlocksMigration', 'data': { 'path': %s, 'tag': %s } }"
 
 #define QERR_VNC_SERVER_FAILED \
-    "{ 'class': 'VNCServerFailed', 'data': { 'target': %s } }"
+    -1, "{ 'class': 'VNCServerFailed', 'data': { 'target': %s } }"
 
 #define QERR_SOCKET_CONNECT_FAILED \
-    "{ 'class': 'SockConnectFailed', 'data': {} }"
+    -1, "{ 'class': 'SockConnectFailed', 'data': {} }"
 
 #define QERR_SOCKET_LISTEN_FAILED \
-    "{ 'class': 'SockListenFailed', 'data': {} }"
+    -1, "{ 'class': 'SockListenFailed', 'data': {} }"
 
 #define QERR_SOCKET_BIND_FAILED \
-    "{ 'class': 'SockBindFailed', 'data': {} }"
+    -1, "{ 'class': 'SockBindFailed', 'data': {} }"
 
 #define QERR_SOCKET_CREATE_FAILED \
-    "{ 'class': 'SockCreateFailed', 'data': {} }"
+    -1, "{ 'class': 'SockCreateFailed', 'data': {} }"
 
 #endif /* QERROR_H */
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 25/35] qerror: add proper ErrorClass value for QERR_ macros
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (23 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 24/35] error, qerror: add ErrorClass argument to error functions Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 26/35] error: add error_get_class() Luiz Capitulino
                   ` (9 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

This commit replaces the place holder value for the ErrorClass
argument with a proper ErrorClass value for all QERR_ macros.

All current errors are mapped to GenericError, except for errors
CommandNotFound, DeviceEncrypted, DeviceNotActive, DeviceNotFound,
KVMMissingCap and MigrationExpected, which are maintained as they
are today.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qerror.h | 140 +++++++++++++++++++++++++++++++--------------------------------
 1 file changed, 70 insertions(+), 70 deletions(-)

diff --git a/qerror.h b/qerror.h
index bcc93f8..4f92218 100644
--- a/qerror.h
+++ b/qerror.h
@@ -45,214 +45,214 @@ char *qerror_format(const char *fmt, QDict *error);
  * Use scripts/check-qerror.sh to check.
  */
 #define QERR_ADD_CLIENT_FAILED \
-    -1, "{ 'class': 'AddClientFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'AddClientFailed', 'data': {} }"
 
 #define QERR_AMBIGUOUS_PATH \
-    -1, "{ 'class': 'AmbiguousPath', 'data': { 'path': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'AmbiguousPath', 'data': { 'path': %s } }"
 
 #define QERR_BAD_BUS_FOR_DEVICE \
-    -1, "{ 'class': 'BadBusForDevice', 'data': { 'device': %s, 'bad_bus_type': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BadBusForDevice', 'data': { 'device': %s, 'bad_bus_type': %s } }"
 
 #define QERR_BASE_NOT_FOUND \
-    -1, "{ 'class': 'BaseNotFound', 'data': { 'base': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BaseNotFound', 'data': { 'base': %s } }"
 
 #define QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED \
-    -1, "{ 'class': 'BlockFormatFeatureNotSupported', 'data': { 'format': %s, 'name': %s, 'feature': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BlockFormatFeatureNotSupported', 'data': { 'format': %s, 'name': %s, 'feature': %s } }"
 
 #define QERR_BUFFER_OVERRUN \
-    -1, "{ 'class': 'BufferOverrun', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BufferOverrun', 'data': {} }"
 
 #define QERR_BUS_NO_HOTPLUG \
-    -1, "{ 'class': 'BusNoHotplug', 'data': { 'bus': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BusNoHotplug', 'data': { 'bus': %s } }"
 
 #define QERR_BUS_NOT_FOUND \
-    -1, "{ 'class': 'BusNotFound', 'data': { 'bus': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BusNotFound', 'data': { 'bus': %s } }"
 
 #define QERR_COMMAND_DISABLED \
-    -1, "{ 'class': 'CommandDisabled', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'CommandDisabled', 'data': { 'name': %s } }"
 
 #define QERR_COMMAND_NOT_FOUND \
-    -1, "{ 'class': 'CommandNotFound', 'data': { 'name': %s } }"
+    ERROR_CLASS_COMMAND_NOT_FOUND, "{ 'class': 'CommandNotFound', 'data': { 'name': %s } }"
 
 #define QERR_DEVICE_ENCRYPTED \
-    -1, "{ 'class': 'DeviceEncrypted', 'data': { 'device': %s, 'filename': %s } }"
+    ERROR_CLASS_DEVICE_ENCRYPTED, "{ 'class': 'DeviceEncrypted', 'data': { 'device': %s, 'filename': %s } }"
 
 #define QERR_DEVICE_FEATURE_BLOCKS_MIGRATION \
-    -1, "{ 'class': 'DeviceFeatureBlocksMigration', 'data': { 'device': %s, 'feature': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceFeatureBlocksMigration', 'data': { 'device': %s, 'feature': %s } }"
 
 #define QERR_DEVICE_HAS_NO_MEDIUM \
-    -1, "{ 'class': 'DeviceHasNoMedium', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceHasNoMedium', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_INIT_FAILED \
-    -1, "{ 'class': 'DeviceInitFailed', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceInitFailed', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_IN_USE \
-    -1, "{ 'class': 'DeviceInUse', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceInUse', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_IS_READ_ONLY \
-    -1, "{ 'class': 'DeviceIsReadOnly', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceIsReadOnly', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_LOCKED \
-    -1, "{ 'class': 'DeviceLocked', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceLocked', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_MULTIPLE_BUSSES \
-    -1, "{ 'class': 'DeviceMultipleBusses', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceMultipleBusses', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NO_BUS \
-    -1, "{ 'class': 'DeviceNoBus', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceNoBus', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NO_HOTPLUG \
-    -1, "{ 'class': 'DeviceNoHotplug', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceNoHotplug', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NOT_ACTIVE \
-    -1, "{ 'class': 'DeviceNotActive', 'data': { 'device': %s } }"
+    ERROR_CLASS_DEVICE_NOT_ACTIVE, "{ 'class': 'DeviceNotActive', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NOT_ENCRYPTED \
-    -1, "{ 'class': 'DeviceNotEncrypted', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceNotEncrypted', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NOT_FOUND \
-    -1, "{ 'class': 'DeviceNotFound', 'data': { 'device': %s } }"
+    ERROR_CLASS_DEVICE_NOT_FOUND, "{ 'class': 'DeviceNotFound', 'data': { 'device': %s } }"
 
 #define QERR_DEVICE_NOT_REMOVABLE \
-    -1, "{ 'class': 'DeviceNotRemovable', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceNotRemovable', 'data': { 'device': %s } }"
 
 #define QERR_DUPLICATE_ID \
-    -1, "{ 'class': 'DuplicateId', 'data': { 'id': %s, 'object': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DuplicateId', 'data': { 'id': %s, 'object': %s } }"
 
 #define QERR_FD_NOT_FOUND \
-    -1, "{ 'class': 'FdNotFound', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'FdNotFound', 'data': { 'name': %s } }"
 
 #define QERR_FD_NOT_SUPPLIED \
-    -1, "{ 'class': 'FdNotSupplied', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'FdNotSupplied', 'data': {} }"
 
 #define QERR_FEATURE_DISABLED \
-    -1, "{ 'class': 'FeatureDisabled', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'FeatureDisabled', 'data': { 'name': %s } }"
 
 #define QERR_INVALID_BLOCK_FORMAT \
-    -1, "{ 'class': 'InvalidBlockFormat', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidBlockFormat', 'data': { 'name': %s } }"
 
 #define QERR_INVALID_OPTION_GROUP \
-    -1, "{ 'class': 'InvalidOptionGroup', 'data': { 'group': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidOptionGroup', 'data': { 'group': %s } }"
 
 #define QERR_INVALID_PARAMETER \
-    -1, "{ 'class': 'InvalidParameter', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidParameter', 'data': { 'name': %s } }"
 
 #define QERR_INVALID_PARAMETER_COMBINATION \
-    -1, "{ 'class': 'InvalidParameterCombination', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidParameterCombination', 'data': {} }"
 
 #define QERR_INVALID_PARAMETER_TYPE \
-    -1, "{ 'class': 'InvalidParameterType', 'data': { 'name': %s,'expected': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidParameterType', 'data': { 'name': %s,'expected': %s } }"
 
 #define QERR_INVALID_PARAMETER_VALUE \
-    -1, "{ 'class': 'InvalidParameterValue', 'data': { 'name': %s, 'expected': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidParameterValue', 'data': { 'name': %s, 'expected': %s } }"
 
 #define QERR_INVALID_PASSWORD \
-    -1, "{ 'class': 'InvalidPassword', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidPassword', 'data': {} }"
 
 #define QERR_IO_ERROR \
-    -1, "{ 'class': 'IOError', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'IOError', 'data': {} }"
 
 #define QERR_JSON_PARSE_ERROR \
-    -1, "{ 'class': 'JSONParseError', 'data': { 'message': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'JSONParseError', 'data': { 'message': %s } }"
 
 #define QERR_JSON_PARSING \
-    -1, "{ 'class': 'JSONParsing', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'JSONParsing', 'data': {} }"
 
 #define QERR_KVM_MISSING_CAP \
-    -1, "{ 'class': 'KVMMissingCap', 'data': { 'capability': %s, 'feature': %s } }"
+    ERROR_CLASS_K_V_M_MISSING_CAP, "{ 'class': 'KVMMissingCap', 'data': { 'capability': %s, 'feature': %s } }"
 
 #define QERR_MIGRATION_ACTIVE \
-    -1, "{ 'class': 'MigrationActive', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'MigrationActive', 'data': {} }"
 
 #define QERR_MIGRATION_NOT_SUPPORTED \
-    -1, "{ 'class': 'MigrationNotSupported', 'data': {'device': %s} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'MigrationNotSupported', 'data': {'device': %s} }"
 
 #define QERR_MIGRATION_EXPECTED \
-    -1, "{ 'class': 'MigrationExpected', 'data': {} }"
+    ERROR_CLASS_MIGRATION_EXPECTED, "{ 'class': 'MigrationExpected', 'data': {} }"
 
 #define QERR_MISSING_PARAMETER \
-    -1, "{ 'class': 'MissingParameter', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'MissingParameter', 'data': { 'name': %s } }"
 
 #define QERR_NO_BUS_FOR_DEVICE \
-    -1, "{ 'class': 'NoBusForDevice', 'data': { 'device': %s, 'bus': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'NoBusForDevice', 'data': { 'device': %s, 'bus': %s } }"
 
 #define QERR_NOT_SUPPORTED \
-    -1, "{ 'class': 'NotSupported', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'NotSupported', 'data': {} }"
 
 #define QERR_OPEN_FILE_FAILED \
-    -1, "{ 'class': 'OpenFileFailed', 'data': { 'filename': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'OpenFileFailed', 'data': { 'filename': %s } }"
 
 #define QERR_PERMISSION_DENIED \
-    -1, "{ 'class': 'PermissionDenied', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PermissionDenied', 'data': {} }"
 
 #define QERR_PROPERTY_NOT_FOUND \
-    -1, "{ 'class': 'PropertyNotFound', 'data': { 'device': %s, 'property': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyNotFound', 'data': { 'device': %s, 'property': %s } }"
 
 #define QERR_PROPERTY_VALUE_BAD \
-    -1, "{ 'class': 'PropertyValueBad', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyValueBad', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
 
 #define QERR_PROPERTY_VALUE_IN_USE \
-    -1, "{ 'class': 'PropertyValueInUse', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyValueInUse', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
 
 #define QERR_PROPERTY_VALUE_NOT_FOUND \
-    -1, "{ 'class': 'PropertyValueNotFound', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyValueNotFound', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
 
 #define QERR_PROPERTY_VALUE_NOT_POWER_OF_2 \
-    -1, "{ 'class': 'PropertyValueNotPowerOf2', 'data': { " \
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyValueNotPowerOf2', 'data': { " \
     "'device': %s, 'property': %s, 'value': %"PRId64" } }"
 
 #define QERR_PROPERTY_VALUE_OUT_OF_RANGE \
-    -1, "{ 'class': 'PropertyValueOutOfRange', 'data': { 'device': %s, 'property': %s, 'value': %"PRId64", 'min': %"PRId64", 'max': %"PRId64" } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyValueOutOfRange', 'data': { 'device': %s, 'property': %s, 'value': %"PRId64", 'min': %"PRId64", 'max': %"PRId64" } }"
 
 #define QERR_QGA_COMMAND_FAILED \
-    -1, "{ 'class': 'QgaCommandFailed', 'data': { 'message': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'QgaCommandFailed', 'data': { 'message': %s } }"
 
 #define QERR_QGA_LOGGING_FAILED \
-    -1, "{ 'class': 'QgaLoggingFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'QgaLoggingFailed', 'data': {} }"
 
 #define QERR_QMP_BAD_INPUT_OBJECT \
-    -1, "{ 'class': 'QMPBadInputObject', 'data': { 'expected': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'QMPBadInputObject', 'data': { 'expected': %s } }"
 
 #define QERR_QMP_BAD_INPUT_OBJECT_MEMBER \
-    -1, "{ 'class': 'QMPBadInputObjectMember', 'data': { 'member': %s, 'expected': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'QMPBadInputObjectMember', 'data': { 'member': %s, 'expected': %s } }"
 
 #define QERR_QMP_EXTRA_MEMBER \
-    -1, "{ 'class': 'QMPExtraInputObjectMember', 'data': { 'member': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'QMPExtraInputObjectMember', 'data': { 'member': %s } }"
 
 #define QERR_RESET_REQUIRED \
-    -1, "{ 'class': 'ResetRequired', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'ResetRequired', 'data': {} }"
 
 #define QERR_SET_PASSWD_FAILED \
-    -1, "{ 'class': 'SetPasswdFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'SetPasswdFailed', 'data': {} }"
 
 #define QERR_TOO_MANY_FILES \
-    -1, "{ 'class': 'TooManyFiles', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'TooManyFiles', 'data': {} }"
 
 #define QERR_UNDEFINED_ERROR \
-    -1, "{ 'class': 'UndefinedError', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'UndefinedError', 'data': {} }"
 
 #define QERR_UNKNOWN_BLOCK_FORMAT_FEATURE \
-    -1, "{ 'class': 'UnknownBlockFormatFeature', 'data': { 'device': %s, 'format': %s, 'feature': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'UnknownBlockFormatFeature', 'data': { 'device': %s, 'format': %s, 'feature': %s } }"
 
 #define QERR_UNSUPPORTED \
-    -1, "{ 'class': 'Unsupported', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'Unsupported', 'data': {} }"
 
 #define QERR_VIRTFS_FEATURE_BLOCKS_MIGRATION \
-    -1, "{ 'class': 'VirtFSFeatureBlocksMigration', 'data': { 'path': %s, 'tag': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'VirtFSFeatureBlocksMigration', 'data': { 'path': %s, 'tag': %s } }"
 
 #define QERR_VNC_SERVER_FAILED \
-    -1, "{ 'class': 'VNCServerFailed', 'data': { 'target': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'VNCServerFailed', 'data': { 'target': %s } }"
 
 #define QERR_SOCKET_CONNECT_FAILED \
-    -1, "{ 'class': 'SockConnectFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'SockConnectFailed', 'data': {} }"
 
 #define QERR_SOCKET_LISTEN_FAILED \
-    -1, "{ 'class': 'SockListenFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'SockListenFailed', 'data': {} }"
 
 #define QERR_SOCKET_BIND_FAILED \
-    -1, "{ 'class': 'SockBindFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'SockBindFailed', 'data': {} }"
 
 #define QERR_SOCKET_CREATE_FAILED \
-    -1, "{ 'class': 'SockCreateFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'SockCreateFailed', 'data': {} }"
 
 #endif /* QERROR_H */
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 26/35] error: add error_get_class()
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (24 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 25/35] qerror: add proper ErrorClass value for QERR_ macros Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 27/35] hmp: hmp_change(): use error_get_class() Luiz Capitulino
                   ` (8 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 error.c | 5 +++++
 error.h | 5 +++++
 2 files changed, 10 insertions(+)

diff --git a/error.c b/error.c
index 648706a..2d34cde 100644
--- a/error.c
+++ b/error.c
@@ -64,6 +64,11 @@ bool error_is_set(Error **errp)
     return (errp && *errp);
 }
 
+ErrorClass error_get_class(const Error *err)
+{
+    return err->err_class;
+}
+
 const char *error_get_pretty(Error *err)
 {
     return err->msg;
diff --git a/error.h b/error.h
index 9678752..114e24b 100644
--- a/error.h
+++ b/error.h
@@ -35,6 +35,11 @@ void error_set(Error **err, ErrorClass err_class, const char *fmt, ...) GCC_FMT_
  */
 bool error_is_set(Error **err);
 
+/*
+ * Get the error class of an error object.
+ */
+ErrorClass error_get_class(const Error *err);
+
 /**
  * Returns an exact copy of the error passed as an argument.
  */
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 27/35] hmp: hmp_change(): use error_get_class()
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (25 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 26/35] error: add error_get_class() Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 28/35] error: drop unused functions Luiz Capitulino
                   ` (7 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

The error_is_type() function is going to be dropped.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 hmp.c | 3 ++-
 1 file changed, 2 insertions(+), 1 deletion(-)

diff --git a/hmp.c b/hmp.c
index 3a9688d..5900251 100644
--- a/hmp.c
+++ b/hmp.c
@@ -799,7 +799,8 @@ void hmp_change(Monitor *mon, const QDict *qdict)
     }
 
     qmp_change(device, target, !!arg, arg, &err);
-    if (error_is_type(err, QERR_DEVICE_ENCRYPTED)) {
+    if (error_is_set(&err) &&
+        error_get_class(err) == ERROR_CLASS_DEVICE_ENCRYPTED) {
         error_free(err);
         monitor_read_block_device_key(mon, device, NULL, NULL);
         return;
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 28/35] error: drop unused functions
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (26 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 27/35] hmp: hmp_change(): use error_get_class() Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 29/35] qmp: switch to the new error format on the wire Luiz Capitulino
                   ` (6 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Besides of being unused, they operate on the current error format,
which is going to be replaced soon.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 error.c     | 48 ------------------------------------------------
 error.h     | 16 ----------------
 error_int.h |  1 -
 3 files changed, 65 deletions(-)

diff --git a/error.c b/error.c
index 2d34cde..b1d5131 100644
--- a/error.c
+++ b/error.c
@@ -74,29 +74,6 @@ const char *error_get_pretty(Error *err)
     return err->msg;
 }
 
-const char *error_get_field(Error *err, const char *field)
-{
-    if (strcmp(field, "class") == 0) {
-        return qdict_get_str(err->obj, field);
-    } else {
-        QDict *dict = qdict_get_qdict(err->obj, "data");
-        return qdict_get_str(dict, field);
-    }
-}
-
-QDict *error_get_data(Error *err)
-{
-    QDict *data = qdict_get_qdict(err->obj, "data");
-    QINCREF(data);
-    return data;
-}
-
-void error_set_field(Error *err, const char *field, const char *value)
-{
-    QDict *dict = qdict_get_qdict(err->obj, "data");
-    qdict_put(dict, field, qstring_from_str(value));
-}
-
 void error_free(Error *err)
 {
     if (err) {
@@ -106,31 +83,6 @@ void error_free(Error *err)
     }
 }
 
-bool error_is_type(Error *err, ErrorClass err_class, const char *fmt)
-{
-    const char *error_class;
-    char *ptr;
-    char *end;
-
-    if (!err) {
-        return false;
-    }
-
-    ptr = strstr(fmt, "'class': '");
-    assert(ptr != NULL);
-    ptr += strlen("'class': '");
-
-    end = strchr(ptr, '\'');
-    assert(end != NULL);
-
-    error_class = error_get_field(err, "class");
-    if (strlen(error_class) != end - ptr) {
-        return false;
-    }
-
-    return strncmp(ptr, error_class, end - ptr) == 0;
-}
-
 void error_propagate(Error **dst_err, Error *local_err)
 {
     if (dst_err && !*dst_err) {
diff --git a/error.h b/error.h
index 114e24b..5336fc5 100644
--- a/error.h
+++ b/error.h
@@ -51,16 +51,6 @@ Error *error_copy(const Error *err);
 const char *error_get_pretty(Error *err);
 
 /**
- * Get an individual named error field.
- */
-const char *error_get_field(Error *err, const char *field);
-
-/**
- * Get an individual named error field.
- */
-void error_set_field(Error *err, const char *field, const char *value);
-
-/**
  * Propagate an error to an indirect pointer to an error.  This function will
  * always transfer ownership of the error reference and handles the case where
  * dst_err is NULL correctly.  Errors after the first are discarded.
@@ -72,10 +62,4 @@ void error_propagate(Error **dst_err, Error *local_err);
  */
 void error_free(Error *err);
 
-/**
- * Determine if an error is of a speific type (based on the qerror format).
- * Non-QEMU users should get the `class' field to identify the error type.
- */
-bool error_is_type(Error *err, ErrorClass err_class, const char *fmt);
-
 #endif
diff --git a/error_int.h b/error_int.h
index 5e39424..4b00d08 100644
--- a/error_int.h
+++ b/error_int.h
@@ -22,7 +22,6 @@
  *
  * These are used to convert QErrors to Errors
  */
-QDict *error_get_data(Error *err);
 QObject *error_get_qobject(Error *err);
 void error_set_qobject(Error **errp, QObject *obj);
   
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 29/35] qmp: switch to the new error format on the wire
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (27 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 28/35] error: drop unused functions Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 30/35] qemu-ga: " Luiz Capitulino
                   ` (5 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

IMPORTANT: this BREAKS QMP's compatibility for the error response.

This commit changes QMP's wire protocol to make use of the simpler
error format introduced by previous commits.

There are two important (and mostly incompatible) changes:

 1. Almost all error classes have been replaced by GenericError. The
    only classes that are still supported for compatibility with
    libvirt are: CommandNotFound, DeviceNotActive, KVMMissingCap,
    DeviceNotFound and MigrationExpected

 2. The 'data' field of the error dictionary is gone

As an example, an error response like:

  { "error": { "class": "DeviceNotRemovable",
               "data": { "device": "virtio0" },
               "desc": "Device 'virtio0' is not removable" } }

Will now be emitted as:

  { "error": { "class": "GenericError",
               "desc": "Device 'virtio0' is not removable" } }

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 QMP/qmp-spec.txt | 10 +++-------
 monitor.c        | 18 +++++++++++++-----
 qapi-schema.json | 55 -------------------------------------------------------
 qmp-commands.hx  |  4 ++--
 4 files changed, 18 insertions(+), 69 deletions(-)

diff --git a/QMP/qmp-spec.txt b/QMP/qmp-spec.txt
index 1ba916c..a277896 100644
--- a/QMP/qmp-spec.txt
+++ b/QMP/qmp-spec.txt
@@ -106,14 +106,11 @@ completed because of an error condition.
 
 The format is:
 
-{ "error": { "class": json-string, "data": json-object, "desc": json-string },
-  "id": json-value }
+{ "error": { "class": json-string, "desc": json-string }, "id": json-value }
 
  Where,
 
-- The "class" member contains the error class name (eg. "ServiceUnavailable")
-- The "data" member contains specific error data and is defined in a
-  per-command basis, it will be an empty json-object if the error has no data
+- The "class" member contains the error class name (eg. "GenericError")
 - The "desc" member is a human-readable error message. Clients should
   not attempt to parse this message.
 - The "id" member contains the transaction identification associated with
@@ -173,8 +170,7 @@ S: {"return": {"enabled": true, "present": true}, "id": "example"}
 ------------------
 
 C: { "execute": }
-S: {"error": {"class": "JSONParsing", "desc": "Invalid JSON syntax", "data":
-{}}}
+S: {"error": {"class": "GenericError", "desc": "Invalid JSON syntax" } }
 
 3.5 Powerdown event
 -------------------
diff --git a/monitor.c b/monitor.c
index aa57167..3694590 100644
--- a/monitor.c
+++ b/monitor.c
@@ -353,16 +353,26 @@ static void monitor_json_emitter(Monitor *mon, const QObject *data)
     QDECREF(json);
 }
 
+static QDict *build_qmp_error_dict(const QError *err)
+{
+    QObject *obj;
+
+    obj = qobject_from_jsonf("{ 'error': { 'class': %s, 'desc': %p } }",
+                             ErrorClass_lookup[err->err_class],
+                             qerror_human(err));
+
+    return qobject_to_qdict(obj);
+}
+
 static void monitor_protocol_emitter(Monitor *mon, QObject *data)
 {
     QDict *qmp;
 
     trace_monitor_protocol_emitter(mon);
 
-    qmp = qdict_new();
-
     if (!monitor_has_error(mon)) {
         /* success response */
+        qmp = qdict_new();
         if (data) {
             qobject_incref(data);
             qdict_put_obj(qmp, "return", data);
@@ -372,9 +382,7 @@ static void monitor_protocol_emitter(Monitor *mon, QObject *data)
         }
     } else {
         /* error response */
-        qdict_put(mon->error->error, "desc", qerror_human(mon->error));
-        qdict_put(qmp, "error", mon->error->error);
-        QINCREF(mon->error->error);
+        qmp = build_qmp_error_dict(mon->error);
         QDECREF(mon->error);
         mon->error = NULL;
     }
diff --git a/qapi-schema.json b/qapi-schema.json
index 8f670f3..b9c05ca 100644
--- a/qapi-schema.json
+++ b/qapi-schema.json
@@ -657,7 +657,6 @@
 # Returns information about the current VNC server
 #
 # Returns: @VncInfo
-#          If VNC support is not compiled in, FeatureDisabled
 #
 # Since: 0.14.0
 ##
@@ -1041,9 +1040,6 @@
 #                       virtual address (defaults to CPU 0)
 #
 # Returns: Nothing on success
-#          If @cpu is not a valid VCPU, InvalidParameterValue
-#          If @filename cannot be opened, OpenFileFailed
-#          If an I/O error occurs while writing the file, IOError
 #
 # Since: 0.14.0
 #
@@ -1064,8 +1060,6 @@
 # @filename: the file to save the memory to as binary data
 #
 # Returns: Nothing on success
-#          If @filename cannot be opened, OpenFileFailed
-#          If an I/O error occurs while writing the file, IOError
 #
 # Since: 0.14.0
 #
@@ -1107,7 +1101,6 @@
 # Injects an Non-Maskable Interrupt into all guest's VCPUs.
 #
 # Returns:  If successful, nothing
-#           If the Virtual Machine doesn't support NMI injection, Unsupported
 #
 # Since:  0.14.0
 #
@@ -1158,7 +1151,6 @@
 # Returns: nothing on success
 #          If @device is not a valid block device, DeviceNotFound
 #          If @device is not encrypted, DeviceNotEncrypted
-#          If @password is not valid for this device, InvalidPassword
 #
 # Notes:  Not all block formats support encryption and some that do are not
 #         able to validate that a password is correct.  Disk corruption may
@@ -1199,11 +1191,6 @@
 #
 # Returns: nothing on success
 #          If @device is not a valid block device, DeviceNotFound
-#          If @size is negative, InvalidParameterValue
-#          If the block device has no medium inserted, DeviceHasNoMedium
-#          If the block device does not support resize, Unsupported
-#          If the block device is read-only, DeviceIsReadOnly
-#          If a long-running operation is using the device, DeviceInUse
 #
 # Since: 0.14.0
 ##
@@ -1265,10 +1252,6 @@
 #
 # Returns: nothing on success
 #          If @device is not a valid block device, DeviceNotFound
-#          If @device is busy, DeviceInUse will be returned
-#          If @snapshot-file can't be created, OpenFileFailed
-#          If @snapshot-file can't be opened, OpenFileFailed
-#          If @format is invalid, InvalidBlockFormat
 #
 # Note: The transaction aborts on the first failure.  Therefore, there will
 # be only one device or snapshot file returned in an error condition, and
@@ -1297,8 +1280,6 @@
 #
 # Returns: nothing on success
 #          If @device is not a valid block device, DeviceNotFound
-#          If @snapshot-file can't be opened, OpenFileFailed
-#          If @format is invalid, InvalidBlockFormat
 #
 # Since 0.14.0
 ##
@@ -1500,11 +1481,6 @@
 #
 # Returns: Nothing on success
 #          If Spice is not enabled, DeviceNotFound
-#          If @protocol does not support connected, InvalidParameter
-#          If @protocol is invalid, InvalidParameter
-#          If any other error occurs, SetPasswdFailed
-#
-# Notes: If VNC is not enabled, SetPasswdFailed is returned.
 #
 # Since: 0.14.0
 ##
@@ -1526,8 +1502,6 @@
 #
 # Returns: Nothing on success
 #          If @protocol is `spice' and Spice is not active, DeviceNotFound
-#          If an error occurs setting password expiration, SetPasswdFailed
-#          If @protocol is not `spice' or 'vnc', InvalidParameter
 #
 # Since: 0.14.0
 #
@@ -1550,8 +1524,6 @@
 #
 # Returns:  Nothing on success
 #           If @device is not a valid block device, DeviceNotFound
-#           If @device is not removable and @force is false, DeviceNotRemovable
-#           If @force is false and @device is locked, DeviceLocked
 #
 # Notes:    Ejecting a device will no media results in success
 #
@@ -1594,7 +1566,6 @@
 #
 # Returns: Nothing on success.
 #          If @device is not a valid block device, DeviceNotFound
-#          If @format is not a valid block format, InvalidBlockFormat
 #          If the new block device is encrypted, DeviceEncrypted.  Note that
 #          if this error is returned, the device has been opened successfully
 #          and an additional call to @block_passwd is required to set the
@@ -1630,7 +1601,6 @@
 #
 # Returns: Nothing on success
 #          If @device is not a valid block device, DeviceNotFound
-#          If the argument combination is invalid, InvalidParameterCombination
 #
 # Since: 1.1
 ##
@@ -1664,11 +1634,7 @@
 # @speed:  #optional the maximum speed, in bytes per second
 #
 # Returns: Nothing on success
-#          If streaming is already active on this device, DeviceInUse
 #          If @device does not exist, DeviceNotFound
-#          If image streaming is not supported by this device, NotSupported
-#          If @base does not exist, BaseNotFound
-#          If @speed is invalid, InvalidParameter
 #
 # Since: 1.1
 ##
@@ -1690,8 +1656,6 @@
 #          Defaults to 0.
 #
 # Returns: Nothing on success
-#          If the job type does not support throttling, NotSupported
-#          If the speed value is invalid, InvalidParameter
 #          If streaming is not active on this device, DeviceNotActive
 #
 # Since: 1.1
@@ -1722,7 +1686,6 @@
 #
 # Returns: Nothing on success
 #          If streaming is not active on this device, DeviceNotActive
-#          If cancellation already in progress, DeviceInUse
 #
 # Since: 1.1
 ##
@@ -1792,8 +1755,6 @@
 # format.
 #
 # Returns: Nothing on success
-#          If @filename cannot be opened, OpenFileFailed
-#          If an I/O error occurs while writing the file, IOError
 #
 # Since: 1.1
 ##
@@ -1808,7 +1769,6 @@
 #
 # Returns: Nothing on success
 #          If @id is not a valid device, DeviceNotFound
-#          If the device does not support unplug, BusNoHotplug
 #
 # Notes: When this command completes, the device may not be removed from the
 #        guest.  Hot removal is an operation that requires guest cooperation.
@@ -1849,14 +1809,6 @@
 # want to dump all guest's memory, please specify the start @begin and @length
 #
 # Returns: nothing on success
-#          If @begin contains an invalid address, InvalidParameter
-#          If only one of @begin and @length is specified, MissingParameter
-#          If @protocol stats with "fd:", and the fd cannot be found, FdNotFound
-#          If @protocol starts with "file:", and the file cannot be
-#             opened, OpenFileFailed
-#          If @protocol does not start with "fd:" or "file:", InvalidParameter
-#          If an I/O error occurs while writing the file, IOError
-#          If the target does not support this command, Unsupported
 #
 # Since: 1.2
 ##
@@ -1883,10 +1835,6 @@
 #
 # Returns: Nothing on success
 #          If @type is not a valid network backend, DeviceNotFound
-#          If @id is not a valid identifier, InvalidParameterValue
-#          if @id already exists, DuplicateId
-#          If @props contains an invalid parameter for this backend,
-#            InvalidParameter
 ##
 { 'command': 'netdev_add',
   'data': {'type': 'str', 'id': 'str', '*props': '**'},
@@ -2206,8 +2154,6 @@
 # @fdname: file descriptor name
 #
 # Returns: Nothing on success
-#          If file descriptor was not received, FdNotSupplied
-#          If @fdname is not valid, InvalidParameterType
 #
 # Since: 0.14.0
 #
@@ -2227,7 +2173,6 @@
 # @fdname: file descriptor name
 #
 # Returns: Nothing on success
-#          If @fdname is not found, FdNotFound
 #
 # Since: 0.14.0
 ##
diff --git a/qmp-commands.hx b/qmp-commands.hx
index ac46638..e07c7b0 100644
--- a/qmp-commands.hx
+++ b/qmp-commands.hx
@@ -435,8 +435,8 @@ Example:
 -> { "execute": "inject-nmi" }
 <- { "return": {} }
 
-Note: inject-nmi is only supported for x86 guest currently, it will
-      returns "Unsupported" error for non-x86 guest.
+Note: inject-nmi fails when the guest doesn't support injecting.
+      Currently, only x86 guests do.
 
 EQMP
 
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 30/35] qemu-ga: switch to the new error format on the wire
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (28 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 29/35] qmp: switch to the new error format on the wire Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 31/35] error: drop error_get_qobject()/error_set_qobject() Luiz Capitulino
                   ` (4 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

IMPORTANT: this BREAKS qemu-ga compatibility for the error response.

Instead of returning something like:

{ "error": { "class": "InvalidParameterValue",
             "data": {"name": "mode", "expected": "halt|powerdown|reboot" } } }

qemu-ga now returns:

 { "error": { "class": "GenericError",
              "desc": "Parameter 'mode' expects halt|powerdown|reboot" } }

Notice that this is also a bug fix, as qemu-ga wasn't returning the
human message.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 Makefile.objs       |  1 +
 qapi/qmp-core.h     |  1 +
 qapi/qmp-dispatch.c | 10 +++++++++-
 qemu-ga.c           |  4 ++--
 4 files changed, 13 insertions(+), 3 deletions(-)

diff --git a/Makefile.objs b/Makefile.objs
index 5ebbcfa..8454b53 100644
--- a/Makefile.objs
+++ b/Makefile.objs
@@ -211,6 +211,7 @@ common-obj-$(CONFIG_SMARTCARD_NSS) += $(libcacard-y)
 # qapi
 
 qapi-obj-y = qapi/
+qapi-obj-y += qapi-types.o qapi-visit.o
 
 common-obj-y += qmp-marshal.o qapi-visit.o qapi-types.o
 common-obj-y += qmp.o hmp.o
diff --git a/qapi/qmp-core.h b/qapi/qmp-core.h
index b0f64ba..00446cf 100644
--- a/qapi/qmp-core.h
+++ b/qapi/qmp-core.h
@@ -49,6 +49,7 @@ void qmp_disable_command(const char *name);
 void qmp_enable_command(const char *name);
 bool qmp_command_is_enabled(const char *name);
 char **qmp_get_command_list(void);
+QObject *qmp_build_error_object(Error *errp);
 
 #endif
 
diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c
index 122c1a2..ec613f8 100644
--- a/qapi/qmp-dispatch.c
+++ b/qapi/qmp-dispatch.c
@@ -14,6 +14,7 @@
 #include "qemu-objects.h"
 #include "qapi/qmp-core.h"
 #include "json-parser.h"
+#include "qapi-types.h"
 #include "error.h"
 #include "error_int.h"
 #include "qerror.h"
@@ -109,6 +110,13 @@ static QObject *do_qmp_dispatch(QObject *request, Error **errp)
     return ret;
 }
 
+QObject *qmp_build_error_object(Error *errp)
+{
+    return qobject_from_jsonf("{ 'class': %s, 'desc': %s }",
+                              ErrorClass_lookup[error_get_class(errp)],
+                              error_get_pretty(errp));
+}
+
 QObject *qmp_dispatch(QObject *request)
 {
     Error *err = NULL;
@@ -119,7 +127,7 @@ QObject *qmp_dispatch(QObject *request)
 
     rsp = qdict_new();
     if (err) {
-        qdict_put_obj(rsp, "error", error_get_qobject(err));
+        qdict_put_obj(rsp, "error", qmp_build_error_object(err));
         error_free(err);
     } else if (ret) {
         qdict_put_obj(rsp, "return", ret);
diff --git a/qemu-ga.c b/qemu-ga.c
index f1a39ec..39abc50 100644
--- a/qemu-ga.c
+++ b/qemu-ga.c
@@ -515,7 +515,7 @@ static void process_event(JSONMessageParser *parser, QList *tokens)
         } else {
             g_warning("failed to parse event: %s", error_get_pretty(err));
         }
-        qdict_put_obj(qdict, "error", error_get_qobject(err));
+        qdict_put_obj(qdict, "error", qmp_build_error_object(err));
         error_free(err);
     } else {
         qdict = qobject_to_qdict(obj);
@@ -532,7 +532,7 @@ static void process_event(JSONMessageParser *parser, QList *tokens)
             qdict = qdict_new();
             g_warning("unrecognized payload format");
             error_set(&err, QERR_UNSUPPORTED);
-            qdict_put_obj(qdict, "error", error_get_qobject(err));
+            qdict_put_obj(qdict, "error", qmp_build_error_object(err));
             error_free(err);
         }
         ret = send_response(s, QOBJECT(qdict));
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 31/35] error: drop error_get_qobject()/error_set_qobject()
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (29 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 30/35] qemu-ga: " Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 32/35] error, qerror: pass desc string to error calls Luiz Capitulino
                   ` (3 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

error_get_qobject() is unused since last commit, error_set_qobject()
has never been used. Also drops error_int.h.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 error.c             | 20 --------------------
 error_int.h         | 28 ----------------------------
 qapi/qmp-dispatch.c |  1 -
 qemu-ga.c           |  1 -
 4 files changed, 50 deletions(-)
 delete mode 100644 error_int.h

diff --git a/error.c b/error.c
index b1d5131..9d7b35f 100644
--- a/error.c
+++ b/error.c
@@ -15,7 +15,6 @@
 #include "qjson.h"
 #include "qdict.h"
 #include "qapi-types.h"
-#include "error_int.h"
 #include "qerror.h"
 
 struct Error
@@ -91,22 +90,3 @@ void error_propagate(Error **dst_err, Error *local_err)
         error_free(local_err);
     }
 }
-
-QObject *error_get_qobject(Error *err)
-{
-    QINCREF(err->obj);
-    return QOBJECT(err->obj);
-}
-
-void error_set_qobject(Error **errp, QObject *obj)
-{
-    Error *err;
-    if (errp == NULL) {
-        return;
-    }
-    err = g_malloc0(sizeof(*err));
-    err->obj = qobject_to_qdict(obj);
-    qobject_incref(obj);
-
-    *errp = err;
-}
diff --git a/error_int.h b/error_int.h
deleted file mode 100644
index 4b00d08..0000000
--- a/error_int.h
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * QEMU Error Objects
- *
- * Copyright IBM, Corp. 2011
- *
- * Authors:
- *  Anthony Liguori   <aliguori@us.ibm.com>
- *
- * This work is licensed under the terms of the GNU LGPL, version 2.  See
- * the COPYING.LIB file in the top-level directory.
- */
-#ifndef QEMU_ERROR_INT_H
-#define QEMU_ERROR_INT_H
-
-#include "qemu-common.h"
-#include "qobject.h"
-#include "qdict.h"
-#include "error.h"
-
-/**
- * Internal QEMU functions for working with Error.
- *
- * These are used to convert QErrors to Errors
- */
-QObject *error_get_qobject(Error *err);
-void error_set_qobject(Error **errp, QObject *obj);
-  
-#endif
diff --git a/qapi/qmp-dispatch.c b/qapi/qmp-dispatch.c
index ec613f8..4085994 100644
--- a/qapi/qmp-dispatch.c
+++ b/qapi/qmp-dispatch.c
@@ -16,7 +16,6 @@
 #include "json-parser.h"
 #include "qapi-types.h"
 #include "error.h"
-#include "error_int.h"
 #include "qerror.h"
 
 static QDict *qmp_dispatch_check_obj(const QObject *request, Error **errp)
diff --git a/qemu-ga.c b/qemu-ga.c
index 39abc50..8f87621 100644
--- a/qemu-ga.c
+++ b/qemu-ga.c
@@ -28,7 +28,6 @@
 #include "module.h"
 #include "signal.h"
 #include "qerror.h"
-#include "error_int.h"
 #include "qapi/qmp-core.h"
 #include "qga/channel.h"
 #ifdef _WIN32
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 32/35] error, qerror: pass desc string to error calls
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (30 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 31/35] error: drop error_get_qobject()/error_set_qobject() Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 33/35] qerror: drop qerror_table and qerror_format() Luiz Capitulino
                   ` (2 subsequent siblings)
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

This commit changes all QERR_ macros to contain a human message (ie.
the desc string found in qerr_table[]) instead of a json dictionary
in string format.

Before this commit, error_set() and qerror_report() would receive
a json dictionary in string format and build a qobject from it. Now,
both function receive a human message instead and the qobject is
not built anymore.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 error.c  |   3 +-
 error.h  |  10 ++---
 qerror.c |  42 +------------------
 qerror.h | 141 +++++++++++++++++++++++++++++++--------------------------------
 4 files changed, 77 insertions(+), 119 deletions(-)

diff --git a/error.c b/error.c
index 9d7b35f..0e10373 100644
--- a/error.c
+++ b/error.c
@@ -37,9 +37,8 @@ void error_set(Error **errp, ErrorClass err_class, const char *fmt, ...)
     err = g_malloc0(sizeof(*err));
 
     va_start(ap, fmt);
-    err->obj = qobject_to_qdict(qobject_from_jsonv(fmt, &ap));
+    err->msg = g_strdup_vprintf(fmt, ap);
     va_end(ap);
-    err->msg = qerror_format(fmt, err->obj);
     err->err_class = err_class;
 
     *errp = err;
diff --git a/error.h b/error.h
index 5336fc5..96fc203 100644
--- a/error.h
+++ b/error.h
@@ -17,15 +17,15 @@
 #include <stdbool.h>
 
 /**
- * A class representing internal errors within QEMU.  An error has a string
- * typename and optionally a set of named string parameters.
+ * A class representing internal errors within QEMU.  An error has a ErrorClass
+ * code and a human message.
  */
 typedef struct Error Error;
 
 /**
- * Set an indirect pointer to an error given a printf-style format parameter.
- * Currently, qerror.h defines these error formats.  This function is not
- * meant to be used outside of QEMU.
+ * Set an indirect pointer to an error given a ErrorClass value and a
+ * printf-style human message.  This function is not meant to be used outside
+ * of QEMU.
  */
 void error_set(Error **err, ErrorClass err_class, const char *fmt, ...) GCC_FMT_ATTR(3, 4);
 
diff --git a/qerror.c b/qerror.c
index 0bf8aec..dda1427 100644
--- a/qerror.c
+++ b/qerror.c
@@ -342,45 +342,6 @@ static QError *qerror_new(void)
     return qerr;
 }
 
-static QDict *error_obj_from_fmt_no_fail(const char *fmt, va_list *va)
-{
-    QObject *obj;
-    QDict *ret;
-
-    obj = qobject_from_jsonv(fmt, va);
-    if (!obj) {
-        fprintf(stderr, "invalid json in error dict '%s'\n", fmt);
-        abort();
-    }
-    if (qobject_type(obj) != QTYPE_QDICT) {
-        fprintf(stderr, "error is not a dict '%s'\n", fmt);
-        abort();
-    }
-
-    ret = qobject_to_qdict(obj);
-    obj = qdict_get(ret, "class");
-    if (!obj) {
-        fprintf(stderr, "missing 'class' key in '%s'\n", fmt);
-        abort();
-    }
-    if (qobject_type(obj) != QTYPE_QSTRING) {
-        fprintf(stderr, "'class' key value should be a string in '%s'\n", fmt);
-        abort();
-    }
-
-    obj = qdict_get(ret, "data");
-    if (!obj) {
-        fprintf(stderr, "missing 'data' key in '%s'\n", fmt);
-        abort();
-    }
-    if (qobject_type(obj) != QTYPE_QDICT) {
-        fprintf(stderr, "'data' key value should be a dict in '%s'\n", fmt);
-        abort();
-    }
-
-    return ret;
-}
-
 /**
  * qerror_from_info(): Create a new QError from error information
  *
@@ -394,9 +355,8 @@ static QError *qerror_from_info(ErrorClass err_class, const char *fmt,
     qerr = qerror_new();
     loc_save(&qerr->loc);
 
+    qerr->err_msg = g_strdup_vprintf(fmt, *va);
     qerr->err_class = err_class;
-    qerr->error = error_obj_from_fmt_no_fail(fmt, va);
-    qerr->err_msg = qerror_format(fmt, qerr->error);
 
     return qerr;
 }
diff --git a/qerror.h b/qerror.h
index 4f92218..057a8f2 100644
--- a/qerror.h
+++ b/qerror.h
@@ -45,214 +45,213 @@ char *qerror_format(const char *fmt, QDict *error);
  * Use scripts/check-qerror.sh to check.
  */
 #define QERR_ADD_CLIENT_FAILED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'AddClientFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Could not add client"
 
 #define QERR_AMBIGUOUS_PATH \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'AmbiguousPath', 'data': { 'path': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Path '%s' does not uniquely identify an object"
 
 #define QERR_BAD_BUS_FOR_DEVICE \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BadBusForDevice', 'data': { 'device': %s, 'bad_bus_type': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Device '%s' can't go on a %s bus"
 
 #define QERR_BASE_NOT_FOUND \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BaseNotFound', 'data': { 'base': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Base '%s' not found"
 
 #define QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BlockFormatFeatureNotSupported', 'data': { 'format': %s, 'name': %s, 'feature': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Block format '%s' used by device '%s' does not support feature '%s'"
 
 #define QERR_BUFFER_OVERRUN \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BufferOverrun', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "An internal buffer overran"
 
 #define QERR_BUS_NO_HOTPLUG \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BusNoHotplug', 'data': { 'bus': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Bus '%s' does not support hotplugging"
 
 #define QERR_BUS_NOT_FOUND \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'BusNotFound', 'data': { 'bus': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Bus '%s' not found"
 
 #define QERR_COMMAND_DISABLED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'CommandDisabled', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "The command %s has been disabled for this instance"
 
 #define QERR_COMMAND_NOT_FOUND \
-    ERROR_CLASS_COMMAND_NOT_FOUND, "{ 'class': 'CommandNotFound', 'data': { 'name': %s } }"
+    ERROR_CLASS_COMMAND_NOT_FOUND, "The command %s has not been found"
 
 #define QERR_DEVICE_ENCRYPTED \
-    ERROR_CLASS_DEVICE_ENCRYPTED, "{ 'class': 'DeviceEncrypted', 'data': { 'device': %s, 'filename': %s } }"
+    ERROR_CLASS_DEVICE_ENCRYPTED, "'%s' (%s) is encrypted"
 
 #define QERR_DEVICE_FEATURE_BLOCKS_MIGRATION \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceFeatureBlocksMigration', 'data': { 'device': %s, 'feature': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Migration is disabled when using feature '%s' in device '%s'"
 
 #define QERR_DEVICE_HAS_NO_MEDIUM \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceHasNoMedium', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Device '%s' has no medium"
 
 #define QERR_DEVICE_INIT_FAILED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceInitFailed', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Device '%s' could not be initialized"
 
 #define QERR_DEVICE_IN_USE \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceInUse', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Device '%s' is in use"
 
 #define QERR_DEVICE_IS_READ_ONLY \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceIsReadOnly', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Device '%s' is read only"
 
 #define QERR_DEVICE_LOCKED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceLocked', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Device '%s' is locked"
 
 #define QERR_DEVICE_MULTIPLE_BUSSES \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceMultipleBusses', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Device '%s' has multiple child busses"
 
 #define QERR_DEVICE_NO_BUS \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceNoBus', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Device '%s' has no child bus"
 
 #define QERR_DEVICE_NO_HOTPLUG \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceNoHotplug', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Device '%s' does not support hotplugging"
 
 #define QERR_DEVICE_NOT_ACTIVE \
-    ERROR_CLASS_DEVICE_NOT_ACTIVE, "{ 'class': 'DeviceNotActive', 'data': { 'device': %s } }"
+    ERROR_CLASS_DEVICE_NOT_ACTIVE, "Device '%s' has not been activated"
 
 #define QERR_DEVICE_NOT_ENCRYPTED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceNotEncrypted', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Device '%s' is not encrypted"
 
 #define QERR_DEVICE_NOT_FOUND \
-    ERROR_CLASS_DEVICE_NOT_FOUND, "{ 'class': 'DeviceNotFound', 'data': { 'device': %s } }"
+    ERROR_CLASS_DEVICE_NOT_FOUND, "Device '%s' not found"
 
 #define QERR_DEVICE_NOT_REMOVABLE \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DeviceNotRemovable', 'data': { 'device': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Device '%s' is not removable"
 
 #define QERR_DUPLICATE_ID \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'DuplicateId', 'data': { 'id': %s, 'object': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Duplicate ID '%s' for %s"
 
 #define QERR_FD_NOT_FOUND \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'FdNotFound', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "File descriptor named '%s' not found"
 
 #define QERR_FD_NOT_SUPPLIED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'FdNotSupplied', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "No file descriptor supplied via SCM_RIGHTS"
 
 #define QERR_FEATURE_DISABLED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'FeatureDisabled', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "The feature '%s' is not enabled"
 
 #define QERR_INVALID_BLOCK_FORMAT \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidBlockFormat', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Invalid block format '%s'"
 
 #define QERR_INVALID_OPTION_GROUP \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidOptionGroup', 'data': { 'group': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "There is no option group '%s'"
 
 #define QERR_INVALID_PARAMETER \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidParameter', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Invalid parameter '%s'"
 
 #define QERR_INVALID_PARAMETER_COMBINATION \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidParameterCombination', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Invalid parameter combination"
 
 #define QERR_INVALID_PARAMETER_TYPE \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidParameterType', 'data': { 'name': %s,'expected': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Invalid parameter type for '%s', expected: %s"
 
 #define QERR_INVALID_PARAMETER_VALUE \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidParameterValue', 'data': { 'name': %s, 'expected': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Parameter '%s' expects %s"
 
 #define QERR_INVALID_PASSWORD \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'InvalidPassword', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Password incorrect"
 
 #define QERR_IO_ERROR \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'IOError', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "An IO error has occurred"
 
 #define QERR_JSON_PARSE_ERROR \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'JSONParseError', 'data': { 'message': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "JSON parse error, %s"
 
 #define QERR_JSON_PARSING \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'JSONParsing', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Invalid JSON syntax"
 
 #define QERR_KVM_MISSING_CAP \
-    ERROR_CLASS_K_V_M_MISSING_CAP, "{ 'class': 'KVMMissingCap', 'data': { 'capability': %s, 'feature': %s } }"
+    ERROR_CLASS_K_V_M_MISSING_CAP, "Using KVM without %s, %s unavailable"
 
 #define QERR_MIGRATION_ACTIVE \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'MigrationActive', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "There's a migration process in progress"
 
 #define QERR_MIGRATION_NOT_SUPPORTED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'MigrationNotSupported', 'data': {'device': %s} }"
+    ERROR_CLASS_GENERIC_ERROR, "State blocked by non-migratable device '%s'"
 
 #define QERR_MIGRATION_EXPECTED \
-    ERROR_CLASS_MIGRATION_EXPECTED, "{ 'class': 'MigrationExpected', 'data': {} }"
+    ERROR_CLASS_MIGRATION_EXPECTED, "An incoming migration is expected before this command can be executed"
 
 #define QERR_MISSING_PARAMETER \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'MissingParameter', 'data': { 'name': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Parameter '%s' is missing"
 
 #define QERR_NO_BUS_FOR_DEVICE \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'NoBusForDevice', 'data': { 'device': %s, 'bus': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "No '%s' bus found for device '%s'"
 
 #define QERR_NOT_SUPPORTED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'NotSupported', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Not supported"
 
 #define QERR_OPEN_FILE_FAILED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'OpenFileFailed', 'data': { 'filename': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Could not open '%s'"
 
 #define QERR_PERMISSION_DENIED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PermissionDenied', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Insufficient permission to perform this operation"
 
 #define QERR_PROPERTY_NOT_FOUND \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyNotFound', 'data': { 'device': %s, 'property': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Property '%s.%s' not found"
 
 #define QERR_PROPERTY_VALUE_BAD \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyValueBad', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Property '%s.%s' doesn't take value '%s'"
 
 #define QERR_PROPERTY_VALUE_IN_USE \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyValueInUse', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Property '%s.%s' can't take value '%s', it's in use"
 
 #define QERR_PROPERTY_VALUE_NOT_FOUND \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyValueNotFound', 'data': { 'device': %s, 'property': %s, 'value': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Property '%s.%s' can't find value '%s'"
 
 #define QERR_PROPERTY_VALUE_NOT_POWER_OF_2 \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyValueNotPowerOf2', 'data': { " \
-    "'device': %s, 'property': %s, 'value': %"PRId64" } }"
+    ERROR_CLASS_GENERIC_ERROR, "Property %s.%s doesn't take value '%" PRId64 "', it's not a power of 2"
 
 #define QERR_PROPERTY_VALUE_OUT_OF_RANGE \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'PropertyValueOutOfRange', 'data': { 'device': %s, 'property': %s, 'value': %"PRId64", 'min': %"PRId64", 'max': %"PRId64" } }"
+    ERROR_CLASS_GENERIC_ERROR, "Property %s.%s doesn't take value %" PRId64 " (minimum: %" PRId64 ", maximum: %" PRId64 ")"
 
 #define QERR_QGA_COMMAND_FAILED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'QgaCommandFailed', 'data': { 'message': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Guest agent command failed, error was '%s'"
 
 #define QERR_QGA_LOGGING_FAILED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'QgaLoggingFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Guest agent failed to log non-optional log statement"
 
 #define QERR_QMP_BAD_INPUT_OBJECT \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'QMPBadInputObject', 'data': { 'expected': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Expected '%s' in QMP input"
 
 #define QERR_QMP_BAD_INPUT_OBJECT_MEMBER \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'QMPBadInputObjectMember', 'data': { 'member': %s, 'expected': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "QMP input object member '%s' expects '%s'"
 
 #define QERR_QMP_EXTRA_MEMBER \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'QMPExtraInputObjectMember', 'data': { 'member': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "QMP input object member '%s' is unexpected"
 
 #define QERR_RESET_REQUIRED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'ResetRequired', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Resetting the Virtual Machine is required"
 
 #define QERR_SET_PASSWD_FAILED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'SetPasswdFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Could not set password"
 
 #define QERR_TOO_MANY_FILES \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'TooManyFiles', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Too many open files"
 
 #define QERR_UNDEFINED_ERROR \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'UndefinedError', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "An undefined error has occurred"
 
 #define QERR_UNKNOWN_BLOCK_FORMAT_FEATURE \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'UnknownBlockFormatFeature', 'data': { 'device': %s, 'format': %s, 'feature': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "'%s' uses a %s feature which is not supported by this qemu version: %s"
 
 #define QERR_UNSUPPORTED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'Unsupported', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "this feature or command is not currently supported"
 
 #define QERR_VIRTFS_FEATURE_BLOCKS_MIGRATION \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'VirtFSFeatureBlocksMigration', 'data': { 'path': %s, 'tag': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Migration is disabled when VirtFS export path '%s' is mounted in the guest using mount_tag '%s'"
 
 #define QERR_VNC_SERVER_FAILED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'VNCServerFailed', 'data': { 'target': %s } }"
+    ERROR_CLASS_GENERIC_ERROR, "Could not start VNC server on %s"
 
 #define QERR_SOCKET_CONNECT_FAILED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'SockConnectFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Failed to connect to socket"
 
 #define QERR_SOCKET_LISTEN_FAILED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'SockListenFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Failed to set socket to listening mode"
 
 #define QERR_SOCKET_BIND_FAILED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'SockBindFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Failed to bind socket"
 
 #define QERR_SOCKET_CREATE_FAILED \
-    ERROR_CLASS_GENERIC_ERROR, "{ 'class': 'SockCreateFailed', 'data': {} }"
+    ERROR_CLASS_GENERIC_ERROR, "Failed to create socket"
 
 #endif /* QERROR_H */
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 33/35] qerror: drop qerror_table and qerror_format()
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (31 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 32/35] error, qerror: pass desc string to error calls Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 34/35] error, qerror: drop QDict member Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 35/35] docs: writing-qmp-commands.txt: update error section Luiz Capitulino
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

They are unused since last commit.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 qerror.c | 400 ---------------------------------------------------------------
 qerror.h |   7 --
 2 files changed, 407 deletions(-)

diff --git a/qerror.c b/qerror.c
index dda1427..ccc52be 100644
--- a/qerror.c
+++ b/qerror.c
@@ -23,311 +23,6 @@ static const QType qerror_type = {
 };
 
 /**
- * The 'desc' parameter is a printf-like string, the format of the format
- * string is:
- *
- * %(KEY)
- *
- * Where KEY is a QDict key, which has to be passed to qerror_from_info().
- *
- * Example:
- *
- * "foo error on device: %(device) slot: %(slot_nr)"
- *
- * A single percent sign can be printed if followed by a second one,
- * for example:
- *
- * "running out of foo: %(foo)%%"
- *
- * Please keep the entries in alphabetical order.
- * Use scripts/check-qerror.sh to check.
- */
-static const QErrorStringTable qerror_table[] = {
-    {
-         QERR_ADD_CLIENT_FAILED,
-         "Could not add client",
-    },
-    {
-         QERR_AMBIGUOUS_PATH,
-         "Path '%(path)' does not uniquely identify an object"
-    },
-    {
-         QERR_BAD_BUS_FOR_DEVICE,
-         "Device '%(device)' can't go on a %(bad_bus_type) bus",
-    },
-    {
-         QERR_BASE_NOT_FOUND,
-         "Base '%(base)' not found",
-    },
-    {
-         QERR_BLOCK_FORMAT_FEATURE_NOT_SUPPORTED,
-         "Block format '%(format)' used by device '%(name)' does not support feature '%(feature)'",
-    },
-    {
-         QERR_BUS_NO_HOTPLUG,
-         "Bus '%(bus)' does not support hotplugging",
-    },
-    {
-         QERR_BUS_NOT_FOUND,
-         "Bus '%(bus)' not found",
-    },
-    {
-         QERR_COMMAND_DISABLED,
-         "The command %(name) has been disabled for this instance",
-    },
-    {
-         QERR_COMMAND_NOT_FOUND,
-         "The command %(name) has not been found",
-    },
-    {
-         QERR_DEVICE_ENCRYPTED,
-         "'%(device)' (%(filename)) is encrypted",
-    },
-    {
-         QERR_DEVICE_FEATURE_BLOCKS_MIGRATION,
-         "Migration is disabled when using feature '%(feature)' in device '%(device)'",
-    },
-    {
-         QERR_DEVICE_HAS_NO_MEDIUM,
-         "Device '%(device)' has no medium",
-    },
-    {
-         QERR_DEVICE_INIT_FAILED,
-         "Device '%(device)' could not be initialized",
-    },
-    {
-         QERR_DEVICE_IN_USE,
-         "Device '%(device)' is in use",
-    },
-    {
-         QERR_DEVICE_IS_READ_ONLY,
-         "Device '%(device)' is read only",
-    },
-    {
-         QERR_DEVICE_LOCKED,
-         "Device '%(device)' is locked",
-    },
-    {
-         QERR_DEVICE_MULTIPLE_BUSSES,
-         "Device '%(device)' has multiple child busses",
-    },
-    {
-         QERR_DEVICE_NO_BUS,
-         "Device '%(device)' has no child bus",
-    },
-    {
-         QERR_DEVICE_NO_HOTPLUG,
-         "Device '%(device)' does not support hotplugging",
-    },
-    {
-         QERR_DEVICE_NOT_ACTIVE,
-         "Device '%(device)' has not been activated",
-    },
-    {
-         QERR_DEVICE_NOT_ENCRYPTED,
-         "Device '%(device)' is not encrypted",
-    },
-    {
-         QERR_DEVICE_NOT_FOUND,
-         "Device '%(device)' not found",
-    },
-    {
-         QERR_DEVICE_NOT_REMOVABLE,
-         "Device '%(device)' is not removable",
-    },
-    {
-         QERR_DUPLICATE_ID,
-         "Duplicate ID '%(id)' for %(object)",
-    },
-    {
-         QERR_FD_NOT_FOUND,
-         "File descriptor named '%(name)' not found",
-    },
-    {
-         QERR_FD_NOT_SUPPLIED,
-         "No file descriptor supplied via SCM_RIGHTS",
-    },
-    {
-         QERR_FEATURE_DISABLED,
-         "The feature '%(name)' is not enabled",
-    },
-    {
-         QERR_INVALID_BLOCK_FORMAT,
-         "Invalid block format '%(name)'",
-    },
-    {
-         QERR_INVALID_OPTION_GROUP,
-         "There is no option group '%(group)'",
-    },
-    {
-         QERR_INVALID_PARAMETER,
-         "Invalid parameter '%(name)'",
-    },
-    {
-         QERR_INVALID_PARAMETER_COMBINATION,
-         "Invalid parameter combination",
-    },
-    {
-         QERR_INVALID_PARAMETER_TYPE,
-         "Invalid parameter type for '%(name)', expected: %(expected)",
-    },
-    {
-         QERR_INVALID_PARAMETER_VALUE,
-         "Parameter '%(name)' expects %(expected)",
-    },
-    {
-         QERR_INVALID_PASSWORD,
-         "Password incorrect",
-    },
-    {
-         QERR_IO_ERROR,
-         "An IO error has occurred",
-    },
-    {
-         QERR_JSON_PARSE_ERROR,
-         "JSON parse error, %(message)",
-
-    },
-    {
-         QERR_JSON_PARSING,
-         "Invalid JSON syntax",
-    },
-    {
-         QERR_KVM_MISSING_CAP,
-         "Using KVM without %(capability), %(feature) unavailable",
-    },
-    {
-         QERR_MIGRATION_ACTIVE,
-         "There's a migration process in progress",
-    },
-    {
-         QERR_MIGRATION_NOT_SUPPORTED,
-         "State blocked by non-migratable device '%(device)'",
-    },
-    {
-         QERR_MIGRATION_EXPECTED,
-         "An incoming migration is expected before this command can be executed",
-    },
-    {
-         QERR_MISSING_PARAMETER,
-         "Parameter '%(name)' is missing",
-    },
-    {
-         QERR_NO_BUS_FOR_DEVICE,
-         "No '%(bus)' bus found for device '%(device)'",
-    },
-    {
-         QERR_NOT_SUPPORTED,
-         "Not supported",
-    },
-    {
-         QERR_OPEN_FILE_FAILED,
-         "Could not open '%(filename)'",
-    },
-    {
-         QERR_PERMISSION_DENIED,
-         "Insufficient permission to perform this operation",
-    },
-    {
-         QERR_PROPERTY_NOT_FOUND,
-         "Property '%(device).%(property)' not found",
-    },
-    {
-         QERR_PROPERTY_VALUE_BAD,
-         "Property '%(device).%(property)' doesn't take value '%(value)'",
-    },
-    {
-         QERR_PROPERTY_VALUE_IN_USE,
-         "Property '%(device).%(property)' can't take value '%(value)', it's in use",
-    },
-    {
-         QERR_PROPERTY_VALUE_NOT_FOUND,
-         "Property '%(device).%(property)' can't find value '%(value)'",
-    },
-    {
-         QERR_PROPERTY_VALUE_NOT_POWER_OF_2,
-         "Property '%(device).%(property)' doesn't take "
-                     "value '%(value)', it's not a power of 2",
-    },
-    {
-         QERR_PROPERTY_VALUE_OUT_OF_RANGE,
-         "Property '%(device).%(property)' doesn't take "
-                     "value %(value) (minimum: %(min), maximum: %(max))",
-    },
-    {
-         QERR_QGA_COMMAND_FAILED,
-         "Guest agent command failed, error was '%(message)'",
-    },
-    {
-         QERR_QGA_LOGGING_FAILED,
-         "Guest agent failed to log non-optional log statement",
-    },
-    {
-         QERR_QMP_BAD_INPUT_OBJECT,
-         "Expected '%(expected)' in QMP input",
-    },
-    {
-         QERR_QMP_BAD_INPUT_OBJECT_MEMBER,
-         "QMP input object member '%(member)' expects '%(expected)'",
-    },
-    {
-         QERR_QMP_EXTRA_MEMBER,
-         "QMP input object member '%(member)' is unexpected",
-    },
-    {
-         QERR_RESET_REQUIRED,
-         "Resetting the Virtual Machine is required",
-    },
-    {
-         QERR_SET_PASSWD_FAILED,
-         "Could not set password",
-    },
-    {
-         QERR_TOO_MANY_FILES,
-         "Too many open files",
-    },
-    {
-         QERR_UNDEFINED_ERROR,
-         "An undefined error has occurred",
-    },
-    {
-         QERR_UNKNOWN_BLOCK_FORMAT_FEATURE,
-         "'%(device)' uses a %(format) feature which is not "
-                     "supported by this qemu version: %(feature)",
-    },
-    {
-         QERR_UNSUPPORTED,
-         "this feature or command is not currently supported",
-    },
-    {
-         QERR_VIRTFS_FEATURE_BLOCKS_MIGRATION,
-         "Migration is disabled when VirtFS export path '%(path)' "
-                     "is mounted in the guest using mount_tag '%(tag)'",
-    },
-    {
-         QERR_VNC_SERVER_FAILED,
-         "Could not start VNC server on %(target)",
-    },
-    {
-         QERR_SOCKET_CONNECT_FAILED,
-         "Failed to connect to socket",
-    },
-    {
-         QERR_SOCKET_LISTEN_FAILED,
-         "Failed to set socket to listening mode",
-    },
-    {
-         QERR_SOCKET_BIND_FAILED,
-         "Failed to bind socket",
-    },
-    {
-         QERR_SOCKET_CREATE_FAILED,
-         "Failed to create socket",
-    },
-    {}
-};
-
-/**
  * qerror_new(): Create a new QError
  *
  * Return strong reference.
@@ -361,101 +56,6 @@ static QError *qerror_from_info(ErrorClass err_class, const char *fmt,
     return qerr;
 }
 
-static void parse_error(const QErrorStringTable *entry, int c)
-{
-    fprintf(stderr, "expected '%c' in '%s'", c, entry->desc);
-    abort();
-}
-
-static const char *append_field(QDict *error, QString *outstr,
-                                const QErrorStringTable *entry,
-                                const char *start)
-{
-    QObject *obj;
-    QDict *qdict;
-    QString *key_qs;
-    const char *end, *key;
-
-    if (*start != '%')
-        parse_error(entry, '%');
-    start++;
-    if (*start != '(')
-        parse_error(entry, '(');
-    start++;
-
-    end = strchr(start, ')');
-    if (!end)
-        parse_error(entry, ')');
-
-    key_qs = qstring_from_substr(start, 0, end - start - 1);
-    key = qstring_get_str(key_qs);
-
-    qdict = qobject_to_qdict(qdict_get(error, "data"));
-    obj = qdict_get(qdict, key);
-    if (!obj) {
-        abort();
-    }
-
-    switch (qobject_type(obj)) {
-        case QTYPE_QSTRING:
-            qstring_append(outstr, qdict_get_str(qdict, key));
-            break;
-        case QTYPE_QINT:
-            qstring_append_int(outstr, qdict_get_int(qdict, key));
-            break;
-        default:
-            abort();
-    }
-
-    QDECREF(key_qs);
-    return ++end;
-}
-
-static QString *qerror_format_desc(QDict *error,
-                                   const QErrorStringTable *entry)
-{
-    QString *qstring;
-    const char *p;
-
-    assert(entry != NULL);
-
-    qstring = qstring_new();
-
-    for (p = entry->desc; *p != '\0';) {
-        if (*p != '%') {
-            qstring_append_chr(qstring, *p++);
-        } else if (*(p + 1) == '%') {
-            qstring_append_chr(qstring, '%');
-            p += 2;
-        } else {
-            p = append_field(error, qstring, entry, p);
-        }
-    }
-
-    return qstring;
-}
-
-char *qerror_format(const char *fmt, QDict *error)
-{
-    const QErrorStringTable *entry = NULL;
-    QString *qstr;
-    char *ret;
-    int i;
-
-    for (i = 0; qerror_table[i].error_fmt; i++) {
-        if (strcmp(qerror_table[i].error_fmt, fmt) == 0) {
-            entry = &qerror_table[i];
-            break;
-        }
-    }
-
-    qstr = qerror_format_desc(error, entry);
-    ret = g_strdup(qstring_get_str(qstr));
-    QDECREF(qstr);
-
-    return ret;
-}
-
 /**
  * qerror_human(): Format QError data into human-readable string.
  */
diff --git a/qerror.h b/qerror.h
index 057a8f2..c5ad29f 100644
--- a/qerror.h
+++ b/qerror.h
@@ -19,12 +19,6 @@
 #include "qapi-types.h"
 #include <stdarg.h>
 
-typedef struct QErrorStringTable {
-    ErrorClass err_class;
-    const char *error_fmt;
-    const char *desc;
-} QErrorStringTable;
-
 typedef struct QError {
     QObject_HEAD;
     QDict *error;
@@ -37,7 +31,6 @@ QString *qerror_human(const QError *qerror);
 void qerror_report(ErrorClass err_class, const char *fmt, ...) GCC_FMT_ATTR(2, 3);
 void qerror_report_err(Error *err);
 void assert_no_error(Error *err);
-char *qerror_format(const char *fmt, QDict *error);
 
 /*
  * QError class list
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 34/35] error, qerror: drop QDict member
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (32 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 33/35] qerror: drop qerror_table and qerror_format() Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 35/35] docs: writing-qmp-commands.txt: update error section Luiz Capitulino
  34 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Used to store error information, but it's unused now.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 error.c  | 4 ----
 qerror.c | 4 ----
 qerror.h | 1 -
 3 files changed, 9 deletions(-)

diff --git a/error.c b/error.c
index 0e10373..1f05fc4 100644
--- a/error.c
+++ b/error.c
@@ -19,7 +19,6 @@
 
 struct Error
 {
-    QDict *obj;
     char *msg;
     ErrorClass err_class;
 };
@@ -51,8 +50,6 @@ Error *error_copy(const Error *err)
     err_new = g_malloc0(sizeof(*err));
     err_new->msg = g_strdup(err->msg);
     err_new->err_class = err->err_class;
-    err_new->obj = err->obj;
-    QINCREF(err_new->obj);
 
     return err_new;
 }
@@ -75,7 +72,6 @@ const char *error_get_pretty(Error *err)
 void error_free(Error *err)
 {
     if (err) {
-        QDECREF(err->obj);
         g_free(err->msg);
         g_free(err);
     }
diff --git a/qerror.c b/qerror.c
index ccc52be..0818504 100644
--- a/qerror.c
+++ b/qerror.c
@@ -100,7 +100,6 @@ void qerror_report(ErrorClass eclass, const char *fmt, ...)
 /* Evil... */
 struct Error
 {
-    QDict *obj;
     char *msg;
     ErrorClass err_class;
 };
@@ -111,8 +110,6 @@ void qerror_report_err(Error *err)
 
     qerr = qerror_new();
     loc_save(&qerr->loc);
-    QINCREF(err->obj);
-    qerr->error = err->obj;
     qerr->err_msg = g_strdup(err->msg);
     qerr->err_class = err->err_class;
 
@@ -154,7 +151,6 @@ static void qerror_destroy_obj(QObject *obj)
     assert(obj != NULL);
     qerr = qobject_to_qerror(obj);
 
-    QDECREF(qerr->error);
     g_free(qerr->err_msg);
     g_free(qerr);
 }
diff --git a/qerror.h b/qerror.h
index c5ad29f..d0a76a4 100644
--- a/qerror.h
+++ b/qerror.h
@@ -21,7 +21,6 @@
 
 typedef struct QError {
     QObject_HEAD;
-    QDict *error;
     Location loc;
     char *err_msg;
     ErrorClass err_class;
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* [Qemu-devel] [PATCH 35/35] docs: writing-qmp-commands.txt: update error section
  2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
                   ` (33 preceding siblings ...)
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 34/35] error, qerror: drop QDict member Luiz Capitulino
@ 2012-08-07 15:53 ` Luiz Capitulino
  2012-08-08 12:35   ` Pavel Hrdina
  34 siblings, 1 reply; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-07 15:53 UTC (permalink / raw)
  To: qemu-devel; +Cc: kwolf, aliguori, armbru, mdroth, pbonzini, eblake

Add information about the new error format and improve the text a bit.

Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
---
 docs/writing-qmp-commands.txt | 47 +++++++++++++++++++++++++------------------
 1 file changed, 27 insertions(+), 20 deletions(-)

diff --git a/docs/writing-qmp-commands.txt b/docs/writing-qmp-commands.txt
index 0ad51aa..10ecd97 100644
--- a/docs/writing-qmp-commands.txt
+++ b/docs/writing-qmp-commands.txt
@@ -210,19 +210,17 @@ if you don't see these strings, then something went wrong.
 === Errors ===
 
 QMP commands should use the error interface exported by the error.h header
-file. The basic function used to set an error is the error_set() one.
+file. Basically, errors are set by calling the error_set() function.
 
 Let's say we don't accept the string "message" to contain the word "love". If
-it does contain it, we want the "hello-world" command to the return the
-InvalidParameter error.
-
-Only one change is required, and it's in the C implementation:
+it does contain it, we want the "hello-world" command to return an error:
 
 void qmp_hello_world(bool has_message, const char *message, Error **errp)
 {
     if (has_message) {
         if (strstr(message, "love")) {
-            error_set(errp, QERR_INVALID_PARAMETER, "message");
+            error_set(errp, ERROR_CLASS_GENERIC_ERROR,
+                      "the word 'love' is not allowed");
             return;
         }
         printf("%s\n", message);
@@ -231,30 +229,40 @@ void qmp_hello_world(bool has_message, const char *message, Error **errp)
     }
 }
 
-Let's test it. Build qemu, run it as defined in the "Testing" section, and
-then issue the following command:
+The first argument to the error_set() function is the Error pointer to pointer,
+which is passed to all QMP functions. The second argument is a ErrorClass
+value, which should be ERROR_CLASS_GENERIC_ERROR most of the time (more
+details about error classes are given below). The third argument is a human
+description of the error, this is a free-form printf-like string.
+
+Let's test the example above. Build qemu, run it as defined in the "Testing"
+section, and then issue the following command:
 
-{ "execute": "hello-world", "arguments": { "message": "we love qemu" } }
+{ "execute": "hello-world", "arguments": { "message": "all you need is love" } }
 
 The QMP server's response should be:
 
 {
     "error": {
-        "class": "InvalidParameter",
-        "desc": "Invalid parameter 'message'",
-        "data": {
-            "name": "message"
-        }
+        "class": "GenericError", 
+        "desc": "the word 'love' is not allowed"
     }
 }
 
-Which is the InvalidParameter error.
+As a general rule, all QMP errors should use ERROR_CLASS_GENERIC_ERROR. There
+are two exceptions to this rule:
+
+ 1. A non-generic ErrorClass value exists* for the failure you want to report
+    (eg. DeviceNotFound)
+
+ 2. Management applications have to take special action on the failure you
+    want to report, hence you have to add a new ErrorClass value so that they
+    can check for it
 
-When you have to return an error but you're unsure what error to return or
-which arguments an error takes, you should look at the qerror.h file. Note
-that you might be required to add new errors if needed.
+If the failure you want to report doesn't fall in one of the two cases above,
+just report ERROR_CLASS_GENERIC_ERROR.
 
-FIXME: describe better the error API and how to add new errors.
+ * All existing ErrorClass values are defined in the qapi-schema.json file
 
 === Command Documentation ===
 
@@ -275,7 +283,6 @@ here goes "hello-world"'s new entry for the qapi-schema.json file:
 # @message: #optional string to be printed
 #
 # Returns: Nothing on success.
-#          If @message contains "love", InvalidParameter
 #
 # Notes: if @message is not provided, the "Hello, world" string will
 #        be printed instead
-- 
1.7.11.2.249.g31c7954.dirty

^ permalink raw reply related	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 35/35] docs: writing-qmp-commands.txt: update error section
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 35/35] docs: writing-qmp-commands.txt: update error section Luiz Capitulino
@ 2012-08-08 12:35   ` Pavel Hrdina
  2012-08-08 13:26     ` Luiz Capitulino
  0 siblings, 1 reply; 49+ messages in thread
From: Pavel Hrdina @ 2012-08-08 12:35 UTC (permalink / raw)
  To: Luiz Capitulino; +Cc: qemu-devel

On 08/07/2012 05:53 PM, Luiz Capitulino wrote:
> Add information about the new error format and improve the text a bit.
>
> Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
> ---
>   docs/writing-qmp-commands.txt | 47 +++++++++++++++++++++++++------------------
>   1 file changed, 27 insertions(+), 20 deletions(-)
>
> diff --git a/docs/writing-qmp-commands.txt b/docs/writing-qmp-commands.txt
> index 0ad51aa..10ecd97 100644
> --- a/docs/writing-qmp-commands.txt
> +++ b/docs/writing-qmp-commands.txt
> @@ -210,19 +210,17 @@ if you don't see these strings, then something went wrong.
>   === Errors ===
>   
>   QMP commands should use the error interface exported by the error.h header
> -file. The basic function used to set an error is the error_set() one.
> +file. Basically, errors are set by calling the error_set() function.
>   
>   Let's say we don't accept the string "message" to contain the word "love". If
> -it does contain it, we want the "hello-world" command to the return the
> -InvalidParameter error.
> -
> -Only one change is required, and it's in the C implementation:
> +it does contain it, we want the "hello-world" command to return an error:
>   
>   void qmp_hello_world(bool has_message, const char *message, Error **errp)
>   {
>       if (has_message) {
>           if (strstr(message, "love")) {
> -            error_set(errp, QERR_INVALID_PARAMETER, "message");
> +            error_set(errp, ERROR_CLASS_GENERIC_ERROR,
> +                      "the word 'love' is not allowed");
>               return;
>           }
>           printf("%s\n", message);
> @@ -231,30 +229,40 @@ void qmp_hello_world(bool has_message, const char *message, Error **errp)
>       }
>   }
>   
> -Let's test it. Build qemu, run it as defined in the "Testing" section, and
> -then issue the following command:
> +The first argument to the error_set() function is the Error pointer to pointer,
> +which is passed to all QMP functions. The second argument is a ErrorClass
> +value, which should be ERROR_CLASS_GENERIC_ERROR most of the time (more
> +details about error classes are given below). The third argument is a human
> +description of the error, this is a free-form printf-like string.
> +
> +Let's test the example above. Build qemu, run it as defined in the "Testing"
> +section, and then issue the following command:
>   
> -{ "execute": "hello-world", "arguments": { "message": "we love qemu" } }
> +{ "execute": "hello-world", "arguments": { "message": "all you need is love" } }
>   
>   The QMP server's response should be:
>   
>   {
>       "error": {
> -        "class": "InvalidParameter",
> -        "desc": "Invalid parameter 'message'",
> -        "data": {
> -            "name": "message"
> -        }
> +        "class": "GenericError",

you have here trailing white-space  ^

> +        "desc": "the word 'love' is not allowed"
>       }
>   }
>   
> -Which is the InvalidParameter error.
> +As a general rule, all QMP errors should use ERROR_CLASS_GENERIC_ERROR. There
> +are two exceptions to this rule:
> +
> + 1. A non-generic ErrorClass value exists* for the failure you want to report
> +    (eg. DeviceNotFound)
> +
> + 2. Management applications have to take special action on the failure you
> +    want to report, hence you have to add a new ErrorClass value so that they
> +    can check for it
>   
> -When you have to return an error but you're unsure what error to return or
> -which arguments an error takes, you should look at the qerror.h file. Note
> -that you might be required to add new errors if needed.
> +If the failure you want to report doesn't fall in one of the two cases above,
> +just report ERROR_CLASS_GENERIC_ERROR.
>   
> -FIXME: describe better the error API and how to add new errors.
> + * All existing ErrorClass values are defined in the qapi-schema.json file
>   
>   === Command Documentation ===
>   
> @@ -275,7 +283,6 @@ here goes "hello-world"'s new entry for the qapi-schema.json file:
>   # @message: #optional string to be printed
>   #
>   # Returns: Nothing on success.
> -#          If @message contains "love", InvalidParameter
>   #
>   # Notes: if @message is not provided, the "Hello, world" string will
>   #        be printed instead

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 35/35] docs: writing-qmp-commands.txt: update error section
  2012-08-08 12:35   ` Pavel Hrdina
@ 2012-08-08 13:26     ` Luiz Capitulino
  0 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-08 13:26 UTC (permalink / raw)
  To: Pavel Hrdina; +Cc: qemu-devel

On Wed, 08 Aug 2012 14:35:23 +0200
Pavel Hrdina <phrdina@redhat.com> wrote:

> On 08/07/2012 05:53 PM, Luiz Capitulino wrote:
> > Add information about the new error format and improve the text a bit.
> >
> > Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
> > ---
> >   docs/writing-qmp-commands.txt | 47 +++++++++++++++++++++++++------------------
> >   1 file changed, 27 insertions(+), 20 deletions(-)
> >
> > diff --git a/docs/writing-qmp-commands.txt b/docs/writing-qmp-commands.txt
> > index 0ad51aa..10ecd97 100644
> > --- a/docs/writing-qmp-commands.txt
> > +++ b/docs/writing-qmp-commands.txt
> > @@ -210,19 +210,17 @@ if you don't see these strings, then something went wrong.
> >   === Errors ===
> >   
> >   QMP commands should use the error interface exported by the error.h header
> > -file. The basic function used to set an error is the error_set() one.
> > +file. Basically, errors are set by calling the error_set() function.
> >   
> >   Let's say we don't accept the string "message" to contain the word "love". If
> > -it does contain it, we want the "hello-world" command to the return the
> > -InvalidParameter error.
> > -
> > -Only one change is required, and it's in the C implementation:
> > +it does contain it, we want the "hello-world" command to return an error:
> >   
> >   void qmp_hello_world(bool has_message, const char *message, Error **errp)
> >   {
> >       if (has_message) {
> >           if (strstr(message, "love")) {
> > -            error_set(errp, QERR_INVALID_PARAMETER, "message");
> > +            error_set(errp, ERROR_CLASS_GENERIC_ERROR,
> > +                      "the word 'love' is not allowed");
> >               return;
> >           }
> >           printf("%s\n", message);
> > @@ -231,30 +229,40 @@ void qmp_hello_world(bool has_message, const char *message, Error **errp)
> >       }
> >   }
> >   
> > -Let's test it. Build qemu, run it as defined in the "Testing" section, and
> > -then issue the following command:
> > +The first argument to the error_set() function is the Error pointer to pointer,
> > +which is passed to all QMP functions. The second argument is a ErrorClass
> > +value, which should be ERROR_CLASS_GENERIC_ERROR most of the time (more
> > +details about error classes are given below). The third argument is a human
> > +description of the error, this is a free-form printf-like string.
> > +
> > +Let's test the example above. Build qemu, run it as defined in the "Testing"
> > +section, and then issue the following command:
> >   
> > -{ "execute": "hello-world", "arguments": { "message": "we love qemu" } }
> > +{ "execute": "hello-world", "arguments": { "message": "all you need is love" } }
> >   
> >   The QMP server's response should be:
> >   
> >   {
> >       "error": {
> > -        "class": "InvalidParameter",
> > -        "desc": "Invalid parameter 'message'",
> > -        "data": {
> > -            "name": "message"
> > -        }
> > +        "class": "GenericError",
> 
> you have here trailing white-space  ^

I've fixed it for v3, thanks.

> 
> > +        "desc": "the word 'love' is not allowed"
> >       }
> >   }
> >   
> > -Which is the InvalidParameter error.
> > +As a general rule, all QMP errors should use ERROR_CLASS_GENERIC_ERROR. There
> > +are two exceptions to this rule:
> > +
> > + 1. A non-generic ErrorClass value exists* for the failure you want to report
> > +    (eg. DeviceNotFound)
> > +
> > + 2. Management applications have to take special action on the failure you
> > +    want to report, hence you have to add a new ErrorClass value so that they
> > +    can check for it
> >   
> > -When you have to return an error but you're unsure what error to return or
> > -which arguments an error takes, you should look at the qerror.h file. Note
> > -that you might be required to add new errors if needed.
> > +If the failure you want to report doesn't fall in one of the two cases above,
> > +just report ERROR_CLASS_GENERIC_ERROR.
> >   
> > -FIXME: describe better the error API and how to add new errors.
> > + * All existing ErrorClass values are defined in the qapi-schema.json file
> >   
> >   === Command Documentation ===
> >   
> > @@ -275,7 +283,6 @@ here goes "hello-world"'s new entry for the qapi-schema.json file:
> >   # @message: #optional string to be printed
> >   #
> >   # Returns: Nothing on success.
> > -#          If @message contains "love", InvalidParameter
> >   #
> >   # Notes: if @message is not provided, the "Hello, world" string will
> >   #        be printed instead
> 

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 12/35] hmp: hmp_cont(): don't rely on QERR_DEVICE_ENCRYPTED
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 12/35] hmp: hmp_cont(): don't rely on QERR_DEVICE_ENCRYPTED Luiz Capitulino
@ 2012-08-10  8:43   ` Markus Armbruster
  0 siblings, 0 replies; 49+ messages in thread
From: Markus Armbruster @ 2012-08-10  8:43 UTC (permalink / raw)
  To: Luiz Capitulino; +Cc: kwolf, aliguori, qemu-devel, mdroth, pbonzini, eblake

Luiz Capitulino <lcapitulino@redhat.com> writes:

> This commit changes hmp_cont() to loop through all block devices
> and proactively set an encryption key for any encrypted device
> without a valid one.
>
> This change is needed because QERR_DEVICE_ENCRYPTED is going to be
> dropped by a future commit.

I'm afraid this breaks for unencrypted images with encrypted backing
files.  See the reply to v1 12/34 I just sent.

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 13/35] hmp_change(): don't access DeviceEncrypted's data
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 13/35] hmp_change(): don't access DeviceEncrypted's data Luiz Capitulino
@ 2012-08-10  9:02   ` Markus Armbruster
  2012-08-10 14:36     ` Luiz Capitulino
  0 siblings, 1 reply; 49+ messages in thread
From: Markus Armbruster @ 2012-08-10  9:02 UTC (permalink / raw)
  To: Luiz Capitulino; +Cc: kwolf, aliguori, qemu-devel, mdroth, pbonzini, eblake

Luiz Capitulino <lcapitulino@redhat.com> writes:

> It's not needed. The device name is already known and
> monitor_read_block_device_key() knows how to do the rest. This overly
> simplifies hmp_change().

"overly"?

My usual complaint about commit messages is that they fail to explain
the change's purpose.  Yours explains your reason just fine, but the
description of what's done falls a bit short.  I'd like to see something
like "replace duplicated password prompting code by common
monitor_read_block_device_key()".

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 14/35] net: inet_connect(), inet_connect_opts(): add in_progress argument
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 14/35] net: inet_connect(), inet_connect_opts(): add in_progress argument Luiz Capitulino
@ 2012-08-10  9:07   ` Markus Armbruster
  2012-08-10 14:47     ` Luiz Capitulino
  0 siblings, 1 reply; 49+ messages in thread
From: Markus Armbruster @ 2012-08-10  9:07 UTC (permalink / raw)
  To: Luiz Capitulino; +Cc: kwolf, aliguori, qemu-devel, mdroth, pbonzini, eblake

Luiz Capitulino <lcapitulino@redhat.com> writes:

> It's used to indicate the special case where a valid file-descriptor
> is returned (ie. success) but the connection can't be completed
> w/o blocking.

Why callers need that isn't obvious from this patch.  It's used in PATCH
16.  Either squash the two to make it obvious, or furher explain the
purpose in this commit message.  I'd recommend the former.

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 15/35] migration: don't rely on any QERR_SOCKET_*
  2012-08-07 15:53 ` [Qemu-devel] [PATCH 15/35] migration: don't rely on any QERR_SOCKET_* Luiz Capitulino
@ 2012-08-10  9:13   ` Markus Armbruster
  2012-08-10 14:49     ` Luiz Capitulino
  2012-08-14 11:19     ` Juan Quintela
  0 siblings, 2 replies; 49+ messages in thread
From: Markus Armbruster @ 2012-08-10  9:13 UTC (permalink / raw)
  To: Luiz Capitulino; +Cc: kwolf, aliguori, qemu-devel, mdroth, pbonzini, eblake

Luiz Capitulino <lcapitulino@redhat.com> writes:

> Use the in_progress argument for QERR_SOCKET_CONNECT_IN_PROGRESS. The
> other errors are handled the same by checking if the error is set and
> then calling migrate_fd_error() if it's.
>
> It's also necessary to change inet_connect_opts() not to set
> QERR_SOCKET_CONNECT_IN_PROGRESS. This error is only used by
> tcp_start_outgoing_migration() and not changing it along with the
> usage of in_progress would break migration.
>
> Furthermore this commit fixes a bug. Today, there's a spurious error
> report when migration succeeds:
>
> (qemu) migrate tcp:0:4444
> migrate: Connection can not be completed immediately
> (qemu)
>
> After this commit no spurious error is reported anymore.
>
> Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
> ---
>  migration-tcp.c | 22 ++++++++--------------
>  qemu-sockets.c  |  2 --
>  2 files changed, 8 insertions(+), 16 deletions(-)
>
> diff --git a/migration-tcp.c b/migration-tcp.c
> index 18944a4..40c277f 100644
> --- a/migration-tcp.c
> +++ b/migration-tcp.c
> @@ -82,27 +82,21 @@ static void tcp_wait_for_connect(void *opaque)
>  int tcp_start_outgoing_migration(MigrationState *s, const char *host_port,
>                                   Error **errp)
>  {
> +    bool in_progress;
> +
>      s->get_error = socket_errno;
>      s->write = socket_write;
>      s->close = tcp_close;
>  
> -    s->fd = inet_connect(host_port, false, NULL, errp);
> -
> -    if (!error_is_set(errp)) {
> -        migrate_fd_connect(s);
> -    } else if (error_is_type(*errp, QERR_SOCKET_CONNECT_IN_PROGRESS)) {
> -        DPRINTF("connect in progress\n");
> -        qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
> -    } else if (error_is_type(*errp, QERR_SOCKET_CREATE_FAILED)) {
> -        DPRINTF("connect failed\n");
> -        return -1;
> -    } else if (error_is_type(*errp, QERR_SOCKET_CONNECT_FAILED)) {
> -        DPRINTF("connect failed\n");
> +    s->fd = inet_connect(host_port, false, &in_progress, errp);
> +    if (error_is_set(errp)) {
>          migrate_fd_error(s);
>          return -1;
> +    } else if (in_progress) {
> +        DPRINTF("connect in progress\n");
> +        qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
>      } else {
> -        DPRINTF("unknown error\n");
> -        return -1;
> +        migrate_fd_connect(s);
>      }
>  
>      return 0;

I'd prefer

       s->fd = inet_connect(host_port, false, &in_progress, errp);
       if (error_is_set(errp)) {
           migrate_fd_error(s);
           return -1;
       }
       if (in_progress) {
           DPRINTF("connect in progress\n");
           qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
       } else {
           migrate_fd_connect(s);
       }
       return 0;

because it separates abnormal and normal code paths more clearly.

Matter of taste.

> diff --git a/qemu-sockets.c b/qemu-sockets.c
> index 9cb47d4..361d890 100644
> --- a/qemu-sockets.c
> +++ b/qemu-sockets.c
> @@ -284,8 +284,6 @@ int inet_connect_opts(QemuOpts *opts, bool *in_progress, Error **errp)
>              if (in_progress) {
>                  *in_progress = true;
>              }
> -
> -            error_set(errp, QERR_SOCKET_CONNECT_IN_PROGRESS);
>          } else if (rc < 0) {
>              if (NULL == e->ai_next)
>                  fprintf(stderr, "%s: connect(%s,%s,%s,%s): %s\n", __FUNCTION__,

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 13/35] hmp_change(): don't access DeviceEncrypted's data
  2012-08-10  9:02   ` Markus Armbruster
@ 2012-08-10 14:36     ` Luiz Capitulino
  0 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-10 14:36 UTC (permalink / raw)
  To: Markus Armbruster; +Cc: kwolf, aliguori, qemu-devel, mdroth, pbonzini, eblake

On Fri, 10 Aug 2012 11:02:21 +0200
Markus Armbruster <armbru@redhat.com> wrote:

> Luiz Capitulino <lcapitulino@redhat.com> writes:
> 
> > It's not needed. The device name is already known and
> > monitor_read_block_device_key() knows how to do the rest. This overly
> > simplifies hmp_change().
> 
> "overly"?
> 
> My usual complaint about commit messages is that they fail to explain
> the change's purpose.  Yours explains your reason just fine, but the
> description of what's done falls a bit short.  I'd like to see something
> like "replace duplicated password prompting code by common
> monitor_read_block_device_key()".

Done, for v3.

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 14/35] net: inet_connect(), inet_connect_opts(): add in_progress argument
  2012-08-10  9:07   ` Markus Armbruster
@ 2012-08-10 14:47     ` Luiz Capitulino
  0 siblings, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-10 14:47 UTC (permalink / raw)
  To: Markus Armbruster; +Cc: kwolf, aliguori, qemu-devel, mdroth, pbonzini, eblake

On Fri, 10 Aug 2012 11:07:53 +0200
Markus Armbruster <armbru@redhat.com> wrote:

> Luiz Capitulino <lcapitulino@redhat.com> writes:
> 
> > It's used to indicate the special case where a valid file-descriptor
> > is returned (ie. success) but the connection can't be completed
> > w/o blocking.
> 
> Why callers need that isn't obvious from this patch.  It's used in PATCH
> 16.  Either squash the two to make it obvious, or furher explain the
> purpose in this commit message.  I'd recommend the former.

Done for v3.

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 15/35] migration: don't rely on any QERR_SOCKET_*
  2012-08-10  9:13   ` Markus Armbruster
@ 2012-08-10 14:49     ` Luiz Capitulino
  2012-08-14 11:19     ` Juan Quintela
  1 sibling, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-10 14:49 UTC (permalink / raw)
  To: Markus Armbruster; +Cc: kwolf, aliguori, qemu-devel, mdroth, pbonzini, eblake

On Fri, 10 Aug 2012 11:13:57 +0200
Markus Armbruster <armbru@redhat.com> wrote:

> Luiz Capitulino <lcapitulino@redhat.com> writes:
> 
> > Use the in_progress argument for QERR_SOCKET_CONNECT_IN_PROGRESS. The
> > other errors are handled the same by checking if the error is set and
> > then calling migrate_fd_error() if it's.
> >
> > It's also necessary to change inet_connect_opts() not to set
> > QERR_SOCKET_CONNECT_IN_PROGRESS. This error is only used by
> > tcp_start_outgoing_migration() and not changing it along with the
> > usage of in_progress would break migration.
> >
> > Furthermore this commit fixes a bug. Today, there's a spurious error
> > report when migration succeeds:
> >
> > (qemu) migrate tcp:0:4444
> > migrate: Connection can not be completed immediately
> > (qemu)
> >
> > After this commit no spurious error is reported anymore.
> >
> > Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
> > ---
> >  migration-tcp.c | 22 ++++++++--------------
> >  qemu-sockets.c  |  2 --
> >  2 files changed, 8 insertions(+), 16 deletions(-)
> >
> > diff --git a/migration-tcp.c b/migration-tcp.c
> > index 18944a4..40c277f 100644
> > --- a/migration-tcp.c
> > +++ b/migration-tcp.c
> > @@ -82,27 +82,21 @@ static void tcp_wait_for_connect(void *opaque)
> >  int tcp_start_outgoing_migration(MigrationState *s, const char *host_port,
> >                                   Error **errp)
> >  {
> > +    bool in_progress;
> > +
> >      s->get_error = socket_errno;
> >      s->write = socket_write;
> >      s->close = tcp_close;
> >  
> > -    s->fd = inet_connect(host_port, false, NULL, errp);
> > -
> > -    if (!error_is_set(errp)) {
> > -        migrate_fd_connect(s);
> > -    } else if (error_is_type(*errp, QERR_SOCKET_CONNECT_IN_PROGRESS)) {
> > -        DPRINTF("connect in progress\n");
> > -        qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
> > -    } else if (error_is_type(*errp, QERR_SOCKET_CREATE_FAILED)) {
> > -        DPRINTF("connect failed\n");
> > -        return -1;
> > -    } else if (error_is_type(*errp, QERR_SOCKET_CONNECT_FAILED)) {
> > -        DPRINTF("connect failed\n");
> > +    s->fd = inet_connect(host_port, false, &in_progress, errp);
> > +    if (error_is_set(errp)) {
> >          migrate_fd_error(s);
> >          return -1;
> > +    } else if (in_progress) {
> > +        DPRINTF("connect in progress\n");
> > +        qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
> >      } else {
> > -        DPRINTF("unknown error\n");
> > -        return -1;
> > +        migrate_fd_connect(s);
> >      }
> >  
> >      return 0;
> 
> I'd prefer
> 
>        s->fd = inet_connect(host_port, false, &in_progress, errp);
>        if (error_is_set(errp)) {
>            migrate_fd_error(s);
>            return -1;
>        }
>        if (in_progress) {
>            DPRINTF("connect in progress\n");
>            qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
>        } else {
>            migrate_fd_connect(s);
>        }
>        return 0;
> 
> because it separates abnormal and normal code paths more clearly.

Very minor, but I've changed it.

> 
> Matter of taste.
> 
> > diff --git a/qemu-sockets.c b/qemu-sockets.c
> > index 9cb47d4..361d890 100644
> > --- a/qemu-sockets.c
> > +++ b/qemu-sockets.c
> > @@ -284,8 +284,6 @@ int inet_connect_opts(QemuOpts *opts, bool *in_progress, Error **errp)
> >              if (in_progress) {
> >                  *in_progress = true;
> >              }
> > -
> > -            error_set(errp, QERR_SOCKET_CONNECT_IN_PROGRESS);
> >          } else if (rc < 0) {
> >              if (NULL == e->ai_next)
> >                  fprintf(stderr, "%s: connect(%s,%s,%s,%s): %s\n", __FUNCTION__,
> 

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 15/35] migration: don't rely on any QERR_SOCKET_*
  2012-08-10  9:13   ` Markus Armbruster
  2012-08-10 14:49     ` Luiz Capitulino
@ 2012-08-14 11:19     ` Juan Quintela
  2012-08-14 11:35       ` Markus Armbruster
  1 sibling, 1 reply; 49+ messages in thread
From: Juan Quintela @ 2012-08-14 11:19 UTC (permalink / raw)
  To: Markus Armbruster
  Cc: kwolf, aliguori, mdroth, qemu-devel, pbonzini, Luiz Capitulino, eblake

Markus Armbruster <armbru@redhat.com> wrote:
> Luiz Capitulino <lcapitulino@redhat.com> writes:
>
>> Use the in_progress argument for QERR_SOCKET_CONNECT_IN_PROGRESS. The
>> other errors are handled the same by checking if the error is set and
>> then calling migrate_fd_error() if it's.
>>
>> It's also necessary to change inet_connect_opts() not to set
>> QERR_SOCKET_CONNECT_IN_PROGRESS. This error is only used by
>> tcp_start_outgoing_migration() and not changing it along with the
>> usage of in_progress would break migration.
>>
>> Furthermore this commit fixes a bug. Today, there's a spurious error
>> report when migration succeeds:
>>
>> (qemu) migrate tcp:0:4444
>> migrate: Connection can not be completed immediately
>> (qemu)
>>
>> After this commit no spurious error is reported anymore.
>>
>> Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
>
> I'd prefer
>
>        s->fd = inet_connect(host_port, false, &in_progress, errp);
>        if (error_is_set(errp)) {
>            migrate_fd_error(s);
>            return -1;
>        }
>        if (in_progress) {
>            DPRINTF("connect in progress\n");
>            qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
>        } else {
>            migrate_fd_connect(s);
>        }
>        return 0;
>
> because it separates abnormal and normal code paths more clearly.
>
> Matter of taste.


The 1st migrate_fd_error() is not needed (it was already wrong).

migrate_fd_* functions are supposed to be called only after
migrate_fd_connect() has been called.

Later, Juan.

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 15/35] migration: don't rely on any QERR_SOCKET_*
  2012-08-14 11:19     ` Juan Quintela
@ 2012-08-14 11:35       ` Markus Armbruster
  2012-08-14 13:06         ` Luiz Capitulino
  2012-08-14 13:09         ` Juan Quintela
  0 siblings, 2 replies; 49+ messages in thread
From: Markus Armbruster @ 2012-08-14 11:35 UTC (permalink / raw)
  To: quintela
  Cc: kwolf, aliguori, mdroth, qemu-devel, pbonzini, Luiz Capitulino, eblake

Juan Quintela <quintela@redhat.com> writes:

> Markus Armbruster <armbru@redhat.com> wrote:
>> Luiz Capitulino <lcapitulino@redhat.com> writes:
>>
>>> Use the in_progress argument for QERR_SOCKET_CONNECT_IN_PROGRESS. The
>>> other errors are handled the same by checking if the error is set and
>>> then calling migrate_fd_error() if it's.
>>>
>>> It's also necessary to change inet_connect_opts() not to set
>>> QERR_SOCKET_CONNECT_IN_PROGRESS. This error is only used by
>>> tcp_start_outgoing_migration() and not changing it along with the
>>> usage of in_progress would break migration.
>>>
>>> Furthermore this commit fixes a bug. Today, there's a spurious error
>>> report when migration succeeds:
>>>
>>> (qemu) migrate tcp:0:4444
>>> migrate: Connection can not be completed immediately
>>> (qemu)
>>>
>>> After this commit no spurious error is reported anymore.
>>>
>>> Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
>>
>> I'd prefer
>>
>>        s->fd = inet_connect(host_port, false, &in_progress, errp);
>>        if (error_is_set(errp)) {
>>            migrate_fd_error(s);
>>            return -1;
>>        }
>>        if (in_progress) {
>>            DPRINTF("connect in progress\n");
>>            qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
>>        } else {
>>            migrate_fd_connect(s);
>>        }
>>        return 0;
>>
>> because it separates abnormal and normal code paths more clearly.
>>
>> Matter of taste.
>
>
> The 1st migrate_fd_error() is not needed (it was already wrong).
>
> migrate_fd_* functions are supposed to be called only after
> migrate_fd_connect() has been called.

It's been committed.  Could you post a patch for it?

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 15/35] migration: don't rely on any QERR_SOCKET_*
  2012-08-14 11:35       ` Markus Armbruster
@ 2012-08-14 13:06         ` Luiz Capitulino
  2012-08-14 13:09         ` Juan Quintela
  1 sibling, 0 replies; 49+ messages in thread
From: Luiz Capitulino @ 2012-08-14 13:06 UTC (permalink / raw)
  To: Markus Armbruster
  Cc: kwolf, aliguori, quintela, mdroth, qemu-devel, pbonzini, eblake

On Tue, 14 Aug 2012 13:35:59 +0200
Markus Armbruster <armbru@redhat.com> wrote:

> Juan Quintela <quintela@redhat.com> writes:
> 
> > Markus Armbruster <armbru@redhat.com> wrote:
> >> Luiz Capitulino <lcapitulino@redhat.com> writes:
> >>
> >>> Use the in_progress argument for QERR_SOCKET_CONNECT_IN_PROGRESS. The
> >>> other errors are handled the same by checking if the error is set and
> >>> then calling migrate_fd_error() if it's.
> >>>
> >>> It's also necessary to change inet_connect_opts() not to set
> >>> QERR_SOCKET_CONNECT_IN_PROGRESS. This error is only used by
> >>> tcp_start_outgoing_migration() and not changing it along with the
> >>> usage of in_progress would break migration.
> >>>
> >>> Furthermore this commit fixes a bug. Today, there's a spurious error
> >>> report when migration succeeds:
> >>>
> >>> (qemu) migrate tcp:0:4444
> >>> migrate: Connection can not be completed immediately
> >>> (qemu)
> >>>
> >>> After this commit no spurious error is reported anymore.
> >>>
> >>> Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
> >>
> >> I'd prefer
> >>
> >>        s->fd = inet_connect(host_port, false, &in_progress, errp);
> >>        if (error_is_set(errp)) {
> >>            migrate_fd_error(s);
> >>            return -1;
> >>        }
> >>        if (in_progress) {
> >>            DPRINTF("connect in progress\n");
> >>            qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
> >>        } else {
> >>            migrate_fd_connect(s);
> >>        }
> >>        return 0;
> >>
> >> because it separates abnormal and normal code paths more clearly.
> >>
> >> Matter of taste.
> >
> >
> > The 1st migrate_fd_error() is not needed (it was already wrong).
> >
> > migrate_fd_* functions are supposed to be called only after
> > migrate_fd_connect() has been called.
> 
> It's been committed.  Could you post a patch for it?

Juan, are you going to do this or do you want me to do it?

^ permalink raw reply	[flat|nested] 49+ messages in thread

* Re: [Qemu-devel] [PATCH 15/35] migration: don't rely on any QERR_SOCKET_*
  2012-08-14 11:35       ` Markus Armbruster
  2012-08-14 13:06         ` Luiz Capitulino
@ 2012-08-14 13:09         ` Juan Quintela
  1 sibling, 0 replies; 49+ messages in thread
From: Juan Quintela @ 2012-08-14 13:09 UTC (permalink / raw)
  To: Markus Armbruster
  Cc: kwolf, aliguori, mdroth, qemu-devel, pbonzini, Luiz Capitulino, eblake

Markus Armbruster <armbru@redhat.com> wrote:
> Juan Quintela <quintela@redhat.com> writes:
>
>> Markus Armbruster <armbru@redhat.com> wrote:
>>> Luiz Capitulino <lcapitulino@redhat.com> writes:
>>>
>>>> Use the in_progress argument for QERR_SOCKET_CONNECT_IN_PROGRESS. The
>>>> other errors are handled the same by checking if the error is set and
>>>> then calling migrate_fd_error() if it's.
>>>>
>>>> It's also necessary to change inet_connect_opts() not to set
>>>> QERR_SOCKET_CONNECT_IN_PROGRESS. This error is only used by
>>>> tcp_start_outgoing_migration() and not changing it along with the
>>>> usage of in_progress would break migration.
>>>>
>>>> Furthermore this commit fixes a bug. Today, there's a spurious error
>>>> report when migration succeeds:
>>>>
>>>> (qemu) migrate tcp:0:4444
>>>> migrate: Connection can not be completed immediately
>>>> (qemu)
>>>>
>>>> After this commit no spurious error is reported anymore.
>>>>
>>>> Signed-off-by: Luiz Capitulino <lcapitulino@redhat.com>
>>>
>>> I'd prefer
>>>
>>>        s->fd = inet_connect(host_port, false, &in_progress, errp);
>>>        if (error_is_set(errp)) {
>>>            migrate_fd_error(s);
>>>            return -1;
>>>        }
>>>        if (in_progress) {
>>>            DPRINTF("connect in progress\n");
>>>            qemu_set_fd_handler2(s->fd, NULL, NULL, tcp_wait_for_connect, s);
>>>        } else {
>>>            migrate_fd_connect(s);
>>>        }
>>>        return 0;
>>>
>>> because it separates abnormal and normal code paths more clearly.
>>>
>>> Matter of taste.
>>
>>
>> The 1st migrate_fd_error() is not needed (it was already wrong).
>>
>> migrate_fd_* functions are supposed to be called only after
>> migrate_fd_connect() has been called.
>
> It's been committed.  Could you post a patch for it?

I am doing it.  Thanks.

^ permalink raw reply	[flat|nested] 49+ messages in thread

end of thread, other threads:[~2012-08-14 13:11 UTC | newest]

Thread overview: 49+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2012-08-07 15:53 [Qemu-devel] [PATCH v2 00/35]: add new error format Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 01/35] monitor: drop unused monitor debug code Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 02/35] qerror: QERR_AMBIGUOUS_PATH: drop %(object) from human msg Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 03/35] qerror: QERR_DEVICE_ENCRYPTED: change error message Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 04/35] qerror: reduce public exposure Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 05/35] qerror: drop qerror_abort() Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 06/35] qerror: avoid passing qerr pointer Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 07/35] qerror: QError: drop file, linenr, func Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 08/35] qerror: qerror_format(): return an allocated string Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 09/35] qerror: don't delay error message construction Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 10/35] error: " Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 11/35] qmp: query-block: add 'valid_encryption_key' field Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 12/35] hmp: hmp_cont(): don't rely on QERR_DEVICE_ENCRYPTED Luiz Capitulino
2012-08-10  8:43   ` Markus Armbruster
2012-08-07 15:53 ` [Qemu-devel] [PATCH 13/35] hmp_change(): don't access DeviceEncrypted's data Luiz Capitulino
2012-08-10  9:02   ` Markus Armbruster
2012-08-10 14:36     ` Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 14/35] net: inet_connect(), inet_connect_opts(): add in_progress argument Luiz Capitulino
2012-08-10  9:07   ` Markus Armbruster
2012-08-10 14:47     ` Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 15/35] migration: don't rely on any QERR_SOCKET_* Luiz Capitulino
2012-08-10  9:13   ` Markus Armbruster
2012-08-10 14:49     ` Luiz Capitulino
2012-08-14 11:19     ` Juan Quintela
2012-08-14 11:35       ` Markus Armbruster
2012-08-14 13:06         ` Luiz Capitulino
2012-08-14 13:09         ` Juan Quintela
2012-08-07 15:53 ` [Qemu-devel] [PATCH 16/35] qerror: drop QERR_SOCKET_CONNECT_IN_PROGRESS Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 17/35] block: block_int: include qerror.h Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 18/35] hmp: hmp.h: include qdict.h Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 19/35] qapi: qapi-types.h: don't include qapi/qapi-types-core.h Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 20/35] qapi: generate correct enum names for camel case enums Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 21/35] qapi: don't convert enum strings to lowercase Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 22/35] qapi-schema: add ErrorClass enum Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 23/35] qerror: qerror_table: don't use C99 struct initializers Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 24/35] error, qerror: add ErrorClass argument to error functions Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 25/35] qerror: add proper ErrorClass value for QERR_ macros Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 26/35] error: add error_get_class() Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 27/35] hmp: hmp_change(): use error_get_class() Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 28/35] error: drop unused functions Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 29/35] qmp: switch to the new error format on the wire Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 30/35] qemu-ga: " Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 31/35] error: drop error_get_qobject()/error_set_qobject() Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 32/35] error, qerror: pass desc string to error calls Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 33/35] qerror: drop qerror_table and qerror_format() Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 34/35] error, qerror: drop QDict member Luiz Capitulino
2012-08-07 15:53 ` [Qemu-devel] [PATCH 35/35] docs: writing-qmp-commands.txt: update error section Luiz Capitulino
2012-08-08 12:35   ` Pavel Hrdina
2012-08-08 13:26     ` Luiz Capitulino

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.