Lines Matching +full:we +full:- +full:extra +full:- +full:delay
1 // SPDX-License-Identifier: GPL-2.0
14 #include <linux/virtio-uml.h>
15 #include <linux/delay.h>
24 /* for MSI-X we have a 32-bit payload */
74 const void *extra, unsigned int extra_size, in um_pci_send_cmd() argument
80 [1] = extra ? &extra_sg : &in_sg, in um_pci_send_cmd()
81 [2] = extra ? &in_sg : NULL, in um_pci_send_cmd()
89 return -EINVAL; in um_pci_send_cmd()
91 switch (cmd->op) { in um_pci_send_cmd()
113 if (extra) in um_pci_send_cmd()
114 memcpy(ncmd + cmd_size, extra, extra_size); in um_pci_send_cmd()
117 extra = NULL; in um_pci_send_cmd()
129 if (extra) in um_pci_send_cmd()
130 sg_init_one(&extra_sg, extra, extra_size); in um_pci_send_cmd()
135 ret = virtqueue_add_sgs(dev->cmd_vq, sgs_list, in um_pci_send_cmd()
136 extra ? 2 : 1, in um_pci_send_cmd()
147 virtqueue_kick(dev->cmd_vq); in um_pci_send_cmd()
153 set_bit(UM_PCI_STAT_WAITING, &dev->status); in um_pci_send_cmd()
154 virtqueue_kick(dev->cmd_vq); in um_pci_send_cmd()
157 void *completed = virtqueue_get_buf(dev->cmd_vq, &len); in um_pci_send_cmd()
165 if (WARN_ONCE(virtqueue_is_broken(dev->cmd_vq) || in um_pci_send_cmd()
167 "um virt-pci delay: %d", delay_count)) { in um_pci_send_cmd()
168 ret = -EIO; in um_pci_send_cmd()
173 clear_bit(UM_PCI_STAT_WAITING, &dev->status); in um_pci_send_cmd()
184 struct um_pci_device *dev = reg->dev; in um_pci_cfgspace_read()
190 /* buf->data is maximum size - we may only use parts of it */ in um_pci_cfgspace_read()
194 size_t bytes = sizeof(buf->data); in um_pci_cfgspace_read()
200 data = buf->data; in um_pci_cfgspace_read()
249 struct um_pci_device *dev = reg->dev; in um_pci_cfgspace_write()
252 /* maximum size - we may only use parts of it */ in um_pci_cfgspace_write()
297 struct um_pci_device *dev = container_of(resptr - *resptr, in um_pci_bar_copy_from()
315 /* buf->data is maximum size - we may only use parts of it */ in um_pci_bar_read()
321 data = buf->data; in um_pci_bar_read()
366 struct um_pci_device *dev = container_of(resptr - *resptr, in um_pci_bar_copy_to()
382 /* maximum size - we may only use parts of it */ in um_pci_bar_write()
411 struct um_pci_device *dev = container_of(resptr - *resptr, in um_pci_bar_set()
442 unsigned int busn = bus->number; in um_pci_map_bus()
458 return (void __iomem *)((unsigned long)dev->iomem + where); in um_pci_map_bus()
470 pci_rescan_bus(bridge->bus); in um_pci_rescan()
488 struct virtio_device *vdev = vq->vdev; in um_pci_handle_irq_message()
489 struct um_pci_device *dev = vdev->priv; in um_pci_handle_irq_message()
491 if (!dev->irq) in um_pci_handle_irq_message()
494 /* we should properly chain interrupts, but on ARCH=um we don't care */ in um_pci_handle_irq_message()
496 switch (msg->op) { in um_pci_handle_irq_message()
498 generic_handle_irq(dev->irq); in um_pci_handle_irq_message()
502 if (msg->size == sizeof(u32)) in um_pci_handle_irq_message()
503 generic_handle_irq(le32_to_cpup((void *)msg->data)); in um_pci_handle_irq_message()
505 generic_handle_irq(le16_to_cpup((void *)msg->data)); in um_pci_handle_irq_message()
508 /* nothing to do - we already woke up due to the message */ in um_pci_handle_irq_message()
511 dev_err(&vdev->dev, "unexpected virt-pci message %d\n", msg->op); in um_pci_handle_irq_message()
518 struct virtio_device *vdev = vq->vdev; in um_pci_cmd_vq_cb()
519 struct um_pci_device *dev = vdev->priv; in um_pci_cmd_vq_cb()
523 if (test_bit(UM_PCI_STAT_WAITING, &dev->status)) in um_pci_cmd_vq_cb()
557 prop = of_get_property(np, "bus-range", NULL); in pcibios_get_phb_of_node()
561 if (bus->number == bus_min) in pcibios_get_phb_of_node()
577 err = virtio_find_vqs(dev->vdev, 2, vqs, vqs_info, NULL); in um_pci_init_vqs()
581 dev->cmd_vq = vqs[0]; in um_pci_init_vqs()
582 dev->irq_vq = vqs[1]; in um_pci_init_vqs()
584 virtio_device_ready(dev->vdev); in um_pci_init_vqs()
590 um_pci_irq_vq_addbuf(dev->irq_vq, msg, false); in um_pci_init_vqs()
593 virtqueue_kick(dev->irq_vq); in um_pci_init_vqs()
602 vdev->config->del_vqs(vdev); in __um_pci_virtio_platform_remove()
616 dev->platform = true; in um_pci_virtio_platform_probe()
622 ret = -EBUSY; in um_pci_virtio_platform_probe()
636 ret = of_platform_default_populate(vdev->dev.of_node, NULL, &vdev->dev); in um_pci_virtio_platform_probe()
650 int i, free = -1; in um_pci_virtio_probe()
651 int err = -ENOSPC; in um_pci_virtio_probe()
655 return -ENOMEM; in um_pci_virtio_probe()
657 dev->vdev = vdev; in um_pci_virtio_probe()
658 vdev->priv = dev; in um_pci_virtio_probe()
660 if (of_device_is_compatible(vdev->dev.of_node, "simple-bus")) in um_pci_virtio_probe()
678 dev->irq = irq_alloc_desc(numa_node_id()); in um_pci_virtio_probe()
679 if (dev->irq < 0) { in um_pci_virtio_probe()
680 err = dev->irq; in um_pci_virtio_probe()
684 vdev->priv = dev; in um_pci_virtio_probe()
688 device_set_wakeup_enable(&vdev->dev, true); in um_pci_virtio_probe()
691 * In order to do suspend-resume properly, don't allow VQs in um_pci_virtio_probe()
700 vdev->config->del_vqs(vdev); in um_pci_virtio_probe()
709 struct um_pci_device *dev = vdev->priv; in um_pci_virtio_remove()
712 if (dev->platform) { in um_pci_virtio_remove()
713 of_platform_depopulate(&vdev->dev); in um_pci_virtio_remove()
718 device_set_wakeup_enable(&vdev->dev, false); in um_pci_virtio_remove()
726 irq_free_desc(dev->irq); in um_pci_virtio_remove()
735 pci_dev = pci_get_slot(bridge->bus, i); in um_pci_virtio_remove()
742 dev->cmd_vq = NULL; in um_pci_virtio_remove()
743 dev->irq_vq = NULL; in um_pci_virtio_remove()
744 vdev->config->del_vqs(vdev); in um_pci_virtio_remove()
756 .driver.name = "virtio-pci",
764 .start = 0xf0000000 - MAX_DEVICES * CFG_SPACE_SIZE,
765 .end = 0xf0000000 - 1,
774 return -EINVAL; in um_pci_map_cfgspace()
783 return -ENOENT; in um_pci_map_cfgspace()
808 struct um_pci_device_reg *reg = &um_pci_devices[pdev->devfn / 8]; in um_pci_map_iomem_walk()
812 if (!reg->dev) in um_pci_map_iomem_walk()
815 for (i = 0; i < ARRAY_SIZE(dev->resptr); i++) { in um_pci_map_iomem_walk()
816 struct resource *r = &pdev->resource[i]; in um_pci_map_iomem_walk()
818 if ((r->flags & IORESOURCE_TYPE_BITS) != IORESOURCE_MEM) in um_pci_map_iomem_walk()
825 if (data->offset < r->start || data->offset > r->end) in um_pci_map_iomem_walk()
827 if (data->offset + data->size - 1 > r->end) in um_pci_map_iomem_walk()
830 dev = reg->dev; in um_pci_map_iomem_walk()
831 *data->ops = &um_pci_device_bar_ops; in um_pci_map_iomem_walk()
832 dev->resptr[i] = i; in um_pci_map_iomem_walk()
833 *data->priv = &dev->resptr[i]; in um_pci_map_iomem_walk()
834 data->ret = data->offset - r->start; in um_pci_map_iomem_walk()
848 /* we want the full address here */ in um_pci_map_iomem()
853 .ret = -ENOENT, in um_pci_map_iomem()
856 pci_walk_bus(bridge->bus, um_pci_map_iomem_walk, &data); in um_pci_map_iomem()
868 * in UML, so we can simply map MSI(-X) vectors to there, it cannot be in um_pci_compose_msi_msg()
870 * We use the (virtual) IRQ number here as the message to simplify the in um_pci_compose_msi_msg()
871 * code that receives the message, where for now we simply trust the in um_pci_compose_msi_msg()
874 msg->address_hi = 0; in um_pci_compose_msi_msg()
875 msg->address_lo = 0xa0000; in um_pci_compose_msi_msg()
876 msg->data = data->irq; in um_pci_compose_msi_msg()
896 return -ENOSPC; in um_pci_inner_domain_alloc()
903 domain->host_data, handle_simple_irq, in um_pci_inner_domain_alloc()
916 if (!test_bit(d->hwirq, um_pci_msi_used)) in um_pci_inner_domain_free()
917 pr_err("trying to free unused MSI#%lu\n", d->hwirq); in um_pci_inner_domain_free()
919 __clear_bit(d->hwirq, um_pci_msi_used); in um_pci_inner_domain_free()
951 struct um_pci_device_reg *reg = &um_pci_devices[pdev->devfn / 8]; in um_pci_map_irq()
953 if (WARN_ON(!reg->dev)) in um_pci_map_irq()
954 return -EINVAL; in um_pci_map_irq()
956 /* Yes, we map all pins to the same IRQ ... doesn't matter for now. */ in um_pci_map_irq()
957 return reg->dev->irq; in um_pci_map_irq()
970 return -ENOENT; in um_pci_map_platform()
973 *priv = &um_pci_platform_device->resptr[0]; in um_pci_map_platform()
1006 "No virtio device ID configured for PCI - no PCI support\n")) in um_pci_init()
1011 return -ENOMEM; in um_pci_init()
1015 err = -ENOMEM; in um_pci_init()
1019 um_pci_fwnode = irq_domain_alloc_named_fwnode("um-pci"); in um_pci_init()
1021 err = -ENOMEM; in um_pci_init()
1036 err = -ENOMEM; in um_pci_init()
1040 pci_add_resource(&bridge->windows, &virt_iomem_resource); in um_pci_init()
1041 pci_add_resource(&bridge->windows, &busn_resource); in um_pci_init()
1042 bridge->ops = &um_pci_ops; in um_pci_init()
1043 bridge->map_irq = um_pci_map_irq; in um_pci_init()
1051 err = -ENOMEM; in um_pci_init()
1070 pci_free_resource_list(&bridge->windows); in um_pci_init()
1083 pci_free_resource_list(&bridge->windows); in um_pci_exit()