From patchwork Thu Jan 21 17:01:27 2016 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Stefano Stabellini X-Patchwork-Id: 8083401 Return-Path: X-Original-To: patchwork-qemu-devel@patchwork.kernel.org Delivered-To: patchwork-parsemail@patchwork1.web.kernel.org Received: from mail.kernel.org (mail.kernel.org [198.145.29.136]) by patchwork1.web.kernel.org (Postfix) with ESMTP id 62AA89F6FA for ; Thu, 21 Jan 2016 17:05:13 +0000 (UTC) Received: from mail.kernel.org (localhost [127.0.0.1]) by mail.kernel.org (Postfix) with ESMTP id 98EF220160 for ; Thu, 21 Jan 2016 17:05:07 +0000 (UTC) Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.kernel.org (Postfix) with ESMTPS id 652A7200F2 for ; Thu, 21 Jan 2016 17:05:06 +0000 (UTC) Received: from localhost ([::1]:48952 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1aMIfR-0000vZ-OH for patchwork-qemu-devel@patchwork.kernel.org; Thu, 21 Jan 2016 12:05:05 -0500 Received: from eggs.gnu.org ([2001:4830:134:3::10]:47600) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1aMId3-0004t7-DC for qemu-devel@nongnu.org; Thu, 21 Jan 2016 12:02:38 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1aMId1-0001tc-SS for qemu-devel@nongnu.org; Thu, 21 Jan 2016 12:02:37 -0500 Received: from smtp.citrix.com ([66.165.176.89]:15843) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1aMId1-0001rV-KV for qemu-devel@nongnu.org; Thu, 21 Jan 2016 12:02:35 -0500 X-IronPort-AV: E=Sophos;i="5.22,326,1449532800"; d="scan'208";a="326849777" From: Stefano Stabellini To: Date: Thu, 21 Jan 2016 17:01:27 +0000 Message-ID: <1453395690-32660-8-git-send-email-stefano.stabellini@eu.citrix.com> X-Mailer: git-send-email 1.7.9.5 In-Reply-To: References: MIME-Version: 1.0 X-DLP: MIA1 X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 66.165.176.89 Cc: Cao jin , xen-devel@lists.xensource.com, qemu-devel@nongnu.org, Stefano Stabellini Subject: [Qemu-devel] [PULL 08/11] Add Error **errp for xen_host_pci_device_get() X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org X-Spam-Status: No, score=-6.9 required=5.0 tests=BAYES_00, RCVD_IN_DNSWL_HI, UNPARSEABLE_RELAY autolearn=unavailable version=3.3.1 X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on mail.kernel.org X-Virus-Scanned: ClamAV using ClamSMTP From: Cao jin To catch the error message. Also modify the caller Signed-off-by: Cao jin Reviewed-by: Stefano Stabellini Reviewed-by: Eric Blake --- hw/xen/xen-host-pci-device.c | 102 +++++++++++++++++++++++------------------- hw/xen/xen-host-pci-device.h | 5 ++- hw/xen/xen_pt.c | 13 +++--- 3 files changed, 68 insertions(+), 52 deletions(-) diff --git a/hw/xen/xen-host-pci-device.c b/hw/xen/xen-host-pci-device.c index 83da9c4..3827ca7 100644 --- a/hw/xen/xen-host-pci-device.c +++ b/hw/xen/xen-host-pci-device.c @@ -44,7 +44,7 @@ static void xen_host_pci_sysfs_path(const XenHostPCIDevice *d, /* This size should be enough to read the first 7 lines of a resource file */ #define XEN_HOST_PCI_RESOURCE_BUFFER_SIZE 400 -static int xen_host_pci_get_resource(XenHostPCIDevice *d) +static void xen_host_pci_get_resource(XenHostPCIDevice *d, Error **errp) { int i, rc, fd; char path[PATH_MAX]; @@ -57,19 +57,18 @@ static int xen_host_pci_get_resource(XenHostPCIDevice *d) fd = open(path, O_RDONLY); if (fd == -1) { - XEN_HOST_PCI_LOG("Error: Can't open %s: %s\n", path, strerror(errno)); - return -errno; + error_setg_file_open(errp, errno, path); + return; } do { - rc = read(fd, &buf, sizeof (buf) - 1); + rc = read(fd, &buf, sizeof(buf) - 1); if (rc < 0 && errno != EINTR) { - rc = -errno; + error_setg_errno(errp, errno, "read err"); goto out; } } while (rc < 0); buf[rc] = 0; - rc = 0; s = buf; for (i = 0; i < PCI_NUM_REGIONS; i++) { @@ -122,20 +121,19 @@ static int xen_host_pci_get_resource(XenHostPCIDevice *d) d->rom.bus_flags = flags & IORESOURCE_BITS; } } + if (i != PCI_NUM_REGIONS) { - /* Invalid format or input to short */ - rc = -ENODEV; + error_setg(errp, "Invalid format or input too short: %s", buf); } out: close(fd); - return rc; } /* This size should be enough to read a long from a file */ #define XEN_HOST_PCI_GET_VALUE_BUFFER_SIZE 22 -static int xen_host_pci_get_value(XenHostPCIDevice *d, const char *name, - unsigned int *pvalue, int base) +static void xen_host_pci_get_value(XenHostPCIDevice *d, const char *name, + unsigned int *pvalue, int base, Error **errp) { char path[PATH_MAX]; char buf[XEN_HOST_PCI_GET_VALUE_BUFFER_SIZE]; @@ -147,39 +145,45 @@ static int xen_host_pci_get_value(XenHostPCIDevice *d, const char *name, fd = open(path, O_RDONLY); if (fd == -1) { - XEN_HOST_PCI_LOG("Error: Can't open %s: %s\n", path, strerror(errno)); - return -errno; + error_setg_file_open(errp, errno, path); + return; } + do { - rc = read(fd, &buf, sizeof (buf) - 1); + rc = read(fd, &buf, sizeof(buf) - 1); if (rc < 0 && errno != EINTR) { - rc = -errno; + error_setg_errno(errp, errno, "read err"); goto out; } } while (rc < 0); + buf[rc] = 0; rc = qemu_strtoul(buf, &endptr, base, &value); if (!rc) { assert(value <= UINT_MAX); *pvalue = value; + } else { + error_setg_errno(errp, -rc, "failed to parse value '%s'", buf); } + out: close(fd); - return rc; } -static inline int xen_host_pci_get_hex_value(XenHostPCIDevice *d, - const char *name, - unsigned int *pvalue) +static inline void xen_host_pci_get_hex_value(XenHostPCIDevice *d, + const char *name, + unsigned int *pvalue, + Error **errp) { - return xen_host_pci_get_value(d, name, pvalue, 16); + xen_host_pci_get_value(d, name, pvalue, 16, errp); } -static inline int xen_host_pci_get_dec_value(XenHostPCIDevice *d, - const char *name, - unsigned int *pvalue) +static inline void xen_host_pci_get_dec_value(XenHostPCIDevice *d, + const char *name, + unsigned int *pvalue, + Error **errp) { - return xen_host_pci_get_value(d, name, pvalue, 10); + xen_host_pci_get_value(d, name, pvalue, 10, errp); } static bool xen_host_pci_dev_is_virtfn(XenHostPCIDevice *d) @@ -192,17 +196,16 @@ static bool xen_host_pci_dev_is_virtfn(XenHostPCIDevice *d) return !stat(path, &buf); } -static int xen_host_pci_config_open(XenHostPCIDevice *d) +static void xen_host_pci_config_open(XenHostPCIDevice *d, Error **errp) { char path[PATH_MAX]; xen_host_pci_sysfs_path(d, "config", path, sizeof(path)); d->config_fd = open(path, O_RDWR); - if (d->config_fd < 0) { - return -errno; + if (d->config_fd == -1) { + error_setg_file_open(errp, errno, path); } - return 0; } static int xen_host_pci_config_read(XenHostPCIDevice *d, @@ -324,11 +327,12 @@ int xen_host_pci_find_ext_cap_offset(XenHostPCIDevice *d, uint32_t cap) return -1; } -int xen_host_pci_device_get(XenHostPCIDevice *d, uint16_t domain, - uint8_t bus, uint8_t dev, uint8_t func) +void xen_host_pci_device_get(XenHostPCIDevice *d, uint16_t domain, + uint8_t bus, uint8_t dev, uint8_t func, + Error **errp) { unsigned int v; - int rc = 0; + Error *err = NULL; d->config_fd = -1; d->domain = domain; @@ -336,43 +340,51 @@ int xen_host_pci_device_get(XenHostPCIDevice *d, uint16_t domain, d->dev = dev; d->func = func; - rc = xen_host_pci_config_open(d); - if (rc) { + xen_host_pci_config_open(d, &err); + if (err) { goto error; } - rc = xen_host_pci_get_resource(d); - if (rc) { + + xen_host_pci_get_resource(d, &err); + if (err) { goto error; } - rc = xen_host_pci_get_hex_value(d, "vendor", &v); - if (rc) { + + xen_host_pci_get_hex_value(d, "vendor", &v, &err); + if (err) { goto error; } d->vendor_id = v; - rc = xen_host_pci_get_hex_value(d, "device", &v); - if (rc) { + + xen_host_pci_get_hex_value(d, "device", &v, &err); + if (err) { goto error; } d->device_id = v; - rc = xen_host_pci_get_dec_value(d, "irq", &v); - if (rc) { + + xen_host_pci_get_dec_value(d, "irq", &v, &err); + if (err) { goto error; } d->irq = v; - rc = xen_host_pci_get_hex_value(d, "class", &v); - if (rc) { + + xen_host_pci_get_hex_value(d, "class", &v, &err); + if (err) { goto error; } d->class_code = v; + d->is_virtfn = xen_host_pci_dev_is_virtfn(d); - return 0; + return; + error: + error_propagate(errp, err); + if (d->config_fd >= 0) { close(d->config_fd); d->config_fd = -1; } - return rc; } bool xen_host_pci_device_closed(XenHostPCIDevice *d) diff --git a/hw/xen/xen-host-pci-device.h b/hw/xen/xen-host-pci-device.h index 3d44e04..6acf36e 100644 --- a/hw/xen/xen-host-pci-device.h +++ b/hw/xen/xen-host-pci-device.h @@ -36,8 +36,9 @@ typedef struct XenHostPCIDevice { int config_fd; } XenHostPCIDevice; -int xen_host_pci_device_get(XenHostPCIDevice *d, uint16_t domain, - uint8_t bus, uint8_t dev, uint8_t func); +void xen_host_pci_device_get(XenHostPCIDevice *d, uint16_t domain, + uint8_t bus, uint8_t dev, uint8_t func, + Error **errp); void xen_host_pci_device_put(XenHostPCIDevice *pci_dev); bool xen_host_pci_device_closed(XenHostPCIDevice *d); diff --git a/hw/xen/xen_pt.c b/hw/xen/xen_pt.c index aa96288..53b5bca 100644 --- a/hw/xen/xen_pt.c +++ b/hw/xen/xen_pt.c @@ -767,6 +767,7 @@ static int xen_pt_initfn(PCIDevice *d) uint8_t machine_irq = 0, scratch; uint16_t cmd = 0; int pirq = XEN_PT_UNASSIGNED_PIRQ; + Error *err = NULL; /* register real device */ XEN_PT_LOG(d, "Assigning real physical device %02x:%02x.%d" @@ -774,11 +775,13 @@ static int xen_pt_initfn(PCIDevice *d) s->hostaddr.bus, s->hostaddr.slot, s->hostaddr.function, s->dev.devfn); - rc = xen_host_pci_device_get(&s->real_device, - s->hostaddr.domain, s->hostaddr.bus, - s->hostaddr.slot, s->hostaddr.function); - if (rc) { - XEN_PT_ERR(d, "Failed to \"open\" the real pci device. rc: %i\n", rc); + xen_host_pci_device_get(&s->real_device, + s->hostaddr.domain, s->hostaddr.bus, + s->hostaddr.slot, s->hostaddr.function, + &err); + if (err) { + error_append_hint(&err, "Failed to \"open\" the real pci device"); + error_report_err(err); return -1; }