Compare commits

...

19 Commits

Author SHA1 Message Date
Richard Henderson
59084feb25 aspeed queue:
* support AST2700 network
 -----BEGIN PGP SIGNATURE-----
 
 iQIzBAABCAAdFiEEoPZlSPBIlev+awtgUaNDx8/77KEFAmaNJCcACgkQUaNDx8/7
 7KF7pw//So48XdPJhdQukO/PDLGSYL8rRjDfZbQFLLw10MozcZZ/Nz/BCzrNxJRg
 rHP/shyO3XL1YZ6U1LNXk6E845giVriSpRRjGX9CuK4fypM9xom6qAIOtOLeH7hG
 iTMW++IxN/JgVmVOKYn3C+2+odiq6NzZxFrblVtGPUDtNkkC9BaYGHnccMsl5zQh
 LOSPJxqLiiuDjZPqdwa4fMbtEeNTU3A0WLlWxX7yPfJt2T20a4wE6bdWVGcI6fiV
 QbCmLLrMXhuZFx+uT4B2hbHi+hGS5H+F3QBOefum6z+i9NEbfAZSyusd8/qTEify
 fSBqxL4LD6K4WKL1Hg9959cBcm5zWgPXk7znus4E/TZuUTdSHaPC7clESIcYqWPS
 veEAppmHneO4cdmK1m+Gv4gpWD/adS4ZfV7O+C3z149ms0gL4JrK6QndPdE5QuIW
 u47PhIT3oIM0WznnMusoCndFxs6Gl/GBkzdxW0gdoJKBRfymbsroWeZamAWTznbV
 mL8Td8bEP/NcV40cm1PtpZyl7j0MzxcKDUHKv9ioQTXLUpkl5LSsIGmd1m78WRlE
 J6bUJ3jqQT6/s5i3TVqTGe7xuqMkg+9Er8rn5nAWgSronsf4nprAfOU8Lj+b06BM
 YRroGgU2lAQrv17liQExrG3Tj1SH+oEp1q0qEq7qo824HlGjBkI=
 =UygB
 -----END PGP SIGNATURE-----

Merge tag 'pull-aspeed-20240709' of https://github.com/legoater/qemu into staging

aspeed queue:

* support AST2700 network

# -----BEGIN PGP SIGNATURE-----
#
# iQIzBAABCAAdFiEEoPZlSPBIlev+awtgUaNDx8/77KEFAmaNJCcACgkQUaNDx8/7
# 7KF7pw//So48XdPJhdQukO/PDLGSYL8rRjDfZbQFLLw10MozcZZ/Nz/BCzrNxJRg
# rHP/shyO3XL1YZ6U1LNXk6E845giVriSpRRjGX9CuK4fypM9xom6qAIOtOLeH7hG
# iTMW++IxN/JgVmVOKYn3C+2+odiq6NzZxFrblVtGPUDtNkkC9BaYGHnccMsl5zQh
# LOSPJxqLiiuDjZPqdwa4fMbtEeNTU3A0WLlWxX7yPfJt2T20a4wE6bdWVGcI6fiV
# QbCmLLrMXhuZFx+uT4B2hbHi+hGS5H+F3QBOefum6z+i9NEbfAZSyusd8/qTEify
# fSBqxL4LD6K4WKL1Hg9959cBcm5zWgPXk7znus4E/TZuUTdSHaPC7clESIcYqWPS
# veEAppmHneO4cdmK1m+Gv4gpWD/adS4ZfV7O+C3z149ms0gL4JrK6QndPdE5QuIW
# u47PhIT3oIM0WznnMusoCndFxs6Gl/GBkzdxW0gdoJKBRfymbsroWeZamAWTznbV
# mL8Td8bEP/NcV40cm1PtpZyl7j0MzxcKDUHKv9ioQTXLUpkl5LSsIGmd1m78WRlE
# J6bUJ3jqQT6/s5i3TVqTGe7xuqMkg+9Er8rn5nAWgSronsf4nprAfOU8Lj+b06BM
# YRroGgU2lAQrv17liQExrG3Tj1SH+oEp1q0qEq7qo824HlGjBkI=
# =UygB
# -----END PGP SIGNATURE-----
# gpg: Signature made Tue 09 Jul 2024 04:51:03 AM PDT
# gpg:                using RSA key A0F66548F04895EBFE6B0B6051A343C7CFFBECA1
# gpg: Good signature from "Cédric Le Goater <clg@kaod.org>" [undefined]
# 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: A0F6 6548 F048 95EB FE6B  0B60 51A3 43C7 CFFB ECA1

* tag 'pull-aspeed-20240709' of https://github.com/legoater/qemu:
  machine_aspeed.py: update to test network for AST2700
  machine_aspeed.py: update to test ASPEED OpenBMC SDK v09.02 for AST2700
  hw/block: m25p80: support quad mode for w25q01jvq
  aspeed/soc: set dma64 property for AST2700 ftgmac100
  hw/net:ftgmac100: update TX and RX packet buffers address to 64 bits
  hw/net:ftgmac100: introduce TX and RX ring base address high registers to support 64 bits
  hw/net:ftgmac100: update ring base address to 64 bits
  hw/net:ftgmac100: update memory region size to 64KB

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
2024-07-09 07:13:55 -07:00
Richard Henderson
4a3eceb403 vfio queue:
* Fixes on VFIO display
 * VIRTIO-IOMMU/HostIOMMUDevice: Fixes and page size mask rework
 -----BEGIN PGP SIGNATURE-----
 
 iQIzBAABCAAdFiEEoPZlSPBIlev+awtgUaNDx8/77KEFAmaNI6MACgkQUaNDx8/7
 7KHMCQ//VrdayFV9psHCCkrku3MQL6VWsiTOf6bgOFz4zp716HQrnZlI6A7L1qFz
 p2OH6bQu9IDa8T65TVyQ/u6LL3VkZGAcji++YQQHYD1uNZryURq7IosxmoLnb5L/
 FcBp22rmYx7/0nBF8VW6SttVXAlVAmxe1dwEdmQNL+YJDmhayS7lTiUgx3mWjgUZ
 0lSvz5w+LWZIuHKLK/o0Fo8Lr4y63nCUxPukl46mjntciEd16zpaCv4ySCf/y83q
 MtRiBhD1+zuV9Kzla1CpwwRKPGccimksXGpmdAVGTUmzfK/ElA8sMB5KDFVDEhdD
 6iqWcdP7MdZIsCC9qXaOqLPyeqSYZ58LgqUOt4tTW9eiGf6eORqHNRqtStR98pDl
 W+SfCj6AY8wRktKSldb+BKE+XJ/7AD24Lxz2iD6RI7hWwWnalu9z6XpZD1QMqUvw
 h+XjIycp1bNgm7i5indA2B1zotT9ebI8AEEAUMbQOMrtMWqZzGORfI8rhS1s4A+B
 Kh37ll6jAVtYgaifercDQa/PFYyp4dIFZDbWt4WiFYxX51YkpnI3GJKDmIT2or7u
 X2o43rk9sp4xHlsge4pT7epoDzgmuv6fIygfxSPKOp9znrWlAVMX7DniN92SnRke
 xyvCxE2Jps9p0Y7cfaM4VZsWIgHk+IB3hr4wrlRwRKa3sPH4fwU=
 =glZK
 -----END PGP SIGNATURE-----

