mirror of https://github.com/xqemu/xqemu.git
error: Fix use of error_prepend() with &error_fatal, &error_abort
From include/qapi/error.h: * Pass an existing error to the caller with the message modified: * error_propagate(errp, err); * error_prepend(errp, "Could not frobnicate '%s': ", name); Fei Li pointed out that doing error_propagate() first doesn't work well when @errp is &error_fatal or &error_abort: the error_prepend() is never reached. Since I doubt fixing the documentation will stop people from getting it wrong, introduce error_propagate_prepend(), in the hope that it lures people away from using its constituents in the wrong order. Update the instructions in error.h accordingly. Convert existing error_prepend() next to error_propagate to error_propagate_prepend(). If any of these get reached with &error_fatal or &error_abort, the error messages improve. I didn't check whether that's the case anywhere. Cc: Fei Li <fli@suse.com> Signed-off-by: Markus Armbruster <armbru@redhat.com> Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com> Reviewed-by: Eric Blake <eblake@redhat.com> Message-Id: <20181017082702.5581-2-armbru@redhat.com>
This commit is contained in:
parent
d7ecf71238
commit
4b5766488f
6
block.c
6
block.c
|
@ -4697,9 +4697,9 @@ bool bdrv_op_is_blocked(BlockDriverState *bs, BlockOpType op, Error **errp)
|
||||||
assert((int) op >= 0 && op < BLOCK_OP_TYPE_MAX);
|
assert((int) op >= 0 && op < BLOCK_OP_TYPE_MAX);
|
||||||
if (!QLIST_EMPTY(&bs->op_blockers[op])) {
|
if (!QLIST_EMPTY(&bs->op_blockers[op])) {
|
||||||
blocker = QLIST_FIRST(&bs->op_blockers[op]);
|
blocker = QLIST_FIRST(&bs->op_blockers[op]);
|
||||||
error_propagate(errp, error_copy(blocker->reason));
|
error_propagate_prepend(errp, error_copy(blocker->reason),
|
||||||
error_prepend(errp, "Node '%s' is busy: ",
|
"Node '%s' is busy: ",
|
||||||
bdrv_get_device_or_node_name(bs));
|
bdrv_get_device_or_node_name(bs));
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
|
|
|
@ -2208,8 +2208,8 @@ static void coroutine_fn qcow2_co_invalidate_cache(BlockDriverState *bs,
|
||||||
qemu_co_mutex_unlock(&s->lock);
|
qemu_co_mutex_unlock(&s->lock);
|
||||||
qobject_unref(options);
|
qobject_unref(options);
|
||||||
if (local_err) {
|
if (local_err) {
|
||||||
error_propagate(errp, local_err);
|
error_propagate_prepend(errp, local_err,
|
||||||
error_prepend(errp, "Could not reopen qcow2 layer: ");
|
"Could not reopen qcow2 layer: ");
|
||||||
bs->drv = NULL;
|
bs->drv = NULL;
|
||||||
return;
|
return;
|
||||||
} else if (ret < 0) {
|
} else if (ret < 0) {
|
||||||
|
|
|
@ -1606,8 +1606,8 @@ static void coroutine_fn bdrv_qed_co_invalidate_cache(BlockDriverState *bs,
|
||||||
ret = bdrv_qed_do_open(bs, NULL, bs->open_flags, &local_err);
|
ret = bdrv_qed_do_open(bs, NULL, bs->open_flags, &local_err);
|
||||||
qemu_co_mutex_unlock(&s->table_lock);
|
qemu_co_mutex_unlock(&s->table_lock);
|
||||||
if (local_err) {
|
if (local_err) {
|
||||||
error_propagate(errp, local_err);
|
error_propagate_prepend(errp, local_err,
|
||||||
error_prepend(errp, "Could not reopen qed layer: ");
|
"Could not reopen qed layer: ");
|
||||||
return;
|
return;
|
||||||
} else if (ret < 0) {
|
} else if (ret < 0) {
|
||||||
error_setg_errno(errp, -ret, "Could not reopen qed layer");
|
error_setg_errno(errp, -ret, "Could not reopen qed layer");
|
||||||
|
|
|
@ -1509,8 +1509,8 @@ static int local_parse_opts(QemuOpts *opts, FsDriverEntry *fse, Error **errp)
|
||||||
|
|
||||||
fsdev_throttle_parse_opts(opts, &fse->fst, &local_err);
|
fsdev_throttle_parse_opts(opts, &fse->fst, &local_err);
|
||||||
if (local_err) {
|
if (local_err) {
|
||||||
error_propagate(errp, local_err);
|
error_propagate_prepend(errp, local_err,
|
||||||
error_prepend(errp, "invalid throttle configuration: ");
|
"invalid throttle configuration: ");
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -320,8 +320,9 @@ static void icp_realize(DeviceState *dev, Error **errp)
|
||||||
|
|
||||||
obj = object_property_get_link(OBJECT(dev), ICP_PROP_XICS, &err);
|
obj = object_property_get_link(OBJECT(dev), ICP_PROP_XICS, &err);
|
||||||
if (!obj) {
|
if (!obj) {
|
||||||
error_propagate(errp, err);
|
error_propagate_prepend(errp, err,
|
||||||
error_prepend(errp, "required link '" ICP_PROP_XICS "' not found: ");
|
"required link '" ICP_PROP_XICS
|
||||||
|
"' not found: ");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -329,8 +330,9 @@ static void icp_realize(DeviceState *dev, Error **errp)
|
||||||
|
|
||||||
obj = object_property_get_link(OBJECT(dev), ICP_PROP_CPU, &err);
|
obj = object_property_get_link(OBJECT(dev), ICP_PROP_CPU, &err);
|
||||||
if (!obj) {
|
if (!obj) {
|
||||||
error_propagate(errp, err);
|
error_propagate_prepend(errp, err,
|
||||||
error_prepend(errp, "required link '" ICP_PROP_CPU "' not found: ");
|
"required link '" ICP_PROP_CPU
|
||||||
|
"' not found: ");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -624,8 +626,9 @@ static void ics_base_realize(DeviceState *dev, Error **errp)
|
||||||
|
|
||||||
obj = object_property_get_link(OBJECT(dev), ICS_PROP_XICS, &err);
|
obj = object_property_get_link(OBJECT(dev), ICS_PROP_XICS, &err);
|
||||||
if (!obj) {
|
if (!obj) {
|
||||||
error_propagate(errp, err);
|
error_propagate_prepend(errp, err,
|
||||||
error_prepend(errp, "required link '" ICS_PROP_XICS "' not found: ");
|
"required link '" ICS_PROP_XICS
|
||||||
|
"' not found: ");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
ics->xics = XICS_FABRIC(obj);
|
ics->xics = XICS_FABRIC(obj);
|
||||||
|
|
|
@ -148,8 +148,8 @@ static void pnv_core_realize(DeviceState *dev, Error **errp)
|
||||||
|
|
||||||
chip = object_property_get_link(OBJECT(dev), "chip", &local_err);
|
chip = object_property_get_link(OBJECT(dev), "chip", &local_err);
|
||||||
if (!chip) {
|
if (!chip) {
|
||||||
error_propagate(errp, local_err);
|
error_propagate_prepend(errp, local_err,
|
||||||
error_prepend(errp, "required link 'chip' not found: ");
|
"required link 'chip' not found: ");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1724,16 +1724,15 @@ static void spapr_phb_realize(DeviceState *dev, Error **errp)
|
||||||
if (smc->legacy_irq_allocation) {
|
if (smc->legacy_irq_allocation) {
|
||||||
irq = spapr_irq_findone(spapr, &local_err);
|
irq = spapr_irq_findone(spapr, &local_err);
|
||||||
if (local_err) {
|
if (local_err) {
|
||||||
error_propagate(errp, local_err);
|
error_propagate_prepend(errp, local_err,
|
||||||
error_prepend(errp, "can't allocate LSIs: ");
|
"can't allocate LSIs: ");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
spapr_irq_claim(spapr, irq, true, &local_err);
|
spapr_irq_claim(spapr, irq, true, &local_err);
|
||||||
if (local_err) {
|
if (local_err) {
|
||||||
error_propagate(errp, local_err);
|
error_propagate_prepend(errp, local_err, "can't allocate LSIs: ");
|
||||||
error_prepend(errp, "can't allocate LSIs: ");
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -454,8 +454,7 @@ static void aspeed_timer_realize(DeviceState *dev, Error **errp)
|
||||||
|
|
||||||
obj = object_property_get_link(OBJECT(dev), "scu", &err);
|
obj = object_property_get_link(OBJECT(dev), "scu", &err);
|
||||||
if (!obj) {
|
if (!obj) {
|
||||||
error_propagate(errp, err);
|
error_propagate_prepend(errp, err, "required link 'scu' not found: ");
|
||||||
error_prepend(errp, "required link 'scu' not found: ");
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
s->scu = ASPEED_SCU(obj);
|
s->scu = ASPEED_SCU(obj);
|
||||||
|
|
|
@ -340,8 +340,9 @@ static USBDevice *usb_try_create_simple(USBBus *bus, const char *name,
|
||||||
}
|
}
|
||||||
object_property_set_bool(OBJECT(dev), true, "realized", &err);
|
object_property_set_bool(OBJECT(dev), true, "realized", &err);
|
||||||
if (err) {
|
if (err) {
|
||||||
error_propagate(errp, err);
|
error_propagate_prepend(errp, err,
|
||||||
error_prepend(errp, "Failed to initialize USB device '%s': ", name);
|
"Failed to initialize USB device '%s': ",
|
||||||
|
name);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
return dev;
|
return dev;
|
||||||
|
|
|
@ -1283,8 +1283,7 @@ static int vfio_msi_setup(VFIOPCIDevice *vdev, int pos, Error **errp)
|
||||||
if (ret == -ENOTSUP) {
|
if (ret == -ENOTSUP) {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
error_prepend(&err, "msi_init failed: ");
|
error_propagate_prepend(errp, err, "msi_init failed: ");
|
||||||
error_propagate(errp, err);
|
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
vdev->msi_cap_size = 0xa + (msi_maskbit ? 0xa : 0) + (msi_64bit ? 0x4 : 0);
|
vdev->msi_cap_size = 0xa + (msi_maskbit ? 0xa : 0) + (msi_64bit ? 0x4 : 0);
|
||||||
|
|
|
@ -52,8 +52,12 @@
|
||||||
* where Error **errp is a parameter, by convention the last one.
|
* where Error **errp is a parameter, by convention the last one.
|
||||||
*
|
*
|
||||||
* Pass an existing error to the caller with the message modified:
|
* Pass an existing error to the caller with the message modified:
|
||||||
|
* error_propagate_prepend(errp, err);
|
||||||
|
*
|
||||||
|
* Avoid
|
||||||
* error_propagate(errp, err);
|
* error_propagate(errp, err);
|
||||||
* error_prepend(errp, "Could not frobnicate '%s': ", name);
|
* error_prepend(errp, "Could not frobnicate '%s': ", name);
|
||||||
|
* because this fails to prepend when @errp is &error_fatal.
|
||||||
*
|
*
|
||||||
* Create a new error and pass it to the caller:
|
* Create a new error and pass it to the caller:
|
||||||
* error_setg(errp, "situation normal, all fouled up");
|
* error_setg(errp, "situation normal, all fouled up");
|
||||||
|
@ -215,6 +219,16 @@ void error_setg_win32_internal(Error **errp,
|
||||||
*/
|
*/
|
||||||
void error_propagate(Error **dst_errp, Error *local_err);
|
void error_propagate(Error **dst_errp, Error *local_err);
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Propagate error object (if any) with some text prepended.
|
||||||
|
* Behaves like
|
||||||
|
* error_prepend(&local_err, fmt, ...);
|
||||||
|
* error_propagate(dst_errp, local_err);
|
||||||
|
*/
|
||||||
|
void error_propagate_prepend(Error **dst_errp, Error *local_err,
|
||||||
|
const char *fmt, ...);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Prepend some text to @errp's human-readable error message.
|
* Prepend some text to @errp's human-readable error message.
|
||||||
* The text is made by formatting @fmt, @ap like vprintf().
|
* The text is made by formatting @fmt, @ap like vprintf().
|
||||||
|
|
|
@ -1546,9 +1546,9 @@ static GSList *migration_blockers;
|
||||||
int migrate_add_blocker(Error *reason, Error **errp)
|
int migrate_add_blocker(Error *reason, Error **errp)
|
||||||
{
|
{
|
||||||
if (migrate_get_current()->only_migratable) {
|
if (migrate_get_current()->only_migratable) {
|
||||||
error_propagate(errp, error_copy(reason));
|
error_propagate_prepend(errp, error_copy(reason),
|
||||||
error_prepend(errp, "disallowing migration blocker "
|
"disallowing migration blocker "
|
||||||
"(--only_migratable) for: ");
|
"(--only_migratable) for: ");
|
||||||
return -EACCES;
|
return -EACCES;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1557,9 +1557,9 @@ int migrate_add_blocker(Error *reason, Error **errp)
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
error_propagate(errp, error_copy(reason));
|
error_propagate_prepend(errp, error_copy(reason),
|
||||||
error_prepend(errp, "disallowing migration blocker (migration in "
|
"disallowing migration blocker "
|
||||||
"progress) for: ");
|
"(migration in progress) for: ");
|
||||||
return -EBUSY;
|
return -EBUSY;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
13
util/error.c
13
util/error.c
|
@ -292,3 +292,16 @@ void error_propagate(Error **dst_errp, Error *local_err)
|
||||||
error_free(local_err);
|
error_free(local_err);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void error_propagate_prepend(Error **dst_errp, Error *err,
|
||||||
|
const char *fmt, ...)
|
||||||
|
{
|
||||||
|
va_list ap;
|
||||||
|
|
||||||
|
if (dst_errp && !*dst_errp) {
|
||||||
|
va_start(ap, fmt);
|
||||||
|
error_vprepend(&err, fmt, ap);
|
||||||
|
va_end(ap);
|
||||||
|
} /* else error is being ignored, don't bother with prepending */
|
||||||
|
error_propagate(dst_errp, err);
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in New Issue