1*baacf047SPaolo Bonzini /* 2*baacf047SPaolo Bonzini * QEMU Error Objects 3*baacf047SPaolo Bonzini * 4*baacf047SPaolo Bonzini * Copyright IBM, Corp. 2011 5*baacf047SPaolo Bonzini * 6*baacf047SPaolo Bonzini * Authors: 7*baacf047SPaolo Bonzini * Anthony Liguori <aliguori@us.ibm.com> 8*baacf047SPaolo Bonzini * 9*baacf047SPaolo Bonzini * This work is licensed under the terms of the GNU LGPL, version 2. See 10*baacf047SPaolo Bonzini * the COPYING.LIB file in the top-level directory. 11*baacf047SPaolo Bonzini */ 12*baacf047SPaolo Bonzini 13*baacf047SPaolo Bonzini #include "qemu-common.h" 14*baacf047SPaolo Bonzini #include "qapi/error.h" 15*baacf047SPaolo Bonzini #include "qapi/qmp/qjson.h" 16*baacf047SPaolo Bonzini #include "qapi/qmp/qdict.h" 17*baacf047SPaolo Bonzini #include "qapi-types.h" 18*baacf047SPaolo Bonzini #include "qapi/qmp/qerror.h" 19*baacf047SPaolo Bonzini 20*baacf047SPaolo Bonzini struct Error 21*baacf047SPaolo Bonzini { 22*baacf047SPaolo Bonzini char *msg; 23*baacf047SPaolo Bonzini ErrorClass err_class; 24*baacf047SPaolo Bonzini }; 25*baacf047SPaolo Bonzini 26*baacf047SPaolo Bonzini void error_set(Error **errp, ErrorClass err_class, const char *fmt, ...) 27*baacf047SPaolo Bonzini { 28*baacf047SPaolo Bonzini Error *err; 29*baacf047SPaolo Bonzini va_list ap; 30*baacf047SPaolo Bonzini 31*baacf047SPaolo Bonzini if (errp == NULL) { 32*baacf047SPaolo Bonzini return; 33*baacf047SPaolo Bonzini } 34*baacf047SPaolo Bonzini assert(*errp == NULL); 35*baacf047SPaolo Bonzini 36*baacf047SPaolo Bonzini err = g_malloc0(sizeof(*err)); 37*baacf047SPaolo Bonzini 38*baacf047SPaolo Bonzini va_start(ap, fmt); 39*baacf047SPaolo Bonzini err->msg = g_strdup_vprintf(fmt, ap); 40*baacf047SPaolo Bonzini va_end(ap); 41*baacf047SPaolo Bonzini err->err_class = err_class; 42*baacf047SPaolo Bonzini 43*baacf047SPaolo Bonzini *errp = err; 44*baacf047SPaolo Bonzini } 45*baacf047SPaolo Bonzini 46*baacf047SPaolo Bonzini void error_set_errno(Error **errp, int os_errno, ErrorClass err_class, 47*baacf047SPaolo Bonzini const char *fmt, ...) 48*baacf047SPaolo Bonzini { 49*baacf047SPaolo Bonzini Error *err; 50*baacf047SPaolo Bonzini char *msg1; 51*baacf047SPaolo Bonzini va_list ap; 52*baacf047SPaolo Bonzini 53*baacf047SPaolo Bonzini if (errp == NULL) { 54*baacf047SPaolo Bonzini return; 55*baacf047SPaolo Bonzini } 56*baacf047SPaolo Bonzini assert(*errp == NULL); 57*baacf047SPaolo Bonzini 58*baacf047SPaolo Bonzini err = g_malloc0(sizeof(*err)); 59*baacf047SPaolo Bonzini 60*baacf047SPaolo Bonzini va_start(ap, fmt); 61*baacf047SPaolo Bonzini msg1 = g_strdup_vprintf(fmt, ap); 62*baacf047SPaolo Bonzini if (os_errno != 0) { 63*baacf047SPaolo Bonzini err->msg = g_strdup_printf("%s: %s", msg1, strerror(os_errno)); 64*baacf047SPaolo Bonzini g_free(msg1); 65*baacf047SPaolo Bonzini } else { 66*baacf047SPaolo Bonzini err->msg = msg1; 67*baacf047SPaolo Bonzini } 68*baacf047SPaolo Bonzini va_end(ap); 69*baacf047SPaolo Bonzini err->err_class = err_class; 70*baacf047SPaolo Bonzini 71*baacf047SPaolo Bonzini *errp = err; 72*baacf047SPaolo Bonzini } 73*baacf047SPaolo Bonzini 74*baacf047SPaolo Bonzini Error *error_copy(const Error *err) 75*baacf047SPaolo Bonzini { 76*baacf047SPaolo Bonzini Error *err_new; 77*baacf047SPaolo Bonzini 78*baacf047SPaolo Bonzini err_new = g_malloc0(sizeof(*err)); 79*baacf047SPaolo Bonzini err_new->msg = g_strdup(err->msg); 80*baacf047SPaolo Bonzini err_new->err_class = err->err_class; 81*baacf047SPaolo Bonzini 82*baacf047SPaolo Bonzini return err_new; 83*baacf047SPaolo Bonzini } 84*baacf047SPaolo Bonzini 85*baacf047SPaolo Bonzini bool error_is_set(Error **errp) 86*baacf047SPaolo Bonzini { 87*baacf047SPaolo Bonzini return (errp && *errp); 88*baacf047SPaolo Bonzini } 89*baacf047SPaolo Bonzini 90*baacf047SPaolo Bonzini ErrorClass error_get_class(const Error *err) 91*baacf047SPaolo Bonzini { 92*baacf047SPaolo Bonzini return err->err_class; 93*baacf047SPaolo Bonzini } 94*baacf047SPaolo Bonzini 95*baacf047SPaolo Bonzini const char *error_get_pretty(Error *err) 96*baacf047SPaolo Bonzini { 97*baacf047SPaolo Bonzini return err->msg; 98*baacf047SPaolo Bonzini } 99*baacf047SPaolo Bonzini 100*baacf047SPaolo Bonzini void error_free(Error *err) 101*baacf047SPaolo Bonzini { 102*baacf047SPaolo Bonzini if (err) { 103*baacf047SPaolo Bonzini g_free(err->msg); 104*baacf047SPaolo Bonzini g_free(err); 105*baacf047SPaolo Bonzini } 106*baacf047SPaolo Bonzini } 107*baacf047SPaolo Bonzini 108*baacf047SPaolo Bonzini void error_propagate(Error **dst_err, Error *local_err) 109*baacf047SPaolo Bonzini { 110*baacf047SPaolo Bonzini if (dst_err && !*dst_err) { 111*baacf047SPaolo Bonzini *dst_err = local_err; 112*baacf047SPaolo Bonzini } else if (local_err) { 113*baacf047SPaolo Bonzini error_free(local_err); 114*baacf047SPaolo Bonzini } 115*baacf047SPaolo Bonzini } 116