Merge tag 'pull-vfio-20240709' of https://github.com/legoater/qemu into staging

vfio queue:

* Fixes on VFIO display
* VIRTIO-IOMMU/HostIOMMUDevice: Fixes and page size mask rework

# -----BEGIN PGP SIGNATURE-----
#
# iQIzBAABCAAdFiEEoPZlSPBIlev+awtgUaNDx8/77KEFAmaNI6MACgkQUaNDx8/7
# 7KHMCQ//VrdayFV9psHCCkrku3MQL6VWsiTOf6bgOFz4zp716HQrnZlI6A7L1qFz
# p2OH6bQu9IDa8T65TVyQ/u6LL3VkZGAcji++YQQHYD1uNZryURq7IosxmoLnb5L/
# FcBp22rmYx7/0nBF8VW6SttVXAlVAmxe1dwEdmQNL+YJDmhayS7lTiUgx3mWjgUZ
# 0lSvz5w+LWZIuHKLK/o0Fo8Lr4y63nCUxPukl46mjntciEd16zpaCv4ySCf/y83q
# MtRiBhD1+zuV9Kzla1CpwwRKPGccimksXGpmdAVGTUmzfK/ElA8sMB5KDFVDEhdD
# 6iqWcdP7MdZIsCC9qXaOqLPyeqSYZ58LgqUOt4tTW9eiGf6eORqHNRqtStR98pDl
# W+SfCj6AY8wRktKSldb+BKE+XJ/7AD24Lxz2iD6RI7hWwWnalu9z6XpZD1QMqUvw
# h+XjIycp1bNgm7i5indA2B1zotT9ebI8AEEAUMbQOMrtMWqZzGORfI8rhS1s4A+B
# Kh37ll6jAVtYgaifercDQa/PFYyp4dIFZDbWt4WiFYxX51YkpnI3GJKDmIT2or7u
# X2o43rk9sp4xHlsge4pT7epoDzgmuv6fIygfxSPKOp9znrWlAVMX7DniN92SnRke
# xyvCxE2Jps9p0Y7cfaM4VZsWIgHk+IB3hr4wrlRwRKa3sPH4fwU=
# =glZK
# -----END PGP SIGNATURE-----
# gpg: Signature made Tue 09 Jul 2024 04:48:51 AM PDT
# gpg:                using RSA key A0F66548F04895EBFE6B0B6051A343C7CFFBECA1
# gpg: Good signature from "Cédric Le Goater <clg@kaod.org>" [undefined]
# 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: A0F6 6548 F048 95EB FE6B  0B60 51A3 43C7 CFFB ECA1

* tag 'pull-vfio-20240709' of https://github.com/legoater/qemu:
  vfio/display: Fix vfio_display_edid_init() error path
  vfio/display: Fix potential memleak of edid info
  virtio-iommu: Revert transient enablement of IOMMU MR in bypass mode
  memory: remove IOMMU MR iommu_set_page_size_mask() callback
  virtio-iommu : Retrieve page size mask on virtio_iommu_set_iommu_device()
  HostIOMMUDevice: Introduce get_page_size_mask() callback
  HostIOMMUDevice : remove Error handle from get_iova_ranges callback
  vfio-container-base: Introduce vfio_container_get_iova_ranges() helper
  virtio-iommu: Fix error handling in virtio_iommu_set_host_iova_ranges()

Signed-off-by: Richard Henderson <richard.henderson@linaro.org>
2024-07-09 07:13:14 -07:00
Zhenzhong Duan
83d9019202 vfio/display: Fix vfio_display_edid_init() error path
vfio_display_edid_init() can fail for many reasons and return silently.
It would be good to report the error.

Old mdev driver may not support vfio edid region and we allow to go
through in this case.

vfio_display_edid_update() isn't changed because it can be called at
runtime when UI changes (i.e. window resize).

Fixes: 08479114b0 ("vfio/display: add edid support.")
Suggested-by: Cédric Le Goater <clg@redhat.com>
Signed-off-by: Zhenzhong Duan <zhenzhong.duan@intel.com>
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
2024-07-09 11:50:37 +02:00
Zhenzhong Duan
f15da599a1 vfio/display: Fix potential memleak of edid info
EDID related device region info is leaked in vfio_display_edid_init()
error path and VFIODisplay destroying path.

