mirror of
https://github.com/izzy2lost/xemu.git
synced 2026-07-06 00:20:22 -07:00
Merge remote-tracking branch 'remotes/mst/tags/for_upstream' into staging
pc, acpi, pci, virtio: fixes, cleanups, features, tests Some fixes and cleanups. New tests. Configurable tx queue size for virtio-net. Signed-off-by: Michael S. Tsirkin <mst@redhat.com> # gpg: Signature made Mon 03 Jul 2017 20:43:17 BST # gpg: using RSA key 0x281F0DB8D28D5469 # gpg: Good signature from "Michael S. Tsirkin <mst@kernel.org>" # gpg: aka "Michael S. Tsirkin <mst@redhat.com>" # gpg: WARNING: This key is not certified with a trusted signature! # gpg: There is no indication that the signature belongs to the owner. # Primary key fingerprint: 0270 606B 6F3C DF3D 0B17 0970 C350 3912 AFBE 8E67 # Subkey fingerprint: 5D09 FD08 71C8 F85B 94CA 8A0D 281F 0DB8 D28D 5469 * remotes/mst/tags/for_upstream: (21 commits) i386/acpi: update expected acpi files virtio-net: fix tx queue size for !vhost-user tests: Add unit tests for the VM Generation ID feature vhost-user: unregister slave req handler at cleanup time vhost: ensure vhost_ops are set before calling iotlb callback intel_iommu: fix migration breakage on mr switch hw/acpi: remove dead acpi code fw_cfg: move setting of FW_CFG_VERSION_DMA bit to fw_cfg_init1() fw_cfg: don't map the fw_cfg IO ports in fw_cfg_io_realize() i386/kvm/pci-assign: Use errp directly rather than local_err i386/kvm/pci-assign: Fix return type of verify_irqchip_kernel() pci: Convert shpc_init() to Error pci: Convert to realize pci: Replace pci_add_capability2() with pci_add_capability() pci: Make errp the last parameter of pci_add_capability() pci: Fix the wrong assertion. pci: Add comment for pci_add_capability2() pci: Clean up error checking in pci_add_capability() intel_iommu: relax iq tail check on VTD_GCMD_QIE enable hw/pci-bridge/dec: Classify the DEC PCI bridge as bridge device ... Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
This commit is contained in:
@@ -1912,16 +1912,6 @@ build_dsdt(GArray *table_data, BIOSLinker *linker,
|
||||
build_piix4_pci_hotplug(dsdt);
|
||||
build_piix4_pci0_int(dsdt);
|
||||
} else {
|
||||
sb_scope = aml_scope("_SB");
|
||||
aml_append(sb_scope,
|
||||
aml_operation_region("PCST", AML_SYSTEM_IO, aml_int(0xae00), 0x0c));
|
||||
aml_append(sb_scope,
|
||||
aml_operation_region("PCSB", AML_SYSTEM_IO, aml_int(0xae0c), 0x01));
|
||||
field = aml_field("PCSB", AML_ANY_ACC, AML_NOLOCK, AML_WRITE_AS_ZEROS);
|
||||
aml_append(field, aml_named_field("PCIB", 8));
|
||||
aml_append(sb_scope, field);
|
||||
aml_append(dsdt, sb_scope);
|
||||
|
||||
sb_scope = aml_scope("_SB");
|
||||
dev = aml_device("PCI0");
|
||||
aml_append(dev, aml_name_decl("_HID", aml_eisaid("PNP0A08")));
|
||||
|
||||
+17
-7
@@ -1158,13 +1158,23 @@ static void amdvi_realize(DeviceState *dev, Error **err)
|
||||
x86_iommu->type = TYPE_AMD;
|
||||
qdev_set_parent_bus(DEVICE(&s->pci), &bus->qbus);
|
||||
object_property_set_bool(OBJECT(&s->pci), true, "realized", err);
|
||||
s->capab_offset = pci_add_capability(&s->pci.dev, AMDVI_CAPAB_ID_SEC, 0,
|
||||
AMDVI_CAPAB_SIZE);
|
||||
assert(s->capab_offset > 0);
|
||||
ret = pci_add_capability(&s->pci.dev, PCI_CAP_ID_MSI, 0, AMDVI_CAPAB_REG_SIZE);
|
||||
assert(ret > 0);
|
||||
ret = pci_add_capability(&s->pci.dev, PCI_CAP_ID_HT, 0, AMDVI_CAPAB_REG_SIZE);
|
||||
assert(ret > 0);
|
||||
ret = pci_add_capability(&s->pci.dev, AMDVI_CAPAB_ID_SEC, 0,
|
||||
AMDVI_CAPAB_SIZE, err);
|
||||
if (ret < 0) {
|
||||
return;
|
||||
}
|
||||
s->capab_offset = ret;
|
||||
|
||||
ret = pci_add_capability(&s->pci.dev, PCI_CAP_ID_MSI, 0,
|
||||
AMDVI_CAPAB_REG_SIZE, err);
|
||||
if (ret < 0) {
|
||||
return;
|
||||
}
|
||||
ret = pci_add_capability(&s->pci.dev, PCI_CAP_ID_HT, 0,
|
||||
AMDVI_CAPAB_REG_SIZE, err);
|
||||
if (ret < 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
/* set up MMIO */
|
||||
memory_region_init_io(&s->mmio, OBJECT(s), &mmio_mem_ops, s, "amdvi-mmio",
|
||||
|
||||
+34
-14
@@ -1450,10 +1450,7 @@ static uint64_t vtd_iotlb_flush(IntelIOMMUState *s, uint64_t val)
|
||||
return iaig;
|
||||
}
|
||||
|
||||
static inline bool vtd_queued_inv_enable_check(IntelIOMMUState *s)
|
||||
{
|
||||
return s->iq_tail == 0;
|
||||
}
|
||||
static void vtd_fetch_inv_desc(IntelIOMMUState *s);
|
||||
|
||||
static inline bool vtd_queued_inv_disable_check(IntelIOMMUState *s)
|
||||
{
|
||||
@@ -1468,16 +1465,24 @@ static void vtd_handle_gcmd_qie(IntelIOMMUState *s, bool en)
|
||||
trace_vtd_inv_qi_enable(en);
|
||||
|
||||
if (en) {
|
||||
if (vtd_queued_inv_enable_check(s)) {
|
||||
s->iq = iqa_val & VTD_IQA_IQA_MASK;
|
||||
/* 2^(x+8) entries */
|
||||
s->iq_size = 1UL << ((iqa_val & VTD_IQA_QS) + 8);
|
||||
s->qi_enabled = true;
|
||||
trace_vtd_inv_qi_setup(s->iq, s->iq_size);
|
||||
/* Ok - report back to driver */
|
||||
vtd_set_clear_mask_long(s, DMAR_GSTS_REG, 0, VTD_GSTS_QIES);
|
||||
} else {
|
||||
trace_vtd_err_qi_enable(s->iq_tail);
|
||||
s->iq = iqa_val & VTD_IQA_IQA_MASK;
|
||||
/* 2^(x+8) entries */
|
||||
s->iq_size = 1UL << ((iqa_val & VTD_IQA_QS) + 8);
|
||||
s->qi_enabled = true;
|
||||
trace_vtd_inv_qi_setup(s->iq, s->iq_size);
|
||||
/* Ok - report back to driver */
|
||||
vtd_set_clear_mask_long(s, DMAR_GSTS_REG, 0, VTD_GSTS_QIES);
|
||||
|
||||
if (s->iq_tail != 0) {
|
||||
/*
|
||||
* This is a spec violation but Windows guests are known to set up
|
||||
* Queued Invalidation this way so we allow the write and process
|
||||
* Invalidation Descriptors right away.
|
||||
*/
|
||||
trace_vtd_warn_invalid_qi_tail(s->iq_tail);
|
||||
if (!(vtd_get_long_raw(s, DMAR_FSTS_REG) & VTD_FSTS_IQE)) {
|
||||
vtd_fetch_inv_desc(s);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (vtd_queued_inv_disable_check(s)) {
|
||||
@@ -2332,11 +2337,26 @@ static void vtd_iommu_notify_flag_changed(MemoryRegion *iommu,
|
||||
}
|
||||
}
|
||||
|
||||
static int vtd_post_load(void *opaque, int version_id)
|
||||
{
|
||||
IntelIOMMUState *iommu = opaque;
|
||||
|
||||
/*
|
||||
* Memory regions are dynamically turned on/off depending on
|
||||
* context entry configurations from the guest. After migration,
|
||||
* we need to make sure the memory regions are still correct.
|
||||
*/
|
||||
vtd_switch_address_space_all(iommu);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static const VMStateDescription vtd_vmstate = {
|
||||
.name = "iommu-intel",
|
||||
.version_id = 1,
|
||||
.minimum_version_id = 1,
|
||||
.priority = MIG_PRI_IOMMU,
|
||||
.post_load = vtd_post_load,
|
||||
.fields = (VMStateField[]) {
|
||||
VMSTATE_UINT64(root, IntelIOMMUState),
|
||||
VMSTATE_UINT64(intr_root, IntelIOMMUState),
|
||||
|
||||
+20
-34
@@ -824,12 +824,13 @@ static void assign_device(AssignedDevice *dev, Error **errp)
|
||||
}
|
||||
}
|
||||
|
||||
static void verify_irqchip_in_kernel(Error **errp)
|
||||
static int verify_irqchip_in_kernel(Error **errp)
|
||||
{
|
||||
if (kvm_irqchip_in_kernel()) {
|
||||
return;
|
||||
return -1;
|
||||
}
|
||||
error_setg(errp, "pci-assign requires KVM with in-kernel irqchip enabled");
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int assign_intx(AssignedDevice *dev, Error **errp)
|
||||
@@ -838,7 +839,6 @@ static int assign_intx(AssignedDevice *dev, Error **errp)
|
||||
PCIINTxRoute intx_route;
|
||||
bool intx_host_msi;
|
||||
int r;
|
||||
Error *local_err = NULL;
|
||||
|
||||
/* Interrupt PIN 0 means don't use INTx */
|
||||
if (assigned_dev_pci_read_byte(&dev->dev, PCI_INTERRUPT_PIN) == 0) {
|
||||
@@ -846,9 +846,7 @@ static int assign_intx(AssignedDevice *dev, Error **errp)
|
||||
return 0;
|
||||
}
|
||||
|
||||
verify_irqchip_in_kernel(&local_err);
|
||||
if (local_err) {
|
||||
error_propagate(errp, local_err);
|
||||
if (verify_irqchip_in_kernel(errp) < 0) {
|
||||
return -ENOTSUP;
|
||||
}
|
||||
|
||||
@@ -1234,7 +1232,6 @@ static int assigned_device_pci_cap_init(PCIDevice *pci_dev, Error **errp)
|
||||
AssignedDevice *dev = PCI_ASSIGN(pci_dev);
|
||||
PCIRegion *pci_region = dev->real_device.regions;
|
||||
int ret, pos;
|
||||
Error *local_err = NULL;
|
||||
|
||||
/* Clear initial capabilities pointer and status copied from hw */
|
||||
pci_set_byte(pci_dev->config + PCI_CAPABILITY_LIST, 0);
|
||||
@@ -1246,18 +1243,15 @@ static int assigned_device_pci_cap_init(PCIDevice *pci_dev, Error **errp)
|
||||
* MSI capability is the 1st capability in capability config */
|
||||
pos = pci_find_cap_offset(pci_dev, PCI_CAP_ID_MSI, 0);
|
||||
if (pos != 0 && kvm_check_extension(kvm_state, KVM_CAP_ASSIGN_DEV_IRQ)) {
|
||||
verify_irqchip_in_kernel(&local_err);
|
||||
if (local_err) {
|
||||
error_propagate(errp, local_err);
|
||||
if (verify_irqchip_in_kernel(errp) < 0) {
|
||||
return -ENOTSUP;
|
||||
}
|
||||
dev->dev.cap_present |= QEMU_PCI_CAP_MSI;
|
||||
dev->cap.available |= ASSIGNED_DEVICE_CAP_MSI;
|
||||
/* Only 32-bit/no-mask currently supported */
|
||||
ret = pci_add_capability2(pci_dev, PCI_CAP_ID_MSI, pos, 10,
|
||||
&local_err);
|
||||
ret = pci_add_capability(pci_dev, PCI_CAP_ID_MSI, pos, 10,
|
||||
errp);
|
||||
if (ret < 0) {
|
||||
error_propagate(errp, local_err);
|
||||
return ret;
|
||||
}
|
||||
pci_dev->msi_cap = pos;
|
||||
@@ -1281,17 +1275,14 @@ static int assigned_device_pci_cap_init(PCIDevice *pci_dev, Error **errp)
|
||||
uint32_t msix_table_entry;
|
||||
uint16_t msix_max;
|
||||
|
||||
verify_irqchip_in_kernel(&local_err);
|
||||
if (local_err) {
|
||||
error_propagate(errp, local_err);
|
||||
if (verify_irqchip_in_kernel(errp) < 0) {
|
||||
return -ENOTSUP;
|
||||
}
|
||||
dev->dev.cap_present |= QEMU_PCI_CAP_MSIX;
|
||||
dev->cap.available |= ASSIGNED_DEVICE_CAP_MSIX;
|
||||
ret = pci_add_capability2(pci_dev, PCI_CAP_ID_MSIX, pos, 12,
|
||||
&local_err);
|
||||
ret = pci_add_capability(pci_dev, PCI_CAP_ID_MSIX, pos, 12,
|
||||
errp);
|
||||
if (ret < 0) {
|
||||
error_propagate(errp, local_err);
|
||||
return ret;
|
||||
}
|
||||
pci_dev->msix_cap = pos;
|
||||
@@ -1318,10 +1309,9 @@ static int assigned_device_pci_cap_init(PCIDevice *pci_dev, Error **errp)
|
||||
if (pos) {
|
||||
uint16_t pmc;
|
||||
|
||||
ret = pci_add_capability2(pci_dev, PCI_CAP_ID_PM, pos, PCI_PM_SIZEOF,
|
||||
&local_err);
|
||||
ret = pci_add_capability(pci_dev, PCI_CAP_ID_PM, pos, PCI_PM_SIZEOF,
|
||||
errp);
|
||||
if (ret < 0) {
|
||||
error_propagate(errp, local_err);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -1386,10 +1376,9 @@ static int assigned_device_pci_cap_init(PCIDevice *pci_dev, Error **errp)
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
ret = pci_add_capability2(pci_dev, PCI_CAP_ID_EXP, pos, size,
|
||||
&local_err);
|
||||
ret = pci_add_capability(pci_dev, PCI_CAP_ID_EXP, pos, size,
|
||||
errp);
|
||||
if (ret < 0) {
|
||||
error_propagate(errp, local_err);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -1462,10 +1451,9 @@ static int assigned_device_pci_cap_init(PCIDevice *pci_dev, Error **errp)
|
||||
uint32_t status;
|
||||
|
||||
/* Only expose the minimum, 8 byte capability */
|
||||
ret = pci_add_capability2(pci_dev, PCI_CAP_ID_PCIX, pos, 8,
|
||||
&local_err);
|
||||
ret = pci_add_capability(pci_dev, PCI_CAP_ID_PCIX, pos, 8,
|
||||
errp);
|
||||
if (ret < 0) {
|
||||
error_propagate(errp, local_err);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -1490,10 +1478,9 @@ static int assigned_device_pci_cap_init(PCIDevice *pci_dev, Error **errp)
|
||||
pos = pci_find_cap_offset(pci_dev, PCI_CAP_ID_VPD, 0);
|
||||
if (pos) {
|
||||
/* Direct R/W passthrough */
|
||||
ret = pci_add_capability2(pci_dev, PCI_CAP_ID_VPD, pos, 8,
|
||||
&local_err);
|
||||
ret = pci_add_capability(pci_dev, PCI_CAP_ID_VPD, pos, 8,
|
||||
errp);
|
||||
if (ret < 0) {
|
||||
error_propagate(errp, local_err);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@@ -1508,10 +1495,9 @@ static int assigned_device_pci_cap_init(PCIDevice *pci_dev, Error **errp)
|
||||
pos += PCI_CAP_LIST_NEXT) {
|
||||
uint8_t len = pci_get_byte(pci_dev->config + pos + PCI_CAP_FLAGS);
|
||||
/* Direct R/W passthrough */
|
||||
ret = pci_add_capability2(pci_dev, PCI_CAP_ID_VNDR, pos, len,
|
||||
&local_err);
|
||||
ret = pci_add_capability(pci_dev, PCI_CAP_ID_VNDR, pos, len,
|
||||
errp);
|
||||
if (ret < 0) {
|
||||
error_propagate(errp, local_err);
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
@@ -74,7 +74,7 @@ vtd_err_dmar_slpte_read_error(uint64_t iova, int level) "iova 0x%"PRIx64" level
|
||||
vtd_err_dmar_slpte_perm_error(uint64_t iova, int level, uint64_t slpte, bool is_write) "iova 0x%"PRIx64" level %d slpte 0x%"PRIx64" write %d"
|
||||
vtd_err_dmar_slpte_resv_error(uint64_t iova, int level, uint64_t slpte) "iova 0x%"PRIx64" level %d slpte 0x%"PRIx64
|
||||
vtd_err_dmar_translate(uint8_t bus, uint8_t slot, uint8_t func, uint64_t iova) "dev %02x:%02x.%02x iova 0x%"PRIx64
|
||||
vtd_err_qi_enable(uint16_t tail) "tail 0x%"PRIx16
|
||||
vtd_warn_invalid_qi_tail(uint16_t tail) "tail 0x%"PRIx16
|
||||
vtd_err_qi_disable(uint16_t head, uint16_t tail, int type) "head 0x%"PRIx16" tail 0x%"PRIx16" last_desc_type %d"
|
||||
vtd_err_qi_tail(uint16_t tail, uint16_t size) "tail 0x%"PRIx16" size 0x%"PRIx16
|
||||
vtd_err_irte(int index, uint64_t lo, uint64_t hi) "index %d low 0x%"PRIx64" high 0x%"PRIx64
|
||||
|
||||
+1
-1
@@ -130,7 +130,7 @@ static void pci_ich9_ahci_realize(PCIDevice *dev, Error **errp)
|
||||
pci_register_bar(dev, ICH9_MEM_BAR, PCI_BASE_ADDRESS_SPACE_MEMORY,
|
||||
&d->ahci.mem);
|
||||
|
||||
sata_cap_offset = pci_add_capability2(dev, PCI_CAP_ID_SATA,
|
||||
sata_cap_offset = pci_add_capability(dev, PCI_CAP_ID_SATA,
|
||||
ICH9_SATA_CAP_OFFSET, SATA_CAP_SIZE,
|
||||
errp);
|
||||
if (sata_cap_offset < 0) {
|
||||
|
||||
+19
-13
@@ -47,6 +47,7 @@
|
||||
#include "e1000e_core.h"
|
||||
|
||||
#include "trace.h"
|
||||
#include "qapi/error.h"
|
||||
|
||||
#define TYPE_E1000E "e1000e"
|
||||
#define E1000E(obj) OBJECT_CHECK(E1000EState, (obj), TYPE_E1000E)
|
||||
@@ -372,22 +373,27 @@ e1000e_gen_dsn(uint8_t *mac)
|
||||
static int
|
||||
e1000e_add_pm_capability(PCIDevice *pdev, uint8_t offset, uint16_t pmc)
|
||||
{
|
||||
int ret = pci_add_capability(pdev, PCI_CAP_ID_PM, offset, PCI_PM_SIZEOF);
|
||||
Error *local_err = NULL;
|
||||
int ret = pci_add_capability(pdev, PCI_CAP_ID_PM, offset,
|
||||
PCI_PM_SIZEOF, &local_err);
|
||||
|
||||
if (ret >= 0) {
|
||||
pci_set_word(pdev->config + offset + PCI_PM_PMC,
|
||||
PCI_PM_CAP_VER_1_1 |
|
||||
pmc);
|
||||
|
||||
pci_set_word(pdev->wmask + offset + PCI_PM_CTRL,
|
||||
PCI_PM_CTRL_STATE_MASK |
|
||||
PCI_PM_CTRL_PME_ENABLE |
|
||||
PCI_PM_CTRL_DATA_SEL_MASK);
|
||||
|
||||
pci_set_word(pdev->w1cmask + offset + PCI_PM_CTRL,
|
||||
PCI_PM_CTRL_PME_STATUS);
|
||||
if (local_err) {
|
||||
error_report_err(local_err);
|
||||
return ret;
|
||||
}
|
||||
|
||||
pci_set_word(pdev->config + offset + PCI_PM_PMC,
|
||||
PCI_PM_CAP_VER_1_1 |
|
||||
pmc);
|
||||
|
||||
pci_set_word(pdev->wmask + offset + PCI_PM_CTRL,
|
||||
PCI_PM_CTRL_STATE_MASK |
|
||||
PCI_PM_CTRL_PME_ENABLE |
|
||||
PCI_PM_CTRL_DATA_SEL_MASK);
|
||||
|
||||
pci_set_word(pdev->w1cmask + offset + PCI_PM_CTRL,
|
||||
PCI_PM_CTRL_PME_STATUS);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
+14
-4
@@ -48,6 +48,7 @@
|
||||
#include "sysemu/sysemu.h"
|
||||
#include "sysemu/dma.h"
|
||||
#include "qemu/bitops.h"
|
||||
#include "qapi/error.h"
|
||||
|
||||
/* QEMU sends frames smaller than 60 bytes to ethernet nics.
|
||||
* Such frames are rejected by real nics and their emulations.
|
||||
@@ -494,7 +495,7 @@ static void eepro100_fcp_interrupt(EEPRO100State * s)
|
||||
}
|
||||
#endif
|
||||
|
||||
static void e100_pci_reset(EEPRO100State * s)
|
||||
static void e100_pci_reset(EEPRO100State *s, Error **errp)
|
||||
{
|
||||
E100PCIDeviceInfo *info = eepro100_get_class(s);
|
||||
uint32_t device = s->device;
|
||||
@@ -570,8 +571,12 @@ static void e100_pci_reset(EEPRO100State * s)
|
||||
/* Power Management Capabilities */
|
||||
int cfg_offset = 0xdc;
|
||||
int r = pci_add_capability(&s->dev, PCI_CAP_ID_PM,
|
||||
cfg_offset, PCI_PM_SIZEOF);
|
||||
assert(r >= 0);
|
||||
cfg_offset, PCI_PM_SIZEOF,
|
||||
errp);
|
||||
if (r < 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
pci_set_word(pci_conf + cfg_offset + PCI_PM_PMC, 0x7e21);
|
||||
#if 0 /* TODO: replace dummy code for power management emulation. */
|
||||
/* TODO: Power Management Control / Status. */
|
||||
@@ -1858,12 +1863,17 @@ static void e100_nic_realize(PCIDevice *pci_dev, Error **errp)
|
||||
{
|
||||
EEPRO100State *s = DO_UPCAST(EEPRO100State, dev, pci_dev);
|
||||
E100PCIDeviceInfo *info = eepro100_get_class(s);
|
||||
Error *local_err = NULL;
|
||||
|
||||
TRACE(OTHER, logout("\n"));
|
||||
|
||||
s->device = info->device;
|
||||
|
||||
e100_pci_reset(s);
|
||||
e100_pci_reset(s, &local_err);
|
||||
if (local_err) {
|
||||
error_propagate(errp, local_err);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Add 64 * 2 EEPROM. i82557 and i82558 support a 64 word EEPROM,
|
||||
* i82559 and later support 64 or 256 word EEPROM. */
|
||||
|
||||
+42
-2
@@ -34,8 +34,11 @@
|
||||
|
||||
/* previously fixed value */
|
||||
#define VIRTIO_NET_RX_QUEUE_DEFAULT_SIZE 256
|
||||
#define VIRTIO_NET_TX_QUEUE_DEFAULT_SIZE 256
|
||||
|
||||
/* for now, only allow larger queues; with virtio-1, guest can downsize */
|
||||
#define VIRTIO_NET_RX_QUEUE_MIN_SIZE VIRTIO_NET_RX_QUEUE_DEFAULT_SIZE
|
||||
#define VIRTIO_NET_TX_QUEUE_MIN_SIZE VIRTIO_NET_TX_QUEUE_DEFAULT_SIZE
|
||||
|
||||
/*
|
||||
* Calculate the number of bytes up to and including the given 'field' of
|
||||
@@ -495,6 +498,24 @@ static void virtio_net_set_mrg_rx_bufs(VirtIONet *n, int mergeable_rx_bufs,
|
||||
}
|
||||
}
|
||||
|
||||
static int virtio_net_max_tx_queue_size(VirtIONet *n)
|
||||
{
|
||||
NetClientState *peer = n->nic_conf.peers.ncs[0];
|
||||
|
||||
/*
|
||||
* Backends other than vhost-user don't support max queue size.
|
||||
*/
|
||||
if (!peer) {
|
||||
return VIRTIO_NET_TX_QUEUE_DEFAULT_SIZE;
|
||||
}
|
||||
|
||||
if (peer->info->type != NET_CLIENT_DRIVER_VHOST_USER) {
|
||||
return VIRTIO_NET_TX_QUEUE_DEFAULT_SIZE;
|
||||
}
|
||||
|
||||
return VIRTQUEUE_MAX_SIZE;
|
||||
}
|
||||
|
||||
static int peer_attach(VirtIONet *n, int index)
|
||||
{
|
||||
NetClientState *nc = qemu_get_subqueue(n->nic, index);
|
||||
@@ -1508,15 +1529,18 @@ static void virtio_net_add_queue(VirtIONet *n, int index)
|
||||
|
||||
n->vqs[index].rx_vq = virtio_add_queue(vdev, n->net_conf.rx_queue_size,
|
||||
virtio_net_handle_rx);
|
||||
|
||||
if (n->net_conf.tx && !strcmp(n->net_conf.tx, "timer")) {
|
||||
n->vqs[index].tx_vq =
|
||||
virtio_add_queue(vdev, 256, virtio_net_handle_tx_timer);
|
||||
virtio_add_queue(vdev, n->net_conf.tx_queue_size,
|
||||
virtio_net_handle_tx_timer);
|
||||
n->vqs[index].tx_timer = timer_new_ns(QEMU_CLOCK_VIRTUAL,
|
||||
virtio_net_tx_timer,
|
||||
&n->vqs[index]);
|
||||
} else {
|
||||
n->vqs[index].tx_vq =
|
||||
virtio_add_queue(vdev, 256, virtio_net_handle_tx_bh);
|
||||
virtio_add_queue(vdev, n->net_conf.tx_queue_size,
|
||||
virtio_net_handle_tx_bh);
|
||||
n->vqs[index].tx_bh = qemu_bh_new(virtio_net_tx_bh, &n->vqs[index]);
|
||||
}
|
||||
|
||||
@@ -1927,6 +1951,17 @@ static void virtio_net_device_realize(DeviceState *dev, Error **errp)
|
||||
return;
|
||||
}
|
||||
|
||||
if (n->net_conf.tx_queue_size < VIRTIO_NET_TX_QUEUE_MIN_SIZE ||
|
||||
n->net_conf.tx_queue_size > VIRTQUEUE_MAX_SIZE ||
|
||||
!is_power_of_2(n->net_conf.tx_queue_size)) {
|
||||
error_setg(errp, "Invalid tx_queue_size (= %" PRIu16 "), "
|
||||
"must be a power of 2 between %d and %d",
|
||||
n->net_conf.tx_queue_size, VIRTIO_NET_TX_QUEUE_MIN_SIZE,
|
||||
VIRTQUEUE_MAX_SIZE);
|
||||
virtio_cleanup(vdev);
|
||||
return;
|
||||
}
|
||||
|
||||
n->max_queues = MAX(n->nic_conf.peers.queues, 1);
|
||||
if (n->max_queues * 2 + 1 > VIRTIO_QUEUE_MAX) {
|
||||
error_setg(errp, "Invalid number of queues (= %" PRIu32 "), "
|
||||
@@ -1947,6 +1982,9 @@ static void virtio_net_device_realize(DeviceState *dev, Error **errp)
|
||||
error_report("Defaulting to \"bh\"");
|
||||
}
|
||||
|
||||
n->net_conf.tx_queue_size = MIN(virtio_net_max_tx_queue_size(n),
|
||||
n->net_conf.tx_queue_size);
|
||||
|
||||
for (i = 0; i < n->max_queues; i++) {
|
||||
virtio_net_add_queue(n, i);
|
||||
}
|
||||
@@ -2106,6 +2144,8 @@ static Property virtio_net_properties[] = {
|
||||
DEFINE_PROP_STRING("tx", VirtIONet, net_conf.tx),
|
||||
DEFINE_PROP_UINT16("rx_queue_size", VirtIONet, net_conf.rx_queue_size,
|
||||
VIRTIO_NET_RX_QUEUE_DEFAULT_SIZE),
|
||||
DEFINE_PROP_UINT16("tx_queue_size", VirtIONet, net_conf.tx_queue_size,
|
||||
VIRTIO_NET_TX_QUEUE_DEFAULT_SIZE),
|
||||
DEFINE_PROP_UINT16("host_mtu", VirtIONet, net_conf.mtu, 0),
|
||||
DEFINE_PROP_BOOL("x-mtu-bypass-backend", VirtIONet, mtu_bypass_backend,
|
||||
true),
|
||||
|
||||
+15
-17
@@ -96,7 +96,6 @@ struct FWCfgIoState {
|
||||
/*< public >*/
|
||||
|
||||
MemoryRegion comb_iomem;
|
||||
uint32_t iobase, dma_iobase;
|
||||
};
|
||||
|
||||
struct FWCfgMemState {
|
||||
@@ -914,6 +913,7 @@ static void fw_cfg_init1(DeviceState *dev)
|
||||
{
|
||||
FWCfgState *s = FW_CFG(dev);
|
||||
MachineState *machine = MACHINE(qdev_get_machine());
|
||||
uint32_t version = FW_CFG_VERSION;
|
||||
|
||||
assert(!object_resolve_path(FW_CFG_PATH, NULL));
|
||||
|
||||
@@ -928,6 +928,12 @@ static void fw_cfg_init1(DeviceState *dev)
|
||||
fw_cfg_bootsplash(s);
|
||||
fw_cfg_reboot(s);
|
||||
|
||||
if (s->dma_enabled) {
|
||||
version |= FW_CFG_VERSION_DMA;
|
||||
}
|
||||
|
||||
fw_cfg_add_i32(s, FW_CFG_ID, version);
|
||||
|
||||
s->machine_ready.notify = fw_cfg_machine_ready;
|
||||
qemu_add_machine_init_done_notifier(&s->machine_ready);
|
||||
}
|
||||
@@ -936,30 +942,31 @@ FWCfgState *fw_cfg_init_io_dma(uint32_t iobase, uint32_t dma_iobase,
|
||||
AddressSpace *dma_as)
|
||||
{
|
||||
DeviceState *dev;
|
||||
SysBusDevice *sbd;
|
||||
FWCfgIoState *ios;
|
||||
FWCfgState *s;
|
||||
uint32_t version = FW_CFG_VERSION;
|
||||
bool dma_requested = dma_iobase && dma_as;
|
||||
|
||||
dev = qdev_create(NULL, TYPE_FW_CFG_IO);
|
||||
qdev_prop_set_uint32(dev, "iobase", iobase);
|
||||
qdev_prop_set_uint32(dev, "dma_iobase", dma_iobase);
|
||||
if (!dma_requested) {
|
||||
qdev_prop_set_bit(dev, "dma_enabled", false);
|
||||
}
|
||||
|
||||
fw_cfg_init1(dev);
|
||||
|
||||
sbd = SYS_BUS_DEVICE(dev);
|
||||
ios = FW_CFG_IO(dev);
|
||||
sysbus_add_io(sbd, iobase, &ios->comb_iomem);
|
||||
|
||||
s = FW_CFG(dev);
|
||||
|
||||
if (s->dma_enabled) {
|
||||
/* 64 bits for the address field */
|
||||
s->dma_as = dma_as;
|
||||
s->dma_addr = 0;
|
||||
|
||||
version |= FW_CFG_VERSION_DMA;
|
||||
sysbus_add_io(sbd, dma_iobase, &s->dma_iomem);
|
||||
}
|
||||
|
||||
fw_cfg_add_i32(s, FW_CFG_ID, version);
|
||||
|
||||
return s;
|
||||
}
|
||||
|
||||
@@ -975,7 +982,6 @@ FWCfgState *fw_cfg_init_mem_wide(hwaddr ctl_addr,
|
||||
DeviceState *dev;
|
||||
SysBusDevice *sbd;
|
||||
FWCfgState *s;
|
||||
uint32_t version = FW_CFG_VERSION;
|
||||
bool dma_requested = dma_addr && dma_as;
|
||||
|
||||
dev = qdev_create(NULL, TYPE_FW_CFG_MEM);
|
||||
@@ -996,11 +1002,8 @@ FWCfgState *fw_cfg_init_mem_wide(hwaddr ctl_addr,
|
||||
s->dma_as = dma_as;
|
||||
s->dma_addr = 0;
|
||||
sysbus_mmio_map(sbd, 2, dma_addr);
|
||||
version |= FW_CFG_VERSION_DMA;
|
||||
}
|
||||
|
||||
fw_cfg_add_i32(s, FW_CFG_ID, version);
|
||||
|
||||
return s;
|
||||
}
|
||||
|
||||
@@ -1059,8 +1062,6 @@ static void fw_cfg_file_slots_allocate(FWCfgState *s, Error **errp)
|
||||
}
|
||||
|
||||
static Property fw_cfg_io_properties[] = {
|
||||
DEFINE_PROP_UINT32("iobase", FWCfgIoState, iobase, -1),
|
||||
DEFINE_PROP_UINT32("dma_iobase", FWCfgIoState, dma_iobase, -1),
|
||||
DEFINE_PROP_BOOL("dma_enabled", FWCfgIoState, parent_obj.dma_enabled,
|
||||
true),
|
||||
DEFINE_PROP_UINT16("x-file-slots", FWCfgIoState, parent_obj.file_slots,
|
||||
@@ -1071,7 +1072,6 @@ static Property fw_cfg_io_properties[] = {
|
||||
static void fw_cfg_io_realize(DeviceState *dev, Error **errp)
|
||||
{
|
||||
FWCfgIoState *s = FW_CFG_IO(dev);
|
||||
SysBusDevice *sbd = SYS_BUS_DEVICE(dev);
|
||||
Error *local_err = NULL;
|
||||
|
||||
fw_cfg_file_slots_allocate(FW_CFG(s), &local_err);
|
||||
@@ -1085,13 +1085,11 @@ static void fw_cfg_io_realize(DeviceState *dev, Error **errp)
|
||||
* of the i/o region used is FW_CFG_CTL_SIZE */
|
||||
memory_region_init_io(&s->comb_iomem, OBJECT(s), &fw_cfg_comb_mem_ops,
|
||||
FW_CFG(s), "fwcfg", FW_CFG_CTL_SIZE);
|
||||
sysbus_add_io(sbd, s->iobase, &s->comb_iomem);
|
||||
|
||||
if (FW_CFG(s)->dma_enabled) {
|
||||
memory_region_init_io(&FW_CFG(s)->dma_iomem, OBJECT(s),
|
||||
&fw_cfg_dma_mem_ops, FW_CFG(s), "fwcfg.dma",
|
||||
sizeof(dma_addr_t));
|
||||
sysbus_add_io(sbd, s->dma_iobase, &FW_CFG(s)->dma_iomem);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -62,6 +62,7 @@ static void dec_21154_pci_bridge_class_init(ObjectClass *klass, void *data)
|
||||
DeviceClass *dc = DEVICE_CLASS(klass);
|
||||
PCIDeviceClass *k = PCI_DEVICE_CLASS(klass);
|
||||
|
||||
set_bit(DEVICE_CATEGORY_BRIDGE, dc->categories);
|
||||
k->realize = dec_pci_bridge_realize;
|
||||
k->exit = pci_bridge_exitfn;
|
||||
k->vendor_id = PCI_VENDOR_ID_DEC;
|
||||
@@ -118,6 +119,7 @@ static void dec_21154_pci_host_class_init(ObjectClass *klass, void *data)
|
||||
PCIDeviceClass *k = PCI_DEVICE_CLASS(klass);
|
||||
DeviceClass *dc = DEVICE_CLASS(klass);
|
||||
|
||||
set_bit(DEVICE_CATEGORY_BRIDGE, dc->categories);
|
||||
k->realize = dec_21154_pci_host_realize;
|
||||
k->vendor_id = PCI_VENDOR_ID_DEC;
|
||||
k->device_id = PCI_DEVICE_ID_DEC_21154;
|
||||
|
||||
@@ -44,6 +44,7 @@
|
||||
#include "qemu/osdep.h"
|
||||
#include "hw/pci/pci.h"
|
||||
#include "hw/i386/ich9.h"
|
||||
#include "qapi/error.h"
|
||||
|
||||
|
||||
/*****************************************************************************/
|
||||
@@ -58,24 +59,23 @@ typedef struct I82801b11Bridge {
|
||||
/*< public >*/
|
||||
} I82801b11Bridge;
|
||||
|
||||
static int i82801b11_bridge_initfn(PCIDevice *d)
|
||||
static void i82801b11_bridge_realize(PCIDevice *d, Error **errp)
|
||||
{
|
||||
int rc;
|
||||
|
||||
pci_bridge_initfn(d, TYPE_PCI_BUS);
|
||||
|
||||
rc = pci_bridge_ssvid_init(d, I82801ba_SSVID_OFFSET,
|
||||
I82801ba_SSVID_SVID, I82801ba_SSVID_SSID);
|
||||
I82801ba_SSVID_SVID, I82801ba_SSVID_SSID,
|
||||
errp);
|
||||
if (rc < 0) {
|
||||
goto err_bridge;
|
||||
}
|
||||
pci_config_set_prog_interface(d->config, PCI_CLASS_BRIDGE_PCI_INF_SUB);
|
||||
return 0;
|
||||
return;
|
||||
|
||||
err_bridge:
|
||||
pci_bridge_exitfn(d);
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
static const VMStateDescription i82801b11_bridge_dev_vmstate = {
|
||||
@@ -95,7 +95,7 @@ static void i82801b11_bridge_class_init(ObjectClass *klass, void *data)
|
||||
k->vendor_id = PCI_VENDOR_ID_INTEL;
|
||||
k->device_id = PCI_DEVICE_ID_INTEL_82801BA_11;
|
||||
k->revision = ICH9_D2P_A2_REVISION;
|
||||
k->init = i82801b11_bridge_initfn;
|
||||
k->realize = i82801b11_bridge_realize;
|
||||
k->config_write = pci_bridge_write_config;
|
||||
dc->vmsd = &i82801b11_bridge_dev_vmstate;
|
||||
set_bit(DEVICE_CATEGORY_BRIDGE, dc->categories);
|
||||
|
||||
@@ -49,7 +49,7 @@ struct PCIBridgeDev {
|
||||
};
|
||||
typedef struct PCIBridgeDev PCIBridgeDev;
|
||||
|
||||
static int pci_bridge_dev_initfn(PCIDevice *dev)
|
||||
static void pci_bridge_dev_realize(PCIDevice *dev, Error **errp)
|
||||
{
|
||||
PCIBridge *br = PCI_BRIDGE(dev);
|
||||
PCIBridgeDev *bridge_dev = PCI_BRIDGE_DEV(dev);
|
||||
@@ -62,7 +62,7 @@ static int pci_bridge_dev_initfn(PCIDevice *dev)
|
||||
dev->config[PCI_INTERRUPT_PIN] = 0x1;
|
||||
memory_region_init(&bridge_dev->bar, OBJECT(dev), "shpc-bar",
|
||||
shpc_bar_size(dev));
|
||||
err = shpc_init(dev, &br->sec_bus, &bridge_dev->bar, 0);
|
||||
err = shpc_init(dev, &br->sec_bus, &bridge_dev->bar, 0, errp);
|
||||
if (err) {
|
||||
goto shpc_error;
|
||||
}
|
||||
@@ -71,7 +71,7 @@ static int pci_bridge_dev_initfn(PCIDevice *dev)
|
||||
bridge_dev->msi = ON_OFF_AUTO_OFF;
|
||||
}
|
||||
|
||||
err = slotid_cap_init(dev, 0, bridge_dev->chassis_nr, 0);
|
||||
err = slotid_cap_init(dev, 0, bridge_dev->chassis_nr, 0, errp);
|
||||
if (err) {
|
||||
goto slotid_error;
|
||||
}
|
||||
@@ -87,7 +87,7 @@ static int pci_bridge_dev_initfn(PCIDevice *dev)
|
||||
/* Can't satisfy user's explicit msi=on request, fail */
|
||||
error_append_hint(&local_err, "You have to use msi=auto (default) "
|
||||
"or msi=off with this machine type.\n");
|
||||
error_report_err(local_err);
|
||||
error_propagate(errp, local_err);
|
||||
goto msi_error;
|
||||
}
|
||||
assert(!local_err || bridge_dev->msi == ON_OFF_AUTO_AUTO);
|
||||
@@ -101,7 +101,7 @@ static int pci_bridge_dev_initfn(PCIDevice *dev)
|
||||
pci_register_bar(dev, 0, PCI_BASE_ADDRESS_SPACE_MEMORY |
|
||||
PCI_BASE_ADDRESS_MEM_TYPE_64, &bridge_dev->bar);
|
||||
}
|
||||
return 0;
|
||||
return;
|
||||
|
||||
msi_error:
|
||||
slotid_cap_cleanup(dev);
|
||||
@@ -111,8 +111,6 @@ slotid_error:
|
||||
}
|
||||
shpc_error:
|
||||
pci_bridge_exitfn(dev);
|
||||
|
||||
return err;
|
||||
}
|
||||
|
||||
static void pci_bridge_dev_exitfn(PCIDevice *dev)
|
||||
@@ -216,7 +214,7 @@ static void pci_bridge_dev_class_init(ObjectClass *klass, void *data)
|
||||
PCIDeviceClass *k = PCI_DEVICE_CLASS(klass);
|
||||
HotplugHandlerClass *hc = HOTPLUG_HANDLER_CLASS(klass);
|
||||
|
||||
k->init = pci_bridge_dev_initfn;
|
||||
k->realize = pci_bridge_dev_realize;
|
||||
k->exit = pci_bridge_dev_exitfn;
|
||||
k->config_write = pci_bridge_dev_write_config;
|
||||
k->vendor_id = PCI_VENDOR_ID_REDHAT;
|
||||
|
||||
@@ -59,29 +59,30 @@ static void rp_realize(PCIDevice *d, Error **errp)
|
||||
PCIDeviceClass *dc = PCI_DEVICE_GET_CLASS(d);
|
||||
PCIERootPortClass *rpc = PCIE_ROOT_PORT_GET_CLASS(d);
|
||||
int rc;
|
||||
Error *local_err = NULL;
|
||||
|
||||
pci_config_set_interrupt_pin(d->config, 1);
|
||||
pci_bridge_initfn(d, TYPE_PCIE_BUS);
|
||||
pcie_port_init_reg(d);
|
||||
|
||||
rc = pci_bridge_ssvid_init(d, rpc->ssvid_offset, dc->vendor_id, rpc->ssid);
|
||||
rc = pci_bridge_ssvid_init(d, rpc->ssvid_offset, dc->vendor_id,
|
||||
rpc->ssid, errp);
|
||||
if (rc < 0) {
|
||||
error_setg(errp, "Can't init SSV ID, error %d", rc);
|
||||
error_append_hint(errp, "Can't init SSV ID, error %d\n", rc);
|
||||
goto err_bridge;
|
||||
}
|
||||
|
||||
if (rpc->interrupts_init) {
|
||||
rc = rpc->interrupts_init(d, &local_err);
|
||||
rc = rpc->interrupts_init(d, errp);
|
||||
if (rc < 0) {
|
||||
error_propagate(errp, local_err);
|
||||
goto err_bridge;
|
||||
}
|
||||
}
|
||||
|
||||
rc = pcie_cap_init(d, rpc->exp_offset, PCI_EXP_TYPE_ROOT_PORT, p->port);
|
||||
rc = pcie_cap_init(d, rpc->exp_offset, PCI_EXP_TYPE_ROOT_PORT,
|
||||
p->port, errp);
|
||||
if (rc < 0) {
|
||||
error_setg(errp, "Can't add Root Port capability, error %d", rc);
|
||||
error_append_hint(errp, "Can't add Root Port capability, "
|
||||
"error %d\n", rc);
|
||||
goto err_int;
|
||||
}
|
||||
|
||||
@@ -98,9 +99,8 @@ static void rp_realize(PCIDevice *d, Error **errp)
|
||||
}
|
||||
|
||||
rc = pcie_aer_init(d, PCI_ERR_VER, rpc->aer_offset,
|
||||
PCI_ERR_SIZEOF, &local_err);
|
||||
PCI_ERR_SIZEOF, errp);
|
||||
if (rc < 0) {
|
||||
error_propagate(errp, local_err);
|
||||
goto err;
|
||||
}
|
||||
pcie_aer_root_init(d);
|
||||
|
||||
@@ -56,33 +56,33 @@ static void xio3130_downstream_reset(DeviceState *qdev)
|
||||
pci_bridge_reset(qdev);
|
||||
}
|
||||
|
||||
static int xio3130_downstream_initfn(PCIDevice *d)
|
||||
static void xio3130_downstream_realize(PCIDevice *d, Error **errp)
|
||||
{
|
||||
PCIEPort *p = PCIE_PORT(d);
|
||||
PCIESlot *s = PCIE_SLOT(d);
|
||||
int rc;
|
||||
Error *err = NULL;
|
||||
|
||||
pci_bridge_initfn(d, TYPE_PCIE_BUS);
|
||||
pcie_port_init_reg(d);
|
||||
|
||||
rc = msi_init(d, XIO3130_MSI_OFFSET, XIO3130_MSI_NR_VECTOR,
|
||||
XIO3130_MSI_SUPPORTED_FLAGS & PCI_MSI_FLAGS_64BIT,
|
||||
XIO3130_MSI_SUPPORTED_FLAGS & PCI_MSI_FLAGS_MASKBIT, &err);
|
||||
XIO3130_MSI_SUPPORTED_FLAGS & PCI_MSI_FLAGS_MASKBIT,
|
||||
errp);
|
||||
if (rc < 0) {
|
||||
assert(rc == -ENOTSUP);
|
||||
error_report_err(err);
|
||||
goto err_bridge;
|
||||
}
|
||||
|
||||
rc = pci_bridge_ssvid_init(d, XIO3130_SSVID_OFFSET,
|
||||
XIO3130_SSVID_SVID, XIO3130_SSVID_SSID);
|
||||
XIO3130_SSVID_SVID, XIO3130_SSVID_SSID,
|
||||
errp);
|
||||
if (rc < 0) {
|
||||
goto err_bridge;
|
||||
}
|
||||
|
||||
rc = pcie_cap_init(d, XIO3130_EXP_OFFSET, PCI_EXP_TYPE_DOWNSTREAM,
|
||||
p->port);
|
||||
p->port, errp);
|
||||
if (rc < 0) {
|
||||
goto err_msi;
|
||||
}
|
||||
@@ -98,13 +98,12 @@ static int xio3130_downstream_initfn(PCIDevice *d)
|
||||
}
|
||||
|
||||
rc = pcie_aer_init(d, PCI_ERR_VER, XIO3130_AER_OFFSET,
|
||||
PCI_ERR_SIZEOF, &err);
|
||||
PCI_ERR_SIZEOF, errp);
|
||||
if (rc < 0) {
|
||||
error_report_err(err);
|
||||
goto err;
|
||||
}
|
||||
|
||||
return 0;
|
||||
return;
|
||||
|
||||
err:
|
||||
pcie_chassis_del_slot(s);
|
||||
@@ -114,7 +113,6 @@ err_msi:
|
||||
msi_uninit(d);
|
||||
err_bridge:
|
||||
pci_bridge_exitfn(d);
|
||||
return rc;
|
||||
}
|
||||
|
||||
static void xio3130_downstream_exitfn(PCIDevice *d)
|
||||
@@ -181,7 +179,7 @@ static void xio3130_downstream_class_init(ObjectClass *klass, void *data)
|
||||
k->is_express = 1;
|
||||
k->is_bridge = 1;
|
||||
k->config_write = xio3130_downstream_write_config;
|
||||
k->init = xio3130_downstream_initfn;
|
||||
k->realize = xio3130_downstream_realize;
|
||||
k->exit = xio3130_downstream_exitfn;
|
||||
k->vendor_id = PCI_VENDOR_ID_TI;
|
||||
k->device_id = PCI_DEVICE_ID_TI_XIO3130D;
|
||||
|
||||
@@ -53,32 +53,32 @@ static void xio3130_upstream_reset(DeviceState *qdev)
|
||||
pcie_cap_deverr_reset(d);
|
||||
}
|
||||
|
||||
static int xio3130_upstream_initfn(PCIDevice *d)
|
||||
static void xio3130_upstream_realize(PCIDevice *d, Error **errp)
|
||||
{
|
||||
PCIEPort *p = PCIE_PORT(d);
|
||||
int rc;
|
||||
Error *err = NULL;
|
||||
|
||||
pci_bridge_initfn(d, TYPE_PCIE_BUS);
|
||||
pcie_port_init_reg(d);
|
||||
|
||||
rc = msi_init(d, XIO3130_MSI_OFFSET, XIO3130_MSI_NR_VECTOR,
|
||||
XIO3130_MSI_SUPPORTED_FLAGS & PCI_MSI_FLAGS_64BIT,
|
||||
XIO3130_MSI_SUPPORTED_FLAGS & PCI_MSI_FLAGS_MASKBIT, &err);
|
||||
XIO3130_MSI_SUPPORTED_FLAGS & PCI_MSI_FLAGS_MASKBIT,
|
||||
errp);
|
||||
if (rc < 0) {
|
||||
assert(rc == -ENOTSUP);
|
||||
error_report_err(err);
|
||||
goto err_bridge;
|
||||
}
|
||||
|
||||
rc = pci_bridge_ssvid_init(d, XIO3130_SSVID_OFFSET,
|
||||
XIO3130_SSVID_SVID, XIO3130_SSVID_SSID);
|
||||
XIO3130_SSVID_SVID, XIO3130_SSVID_SSID,
|
||||
errp);
|
||||
if (rc < 0) {
|
||||
goto err_bridge;
|
||||
}
|
||||
|
||||
rc = pcie_cap_init(d, XIO3130_EXP_OFFSET, PCI_EXP_TYPE_UPSTREAM,
|
||||
p->port);
|
||||
p->port, errp);
|
||||
if (rc < 0) {
|
||||
goto err_msi;
|
||||
}
|
||||
@@ -86,13 +86,12 @@ static int xio3130_upstream_initfn(PCIDevice *d)
|
||||
pcie_cap_deverr_init(d);
|
||||
|
||||
rc = pcie_aer_init(d, PCI_ERR_VER, XIO3130_AER_OFFSET,
|
||||
PCI_ERR_SIZEOF, &err);
|
||||
PCI_ERR_SIZEOF, errp);
|
||||
if (rc < 0) {
|
||||
error_report_err(err);
|
||||
goto err;
|
||||
}
|
||||
|
||||
return 0;
|
||||
return;
|
||||
|
||||
err:
|
||||
pcie_cap_exit(d);
|
||||
@@ -100,7 +99,6 @@ err_msi:
|
||||
msi_uninit(d);
|
||||
err_bridge:
|
||||
pci_bridge_exitfn(d);
|
||||
return rc;
|
||||
}
|
||||
|
||||
static void xio3130_upstream_exitfn(PCIDevice *d)
|
||||
@@ -153,7 +151,7 @@ static void xio3130_upstream_class_init(ObjectClass *klass, void *data)
|
||||
k->is_express = 1;
|
||||
k->is_bridge = 1;
|
||||
k->config_write = xio3130_upstream_write_config;
|
||||
k->init = xio3130_upstream_initfn;
|
||||
k->realize = xio3130_upstream_realize;
|
||||
k->exit = xio3130_upstream_exitfn;
|
||||
k->vendor_id = PCI_VENDOR_ID_TI;
|
||||
k->device_id = PCI_DEVICE_ID_TI_XIO3130U;
|
||||
|
||||
+1
-1
@@ -216,7 +216,7 @@ int msi_init(struct PCIDevice *dev, uint8_t offset,
|
||||
}
|
||||
|
||||
cap_size = msi_cap_sizeof(flags);
|
||||
config_offset = pci_add_capability2(dev, PCI_CAP_ID_MSI, offset,
|
||||
config_offset = pci_add_capability(dev, PCI_CAP_ID_MSI, offset,
|
||||
cap_size, errp);
|
||||
if (config_offset < 0) {
|
||||
return config_offset;
|
||||
|
||||
+1
-1
@@ -301,7 +301,7 @@ int msix_init(struct PCIDevice *dev, unsigned short nentries,
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
cap = pci_add_capability2(dev, PCI_CAP_ID_MSIX,
|
||||
cap = pci_add_capability(dev, PCI_CAP_ID_MSIX,
|
||||
cap_pos, MSIX_CAP_LENGTH, errp);
|
||||
if (cap < 0) {
|
||||
return cap;
|
||||
|
||||
+4
-20
@@ -2259,28 +2259,12 @@ static void pci_del_option_rom(PCIDevice *pdev)
|
||||
}
|
||||
|
||||
/*
|
||||
* if offset = 0,
|
||||
* Find and reserve space and add capability to the linked list
|
||||
* in pci config space
|
||||
* On success, pci_add_capability() returns a positive value
|
||||
* that the offset of the pci capability.
|
||||
* On failure, it sets an error and returns a negative error
|
||||
* code.
|
||||
*/
|
||||
int pci_add_capability(PCIDevice *pdev, uint8_t cap_id,
|
||||
uint8_t offset, uint8_t size)
|
||||
{
|
||||
int ret;
|
||||
Error *local_err = NULL;
|
||||
|
||||
ret = pci_add_capability2(pdev, cap_id, offset, size, &local_err);
|
||||
if (local_err) {
|
||||
assert(ret < 0);
|
||||
error_report_err(local_err);
|
||||
} else {
|
||||
/* success implies a positive offset in config space */
|
||||
assert(ret > 0);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
int pci_add_capability2(PCIDevice *pdev, uint8_t cap_id,
|
||||
uint8_t offset, uint8_t size,
|
||||
Error **errp)
|
||||
{
|
||||
|
||||
+6
-2
@@ -33,6 +33,7 @@
|
||||
#include "hw/pci/pci_bridge.h"
|
||||
#include "hw/pci/pci_bus.h"
|
||||
#include "qemu/range.h"
|
||||
#include "qapi/error.h"
|
||||
|
||||
/* PCI bridge subsystem vendor ID helper functions */
|
||||
#define PCI_SSVID_SIZEOF 8
|
||||
@@ -40,10 +41,13 @@
|
||||
#define PCI_SSVID_SSID 6
|
||||
|
||||
int pci_bridge_ssvid_init(PCIDevice *dev, uint8_t offset,
|
||||
uint16_t svid, uint16_t ssid)
|
||||
uint16_t svid, uint16_t ssid,
|
||||
Error **errp)
|
||||
{
|
||||
int pos;
|
||||
pos = pci_add_capability(dev, PCI_CAP_ID_SSVID, offset, PCI_SSVID_SIZEOF);
|
||||
|
||||
pos = pci_add_capability(dev, PCI_CAP_ID_SSVID, offset,
|
||||
PCI_SSVID_SIZEOF, errp);
|
||||
if (pos < 0) {
|
||||
return pos;
|
||||
}
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user