+clib_error_t *
+vlib_pci_io_region (vlib_main_t * vm, vlib_pci_dev_handle_t h, u32 resource)
+{
+ linux_pci_device_t *p = linux_pci_get_device (h);
+ clib_error_t *error = 0;
+ int fd = -1;
+ u64 size = 0, offset = 0;
+
+ if ((error = vlib_pci_region (vm, h, resource, &fd, &size, &offset)))
+ return error;
+
+ p->io_fd = fd;
+ p->io_offset = offset;
+ return error;
+}
+
+clib_error_t *
+vlib_pci_read_write_io (vlib_main_t * vm, vlib_pci_dev_handle_t h,
+ vlib_read_or_write_t read_or_write,
+ uword offset, void *data, u32 length)
+{
+ linux_pci_device_t *p = linux_pci_get_device (h);
+ int n = 0;
+
+ if (read_or_write == VLIB_READ)
+ n = pread (p->io_fd, data, length, p->io_offset + offset);
+ else
+ n = pwrite (p->io_fd, data, length, p->io_offset + offset);
+
+ if (n != length)
+ return clib_error_return_unix (0, "%s",
+ read_or_write == VLIB_READ
+ ? "read" : "write");
+ return 0;
+}
+
+clib_error_t *
+vlib_pci_map_dma (vlib_main_t * vm, vlib_pci_dev_handle_t h, void *ptr)
+{
+ linux_pci_device_t *p = linux_pci_get_device (h);
+
+ if (!p->supports_va_dma)
+ return 0;
+
+ return vfio_map_physmem_page (vm, ptr);
+}
+
+int
+vlib_pci_supports_virtual_addr_dma (vlib_main_t * vm, vlib_pci_dev_handle_t h)
+{
+ linux_pci_device_t *p = linux_pci_get_device (h);
+
+ return p->supports_va_dma != 0;
+}
+