Fixes: 08479114b0 ("vfio/display: add edid support.")
Signed-off-by: Zhenzhong Duan <zhenzhong.duan@intel.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
Reviewed-by: Marc-André Lureau <marcandre.lureau@redhat.com>
2024-07-09 11:50:37 +02:00
Eric Auger
956b30b9cf virtio-iommu: Revert transient enablement of IOMMU MR in bypass mode
In 94df5b2180 ("virtio-iommu: Fix 64kB host page size VFIO device
assignment"), in case of bypass mode, we transiently enabled the
IOMMU MR to allow the set_page_size_mask() to be called and pass
information about the page size mask constraint of cold plugged
VFIO devices. Now we do not use the IOMMU MR callback anymore, we
can just get rid of this hack.

Signed-off-by: Eric Auger <eric.auger@redhat.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
Reviewed-by: Zhenzhong Duan <zhenzhong.duan@intel.com>
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
2024-07-09 11:50:37 +02:00
Eric Auger
2457343d05 memory: remove IOMMU MR iommu_set_page_size_mask() callback
Everything is now in place to use the Host IOMMU Device callbacks
to retrieve the page size mask usable with a given assigned device.
This new method brings the advantage to pass the info much earlier
to the virtual IOMMU and before the IOMMU MR gets enabled. So let's
remove the call to memory_region_iommu_set_page_size_mask in
vfio common.c and remove the single implementation of the IOMMU MR
callback in the virtio-iommu.c

Signed-off-by: Eric Auger <eric.auger@redhat.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
Reviewed-by: Zhenzhong Duan <zhenzhong.duan@intel.com>
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
2024-07-09 11:50:37 +02:00
Eric Auger
d7c8c95fbc virtio-iommu : Retrieve page size mask on virtio_iommu_set_iommu_device()
Retrieve the Host IOMMU Device page size mask when this latter is set.
This allows to get the information much sooner than when relying on
IOMMU MR set_page_size_mask() call, whcih happens when the IOMMU MR
gets enabled. We introduce check_page_size_mask() helper whose code
is inherited from current virtio_iommu_set_page_size_mask()
implementation. This callback will be removed in a subsequent patch.

Signed-off-by: Eric Auger <eric.auger@redhat.com>
Reviewed-by: Zhenzhong Duan <zhenzhong.duan@intel.com>
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
2024-07-09 11:50:37 +02:00
Eric Auger
8fe0ebe15d HostIOMMUDevice: Introduce get_page_size_mask() callback
This callback will be used to retrieve the page size mask supported
along a given Host IOMMU device.

Signed-off-by: Eric Auger <eric.auger@redhat.com>
Reviewed-by: Zhenzhong Duan <zhenzhong.duan@intel.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
2024-07-09 11:50:37 +02:00
Eric Auger
d59ca1ca17 HostIOMMUDevice : remove Error handle from get_iova_ranges callback
The error handle argument is not used anywhere. let's remove it.

Signed-off-by: Eric Auger <eric.auger@redhat.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
Reviewed-by: Zhenzhong Duan <zhenzhong.duan@intel.com>
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
2024-07-09 11:50:37 +02:00
Eric Auger
3966bca539 vfio-container-base: Introduce vfio_container_get_iova_ranges() helper
Introduce vfio_container_get_iova_ranges() to retrieve the usable
IOVA regions of the base container and use it in the Host IOMMU
device implementations of get_iova_ranges() callback.

We also fix a UAF bug as the list was shallow copied while
g_list_free_full() was used both on the single call site, in
virtio_iommu_set_iommu_device() but also in
vfio_container_instance_finalize(). Instead use g_list_copy_deep.

Fixes: cf2647a76e ("virtio-iommu: Compute host reserved regions")
Signed-off-by: Eric Auger <eric.auger@redhat.com>
Suggested-by: Cédric Le Goater <clg@redhat.com>
Reviewed-by: Zhenzhong Duan <zhenzhong.duan@intel.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
2024-07-09 11:50:37 +02:00
Eric Auger
37baedf8e8 virtio-iommu: Fix error handling in virtio_iommu_set_host_iova_ranges()
In case no IOMMUPciBus/IOMMUDevice are found we need to properly
set the error handle and return.

Fixes : Coverity CID 1549006

Signed-off-by: Eric Auger <eric.auger@redhat.com>
Fixes: cf2647a76e ("virtio-iommu: Compute host reserved regions")
Reviewed-by: Cédric Le Goater <clg@redhat.com>
Reviewed-by: Zhenzhong Duan <zhenzhong.duan@intel.com>
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
2024-07-09 11:50:37 +02:00
Jamin Lin
d847ea7cfc machine_aspeed.py: update to test network for AST2700
Update test case to test network connection via SSH.

Test command:
```
cd build
pyvenv/bin/avocado run ../qemu/tests/avocado/machine_aspeed.py:AST2x00MachineSDK.test_aarch64_ast2700_evb_sdk_v09_02
```

Signed-off-by: Jamin Lin <jamin_lin@aspeedtech.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
2024-07-09 08:05:44 +02:00
Jamin Lin
d8b76d9ab1 machine_aspeed.py: update to test ASPEED OpenBMC SDK v09.02 for AST2700
Update test case to test ASPEED OpenBMC SDK v09.02 for AST2700.

ASPEED fixed TX mask issue from linux/drivers/ftgmac100.c.
It is required to use ASPEED OpenBMC SDK since v09.02
for AST2700 QEMU network testing.

A test image is downloaded from the ASPEED Forked OpenBMC GitHub
release repository :
https://github.com/AspeedTech-BMC/openbmc/releases/

Signed-off-by: Jamin Lin <jamin_lin@aspeedtech.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
2024-07-09 08:05:44 +02:00
Jamin Lin
61f9376775 hw/block: m25p80: support quad mode for w25q01jvq
According to the w25q01jv datasheet at page 16,
it is required to set QE bit in "Status Register 2".
Besides, users are able to utilize "Write Status Register 1(0x01)"
command to set QE bit in "Status Register 2" and
utilize "Read Status Register 2(0x35)" command to get the QE bit status.

To support quad mode for w25q01jvq, update collecting data needed
2 bytes for WRSR command in decode_new_cmd function and
verify QE bit at the second byte of collecting data bit 2
in complete_collecting_data.

Update RDCR_EQIO command to set bit 2 of return data
if quad mode enable in decode_new_cmd.

Signed-off-by: Troy Lee <troy_lee@aspeedtech.com>
Signed-off-by: Jamin Lin <jamin_lin@aspeedtech.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
2024-07-09 08:05:44 +02:00
Jamin Lin
f2146bc6cb aspeed/soc: set dma64 property for AST2700 ftgmac100
ASPEED AST2700 SOC is a 64 bits quad core CPUs (Cortex-a35)
And the base address of dram is "0x4 00000000" which
is 64bits address.

Set dma64 property for ftgmac100 model to support
64bits dram address DMA.

Signed-off-by: Jamin Lin <jamin_lin@aspeedtech.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
2024-07-09 08:05:44 +02:00
Jamin Lin
2095468d2c hw/net:ftgmac100: update TX and RX packet buffers address to 64 bits
ASPEED AST2700 SOC is a 64 bits quad core CPUs (Cortex-a35)
And the base address of dram is "0x4 00000000" which
is 64bits address.

It have "TXDES 2" and "RXDES 2" to save the high part
physical address of packet buffer.
Ex: TX packet buffer address [34:0]
The "TXDES 2" bits [18:16] which corresponds the bits [34:32]
of the 64 bits address of the TX packet buffer address
and "TXDES 3" bits [31:0] which corresponds the bits [31:0]
of the 64 bits address of the TX packet buffer address.

Update TX and RX packet buffers address type to
64 bits for dram 64 bits address DMA support.

Signed-off-by: Jamin Lin <jamin_lin@aspeedtech.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
2024-07-09 08:05:44 +02:00
Jamin Lin
578c6e9ed5 hw/net:ftgmac100: introduce TX and RX ring base address high registers to support 64 bits
ASPEED AST2700 SOC is a 64 bits quad core CPUs (Cortex-a35)
And the base address of dram is "0x4 00000000" which
is 64bits address.

It have "Normal Priority Transmit Ring Base Address Register High(0x17C)",
"High Priority Transmit Ring Base Address Register High(0x184)" and
"Receive Ring Base Address Register High(0x18C)" to save the high part physical
address of descriptor manager.
Ex: TX descriptor manager address [34:0]
The "Normal Priority Transmit Ring Base Address Register High(0x17C)"
bits [2:0] which corresponds the bits [34:32] of the 64 bits address of
the TX ring buffer address.
The "Normal Priority Transmit Ring Base Address Register(0x20)" bits [31:0]
which corresponds the bits [31:0] of the 64 bits address
of the TX ring buffer address.

Introduce a new sub region which size is 0x100 for the set of new registers
and map it at 0x100 in the container region.
This sub region range is from 0x100 to 0x1ff.

Introduce a new property and object attribute to activate the region for new registers.
Introduce a new memop handlers for the new register read and write.

Signed-off-by: Jamin Lin <jamin_lin@aspeedtech.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
2024-07-09 08:05:44 +02:00
Jamin Lin
0b51fd0f99 hw/net:ftgmac100: update ring base address to 64 bits
Update TX and RX ring base address data type to uint64_t for
64 bits dram address DMA support.

Both "Normal Priority Transmit Ring Base Address Register(0x20)" and
"Receive Ring Base Address Register (0x24)" are used for saving the
low part physical address of descriptor manager.

Therefore, changes to set TX and RX descriptor manager address bits [31:0]
in ftgmac100_read and ftgmac100_write functions.

Incrementing the version of vmstate to 2.

Signed-off-by: Jamin Lin <jamin_lin@aspeedtech.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
2024-07-09 08:05:44 +02:00
Jamin Lin
eec2f9cc69 hw/net:ftgmac100: update memory region size to 64KB
According to the datasheet of ASPEED SOCs,
one MAC controller owns 128KB of register space for AST2500.
However, one MAC controller only owns 64KB of register space for AST2600
and AST2700. It set the memory region size 128KB and it occupied another
controllers Address Spaces.

Update one MAC controller memory region size to 0x1000
because AST2500 did not use register spaces over than 64KB.

Introduce a new container region size to 0x1000 and its range
is from 0 to 0xfff. This container is mapped a sub region
for the current set of register.
This sub region range is from 0 to 0xff.

Signed-off-by: Jamin Lin <jamin_lin@aspeedtech.com>
Reviewed-by: Cédric Le Goater <clg@redhat.com>
2024-07-09 08:05:44 +02:00
16 changed files with 291 additions and 176 deletions

View File

@ -552,9 +552,12 @@ static void aspeed_soc_ast2700_realize(DeviceState *dev, Error **errp)
return;
}
/* Net */
for (i = 0; i < sc->macs_num; i++) {
object_property_set_bool(OBJECT(&s->ftgmac100[i]), "aspeed", true,
&error_abort);
object_property_set_bool(OBJECT(&s->ftgmac100[i]), "dma64", true,
&error_abort);
if (!sysbus_realize(SYS_BUS_DEVICE(&s->ftgmac100[i]), errp)) {
return;
}

View File

@ -416,6 +416,7 @@ typedef enum {
/*
* Micron: 0x35 - enable QPI
* Spansion: 0x35 - read control register
* Winbond: 0x35 - quad enable
*/
RDCR_EQIO = 0x35,
RSTQIO = 0xf5,
@ -798,6 +799,11 @@ static void complete_collecting_data(Flash *s)
s->four_bytes_address_mode = extract32(s->data[1], 5, 1);
}
break;
case MAN_WINBOND:
if (s->len > 1) {
s->quad_enable = !!(s->data[1] & 0x02);
}
break;
default:
break;
}
@ -1254,6 +1260,10 @@ static void decode_new_cmd(Flash *s, uint32_t value)
s->needed_bytes = 2;
s->state = STATE_COLLECTING_VAR_LEN_DATA;
break;
case MAN_WINBOND:
s->needed_bytes = 2;
s->state = STATE_COLLECTING_VAR_LEN_DATA;
break;
default:
s->needed_bytes = 1;
s->state = STATE_COLLECTING_DATA;
@ -1431,6 +1441,12 @@ static void decode_new_cmd(Flash *s, uint32_t value)
case MAN_MACRONIX:
s->quad_enable = true;
break;
case MAN_WINBOND:
s->data[0] = (!!s->quad_enable) << 1;
s->pos = 0;
s->len = 1;
s->state = STATE_READING_DATA;
break;
default:
break;
}

