diff options
Diffstat (limited to 'src/vlib/linux/pci.c')
-rw-r--r-- | src/vlib/linux/pci.c | 113 |
1 files changed, 55 insertions, 58 deletions
diff --git a/src/vlib/linux/pci.c b/src/vlib/linux/pci.c index 75d9edf8849..e94fee1bcbd 100644 --- a/src/vlib/linux/pci.c +++ b/src/vlib/linux/pci.c @@ -61,12 +61,17 @@ static const char *sysfs_pci_drv_path = "/sys/bus/pci/drivers"; static char *sysfs_mod_vfio_noiommu = "/sys/module/vfio/parameters/enable_unsafe_noiommu_mode"; -#define pci_log_debug(vm, dev, f, ...) \ - vlib_log(VLIB_LOG_LEVEL_DEBUG, pci_main.log_default, "%U: " f, \ - format_vlib_pci_addr, vlib_pci_get_addr(vm, dev->handle), ## __VA_ARGS__) -#define pci_log_err(vm, dev, f, ...) \ - vlib_log(VLIB_LOG_LEVEL_ERR, pci_main.log_default, "%U: " f, \ - format_vlib_pci_addr, vlib_pci_get_addr(vm, dev->handle), ## __VA_ARGS__) +VLIB_REGISTER_LOG_CLASS (pci_log, static) = { + .class_name = "pci", + .subclass_name = "linux", +}; + +#define log_debug(p, f, ...) \ + vlib_log (VLIB_LOG_LEVEL_DEBUG, pci_log.class, "%U: " f, \ + format_vlib_pci_log, p->handle, ##__VA_ARGS__) +#define log_err(p, f, ...) \ + vlib_log (VLIB_LOG_LEVEL_ERR, pci_log.class, "%U: " f, format_vlib_pci_log, \ + p->handle, ##__VA_ARGS__) typedef struct { @@ -233,32 +238,13 @@ vlib_pci_get_device_info (vlib_main_t * vm, vlib_pci_addr_t * addr, /* You can only read more that 64 bytes of config space as root; so we try to read the full space but fall back to just the first 64 bytes. */ - if (read (fd, &di->config_data, sizeof (di->config_data)) < - sizeof (di->config0)) + if (read (fd, &di->config, sizeof (di->config)) < sizeof (di->config)) { err = clib_error_return_unix (0, "read `%s'", f); close (fd); goto error; } - { - static pci_config_header_t all_ones; - if (all_ones.vendor_id == 0) - clib_memset (&all_ones, ~0, sizeof (all_ones)); - - if (!memcmp (&di->config0.header, &all_ones, sizeof (all_ones))) - { - err = clib_error_return (0, "invalid PCI config for `%s'", f); - close (fd); - goto error; - } - } - - if (di->config0.header.header_type == 0) - pci_config_type0_little_to_host (&di->config0); - else - pci_config_type1_little_to_host (&di->config1); - di->numa_node = -1; vec_reset_length (f); f = format (f, "%v/numa_node%c", dev_dir_name, 0); @@ -301,6 +287,13 @@ vlib_pci_get_device_info (vlib_main_t * vm, vlib_pci_addr_t * addr, di->device_id = tmp; vec_reset_length (f); + f = format (f, "%v/revision%c", dev_dir_name, 0); + err = clib_sysfs_read ((char *) f, "0x%x", &tmp); + if (err) + goto error; + di->revision = tmp; + + vec_reset_length (f); f = format (f, "%v/driver%c", dev_dir_name, 0); di->driver_name = clib_sysfs_link_to_name ((char *) f); if (!di->driver_name) @@ -670,13 +663,12 @@ vfio_set_irqs (vlib_main_t * vm, linux_pci_device_t * p, u32 index, u32 start, return clib_error_return_unix (0, "ioctl(VFIO_DEVICE_GET_IRQ_INFO) " "'%U'", format_vlib_pci_addr, &p->addr); - pci_log_debug (vm, p, "%s index:%u count:%u flags: %s%s%s%s(0x%x)", - __func__, ii.index, ii.count, - ii.flags & VFIO_IRQ_INFO_EVENTFD ? "eventfd " : "", - ii.flags & VFIO_IRQ_INFO_MASKABLE ? "maskable " : "", - ii.flags & VFIO_IRQ_INFO_AUTOMASKED ? "automasked " : "", - ii.flags & VFIO_IRQ_INFO_NORESIZE ? "noresize " : "", - ii.flags); + log_debug (p, "%s index:%u count:%u flags: %s%s%s%s(0x%x)", __func__, + ii.index, ii.count, + ii.flags & VFIO_IRQ_INFO_EVENTFD ? "eventfd " : "", + ii.flags & VFIO_IRQ_INFO_MASKABLE ? "maskable " : "", + ii.flags & VFIO_IRQ_INFO_AUTOMASKED ? "automasked " : "", + ii.flags & VFIO_IRQ_INFO_NORESIZE ? "noresize " : "", ii.flags); if (ii.count < start + count) return clib_error_return_unix (0, "vfio_set_irq: unexistng interrupt on " @@ -864,13 +856,12 @@ vlib_pci_register_intx_handler (vlib_main_t * vm, vlib_pci_dev_handle_t h, if (ioctl (p->fd, VFIO_DEVICE_GET_IRQ_INFO, &ii) < 0) return clib_error_return_unix (0, "ioctl(VFIO_DEVICE_GET_IRQ_INFO) '" "%U'", format_vlib_pci_addr, &p->addr); - pci_log_debug (vm, p, "%s index:%u count:%u flags: %s%s%s%s(0x%x)", - __func__, ii.index, ii.count, - ii.flags & VFIO_IRQ_INFO_EVENTFD ? "eventfd " : "", - ii.flags & VFIO_IRQ_INFO_MASKABLE ? "maskable " : "", - ii.flags & VFIO_IRQ_INFO_AUTOMASKED ? "automasked " : "", - ii.flags & VFIO_IRQ_INFO_NORESIZE ? "noresize " : "", - ii.flags); + log_debug ( + p, "%s index:%u count:%u flags: %s%s%s%s(0x%x)", __func__, ii.index, + ii.count, ii.flags & VFIO_IRQ_INFO_EVENTFD ? "eventfd " : "", + ii.flags & VFIO_IRQ_INFO_MASKABLE ? "maskable " : "", + ii.flags & VFIO_IRQ_INFO_AUTOMASKED ? "automasked " : "", + ii.flags & VFIO_IRQ_INFO_NORESIZE ? "noresize " : "", ii.flags); if (ii.count != 1) return clib_error_return (0, "INTx interrupt does not exist on device" "'%U'", format_vlib_pci_addr, &p->addr); @@ -1042,7 +1033,7 @@ add_device_vfio (vlib_main_t * vm, linux_pci_device_t * p, goto error; } - pci_log_debug (vm, p, "%s %U", __func__, format_vfio_region_info, ®); + log_debug (p, "%s %U", __func__, format_vfio_region_info, ®); p->config_offset = reg.offset; p->config_fd = p->fd; @@ -1177,7 +1168,7 @@ vlib_pci_region (vlib_main_t * vm, vlib_pci_dev_handle_t h, u32 bar, int *fd, _fd = p->fd; _size = r->size; _offset = r->offset; - pci_log_debug (vm, p, "%s %U", __func__, format_vfio_region_info, r); + log_debug (p, "%s %U", __func__, format_vfio_region_info, r); clib_mem_free (r); } else @@ -1198,18 +1189,18 @@ vlib_pci_map_region_int (vlib_main_t * vm, vlib_pci_dev_handle_t h, int fd = -1; clib_error_t *error; u64 size = 0, offset = 0; - u16 command; + vlib_pci_config_reg_command_t command; - pci_log_debug (vm, p, "map region %u to va %p", bar, addr); + log_debug (p, "map region %u to va %p", bar, addr); - if ((error = vlib_pci_read_config_u16 (vm, h, 4, &command))) + if ((error = vlib_pci_read_config_u16 (vm, h, 4, &command.as_u16))) return error; - if (!(command & PCI_COMMAND_MEMORY)) + if (!(command.mem_space)) { - pci_log_debug (vm, p, "setting memory enable bit"); - command |= PCI_COMMAND_MEMORY; - if ((error = vlib_pci_write_config_u16 (vm, h, 4, &command))) + log_debug (p, "setting memory enable bit"); + command.mem_space = 1; + if ((error = vlib_pci_write_config_u16 (vm, h, 4, &command.as_u16))) return error; } @@ -1321,12 +1312,19 @@ vlib_pci_device_open (vlib_main_t * vm, vlib_pci_addr_t * addr, if (err) return err; - for (i = ids; i->vendor_id != 0; i++) - if (i->vendor_id == di->vendor_id && i->device_id == di->device_id) - break; - if (i->vendor_id == 0) - return clib_error_return (0, "Wrong vendor or device id"); + if (ids) + { + for (i = ids; i->vendor_id != 0; i++) + if (i->vendor_id == di->vendor_id && i->device_id == di->device_id) + break; + + if (i->vendor_id == 0) + { + vlib_pci_free_device_info (di); + return clib_error_return (0, "Wrong vendor or device id"); + } + } pool_get (lpm->linux_pci_devices, p); p->handle = p - lpm->linux_pci_devices; @@ -1339,9 +1337,8 @@ vlib_pci_device_open (vlib_main_t * vm, vlib_pci_addr_t * addr, */ p->io_fd = -1; - pci_log_debug (vm, p, "open vid:0x%04x did:0x%04x driver:%s iommu_group:%d", - di->vendor_id, di->device_id, di->driver_name, - di->iommu_group); + log_debug (p, "open vid:0x%04x did:0x%04x driver:%s iommu_group:%d", + di->vendor_id, di->device_id, di->driver_name, di->iommu_group); if (clib_strncmp ("vfio-pci", (char *) di->driver_name, 8) == 0) err = add_device_vfio (vm, p, di, 0); @@ -1359,7 +1356,7 @@ error: vlib_pci_free_device_info (di); if (err) { - pci_log_err (vm, p, "%U", format_clib_error, err); + log_err (p, "%U", format_clib_error, err); clib_memset (p, 0, sizeof (linux_pci_device_t)); pool_put (lpm->linux_pci_devices, p); } |