View File

@ -56,6 +56,16 @@
#define FTGMAC100_PHYDATA 0x64
#define FTGMAC100_FCR 0x68
/*
* FTGMAC100 registers high
*
* values below are offset by - FTGMAC100_REG_HIGH_OFFSET from datasheet
* because its memory region is start at FTGMAC100_REG_HIGH_OFFSET
*/
#define FTGMAC100_NPTXR_BADR_HIGH (0x17C - FTGMAC100_REG_HIGH_OFFSET)
#define FTGMAC100_HPTXR_BADR_HIGH (0x184 - FTGMAC100_REG_HIGH_OFFSET)
#define FTGMAC100_RXR_BADR_HIGH (0x18C - FTGMAC100_REG_HIGH_OFFSET)
/*
* Interrupt status register & interrupt enable register
*/
@ -165,6 +175,8 @@
#define FTGMAC100_TXDES1_TX2FIC (1 << 30)
#define FTGMAC100_TXDES1_TXIC (1 << 31)
#define FTGMAC100_TXDES2_TXBUF_BADR_HI(x) (((x) >> 16) & 0x7)
/*
* Receive descriptor
*/
@ -198,13 +210,15 @@
#define FTGMAC100_RXDES1_UDP_CHKSUM_ERR (1 << 26)
#define FTGMAC100_RXDES1_IP_CHKSUM_ERR (1 << 27)
#define FTGMAC100_RXDES2_RXBUF_BADR_HI(x) (((x) >> 16) & 0x7)
/*
* Receive and transmit Buffer Descriptor
*/
typedef struct {
uint32_t des0;
uint32_t des1;
uint32_t des2; /* not used by HW */
uint32_t des2; /* used by HW 64 bits DMA */
uint32_t des3;
} FTGMAC100Desc;
@ -515,12 +529,13 @@ out:
return frame_size;
}
static void ftgmac100_do_tx(FTGMAC100State *s, uint32_t tx_ring,
uint32_t tx_descriptor)
static void ftgmac100_do_tx(FTGMAC100State *s, uint64_t tx_ring,
uint64_t tx_descriptor)
{
int frame_size = 0;
uint8_t *ptr = s->frame;
uint32_t addr = tx_descriptor;
uint64_t addr = tx_descriptor;
uint64_t buf_addr = 0;
uint32_t flags = 0;
while (1) {
@ -559,7 +574,12 @@ static void ftgmac100_do_tx(FTGMAC100State *s, uint32_t tx_ring,
len = sizeof(s->frame) - frame_size;
}
if (dma_memory_read(&address_space_memory, bd.des3,
buf_addr = bd.des3;
if (s->dma64) {
buf_addr = deposit64(buf_addr, 32, 32,
FTGMAC100_TXDES2_TXBUF_BADR_HI(bd.des2));
}
if (dma_memory_read(&address_space_memory, buf_addr,
ptr, len, MEMTXATTRS_UNSPECIFIED)) {
qemu_log_mask(LOG_GUEST_ERROR, "%s: failed to read packet @ 0x%x\n",
__func__, bd.des3);
@ -726,9 +746,9 @@ static uint64_t ftgmac100_read(void *opaque, hwaddr addr, unsigned size)
case FTGMAC100_MATH1:
return s->math[1];
case FTGMAC100_RXR_BADR:
return s->rx_ring;
return extract64(s->rx_ring, 0, 32);
case FTGMAC100_NPTXR_BADR:
return s->tx_ring;
return extract64(s->tx_ring, 0, 32);
case FTGMAC100_ITC:
return s->itc;
case FTGMAC100_DBLAC:
@ -799,9 +819,8 @@ static void ftgmac100_write(void *opaque, hwaddr addr,
HWADDR_PRIx "\n", __func__, value);
return;
}
s->rx_ring = value;
s->rx_descriptor = s->rx_ring;
s->rx_ring = deposit64(s->rx_ring, 0, 32, value);
s->rx_descriptor = deposit64(s->rx_descriptor, 0, 32, value);
break;
case FTGMAC100_RBSR: /* DMA buffer size */
@ -814,8 +833,8 @@ static void ftgmac100_write(void *opaque, hwaddr addr,
HWADDR_PRIx "\n", __func__, value);
return;
}
s->tx_ring = value;
s->tx_descriptor = s->tx_ring;
s->tx_ring = deposit64(s->tx_ring, 0, 32, value);
s->tx_descriptor = deposit64(s->tx_descriptor, 0, 32, value);
break;
case FTGMAC100_NPTXPD: /* Trigger transmit */
@ -914,6 +933,60 @@ static void ftgmac100_write(void *opaque, hwaddr addr,
ftgmac100_update_irq(s);
}
static uint64_t ftgmac100_high_read(void *opaque, hwaddr addr, unsigned size)
{
FTGMAC100State *s = FTGMAC100(opaque);
uint64_t val = 0;
switch (addr) {
case FTGMAC100_NPTXR_BADR_HIGH:
val = extract64(s->tx_ring, 32, 32);
break;
case FTGMAC100_HPTXR_BADR_HIGH:
/* High Priority Transmit Ring Base High Address */
qemu_log_mask(LOG_UNIMP, "%s: read to unimplemented register 0x%"
HWADDR_PRIx "\n", __func__, addr);
break;
case FTGMAC100_RXR_BADR_HIGH:
val = extract64(s->rx_ring, 32, 32);
break;
default:
qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad address at offset 0x%"
HWADDR_PRIx "\n", __func__, addr);
break;
}
return val;
}
static void ftgmac100_high_write(void *opaque, hwaddr addr,
uint64_t value, unsigned size)
{
FTGMAC100State *s = FTGMAC100(opaque);
switch (addr) {
case FTGMAC100_NPTXR_BADR_HIGH:
s->tx_ring = deposit64(s->tx_ring, 32, 32, value);
s->tx_descriptor = deposit64(s->tx_descriptor, 32, 32, value);
break;
case FTGMAC100_HPTXR_BADR_HIGH:
/* High Priority Transmit Ring Base High Address */
qemu_log_mask(LOG_UNIMP, "%s: write to unimplemented register 0x%"
HWADDR_PRIx "\n", __func__, addr);
break;
case FTGMAC100_RXR_BADR_HIGH:
s->rx_ring = deposit64(s->rx_ring, 32, 32, value);
s->rx_descriptor = deposit64(s->rx_descriptor, 32, 32, value);
break;
default:
qemu_log_mask(LOG_GUEST_ERROR, "%s: Bad address at offset 0x%"
HWADDR_PRIx "\n", __func__, addr);
break;
}
ftgmac100_update_irq(s);
}
static int ftgmac100_filter(FTGMAC100State *s, const uint8_t *buf, size_t len)
{
unsigned mcast_idx;
@ -957,9 +1030,9 @@ static ssize_t ftgmac100_receive(NetClientState *nc, const uint8_t *buf,
FTGMAC100State *s = FTGMAC100(qemu_get_nic_opaque(nc));
FTGMAC100Desc bd;
uint32_t flags = 0;
uint32_t addr;
uint64_t addr;
uint32_t crc;
uint32_t buf_addr;
uint64_t buf_addr = 0;
uint8_t *crc_ptr;
uint32_t buf_len;
size_t size = len;
@ -1024,7 +1097,12 @@ static ssize_t ftgmac100_receive(NetClientState *nc, const uint8_t *buf,
if (size < 4) {
buf_len += size - 4;
}
buf_addr = bd.des3;
if (s->dma64) {
buf_addr = deposit64(buf_addr, 32, 32,
FTGMAC100_RXDES2_RXBUF_BADR_HI(bd.des2));
}
if (first && proto == ETH_P_VLAN && buf_len >= 18) {
bd.des1 = lduw_be_p(buf + 14) | FTGMAC100_RXDES1_VLANTAG_AVAIL;
@ -1078,6 +1156,14 @@ static const MemoryRegionOps ftgmac100_ops = {
.endianness = DEVICE_LITTLE_ENDIAN,
};
static const MemoryRegionOps ftgmac100_high_ops = {
.read = ftgmac100_high_read,
.write = ftgmac100_high_write,
.valid.min_access_size = 4,
.valid.max_access_size = 4,
.endianness = DEVICE_LITTLE_ENDIAN,
};
static void ftgmac100_cleanup(NetClientState *nc)
{
FTGMAC100State *s = FTGMAC100(qemu_get_nic_opaque(nc));
@ -1107,9 +1193,23 @@ static void ftgmac100_realize(DeviceState *dev, Error **errp)
s->rxdes0_edorr = FTGMAC100_RXDES0_EDORR;
}
memory_region_init_io(&s->iomem, OBJECT(dev), &ftgmac100_ops, s,
TYPE_FTGMAC100, 0x2000);
sysbus_init_mmio(sbd, &s->iomem);
memory_region_init(&s->iomem_container, OBJECT(s),
TYPE_FTGMAC100 ".container", FTGMAC100_MEM_SIZE);
sysbus_init_mmio(sbd, &s->iomem_container);
memory_region_init_io(&s->iomem, OBJECT(s), &ftgmac100_ops, s,
TYPE_FTGMAC100 ".regs", FTGMAC100_REG_MEM_SIZE);
memory_region_add_subregion(&s->iomem_container, 0x0, &s->iomem);
if (s->dma64) {
memory_region_init_io(&s->iomem_high, OBJECT(s), &ftgmac100_high_ops,
s, TYPE_FTGMAC100 ".regs.high",
FTGMAC100_REG_HIGH_MEM_SIZE);
memory_region_add_subregion(&s->iomem_container,
FTGMAC100_REG_HIGH_OFFSET,
&s->iomem_high);
}
sysbus_init_irq(sbd, &s->irq);
qemu_macaddr_default_if_unset(&s->conf.macaddr);
@ -1121,18 +1221,14 @@ static void ftgmac100_realize(DeviceState *dev, Error **errp)
static const VMStateDescription vmstate_ftgmac100 = {
.name = TYPE_FTGMAC100,
.version_id = 1,
.minimum_version_id = 1,
.version_id = 2,
.minimum_version_id = 2,
.fields = (const VMStateField[]) {
VMSTATE_UINT32(irq_state, FTGMAC100State),
VMSTATE_UINT32(isr, FTGMAC100State),
VMSTATE_UINT32(ier, FTGMAC100State),
VMSTATE_UINT32(rx_enabled, FTGMAC100State),
VMSTATE_UINT32(rx_ring, FTGMAC100State),
VMSTATE_UINT32(rbsr, FTGMAC100State),
VMSTATE_UINT32(tx_ring, FTGMAC100State),
VMSTATE_UINT32(rx_descriptor, FTGMAC100State),
VMSTATE_UINT32(tx_descriptor, FTGMAC100State),
VMSTATE_UINT32_ARRAY(math, FTGMAC100State, 2),
VMSTATE_UINT32(itc, FTGMAC100State),
VMSTATE_UINT32(aptcr, FTGMAC100State),
@ -1151,6 +1247,10 @@ static const VMStateDescription vmstate_ftgmac100 = {
VMSTATE_UINT32(phy_int_mask, FTGMAC100State),
VMSTATE_UINT32(txdes0_edotr, FTGMAC100State),
VMSTATE_UINT32(rxdes0_edorr, FTGMAC100State),
VMSTATE_UINT64(rx_ring, FTGMAC100State),
VMSTATE_UINT64(tx_ring, FTGMAC100State),
VMSTATE_UINT64(rx_descriptor, FTGMAC100State),
VMSTATE_UINT64(tx_descriptor, FTGMAC100State),
VMSTATE_END_OF_LIST()
}
};
@ -1158,6 +1258,7 @@ static const VMStateDescription vmstate_ftgmac100 = {
static Property ftgmac100_properties[] = {
DEFINE_PROP_BOOL("aspeed", FTGMAC100State, aspeed, false),
DEFINE_NIC_PROPERTIES(FTGMAC100State, conf),
DEFINE_PROP_BOOL("dma64", FTGMAC100State, dma64, false),
DEFINE_PROP_END_OF_LIST(),
};

View File

@ -622,14 +622,6 @@ static void vfio_listener_region_add(MemoryListener *listener,
int128_get64(llend),
iommu_idx);
ret = memory_region_iommu_set_page_size_mask(giommu->iommu_mr,
bcontainer->pgsizes,
&err);
if (ret) {
g_free(giommu);
goto fail;
}
ret = memory_region_register_iommu_notifier(section->mr, &giommu->n,
&err);
if (ret) {

View File

@ -83,6 +83,21 @@ int vfio_container_query_dirty_bitmap(const VFIOContainerBase *bcontainer,
errp);
}
static gpointer copy_iova_range(gconstpointer src, gpointer data)
{
Range *source = (Range *)src;
Range *dest = g_new(Range, 1);
range_set_bounds(dest, range_lob(source), range_upb(source));
return dest;
}
GList *vfio_container_get_iova_ranges(const VFIOContainerBase *bcontainer)
{
assert(bcontainer);
return g_list_copy_deep(bcontainer->iova_ranges, copy_iova_range, NULL);
}
static void vfio_container_instance_finalize(Object *obj)
{
VFIOContainerBase *bcontainer = VFIO_IOMMU(obj);

View File

@ -1165,18 +1165,21 @@ static int hiod_legacy_vfio_get_cap(HostIOMMUDevice *hiod, int cap,
}
static GList *
hiod_legacy_vfio_get_iova_ranges(HostIOMMUDevice *hiod, Error **errp)
hiod_legacy_vfio_get_iova_ranges(HostIOMMUDevice *hiod)
{
VFIODevice *vdev = hiod->agent;
GList *l = NULL;
g_assert(vdev);
if (vdev->bcontainer) {
l = g_list_copy(vdev->bcontainer->iova_ranges);
return vfio_container_get_iova_ranges(vdev->bcontainer);
}
return l;
static uint64_t
hiod_legacy_vfio_get_page_size_mask(HostIOMMUDevice *hiod)
{
VFIODevice *vdev = hiod->agent;
g_assert(vdev);
return vfio_container_get_page_size_mask(vdev->bcontainer);
}
static void vfio_iommu_legacy_instance_init(Object *obj)
@ -1193,6 +1196,7 @@ static void hiod_legacy_vfio_class_init(ObjectClass *oc, void *data)
hioc->realize = hiod_legacy_vfio_realize;
hioc->get_cap = hiod_legacy_vfio_get_cap;
hioc->get_iova_ranges = hiod_legacy_vfio_get_iova_ranges;
hioc->get_page_size_mask = hiod_legacy_vfio_get_page_size_mask;
};
static const TypeInfo types[] = {

View File

@ -124,7 +124,7 @@ static void vfio_display_edid_ui_info(void *opaque, uint32_t idx,
}
}
static void vfio_display_edid_init(VFIOPCIDevice *vdev)
static bool vfio_display_edid_init(VFIOPCIDevice *vdev, Error **errp)
{
VFIODisplay *dpy = vdev->dpy;
int fd = vdev->vbasedev.fd;
@ -135,7 +135,8 @@ static void vfio_display_edid_init(VFIOPCIDevice *vdev)
VFIO_REGION_SUBTYPE_GFX_EDID,
&dpy->edid_info);
if (ret) {
return;
/* Failed to get GFX edid info, allow to go through without edid. */
return true;
}
trace_vfio_display_edid_available();
@ -167,13 +168,16 @@ static void vfio_display_edid_init(VFIOPCIDevice *vdev)
vfio_display_edid_link_up, vdev);
vfio_display_edid_update(vdev, true, 0, 0);
return;
return true;
err:
error_setg(errp, "vfio: failed to read GFX edid field");
trace_vfio_display_edid_write_error();
g_free(dpy->edid_info);
g_free(dpy->edid_regs);
dpy->edid_info = NULL;
dpy->edid_regs = NULL;
return;
return false;
}
static void vfio_display_edid_exit(VFIODisplay *dpy)
@ -182,6 +186,7 @@ static void vfio_display_edid_exit(VFIODisplay *dpy)
return;
}
g_free(dpy->edid_info);
g_free(dpy->edid_regs);
g_free(dpy->edid_blob);
timer_free(dpy->edid_link_timer);
@ -365,8 +370,7 @@ static bool vfio_display_dmabuf_init(VFIOPCIDevice *vdev, Error **errp)
return false;
}
}
vfio_display_edid_init(vdev);
return true;
return vfio_display_edid_init(vdev, errp);
}
static void vfio_display_dmabuf_exit(VFIODisplay *dpy)

View File

@ -644,26 +644,31 @@ static bool hiod_iommufd_vfio_realize(HostIOMMUDevice *hiod, void *opaque,
}
static GList *
hiod_iommufd_vfio_get_iova_ranges(HostIOMMUDevice *hiod, Error **errp)
hiod_iommufd_vfio_get_iova_ranges(HostIOMMUDevice *hiod)
{
VFIODevice *vdev = hiod->agent;
GList *l = NULL;
g_assert(vdev);
if (vdev->bcontainer) {
l = g_list_copy(vdev->bcontainer->iova_ranges);
return vfio_container_get_iova_ranges(vdev->bcontainer);
}
return l;
static uint64_t
hiod_iommufd_vfio_get_page_size_mask(HostIOMMUDevice *hiod)
{
VFIODevice *vdev = hiod->agent;
g_assert(vdev);
return vfio_container_get_page_size_mask(vdev->bcontainer);
}
static void hiod_iommufd_vfio_class_init(ObjectClass *oc, void *data)
{
HostIOMMUDeviceClass *hiodc = HOST_IOMMU_DEVICE_CLASS(oc);
hiodc->realize = hiod_iommufd_vfio_realize;
hiodc->get_iova_ranges = hiod_iommufd_vfio_get_iova_ranges;
hiodc->get_page_size_mask = hiod_iommufd_vfio_get_page_size_mask;
};
static const TypeInfo types[] = {

View File

@ -131,7 +131,7 @@ virtio_iommu_fill_resv_property(uint32_t devid, uint8_t subtype, uint64_t start,
virtio_iommu_notify_map(const char *name, uint64_t virt_start, uint64_t virt_end, uint64_t phys_start, uint32_t flags) "mr=%s virt_start=0x%"PRIx64" virt_end=0x%"PRIx64" phys_start=0x%"PRIx64" flags=%d"
virtio_iommu_notify_unmap(const char *name, uint64_t virt_start, uint64_t virt_end) "mr=%s virt_start=0x%"PRIx64" virt_end=0x%"PRIx64
virtio_iommu_remap(const char *name, uint64_t virt_start, uint64_t virt_end, uint64_t phys_start) "mr=%s virt_start=0x%"PRIx64" virt_end=0x%"PRIx64" phys_start=0x%"PRIx64
virtio_iommu_set_page_size_mask(const char *name, uint64_t old, uint64_t new) "mr=%s old_mask=0x%"PRIx64" new_mask=0x%"PRIx64
virtio_iommu_update_page_size_mask(const char *name, uint64_t old, uint64_t new) "host iommu device=%s old_mask=0x%"PRIx64" new_mask=0x%"PRIx64
virtio_iommu_notify_flag_add(const char *name) "add notifier to mr %s"
virtio_iommu_notify_flag_del(const char *name) "del notifier from mr %s"
virtio_iommu_switch_address_space(uint8_t bus, uint8_t slot, uint8_t fn, bool on) "Device %02x:%02x.%x switching address space (iommu enabled=%d)"

View File

@ -563,10 +563,15 @@ static int virtio_iommu_set_host_iova_ranges(VirtIOIOMMU *s, PCIBus *bus,
int ret = -EINVAL;
if (!sbus) {
error_report("%s no sbus", __func__);
error_setg(errp, "%s: no IOMMUPciBus found!", __func__);
return ret;
}
sdev = sbus->pbdev[devfn];
if (!sdev) {
error_setg(errp, "%s: no IOMMUDevice found!", __func__);
return ret;
}
current_ranges = sdev->host_resv_ranges;
@ -613,9 +618,39 @@ out:
return ret;
}
static bool check_page_size_mask(VirtIOIOMMU *viommu, uint64_t new_mask,
Error **errp)
{
uint64_t cur_mask = viommu->config.page_size_mask;
if ((cur_mask & new_mask) == 0) {
error_setg(errp, "virtio-iommu reports a page size mask 0x%"PRIx64
" incompatible with currently supported mask 0x%"PRIx64,
new_mask, cur_mask);
return false;
}
/*
* Once the granule is frozen we can't change the mask anymore. If by
* chance the hotplugged device supports the same granule, we can still
* accept it.
*/
if (viommu->granule_frozen) {
int cur_granule = ctz64(cur_mask);
if (!(BIT_ULL(cur_granule) & new_mask)) {
error_setg(errp,
"virtio-iommu does not support frozen granule 0x%llx",
BIT_ULL(cur_granule));
return false;
}
}
return true;
}
static bool virtio_iommu_set_iommu_device(PCIBus *bus, void *opaque, int devfn,
HostIOMMUDevice *hiod, Error **errp)
{
ERRP_GUARD();
VirtIOIOMMU *viommu = opaque;
HostIOMMUDeviceClass *hiodc = HOST_IOMMU_DEVICE_GET_CLASS(hiod);
struct hiod_key *new_key;
@ -630,7 +665,7 @@ static bool virtio_iommu_set_iommu_device(PCIBus *bus, void *opaque, int devfn,
if (hiodc->get_iova_ranges) {
int ret;
host_iova_ranges = hiodc->get_iova_ranges(hiod, errp);
host_iova_ranges = hiodc->get_iova_ranges(hiod);
if (!host_iova_ranges) {
return true; /* some old kernels may not support that capability */
}
@ -638,8 +673,28 @@ static bool virtio_iommu_set_iommu_device(PCIBus *bus, void *opaque, int devfn,
hiod->aliased_devfn,
host_iova_ranges, errp);
if (ret) {
g_list_free_full(host_iova_ranges, g_free);
return false;
goto error;
}
}
if (hiodc->get_page_size_mask) {
uint64_t new_mask = hiodc->get_page_size_mask(hiod);
if (check_page_size_mask(viommu, new_mask, errp)) {
/*
* The default mask depends on the "granule" property. For example,
* with 4k granule, it is -(4 * KiB). When an assigned device has
* page size restrictions due to the hardware IOMMU configuration,
* apply this restriction to the mask.
*/
trace_virtio_iommu_update_page_size_mask(hiod->name,
viommu->config.page_size_mask,
new_mask);
if (!viommu->granule_frozen) {
viommu->config.page_size_mask &= new_mask;
}
} else {
error_prepend(errp, "%s: ", hiod->name);
goto error;
}
}
@ -652,6 +707,9 @@ static bool virtio_iommu_set_iommu_device(PCIBus *bus, void *opaque, int devfn,
g_list_free_full(host_iova_ranges, g_free);
return true;
error:
g_list_free_full(host_iova_ranges, g_free);
return false;
}
static void
@ -1350,50 +1408,6 @@ static int virtio_iommu_notify_flag_changed(IOMMUMemoryRegion *iommu_mr,
return 0;
}
/*
* The default mask depends on the "granule" property. For example, with
* 4k granule, it is -(4 * KiB). When an assigned device has page size
* restrictions due to the hardware IOMMU configuration, apply this restriction
* to the mask.
*/
static int virtio_iommu_set_page_size_mask(IOMMUMemoryRegion *mr,
uint64_t new_mask,
Error **errp)
{
IOMMUDevice *sdev = container_of(mr, IOMMUDevice, iommu_mr);
VirtIOIOMMU *s = sdev->viommu;
uint64_t cur_mask = s->config.page_size_mask;
trace_virtio_iommu_set_page_size_mask(mr->parent_obj.name, cur_mask,
new_mask);
if ((cur_mask & new_mask) == 0) {
error_setg(errp, "virtio-iommu %s reports a page size mask 0x%"PRIx64
" incompatible with currently supported mask 0x%"PRIx64,
mr->parent_obj.name, new_mask, cur_mask);
return -1;
}
/*
* Once the granule is frozen we can't change the mask anymore. If by
* chance the hotplugged device supports the same granule, we can still
* accept it.
*/
if (s->granule_frozen) {
int cur_granule = ctz64(cur_mask);
if (!(BIT_ULL(cur_granule) & new_mask)) {
error_setg(errp, "virtio-iommu %s does not support frozen granule 0x%llx",
mr->parent_obj.name, BIT_ULL(cur_granule));
return -1;
}
return 0;
}
s->config.page_size_mask &= new_mask;
return 0;
}
static void virtio_iommu_system_reset(void *opaque)
{
VirtIOIOMMU *s = opaque;
@ -1416,18 +1430,6 @@ static void virtio_iommu_freeze_granule(Notifier *notifier, void *data)
VirtIOIOMMU *s = container_of(notifier, VirtIOIOMMU, machine_done);
int granule;
if (likely(s->config.bypass)) {
/*
* Transient IOMMU MR enable to collect page_size_mask requirements
* through memory_region_iommu_set_page_size_mask() called by
* VFIO region_add() callback
*/
s->config.bypass = false;
virtio_iommu_switch_address_space_all(s);
/* restore default */
s->config.bypass = true;
virtio_iommu_switch_address_space_all(s);
}
s->granule_frozen = true;
granule = ctz64(s->config.page_size_mask);
trace_virtio_iommu_freeze_granule(BIT_ULL(granule));
@ -1718,7 +1720,6 @@ static void virtio_iommu_memory_region_class_init(ObjectClass *klass,
imrc->translate = virtio_iommu_translate;
imrc->replay = virtio_iommu_replay;
imrc->notify_flag_changed = virtio_iommu_notify_flag_changed;
imrc->iommu_set_page_size_mask = virtio_iommu_set_page_size_mask;
}
static const TypeInfo virtio_iommu_info = {

View File

@ -504,32 +504,6 @@ struct IOMMUMemoryRegionClass {
* @iommu: the IOMMUMemoryRegion
*/
int (*num_indexes)(IOMMUMemoryRegion *iommu);
/**
* @iommu_set_page_size_mask:
*
* Restrict the page size mask that can be supported with a given IOMMU
* memory region. Used for example to propagate host physical IOMMU page
* size mask limitations to the virtual IOMMU.
*
* Optional method: if this method is not provided, then the default global
* page mask is used.
*
* @iommu: the IOMMUMemoryRegion
*
* @page_size_mask: a bitmask of supported page sizes. At least one bit,
* representing the smallest page size, must be set. Additional set bits
* represent supported block sizes. For example a host physical IOMMU that
* uses page tables with a page size of 4kB, and supports 2MB and 4GB
* blocks, will set mask 0x40201000. A granule of 4kB with indiscriminate
* block sizes is specified with mask 0xfffffffffffff000.
*
* Returns 0 on success, or a negative error. In case of failure, the error
* object must be created.
*/
int (*iommu_set_page_size_mask)(IOMMUMemoryRegion *iommu,
uint64_t page_size_mask,
Error **errp);
};
typedef struct RamDiscardListener RamDiscardListener;
@ -1919,18 +1893,6 @@ int memory_region_iommu_attrs_to_index(IOMMUMemoryRegion *iommu_mr,
*/
int memory_region_iommu_num_indexes(IOMMUMemoryRegion *iommu_mr);
/**
* memory_region_iommu_set_page_size_mask: set the supported page
* sizes for a given IOMMU memory region
*
* @iommu_mr: IOMMU memory region
* @page_size_mask: supported page size mask
* @errp: pointer to Error*, to store an error if it happens.
*/
int memory_region_iommu_set_page_size_mask(IOMMUMemoryRegion *iommu_mr,
uint64_t page_size_mask,
Error **errp);
/**
* memory_region_name: get a memory region's name
*

View File

@ -14,6 +14,11 @@
#define TYPE_FTGMAC100 "ftgmac100"
OBJECT_DECLARE_SIMPLE_TYPE(FTGMAC100State, FTGMAC100)
#define FTGMAC100_MEM_SIZE 0x1000
#define FTGMAC100_REG_MEM_SIZE 0x100
#define FTGMAC100_REG_HIGH_MEM_SIZE 0x100
#define FTGMAC100_REG_HIGH_OFFSET 0x100
#include "hw/sysbus.h"
#include "net/net.h"
@ -30,7 +35,9 @@ struct FTGMAC100State {
NICState *nic;
NICConf conf;
qemu_irq irq;
MemoryRegion iomem_container;
MemoryRegion iomem;
MemoryRegion iomem_high;
uint8_t frame[FTGMAC100_MAX_FRAME_SIZE];
@ -38,10 +45,6 @@ struct FTGMAC100State {
uint32_t isr;
uint32_t ier;
uint32_t rx_enabled;
uint32_t rx_ring;
uint32_t rx_descriptor;
uint32_t tx_ring;
uint32_t tx_descriptor;
uint32_t math[2];
uint32_t rbsr;
uint32_t itc;
@ -54,7 +57,10 @@ struct FTGMAC100State {
uint32_t phycr;
uint32_t phydata;
uint32_t fcr;
uint64_t rx_ring;
uint64_t rx_descriptor;
uint64_t tx_ring;
uint64_t tx_descriptor;
uint32_t phy_status;
uint32_t phy_control;
@ -65,6 +71,7 @@ struct FTGMAC100State {
bool aspeed;
uint32_t txdes0_edotr;
uint32_t rxdes0_edorr;
bool dma64;
};
#define TYPE_ASPEED_MII "aspeed-mmi"

View File

@ -86,6 +86,15 @@ int vfio_container_set_dirty_page_tracking(VFIOContainerBase *bcontainer,
int vfio_container_query_dirty_bitmap(const VFIOContainerBase *bcontainer,
VFIOBitmap *vbmap, hwaddr iova, hwaddr size, Error **errp);
GList *vfio_container_get_iova_ranges(const VFIOContainerBase *bcontainer);
static inline uint64_t
vfio_container_get_page_size_mask(const VFIOContainerBase *bcontainer)
{
assert(bcontainer);
return bcontainer->pgsizes;
}
#define TYPE_VFIO_IOMMU "vfio-iommu"
#define TYPE_VFIO_IOMMU_LEGACY TYPE_VFIO_IOMMU "-legacy"
#define TYPE_VFIO_IOMMU_SPAPR TYPE_VFIO_IOMMU "-spapr"

View File

@ -87,9 +87,16 @@ struct HostIOMMUDeviceClass {
* @hiod Host IOMMU device
*
* @hiod: handle to the host IOMMU device
* @errp: error handle
*/
GList* (*get_iova_ranges)(HostIOMMUDevice *hiod, Error **errp);
GList* (*get_iova_ranges)(HostIOMMUDevice *hiod);
/**
*
* @get_page_size_mask: Return the page size mask supported along this
* @hiod Host IOMMU device
*
* @hiod: handle to the host IOMMU device
*/
uint64_t (*get_page_size_mask)(HostIOMMUDevice *hiod);
};
/*

View File

@ -1901,19 +1901,6 @@ static int memory_region_update_iommu_notify_flags(IOMMUMemoryRegion *iommu_mr,
return ret;
}
int memory_region_iommu_set_page_size_mask(IOMMUMemoryRegion *iommu_mr,
uint64_t page_size_mask,
Error **errp)
{
IOMMUMemoryRegionClass *imrc = IOMMU_MEMORY_REGION_GET_CLASS(iommu_mr);
int ret = 0;
if (imrc->iommu_set_page_size_mask) {
ret = imrc->iommu_set_page_size_mask(iommu_mr, page_size_mask, errp);
}
return ret;
}
int memory_region_register_iommu_notifier(MemoryRegion *mr,
IOMMUNotifier *n, Error **errp)
{

View File

@ -313,14 +313,14 @@ class AST2x00MachineSDK(QemuSystemTest, LinuxSSHMixIn):
def do_test_aarch64_aspeed_sdk_start(self, image):
self.vm.set_console()
self.vm.add_args('-drive', 'file=' + image + ',if=mtd,format=raw')
self.vm.add_args('-drive', 'file=' + image + ',if=mtd,format=raw',
'-net', 'nic', '-net', 'user,hostfwd=:127.0.0.1:0-:22')
self.vm.launch()
self.wait_for_console_pattern('U-Boot 2023.10')
self.wait_for_console_pattern('## Loading kernel from FIT Image')
self.wait_for_console_pattern('Starting kernel ...')
self.wait_for_console_pattern("systemd[1]: Hostname set to")
@skipUnless(os.getenv('QEMU_TEST_FLAKY_TESTS'), 'Test is unstable on GitLab')
@ -387,15 +387,15 @@ class AST2x00MachineSDK(QemuSystemTest, LinuxSSHMixIn):
year = time.strftime("%Y")
self.ssh_command_output_contains('/sbin/hwclock -f /dev/rtc1', year);
def test_aarch64_ast2700_evb_sdk_v09_01(self):
def test_aarch64_ast2700_evb_sdk_v09_02(self):
"""
:avocado: tags=arch:aarch64
:avocado: tags=machine:ast2700-evb
"""
image_url = ('https://github.com/AspeedTech-BMC/openbmc/releases/'
'download/v09.01/ast2700-default-obmc.tar.gz')
image_hash = 'b1cc0fd73c7650d34c9c8459a243f52a91e9e27144b8608b2645ab19461d1e07'
'download/v09.02/ast2700-default-obmc.tar.gz')
image_hash = 'ac969c2602f4e6bdb69562ff466b89ae3fe1d86e1f6797bb7969d787f82116a7'
image_path = self.fetch_asset(image_url, asset_hash=image_hash,
algorithm='sha256')
archive.extract(image_path, self.workdir)
@ -436,4 +436,6 @@ class AST2x00MachineSDK(QemuSystemTest, LinuxSSHMixIn):
self.vm.add_args('-smp', str(num_cpu))
self.do_test_aarch64_aspeed_sdk_start(image_dir + 'image-bmc')
self.wait_for_console_pattern('nodistro.0 ast2700-default ttyS12')
self.ssh_connect('root', '0penBmc', False)