Compare commits

...
Sign in to create a new pull request.

215 commits

Author SHA1 Message Date
Python Maint
c8af4d85b6 Rebuilt for Python 3.15.0b4 ABI change 2026-07-22 10:47:19 +02:00
Fedora Release Engineering
5bd254f006 Rebuilt for https://fedoraproject.org/wiki/Fedora_45_Mass_Rebuild 2026-07-17 09:07:32 +00:00
Jerry James
87e40ff1ba OCaml 5.5.0 rebuild 2026-07-09 11:46:55 -06:00
Yaakov Selkowitz
1e49e52adb Rebuilt for openssl 4.0 2026-06-18 16:36:54 -04:00
Michael Young
0c18c23c4c 4 security updates
x86 HVM I/O port list traversal [XSA-491, CVE-2026-42487]
domctl lock open to abuse [XSA-492, CVE-2026-42489, CVE-2026-42490]
Arm: Completion of memory accesses not guaranteed by completion of a TLBI
	 [XSA-493, CVE-2025-10263]
x86: mismatched mapcache metadata [XSA-494, CVE-2026-42488]
2026-06-18 21:14:50 +01:00
Yaakov Selkowitz
124455e632 Rebuilt for openssl 4.0 2026-06-12 20:07:37 -04:00
Python Maint
f67d5718e2 Rebuilt for Python 3.15 2026-06-03 19:38:16 +02:00
Michael Young
b448fd6e2f x86: CPU Opcode Cache corruption [XSA-490,CVE-2025-54518] 2026-05-12 20:57:06 +01:00
Michael Young
cf70d8c84e 4 security patches
+- oxenstored keeps quota related use counts across domain destruction
+       [XSA-483, CVE-2026-23556]
+- Xenstored DoS via XS_RESET_WATCHES command [XSA-484, CVE-2026-23557]
+- grant table v2 race in status page mapping [XSA-486, CVE-2026-23558]
+- x86: Floating Point Divider State Sampling [XSA-488, CVE-2025-54505]
2026-04-28 21:20:56 +01:00
Adam Williamson
18cf277715 Revert "Make licenses package noarch"
This reverts commit 545511922a.
Turns out we can't do this because different license files show
up on x86_64 and aarch64 (there are more on x86_64 as we build
more stuff there).
2026-03-27 15:59:15 -07:00
Adam Williamson
545511922a Make licenses package noarch
It only has licenses in it, after all.

Signed-off-by: Adam Williamson <awilliam@redhat.com>
2026-03-27 14:13:04 -07:00
Michael Young
30cb19d1ba update to xen 4.21.1 2026-03-26 20:52:44 +00:00
Michael Young
fbec0bc65a 2 security updates
Use after free of paging structures in EPT [XSA-480, CVE-2026-23554]
Xenstored DoS by unprivileged domain [XSA-481, CVE-2026-23555]
2026-03-17 19:57:45 +00:00
Richard W.M. Jones
2b36f2e8ca OCaml 5.4.1 rebuild 2026-02-20 16:06:05 +00:00
Michael Young
d409186bf5 2 security updates
x86: buffer overrun with shadow paging + tracing [XSA-477, CVE-2025-58150]
x86: incomplete IBPB for vCPU isolation [XSA-479, CVE-2026-23553]
2026-01-28 22:25:55 +00:00
Fedora Release Engineering
461c19a5ca Rebuilt for https://fedoraproject.org/wiki/Fedora_44_Mass_Rebuild 2026-01-17 20:34:16 +00:00
Jerry James
ca06290682 Fix a changelog entry 2026-01-13 20:56:05 -07:00
Michael Young
aa9dce01d1 update to xen 4.21.0 2026-01-07 20:11:57 +00:00
Michael Young
b27c4b799d update to xen 4.20.2 2025-11-14 18:46:13 +00:00
Michael Young
310309c8d5 teecr32_el1 and teehbr32_el1 support dropped in binutils 2.45.50-5.fc44
Incorrect removal of permissions on PCI device unplug
	[XSA-476, CVE-2025-58149]
x86: Incorrect input sanitisation in Viridian hypercalls
	[XSA-475, CVE-2025-58147, CVE-2025-58148]
2025-10-26 12:39:49 +00:00
Richard W.M. Jones
932125ac66 OCaml 5.4.0 rebuild 2025-10-15 17:21:56 +01:00
Python Maint
d001d8f7cf Rebuilt for Python 3.14.0rc3 bytecode 2025-09-19 15:03:51 +02:00
Michael Young
8bc3f5aa32 2 security updates
Mutiple vulnerabilities in the Viridian interface [XSA-472,
	CVE-2025-27466, CVE-2025-58142, CVE-2025-58143]
Arm issues with page refcounting [XSA-473, CVE-2025-58144, CVE-2025-58145]
2025-09-10 23:41:07 +01:00
Michael Young
ca8c5d5135 tools/xl: don't crash on NULL command line 2025-09-02 20:20:57 +01:00
Python Maint
39101b511c Rebuilt for Python 3.14.0rc2 bytecode 2025-08-15 15:23:19 +02:00
Fedora Release Engineering
e2d4d104a0 Rebuilt for https://fedoraproject.org/wiki/Fedora_43_Mass_Rebuild 2025-07-25 20:44:23 +00:00
Michael Young
d382b68b39 update to xen 4.20.1
includes fixes for
x86: Incorrect stubs exception handling for flags recovery [XSA-470,
        CVE-2025-27465]
x86: Transitive Scheduler Attacks [XSA-471, CVE-2024-36350,
        CVE-2024-36357]
2025-07-15 21:03:56 +01:00
Jerry James
80e497a295 Rebuild to fix OCaml dependencies 2025-07-11 14:54:03 -06:00
Python Maint
41f5d9097f Rebuilt for Python 3.14 2025-06-02 21:24:59 +02:00
Michael Young
3a0543c8d6 x86: Indirect Target Selection [XSA-469, CVE-2024-28956] 2025-05-12 21:42:55 +01:00
Michael Young
88c9f05c39 update to xen-4.19.2
remove patches now included or superceded upstream
remove xen*.efi.elf files to avoid debuginfo failure
2025-04-07 21:00:32 +01:00
Michael Young
59fe5ad165 deadlock potential with VT-d and legacy PCI device pass-through
[XSA-467, CVE-2025-1713]
2025-02-27 18:20:39 +00:00
Michael Young
0e81fe4bff adjust file locations now /usr/sbin is a symlink to /usr/bin
remove debugedit fix as no longer needed
2025-01-24 22:32:04 +00:00
Fedora Release Engineering
0d1f7da88a Rebuilt for https://fedoraproject.org/wiki/Fedora_42_Mass_Rebuild 2025-01-19 15:38:51 +00:00
Jerry James
5c740ce63a OCaml 5.3.0 rebuild for Fedora 42 2025-01-10 13:42:27 -07:00
Michael Young
d458004d8b work around debugedit bug to fix aarch64 builds 2025-01-09 21:24:58 +00:00
Andrea Perotti
ebbbc5ccb7 FIX #2335558: xen-hypervisor %post doesn't load all needed grub2 modules (elf.mod is missing) 2025-01-04 14:12:34 +01:00
Michael Young
2b88083cfc update to xen-4.19.1 2024-12-06 19:19:08 +00:00
Michael Young
a322535e9f add bugzilla references 2024-09-25 22:02:12 +01:00
Michael Young
417c2eb41a x86: Deadlock in vlapic_error() [XSA-462, CVE-2024-45817] 2024-09-24 16:48:07 +01:00
Miroslav Suchý
b5342a4b67 convert license to SPDX
This is part of https://fedoraproject.org/wiki/Changes/SPDX_Licenses_Phase_4
2024-09-04 22:52:13 +02:00
Michael Young
ef4574608a 2 security fixes
error handling in x86 IOMMU identity mapping [XSA-460, CVE-2024-31145]
PCI device pass-through with shared resources [XSA-461, CVE-2024-31146]
2024-08-14 22:07:13 +01:00
Michael Young
08778ae14d update to xen-4.19.0 2024-08-03 22:01:35 +01:00
Fedora Release Engineering
589e86cf56 Rebuilt for https://fedoraproject.org/wiki/Fedora_41_Mass_Rebuild 2024-07-20 09:54:27 +00:00
Michael Young
1b82c01894 add bugzilla reference 2024-07-18 22:27:45 +01:00
Alejandro Vallejo
9e3a14be33 Split xen-runtime posttrans conditional
$(ls -A ...) expands before the whole condition is passed to `[`. This
means `-d <path>` does not gate the `ls` command being executed.

While it's benign, it causes ls's stderr to propagate to yum/dnf output,
which is somewhat disconcerting for the user.

Fix it by forcing ls into its own conditional.
2024-07-17 00:12:04 +01:00
Michael Young
269fa36c52 double unlock in x86 guest IRQ handling [XSA-458, CVE-2024-31143] 2024-07-16 21:23:30 +01:00
Python Maint
bac467190c Rebuilt for Python 3.13 2024-06-07 09:52:18 +02:00
Michael Young
254a309537 x86: Native Branch History Injection [XSA-456 version 3, CVE-2024-2201] 2024-06-03 21:39:12 +01:00
Michael Young
c762409b33 x86: Native Branch History Injection [XSA-456, CVE-2024-2201]
update to xen 4.18.2, remove patches now included upstream
2024-04-09 21:43:30 +01:00
Michael Young
4dc6f761c8 2 security updates
x86 HVM hypercalls may trigger Xen bug check [XSA-454, CVE-2023-46842]
x86: Incorrect logic for BTC/SRSO mitigations [XSA-455, CVE-2024-31142]
2024-04-09 19:25:08 +01:00
Michael Young
81b1db8227 update to xen-4.18.1 2024-03-20 19:12:09 +00:00
Michael Young
4d6e2c0007 2 security updates
x86: Register File Data Sampling [XSA-452, CVE-2023-28746]
GhostRace: Speculative Race Conditions [XSA-453, CVE-2024-2193]
2024-03-13 20:26:24 +00:00
Michael Young
ef85dabcd3 x86: shadow stack vs exceptions from emulation stubs
[XSA-451, CVE-2023-46841] (#2266326)
2024-02-27 20:02:19 +00:00
Michael Young
950832bad0 2 security updates + drop glibc32 requirement
pci: phantom functions assigned to incorrect contexts [XSA-449,
        CVE-2023-46839]
VT-d: Failure to quarantine devices in !HVM build [XSA-450,
        CVE-2023-46840]
2024-02-04 19:57:54 +00:00
Michael Young
b644c52cfa build fixes for gcc14, replace stubs-32.h requirement with glibc32 2024-02-03 09:47:57 +00:00
Fedora Release Engineering
869574bf2f Rebuilt for https://fedoraproject.org/wiki/Fedora_40_Mass_Rebuild 2024-01-27 09:30:44 +00:00
Michael Young
343a901c21 arm32: The cache may not be properly cleaned/invalidated (take two)
[XSA-447, CVE-2023-46837]
rebuild for OCaml-5.1.1
2023-12-13 17:39:02 +00:00
Michael Young
99dc35fd60 update to xen-4.18.0 2023-11-29 19:15:48 +00:00
Michael Young
b5231bddba 2 security issues
x86/AMD: mismatch in IOMMU quarantine page table levels [XSA-445,
	CVE-2023-46835]
x86: BTC/SRSO fixes not fully effective [XSA-446, CVE-2023-46836]
2023-11-14 22:32:53 +00:00
Michael Young
ad078f957f 4 security issues
xenstored: A transaction conflict can crash C Xenstored [XSA-440,
        CVE-2023-34323]
x86/AMD: missing IOMMU TLB flushing [XSA-442, CVE-2023-34326]
Multiple vulnerabilities in libfsimage disk handling [XSA-443,
        CVE-2023-34325]
x86/AMD: Debug Mask handling [XSA-444, CVE-2023-34327,
        CVE-2023-34328]
2023-10-10 21:42:36 +01:00
Michael Young
7fa4a3eee6 rebuild for OCaml 5.1 2023-10-08 12:02:22 +01:00
Michael Young
afce7b2845 3 security issues
- arm32: The cache may not be properly cleaned/invalidated [XSA-437,
        CVE-2023-34321]
- top-level shadow reference dropped too early for 64-bit PV guests
        [XSA-438, CVE-2023-34322]
- x86/AMD: Divide speculative information leak [XSA-439, CVE-2023-20588]
2023-09-26 15:20:03 +01:00
Michael Young
9f61265760 update to xen-4.17.2 which includes security updates
x86/AMD: Speculative Return Stack Overflow [XSA-434, CVE-2023-20569]
x86/Intel: Gather Data Sampling [XSA-435, CVE-2022-40982]
remove patches now included upstream
2023-08-10 19:07:43 +01:00
Michael Young
c0ff82bee4 arm: Guests can trigger a deadlock on Cortex-A77 [XSA-436, CVE-2023-34320] 2023-08-01 21:16:33 +01:00
Michael Young
ca3f59d0e3 increment Release 2023-07-31 20:53:11 +01:00
Michael Young
eb85956ccc bugfix for x86/AMD: Zenbleed [XSA-433, CVE-2023-20593] 2023-07-31 20:47:37 +01:00
Michael Young
c09e550528 add CVE reference 2023-07-26 19:46:52 +01:00
Michael Young
baa6ba2e5a adjust OCaml patch condition so eln builds work 2023-07-26 00:01:08 +01:00
Michael Young
14c61e3105 x86/AMD: Zenbleed [XSA-433]
omit OCaml 5 patch on fc38
2023-07-24 22:15:29 +01:00
Fedora Release Engineering
7669a61055 Rebuilt for https://fedoraproject.org/wiki/Fedora_39_Mass_Rebuild
Signed-off-by: Fedora Release Engineering <releng@fedoraproject.org>
2023-07-22 18:41:52 +00:00
Jerry James
70cfe51077 Add patch for OCaml 5.0.0 2023-07-10 15:55:49 -06:00
Michael Young
19ebd639fc work around a build problem with python 3.12 2023-06-27 20:32:48 +01:00
Python Maint
b65002c5bf Rebuilt for Python 3.12 2023-06-13 21:39:25 +02:00
Michael Young
f3cac52735 Mishandling of guest SSBD selection on AMD hardware
[XSA-431, CVE-2022-42336]
2023-05-16 19:21:37 +01:00
Michael Young
d6d8d8a393 update to xen-4.17.1
remove patches now included upstream
switch from patchN to patch N format for applying patches
2023-05-02 21:53:01 +01:00
Michael Young
e44f0d9ede x86 shadow paging arbitrary pointer dereference [XSA-430, CVE-2022-42335] 2023-04-25 21:24:14 +01:00
Michael Young
bf947f8f93 3 security issues (#2180425)
x86 shadow plus log-dirty mode use-after-free [XSA-427, CVE-2022-42332]
x86/HVM pinned cache attributes mis-handling [XSA-428, CVE-2022-42333,
	CVE-2022-42334]
x86: speculative vulnerability in 32bit SYSCALL path [XSA-429,
	CVE-2022-42331]
2023-03-21 17:20:08 +00:00
Michael Young
04f2270c6e use OVMF.fd from new edk2-ovmf-xen package
ovmf.bin file built from edk2-ovmf package no longer supports xen (#2170930)
2023-02-18 08:18:51 +00:00
Michael Young
cef4bbf959 x86: Cross-Thread Return Address Predictions [XSA-426, CVE-2022-27672] 2023-02-14 21:19:26 +00:00
Michael Young
d59e49c417 Guests can cause Xenstore crash via soft reset [XSA-425, CVE-2022-42330] 2023-01-25 17:36:04 +00:00
Michael Young
eadd06a27e now need BuildRequires for hostname 2023-01-24 23:45:25 +00:00
Fedora Release Engineering
e92b341446 Rebuilt for https://fedoraproject.org/wiki/Fedora_38_Mass_Rebuild
Signed-off-by: Fedora Release Engineering <releng@fedoraproject.org>
2023-01-21 07:19:34 +00:00
Michael Young
0e3619e057 build fix for gcc13 2023-01-17 22:07:23 +00:00
Michael Young
8695caf85a fix clean up of init scripts if /etc/rc.d/init.d doesn't exist 2023-01-08 09:35:06 +00:00
Michael Young
766c47c1cb python3-setuptools BuildRequires is needed for python 3.12 2022-12-20 19:55:18 +00:00
Michael Young
a54439cc72 update to xen-4.17.0
rebase xen.fedora.systemd.patch and xen.canonicalize.patch
remove or adjust patches now included or superceded upstream
/var/lib/xenstored has moved to /run/xenstored
2022-12-13 20:46:36 +00:00
Michael Young
0aca66e99a x86: Multiple speculative security issues 2022-11-08 22:29:29 +00:00
Michael Young
97374c0faa several security updates
x86: unintended memory sharing between guests [XSA-412, CVE-2022-42327]
Xenstore: Guests can crash xenstored [XSA-414, CVE-2022-42309]
Xenstore: Guests can create orphaned Xenstore nodes [XSA-415,
	CVE-2022-42310]
Xenstore: guests can let run xenstored out of memory [XSA-326,
	CVE-2022-42311, CVE-2022-42312, CVE-2022-42313, CVE-2022-42314,
	CVE-2022-42315, CVE-2022-42316, CVE-2022-42317, CVE-2022-42318]
Xenstore: Guests can cause Xenstore to not free temporary memory
	[XSA-416, CVE-2022-42319]
Xenstore: Guests can get access to Xenstore nodes of deleted domains
	[XSA-417, CVE-2022-42320]
Xenstore: Guests can crash xenstored via exhausting the stack
	[XSA-418, CVE-2022-42321]
Xenstore: Cooperating guests can create arbitrary numbers of nodes
	[XSA-419, CVE-2022-42322, CVE-2022-42323]
Oxenstored 32->31 bit integer truncation issues [XSA-420, CVE-2022-42324]
Xenstore: Guests can create arbitrary number of nodes via transactions
	[XSA-421, CVE-2022-42325, CVE-2022-42326]
2022-11-01 17:09:30 +00:00
Michael Young
ca586624b1 add bug references 2022-10-18 19:15:03 +01:00
Michael Young
ebc4dec9e2 3 security fixes
Arm: unbounded memory consumption for 2nd-level page tables [XSA-409,
        CVE-2022-33747]
P2M pool freeing may take excessively long [XSA-410, CVE-2022-33746]
lock order inversion in transitive grant copy handling [XSA-411,
        CVE-2022-33748]
2022-10-14 20:50:36 +01:00
Michael Young
136d0a1506 update to xen-4.16.2 2022-09-17 16:52:46 +01:00
Michael Young
744bd15194 add bug reference 2022-08-01 19:39:42 +01:00
Michael Young
305416ce5a insufficient TLB flush for x86 PV guests in shadow mode
[XSA-408, CVE-2022-33745]
2022-07-26 19:35:01 +01:00
Fedora Release Engineering
abd09f4c10 Rebuilt for https://fedoraproject.org/wiki/Fedora_37_Mass_Rebuild
Signed-off-by: Fedora Release Engineering <releng@fedoraproject.org>
2022-07-23 12:58:40 +00:00
Michael Young
ab3164079e Retbleed - arbitrary speculative code execution with return instructions
[XSA-407, CVE-2022-23816, CVE-2022-23825, CVE-2022-29900]
2022-07-12 21:34:09 +01:00
Michael Young
a743b10608 Add bug reference, fix CVE reference 2022-07-07 09:41:58 +01:00
Michael Young
9381fafa32 Linux disk/nic frontends data leaks
[XSA-403, CVE-2022-26365, CVE-2022-33740, CVE-2022-33741, CVE-2022-3374]
2022-07-06 12:30:05 +01:00
Michael Young
6cac8ee872 x86: MMIO Stale Data vulnerabilities
[XSA-404, CVE-2022-21123, CVE-2022-21125, CVE-2022-21166]
2022-06-21 23:12:54 +01:00
Python Maint
25f5ec29c8 Rebuilt for Python 3.11 2022-06-13 17:18:01 +02:00
Michael Young
161d5c0fe9 stop building for ix86 and armv7hl and 2 security updates
stop building for ix86 and armv7hl due to missing build dependency
x86 pv: Race condition in typeref acquisition [XSA-401, CVE-2022-26362]
x86 pv: Insufficient care with non-coherent mappings [ XSA-402,
        CVE-2022-26363, CVE-2022-26364]
2022-06-11 17:13:19 +01:00
Michael Young
7c54ce20c6 update to xen-4.16.1
strip .efi file to help EFI partitions with limited space
2022-04-14 21:06:05 +01:00
Michael Young
cac6545cdc 3 security update
Racy interactions between dirty vram tracking and paging log dirty
	hypercalls [XSA-397, CVE-2022-26356]
race in VT-d domain ID cleanup [XSA-399, CVE-2022-26357]
IOMMU: RMRR (VT-d) and unity map (AMD-Vi) handling issues [XSA-400,
	CVE-2022-26358, CVE-2022-26359, CVE-2022-26360, CVE-2022-26361]
additional patches so above applies cleanly
2022-04-05 22:06:41 +01:00
Michael Young
288b363e21 fix patch name 2022-03-21 10:12:29 +00:00
Michael Young
f1540fc363 fix build of xen*.efi file and package it in /usr/lib*/efi 2022-03-21 09:44:00 +00:00
Michael Young
d3847f2127 Multiple speculative security issues [XSA-398]
additional patches so above applies cleanly
2022-03-15 22:26:35 +00:00
Michael Young
a1bf0486e5 adjust build script and patches for gcc12 and package note support 2022-01-29 17:23:43 +00:00
Michael Young
6ccd000828 3 security updates
arm: guest_physmap_remove_page not removing the p2m mappings [XSA-393,
	CVE-2022-23033] (#2045044)
A PV guest could DoS Xen while unmapping a grant [XSA-394, CVE-2022-23034]
	(#2045042)
Insufficient cleanup of passed-through device IRQs [XSA-395,
	CVE-2022-23035] (#2045040)
2022-01-29 11:59:54 +00:00
Fedora Release Engineering
f752e6d4e7 - Rebuilt for https://fedoraproject.org/wiki/Fedora_36_Mass_Rebuild
Signed-off-by: Fedora Release Engineering <releng@fedoraproject.org>
2022-01-22 04:58:02 +00:00
Michael Young
8c923532c1 update to xen-4.16.0
don't build qemu-traditional or pv-grub by default (following upstream)
change grub module package dependencies from Suggests to Recommends
	and move to hypervisor package
rework seabios configure logic (bios.bin is no longer useful)
frontends vulnerable to backends [XSA-376] (document change only)
2022-01-10 19:46:29 +00:00
Michael Young
25ef88628b 4 security fixes
guests may exceed their designated memory limit [XSA-385, CVE-2021-28706]
PoD operations on misaligned GFNs [XSA-388, CVE-2021-28704, CVE-2021-28707
        CVE-2021-28708]
issues with partially successful P2M updates on x86 [XSA-389,
        CVE-2021-28705, CVE-2021-28709]
certain VT-d IOMMUs may not work in shared page table mode [XSA-390,
        CVE-2021-28710]
2021-11-23 18:54:02 +00:00
Michael Young
6e2824bf21 rebuild (f36 only) for OCaml 4.13.1
also fix date in changelog and add bug reference
2021-10-06 21:29:26 +01:00
Michael Young
41796d118d PCI devices with RMRRs not deassigned correctly [XSA-386, CVE-2021-28702] 2021-10-05 22:11:15 +01:00
Michael Young
7724e33e73 update to xen-4.15.1 2021-09-12 16:19:18 +01:00
Michael Young
84657107f4 add bug reference 2021-09-09 20:04:03 +01:00
Michael Young
3b4e0888e1 Another race in XENMAPSPACE_grant_table handling [XSA-384, CVE-2021-28701]
bugfix for XSA-380
stop editing grub files in /boot/efi/EFI/fedora
2021-09-08 20:58:27 +01:00
Michael Young
2a7e6767df 5 security fixes, 1 grub fix
IOMMU page mapping issues on x86 [XSA-378, CVE-2021-28694,
	CVE-2021-28695, CVE-2021-28696] (#1997531) (#1997568)
	(#1997537)
grant table v2 status pages may remain accessible after de-allocation
	[XSA-379, CVE-2021-28697] (#1997520)
long running loops in grant table handling [XSA-380, CVE-2021-28698]
	(#1997526)
inadequate grant-v2 status frames array bounds check [XSA-382,
	CVE-2021-28699] (#1997523)
xen/arm: No memory limit for dom0less domUs [XSA-383, CVE-2021-28700]
	(#1997527)
grub x86_64-efi modules now go into /boot/grub2
2021-08-25 21:28:07 +01:00
Michael Young
0fd71b054e fix build release 2021-08-13 00:22:54 +01:00
Michael Young
be07911010 work around build issue with GNU ld 2.37 2021-08-12 23:55:23 +01:00
Fedora Release Engineering
cf76d0c21e - Rebuilt for https://fedoraproject.org/wiki/Fedora_35_Mass_Rebuild
Signed-off-by: Fedora Release Engineering <releng@fedoraproject.org>
2021-07-23 21:26:33 +00:00
Michael Young
2f753f7e9b add bug references and an extra CVE 2021-06-10 21:21:02 +01:00
Michael Young
84f0fa5dbf 4 security updates
xen/arm: Boot modules are not scrubbed [XSA-372, CVE-2021-28693]
inappropriate x86 IOMMU timeout detection / handling
	[XSA-373, CVE-2021-28692]
Speculative Code Store Bypass [XSA-375, CVE-2021-0089]
x86: TSX Async Abort protections not restored after S3
	[XSA-377, CVE-2021-28690]
2021-06-08 22:20:24 +01:00
Python Maint
e525cde881 Rebuilt for Python 3.10 2021-06-04 21:20:24 +02:00
Michael Young
e48c1754f3 xen-memshare doesn't exist on armv7hl and aarch64 2021-05-05 23:27:58 +01:00
Michael Young
0736a4dbf1 update to xen-4.15.0
adjust xen.ocaml.4.12.fixes.patch to work with earlier ocaml
re-copy grub modules if they have changed
2021-05-05 22:40:31 +01:00
Michael Young
520a08e991 HVM soft-reset crashes toolstack [XSA-368, CVE-2021-28687] (#1940610)
adjust efi test to stop build failing
2021-03-19 22:19:01 +00:00
Michael Young
2ba51878a6 build fixes for OCaml 4.12.0 2021-03-02 18:46:24 +00:00
Michael Young
a8899f28f9 Add bug references 2021-02-17 21:08:18 +00:00
Michael Young
811d8e19d1 Linux: display frontend "be-alloc" mode is unsupported (comment only)
[XSA-363, CVE-2021-26934]
arm: The cache may not be cleaned for newly allocated scrubbed pages
	[XSA-364, CVE-2021-26933]
2021-02-16 22:17:42 +00:00
Michael Young
ab9408e4e3 backport upstream zstd dom0 and guest patches
add libzstd-devel BuildRequires
add weak dependency on grub modules to improve initial boot setup
2021-02-01 20:01:40 +00:00
Fedora Release Engineering
7794fedff3 - Rebuilt for https://fedoraproject.org/wiki/Fedora_34_Mass_Rebuild
Signed-off-by: Fedora Release Engineering <releng@fedoraproject.org>
2021-01-27 23:55:36 +00:00
Michael Young
5f1904ebd4 IRQ vector leak on x86 [XSA-360] 2021-01-21 20:10:24 +00:00
Michael Young
e30580581d renumber patches 2020-12-20 19:02:45 +00:00
Michael Young
05650b8adf update to xen 4.14.1 2020-12-20 18:59:11 +00:00
Michael Young
3f30b99783 fix bug references 2020-12-16 19:52:11 +00:00
Michael Young
960733fb60 multiple security updates
xenstore watch notifications lacking permission checks [XSA-115,
	CVE-2020-29480] (#1908091)
Xenstore: new domains inheriting existing node permissions [XSA-322,
	CVE-2020-29481] (#1908095)
Xenstore: wrong path length check [XSA-323, CVE-2020-29482] (#1908096)
Xenstore: guests can crash xenstored via watchs [XSA-324, CVE-2020-29484]
	(#1908088)
Xenstore: guests can disturb domain cleanup [XSA-325, CVE-2020-29483]
	(#1905648)
oxenstored memory leak in reset_watches [XSA-330, CVE-2020-29485]
	(#1908000)
undue recursion in x86 HVM context switch code [XSA-348, CVE-2020-29566]
	(#1908085)
oxenstored: node ownership can be changed by unprivileged clients
	[XSA-352, CVE-2020-29486] (#1908003)
oxenstored: permissions not checked on root node [XSA-353, CVE-2020-29479]
	(#1908003)
infinite loop when cleaning up IRQ vectors [XSA-356, CVE-2020-29567]
	(#1907932)
FIFO event channels control block related ordering [XSA-358,
	CVE-2020-29570] (#1907931)
FIFO event channels control structure ordering [XSA-359, CVE-2020-29571]
	(#1908089)
2020-12-15 23:46:04 +00:00
Jeff Law
77c10a7976 Work around another gcc-11 stringop-overflow diagnostic 2020-12-05 08:52:08 -07:00
Michael Young
34e0b01ed4 stack corruption from XSA-346 change [XSA-355] 2020-11-24 19:25:50 +00:00
Michael Young
32c79cab5f support zstd compressed kernels (dom0 only) based on linux kernel code 2020-11-23 21:43:26 +00:00
Michael Young
4d1f7dbe43 add CVE and bug reference 2020-11-12 20:24:10 +00:00
Michael Young
30f2ec4b6c Information leak via power sidechannel [XSA-351]
add make as build requires
2020-11-10 20:21:03 +00:00
Michael Young
f458ebe460 revised patch for XSA-286 (mitigating performance impact) 2020-11-03 20:48:36 +00:00
Jeff Law
6554d4f557 - Work around gcc-11 stringop-overflow diagnostics as well 2020-10-30 12:05:42 -06:00
Michael Young
a104bbcf02 x86 PV guest INVLPG-like flushes may leave stale TLB entries
[XSA-286, CVE-2020-27674] (#1891092)
simplify grub scripts (patches from Thierry Vignaud <tvignaud@redhat.com>)
some fixes for gcc 11
2020-10-28 20:46:44 +00:00
Michael Young
054f9045ad 3 security updates
x86: Race condition in Xen mapping code [XSA-345]
undue deferral of IOMMU TLB flushes [XSA-346]
unsafe AMD IOMMU page table updates [XSA-347]
2020-10-20 18:52:27 +01:00
Michael Young
4cbc5a57f1 add more CVE references 2020-09-22 19:54:18 +01:00
Michael Young
205c567efb add CVE references 2020-09-22 19:27:40 +01:00
Michael Young
6594c32499 10 security updates
x86 pv: Crash when handling guest access to MSR_MISC_ENABLE [XSA-333,
	CVE-2020-25602]
Missing unlock in XENMEM_acquire_resource error path [XSA-334,
	CVE-2020-25598]
race when migrating timers between x86 HVM vCPU-s [XSA-336,
	CVE-2020-25604]
PCI passthrough code reading back hardware registers [XSA-337,
	CVE-2020-25595]
once valid event channels may not turn invalid [XSA-338, CVE-2020-25597]
x86 pv guest kernel DoS via SYSENTER [XSA-339, CVE-2020-25596]
Missing memory barriers when accessing/allocating an event channel [XSA-340,
	CVE-2020-25603]
out of bounds event channels available to 32-bit x86 domains [XSA-342,
	CVE-2020-25600]
races with evtchn_reset() [XSA-343, CVE-2020-25599]
lack of preemption in evtchn_reset() / evtchn_destroy() [XSA-344,
	CVE-2020-25601]
2020-09-22 17:23:20 +01:00
Michael Young
066167cb69 rebuild for OCaml 4.11.1 2020-09-03 21:05:20 +01:00
Michael Young
3ba0708ee8 QEMU: usb: out-of-bounds r/w access issue [XSA-335, CVE-2020-14364]
(#1871850)
2020-08-24 23:40:18 +01:00
Fedora Release Engineering
62a55dab2d - Rebuilt for https://fedoraproject.org/wiki/Fedora_33_Mass_Rebuild
Signed-off-by: Fedora Release Engineering <releng@fedoraproject.org>
2020-07-29 14:35:36 +00:00
Michael Young
f15c128730 update to xen-4.14.0 2020-07-26 17:17:25 +01:00
Tom Stellard
5c5498aae8 Use make macros
https://fedoraproject.org/wiki/Changes/UseMakeBuildInstallMacro
2020-07-14 14:55:13 +00:00
Michael Young
9d8391a472 5 security updates
incorrect error handling in event channel port allocation leads to
	DoS [XSA-317, CVE-2020-15566] (#1854465)
inverted code paths in x86 dirty VRAM tracking leads to DoS
	[XSA-319, CVE-2020-15563] (#1854463)
xen: insufficient cache write-back under VT-d leads to DoS
	[XSA-321, CVE-2020-15565] (#1854467)
missing alignment check in VCPUOP_register_vcpu_info leads to DoS
	[XSA-327, CVE-2020-15564] (#1854458)
non-atomic modification of live EPT PTE leads to DoS
	[XSA-328, CVE-2020-15567] (#1854464)
2020-07-07 19:01:41 +01:00
Jeff Law
0e913fb9ea Disable LTO 2020-06-30 14:09:07 -06:00
Michael Young
a23d05f0ce Special Register Buffer speculative side channel [XSA-320] 2020-06-10 19:03:53 +01:00
Miro Hrončok
4dbcf4d3f7 Rebuilt for Python 3.9 2020-05-26 03:55:27 +02:00
Michael Young
5b7f356ae7 update to xen-4.13.1 2020-05-19 19:10:34 +01:00
Michael Young
b801938d78 build aarch64 hypervisor with -mno-outline-atomics to fix gcc 10 build 2020-05-05 21:55:53 +01:00
Michael Young
e6b8299a36 4 security updates
multiple xenoprof issues [XSA-313, CVE-2020-11740, CVE-2020-11741]
	(#1823912, #1823914)
Missing memory barriers in read-write unlock paths [XSA-314,
	CVE-2020-11739] (#1823784)
Bad error path in GNTTABOP_map_grant [XSA-316, CVE-2020-11743] (#1823926)
Bad continuation handling in GNTTABOP_copy [XSA-318, CVE-2020-11742]
	(#1823943)
2020-04-14 22:37:54 +01:00
Michael Young
b64e04acdf fix issues in pygrub dependency found by python 3.8 2020-03-17 19:50:04 +00:00
Michael Young
fa37c9fcb0 try setting --with-system-ipxe to a rom file (dir doesn't work)
add weak depends on ipxe-roms-qemu and qemu-system-x86-core
2020-03-10 10:09:58 +00:00
Fedora Release Engineering
1e9fc415c6 - Rebuilt for https://fedoraproject.org/wiki/Fedora_32_Mass_Rebuild
Signed-off-by: Fedora Release Engineering <releng@fedoraproject.org>
2020-01-31 04:16:50 +00:00
Michael Young
05b5d868bc build fixes for OCaml 4.10.0 and gcc 10 2020-01-22 22:40:26 +00:00
Michael Young
b1a2540d9f arm: a CPU may speculate past the ERET instruction [XSA-312]
use more explicit library names
add weak requires for perl (/etc/xen/scripts/locking.sh)
2020-01-14 19:51:54 +00:00
Michael Young
75bef3ece1 update to xen-4.13.0 2019-12-18 20:12:13 +00:00
Michael Young
7fc59869cb fix build with OCaml 4.09.0 2019-12-15 19:03:55 +00:00
Michael Young
8a43935ac4 correct the correction to the bug reference 2019-12-12 00:25:50 +00:00
Michael Young
5f01f1feca fix a bug reference 2019-12-12 00:22:46 +00:00
Michael Young
e4c797f0d8 5 security fixes
denial of service in find_next_bit() [XSA-307, CVE-2019-19581,
        CVE-2019-19582] (#1780559)
denial of service in HVM/PVH guest userspace code [XSA-308,
        CVE-2019-19583] (#1782206)
privilege escalation due to malicious PV guest [XSA-309, CVE-2019-19578]
        (#1782210)
Further issues with restartable PV type change operations [XSA-310,
        CVE-2019-19580] (#1782207)
vulnerability in dynamic height handling for AMD IOMMU pagetables
        [XSA-311, CVE-2019-19577] (#1782208)
2019-12-11 22:41:13 +00:00
Michael Young
b6c6fc0ef1 Device quarantine for alternate pci assignment methods [XSA-306] 2019-11-26 18:34:05 +00:00
Michael Young
3b402adc22 add missing XSA-299 patches 2019-11-12 22:27:28 +00:00
Michael Young
e1f73cd699 2 security fixes
x86: Machine Check Error on Page Size Change DoS [XSA-304, CVE-2018-12207]
TSX Asynchronous Abort speculative side channel [XSA-305, CVE-2019-11135]
2019-11-12 20:25:31 +00:00
Michael Young
181c01aee5 add CVE and bugzilla references 2019-11-12 20:14:31 +00:00
Michael Young
0b616dfcac add CVE references 2019-11-01 18:33:39 +00:00
Michael Young
ed166e2fa9 6 security fixes
VCPUOP_initialise DoS [XSA-296, CVE-2019-18420]
missing descriptor table limit checking in x86 PV emulation [XSA-298,
	CVE-2019-18425]
Issues with restartable PV type change operations [XSA-299, CVE-2019-18421]
add-to-physmap can be abused to DoS Arm hosts [XSA-301, CVE-2019-18423]
passed through PCI devices may corrupt host memory after deassignment
	[XSA-302, CVE-2019-18424]
ARM: Interrupts are unconditionally unmasked in exception handlers
	[XSA-303, CVE-2019-18422]
2019-10-31 20:47:20 +00:00
Miro Hrončok
9e7881994e Rebuilt for Python 3.8.0rc1 (#1748018) 2019-10-03 14:41:52 +02:00
Miro Hrončok
a5572496fb Rebuilt for Python 3.8 2019-08-19 11:09:49 +02:00
Michael Young
8e8503393c update to xen-4.12.1 2019-08-09 18:15:22 +01:00
Fedora Release Engineering
9aac9aad77 - Rebuilt for https://fedoraproject.org/wiki/Fedora_31_Mass_Rebuild
Signed-off-by: Fedora Release Engineering <releng@fedoraproject.org>
2019-07-27 04:01:59 +00:00
Michael Young
fcaf32cd71 some debug files are now properly packaged in debuginfo rpms 2019-06-19 19:36:49 +01:00
Michael Young
7829dfecf9 Unlimited Arm Atomics Operations [XSA-295] (#1720760) 2019-06-18 20:21:13 +01:00
c362e0407d Fix build with python3.8 2019-06-18 15:49:10 +02:00
Michael Young
0b88acdac0 fix HVM DomU boot on some chipsets
fix expected FTBFS with Python 3.8 (#1704807)
adjust grub2 workaround
2019-06-02 00:17:26 +01:00
Michael Young
6ea38f207f Microarchitectural Data Sampling speculative side channel [XSA-297,
CVE-2018-12126, CVE-2018-12127, CVE-2018-12130, CVE-2019-11091]
additional patches so above applies cleanly
work around grub2 issues in dom0
2019-05-14 21:53:52 +01:00
Michael Young
852b076a0e drop systemd_postun and renumber patches 2019-04-05 21:08:20 +01:00
Michael Young
995f98f000 switch from python2 to python3 2019-04-05 20:55:26 +01:00
Michael Young
ba63a02fbc remove traces of efiming and efi_flags logic from spec file 2019-04-04 21:00:20 +01:00
Michael Young
937578a14e update to xen-4.12.0 2019-04-04 20:48:28 +01:00
Michael Young
593eb17437 xen: various flaws (#1685577)
grant table transfer issues on large hosts [XSA-284]
race with pass-through device hotplug [XSA-285]
x86: steal_page violates page_struct access discipline [XSA-287]
x86: Inconsistent PV IOMMU discipline [XSA-288]
missing preemption in x86 PV page table unvalidation [XSA-290]
x86/PV: page type reference counting issue with failed IOMMU update [XSA-291]
x86: insufficient TLB flushing when using PCID [XSA-292]
x86: PV kernel context switch corruption [XSA-293]
x86 shadow: Insufficient TLB flushing when using PCID [XSA-294]
2019-03-05 21:29:30 +00:00
Michael Young
6c22ec879a add gcc9 build fixes 2019-02-14 23:42:45 +00:00
Fedora Release Engineering
a9fcba2c11 - Rebuilt for https://fedoraproject.org/wiki/Fedora_30_Mass_Rebuild
Signed-off-by: Fedora Release Engineering <releng@fedoraproject.org>
2019-02-03 12:15:30 +00:00
e03e4d3811 Remove obsolete Group tag
References: https://fedoraproject.org/wiki/Changes/Remove_Group_Tag
2019-01-28 20:24:55 +01:00
Michael Young
b5b754ce6a add CVE reference 2019-01-08 22:44:44 +00:00
Michael Young
fbe16bba56 add CVE references 2018-12-12 12:34:08 +00:00
Michael Young
7b4d0d1171 - update to 4.11.1
remove patches for issues now fixed upstream
  adjust xen.use.fedora.ipxe.patch
- only include qemutrad build requirements for platforms that use it
- construct ovmf.bin from edk2-ovmf package (#1656651)
2018-12-11 17:16:08 +00:00
Michael Young
bae3b798c8 add bug references 2018-11-21 18:31:34 +00:00
Michael Young
834ca81402 insufficient TLB flushing / improper large page mappings with AMD IOMMUs
[XSA-275] (#1651665)
resource accounting issues in x86 IOREQ server handling [XSA-276]
x86: incorrect error handling for guest p2m page removals [XSA-277]
x86: DoS from attempting to use INVPCID with a non-canonical addresses
	[XSA-279]
Fix for XSA-240 conflicts with shadow paging [XSA-280]
2018-11-20 14:45:36 +00:00
Michael Young
c3ca819bab guest use of HLE constructs may lock up host [XSA-282] 2018-11-06 19:45:46 +00:00
Michael Young
fb94fb22a3 add bug reference 2018-10-25 19:48:07 +01:00
Michael Young
83a7abe677 x86: Nested VT-x usable even when disabled [XSA-278] 2018-10-24 23:16:51 +01:00
Peter Robinson
476f568d2e drop chkconfig, no longer needed due to systemd 2018-10-14 19:38:33 +01:00
Michael Young
06b9276964 set /usr/bin/python2 at the start of another python script 2018-09-18 22:27:42 +01:00
Michael Young
51cdff244e move pkgconfig files to xen-devel (#1629643) 2018-09-18 21:33:23 +01:00
Michael Young
ccb3d5f799 set /usr/bin/python2 at the start of some python scripts
add some CVE references
2018-09-12 19:35:48 +01:00
Michael Young
57295488a1 move creation of /usr/lib/xen symlink to posttrans to avoid rpm conflict 2018-08-23 21:47:16 +01:00
Michael Young
a6bb4c145b move files from /usr/lib/xen to /usr/libexec/xen 2018-08-17 21:36:44 +01:00
Michael Young
03a5477b96 replace use of deprecated vwprintw
add bug references
2018-08-14 23:11:13 +01:00
Michael Young
c6bfd9a2dd L1 Terminal Fault speculative side channel patch bundle [XSA-273,
CVE-2018-3620, CVE-2018-3646]
Use of v2 grant tables may cause crash on ARM [XSA-268]
x86: Incorrect MSR_DEBUGCTL handling lets guests enable BTS [XSA-269]
oxenstored does not apply quota-maxentity [XSA-272]
no longer need to set python_sitearch
2018-08-14 21:00:08 +01:00
43fce97b00
%{python_sitearch} → %{python2_sitearch}
Signed-off-by: Igor Gnatenko <ignatenkobrain@fedoraproject.org>
2018-07-30 00:22:21 +02:00
Michael Young
86492e72ca build fixes
i686 now want to build EFI hypervisor (actually x86_64) so let it
2018-07-12 19:39:22 +01:00
Michael Young
fd9d08821d adjustments now /usr/bin/python is in a separate package
update hypervisor configuration for arm
2018-07-11 00:03:08 +01:00
Michael Young
a63e14184f replace use of deprecated brctl command (#1588712)
add gcc BuildRequires
2018-07-10 19:23:50 +01:00
Michael Young
8dcf680a4d update to xen-4.11.0 2018-07-10 18:35:39 +01:00
Jason Tibbitts
52ff364dd3 Remove needless use of %defattr 2018-07-09 23:54:03 -05:00
110 changed files with 6031 additions and 6266 deletions

3
.gitignore vendored
View file

@ -6,4 +6,5 @@ lwip-1.3.0.tar.gz
pciutils-2.2.9.tar.bz2
zlib-1.2.3.tar.gz
polarssl-1.1.4-gpl.tgz
/xen-4.10.1.tar.gz
/mini-os-4.21.0.tar.xz
/xen-4.21.1.tar.xz

View file

@ -1,11 +0,0 @@
--- xen-4.4.1/tools/qemu-xen-traditional/hw/virtio-net.c.orig 2014-07-02 15:54:37.000000000 +0100
+++ xen-4.4.1/tools/qemu-xen-traditional/hw/virtio-net.c 2014-11-18 20:50:13.593122915 +0000
@@ -192,7 +192,7 @@
return VIRTIO_NET_ERR;
if (mac_data.entries) {
- if (n->mac_table.in_use + mac_data.entries <= MAC_TABLE_ENTRIES) {
+ if (n->mac_table.in_use <= MAC_TABLE_ENTRIES - mac_data.entries) {
memcpy(n->mac_table.macs + (n->mac_table.in_use * ETH_ALEN),
elem->out_sg[2].iov_base + sizeof(mac_data),
mac_data.entries * ETH_ALEN);

View file

@ -1,11 +0,0 @@
--- xen-4.5.1/tools/qemu-xen-traditional/hw/ne2000.c.orig 2015-09-26 17:27:49.494334726 +0100
+++ xen-4.5.1/tools/qemu-xen-traditional/hw/ne2000.c 2015-09-26 17:31:53.107474932 +0100
@@ -331,7 +331,7 @@
if (index <= s->stop)
avail = s->stop - index;
else
- avail = 0;
+ break;
len = size;
if (len > avail)
len = avail;

View file

@ -1,48 +0,0 @@
--- xen-4.5.1/tools/qemu-xen-traditional/hw/ne2000.c.orig 2015-06-09 16:32:24.000000000 +0100
+++ xen-4.5.1/tools/qemu-xen-traditional/hw/ne2000.c 2015-09-26 17:27:49.494334726 +0100
@@ -304,6 +304,9 @@
}
index = s->curpag << 8;
+ if (index >= NE2000_PMEM_END) {
+ index = s->start;
+ }
/* 4 bytes for header */
total_len = size + 4;
/* address for next packet (4 bytes for CRC) */
@@ -387,15 +390,21 @@
offset = addr | (page << 4);
switch(offset) {
case EN0_STARTPG:
- s->start = val << 8;
+ if (val << 8 <= NE2000_PMEM_END) {
+ s->start = val << 8;
+ }
s->tainted = 1;
break;
case EN0_STOPPG:
- s->stop = val << 8;
+ if (val << 8 <= NE2000_PMEM_END) {
+ s->stop = val << 8;
+ }
s->tainted = 1;
break;
case EN0_BOUNDARY:
- s->boundary = val;
+ if (val << 8 < NE2000_PMEM_END) {
+ s->boundary = val;
+ }
break;
case EN0_IMR:
s->imr = val;
@@ -436,7 +445,9 @@
s->phys[offset - EN1_PHYS] = val;
break;
case EN1_CURPAG:
- s->curpag = val;
+ if (val << 8 < NE2000_PMEM_END) {
+ s->curpag = val;
+ }
s->tainted = 1;
break;
case EN1_MULT ... EN1_MULT + 7:

View file

@ -1,12 +0,0 @@
--- xen-4.5.1/tools/qemu-xen-traditional/hw/e1000.c.orig 2015-06-09 16:32:24.000000000 +0100
+++ xen-4.5.1/tools/qemu-xen-traditional/hw/e1000.c 2015-09-26 17:16:36.406544380 +0100
@@ -461,7 +461,8 @@
memmove(tp->data, tp->header, hdr);
tp->size = hdr;
}
- } while (split_size -= bytes);
+ split_size -= bytes;
+ } while (bytes && split_size);
} else if (!tp->tse && tp->cptse) {
// context descriptor TSE is not set, while data descriptor TSE is set
DBGOUT(TXERR, "TCP segmentaion Error\n");

View file

@ -1,63 +0,0 @@
--- xen-4.5.1/tools/qemu-xen-traditional/hw/virtio.c.orig 2015-06-09 16:32:24.000000000 +0100
+++ xen-4.5.1/tools/qemu-xen-traditional/hw/virtio.c 2015-10-10 16:57:01.806370020 +0100
@@ -268,8 +268,8 @@
return vring_avail_idx(vq) == vq->last_avail_idx;
}
-void virtqueue_fill(VirtQueue *vq, const VirtQueueElement *elem,
- unsigned int len, unsigned int idx)
+static void virtqueue_unmap_sg(VirtQueue *vq, const VirtQueueElement *elem,
+ unsigned int len)
{
unsigned int offset;
int i;
@@ -302,7 +302,19 @@
offset += size;
}
+}
+void virtqueue_discard(VirtQueue *vq, const VirtQueueElement *elem,
+ unsigned int len)
+{
+ vq->last_avail_idx--;
+ virtqueue_unmap_sg(vq, elem, len);
+}
+
+void virtqueue_fill(VirtQueue *vq, const VirtQueueElement *elem,
+ unsigned int len, unsigned int idx)
+{
+ virtqueue_unmap_sg(vq, elem, len);
idx = (idx + vring_used_idx(vq)) % vq->vring.num;
/* Get a pointer to the next entry in the used ring. */
--- xen-4.5.1/tools/qemu-xen-traditional/hw/virtio.h.orig 2015-06-09 16:32:24.000000000 +0100
+++ xen-4.5.1/tools/qemu-xen-traditional/hw/virtio.h 2015-10-10 16:57:53.146216039 +0100
@@ -105,6 +105,8 @@
void virtqueue_push(VirtQueue *vq, const VirtQueueElement *elem,
unsigned int len);
void virtqueue_flush(VirtQueue *vq, unsigned int count);
+void virtqueue_discard(VirtQueue *vq, const VirtQueueElement *elem,
+ unsigned int len);
void virtqueue_fill(VirtQueue *vq, const VirtQueueElement *elem,
unsigned int len, unsigned int idx);
--- xen-4.5.1/tools/qemu-xen-traditional/hw/virtio-net.c.orig 2015-10-10 16:10:05.071786348 +0100
+++ xen-4.5.1/tools/qemu-xen-traditional/hw/virtio-net.c 2015-10-10 19:05:34.510029916 +0100
@@ -424,11 +424,15 @@
len = iov_fill(sg, elem.in_num,
buf + offset, size - offset);
total += len;
+ offset += len;
+ if (!n->mergeable_rx_bufs && offset < size) {
+ virtqueue_discard(n->rx_vq, &elem, total);
+ return;
+ }
/* signal other side */
virtqueue_fill(n->rx_vq, &elem, total, i++);
- offset += len;
}
if (mhdr)

View file

@ -1,37 +0,0 @@
From 8b98a2f07175d46c3f7217639bd5e03f2ec56343 Mon Sep 17 00:00:00 2001
From: Jason Wang <jasowang@redhat.com>
Date: Mon, 30 Nov 2015 15:00:06 +0800
Subject: [PATCH] pcnet: fix rx buffer overflow(CVE-2015-7512)
Backends could provide a packet whose length is greater than buffer
size. Check for this and truncate the packet to avoid rx buffer
overflow in this case.
Cc: Prasad J Pandit <pjp@fedoraproject.org>
Cc: qemu-stable@nongnu.org
Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
Signed-off-by: Jason Wang <jasowang@redhat.com>
---
tools/qemu-xen-traditional/hw/pcnet.c | 6 ++++++
1 files changed, 6 insertions(+), 0 deletions(-)
diff --git a/tools/qemu-xen-traditional/hw/pcnet.c b/tools/qemu-xen-traditional/hw/pcnet.c
index 309c40b..1f4a3db 100644
--- a/tools/qemu-xen-traditional/hw/pcnet.c
+++ b/tools/qemu-xen-traditional/hw/pcnet.c
@@ -1064,6 +1064,12 @@ ssize_t pcnet_receive(NetClientState *nc, const uint8_t *buf, size_t size_)
int pktcount = 0;
if (!s->looptest) {
+ if (size > 4092) {
+#ifdef PCNET_DEBUG_RMD
+ fprintf(stderr, "pcnet: truncates rx packet.\n");
+#endif
+ size = 4092;
+ }
memcpy(src, buf, size);
/* no need to compute the CRC */
src[size] = 0;
--
1.7.0.4

View file

@ -1,38 +0,0 @@
From 00837731d254908a841d69298a4f9f077babaf24 Mon Sep 17 00:00:00 2001
From: Stefan Weil <sw@weilnetz.de>
Date: Fri, 20 Nov 2015 08:42:33 +0100
Subject: [PATCH] eepro100: Prevent two endless loops
http://lists.nongnu.org/archive/html/qemu-devel/2015-11/msg04592.html
shows an example how an endless loop in function action_command can
be achieved.
During my code review, I noticed a 2nd case which can result in an
endless loop.
Reported-by: Qinghao Tang <luodalongde@gmail.com>
Signed-off-by: Stefan Weil <sw@weilnetz.de>
Signed-off-by: Jason Wang <jasowang@redhat.com>
---
tools/qemu-xen-traditional/hw/eepro100.c | 16 ++++++++++++++++
1 files changed, 16 insertions(+), 0 deletions(-)
diff --git a/tools/qemu-xen-traditional/hw/eepro100.c b/tools/qemu-xen-traditional/hw/eepro100.c
index 60333b7..685a478 100644
--- a/tools/qemu-xen-traditional/hw/eepro100.c
+++ b/tools/qemu-xen-traditional/hw/eepro100.c
@@ -774,6 +774,11 @@ static void tx_command(EEPRO100State *s)
uint32_t tx_buffer_address = ldl_phys(tbd_address);
uint16_t tx_buffer_size = lduw_phys(tbd_address + 4);
//~ uint16_t tx_buffer_el = lduw_phys(tbd_address + 6);
+ if (tx_buffer_size == 0) {
+ /* Prevent an endless loop. */
+ logout("loop in %s:%u\n", __FILE__, __LINE__);
+ break;
+ }
tbd_address += 8;
logout
("TBD (simplified mode): buffer address 0x%08x, size 0x%04x\n",
--
1.7.0.4

View file

@ -1,44 +0,0 @@
From 4c65fed8bdf96780735dbdb92a8bd0d6b6526cc3 Mon Sep 17 00:00:00 2001
From: Prasad J Pandit <pjp@fedoraproject.org>
Date: Thu, 3 Dec 2015 18:54:17 +0530
Subject: [PATCH] ui: vnc: avoid floating point exception
While sending 'SetPixelFormat' messages to a VNC server,
the client could set the 'red-max', 'green-max' and 'blue-max'
values to be zero. This leads to a floating point exception in
write_png_palette while doing frame buffer updates.
Reported-by: Lian Yihan <lianyihan@360.cn>
Signed-off-by: Prasad J Pandit <pjp@fedoraproject.org>
Reviewed-by: Gerd Hoffmann <kraxel@redhat.com>
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
tools/qemu-xen-traditional/vnc.c | 6 +++---
1 files changed, 3 insertions(+), 3 deletions(-)
diff --git a/tools/qemu-xen-traditional/vnc.c b/tools/qemu-xen-traditional/vnc.c
index 7538405..cbe4d33 100644
--- a/tools/qemu-xen-traditional/vnc.c
+++ b/tools/qemu-xen-traditional/vnc.c
@@ -2198,15 +2198,15 @@ static void set_pixel_format(VncState *vs,
}
vs->clientds = vs->serverds;
- vs->clientds.pf.rmax = red_max;
+ vs->clientds.pf.rmax = red_max ? red_max : 0xFF;
count_bits(vs->clientds.pf.rbits, red_max);
vs->clientds.pf.rshift = red_shift;
vs->clientds.pf.rmask = red_max << red_shift;
- vs->clientds.pf.gmax = green_max;
+ vs->clientds.pf.gmax = green_max ? green_max : 0xFF;
count_bits(vs->clientds.pf.gbits, green_max);
vs->clientds.pf.gshift = green_shift;
vs->clientds.pf.gmask = green_max << green_shift;
- vs->clientds.pf.bmax = blue_max;
+ vs->clientds.pf.bmax = blue_max ? blue_max : 0xFF;
count_bits(vs->clientds.pf.bbits, blue_max);
vs->clientds.pf.bshift = blue_shift;
vs->clientds.pf.bmask = blue_max << blue_shift;
--
1.7.0.4

View file

@ -1,30 +0,0 @@
--- xen-4.6.1/tools/qemu-xen-traditional/hw/fw_cfg.c.orig 2016-01-04 15:35:42.000000000 +0000
+++ xen-4.6.1/tools/qemu-xen-traditional/hw/fw_cfg.c 2016-03-06 16:42:33.464296362 +0000
@@ -54,11 +54,15 @@
static void fw_cfg_write(FWCfgState *s, uint8_t value)
{
int arch = !!(s->cur_entry & FW_CFG_ARCH_LOCAL);
- FWCfgEntry *e = &s->entries[arch][s->cur_entry & FW_CFG_ENTRY_MASK];
+ FWCfgEntry *e = (s->cur_entry == FW_CFG_INVALID) ? NULL :
+ &s->entries[arch][s->cur_entry & FW_CFG_ENTRY_MASK];
FW_CFG_DPRINTF("write %d\n", value);
- if (s->cur_entry & FW_CFG_WRITE_CHANNEL && s->cur_offset < e->len) {
+ if (s->cur_entry & FW_CFG_WRITE_CHANNEL
+ && e != NULL
+ && e->callback
+ && s->cur_offset < e->len) {
e->data[s->cur_offset++] = value;
if (s->cur_offset == e->len) {
e->callback(e->callback_opaque, e->data);
@@ -88,7 +92,8 @@
static uint8_t fw_cfg_read(FWCfgState *s)
{
int arch = !!(s->cur_entry & FW_CFG_ARCH_LOCAL);
- FWCfgEntry *e = &s->entries[arch][s->cur_entry & FW_CFG_ENTRY_MASK];
+ FWCfgEntry *e = (s->cur_entry == FW_CFG_INVALID) ? NULL :
+ &s->entries[arch][s->cur_entry & FW_CFG_ENTRY_MASK];
uint8_t ret;
if (s->cur_entry == FW_CFG_INVALID || !e->data || s->cur_offset >= e->len)

View file

@ -1,104 +0,0 @@
------------------------------------------------------------------------
*From*: Laszlo Ersek
*Subject*: [Qemu-devel] [PATCH] e1000: eliminate infinite loops on
out-of-bounds transfer start
*Date*: Tue, 19 Jan 2016 14:17:20 +0100
------------------------------------------------------------------------
The start_xmit() and e1000_receive_iov() functions implement DMA transfers
iterating over a set of descriptors that the guest's e1000 driver
prepares:
- the TDLEN and RDLEN registers store the total size of the descriptor
area,
- while the TDH and RDH registers store the offset (in whole tx / rx
descriptors) into the area where the transfer is supposed to start.
Each time a descriptor is processed, the TDH and RDH register is bumped
(as appropriate for the transfer direction).
QEMU already contains logic to deal with bogus transfers submitted by the
guest:
- Normally, the transmit case wants to increase TDH from its initial value
to TDT. (TDT is allowed to be numerically smaller than the initial TDH
value; wrapping at or above TDLEN bytes to zero is normal.) The failsafe
that QEMU currently has here is a check against reaching the original
TDH value again -- a complete wraparound, which should never happen.
- In the receive case RDH is increased from its initial value until
"total_size" bytes have been received; preferably in a single step, or
in "s->rxbuf_size" byte steps, if the latter is smaller. However, null
RX descriptors are skipped without receiving data, while RDH is
incremented just the same. QEMU tries to prevent an infinite loop
(processing only null RX descriptors) by detecting whether RDH assumes
its original value during the loop. (Again, wrapping from RDLEN to 0 is
normal.)
What both directions miss is that the guest could program TDLEN and RDLEN
so low, and the initial TDH and RDH so high, that these registers will
immediately be truncated to zero, and then never reassume their initial
values in the loop -- a full wraparound will never occur.
The condition that expresses this is:
xdh_start >= s->mac_reg[XDLEN] / sizeof(desc)
i.e., TDH or RDH start out after the last whole rx or tx descriptor that
fits into the TDLEN or RDLEN sized area.
This condition could be checked before we enter the loops, but
pci_dma_read() / pci_dma_write() knows how to fill in buffers safely for
bogus DMA addresses, so we just extend the existing failsafes with the
above condition.
Cc: "Michael S. Tsirkin" <address@hidden>
Cc: Petr Matousek <address@hidden>
Cc: Stefano Stabellini <address@hidden>
Cc: Prasad Pandit <address@hidden>
Cc: Michael Roth <address@hidden>
Cc: Jason Wang <address@hidden>
RHBZ: https://bugzilla.redhat.com/show_bug.cgi?id=1296044
Signed-off-by: Laszlo Ersek <address@hidden>
Reviewed-by: Jason Wang <address@hidden>
---
Notes:
Regarding the public posting: we made an honest effort to vet this
vulnerability, and the impact seems low -- no host side reads/writes,
"just" a DoS (infinite loop). We decided the patch could be posted
publicly, for the usual review process. Jason and Prasad checked the
patch in the internal discussion already, but comments, improvements
etc. are clearly welcome. The CVE request is underway. Thanks.
hw/net/e1000.c | 6 ++++--
1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/hw/net/e1000.c b/hw/net/e1000.c
index bec06e9..34d0823 100644
--- a/tools/qemu-xen-traditional/hw/e1000.c
+++ b/tools/qemu-xen-traditional/hw/e1000.c
@@ -908,7 +908,8 @@ start_xmit(E1000State *s)
* bogus values to TDT/TDLEN.
* there's nothing too intelligent we could do about this.
*/
- if (s->mac_reg[TDH] == tdh_start) {
+ if (s->mac_reg[TDH] == tdh_start ||
+ tdh_start >= s->mac_reg[TDLEN] / sizeof(desc)) {
DBGOUT(TXERR, "TDH wraparound @%x, TDT %x, TDLEN %x\n",
tdh_start, s->mac_reg[TDT], s->mac_reg[TDLEN]);
break;
@@ -1165,7 +1166,8 @@ e1000_receive_iov(NetClientState *nc, const struct iovec *iov, int iovcnt)
s->mac_reg[RDH] = 0;
s->check_rxov = 1;
/* see comment in start_xmit; same here */
- if (s->mac_reg[RDH] == rdh_start) {
+ if (s->mac_reg[RDH] == rdh_start ||
+ rdh_start >= s->mac_reg[RDLEN] / sizeof(desc)) {
DBGOUT(RXERR, "RDH wraparound @%x, RDT %x, RDLEN %x\n",
rdh_start, s->mac_reg[RDT], s->mac_reg[RDLEN]);
set_ics(s, 0, E1000_ICS_RXO);
--
1.8.3.1

View file

@ -1,56 +0,0 @@
From: Prasad J Pandit <address@hidden>
When processing remote NDIS control message packets,
the USB Net device emulator uses a fixed length(4096) data buffer.
The incoming informationBufferOffset & Length combination could
overflow and cross that range. Check control message buffer
offsets and length to avoid it.
Reported-by: Qinghao Tang <address@hidden>
Signed-off-by: Prasad J Pandit <address@hidden>
---
hw/usb/dev-network.c | 9 ++++++---
1 file changed, 6 insertions(+), 3 deletions(-)
Update as per review
-> https://lists.gnu.org/archive/html/qemu-devel/2016-02/msg03475.html
diff --git a/hw/usb/dev-network.c b/hw/usb/dev-network.c
index 8a4ff49..180adce 100644
--- a/tools/qemu-xen-traditional/hw/usb-net.c
+++ b/tools/qemu-xen-traditional/hw/usb-net.c
@@ -915,8 +915,9 @@ static int rndis_query_response(USBNetState *s,
bufoffs = le32_to_cpu(buf->InformationBufferOffset) + 8;
buflen = le32_to_cpu(buf->InformationBufferLength);
- if (bufoffs + buflen > length)
+ if (buflen > length || bufoffs >= length || bufoffs + buflen > length) {
return USB_RET_STALL;
+ }
infobuflen = ndis_query(s, le32_to_cpu(buf->OID),
bufoffs + (uint8_t *) buf, buflen, infobuf,
@@ -961,8 +962,9 @@ static int rndis_set_response(USBNetState *s,
bufoffs = le32_to_cpu(buf->InformationBufferOffset) + 8;
buflen = le32_to_cpu(buf->InformationBufferLength);
- if (bufoffs + buflen > length)
+ if (buflen > length || bufoffs >= length || bufoffs + buflen > length) {
return USB_RET_STALL;
+ }
ret = ndis_set(s, le32_to_cpu(buf->OID),
bufoffs + (uint8_t *) buf, buflen);
@@ -1212,8 +1214,9 @@ static void usb_net_handle_dataout(USBNetState *s, USBPacket *p)
if (le32_to_cpu(msg->MessageType) == RNDIS_PACKET_MSG) {
uint32_t offs = 8 + le32_to_cpu(msg->DataOffset);
uint32_t size = le32_to_cpu(msg->DataLength);
- if (offs + size <= len)
+ if (offs < len && size < len && offs + size <= len) {
qemu_send_packet(s->vc, s->out_buf + offs, size);
+ }
}
s->out_ptr -= len;
memmove(s->out_buf, &s->out_buf[len], s->out_ptr);
--
2.5.0

View file

@ -1,34 +0,0 @@
From: Prasad J Pandit <address@hidden>
Ne2000 NIC uses ring buffer of NE2000_MEM_SIZE(49152)
bytes to process network packets. Registers PSTART & PSTOP
define ring buffer size & location. Setting these registers
to invalid values could lead to infinite loop or OOB r/w
access issues. Add check to avoid it.
Reported-by: Yang Hongke <address@hidden>
Signed-off-by: Prasad J Pandit <address@hidden>
---
hw/net/ne2000.c | 4 ++++
1 file changed, 4 insertions(+)
Update per review:
-> https://lists.gnu.org/archive/html/qemu-devel/2016-02/msg05522.html
diff --git a/hw/net/ne2000.c b/hw/net/ne2000.c
index b032212..ced4666 100644
--- a/tools/qemu-xen-traditional/hw/ne2000.c
+++ b/tools/qemu-xen-traditional/hw/ne2000.c
@@ -154,6 +154,10 @@ static int ne2000_buffer_full(NE2000State *s)
{
int avail, index, boundary;
+ if (s->stop <= s->start) {
+ return 1;
+ }
+
index = s->curpag << 8;
boundary = s->boundary << 8;
if (index < boundary)
--
2.5.0

View file

@ -1,45 +0,0 @@
From: Prasad J Pandit <address@hidden>
While computing IP checksum, 'net_checksum_calculate' reads
payload length from the packet. It could exceed the given 'data'
buffer size. Add a check to avoid it.
Reported-by: Liu Ling <address@hidden>
Signed-off-by: Prasad J Pandit <address@hidden>
---
net/checksum.c | 10 ++++++++--
1 file changed, 8 insertions(+), 2 deletions(-)
Update as per review:
-> https://lists.gnu.org/archive/html/qemu-devel/2016-02/msg06121.html
diff --git a/net/checksum.c b/net/checksum.c
index 14c0855..0942437 100644
--- a/tools/qemu-xen-traditional/net-checksum.c
+++ b/tools/qemu-xen-traditional/net-checksum.c
@@ -59,6 +59,11 @@ void net_checksum_calculate(uint8_t *data, int length)
int hlen, plen, proto, csum_offset;
uint16_t csum;
+ /* Ensure data has complete L2 & L3 headers. */
+ if (length < 14 + 20) {
+ return;
+ }
+
if ((data[14] & 0xf0) != 0x40)
return; /* not IPv4 */
hlen = (data[14] & 0x0f) * 4;
@@ -76,8 +81,9 @@ void net_checksum_calculate(uint8_t *data, int length)
return;
}
- if (plen < csum_offset+2)
- return;
+ if (plen < csum_offset + 2 || 14 + hlen + plen > length) {
+ return;
+ }
data[14+hlen+csum_offset] = 0;
data[14+hlen+csum_offset+1] = 0;
--
2.5.0

View file

@ -1,46 +0,0 @@
From 3a15cc0e1ee7168db0782133d2607a6bfa422d66 Mon Sep 17 00:00:00 2001
From: Prasad J Pandit <pjp@fedoraproject.org>
Date: Fri, 8 Apr 2016 11:33:48 +0530
Subject: [PATCH] net: stellaris_enet: check packet length against receive buffer
When receiving packets over Stellaris ethernet controller, it
uses receive buffer of size 2048 bytes. In case the controller
accepts large(MTU) packets, it could lead to memory corruption.
Add check to avoid it.
Reported-by: Oleksandr Bazhaniuk <oleksandr.bazhaniuk@intel.com>
Signed-off-by: Prasad J Pandit <pjp@fedoraproject.org>
Message-id: 1460095428-22698-1-git-send-email-ppandit@redhat.com
Reviewed-by: Peter Maydell <peter.maydell@linaro.org>
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
---
tools/qemu-xen-traditional/hw/stellaris_enet.c | 12 +++++++++++-
1 files changed, 11 insertions(+), 1 deletions(-)
diff --git a/tools/qemu-xen-traditional/hw/stellaris_enet.c b/tools/qemu-xen-traditional/hw/stellaris_enet.c
index 84cf60b..6880894 100644
--- a/tools/qemu-xen-traditional/hw/stellaris_enet.c
+++ b/tools/qemu-xen-traditional/hw/stellaris_enet.c
@@ -236,8 +236,18 @@ static ssize_t stellaris_enet_receive(NetClientState *nc, const uint8_t *buf, si
n = s->next_packet + s->np;
if (n >= 31)
n -= 31;
- s->np++;
+ if (size >= sizeof(s->rx[n].data) - 6) {
+ /* If the packet won't fit into the
+ * emulated 2K RAM, this is reported
+ * as a FIFO overrun error.
+ */
+ s->ris |= SE_INT_FOV;
+ stellaris_enet_update(s);
+ return -1;
+ }
+
+ s->np++;
s->rx[n].len = size + 6;
p = s->rx[n].data;
*(p++) = (size + 6);
--
1.7.0.4

View file

@ -1,31 +0,0 @@
From: Prasad J Pandit <address@hidden>
When receiving packets over MIPSnet network device, it uses
receive buffer of size 1514 bytes. In case the controller
accepts large(MTU) packets, it could lead to memory corruption.
Add check to avoid it.
Reported by: Oleksandr Bazhaniuk <address@hidden>
Signed-off-by: Prasad J Pandit <address@hidden>
---
tools/qemu-xen-traditional/hw/mipsnet.c | 3 +++
1 file changed, 3 insertions(+)
diff --git a/tools/qemu-xen-traditional/hw/mipsnet.c b/tools/qemu-xen-traditional/hw/mipsnet.c
index f261011..e134b31 100644
--- a/tools/qemu-xen-traditional/hw/mipsnet.c
+++ b/tools/qemu-xen-traditional/hw/mipsnet.c
@@ -82,6 +82,9 @@ static ssize_t mipsnet_receive(NetClientState *nc, const uint8_t *buf, size_t si
if (!mipsnet_can_receive(opaque))
return;
+ if (size >= sizeof(s->rx_buffer)) {
+ return;
+ }
s->busy = 1;
/* Just accept everything. */
--
2.5.5

View file

@ -1,44 +0,0 @@
------------------------------------------------------------------------
*From*: P J P
*Subject*: [Qemu-devel] [PATCH 1/2] scsi: check command buffer length
before write(CVE-2016-4439)
*Date*: Thu, 19 May 2016 16:09:30 +0530
------------------------------------------------------------------------
From: Prasad J Pandit <address@hidden>
The 53C9X Fast SCSI Controller(FSC) comes with an internal 16-byte
FIFO buffer. It is used to handle command and data transfer. While
writing to this command buffer 's->cmdbuf[TI_BUFSZ=16]', a check
was missing to validate input length. Add check to avoid OOB write
access.
Fixes CVE-2016-4439
Reported-by: Li Qiang <address@hidden>
Signed-off-by: Prasad J Pandit <address@hidden>
---
hw/scsi/esp.c | 6 +++++-
1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/tools/qemu-xen-traditional/hw/esp.c b/tools/qemu-xen-traditional/hw/esp.c
index 8961be2..01497e6 100644
--- a/tools/qemu-xen-traditional/hw/esp.c
+++ b/tools/qemu-xen-traditional/hw/esp.c
@@ -448,7 +448,11 @@ void esp_reg_write(ESPState *s, uint32_t saddr, uint64_t val)
break;
case ESP_FIFO:
if (s->do_cmd) {
- s->cmdbuf[s->cmdlen++] = val & 0xff;
+ if (s->cmdlen < TI_BUFSZ) {
+ s->cmdbuf[s->cmdlen++] = val & 0xff;
+ } else {
+ ESP_ERROR("fifo overrun\n");
+ }
} else if (s->ti_size == TI_BUFSZ - 1) {
ESP_ERROR("fifo overrun\n");
} else {
--
2.5.5

View file

@ -1,68 +0,0 @@
------------------------------------------------------------------------
*From*: P J P
*Subject*: [Qemu-devel] [PATCH 2/2] scsi: check dma length before
reading scsi command(CVE-2016-4441)
*Date*: Thu, 19 May 2016 16:09:31 +0530
------------------------------------------------------------------------
From: Prasad J Pandit <address@hidden>
The 53C9X Fast SCSI Controller(FSC) comes with an internal 16-byte
FIFO buffer. It is used to handle command and data transfer.
Routine get_cmd() uses DMA to read scsi commands into this buffer.
Add check to validate DMA length against buffer size to avoid any
overrun.
Fixes CVE-2016-4441
Reported-by: Li Qiang <address@hidden>
Signed-off-by: Prasad J Pandit <address@hidden>
---
hw/scsi/esp.c | 11 +++++++----
1 file changed, 7 insertions(+), 4 deletions(-)
diff --git a/tools/qemu-xen-traditional/hw/esp.c b/tools/qemu-xen-traditional/hw/esp.c
index 01497e6..591c817 100644
--- a/tools/qemu-xen-traditional/hw/esp.c
+++ b/tools/qemu-xen-traditional/hw/esp.c
@@ -82,7 +82,7 @@ void esp_request_cancelled(SCSIRequest *req)
}
}
-static uint32_t get_cmd(ESPState *s, uint8_t *buf)
+static uint32_t get_cmd(ESPState *s, uint8_t *buf, uint8_t buflen)
{
uint32_t dmalen;
int target;
@@ -92,6 +92,9 @@ static uint32_t get_cmd(ESPState *s, uint8_t *buf)
target = s->wregs[ESP_WBUSID] & BUSID_DID;
if (s->dma) {
dmalen = s->rregs[ESP_TCLO] | (s->rregs[ESP_TCMID] << 8);
+ if (dmalen > buflen) {
+ return 0;
+ }
s->dma_memory_read(s->dma_opaque, buf, dmalen);
} else {
dmalen = s->ti_size;
@@ -166,7 +169,7 @@ static void handle_satn(ESPState *s)
uint8_t buf[32];
int len;
- len = get_cmd(s, buf);
+ len = get_cmd(s, buf, sizeof(buf));
if (len)
do_cmd(s, buf);
}
@@ -192,7 +195,7 @@ static void handle_satn_stop(ESPState *s)
static void handle_satn_stop(ESPState *s)
{
- s->cmdlen = get_cmd(s, s->cmdbuf);
+ s->cmdlen = get_cmd(s, s->cmdbuf, sizeof(s->cmdbuf));
if (s->cmdlen) {
DPRINTF("Set ATN & Stop: cmdlen %d\n", s->cmdlen);
s->do_cmd = 1;
--
2.5.5

View file

@ -1,65 +0,0 @@
------------------------------------------------------------------------
*From*: Paolo Bonzini
*Subject*: Re: [Qemu-devel] [PATCH] scsi: check buffer length before
reading scsi command
*Date*: Wed, 1 Jun 2016 15:10:16 +0200
*User-agent*: Mozilla/5.0 (X11; Linux x86_64; rv:45.0) Gecko/20100101
Thunderbird/45.1.0
------------------------------------------------------------------------
On 31/05/2016 19:53, P J P wrote:
>/ From: Prasad J Pandit <address@hidden>/
>/ /
>/ The 53C9X Fast SCSI Controller(FSC) comes with an internal 16-byte/
>/ FIFO buffer. It is used to handle command and data transfer./
>/ Routine get_cmd() in non-DMA mode, uses 'ti_size' to read scsi/
>/ command into a buffer. Add check to validate command length against/
>/ buffer size to avoid any overrun./
>/ /
>/ Reported-by: Li Qiang <address@hidden>/
>/ Signed-off-by: Prasad J Pandit <address@hidden>/
>/ ---/
>/ hw/scsi/esp.c | 3 +++/
>/ 1 file changed, 3 insertions(+)/
>/ /
>/ diff --git a/tools/qemu-xen-traditional/hw/esp.c b/tools/qemu-xen-traditional/hw/esp.c/
>/ index 60c1b28..953027a 100644/
>/ --- a/tools/qemu-xen-traditional/hw/esp.c/
>/ +++ b/tools/qemu-xen-traditional/hw/esp.c/
>/ @@ -98,6 +98,9 @@ static uint32_t get_cmd(ESPState *s, uint8_t *buf, uint8_t /
>/ buflen)/
>/ s->dma_memory_read(s->dma_opaque, buf, dmalen);/
>/ } else {/
>/ dmalen = s->ti_size;/
>/ + if (dmalen > TI_BUFSZ) {/
>/ + return 0;/
>/ + }/
>/ memcpy(buf, s->ti_buf, dmalen);/
>/ buf[0] = buf[2] >> 5;/
>/ }/
>/ /
In theory this shouldn't happen, but I agree that it is better to be
defensive. I'm queuing this patch.
At least the following patch is needed to ensure that ti_size always
matches ti_rptr/ti_wptr (Hervé, what do you think about it? should I
resubmit it formally?). Also, things are more complicated than
necessary due to ti_size being used for both DMA and FIFO transfers.
diff --git a/tools/qemu-xen-traditional/hw/esp.c b/tools/qemu-xen-traditional/hw/esp.c
index c2f6f8f..6407844 100644
--- a/tools/qemu-xen-traditional/hw/esp.c
+++ b/tools/qemu-xen-traditional/hw/esp.c
@@ -222,7 +222,7 @@ static void write_response(ESPState *s)
} else {
s->ti_size = 2;
s->ti_rptr = 0;
- s->ti_wptr = 0;
+ s->ti_wptr = 2;
s->rregs[ESP_RFLAGS] = 2;
}
esp_raise_irq(s);

View file

@ -1,76 +0,0 @@
------------------------------------------------------------------------
*From*: P J P
*Subject*: [Qemu-devel] [PATCH v3] scsi: esp: check TI buffer index
before read/write
*Date*: Mon, 6 Jun 2016 22:04:43 +0530
------------------------------------------------------------------------
From: Prasad J Pandit <address@hidden>
The 53C9X Fast SCSI Controller(FSC) comes with internal 16-byte
FIFO buffers. One is used to handle commands and other is for
information transfer. Three control variables 'ti_rptr',
'ti_wptr' and 'ti_size' are used to control r/w access to the
information transfer buffer ti_buf[TI_BUFSZ=16]. In that,
'ti_rptr' is used as read index, where read occurs.
'ti_wptr' is a write index, where write would occur.
'ti_size' indicates total bytes to be read from the buffer.
While reading/writing to this buffer, index could exceed its
size. Add check to avoid OOB r/w access.
Reported-by: Huawei PSIRT <address@hidden>
Reported-by: Li Qiang <address@hidden>
Signed-off-by: Prasad J Pandit <address@hidden>
---
hw/scsi/esp.c | 20 +++++++++-----------
1 file changed, 9 insertions(+), 11 deletions(-)
Update as per:
-> https://lists.gnu.org/archive/html/qemu-devel/2016-06/msg01326.html
diff --git a/tools/qemu-xen-traditional/hw/esp.c b/tools/qemu-xen-traditional/hw/esp.c
index c2f6f8f..4b94bbc 100644
--- a/tools/qemu-xen-traditional/hw/esp.c
+++ b/tools/qemu-xen-traditional/hw/esp.c
@@ -403,18 +403,17 @@ uint64_t esp_reg_read(ESPState *s, uint32_t saddr)
DPRINTF("read reg[%d]: 0x%2.2x\n", saddr, s->rregs[saddr]);
switch (saddr) {
case ESP_FIFO:
- if (s->ti_size > 0) {
+ if ((s->rregs[ESP_RSTAT] & STAT_PIO_MASK) == 0) {
+ /* Data out. */
+ ESP_ERROR("PIO data read not implemented\n");
+ s->rregs[ESP_FIFO] = 0;
+ esp_raise_irq(s);
+ } else if (s->ti_rptr < s->ti_wptr) {
s->ti_size--;
- if ((s->rregs[ESP_RSTAT] & STAT_PIO_MASK) == 0) {
- /* Data out. */
- ESP_ERROR("PIO data read not implemented\n");
- s->rregs[ESP_FIFO] = 0;
- } else {
- s->rregs[ESP_FIFO] = s->ti_buf[s->ti_rptr++];
- }
+ s->rregs[ESP_FIFO] = s->ti_buf[s->ti_rptr++];
esp_raise_irq(s);
}
- if (s->ti_size == 0) {
+ if (s->ti_rptr == s->ti_wptr) {
s->ti_rptr = 0;
s->ti_wptr = 0;
}
@@ -459,7 +457,7 @@ void esp_reg_write(ESPState *s, uint32_t saddr, uint64_t val)
} else {
ESP_ERROR("fifo overrun\n");
}
- } else if (s->ti_size == TI_BUFSZ - 1) {
+ } else if (s->ti_wptr == TI_BUFSZ - 1) {
ESP_ERROR("fifo overrun\n");
} else {
s->ti_size++;
--
2.5.5

View file

@ -1,81 +0,0 @@
From 926cde5f3e4d2504ed161ed0cb771ac7cad6fd11 Mon Sep 17 00:00:00 2001
From: Prasad J Pandit <pjp@fedoraproject.org>
Date: Thu, 16 Jun 2016 00:22:35 +0200
Subject: [PATCH] scsi: esp: make cmdbuf big enough for maximum CDB size
While doing DMA read into ESP command buffer 's->cmdbuf', it could
write past the 's->cmdbuf' area, if it was transferring more than 16
bytes. Increase the command buffer size to 32, which is maximum when
's->do_cmd' is set, and add a check on 'len' to avoid OOB access.
Reported-by: Li Qiang <liqiang6-s@360.cn>
Signed-off-by: Prasad J Pandit <pjp@fedoraproject.org>
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
hw/esp.c | 6 ++++--
hw/esp.c | 3 ++-
2 files changed, 6 insertions(+), 3 deletions(-)
diff --git a/hw/esp.c b/hw/esp.c
index 64680b3..baa0a2c 100644
--- a/hw/esp.c
+++ b/hw/esp.c
@@ -25,6 +25,7 @@
#include "hw.h"
#include "scsi-disk.h"
#include "scsi.h"
+#include <assert.h>
/* debug ESP card */
//#define DEBUG_ESP
@@ -248,6 +248,8 @@ static void esp_do_dma(ESPState *s)
len = s->dma_left;
if (s->do_cmd) {
DPRINTF("command len %d + %d\n", s->cmdlen, len);
+ assert (s->cmdlen <= sizeof(s->cmdbuf) &&
+ len <= sizeof(s->cmdbuf) - s->cmdlen);
s->dma_memory_read(s->dma_opaque, &s->cmdbuf[s->cmdlen], len);
s->ti_size = 0;
s->cmdlen = 0;
@@ -345,7 +347,7 @@ static void handle_ti(ESPState *s)
s->dma_counter = dmalen;
if (s->do_cmd)
- minlen = (dmalen < 32) ? dmalen : 32;
+ minlen = (dmalen < ESP_CMDBUF_SZ) ? dmalen : ESP_CMDBUF_SZ;
else if (s->ti_size < 0)
minlen = (dmalen < -s->ti_size) ? dmalen : -s->ti_size;
else
@@ -449,7 +451,7 @@ void esp_reg_write(ESPState *s, uint32_t saddr, uint64_t val)
break;
case ESP_FIFO:
if (s->do_cmd) {
- if (s->cmdlen < TI_BUFSZ) {
+ if (s->cmdlen < ESP_CMDBUF_SZ) {
s->cmdbuf[s->cmdlen++] = val & 0xff;
} else {
ESP_ERROR("fifo overrun\n");
diff --git a/hw/esp.c b/hw/esp.c
index 6c79527..d2c4886 100644
--- a/hw/esp.c
+++ b/hw/esp.c
@@ -14,6 +14,7 @@ void esp_init(hwaddr espaddr, int it_shift,
#define ESP_REGS 16
#define TI_BUFSZ 16
+#define ESP_CMDBUF_SZ 32
typedef struct ESPState ESPState;
@@ -31,7 +32,7 @@ struct ESPState {
uint32_t dma;
SCSIDevice *scsi_dev[ESP_MAX_DEVS];
SCSIDevice *current_dev;
- uint8_t cmdbuf[TI_BUFSZ];
+ uint8_t cmdbuf[ESP_CMDBUF_SZ];
uint32_t cmdlen;
uint32_t do_cmd;
--
1.7.0.4

View file

@ -1,37 +0,0 @@
From 3592fe0c919cf27a81d8e9f9b4f269553418bb01 Mon Sep 17 00:00:00 2001
From: Prasad J Pandit <pjp@fedoraproject.org>
Date: Wed, 12 Oct 2016 11:28:08 +0530
Subject: [PATCH] char: serial: check divider value against baud base
16550A UART device uses an oscillator to generate frequencies
(baud base), which decide communication speed. This speed could
be changed by dividing it by a divider. If the divider is
greater than the baud base, speed is set to zero, leading to a
divide by zero error. Add check to avoid it.
Reported-by: Huawei PSIRT <psirt@huawei.com>
Signed-off-by: Prasad J Pandit <pjp@fedoraproject.org>
Message-Id: <1476251888-20238-1-git-send-email-ppandit@redhat.com>
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
hw/char/serial.c | 3 ++-
1 files changed, 2 insertions(+), 1 deletions(-)
diff --git a/hw/serial.c b/hw/serial.c
index 3442f47..eec72b7 100644
--- a/hw/serial.c
+++ b/hw/serial.c
@@ -153,8 +153,9 @@ static void serial_update_parameters(SerialState *s)
int speed, parity, data_bits, stop_bits, frame_size;
QEMUSerialSetParams ssp;
- if (s->divider == 0)
+ if (s->divider == 0 || s->divider > s->baudbase) {
return;
+ }
frame_size = 1;
if (s->lcr & 0x08) {
--
1.7.0.4

View file

@ -1,29 +0,0 @@
From: Prasad J Pandit <address@hidden>
RTL8139 ethernet controller in C+ mode supports multiple
descriptor rings, each with maximum of 64 descriptors. While
processing transmit descriptor ring in 'rtl8139_cplus_transmit',
it does not limit the descriptor count and runs forever. Add
check to avoid it.
Reported-by: Andrew Henderson <address@hidden>
Signed-off-by: Prasad J Pandit <address@hidden>
---
hw/net/rtl8139.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/hw/rtl8139.c b/hw/rtl8139.c
index 3345bc6..f05e59c 100644
--- a/hw/rtl8139.c
+++ b/hw/rtl8139.c
@@ -2350,7 +2350,7 @@ static void rtl8139_cplus_transmit(RTL8139State *s)
{
int txcount = 0;
- while (rtl8139_cplus_transmit_one(s))
+ while (txcount < 64 && rtl8139_cplus_transmit_one(s))
{
++txcount;
}
--
2.7.4

View file

@ -1,34 +0,0 @@
From 77d54985b85a0cb760330ec2bd92505e0a2a97a9 Mon Sep 17 00:00:00 2001
From: Prasad J Pandit <pjp@fedoraproject.org>
Date: Tue, 29 Nov 2016 00:38:39 +0530
Subject: [PATCH] net: mcf: check receive buffer size register value
ColdFire Fast Ethernet Controller uses a receive buffer size
register(EMRBR) to hold maximum size of all receive buffers.
It is set by a user before any operation. If it was set to be
zero, ColdFire emulator would go into an infinite loop while
receiving data in mcf_fec_receive. Add check to avoid it.
Reported-by: Wjjzhang <wjjzhang@tencent.com>
Signed-off-by: Prasad J Pandit <pjp@fedoraproject.org>
Signed-off-by: Jason Wang <jasowang@redhat.com>
---
hw/net/mcf_fec.c | 2 +-
1 files changed, 1 insertions(+), 1 deletions(-)
diff --git a/hw/mcf_fec.c b/hw/mcf_fec.c
index dc61bac..4025eb3 100644
--- a/hw/mcf_fec.c
+++ b/hw/mcf_fec.c
@@ -393,7 +393,7 @@ static void mcf_fec_write(void *opaque, hwaddr addr,
s->tx_descriptor = s->etdsr;
break;
case 0x188:
- s->emrbr = value & 0x7f0;
+ s->emrbr = value > 0 ? value & 0x7F0 : 0x7F0;
break;
default:
cpu_abort(cpu_single_env, "mcf_fec_write Bad address 0x%x\n",
--
1.7.0.4

View file

@ -1,51 +0,0 @@
From 95ed56939eb2eaa4e2f349fe6dcd13ca4edfd8fb Mon Sep 17 00:00:00 2001
From: Li Qiang <liqiang6-s@360.cn>
Date: Tue, 7 Feb 2017 02:23:33 -0800
Subject: [PATCH] usb: ohci: limit the number of link eds
The guest may builds an infinite loop with link eds. This patch
limit the number of linked ed to avoid this.
Signed-off-by: Li Qiang <liqiang6-s@360.cn>
Message-id: 5899a02e.45ca240a.6c373.93c1@mx.google.com
Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
---
hw/usb-ohci.c | 9 ++++++++-
1 file changed, 8 insertions(+), 1 deletion(-)
diff --git a/hw/usb-ohci.c b/hw/usb-ohci.c
index 2cba3e3..21c93e0 100644
--- a/hw/usb-ohci.c
+++ b/hw/usb-ohci.c
@@ -42,6 +42,8 @@
#define OHCI_MAX_PORTS 15
+#define ED_LINK_LIMIT 4
+
static int64_t usb_frame_time;
static int64_t usb_bit_time;
@@ -1184,7 +1186,7 @@ static int ohci_service_ed_list(OHCIState *ohci, uint32_t head, int completion)
uint32_t next_ed;
uint32_t cur;
int active;
-
+ uint32_t link_cnt = 0;
active = 0;
if (head == 0)
@@ -1199,6 +1201,10 @@ static int ohci_service_ed_list(OHCIState *ohci, uint32_t head, int completion)
next_ed = ed.next & OHCI_DPTR_MASK;
+ if (++link_cnt > ED_LINK_LIMIT) {
+ return 0;
+ }
+
if ((ed.head & OHCI_ED_H) || (ed.flags & OHCI_ED_K)) {
uint32_t addr;
/* Cancel pending packets for ED that have been paused. */
--
1.8.3.1

View file

@ -1,51 +0,0 @@
From 215902d7b6fb50c6fc216fc74f770858278ed904 Mon Sep 17 00:00:00 2001
From: hangaohuai <hangaohuai@huawei.com>
Date: Tue, 14 Mar 2017 14:39:19 +0800
Subject: [PATCH] fix :cirrus_vga fix OOB read case qemu Segmentation fault
check the validity of parameters in cirrus_bitblt_rop_fwd_transp_xxx
and cirrus_bitblt_rop_fwd_xxx to avoid the OOB read which causes qemu Segmentation fault.
After the fix, we will touch the assert in
cirrus_invalidate_region:
assert(off_cur_end >= off_cur);
Signed-off-by: fangying <fangying1@huawei.com>
Signed-off-by: hangaohuai <hangaohuai@huawei.com>
Message-id: 20170314063919.16200-1-hangaohuai@huawei.com
Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
---
hw/cirrus_vga_rop.h | 10 ++++++++++
1 file changed, 10 insertions(+)
diff --git a/hw/cirrus_vga_rop.h b/hw/cirrus_vga_rop.h
index 0925a00..b7447f8 100644
--- a/hw/cirrus_vga_rop.h
+++ b/hw/cirrus_vga_rop.h
@@ -97,6 +97,11 @@ glue(glue(cirrus_bitblt_rop_fwd_transp_, ROP_NAME),_8)(CirrusVGAState *s,
src = src_ - src_base;
dstpitch -= bltwidth;
srcpitch -= bltwidth;
+
+ if (bltheight > 1 && (dstpitch < 0 || srcpitch < 0)) {
+ return;
+ }
+
for (y = 0; y < bltheight; y++) {
for (x = 0; x < bltwidth; x++) {
p = *(dst_base + m(dst));
@@ -143,6 +148,11 @@ glue(glue(cirrus_bitblt_rop_fwd_transp_, ROP_NAME),_16)(CirrusVGAState *s,
src = src_ - src_base;
dstpitch -= bltwidth;
srcpitch -= bltwidth;
+
+ if (bltheight > 1 && (dstpitch < 0 || srcpitch < 0)) {
+ return;
+ }
+
for (y = 0; y < bltheight; y++) {
for (x = 0; x < bltwidth; x+=2) {
p1 = *(dst_base + m(dst));
--
1.8.3.1

View file

@ -1,38 +0,0 @@
From 3268a845f41253fb55852a8429c32b50f36f349a Mon Sep 17 00:00:00 2001
From: Gerd Hoffmann <kraxel@redhat.com>
Date: Fri, 28 Apr 2017 09:56:12 +0200
Subject: [PATCH] audio: release capture buffers
AUD_add_capture() allocates two buffers which are never released.
Add the missing calls to AUD_del_capture().
Impact: Allows vnc clients to exhaust host memory by repeatedly
starting and stopping audio capture.
Fixes: CVE-2017-8309
Cc: P J P <ppandit@redhat.com>
Cc: Huawei PSIRT <PSIRT@huawei.com>
Reported-by: "Jiangxin (hunter, SCC)" <jiangxin1@huawei.com>
Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
Reviewed-by: Prasad J Pandit <pjp@fedoraproject.org>
Message-id: 20170428075612.9997-1-kraxel@redhat.com
---
audio/audio.c | 2 ++
1 file changed, 2 insertions(+)
diff --git a/audio/audio.c b/audio/audio.c
index c8898d8..beafed2 100644
--- a/audio/audio.c
+++ b/audio/audio.c
@@ -2028,6 +2028,8 @@ void AUD_del_capture (CaptureVoiceOut *cap, void *cb_opaque)
sw = sw1;
}
LIST_REMOVE (cap, entries);
+ qemu_free (cap->hw.mix_buf);
+ qemu_free (cap->buf);
qemu_free (cap);
}
return;
--
1.8.3.1

View file

@ -1,31 +0,0 @@
From 26f670a244982335cc08943fb1ec099a2c81e42d Mon Sep 17 00:00:00 2001
From: Li Qiang <liqiang6-s@360.cn>
Date: Tue, 7 Feb 2017 03:15:03 -0800
Subject: [PATCH] usb: ohci: fix error return code in servicing iso td
It should return 1 if an error occurs when reading iso td.
This will avoid an infinite loop issue in ohci_service_ed_list.
Signed-off-by: Li Qiang <liqiang6-s@360.cn>
Message-id: 5899ac3e.1033240a.944d5.9a2d@mx.google.com
Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
---
hw/usb-ohci.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/hw/usb-ohci.c b/hw/usb-ohci.c
index c82a92f..2cba3e3 100644
--- a/hw/usb-ohci.c
+++ b/hw/usb-ohci.c
@@ -725,7 +725,7 @@ static int ohci_service_iso_td(OHCIState *ohci, struct ohci_ed *ed,
if (!ohci_read_iso_td(addr, &iso_td)) {
printf("usb-ohci: ISO_TD read error at %x\n", addr);
- return 0;
+ return 1;
}
starting_frame = OHCI_BM(iso_td.flags, TD_SF);
--
1.8.3.1

View file

@ -1,76 +0,0 @@
From 4299b90e9ba9ce5ca9024572804ba751aa1a7e70 Mon Sep 17 00:00:00 2001
From: Prasad J Pandit <pjp@fedoraproject.org>
Date: Tue, 18 Oct 2016 13:15:17 +0530
Subject: [PATCH] display: cirrus: check vga bits per pixel(bpp) value
In Cirrus CLGD 54xx VGA Emulator, if cirrus graphics mode is VGA,
'cirrus_get_bpp' returns zero(0), which could lead to a divide
by zero error in while copying pixel data. The same could occur
via blit pitch values. Add check to avoid it.
Reported-by: Huawei PSIRT <psirt@huawei.com>
Signed-off-by: Prasad J Pandit <pjp@fedoraproject.org>
Message-id: 1476776717-24807-1-git-send-email-ppandit@redhat.com
Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
---
hw/cirrus_vga.c | 14 ++++++++++----
1 files changed, 10 insertions(+), 4 deletions(-)
diff --git a/hw/cirrus_vga.c b/hw/cirrus_vga.c
index 3d712d5..bdb092e 100644
--- a/hw/cirrus_vga.c
+++ b/hw/cirrus_vga.c
@@ -272,6 +272,9 @@ static void cirrus_update_memory_access(CirrusVGAState *s);
static bool blit_region_is_unsafe(struct CirrusVGAState *s,
int32_t pitch, int32_t addr)
{
+ if (!pitch) {
+ return true;
+ }
if (pitch < 0) {
int64_t min = addr
+ ((int64_t)s->cirrus_blt_height - 1) * pitch
@@ -715,7 +718,7 @@ static int cirrus_bitblt_videotovideo_patterncopy(CirrusVGAState * s)
s->cirrus_addr_mask));
}
-static void cirrus_do_copy(CirrusVGAState *s, int dst, int src, int w, int h)
+static int cirrus_do_copy(CirrusVGAState *s, int dst, int src, int w, int h)
{
int sx = 0, sy = 0;
int dx = 0, dy = 0;
@@ -729,6 +732,9 @@ static void cirrus_do_copy(CirrusVGAState *s, int dst, int src, int w, int h)
int width, height;
depth = s->get_bpp((VGAState *)s) / 8;
+ if (!depth) {
+ return 0;
+ }
s->get_resolution((VGAState *)s, &width, &height);
/* extra x, y */
@@ -783,6 +789,8 @@ static void cirrus_do_copy(CirrusVGAState *s, int dst, int src, int w, int h)
cirrus_invalidate_region(s, s->cirrus_blt_dstaddr,
s->cirrus_blt_dstpitch, s->cirrus_blt_width,
s->cirrus_blt_height);
+
+ return 1;
}
static int cirrus_bitblt_videotovideo_copy(CirrusVGAState * s)
@@ -790,11 +798,9 @@ static int cirrus_bitblt_videotovideo_copy(CirrusVGAState * s)
if (blit_is_unsafe(s))
return 0;
- cirrus_do_copy(s, s->cirrus_blt_dstaddr - s->start_addr,
+ return cirrus_do_copy(s, s->cirrus_blt_dstaddr - s->start_addr,
s->cirrus_blt_srcaddr - s->start_addr,
s->cirrus_blt_width, s->cirrus_blt_height);
-
- return 1;
}
/***************************************
--
1.7.0.4

View file

@ -4,4 +4,5 @@ SHA512 (newlib-1.16.0.tar.gz) = 40eb96bbc6736a16b6399e0cdb73e853d0d90b685c967e77
SHA512 (zlib-1.2.3.tar.gz) = 021b958fcd0d346c4ba761bcf0cc40f3522de6186cf5a0a6ea34a70504ce9622b1c2626fce40675bc8282cf5f5ade18473656abc38050f72f5d6480507a2106e
SHA512 (polarssl-1.1.4-gpl.tgz) = 88da614e4d3f4409c4fd3bb3e44c7587ba051e3fed4e33d526069a67e8180212e1ea22da984656f50e290049f60ddca65383e5983c0f8884f648d71f698303ad
SHA512 (pciutils-2.2.9.tar.bz2) = 2b3d98d027e46d8c08037366dde6f0781ca03c610ef2b380984639e4ef39899ed8d8b8e4cd9c9dc54df101279b95879bd66bfd4d04ad07fef41e847ea7ae32b5
SHA512 (xen-4.10.1.tar.gz) = 236c02bee69e33644703ed26d323d4c491a91fc05bd0ee0990a7368579f7c82f5bb4510845bf80348fd923024d7d60d521f593dfd0365d971dc592f8ef10fbea
SHA512 (mini-os-4.21.0.tar.xz) = 7543774d15da84476d93d04154990923c82209cb3fa125574c0383652c5a310957200f54b63b34502161f9c3afce4907e0060d9036f3eaf3a7cb6b1b3119b546
SHA512 (xen-4.21.1.tar.xz) = 8dfe65255e202b3dacf9d0d7265636bc1f97627c11b08babc13a5b8e74c7c65e7e2c6a1513e28b3c713fe512edb6702a73b2bf667e2a8f2ce825b196a2cd5aab

View file

@ -1,27 +0,0 @@
--- xen-4.1.0-orig/tools/hotplug/Linux/vif-bridge 2008-08-22 10:49:07.000000000 +0100
+++ xen-4.1.0-new/tools/hotplug/Linux/vif-bridge 2008-08-29 11:29:38.000000000 +0100
@@ -96,8 +96,6 @@ case "$command" in
;;
esac
-handle_iptable
-
call_hooks vif post
log debug "Successful vif-bridge $command for $dev, bridge $bridge."
--- xen-3.3.0-orig/tools/hotplug/Linux/xen-network-common.sh 2008-08-22 10:49:07.000000000 +0100
+++ xen-3.3.0-new/tools/hotplug/Linux/xen-network-common.sh 2008-08-29 11:29:38.000000000 +0100
@@ -99,6 +99,13 @@ create_bridge () {
brctl addbr ${bridge}
brctl stp ${bridge} off
brctl setfd ${bridge} 0
+ # Setting these to zero stops guest<->LAN traffic
+ # traversing the bridge from hitting the *tables
+ # rulesets. guest<->host traffic still gets processed
+ # by the host's iptables rules so this isn't a hole
+ sysctl -q -w "net.bridge.bridge-nf-call-arptables=0"
+ sysctl -q -w "net.bridge.bridge-nf-call-ip6tables=0"
+ sysctl -q -w "net.bridge.bridge-nf-call-iptables=0"
fi
}

View file

@ -1,56 +1,54 @@
--- xen-4.9.0-rc1.2/tools/xenstore/xenstored_watch.c.orig 2017-04-12 16:18:57.000000000 +0100
+++ xen-4.9.0-rc1.2/tools/xenstore/xenstored_watch.c 2017-04-13 21:17:12.255231094 +0100
@@ -166,7 +166,7 @@
/* check if valid event */
} else {
relative = !strstarts(vec[0], "/");
- vec[0] = canonicalize(conn, in, vec[0]);
+ vec[0] = xenstore_canonicalize(conn, in, vec[0]);
if (!vec[0])
return ENOMEM;
if (!is_valid_nodename(vec[0]))
@@ -219,7 +219,7 @@
--- xen-4.18.0-rc1/tools/xenstored/watch.c.orig 2023-09-29 09:09:29.000000000 +0100
+++ xen-4.18.0-rc1/tools/xenstored/watch.c 2023-10-02 16:12:14.971264769 +0100
@@ -164,7 +164,7 @@
const char **path, bool *relative)
{
*relative = !strstarts(*path, "/") && !strstarts(*path, "@");
- *path = canonicalize(conn, ctx, *path, true);
+ *path = xenstore_canonicalize(conn, ctx, *path, true);
return *path ? 0 : errno;
}
@@ -250,7 +250,7 @@
if (get_strings(in, vec, ARRAY_SIZE(vec)) != ARRAY_SIZE(vec))
return EINVAL;
- node = canonicalize(conn, in, vec[0]);
+ node = xenstore_canonicalize(conn, in, vec[0]);
- node = canonicalize(conn, ctx, vec[0], true);
+ node = xenstore_canonicalize(conn, ctx, vec[0], true);
if (!node)
return ENOMEM;
return errno;
list_for_each_entry(watch, &conn->watches, list) {
--- xen-4.9.0-rc1.2/tools/xenstore/xenstored_core.c.orig 2017-04-12 16:18:57.000000000 +0100
+++ xen-4.9.0-rc1.2/tools/xenstore/xenstored_core.c 2017-04-13 21:19:35.668429881 +0100
@@ -777,7 +777,7 @@
--- xen-4.18.0-rc1/tools/xenstored/core.c.orig 2023-09-29 09:09:29.000000000 +0100
+++ xen-4.18.0-rc1/tools/xenstored/core.c 2023-10-02 16:12:14.993264626 +0100
@@ -1249,7 +1249,7 @@
return strings;
}
-char *canonicalize(struct connection *conn, const void *ctx, const char *node)
+char *xenstore_canonicalize(struct connection *conn, const void *ctx, const char *node)
-const char *canonicalize(struct connection *conn, const void *ctx,
+const char *xenstore_canonicalize(struct connection *conn, const void *ctx,
const char *node, bool allow_special)
{
const char *prefix;
const char *name;
@@ -1303,7 +1303,7 @@
{
struct node *node;
@@ -799,7 +799,7 @@
- *canonical_name = canonicalize(conn, ctx, name, allow_special);
+ *canonical_name = xenstore_canonicalize(conn, ctx, name, allow_special);
if (!*canonical_name)
return NULL;
if (!canonical_name)
canonical_name = &tmp_name;
- *canonical_name = canonicalize(conn, ctx, name);
+ *canonical_name = xenstore_canonicalize(conn, ctx, name);
return get_node(conn, ctx, *canonical_name, perm);
}
@@ -1320,7 +1320,7 @@
const char *tmp_name;
const struct node *node;
--- xen-4.9.0-rc1.2/tools/xenstore/xenstored_core.h.orig 2017-04-12 16:18:57.000000000 +0100
+++ xen-4.9.0-rc1.2/tools/xenstore/xenstored_core.h 2017-04-13 21:20:29.146368478 +0100
@@ -148,7 +148,7 @@
void send_ack(struct connection *conn, enum xsd_sockmsg_type type);
- tmp_name = canonicalize(conn, ctx, name, allow_special);
+ tmp_name = xenstore_canonicalize(conn, ctx, name, allow_special);
if (!tmp_name)
return NULL;
/* Canonicalize this path if possible. */
-char *canonicalize(struct connection *conn, const void *ctx, const char *node);
+char *xenstore_canonicalize(struct connection *conn, const void *ctx, const char *node);
/* Write a node to the tdb data base. */
int write_node_raw(struct connection *conn, TDB_DATA *key, struct node *node);
--- xen-4.8.0/tools/console/testsuite/console-dom0.c.orig 2016-12-05 12:03:27.000000000 +0000
+++ xen-4.8.0/tools/console/testsuite/console-dom0.c 2017-02-26 21:52:24.554678631 +0000
--- xen-4.18.0-rc1/tools/console/testsuite/console-dom0.c.orig 2023-09-29 09:09:29.000000000 +0100
+++ xen-4.18.0-rc1/tools/console/testsuite/console-dom0.c 2023-10-02 16:12:15.001264574 +0100
@@ -18,7 +18,7 @@
}
}
@ -87,8 +85,8 @@
fprintf(stderr, "%s", line);
} while (strcmp(line, "Okay.\n") != 0);
--- xen-4.8.0/tools/console/testsuite/console-domU.c.orig 2016-12-05 12:03:27.000000000 +0000
+++ xen-4.8.0/tools/console/testsuite/console-domU.c 2017-02-26 21:52:50.320622804 +0000
--- xen-4.18.0-rc1/tools/console/testsuite/console-domU.c.orig 2023-09-29 09:09:29.000000000 +0100
+++ xen-4.18.0-rc1/tools/console/testsuite/console-domU.c 2023-10-02 16:12:15.008264528 +0100
@@ -6,7 +6,7 @@
#include <termios.h>
#include <unistd.h>
@ -107,3 +105,14 @@
seed = strtoul(line, 0, 0);
printf("Seed Okay.\n"); fflush(stdout);
--- xen-4.18.0-rc1/tools/xenstored/core.h.orig 2023-09-29 09:09:29.000000000 +0100
+++ xen-4.18.0-rc1/tools/xenstored/core.h 2023-10-02 16:12:15.015264482 +0100
@@ -240,7 +240,7 @@
void send_ack(struct connection *conn, enum xsd_sockmsg_type type);
/* Canonicalize this path if possible. */
-const char *canonicalize(struct connection *conn, const void *ctx,
+const char *xenstore_canonicalize(struct connection *conn, const void *ctx,
const char *node, bool allow_special);
/* Get access permissions. */

13
xen.efi.build.patch Normal file
View file

@ -0,0 +1,13 @@
--- xen-4.20.0-rc4/xen/arch/x86/arch.mk.orig 2025-02-07 11:56:01.000000000 +0000
+++ xen-4.20.0-rc4/xen/arch/x86/arch.mk 2025-02-09 22:56:05.579507311 +0000
@@ -95,7 +95,9 @@
-c $(srctree)/$(efi-check).c -o $(efi-check).o,y)
# Check if the linker supports PE.
-EFI_LDFLAGS := $(patsubst -m%,-mi386pep,$(LDFLAGS)) --subsystem=10 --enable-long-section-names
+#EFI_LDFLAGS := $(patsubst -m%,-mi386pep,$(LDFLAGS)) --subsystem=10 --enable-long-section-names
+# use a reduced set of options from LDFLAGS
+EFI_LDFLAGS = --as-needed --build-id=sha1 -mi386pep --subsystem=10 --enable-long-section-names
LD_PE_check_cmd = $(call ld-option,$(EFI_LDFLAGS) --image-base=0x100000000 -o $(efi-check).efi $(efi-check).o)
XEN_BUILD_PE := $(LD_PE_check_cmd)

View file

@ -1,11 +0,0 @@
--- xen-4.5.1/tools/qemu-xen-traditional/vnc.c.orig 2015-07-12 21:55:32.875504811 +0100
+++ xen-4.5.1/tools/qemu-xen-traditional/vnc.c 2015-07-12 22:03:03.860005391 +0100
@@ -2140,7 +2140,7 @@
GNUTLS_VERSION_NUMBER >= 0x020200 /* 2.2.0 */
static int vnc_set_gnutls_priority(gnutls_session_t s, int x509)
{
- const char *priority = x509 ? "NORMAL" : "NORMAL:+ANON-DH";
+ const char *priority = x509 ? "@SYSTEM" : "@SYSTEM:+ANON-DH";
int rc;
rc = gnutls_priority_set_direct(s, priority, NULL);

View file

@ -1,57 +0,0 @@
--- xen-4.8.0/xen/arch/x86/Makefile.orig 2016-12-05 12:03:27.000000000 +0000
+++ xen-4.8.0/xen/arch/x86/Makefile 2017-02-28 00:02:27.989589825 +0000
@@ -73,6 +73,7 @@
efi-y := $(shell if [ ! -r $(BASEDIR)/include/xen/compile.h -o \
-O $(BASEDIR)/include/xen/compile.h ]; then \
echo '$(TARGET).efi'; fi)
+LD_EFI ?= $(LD)
ifneq ($(build_id_linker),)
notes_phdrs = --notes
@@ -173,20 +174,20 @@
$(TARGET).efi: prelink-efi.o $(note_file) efi.lds efi/relocs-dummy.o $(BASEDIR)/common/symbols-dummy.o efi/mkreloc
$(foreach base, $(VIRT_BASE) $(ALT_BASE), \
- $(guard) $(LD) $(call EFI_LDFLAGS,$(base)) -T efi.lds -N $< efi/relocs-dummy.o \
+ $(guard) $(LD_EFI) $(call EFI_LDFLAGS,$(base)) -T efi.lds -N $< efi/relocs-dummy.o \
$(BASEDIR)/common/symbols-dummy.o $(note_file) -o $(@D)/.$(@F).$(base).0 &&) :
$(guard) efi/mkreloc $(foreach base,$(VIRT_BASE) $(ALT_BASE),$(@D)/.$(@F).$(base).0) >$(@D)/.$(@F).0r.S
$(guard) $(NM) -pa --format=sysv $(@D)/.$(@F).$(VIRT_BASE).0 \
| $(guard) $(BASEDIR)/tools/symbols $(all_symbols) --sysv --sort >$(@D)/.$(@F).0s.S
$(guard) $(MAKE) -f $(BASEDIR)/Rules.mk $(@D)/.$(@F).0r.o $(@D)/.$(@F).0s.o
$(foreach base, $(VIRT_BASE) $(ALT_BASE), \
- $(guard) $(LD) $(call EFI_LDFLAGS,$(base)) -T efi.lds -N $< \
+ $(guard) $(LD_EFI) $(call EFI_LDFLAGS,$(base)) -T efi.lds -N $< \
$(@D)/.$(@F).0r.o $(@D)/.$(@F).0s.o $(note_file) -o $(@D)/.$(@F).$(base).1 &&) :
$(guard) efi/mkreloc $(foreach base,$(VIRT_BASE) $(ALT_BASE),$(@D)/.$(@F).$(base).1) >$(@D)/.$(@F).1r.S
$(guard) $(NM) -pa --format=sysv $(@D)/.$(@F).$(VIRT_BASE).1 \
| $(guard) $(BASEDIR)/tools/symbols $(all_symbols) --sysv --sort >$(@D)/.$(@F).1s.S
$(guard) $(MAKE) -f $(BASEDIR)/Rules.mk $(@D)/.$(@F).1r.o $(@D)/.$(@F).1s.o
- $(guard) $(LD) $(call EFI_LDFLAGS,$(VIRT_BASE)) -T efi.lds -N $< \
+ $(guard) $(LD_EFI) $(call EFI_LDFLAGS,$(VIRT_BASE)) -T efi.lds -N $< \
$(@D)/.$(@F).1r.o $(@D)/.$(@F).1s.o $(note_file) -o $@
if $(guard) false; then rm -f $@; echo 'EFI support disabled'; \
else $(NM) -pa --format=sysv $(@D)/$(@F) \
--- xen-4.9.0-rc1.2/xen/arch/x86/efi/Makefile.orig 2017-04-12 16:18:57.000000000 +0100
+++ xen-4.9.0-rc1.2/xen/arch/x86/efi/Makefile 2017-04-13 21:05:54.170387130 +0100
@@ -1,8 +1,9 @@
CFLAGS += -fshort-wchar
+LD_EFI ?= $(LD)
efi := y$(shell rm -f disabled)
efi := $(if $(efi),$(shell $(CC) $(filter-out $(CFLAGS-y) .%.d,$(CFLAGS)) -c check.c 2>disabled && echo y))
-efi := $(if $(efi),$(shell $(LD) -mi386pep --subsystem=10 -o check.efi check.o 2>disabled && echo y))
+efi := $(if $(efi),$(shell $(LD_EFI) -mi386pep --subsystem=10 -o check.efi check.o 2>disabled && echo y))
efi := $(if $(efi),$(shell rm disabled)y)
%.o: %.ihex
--- xen-4.8.0/xen/Makefile.orig 2016-12-05 12:03:27.000000000 +0000
+++ xen-4.8.0/xen/Makefile 2017-02-28 00:02:54.080529810 +0000
@@ -20,6 +20,7 @@
MAKEFLAGS += -rR
EFI_MOUNTPOINT ?= $(BOOT_DIR)/efi
+EFI_VENDOR=fedora
ARCH=$(XEN_TARGET_ARCH)
SRCARCH=$(shell echo $(ARCH) | sed -e 's/x86.*/x86/' -e s'/arm\(32\|64\)/arm/g')

View file

@ -1,7 +1,6 @@
diff -uN xen-4.5.0/tools/hotplug/Linux/systemd.orig/Makefile xen-4.5.0/tools/hotplug/Linux/systemd/Makefile
--- xen-4.5.0/tools/hotplug/Linux/systemd.orig/Makefile 2015-01-12 16:53:24.000000000 +0000
+++ xen-4.5.0/tools/hotplug/Linux/systemd/Makefile 2015-01-25 22:23:26.000000000 +0000
@@ -14,7 +14,8 @@
--- xen-4.17.0/tools/hotplug/Linux/systemd/Makefile.orig 2022-12-08 18:03:08.000000000 +0000
+++ xen-4.17.0/tools/hotplug/Linux/systemd/Makefile 2022-12-09 19:47:53.227189371 +0000
@@ -10,7 +10,8 @@
XEN_SYSTEMD_SERVICE += xen-qemu-dom0-disk-backend.service
XEN_SYSTEMD_SERVICE += xendomains.service
XEN_SYSTEMD_SERVICE += xen-watchdog.service
@ -10,16 +9,7 @@ diff -uN xen-4.5.0/tools/hotplug/Linux/systemd.orig/Makefile xen-4.5.0/tools/hot
+XEN_SYSTEMD_SERVICE += oxenstored.service
XEN_SYSTEMD_SERVICE += xendriverdomain.service
ALL_XEN_SYSTEMD = $(XEN_SYSTEMD_MODULES) \
diff -uN xen-4.5.0/tools/hotplug/Linux/systemd.orig/var-lib-xenstored.mount.in xen-4.5.0/tools/hotplug/Linux/systemd/var-lib-xenstored.mount.in
--- xen-4.5.0/tools/hotplug/Linux/systemd.orig/var-lib-xenstored.mount.in 2015-01-12 16:53:24.000000000 +0000
+++ xen-4.5.0/tools/hotplug/Linux/systemd/var-lib-xenstored.mount.in 2015-01-25 22:28:59.000000000 +0000
@@ -9,4 +9,4 @@
What=xenstore
Where=@XEN_LIB_STORED@
Type=tmpfs
-Options=mode=755
+Options=mode=755,context="system_u:object_r:xenstored_var_lib_t:s0"
ALL_XEN_SYSTEMD := $(XEN_SYSTEMD_MODULES) \
diff -uN xen-4.5.0/tools/hotplug/Linux/systemd.orig/xenconsoled.service.in xen-4.5.0/tools/hotplug/Linux/systemd/xenconsoled.service.in
--- xen-4.5.0/tools/hotplug/Linux/systemd.orig/xenconsoled.service.in 2015-01-12 16:53:24.000000000 +0000
+++ xen-4.5.0/tools/hotplug/Linux/systemd/xenconsoled.service.in 2015-01-25 22:30:26.000000000 +0000
@ -59,27 +49,26 @@ diff -uN xen-4.5.0/tools/hotplug/Linux/systemd.orig/xen-qemu-dom0-disk-backend.s
Before=xendomains.service libvirtd.service libvirt-guests.service
RefuseManualStop=true
ConditionPathExists=/proc/xen/capabilities
--- xen-4.6.0/tools/configure.ac.orig 2015-02-15 16:47:22.000000000 +0000
+++ xen-4.6.0/tools/configure.ac 2015-03-01 16:18:30.493647587 +0000
@@ -382,9 +382,9 @@
--- xen-4.17.0/tools/configure.ac.orig 2022-12-08 18:03:08.000000000 +0000
+++ xen-4.17.0/tools/configure.ac 2022-12-09 19:50:24.773193862 +0000
@@ -481,8 +481,8 @@
AS_IF([test "x$systemd" = "xy"], [
AC_CONFIG_FILES([
+ hotplug/Linux/systemd/oxenstored.service
hotplug/Linux/systemd/proc-xen.mount
hotplug/Linux/systemd/var-lib-xenstored.mount
- hotplug/Linux/systemd/xen-init-dom0.service
hotplug/Linux/systemd/xen-qemu-dom0-disk-backend.service
hotplug/Linux/systemd/xen-watchdog.service
hotplug/Linux/systemd/xenconsoled.service
--- xen-4.6.0/tools/configure.orig 2015-02-15 16:47:22.000000000 +0000
+++ xen-4.6.0/tools/configure 2015-03-01 16:20:10.648285840 +0000
@@ -8995,7 +8995,7 @@
--- xen-4.17.0/tools/configure.orig 2022-12-08 18:03:08.000000000 +0000
+++ xen-4.17.0/tools/configure 2022-12-09 19:51:43.278708226 +0000
@@ -10081,7 +10081,7 @@
if test "x$systemd" = "xy"
then :
if test "x$systemd" = "xy"; then :
- ac_config_files="$ac_config_files hotplug/Linux/systemd/proc-xen.mount hotplug/Linux/systemd/var-lib-xenstored.mount hotplug/Linux/systemd/xen-init-dom0.service hotplug/Linux/systemd/xen-qemu-dom0-disk-backend.service hotplug/Linux/systemd/xen-watchdog.service hotplug/Linux/systemd/xenconsoled.service hotplug/Linux/systemd/xendomains.service hotplug/Linux/systemd/xendriverdomain.service hotplug/Linux/systemd/xenstored.service"
+ ac_config_files="$ac_config_files hotplug/Linux/systemd/oxenstored.service hotplug/Linux/systemd/proc-xen.mount hotplug/Linux/systemd/var-lib-xenstored.mount hotplug/Linux/systemd/xen-qemu-dom0-disk-backend.service hotplug/Linux/systemd/xen-watchdog.service hotplug/Linux/systemd/xenconsoled.service hotplug/Linux/systemd/xendomains.service hotplug/Linux/systemd/xendriverdomain.service hotplug/Linux/systemd/xenstored.service"
- ac_config_files="$ac_config_files hotplug/Linux/systemd/proc-xen.mount hotplug/Linux/systemd/xen-init-dom0.service hotplug/Linux/systemd/xen-qemu-dom0-disk-backend.service hotplug/Linux/systemd/xen-watchdog.service hotplug/Linux/systemd/xenconsoled.service hotplug/Linux/systemd/xendomains.service hotplug/Linux/systemd/xendriverdomain.service hotplug/Linux/systemd/xenstored.service"
+ ac_config_files="$ac_config_files hotplug/Linux/systemd/oxenstored.service hotplug/Linux/systemd/proc-xen.mount hotplug/Linux/systemd/xen-qemu-dom0-disk-backend.service hotplug/Linux/systemd/xen-watchdog.service hotplug/Linux/systemd/xenconsoled.service hotplug/Linux/systemd/xendomains.service hotplug/Linux/systemd/xendriverdomain.service hotplug/Linux/systemd/xenstored.service"
fi

24
xen.gcc11.fixes.patch Normal file
View file

@ -0,0 +1,24 @@
--- xen-4.14.0/xen/include/crypto/vmac.h.orig 2020-07-23 16:07:51.000000000 +0100
+++ xen-4.14.0/xen/include/crypto/vmac.h 2020-10-24 15:45:49.246467465 +0100
@@ -142,7 +142,7 @@
#define vmac_update vhash_update
-void vhash_update(unsigned char m[],
+void vhash_update(uint8_t *m,
unsigned int mbytes,
vmac_ctx_t *ctx);
diff --git a/xen/arch/x86/tboot.c b/xen/arch/x86/tboot.c
index 320e06f..618ae92 100644
--- a/xen/arch/x86/tboot.c
+++ b/xen/arch/x86/tboot.c
@@ -91,7 +91,7 @@ static void __init tboot_copy_memory(unsigned char *va, uint32_t size,
void __init tboot_probe(void)
{
- tboot_shared_t *tboot_shared;
+ tboot_shared_t * volatile tboot_shared;
static const uuid_t __initconst tboot_shared_uuid = TBOOT_SHARED_UUID;
/* Look for valid page-aligned address for shared page. */

10
xen.gcc12.fixes.patch Normal file
View file

@ -0,0 +1,10 @@
--- xen-4.16.0/Config.mk.orig 2021-11-30 11:42:42.000000000 +0000
+++ xen-4.16.0/Config.mk 2022-01-24 20:25:16.687125822 +0000
@@ -186,6 +186,7 @@
$(call cc-option-add,CFLAGS,CC,-Wno-unused-but-set-variable)
$(call cc-option-add,CFLAGS,CC,-Wno-unused-local-typedefs)
+$(call cc-option-add,CFLAGS,CC,-Wno-error=array-bounds)
LDFLAGS += $(foreach i, $(EXTRA_LIB), -L$(i))
CFLAGS += $(foreach i, $(EXTRA_INCLUDES), -I$(i))

View file

@ -1,12 +0,0 @@
--- xen-4.8.0/extras/mini-os/Makefile.orig 2016-09-28 12:09:38.000000000 +0100
+++ xen-4.8.0/extras/mini-os/Makefile 2017-02-15 21:15:19.340197960 +0000
@@ -142,6 +142,9 @@
APP_LDLIBS += -lz
APP_LDLIBS += -lm
LDLIBS += -lc
+ifeq ($(MINIOS_TARGET_ARCH),x86_32)
+LDLIBS += -L$(shell dirname `gcc -m32 -print-libgcc-file-name`) -lgcc
+endif
endif
ifneq ($(APP_OBJS)-$(lwip),-y)

View file

@ -1,133 +0,0 @@
--- xen-4.10.0/tools/libxc/xc_pm.c.orig 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/libxc/xc_pm.c 2018-02-10 21:33:02.116856335 +0000
@@ -305,7 +305,7 @@
sysctl.cmd = XEN_SYSCTL_pm_op;
sysctl.u.pm_op.cmd = SET_CPUFREQ_GOV;
sysctl.u.pm_op.cpuid = cpuid;
- strncpy(scaling_governor, govname, CPUFREQ_NAME_LEN);
+ strncpy(scaling_governor, govname, CPUFREQ_NAME_LEN - 1);
scaling_governor[CPUFREQ_NAME_LEN - 1] = '\0';
return xc_sysctl(xch, &sysctl);
--- xen-4.10.0/tools/misc/xenperf.c.orig 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/misc/xenperf.c 2018-02-10 21:46:09.154694376 +0000
@@ -176,7 +176,7 @@
continue;
if ( (j < 64) && hypercall_name_table[j] )
strncpy(hypercall_name, hypercall_name_table[j],
- sizeof(hypercall_name));
+ sizeof(hypercall_name)-1);
else
snprintf(hypercall_name, sizeof(hypercall_name), "[%d]", j);
hypercall_name[sizeof(hypercall_name)-1]='\0';
--- xen-4.10.0/tools/misc/xen-lowmemd.c.orig 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/misc/xen-lowmemd.c 2018-02-10 22:12:45.366114605 +0000
@@ -41,7 +41,7 @@
xc_dominfo_t dom0_info;
xc_physinfo_t info;
unsigned long long free_pages, dom0_pages, diff, dom0_target;
- char data[BUFSZ], error[BUFSZ];
+ char data[BUFSZ], error[BUFSZ + 36];
if (xc_physinfo(xch, &info) < 0)
{
@@ -77,7 +77,7 @@
if (!xs_write(xs_handle, XBT_NULL,
"/local/domain/0/memory/target", data, strlen(data)))
{
- snprintf(error, BUFSZ,"Failed to write target %s to xenstore", data);
+ snprintf(error, BUFSZ + 36,"Failed to write target %s to xenstore", data);
perror(error);
}
}
--- xen-4.10.0/tools/xenpmd/xenpmd.c.orig 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/xenpmd/xenpmd.c 2018-02-10 23:02:16.162049075 +0000
@@ -186,25 +186,25 @@
if ( strstr(attrib_name, "model number") )
{
- strncpy(info->model_number, attrib_value, 32);
+ strncpy(info->model_number, attrib_value, 31);
return;
}
if ( strstr(attrib_name, "serial number") )
{
- strncpy(info->serial_number, attrib_value, 32);
+ strncpy(info->serial_number, attrib_value, 31);
return;
}
if ( strstr(attrib_name, "battery type") )
{
- strncpy(info->battery_type, attrib_value, 32);
+ strncpy(info->battery_type, attrib_value, 31);
return;
}
if ( strstr(attrib_name, "OEM info") )
{
- strncpy(info->oem_info, attrib_value, 32);
+ strncpy(info->oem_info, attrib_value, 31);
return;
}
--- xen-4.10.0/tools/debugger/gdbsx/gx/gx_main.c.orig 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/debugger/gdbsx/gx/gx_main.c 2018-02-10 23:39:39.211459635 +0000
@@ -382,7 +382,7 @@
/* TBD: check if we stopped because of watchpoint */
if (watchpoint_stop()) {
- strncpy(buf, "watch:", 6);
+ strncpy(buf, "watch:", 7);
buf += 6;
/* TBD: **/
}
--- xen-4.10.0/tools/ocaml/libs/xc/xenctrl_stubs.c.orig 2018-02-22 19:09:08.609546441 +0000
+++ xen-4.10.0/tools/ocaml/libs/xc/xenctrl_stubs.c 2018-02-22 19:24:25.622166925 +0000
@@ -54,7 +54,7 @@
static void Noreturn failwith_xc(xc_interface *xch)
{
- char error_str[1028];
+ char error_str[1029];
if (xch) {
const xc_error *error = xc_get_last_error(xch);
if (error->code == XC_ERROR_NONE)
--- xen-4.10.0/tools/libxl/libxl_arm_acpi.c.orig 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/libxl/libxl_arm_acpi.c 2018-02-28 12:37:08.887221211 +0000
@@ -190,7 +190,7 @@
struct acpi_table_rsdp *rsdp = (void *)dom->acpi_modules[0].data + offset;
memcpy(rsdp->signature, "RSD PTR ", sizeof(rsdp->signature));
- memcpy(rsdp->oem_id, ACPI_OEM_ID, sizeof(rsdp->oem_id));
+ memcpy(rsdp->oem_id, ACPI_OEM_ID, sizeof(ACPI_OEM_ID));
rsdp->length = acpitables[RSDP].size;
rsdp->revision = 0x02;
rsdp->xsdt_physical_address = acpitables[XSDT].addr;
@@ -205,11 +205,11 @@
memcpy(h->signature, sig, 4);
h->length = len;
h->revision = rev;
- memcpy(h->oem_id, ACPI_OEM_ID, sizeof(h->oem_id));
- memcpy(h->oem_table_id, ACPI_OEM_TABLE_ID, sizeof(h->oem_table_id));
+ memcpy(h->oem_id, ACPI_OEM_ID, sizeof(ACPI_OEM_ID));
+ memcpy(h->oem_table_id, ACPI_OEM_TABLE_ID, sizeof(ACPI_OEM_TABLE_ID));
h->oem_revision = 0;
memcpy(h->asl_compiler_id, ACPI_ASL_COMPILER_ID,
- sizeof(h->asl_compiler_id));
+ sizeof(ACPI_ASL_COMPILER_ID));
h->asl_compiler_revision = 0;
h->checksum = 0;
}
--- xen-4.10.0/tools/xenpmd/xenpmd.c.orig 2018-02-28 16:18:50.377726049 +0000
+++ xen-4.10.0/tools/xenpmd/xenpmd.c 2018-02-28 16:20:31.502426829 +0000
@@ -352,7 +352,7 @@
strlen(info->model_number) +
strlen(info->serial_number) +
strlen(info->battery_type) +
- strlen(info->oem_info) + 4));
+ strlen(info->oem_info) + 4) & 0xff);
write_ulong_lsb_first(val+2, info->present);
write_ulong_lsb_first(val+10, info->design_capacity);
write_ulong_lsb_first(val+18, info->last_full_capacity);

View file

@ -1,44 +0,0 @@
--- xen-4.10.0/tools/Makefile.orig 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/Makefile 2018-02-27 12:04:44.376192357 +0000
@@ -8,7 +8,7 @@
SUBDIRS-y += libs
SUBDIRS-y += libxc
SUBDIRS-y += flask
-SUBDIRS-y += fuzz
+#SUBDIRS-y += fuzz
SUBDIRS-y += xenstore
SUBDIRS-y += misc
SUBDIRS-y += examples
--- xen-4.10.0/tools/libacpi/Makefile.orig 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/libacpi/Makefile 2018-02-27 21:12:56.928470227 +0000
@@ -89,7 +89,7 @@
@echo
@exit 1
-build.o: ssdt_s3.h ssdt_s4.h ssdt_pm.h ssdt_tpm.h ssdt_laptop_slate.h
+build.o: ssdt_s3.h ssdt_s4.h ssdt_pm.h ssdt_tpm.h ssdt_laptop_slate.h $(H_SRC)
acpi.a: $(OBJS)
$(AR) rc $@ $(OBJS)
--- xen-4.10.0/tools/debugger/kdd/kdd.c.orig 2018-02-22 12:31:57.007039159 +0000
+++ xen-4.10.0/tools/debugger/kdd/kdd.c 2018-02-22 18:27:37.213653422 +0000
@@ -687,7 +687,7 @@
}
} else {
/* 32-bit control-register space starts at 0x[2]cc, for 84 bytes */
- uint64_t offset = addr;
+/* uint64_t offset = addr;
if (offset > 0x200)
offset -= 0x200;
offset -= 0xcc;
@@ -696,7 +696,9 @@
len = 0;
} else {
memcpy(buf, ((uint8_t *)&ctrl.c32) + offset, len);
- }
+ } */
+ /* disable above code due to compile issue for now */
+ len = 0;
}
s->txp.cmd.mem.addr = addr;

23
xen.gcc9.fixes.patch Normal file
View file

@ -0,0 +1,23 @@
--- xen-4.11.1/xen/drivers/passthrough/vtd/vtd.h.orig 2018-11-29 14:04:11.000000000 +0000
+++ xen-4.11.1/xen/drivers/passthrough/vtd/vtd.h 2019-02-05 21:32:50.056774501 +0000
@@ -28,7 +28,7 @@
/* Allow for both IOAPIC and IOSAPIC. */
#define IO_xAPIC_route_entry IO_APIC_route_entry
-struct IO_APIC_route_remap_entry {
+struct __packed IO_APIC_route_remap_entry {
union {
u64 val;
struct {
--- xen-4.11.1/xen/arch/x86/cpu/mtrr/generic.c.orig 2018-11-29 14:04:11.000000000 +0000
+++ xen-4.11.1/xen/arch/x86/cpu/mtrr/generic.c 2019-02-10 19:24:09.378805103 +0000
@@ -171,6 +171,9 @@
printk("%sMTRR variable ranges %sabled:\n", level,
mtrr_state.enabled ? "en" : "dis");
width = (paddr_bits - PAGE_SHIFT + 3) / 4;
+ if ( width > 64 ) {
+ width=64;
+ }
for (i = 0; i < num_var_ranges; ++i) {
if (mtrr_state.var_ranges[i].mask & MTRR_PHYSMASK_VALID)

View file

@ -1,63 +0,0 @@
From 6b8d820bbe5c4aeba8601b31a650f6e6cd12843e Mon Sep 17 00:00:00 2001
From: Jan Beulich <jbeulich@suse.com>
Date: Fri, 18 May 2018 11:39:07 +0200
Subject: [PATCH] x86: correct ordering of operations during S3 resume
Microcode loading needs to happen before re-enabling interrupts, in case
only updated microcode allows the use of e.g. the SPEC_{CTRL,CMD} MSRs.
Otoh it doesn't need to happen at all when we didn't suspend in the
first place. It needs to happen before spin_debug_enable() though, as it
acquires a lock and hence would otherwise make
common/spinlock.c:check_lock() unhappy. As micrcode loading can be
pretty verbose, also make sure it only runs after console_end_sync().
cpufreq_add_cpu() doesn't need calling on the only "goto enable_cpu"
path, which sits ahead of cpufreq_del_cpu().
Reported-by: Simon Gaiser <simon@invisiblethingslab.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Acked-by: Andrew Cooper <andrew.cooper3@citrix.com>
master commit: cb2a4a449dfd50af309a333aa805835015fbc8c8
master date: 2018-04-16 14:08:30 +0200
---
xen/arch/x86/acpi/power.c | 9 ++++++---
1 file changed, 6 insertions(+), 3 deletions(-)
diff --git a/xen/arch/x86/acpi/power.c b/xen/arch/x86/acpi/power.c
index 1e4e5680a7..cb06f842cd 100644
--- a/xen/arch/x86/acpi/power.c
+++ b/xen/arch/x86/acpi/power.c
@@ -203,6 +203,7 @@ static int enter_state(u32 state)
printk(XENLOG_ERR "Some devices failed to power down.");
system_state = SYS_STATE_resume;
device_power_up(error);
+ console_end_sync();
error = -EIO;
goto done;
}
@@ -243,17 +244,19 @@ static int enter_state(u32 state)
if ( (state == ACPI_STATE_S3) && error )
tboot_s3_error(error);
+ console_end_sync();
+
+ microcode_resume_cpu(0);
+
done:
spin_debug_enable();
local_irq_restore(flags);
- console_end_sync();
acpi_sleep_post(state);
if ( hvm_cpu_up() )
BUG();
+ cpufreq_add_cpu(0);
enable_cpu:
- cpufreq_add_cpu(0);
- microcode_resume_cpu(0);
rcu_barrier();
mtrr_aps_sync_begin();
enable_nonboot_cpus();
--
2.11.0

View file

@ -0,0 +1,88 @@
From 90b20547b756a5cf9b0fec9fb0de5b361e8bf4c3 Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Fri, 10 Apr 2026 21:55:46 +0100
Subject: [PATCH] x86/amd: Mitigate AMD-SN-7053 / FP-DSS
MIME-Version: 1.0
Content-Type: text/plain; charset=utf8
Content-Transfer-Encoding: 8bit
This is XSA-488 / CVE-2025-54505
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
(cherry picked from commit 99912d346009fda1e7fb1510c9501fbab17e92a0)
---
xen/arch/x86/cpu/amd.c | 37 ++++++++++++++++++++++++++++
xen/arch/x86/include/asm/msr-index.h | 1 +
2 files changed, 38 insertions(+)
diff --git a/xen/arch/x86/cpu/amd.c b/xen/arch/x86/cpu/amd.c
index 8c55d233f3..1bb0766ebf 100644
--- a/xen/arch/x86/cpu/amd.c
+++ b/xen/arch/x86/cpu/amd.c
@@ -1048,6 +1048,42 @@ void amd_init_de_cfg(const struct cpuinfo_x86 *c)
wrmsrl(MSR_AMD64_DE_CFG, val | new);
}
+static void amd_init_fp_cfg(const struct cpuinfo_x86 *c)
+{
+ uint64_t val, new = 0;
+
+ /* If virtualised, we won't have mutable access even if we can read it. */
+ if ( cpu_has_hypervisor )
+ return;
+
+ /*
+ * On Zen1, mitigate SB-7053 / FP-DSS Floating Point Divider State
+ * Sampling by setting bit 9 as instructed.
+ */
+ if ( c->family == 0x17 && is_zen1_uarch() )
+ new |= 1 << 9;
+
+ /*
+ * Avoid reading FP_CFG if we don't intend to change anything. The
+ * register doesn't exist on all families.
+ */
+ if ( !new )
+ return;
+
+ val = rdmsr(MSR_AMD64_FP_CFG);
+
+ if ( (val & new) == new )
+ return;
+
+ /*
+ * FP_CFG is a Core-scoped MSR, and this write is racy. However, both
+ * threads calculate the new value from state which expected to be
+ * consistent across CPUs and unrelated to the old value, so the result
+ * should be consistent.
+ */
+ wrmsr(MSR_AMD64_FP_CFG, val | new);
+}
+
void __init amd_init_lfence_dispatch(void)
{
struct cpuinfo_x86 *c = &boot_cpu_data;
@@ -1120,6 +1156,7 @@ static void cf_check init_amd(struct cpuinfo_x86 *c)
uint64_t value;
amd_init_de_cfg(c);
+ amd_init_fp_cfg(c);
if (c == &boot_cpu_data)
amd_init_lfence_dispatch(); /* Needs amd_init_de_cfg() */
diff --git a/xen/arch/x86/include/asm/msr-index.h b/xen/arch/x86/include/asm/msr-index.h
index df52587c85..6c5b2569e1 100644
--- a/xen/arch/x86/include/asm/msr-index.h
+++ b/xen/arch/x86/include/asm/msr-index.h
@@ -428,6 +428,7 @@
#define MSR_AMD64_LS_CFG 0xc0011020U
#define MSR_AMD64_IC_CFG 0xc0011021U
#define MSR_AMD64_DC_CFG 0xc0011022U
+#define MSR_AMD64_FP_CFG 0xc0011028U
#define MSR_AMD64_DE_CFG 0xc0011029U
#define AMD64_DE_CFG_LFENCE_SERIALISE (_AC(1, ULL) << 1)
#define MSR_AMD64_EX_CFG 0xc001102cU
--
2.39.5

View file

@ -1,148 +0,0 @@
From a7f8880adc1604335e42920340c127ba7c51b0a5 Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Fri, 18 May 2018 11:41:53 +0200
Subject: [PATCH] x86/spec_ctrl: Updates to retpoline-safety decision making
All of this is as recommended by the Intel whitepaper:
https://software.intel.com/sites/default/files/managed/1d/46/Retpoline-A-Branch-Target-Injection-Mitigation.pdf
The 'RSB Alternative' bit in MSR_ARCH_CAPABILITIES may be set by a hypervisor
to indicate that the virtual machine may migrate to a processor which isn't
retpoline-safe. Introduce a shortened name (to reduce code volume), treat it
as authorative in retpoline_safe(), and print its value along with the other
ARCH_CAPS bits.
The exact processor models which do have RSB semantics which fall back to BTB
predictions are enumerated, and include Kabylake and Coffeelake. Leave a
printk() in the default case to help identify cases which aren't covered.
The exact microcode versions from Broadwell RSB-safety are taken from the
referenced microcode update file (adjusting for the known-bad microcode
versions). Despite the exact wording of the text, it is only Broadwell
processors which need a microcode check.
In practice, this means that all Broadwell hardware with up-to-date microcode
will use retpoline in preference to IBRS, which will be a performance
improvement for desktop and server systems which would previously always opt
for IBRS over retpoline.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
x86/spec_ctrl: Fix typo in ARCH_CAPS decode
Reported-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Acked-by: Jan Beulich <jbeulich@suse.com>
master commit: 1232378bd2fef45f613db049b33852fdf84d7ddf
master date: 2018-04-19 17:28:23 +0100
master commit: 27170adb54a558e11defcd51989326a9beb95afe
master date: 2018-04-24 13:34:12 +0100
---
xen/arch/x86/spec_ctrl.c | 51 +++++++++++++++++++++++++++++++++++------
xen/include/asm-x86/msr-index.h | 1 +
2 files changed, 45 insertions(+), 7 deletions(-)
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index 3c7447bfe6..fa67a0ffbd 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -97,12 +97,13 @@ static void __init print_details(enum ind_thunk thunk)
printk(XENLOG_DEBUG "Speculative mitigation facilities:\n");
/* Hardware features which pertain to speculative mitigations. */
- printk(XENLOG_DEBUG " Hardware features:%s%s%s%s%s\n",
+ printk(XENLOG_DEBUG " Hardware features:%s%s%s%s%s%s\n",
(_7d0 & cpufeat_mask(X86_FEATURE_IBRSB)) ? " IBRS/IBPB" : "",
(_7d0 & cpufeat_mask(X86_FEATURE_STIBP)) ? " STIBP" : "",
(e8b & cpufeat_mask(X86_FEATURE_IBPB)) ? " IBPB" : "",
(caps & ARCH_CAPABILITIES_IBRS_ALL) ? " IBRS_ALL" : "",
- (caps & ARCH_CAPABILITIES_RDCL_NO) ? " RDCL_NO" : "");
+ (caps & ARCH_CAPABILITIES_RDCL_NO) ? " RDCL_NO" : "",
+ (caps & ARCH_CAPS_RSBA) ? " RSBA" : "");
/* Compiled-in support which pertains to BTI mitigations. */
if ( IS_ENABLED(CONFIG_INDIRECT_THUNK) )
@@ -135,6 +136,20 @@ static bool __init retpoline_safe(void)
boot_cpu_data.x86 != 6 )
return false;
+ if ( boot_cpu_has(X86_FEATURE_ARCH_CAPS) )
+ {
+ uint64_t caps;
+
+ rdmsrl(MSR_ARCH_CAPABILITIES, caps);
+
+ /*
+ * RBSA may be set by a hypervisor to indicate that we may move to a
+ * processor which isn't retpoline-safe.
+ */
+ if ( caps & ARCH_CAPS_RSBA )
+ return false;
+ }
+
switch ( boot_cpu_data.x86_model )
{
case 0x17: /* Penryn */
@@ -161,18 +176,40 @@ static bool __init retpoline_safe(void)
* versions.
*/
case 0x3d: /* Broadwell */
- return ucode_rev >= 0x28;
+ return ucode_rev >= 0x2a;
case 0x47: /* Broadwell H */
- return ucode_rev >= 0x1b;
+ return ucode_rev >= 0x1d;
case 0x4f: /* Broadwell EP/EX */
- return ucode_rev >= 0xb000025;
+ return ucode_rev >= 0xb000021;
case 0x56: /* Broadwell D */
- return false; /* TBD. */
+ switch ( boot_cpu_data.x86_mask )
+ {
+ case 2: return ucode_rev >= 0x15;
+ case 3: return ucode_rev >= 0x7000012;
+ case 4: return ucode_rev >= 0xf000011;
+ case 5: return ucode_rev >= 0xe000009;
+ default:
+ printk("Unrecognised CPU stepping %#x - assuming not reptpoline safe\n",
+ boot_cpu_data.x86_mask);
+ return false;
+ }
+ break;
/*
- * Skylake and later processors are not retpoline-safe.
+ * Skylake, Kabylake and Cannonlake processors are not retpoline-safe.
*/
+ case 0x4e:
+ case 0x55:
+ case 0x5e:
+ case 0x66:
+ case 0x67:
+ case 0x8e:
+ case 0x9e:
+ return false;
+
default:
+ printk("Unrecognised CPU model %#x - assuming not reptpoline safe\n",
+ boot_cpu_data.x86_model);
return false;
}
}
diff --git a/xen/include/asm-x86/msr-index.h b/xen/include/asm-x86/msr-index.h
index a8ceecf3e2..bb6295790c 100644
--- a/xen/include/asm-x86/msr-index.h
+++ b/xen/include/asm-x86/msr-index.h
@@ -42,6 +42,7 @@
#define MSR_ARCH_CAPABILITIES 0x0000010a
#define ARCH_CAPABILITIES_RDCL_NO (_AC(1, ULL) << 0)
#define ARCH_CAPABILITIES_IBRS_ALL (_AC(1, ULL) << 1)
+#define ARCH_CAPS_RSBA (_AC(1, ULL) << 2)
/* Intel MSRs. Some also available on other CPUs */
#define MSR_IA32_PERFCTR0 0x000000c1
--
2.11.0

View file

@ -1,77 +0,0 @@
From d93ae631a49289992dabb7bcd08358afc5f22b56 Mon Sep 17 00:00:00 2001
From: Jan Beulich <jbeulich@suse.com>
Date: Fri, 18 May 2018 11:39:38 +0200
Subject: [PATCH] x86: suppress BTI mitigations around S3 suspend/resume
NMI and #MC can occur at any time after S3 resume, yet the MSR_SPEC_CTRL
may become available only once we're reloaded microcode. Make
SPEC_CTRL_ENTRY_FROM_INTR_IST and DO_SPEC_CTRL_EXIT_TO_XEN no-ops for
the critical period of time.
Also set the MSR back to its intended value.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Acked-by: Andrew Cooper <andrew.cooper3@citrix.com>
x86: Use spec_ctrl_{enter,exit}_idle() in the S3/S5 path
The main purpose of this patch is to avoid opencoding the recovery logic at
the end, but also has the positive side effect of relaxing the SPEC_CTRL
mitigations when working to shut the final CPU down.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
master commit: 710a8ebf2bc111a34bba04d1c85b6d07ed3d9389
master date: 2018-04-16 14:09:55 +0200
master commit: ef3ab46493f650b7e5cca2b2578a99ca0cbff195
master date: 2018-04-19 10:55:59 +0100
---
xen/arch/x86/acpi/power.c | 11 +++++++++++
1 file changed, 11 insertions(+)
diff --git a/xen/arch/x86/acpi/power.c b/xen/arch/x86/acpi/power.c
index cb06f842cd..f7085d3c7b 100644
--- a/xen/arch/x86/acpi/power.c
+++ b/xen/arch/x86/acpi/power.c
@@ -28,6 +28,7 @@
#include <asm/tboot.h>
#include <asm/apic.h>
#include <asm/io_apic.h>
+#include <asm/spec_ctrl.h>
#include <acpi/cpufreq/cpufreq.h>
uint32_t system_reset_counter = 1;
@@ -163,6 +164,7 @@ static int enter_state(u32 state)
{
unsigned long flags;
int error;
+ struct cpu_info *ci;
unsigned long cr4;
if ( (state <= ACPI_STATE_S0) || (state > ACPI_S_STATES_MAX) )
@@ -210,6 +212,11 @@ static int enter_state(u32 state)
else
error = 0;
+ ci = get_cpu_info();
+ spec_ctrl_enter_idle(ci);
+ /* Avoid NMI/#MC using MSR_SPEC_CTRL until we've reloaded microcode. */
+ ci->bti_ist_info = 0;
+
ACPI_FLUSH_CPU_CACHE();
switch ( state )
@@ -248,6 +255,10 @@ static int enter_state(u32 state)
microcode_resume_cpu(0);
+ /* Re-enabled default NMI/#MC use of MSR_SPEC_CTRL. */
+ ci->bti_ist_info = default_bti_ist_info;
+ spec_ctrl_exit_idle(ci);
+
done:
spin_debug_enable();
local_irq_restore(flags);
--
2.11.0

View file

@ -1,20 +0,0 @@
--- xen-4.7.0/tools/blktap2/control/tap-ctl-allocate.c.orig 2016-06-20 11:38:15.000000000 +0100
+++ xen-4.7.0/tools/blktap2/control/tap-ctl-allocate.c 2016-09-02 10:07:55.964084808 +0100
@@ -36,6 +36,7 @@
#include <sys/stat.h>
#include <sys/types.h>
#include <sys/ioctl.h>
+#include <sys/sysmacros.h>
#include <linux/major.h>
#include "tap-ctl.h"
--- xen-4.7.0/tools/libxl/libxl_internal.h.orig 2016-06-20 11:38:15.000000000 +0100
+++ xen-4.7.0/tools/libxl/libxl_internal.h 2016-09-02 17:35:24.853783711 +0100
@@ -47,6 +47,7 @@
#include <sys/socket.h>
#include <sys/file.h>
#include <sys/ioctl.h>
+#include <sys/sysmacros.h>
#include <xenevtchn.h>
#include <xenstore.h>

View file

@ -1,79 +1,208 @@
#
# Automatically generated file; DO NOT EDIT.
# Xen/x86 4.10.0 Configuration
# Xen/x86 4.20 Configuration
#
CONFIG_CC_IS_GCC=y
CONFIG_GCC_VERSION=150001
CONFIG_CLANG_VERSION=0
CONFIG_LD_IS_GNU=y
CONFIG_CC_HAS_VISIBILITY_ATTRIBUTE=y
CONFIG_CC_SPLIT_SECTIONS=y
CONFIG_FUNCTION_ALIGNMENT_16B=y
CONFIG_FUNCTION_ALIGNMENT=16
CONFIG_X86_64=y
CONFIG_X86=y
CONFIG_ARCH_DEFCONFIG="arch/x86/configs/x86_64_defconfig"
CONFIG_CC_HAS_INDIRECT_THUNK=y
CONFIG_HAS_AS_CET_SS=y
CONFIG_HAS_CC_CET_IBT=y
#
# Architecture Features
#
CONFIG_AMD=y
CONFIG_INTEL=y
CONFIG_64BIT=y
CONFIG_NR_CPUS=256
CONFIG_NR_NUMA_NODES=64
CONFIG_PV=y
CONFIG_PV32=y
CONFIG_PV_LINEAR_PT=y
CONFIG_HVM=y
CONFIG_AMD_SVM=y
CONFIG_INTEL_VMX=y
CONFIG_XEN_SHSTK=y
CONFIG_XEN_IBT=y
CONFIG_SHADOW_PAGING=y
# CONFIG_BIGMEM is not set
# CONFIG_HVM_FEP is not set
CONFIG_TBOOT=y
CONFIG_HVM_FEP=y
CONFIG_X86_PSR=y
CONFIG_XEN_ALIGN_DEFAULT=y
# CONFIG_XEN_ALIGN_2M is not set
# CONFIG_X2APIC_PHYSICAL is not set
CONFIG_X2APIC_MIXED=y
# CONFIG_XEN_GUEST is not set
# CONFIG_HYPERV_GUEST is not set
# CONFIG_REQUIRE_NX is not set
CONFIG_ALTP2M=y
# end of Architecture Features
#
# Common Features
#
CONFIG_COMPAT=y
CONFIG_CORE_PARKING=y
CONFIG_GRANT_TABLE=y
CONFIG_ALTERNATIVE_CALL=y
CONFIG_ARCH_MAP_DOMAIN_PAGE=y
CONFIG_GENERIC_BUG_FRAME=y
CONFIG_HAS_ALTERNATIVE=y
CONFIG_HAS_COMPAT=y
CONFIG_HAS_DIT=y
CONFIG_HAS_EX_TABLE=y
CONFIG_HAS_MEM_ACCESS=y
CONFIG_HAS_MEM_PAGING=y
CONFIG_HAS_MEM_SHARING=y
CONFIG_HAS_PDX=y
CONFIG_HAS_KEXEC=y
CONFIG_HAS_GDBSX=y
CONFIG_HAS_FAST_MULTIPLY=y
CONFIG_HAS_IOPORTS=y
CONFIG_HAS_KEXEC=y
CONFIG_HAS_PIRQ=y
CONFIG_HAS_SCHED_GRANULARITY=y
CONFIG_HAS_UBSAN=y
CONFIG_HAS_VMAP=y
CONFIG_MEM_ACCESS_ALWAYS_ON=y
CONFIG_MEM_ACCESS=y
CONFIG_NEEDS_LIBELF=y
CONFIG_NUMA=y
#
# Speculative hardening
#
CONFIG_INDIRECT_THUNK=y
CONFIG_RETURN_THUNK=y
CONFIG_SPECULATIVE_HARDEN_ARRAY=y
CONFIG_SPECULATIVE_HARDEN_BRANCH=y
CONFIG_SPECULATIVE_HARDEN_GUEST_ACCESS=y
CONFIG_SPECULATIVE_HARDEN_LOCK=y
# end of Speculative hardening
# CONFIG_DIT_DEFAULT is not set
CONFIG_HYPFS=y
CONFIG_HYPFS_CONFIG=y
CONFIG_IOREQ_SERVER=y
CONFIG_KEXEC=y
CONFIG_TMEM=y
CONFIG_XENOPROF=y
# CONFIG_XSM is not set
CONFIG_SCHED_CREDIT=y
CONFIG_SCHED_CREDIT2=y
CONFIG_SCHED_RTDS=y
CONFIG_SCHED_ARINC653=y
CONFIG_SCHED_NULL=y
CONFIG_SCHED_DEFAULT="credit"
CONFIG_CRYPTO=y
CONFIG_SCHED_DEFAULT="credit2"
# CONFIG_BOOT_TIME_CPUPOOLS is not set
CONFIG_LIVEPATCH=y
CONFIG_FAST_SYMBOL_LOOKUP=y
CONFIG_ENFORCE_UNIQUE_SYMBOLS=y
CONFIG_CMDLINE=""
CONFIG_DOM0_MEM=""
CONFIG_DTB_FILE=""
CONFIG_TRACEBUFFER=y
# end of Common Features
#
# Device Drivers
#
CONFIG_ACPI=y
CONFIG_ACPI_LEGACY_TABLES_LOOKUP=y
CONFIG_NUMA=y
CONFIG_ACPI_NUMA=y
CONFIG_HAS_NS16550=y
CONFIG_HAS_EHCI=y
CONFIG_SERIAL_TX_BUFSIZE=32768
# CONFIG_XHCI is not set
CONFIG_HAS_CPUFREQ=y
CONFIG_HAS_PASSTHROUGH=y
CONFIG_AMD_IOMMU=y
CONFIG_INTEL_IOMMU=y
# CONFIG_IOMMU_QUARANTINE_NONE is not set
CONFIG_IOMMU_QUARANTINE_BASIC=y
# CONFIG_IOMMU_QUARANTINE_SCRATCH_PAGE is not set
CONFIG_HAS_PCI=y
CONFIG_HAS_PCI_MSI=y
CONFIG_VIDEO=y
CONFIG_VGA=y
CONFIG_DEFCONFIG_LIST="$ARCH_DEFCONFIG"
CONFIG_XEN_GUEST=n
CONFIG_HAS_VPCI=y
# end of Device Drivers
# CONFIG_EXPERT is not set
# CONFIG_UNSUPPORTED is not set
CONFIG_ARCH_SUPPORTS_INT128=y
CONFIG_ARCH_VCPU_IOREQ_COMPLETION=y
#
# Debugging Options
#
# CONFIG_DEBUG is not set
CONFIG_GDBSX=y
CONFIG_FRAME_POINTER=y
CONFIG_SELF_TESTS=y
# CONFIG_DEBUG_LOCK_PROFILE is not set
CONFIG_DEBUG_LOCKS=y
# CONFIG_PERF_COUNTERS is not set
CONFIG_VERBOSE_DEBUG=y
CONFIG_SCRUB_DEBUG=y
# CONFIG_UBSAN is not set
# CONFIG_DEBUG_TRACE is not set
CONFIG_XMEM_POOL_POISON=y
CONFIG_DEBUG_INFO=y
# end of Debugging Options
# ARM64 settings
CONFIG_MMU=y
CONFIG_ARM_64=y
CONFIG_ARM=y
CONFIG_ARM_EFI=y
CONFIG_GICV2=y
CONFIG_GICV3=y
CONFIG_VGICV2=y
# CONFIG_NEW_VGIC is not set
CONFIG_SBSA_VUART_CONSOLE=y
CONFIG_HWDOM_VUART=y
CONFIG_ARM_SSBD=y
CONFIG_HARDEN_BRANCH_PREDICTOR=y
CONFIG_STATIC_EVTCHN=y
CONFIG_PARTIAL_EMULATION=y
#
# ARM errata workaround via the alternative framework
#
CONFIG_ARM64_ERRATUM_827319=y
CONFIG_ARM64_ERRATUM_824069=y
CONFIG_ARM64_ERRATUM_819472=y
CONFIG_ARM64_ERRATUM_843419=y
CONFIG_ARM64_ERRATUM_832075=y
CONFIG_ARM64_ERRATUM_834220=y
CONFIG_ARM_ERRATUM_858921=y
CONFIG_ARM64_WORKAROUND_REPEAT_TLBI=y
CONFIG_ARM64_ERRATUM_1286807=y
CONFIG_ARM64_ERRATUM_1508412=y
CONFIG_SBSA_VUART_CONSOLE=y
# end of ARM errata workaround via the alternative framework
CONFIG_ARM64_HARDEN_BRANCH_PREDICTOR=y
CONFIG_ALL_PLAT=y
# CONFIG_QEMU is not set
# CONFIG_RCAR3 is not set
# CONFIG_MPSOC is not set
# CONFIG_NO_PLAT is not set
CONFIG_ALL64_PLAT=y
CONFIG_MPSOC_PLATFORM=y
#
# Common Features
#
CONFIG_HAS_DEVICE_TREE=y
CONFIG_HAS_CADENCE_UART=y
CONFIG_HAS_LINFLEX=y
CONFIG_HAS_IMX_LPUART=y
CONFIG_HAS_MVEBU=y
CONFIG_HAS_MESON=y
CONFIG_HAS_PL011=y
CONFIG_HAS_OMAP=y
CONFIG_HAS_SCIF=y
CONFIG_ARM_SMMU=y
# CONFIG_IPMMU_VMSA is not set

View file

@ -1,20 +0,0 @@
--- xen-4.10.1/tools/libacpi/Makefile.orig 2018-06-15 22:05:18.875735520 +0100
+++ xen-4.10.1/tools/libacpi/Makefile 2018-06-15 22:07:16.087982920 +0100
@@ -43,7 +43,7 @@
$(H_SRC): $(ACPI_BUILD_DIR)/%.h: %.asl iasl
iasl -vs -p $(ACPI_BUILD_DIR)/$*.$(TMP_SUFFIX) -tc $<
- sed -e 's/AmlCode/$*/g' $(ACPI_BUILD_DIR)/$*.hex >$@
+ sed -e 's/_aml_code//g' $(ACPI_BUILD_DIR)/$*.hex >$@
rm -f $(addprefix $(ACPI_BUILD_DIR)/, $*.aml $*.hex)
$(MK_DSDT): mk_dsdt.c
@@ -76,7 +76,7 @@
$(C_SRC): $(ACPI_BUILD_DIR)/%.c: iasl $(ACPI_BUILD_DIR)/%.asl
iasl -vs -p $(ACPI_BUILD_DIR)/$*.$(TMP_SUFFIX) -tc $(ACPI_BUILD_DIR)/$*.asl
- sed -e 's/AmlCode/$*/g' $(ACPI_BUILD_DIR)/$*.hex > $@.$(TMP_SUFFIX)
+ sed -e 's/_aml_code//g' $(ACPI_BUILD_DIR)/$*.hex > $@.$(TMP_SUFFIX)
echo "int $*_len=sizeof($*);" >> $@.$(TMP_SUFFIX)
mv -f $@.$(TMP_SUFFIX) $@
rm -f $(addprefix $(ACPI_BUILD_DIR)/, $*.aml $*.hex)

27
xen.json.nocpuid.patch Normal file
View file

@ -0,0 +1,27 @@
--- xen-4.21.0/tools/libs/light/libxl_nocpuid.c.orig 2025-11-18 18:02:13.000000000 +0000
+++ xen-4.21.0/tools/libs/light/libxl_nocpuid.c 2025-11-20 09:03:56.517804514 +0000
@@ -40,11 +40,24 @@
return 0;
}
+#ifdef HAVE_LIBJSONC
+#ifndef _hidden
+#define _hidden
+#endif
+_hidden int libxl_cpuid_policy_list_gen_jso(json_object **jso_r,
+ libxl_cpuid_policy_list *pcpuid)
+{
+ return 0;
+}
+#endif
+
+#if defined(HAVE_LIBYAJL)
yajl_gen_status libxl_cpuid_policy_list_gen_json(yajl_gen hand,
libxl_cpuid_policy_list *pcpuid)
{
return 0;
}
+#endif
int libxl__cpuid_policy_list_parse_json(libxl__gc *gc,
const libxl__json_object *o,

View file

@ -1,214 +0,0 @@
--- xen-4.10.0/tools/ocaml/libs/xc/xenctrl.ml.orig 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/ocaml/libs/xc/xenctrl.ml 2017-12-16 15:01:29.683432280 +0000
@@ -263,7 +263,7 @@
(* coredump *)
let coredump xch domid fd =
let dump s =
- let wd = Unix.write fd s 0 (String.length s) in
+ let wd = Unix.write fd (Bytes.of_string s) 0 (String.length s) in
if wd <> String.length s then
failwith "error while writing";
in
--- xen-4.10.0/tools/ocaml/libs/xb/xb.ml.orig 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/ocaml/libs/xb/xb.ml 2017-12-16 16:30:25.195726461 +0000
@@ -40,7 +40,7 @@
type backend = Fd of backend_fd | Xenmmap of backend_mmap
-type partial_buf = HaveHdr of Partial.pkt | NoHdr of int * string
+type partial_buf = HaveHdr of Partial.pkt | NoHdr of int * bytes
type t =
{
@@ -52,7 +52,7 @@
}
let init_partial_in () = NoHdr
- (Partial.header_size (), String.make (Partial.header_size()) '\000')
+ (Partial.header_size (), Bytes.make (Partial.header_size()) '\000')
let reconnect t = match t.backend with
| Fd _ ->
@@ -76,7 +76,9 @@
rd
let read_mmap back con s len =
- let rd = Xs_ring.read back.mmap s len in
+ let stmp = String.make len (char_of_int 0) in
+ let rd = Xs_ring.read back.mmap stmp len in
+ Bytes.blit_string stmp 0 s 0 rd;
back.work_again <- (rd > 0);
if rd > 0 then
back.eventchn_notify ();
@@ -100,7 +98,7 @@
let write con s len =
match con.backend with
- | Fd backfd -> write_fd backfd con s len
+ | Fd backfd -> write_fd backfd con (Bytes.of_string s) len
| Xenmmap backmmap -> write_mmap backmmap con s len
(* NB: can throw Reconnect *)
@@ -131,7 +129,7 @@
| NoHdr (i, buf) -> i in
(* try to get more data from input stream *)
- let s = String.make to_read '\000' in
+ let s = Bytes.make to_read '\000' in
let sz = if to_read > 0 then read con s to_read else 0 in
(
@@ -139,7 +137,7 @@
| HaveHdr partial_pkt ->
(* we complete the data *)
if sz > 0 then
- Partial.append partial_pkt s sz;
+ Partial.append partial_pkt (Bytes.to_string s) sz;
if Partial.to_complete partial_pkt = 0 then (
let pkt = Packet.of_partialpkt partial_pkt in
con.partial_in <- init_partial_in ();
@@ -149,9 +147,9 @@
| NoHdr (i, buf) ->
(* we complete the partial header *)
if sz > 0 then
- String.blit s 0 buf (Partial.header_size () - i) sz;
+ Bytes.blit s 0 buf (Partial.header_size () - i) sz;
con.partial_in <- if sz = i then
- HaveHdr (Partial.of_string buf) else NoHdr (i - sz, buf)
+ HaveHdr (Partial.of_string (Bytes.to_string buf)) else NoHdr (i - sz, buf)
);
!newpacket
--- xen-4.10.0/tools/ocaml/libs/xb/xb.mli.orig 2018-03-09 19:02:47.853172392 +0000
+++ xen-4.10.0/tools/ocaml/libs/xb/xb.mli 2017-12-13 11:37:59.000000000 +0000
@@ -65,7 +65,7 @@
}
type backend_fd = { fd : Unix.file_descr; }
type backend = Fd of backend_fd | Xenmmap of backend_mmap
-type partial_buf = HaveHdr of Partial.pkt | NoHdr of int * string
+type partial_buf = HaveHdr of Partial.pkt | NoHdr of int * bytes
type t = {
backend : backend;
pkt_in : Packet.t Queue.t;
@@ -76,10 +76,10 @@
val init_partial_in : unit -> partial_buf
val reconnect : t -> unit
val queue : t -> Packet.t -> unit
-val read_fd : backend_fd -> 'a -> string -> int -> int
-val read_mmap : backend_mmap -> 'a -> string -> int -> int
-val read : t -> string -> int -> int
-val write_fd : backend_fd -> 'a -> string -> int -> int
+val read_fd : backend_fd -> 'a -> bytes -> int -> int
+val read_mmap : backend_mmap -> 'a -> bytes -> int -> int
+val read : t -> bytes -> int -> int
+val write_fd : backend_fd -> 'a -> bytes -> int -> int
val write_mmap : backend_mmap -> 'a -> string -> int -> int
val write : t -> string -> int -> int
val output : t -> bool
--- xen-4.10.0/tools/ocaml/xenstored/stdext.ml.orig 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/ocaml/xenstored/stdext.ml 2017-12-16 16:39:35.645109021 +0000
@@ -122,7 +122,7 @@
let pid = Unix.getpid () in
let buf = string_of_int pid ^ "\n" in
let len = String.length buf in
- if Unix.write fd buf 0 len <> len
+ if Unix.write fd (Bytes.of_string buf) 0 len <> len
then failwith "pidfile_write failed";
)
(fun () -> Unix.close fd)
diff -ur xen-4.10.0.orig/tools/ocaml/xenstored/logging.ml xen-4.10.0/tools/ocaml/xenstored/logging.ml
--- xen-4.10.0.orig/tools/ocaml/xenstored/logging.ml 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/ocaml/xenstored/logging.ml 2017-12-16 23:24:47.402606119 +0000
@@ -60,11 +60,11 @@
let truncate_line nb_chars line =
if String.length line > nb_chars - 1 then
let len = max (nb_chars - 1) 2 in
- let dst_line = String.create len in
- String.blit line 0 dst_line 0 (len - 2);
- dst_line.[len-2] <- '.';
- dst_line.[len-1] <- '.';
- dst_line
+ let dst_line = Bytes.create len in
+ Bytes.blit_string line 0 dst_line 0 (len - 2);
+ Bytes.set dst_line (len-2) '.';
+ Bytes.set dst_line (len-1) '.';
+ Bytes.to_string dst_line
else line
let log_rotate ref_ch log_file log_nb_files =
@@ -252,13 +252,13 @@
*)
let sanitize_data data =
- let data = String.copy data in
- for i = 0 to String.length data - 1
+ let data = Bytes.copy data in
+ for i = 0 to Bytes.length data - 1
do
- if data.[i] = '\000' then
- data.[i] <- ' '
+ if Bytes.get data i = '\000' then
+ Bytes.set data i ' '
done;
- String.escaped data
+ String.escaped (Bytes.to_string data)
let activate_access_log = ref true
let access_log_destination = ref (File (Paths.xen_log_dir ^ "/xenstored-access.log"))
@@ -291,7 +291,7 @@
let date = string_of_date() in
let tid = string_of_tid ~con tid in
let access_type = string_of_access_type access_type in
- let data = sanitize_data data in
+ let data = sanitize_data (Bytes.of_string data) in
let prefix = prefix !access_log_destination date in
let msg = Printf.sprintf "%s %s %s %s" prefix tid access_type data in
logger.write ~level msg)
diff -ur xen-4.10.0.orig/tools/ocaml/xenstored/utils.ml xen-4.10.0/tools/ocaml/xenstored/utils.ml
--- xen-4.10.0.orig/tools/ocaml/xenstored/utils.ml 2017-12-13 11:37:59.000000000 +0000
+++ xen-4.10.0/tools/ocaml/xenstored/utils.ml 2017-12-16 23:26:24.968649002 +0000
@@ -45,23 +45,23 @@
let hexify s =
let hexseq_of_char c = sprintf "%02x" (Char.code c) in
- let hs = String.create (String.length s * 2) in
+ let hs = Bytes.create (String.length s * 2) in
for i = 0 to String.length s - 1
do
let seq = hexseq_of_char s.[i] in
- hs.[i * 2] <- seq.[0];
- hs.[i * 2 + 1] <- seq.[1];
+ Bytes.set hs (i * 2) seq.[0];
+ Bytes.set hs (i * 2 + 1) seq.[1];
done;
- hs
+ Bytes.to_string hs
let unhexify hs =
let char_of_hexseq seq0 seq1 = Char.chr (int_of_string (sprintf "0x%c%c" seq0 seq1)) in
- let s = String.create (String.length hs / 2) in
- for i = 0 to String.length s - 1
+ let s = Bytes.create (String.length hs / 2) in
+ for i = 0 to Bytes.length s - 1
do
- s.[i] <- char_of_hexseq hs.[i * 2] hs.[i * 2 + 1]
+ Bytes.set s i (char_of_hexseq hs.[i * 2] hs.[i * 2 + 1])
done;
- s
+ Bytes.to_string s
let trim_path path =
try
@@ -84,10 +84,10 @@
let read_file_single_integer filename =
let fd = Unix.openfile filename [ Unix.O_RDONLY ] 0o640 in
- let buf = String.make 20 (char_of_int 0) in
+ let buf = Bytes.make 20 (char_of_int 0) in
let sz = Unix.read fd buf 0 20 in
Unix.close fd;
- int_of_string (String.sub buf 0 sz)
+ int_of_string (Bytes.to_string (Bytes.sub buf 0 sz))
let path_complete path connection_path =
if String.get path 0 <> '/' then

22
xen.python3.12.patch Normal file
View file

@ -0,0 +1,22 @@
--- xen-4.17.1/tools/python/Makefile.orig 2023-04-27 13:53:19.000000000 +0100
+++ xen-4.17.1/tools/python/Makefile 2023-06-22 22:21:25.287486906 +0100
@@ -4,7 +4,7 @@
.PHONY: all
all: build
-PY_CFLAGS = $(CFLAGS) $(PY_NOOPT_CFLAGS)
+PY_CFLAGS = $(CFLAGS) $(PY_NOOPT_CFLAGS) -Wno-error=declaration-after-statement
PY_LDFLAGS = $(SHLIB_LDFLAGS) $(APPEND_LDFLAGS)
INSTALL_LOG = build/installed_files.txt
--- xen-4.17.1/tools/pygrub/Makefile.orig 2023-04-27 13:53:19.000000000 +0100
+++ xen-4.17.1/tools/pygrub/Makefile 2023-06-22 22:52:52.803047401 +0100
@@ -2,7 +2,7 @@
XEN_ROOT = $(CURDIR)/../..
include $(XEN_ROOT)/tools/Rules.mk
-PY_CFLAGS = $(CFLAGS) $(PY_NOOPT_CFLAGS)
+PY_CFLAGS = $(CFLAGS) $(PY_NOOPT_CFLAGS) -Wno-error=declaration-after-statement
PY_LDFLAGS = $(SHLIB_LDFLAGS) $(APPEND_LDFLAGS)
INSTALL_LOG = build/installed_files.txt

1643
xen.spec

File diff suppressed because it is too large Load diff

View file

@ -1,33 +0,0 @@
--- xen-4.2.0/tools/firmware/hvmloader/Makefile.orig 2012-05-27 21:57:04.481812859 +0100
+++ xen-4.2.0/tools/firmware/hvmloader/Makefile 2012-06-02 18:52:44.935034128 +0100
@@ -48,7 +48,7 @@
else
CIRRUSVGA_ROM := ../vgabios/VGABIOS-lgpl-latest.cirrus.bin
endif
-ETHERBOOT_ROMS := $(addprefix ../etherboot/ipxe/src/bin/, $(addsuffix .rom, $(ETHERBOOT_NICS)))
+ETHERBOOT_ROMS := $(addprefix /usr/share/ipxe/, $(addsuffix .rom, $(ETHERBOOT_NICS)))
endif
ROMS :=
--- xen-4.2.0/Config.mk.orig 2012-05-27 21:57:04.479812884 +0100
+++ xen-4.2.0/Config.mk 2012-06-02 18:55:14.087169469 +0100
@@ -206,7 +206,7 @@
# Wed Jun 22 14:53:24 2016 +0800
# fw/msr_feature_control: add support to set MSR_IA32_FEATURE_CONTROL
-ETHERBOOT_NICS ?= rtl8139 8086100e
+ETHERBOOT_NICS ?= 10ec8139 8086100e
QEMU_TRADITIONAL_REVISION ?= xen-4.10.1
--- xen-4.2.0/tools/firmware/Makefile.orig 2012-05-27 21:57:04.480812871 +0100
+++ xen-4.2.0/tools/firmware/Makefile 2012-06-02 19:03:52.254691484 +0100
@@ -10,7 +10,7 @@
SUBDIRS-$(CONFIG_SEABIOS) += seabios-dir
SUBDIRS-$(CONFIG_ROMBIOS) += rombios
SUBDIRS-$(CONFIG_ROMBIOS) += vgabios
-SUBDIRS-$(CONFIG_ROMBIOS) += etherboot
+#SUBDIRS-$(CONFIG_ROMBIOS) += etherboot
SUBDIRS-$(CONFIG_PV_SHIM) += xen-dir
SUBDIRS-y += hvmloader

View file

@ -1,24 +0,0 @@
--- xen-4.6.3/tools/xenstore/xs.c.orig 2016-06-20 13:08:22.000000000 +0100
+++ xen-4.6.3/tools/xenstore/xs.c 2016-07-10 21:05:57.082217329 +0100
@@ -733,6 +733,7 @@
if (!h->read_thr_exists) {
sigset_t set, old_set;
pthread_attr_t attr;
+ int ptret;
if (pthread_attr_init(&attr) != 0) {
mutex_unlock(&h->request_mutex);
@@ -747,7 +748,12 @@
sigfillset(&set);
pthread_sigmask(SIG_SETMASK, &set, &old_set);
- if (pthread_create(&h->read_thr, &attr, read_thread, h) != 0) {
+ ptret = pthread_create(&h->read_thr, &attr, read_thread, h);
+ if ( (ptret == EINVAL) && (pthread_attr_setstacksize(&attr, READ_THREAD_STACKSIZE + (8*1024)) == 0) ) {
+ /* have a second try with the bigger stacksize */
+ ptret = pthread_create(&h->read_thr, &attr, read_thread, h);
+ }
+ if (ptret != 0) {
pthread_sigmask(SIG_SETMASK, &old_set, NULL);
pthread_attr_destroy(&attr);
mutex_unlock(&h->request_mutex);

View file

@ -1,72 +0,0 @@
From: Andrew Cooper <andrew.cooper3@citrix.com>
Subject: x86/traps: Fix %dr6 handing in #DB handler
Most bits in %dr6 accumulate, rather than being set directly based on the
current source of #DB. Have the handler follow the manuals guidance, which
avoids leaking hypervisor debugging activities into guest context.
This is part of XSA-260 / CVE-2018-8897.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
--- a/xen/arch/x86/traps.c 2018-04-13 15:29:36.006747135 +0200
+++ b/xen/arch/x86/traps.c 2018-04-13 15:44:57.015516185 +0200
@@ -1761,11 +1761,36 @@ static void ler_enable(void)
void do_debug(struct cpu_user_regs *regs)
{
+ unsigned long dr6;
struct vcpu *v = current;
+ /* Stash dr6 as early as possible. */
+ dr6 = read_debugreg(6);
+
if ( debugger_trap_entry(TRAP_debug, regs) )
return;
+ /*
+ * At the time of writing (March 2018), on the subject of %dr6:
+ *
+ * The Intel manual says:
+ * Certain debug exceptions may clear bits 0-3. The remaining contents
+ * of the DR6 register are never cleared by the processor. To avoid
+ * confusion in identifying debug exceptions, debug handlers should
+ * clear the register (except bit 16, which they should set) before
+ * returning to the interrupted task.
+ *
+ * The AMD manual says:
+ * Bits 15:13 of the DR6 register are not cleared by the processor and
+ * must be cleared by software after the contents have been read.
+ *
+ * Some bits are reserved set, some are reserved clear, and some bits
+ * which were previously reserved set are reused and cleared by hardware.
+ * For future compatibility, reset to the default value, which will allow
+ * us to spot any bit being changed by hardware to its non-default value.
+ */
+ write_debugreg(6, X86_DR6_DEFAULT);
+
if ( !guest_mode(regs) )
{
if ( regs->eflags & X86_EFLAGS_TF )
@@ -1798,7 +1823,8 @@ void do_debug(struct cpu_user_regs *regs
}
/* Save debug status register where guest OS can peek at it */
- v->arch.debugreg[6] = read_debugreg(6);
+ v->arch.debugreg[6] |= (dr6 & ~X86_DR6_DEFAULT);
+ v->arch.debugreg[6] &= (dr6 | ~X86_DR6_DEFAULT);
ler_enable();
pv_inject_hw_exception(TRAP_debug, X86_EVENT_NO_EC);
--- a/xen/include/asm-x86/debugreg.h 2015-02-11 09:36:29.000000000 +0100
+++ b/xen/include/asm-x86/debugreg.h 2018-04-13 15:44:57.015516185 +0200
@@ -24,6 +24,8 @@
#define DR_STATUS_RESERVED_ZERO (~0xffffeffful) /* Reserved, read as zero */
#define DR_STATUS_RESERVED_ONE 0xffff0ff0ul /* Reserved, read as one */
+#define X86_DR6_DEFAULT 0xffff0ff0ul /* Default %dr6 value. */
+
/* Now define a bunch of things for manipulating the control register.
The top two bytes of the control register consist of 4 fields of 4
bits - each field corresponds to one of the four debug registers,

View file

@ -1,110 +0,0 @@
From: Andrew Cooper <andrew.cooper3@citrix.com>
Subject: x86/pv: Move exception injection into {,compat_}test_all_events()
This allows paths to jump straight to {,compat_}test_all_events() and have
injection of pending exceptions happen automatically, rather than requiring
all calling paths to handle exceptions themselves.
The normal exception path is simplified as a result, and
compat_post_handle_exception() is removed entirely.
This is part of XSA-260 / CVE-2018-8897.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
--- a/xen/arch/x86/x86_64/compat/entry.S
+++ b/xen/arch/x86/x86_64/compat/entry.S
@@ -39,6 +39,12 @@ ENTRY(compat_test_all_events)
leaq irq_stat+IRQSTAT_softirq_pending(%rip),%rcx
cmpl $0,(%rcx,%rax,1)
jne compat_process_softirqs
+
+ /* Inject exception if pending. */
+ lea VCPU_trap_bounce(%rbx), %rdx
+ testb $TBF_EXCEPTION, TRAPBOUNCE_flags(%rdx)
+ jnz .Lcompat_process_trapbounce
+
testb $1,VCPU_mce_pending(%rbx)
jnz compat_process_mce
.Lcompat_test_guest_nmi:
@@ -68,6 +74,15 @@ compat_process_softirqs:
call do_softirq
jmp compat_test_all_events
+ ALIGN
+/* %rbx: struct vcpu, %rdx: struct trap_bounce */
+.Lcompat_process_trapbounce:
+ sti
+.Lcompat_bounce_exception:
+ call compat_create_bounce_frame
+ movb $0, TRAPBOUNCE_flags(%rdx)
+ jmp compat_test_all_events
+
ALIGN
/* %rbx: struct vcpu */
compat_process_mce:
@@ -189,15 +204,6 @@ ENTRY(cr4_pv32_restore)
xor %eax, %eax
ret
-/* %rdx: trap_bounce, %rbx: struct vcpu */
-ENTRY(compat_post_handle_exception)
- testb $TBF_EXCEPTION,TRAPBOUNCE_flags(%rdx)
- jz compat_test_all_events
-.Lcompat_bounce_exception:
- call compat_create_bounce_frame
- movb $0,TRAPBOUNCE_flags(%rdx)
- jmp compat_test_all_events
-
.section .text.entry, "ax", @progbits
/* See lstar_enter for entry register state. */
--- a/xen/arch/x86/x86_64/entry.S
+++ b/xen/arch/x86/x86_64/entry.S
@@ -42,6 +42,12 @@ test_all_events:
leaq irq_stat+IRQSTAT_softirq_pending(%rip), %rcx
cmpl $0, (%rcx, %rax, 1)
jne process_softirqs
+
+ /* Inject exception if pending. */
+ lea VCPU_trap_bounce(%rbx), %rdx
+ testb $TBF_EXCEPTION, TRAPBOUNCE_flags(%rdx)
+ jnz .Lprocess_trapbounce
+
cmpb $0, VCPU_mce_pending(%rbx)
jne process_mce
.Ltest_guest_nmi:
@@ -70,6 +76,15 @@ process_softirqs:
jmp test_all_events
ALIGN
+/* %rbx: struct vcpu, %rdx struct trap_bounce */
+.Lprocess_trapbounce:
+ sti
+.Lbounce_exception:
+ call create_bounce_frame
+ movb $0, TRAPBOUNCE_flags(%rdx)
+ jmp test_all_events
+
+ ALIGN
/* %rbx: struct vcpu */
process_mce:
testb $1 << VCPU_TRAP_MCE, VCPU_async_exception_mask(%rbx)
@@ -667,15 +682,9 @@ handle_exception_saved:
mov %r15, STACK_CPUINFO_FIELD(xen_cr3)(%r14)
testb $3,UREGS_cs(%rsp)
jz restore_all_xen
- leaq VCPU_trap_bounce(%rbx),%rdx
movq VCPU_domain(%rbx),%rax
testb $1,DOMAIN_is_32bit_pv(%rax)
- jnz compat_post_handle_exception
- testb $TBF_EXCEPTION,TRAPBOUNCE_flags(%rdx)
- jz test_all_events
-.Lbounce_exception:
- call create_bounce_frame
- movb $0,TRAPBOUNCE_flags(%rdx)
+ jnz compat_test_all_events
jmp test_all_events
/* No special register assumptions. */

View file

@ -1,138 +0,0 @@
From: Andrew Cooper <andrew.cooper3@citrix.com>
Subject: x86/traps: Use an Interrupt Stack Table for #DB
PV guests can use architectural corner cases to cause #DB to be raised after
transitioning into supervisor mode.
Use an interrupt stack table for #DB to prevent the exception being taken with
a guest controlled stack pointer.
This is part of XSA-260 / CVE-2018-8897.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
--- a/xen/arch/x86/cpu/common.c
+++ b/xen/arch/x86/cpu/common.c
@@ -679,6 +679,7 @@ void load_system_tables(void)
[IST_MCE - 1] = stack_top + IST_MCE * PAGE_SIZE,
[IST_DF - 1] = stack_top + IST_DF * PAGE_SIZE,
[IST_NMI - 1] = stack_top + IST_NMI * PAGE_SIZE,
+ [IST_DB - 1] = stack_top + IST_DB * PAGE_SIZE,
[IST_MAX ... ARRAY_SIZE(tss->ist) - 1] =
0x8600111111111111ul,
@@ -706,6 +707,7 @@ void load_system_tables(void)
set_ist(&idt_tables[cpu][TRAP_double_fault], IST_DF);
set_ist(&idt_tables[cpu][TRAP_nmi], IST_NMI);
set_ist(&idt_tables[cpu][TRAP_machine_check], IST_MCE);
+ set_ist(&idt_tables[cpu][TRAP_debug], IST_DB);
/*
* Bottom-of-stack must be 16-byte aligned!
--- a/xen/arch/x86/hvm/svm/svm.c
+++ b/xen/arch/x86/hvm/svm/svm.c
@@ -1046,6 +1046,7 @@ static void svm_ctxt_switch_from(struct
set_ist(&idt_tables[cpu][TRAP_double_fault], IST_DF);
set_ist(&idt_tables[cpu][TRAP_nmi], IST_NMI);
set_ist(&idt_tables[cpu][TRAP_machine_check], IST_MCE);
+ set_ist(&idt_tables[cpu][TRAP_debug], IST_DB);
}
static void svm_ctxt_switch_to(struct vcpu *v)
@@ -1067,6 +1068,7 @@ static void svm_ctxt_switch_to(struct vc
set_ist(&idt_tables[cpu][TRAP_double_fault], IST_NONE);
set_ist(&idt_tables[cpu][TRAP_nmi], IST_NONE);
set_ist(&idt_tables[cpu][TRAP_machine_check], IST_NONE);
+ set_ist(&idt_tables[cpu][TRAP_debug], IST_NONE);
svm_restore_dr(v);
--- a/xen/arch/x86/smpboot.c
+++ b/xen/arch/x86/smpboot.c
@@ -964,6 +964,7 @@ static int cpu_smpboot_alloc(unsigned in
set_ist(&idt_tables[cpu][TRAP_double_fault], IST_NONE);
set_ist(&idt_tables[cpu][TRAP_nmi], IST_NONE);
set_ist(&idt_tables[cpu][TRAP_machine_check], IST_NONE);
+ set_ist(&idt_tables[cpu][TRAP_debug], IST_NONE);
for ( stub_page = 0, i = cpu & ~(STUBS_PER_PAGE - 1);
i < nr_cpu_ids && i <= (cpu | (STUBS_PER_PAGE - 1)); ++i )
--- a/xen/arch/x86/traps.c
+++ b/xen/arch/x86/traps.c
@@ -325,13 +325,13 @@ static void show_guest_stack(struct vcpu
/*
* Notes for get_stack_trace_bottom() and get_stack_dump_bottom()
*
- * Stack pages 0, 1 and 2:
+ * Stack pages 0 - 3:
* These are all 1-page IST stacks. Each of these stacks have an exception
* frame and saved register state at the top. The interesting bound for a
* trace is the word adjacent to this, while the bound for a dump is the
* very top, including the exception frame.
*
- * Stack pages 3, 4 and 5:
+ * Stack pages 4 and 5:
* None of these are particularly interesting. With MEMORY_GUARD, page 5 is
* explicitly not present, so attempting to dump or trace it is
* counterproductive. Without MEMORY_GUARD, it is possible for a call chain
@@ -352,12 +352,12 @@ unsigned long get_stack_trace_bottom(uns
{
switch ( get_stack_page(sp) )
{
- case 0 ... 2:
+ case 0 ... 3:
return ROUNDUP(sp, PAGE_SIZE) -
offsetof(struct cpu_user_regs, es) - sizeof(unsigned long);
#ifndef MEMORY_GUARD
- case 3 ... 5:
+ case 4 ... 5:
#endif
case 6 ... 7:
return ROUNDUP(sp, STACK_SIZE) -
@@ -372,11 +372,11 @@ unsigned long get_stack_dump_bottom(unsi
{
switch ( get_stack_page(sp) )
{
- case 0 ... 2:
+ case 0 ... 3:
return ROUNDUP(sp, PAGE_SIZE) - sizeof(unsigned long);
#ifndef MEMORY_GUARD
- case 3 ... 5:
+ case 4 ... 5:
#endif
case 6 ... 7:
return ROUNDUP(sp, STACK_SIZE) - sizeof(unsigned long);
@@ -1943,6 +1943,7 @@ void __init init_idt_traps(void)
set_ist(&idt_table[TRAP_double_fault], IST_DF);
set_ist(&idt_table[TRAP_nmi], IST_NMI);
set_ist(&idt_table[TRAP_machine_check], IST_MCE);
+ set_ist(&idt_table[TRAP_debug], IST_DB);
/* CPU0 uses the master IDT. */
idt_tables[0] = idt_table;
--- a/xen/arch/x86/x86_64/entry.S
+++ b/xen/arch/x86/x86_64/entry.S
@@ -739,7 +739,7 @@ ENTRY(device_not_available)
ENTRY(debug)
pushq $0
movl $TRAP_debug,4(%rsp)
- jmp handle_exception
+ jmp handle_ist_exception
ENTRY(int3)
pushq $0
--- a/xen/include/asm-x86/processor.h
+++ b/xen/include/asm-x86/processor.h
@@ -443,7 +443,8 @@ struct __packed __cacheline_aligned tss_
#define IST_DF 1UL
#define IST_NMI 2UL
#define IST_MCE 3UL
-#define IST_MAX 3UL
+#define IST_DB 4UL
+#define IST_MAX 4UL
/* Set the interrupt stack table used by a particular interrupt
* descriptor table entry. */

View file

@ -1,72 +0,0 @@
From: Andrew Cooper <andrew.cooper3@citrix.com>
Subject: x86/traps: Fix handling of #DB exceptions in hypervisor context
The WARN_ON() can be triggered by guest activities, and emits a full stack
trace without rate limiting. Swap it out for a ratelimited printk with just
enough information to work out what is going on.
Not all #DB exceptions are traps, so blindly continuing is not a safe action
to take. We don't let PV guests select these settings in the real %dr7 to
begin with, but for added safety against unexpected situations, detect the
fault cases and crash in an obvious manner.
This is part of XSA-260 / CVE-2018-8897.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
--- a/xen/arch/x86/traps.c
+++ b/xen/arch/x86/traps.c
@@ -1809,16 +1809,44 @@ void do_debug(struct cpu_user_regs *regs
regs->eflags &= ~X86_EFLAGS_TF;
}
}
- else
+
+ /*
+ * Check for fault conditions. General Detect, and instruction
+ * breakpoints are faults rather than traps, at which point attempting
+ * to ignore and continue will result in a livelock.
+ */
+ if ( dr6 & DR_GENERAL_DETECT )
+ {
+ printk(XENLOG_ERR "Hit General Detect in Xen context\n");
+ fatal_trap(regs, 0);
+ }
+
+ if ( dr6 & (DR_TRAP3 | DR_TRAP2 | DR_TRAP1 | DR_TRAP0) )
{
- /*
- * We ignore watchpoints when they trigger within Xen. This may
- * happen when a buffer is passed to us which previously had a
- * watchpoint set on it. No need to bump EIP; the only faulting
- * trap is an instruction breakpoint, which can't happen to us.
- */
- WARN_ON(!search_exception_table(regs));
+ unsigned int bp, dr7 = read_debugreg(7) >> DR_CONTROL_SHIFT;
+
+ for ( bp = 0; bp < 4; ++bp )
+ {
+ if ( (dr6 & (1u << bp)) && /* Breakpoint triggered? */
+ ((dr7 & (3u << (bp * DR_CONTROL_SIZE))) == 0) /* Insn? */ )
+ {
+ printk(XENLOG_ERR
+ "Hit instruction breakpoint in Xen context\n");
+ fatal_trap(regs, 0);
+ }
+ }
}
+
+ /*
+ * Whatever caused this #DB should be a trap. Note it and continue.
+ * Guests can trigger this in certain corner cases, so ensure the
+ * message is ratelimited.
+ */
+ gprintk(XENLOG_WARNING,
+ "Hit #DB in Xen context: %04x:%p [%ps], stk %04x:%p, dr6 %lx\n",
+ regs->cs, _p(regs->rip), _p(regs->rip),
+ regs->ss, _p(regs->rsp), dr6);
+
goto out;
}

View file

@ -1,279 +0,0 @@
From: Xen Project Security Team <security@xenproject.org>
Subject: x86/vpt: add support for IO-APIC routed interrupts
And modify the HPET code to make use of it. Currently HPET interrupts
are always treated as ISA and thus injected through the vPIC. This is
wrong because HPET interrupts when not in legacy mode should be
injected from the IO-APIC.
To make things worse, the supported interrupt routing values are set
to [20..23], which clearly falls outside of the ISA range, thus
leading to an ASSERT in debug builds or memory corruption in non-debug
builds because the interrupt injection code will write out of the
bounds of the arch.hvm_domain.vpic array.
Since the HPET interrupt source can change between ISA and IO-APIC
always destroy the timer before changing the mode, or else Xen risks
changing it while the timer is active.
Note that vpt interrupt injection is racy in the sense that the
vIO-APIC RTE entry can be written by the guest in between the call to
pt_irq_masked and hvm_ioapic_assert, or the call to pt_update_irq and
pt_intr_post. Those are not deemed to be security issues, but rather
quirks of the current implementation. In the worse case the guest
might lose interrupts or get multiple interrupt vectors injected for
the same timer source.
This is part of XSA-261.
Address actual and potential compiler warnings. Fix formatting.
Signed-off-by: Roger Pau Monné <roger.pau@citrix.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
---
Changes since v2:
- Move fallthrough comment to be just above the case label.
- Fix now stale comment in pt_update_irq.
- Use NR_ISAIRQS instead of 16.
- Expand commit message to mention the quirkiness of vpt interrupt
injection.
Changes since v1:
- Simply usage of gsi in pt_irq_masked.
- Introduce hvm_ioapic_assert.
- Fix pt->source == PTSRC_isa in create_periodic_time.
--- a/xen/arch/x86/hvm/hpet.c
+++ b/xen/arch/x86/hvm/hpet.c
@@ -264,13 +264,20 @@ static void hpet_set_timer(HPETState *h,
diff = (timer_is_32bit(h, tn) && (-diff > HPET_TINY_TIME_SPAN))
? (uint32_t)diff : 0;
+ destroy_periodic_time(&h->pt[tn]);
if ( (tn <= 1) && (h->hpet.config & HPET_CFG_LEGACY) )
+ {
/* if LegacyReplacementRoute bit is set, HPET specification requires
timer0 be routed to IRQ0 in NON-APIC or IRQ2 in the I/O APIC,
timer1 be routed to IRQ8 in NON-APIC or IRQ8 in the I/O APIC. */
irq = (tn == 0) ? 0 : 8;
+ h->pt[tn].source = PTSRC_isa;
+ }
else
+ {
irq = timer_int_route(h, tn);
+ h->pt[tn].source = PTSRC_ioapic;
+ }
/*
* diff is the time from now when the timer should fire, for a periodic
--- a/xen/arch/x86/hvm/irq.c
+++ b/xen/arch/x86/hvm/irq.c
@@ -41,6 +41,26 @@ static void assert_gsi(struct domain *d,
vioapic_irq_positive_edge(d, ioapic_gsi);
}
+int hvm_ioapic_assert(struct domain *d, unsigned int gsi, bool level)
+{
+ struct hvm_irq *hvm_irq = hvm_domain_irq(d);
+ int vector;
+
+ if ( gsi >= hvm_irq->nr_gsis )
+ {
+ ASSERT_UNREACHABLE();
+ return -1;
+ }
+
+ spin_lock(&d->arch.hvm_domain.irq_lock);
+ if ( !level || hvm_irq->gsi_assert_count[gsi]++ == 0 )
+ assert_gsi(d, gsi);
+ vector = vioapic_get_vector(d, gsi);
+ spin_unlock(&d->arch.hvm_domain.irq_lock);
+
+ return vector;
+}
+
static void assert_irq(struct domain *d, unsigned ioapic_gsi, unsigned pic_irq)
{
assert_gsi(d, ioapic_gsi);
--- a/xen/arch/x86/hvm/vpt.c
+++ b/xen/arch/x86/hvm/vpt.c
@@ -107,31 +107,49 @@ static int pt_irq_vector(struct periodic
static int pt_irq_masked(struct periodic_time *pt)
{
struct vcpu *v = pt->vcpu;
- unsigned int gsi, isa_irq;
- int mask;
- uint8_t pic_imr;
+ unsigned int gsi = pt->irq;
- if ( pt->source == PTSRC_lapic )
+ switch ( pt->source )
+ {
+ case PTSRC_lapic:
{
struct vlapic *vlapic = vcpu_vlapic(v);
+
return (!vlapic_enabled(vlapic) ||
(vlapic_get_reg(vlapic, APIC_LVTT) & APIC_LVT_MASKED));
}
- isa_irq = pt->irq;
- gsi = hvm_isa_irq_to_gsi(isa_irq);
- pic_imr = v->domain->arch.hvm_domain.vpic[isa_irq >> 3].imr;
- mask = vioapic_get_mask(v->domain, gsi);
- if ( mask < 0 )
- {
- dprintk(XENLOG_WARNING, "d%u: invalid GSI (%u) for platform timer\n",
- v->domain->domain_id, gsi);
- domain_crash(v->domain);
- return -1;
+ case PTSRC_isa:
+ {
+ uint8_t pic_imr = v->domain->arch.hvm_domain.vpic[pt->irq >> 3].imr;
+
+ /* Check if the interrupt is unmasked in the PIC. */
+ if ( !(pic_imr & (1 << (pt->irq & 7))) && vlapic_accept_pic_intr(v) )
+ return 0;
+
+ gsi = hvm_isa_irq_to_gsi(pt->irq);
+ }
+
+ /* Fallthrough to check if the interrupt is masked on the IO APIC. */
+ case PTSRC_ioapic:
+ {
+ int mask = vioapic_get_mask(v->domain, gsi);
+
+ if ( mask < 0 )
+ {
+ dprintk(XENLOG_WARNING,
+ "d%d: invalid GSI (%u) for platform timer\n",
+ v->domain->domain_id, gsi);
+ domain_crash(v->domain);
+ return -1;
+ }
+
+ return mask;
+ }
}
- return (((pic_imr & (1 << (isa_irq & 7))) || !vlapic_accept_pic_intr(v)) &&
- mask);
+ ASSERT_UNREACHABLE();
+ return 1;
}
static void pt_lock(struct periodic_time *pt)
@@ -252,7 +270,7 @@ int pt_update_irq(struct vcpu *v)
struct list_head *head = &v->arch.hvm_vcpu.tm_list;
struct periodic_time *pt, *temp, *earliest_pt;
uint64_t max_lag;
- int irq, is_lapic, pt_vector;
+ int irq, pt_vector = -1;
spin_lock(&v->arch.hvm_vcpu.tm_lock);
@@ -288,29 +306,26 @@ int pt_update_irq(struct vcpu *v)
earliest_pt->irq_issued = 1;
irq = earliest_pt->irq;
- is_lapic = (earliest_pt->source == PTSRC_lapic);
spin_unlock(&v->arch.hvm_vcpu.tm_lock);
- /*
- * If periodic timer interrut is handled by lapic, its vector in
- * IRR is returned and used to set eoi_exit_bitmap for virtual
- * interrupt delivery case. Otherwise return -1 to do nothing.
- */
- if ( is_lapic )
+ switch ( earliest_pt->source )
{
+ case PTSRC_lapic:
+ /*
+ * If periodic timer interrupt is handled by lapic, its vector in
+ * IRR is returned and used to set eoi_exit_bitmap for virtual
+ * interrupt delivery case. Otherwise return -1 to do nothing.
+ */
vlapic_set_irq(vcpu_vlapic(v), irq, 0);
pt_vector = irq;
- }
- else
- {
+ break;
+
+ case PTSRC_isa:
hvm_isa_irq_deassert(v->domain, irq);
if ( platform_legacy_irq(irq) && vlapic_accept_pic_intr(v) &&
v->domain->arch.hvm_domain.vpic[irq >> 3].int_output )
- {
hvm_isa_irq_assert(v->domain, irq, NULL);
- pt_vector = -1;
- }
else
{
pt_vector = hvm_isa_irq_assert(v->domain, irq, vioapic_get_vector);
@@ -321,6 +336,17 @@ int pt_update_irq(struct vcpu *v)
if ( pt_vector < 0 || !vlapic_test_irq(vcpu_vlapic(v), pt_vector) )
pt_vector = -1;
}
+ break;
+
+ case PTSRC_ioapic:
+ /*
+ * NB: At the moment IO-APIC routed interrupts generated by vpt devices
+ * (HPET) are edge-triggered.
+ */
+ pt_vector = hvm_ioapic_assert(v->domain, irq, false);
+ if ( pt_vector < 0 || !vlapic_test_irq(vcpu_vlapic(v), pt_vector) )
+ pt_vector = -1;
+ break;
}
return pt_vector;
@@ -418,7 +444,14 @@ void create_periodic_time(
struct vcpu *v, struct periodic_time *pt, uint64_t delta,
uint64_t period, uint8_t irq, time_cb *cb, void *data)
{
- ASSERT(pt->source != 0);
+ if ( !pt->source ||
+ (pt->irq >= NR_ISAIRQS && pt->source == PTSRC_isa) ||
+ (pt->irq >= hvm_domain_irq(v->domain)->nr_gsis &&
+ pt->source == PTSRC_ioapic) )
+ {
+ ASSERT_UNREACHABLE();
+ return;
+ }
destroy_periodic_time(pt);
@@ -498,7 +531,7 @@ static void pt_adjust_vcpu(struct period
{
int on_list;
- ASSERT(pt->source == PTSRC_isa);
+ ASSERT(pt->source == PTSRC_isa || pt->source == PTSRC_ioapic);
if ( pt->vcpu == NULL )
return;
--- a/xen/include/asm-x86/hvm/irq.h
+++ b/xen/include/asm-x86/hvm/irq.h
@@ -207,6 +207,9 @@ int hvm_set_pci_link_route(struct domain
int hvm_inject_msi(struct domain *d, uint64_t addr, uint32_t data);
+/* Assert an IO APIC pin. */
+int hvm_ioapic_assert(struct domain *d, unsigned int gsi, bool level);
+
void hvm_maybe_deassert_evtchn_irq(void);
void hvm_assert_evtchn_irq(struct vcpu *v);
void hvm_set_callback_via(struct domain *d, uint64_t via);
--- a/xen/include/asm-x86/hvm/vpt.h
+++ b/xen/include/asm-x86/hvm/vpt.h
@@ -44,6 +44,7 @@ struct periodic_time {
bool_t warned_timeout_too_short;
#define PTSRC_isa 1 /* ISA time source */
#define PTSRC_lapic 2 /* LAPIC time source */
+#define PTSRC_ioapic 3 /* IOAPIC time source */
u8 source; /* PTSRC_ */
u8 irq;
struct vcpu *vcpu; /* vcpu timer interrupt delivers to */

View file

@ -1,76 +0,0 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: x86/HVM: guard against emulator driving ioreq state in weird ways
In the case where hvm_wait_for_io() calls wait_on_xen_event_channel(),
p->state ends up being read twice in succession: once to determine that
state != p->state, and then again at the top of the loop. This gives a
compromised emulator a chance to change the state back between the two
reads, potentially keeping Xen in a loop indefinitely.
Instead:
* Read p->state once in each of the wait_on_xen_event_channel() tests,
* re-use that value the next time around,
* and insist that the states continue to transition "forward" (with the
exception of the transition to STATE_IOREQ_NONE).
This is XSA-262.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: George Dunlap <george.dunlap@citrix.com>
--- a/xen/arch/x86/hvm/ioreq.c
+++ b/xen/arch/x86/hvm/ioreq.c
@@ -87,14 +87,17 @@ static void hvm_io_assist(struct hvm_ior
static bool hvm_wait_for_io(struct hvm_ioreq_vcpu *sv, ioreq_t *p)
{
+ unsigned int prev_state = STATE_IOREQ_NONE;
+
while ( sv->pending )
{
unsigned int state = p->state;
- rmb();
- switch ( state )
+ smp_rmb();
+
+ recheck:
+ if ( unlikely(state == STATE_IOREQ_NONE) )
{
- case STATE_IOREQ_NONE:
/*
* The only reason we should see this case is when an
* emulator is dying and it races with an I/O being
@@ -102,14 +105,30 @@ static bool hvm_wait_for_io(struct hvm_i
*/
hvm_io_assist(sv, ~0ul);
break;
+ }
+
+ if ( unlikely(state < prev_state) )
+ {
+ gdprintk(XENLOG_ERR, "Weird HVM ioreq state transition %u -> %u\n",
+ prev_state, state);
+ sv->pending = false;
+ domain_crash(sv->vcpu->domain);
+ return false; /* bail */
+ }
+
+ switch ( prev_state = state )
+ {
case STATE_IORESP_READY: /* IORESP_READY -> NONE */
p->state = STATE_IOREQ_NONE;
hvm_io_assist(sv, p->data);
break;
case STATE_IOREQ_READY: /* IOREQ_{READY,INPROCESS} -> IORESP_READY */
case STATE_IOREQ_INPROCESS:
- wait_on_xen_event_channel(sv->ioreq_evtchn, p->state != state);
- break;
+ wait_on_xen_event_channel(sv->ioreq_evtchn,
+ ({ state = p->state;
+ smp_rmb();
+ state != prev_state; }));
+ goto recheck;
default:
gdprintk(XENLOG_ERR, "Weird HVM iorequest state %u\n", state);
sv->pending = false;

View file

@ -1,110 +0,0 @@
From 13fafdf5c97d3bc2a8851c4d1796feac0f82d498 Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Thu, 26 Apr 2018 12:21:00 +0100
Subject: [PATCH] x86/spec_ctrl: Read MSR_ARCH_CAPABILITIES only once
Make it available from the beginning of init_speculation_mitigations(), and
pass it into appropriate functions. Fix an RSBA typo while moving the
affected comment.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Konrad Rzeszutek Wilk <konrad.wilk@oracle.com>
Reviewed-by: Wei Liu <wei.liu2@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
Release-acked-by: Juergen Gross <jgross@suse.com>
(cherry picked from commit d6c65187252a6c1810fd24c4d46f812840de8d3c)
---
xen/arch/x86/spec_ctrl.c | 34 ++++++++++++++--------------------
1 file changed, 14 insertions(+), 20 deletions(-)
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index fa67a0f..dc90743 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -81,18 +81,15 @@ static int __init parse_bti(const char *s)
}
custom_param("bti", parse_bti);
-static void __init print_details(enum ind_thunk thunk)
+static void __init print_details(enum ind_thunk thunk, uint64_t caps)
{
unsigned int _7d0 = 0, e8b = 0, tmp;
- uint64_t caps = 0;
/* Collect diagnostics about available mitigations. */
if ( boot_cpu_data.cpuid_level >= 7 )
cpuid_count(7, 0, &tmp, &tmp, &tmp, &_7d0);
if ( boot_cpu_data.extended_cpuid_level >= 0x80000008 )
cpuid(0x80000008, &tmp, &e8b, &tmp, &tmp);
- if ( _7d0 & cpufeat_mask(X86_FEATURE_ARCH_CAPS) )
- rdmsrl(MSR_ARCH_CAPABILITIES, caps);
printk(XENLOG_DEBUG "Speculative mitigation facilities:\n");
@@ -125,7 +122,7 @@ static void __init print_details(enum ind_thunk thunk)
}
/* Calculate whether Retpoline is known-safe on this CPU. */
-static bool __init retpoline_safe(void)
+static bool __init retpoline_safe(uint64_t caps)
{
unsigned int ucode_rev = this_cpu(ucode_cpu_info).cpu_sig.rev;
@@ -136,19 +133,12 @@ static bool __init retpoline_safe(void)
boot_cpu_data.x86 != 6 )
return false;
- if ( boot_cpu_has(X86_FEATURE_ARCH_CAPS) )
- {
- uint64_t caps;
-
- rdmsrl(MSR_ARCH_CAPABILITIES, caps);
-
- /*
- * RBSA may be set by a hypervisor to indicate that we may move to a
- * processor which isn't retpoline-safe.
- */
- if ( caps & ARCH_CAPS_RSBA )
- return false;
- }
+ /*
+ * RSBA may be set by a hypervisor to indicate that we may move to a
+ * processor which isn't retpoline-safe.
+ */
+ if ( caps & ARCH_CAPS_RSBA )
+ return false;
switch ( boot_cpu_data.x86_model )
{
@@ -218,6 +208,10 @@ void __init init_speculation_mitigations(void)
{
enum ind_thunk thunk = THUNK_DEFAULT;
bool ibrs = false;
+ uint64_t caps = 0;
+
+ if ( boot_cpu_has(X86_FEATURE_ARCH_CAPS) )
+ rdmsrl(MSR_ARCH_CAPABILITIES, caps);
/*
* Has the user specified any custom BTI mitigations? If so, follow their
@@ -246,7 +240,7 @@ void __init init_speculation_mitigations(void)
* On Intel hardware, we'd like to use retpoline in preference to
* IBRS, but only if it is safe on this hardware.
*/
- else if ( retpoline_safe() )
+ else if ( retpoline_safe(caps) )
thunk = THUNK_RETPOLINE;
else if ( boot_cpu_has(X86_FEATURE_IBRSB) )
ibrs = true;
@@ -331,7 +325,7 @@ void __init init_speculation_mitigations(void)
/* (Re)init BSP state now that default_bti_ist_info has been calculated. */
init_shadow_spec_ctrl_state();
- print_details(thunk);
+ print_details(thunk, caps);
}
static void __init __maybe_unused build_assertions(void)
--
2.1.4

View file

@ -1,138 +0,0 @@
From d7b345e4ca136a995bfaaf2ee20901ee20e63570 Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Tue, 17 Apr 2018 14:15:04 +0100
Subject: [PATCH] x86/spec_ctrl: Express Xen's choice of MSR_SPEC_CTRL value as
a variable
At the moment, we have two different encodings of Xen's MSR_SPEC_CTRL value,
which is a side effect of how the Spectre series developed. One encoding is
via an alias with the bottom bit of bti_ist_info, and can encode IBRS or not,
but not other configurations such as STIBP.
Break Xen's value out into a separate variable (in the top of stack block for
XPTI reasons) and use this instead of bti_ist_info in the IST path.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Wei Liu <wei.liu2@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
Release-acked-by: Juergen Gross <jgross@suse.com>
(cherry picked from commit 66dfae0f32bfbc899c2f3446d5ee57068cb7f957)
---
xen/arch/x86/spec_ctrl.c | 8 +++++---
xen/arch/x86/x86_64/asm-offsets.c | 1 +
xen/include/asm-x86/current.h | 1 +
xen/include/asm-x86/spec_ctrl.h | 2 ++
xen/include/asm-x86/spec_ctrl_asm.h | 8 ++------
5 files changed, 11 insertions(+), 9 deletions(-)
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index dc90743..1143521 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -38,6 +38,7 @@ static int8_t __initdata opt_ibrs = -1;
static bool __initdata opt_rsb_native = true;
static bool __initdata opt_rsb_vmexit = true;
bool __read_mostly opt_ibpb = true;
+uint8_t __read_mostly default_xen_spec_ctrl;
uint8_t __read_mostly default_bti_ist_info;
static int __init parse_bti(const char *s)
@@ -285,11 +286,14 @@ void __init init_speculation_mitigations(void)
* guests.
*/
if ( ibrs )
+ {
+ default_xen_spec_ctrl |= SPEC_CTRL_IBRS;
setup_force_cpu_cap(X86_FEATURE_XEN_IBRS_SET);
+ }
else
setup_force_cpu_cap(X86_FEATURE_XEN_IBRS_CLEAR);
- default_bti_ist_info |= BTI_IST_WRMSR | ibrs;
+ default_bti_ist_info |= BTI_IST_WRMSR;
}
/*
@@ -330,8 +334,6 @@ void __init init_speculation_mitigations(void)
static void __init __maybe_unused build_assertions(void)
{
- /* The optimised assembly relies on this alias. */
- BUILD_BUG_ON(BTI_IST_IBRS != SPEC_CTRL_IBRS);
}
/*
diff --git a/xen/arch/x86/x86_64/asm-offsets.c b/xen/arch/x86/x86_64/asm-offsets.c
index 13478d4..0726147 100644
--- a/xen/arch/x86/x86_64/asm-offsets.c
+++ b/xen/arch/x86/x86_64/asm-offsets.c
@@ -142,6 +142,7 @@ void __dummy__(void)
OFFSET(CPUINFO_xen_cr3, struct cpu_info, xen_cr3);
OFFSET(CPUINFO_pv_cr3, struct cpu_info, pv_cr3);
OFFSET(CPUINFO_shadow_spec_ctrl, struct cpu_info, shadow_spec_ctrl);
+ OFFSET(CPUINFO_xen_spec_ctrl, struct cpu_info, xen_spec_ctrl);
OFFSET(CPUINFO_use_shadow_spec_ctrl, struct cpu_info, use_shadow_spec_ctrl);
OFFSET(CPUINFO_bti_ist_info, struct cpu_info, bti_ist_info);
DEFINE(CPUINFO_sizeof, sizeof(struct cpu_info));
diff --git a/xen/include/asm-x86/current.h b/xen/include/asm-x86/current.h
index 4678a0f..d10b13c 100644
--- a/xen/include/asm-x86/current.h
+++ b/xen/include/asm-x86/current.h
@@ -56,6 +56,7 @@ struct cpu_info {
/* See asm-x86/spec_ctrl_asm.h for usage. */
unsigned int shadow_spec_ctrl;
+ uint8_t xen_spec_ctrl;
bool use_shadow_spec_ctrl;
uint8_t bti_ist_info;
diff --git a/xen/include/asm-x86/spec_ctrl.h b/xen/include/asm-x86/spec_ctrl.h
index 5ab4ff3..5e4fc84 100644
--- a/xen/include/asm-x86/spec_ctrl.h
+++ b/xen/include/asm-x86/spec_ctrl.h
@@ -27,6 +27,7 @@
void init_speculation_mitigations(void);
extern bool opt_ibpb;
+extern uint8_t default_xen_spec_ctrl;
extern uint8_t default_bti_ist_info;
static inline void init_shadow_spec_ctrl_state(void)
@@ -34,6 +35,7 @@ static inline void init_shadow_spec_ctrl_state(void)
struct cpu_info *info = get_cpu_info();
info->shadow_spec_ctrl = info->use_shadow_spec_ctrl = 0;
+ info->xen_spec_ctrl = default_xen_spec_ctrl;
info->bti_ist_info = default_bti_ist_info;
}
diff --git a/xen/include/asm-x86/spec_ctrl_asm.h b/xen/include/asm-x86/spec_ctrl_asm.h
index 1f2b6f3..697da13 100644
--- a/xen/include/asm-x86/spec_ctrl_asm.h
+++ b/xen/include/asm-x86/spec_ctrl_asm.h
@@ -21,7 +21,6 @@
#define __X86_SPEC_CTRL_ASM_H__
/* Encoding of the bottom bits in cpuinfo.bti_ist_info */
-#define BTI_IST_IBRS (1 << 0)
#define BTI_IST_WRMSR (1 << 1)
#define BTI_IST_RSB (1 << 2)
@@ -286,12 +285,9 @@
setz %dl
and %dl, STACK_CPUINFO_FIELD(use_shadow_spec_ctrl)(%r14)
- /*
- * Load Xen's intended value. SPEC_CTRL_IBRS vs 0 is encoded in the
- * bottom bit of bti_ist_info, via a deliberate alias with BTI_IST_IBRS.
- */
+ /* Load Xen's intended value. */
mov $MSR_SPEC_CTRL, %ecx
- and $BTI_IST_IBRS, %eax
+ movzbl STACK_CPUINFO_FIELD(xen_spec_ctrl)(%r14), %eax
xor %edx, %edx
wrmsr
--
2.1.4

View file

@ -1,340 +0,0 @@
From a0c2f734b4c683cb407e10ff943671c413480287 Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Tue, 17 Apr 2018 14:15:04 +0100
Subject: [PATCH] x86/spec_ctrl: Merge bti_ist_info and use_shadow_spec_ctrl
into spec_ctrl_flags
All 3 bits of information here are control flags for the entry/exit code
behaviour. Treat them as such, rather than having two different variables.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Wei Liu <wei.liu2@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
Release-acked-by: Juergen Gross <jgross@suse.com>
(cherry picked from commit 5262ba2e7799001402dfe139ff944e035dfff928)
---
xen/arch/x86/acpi/power.c | 4 +--
xen/arch/x86/spec_ctrl.c | 10 ++++---
xen/arch/x86/x86_64/asm-offsets.c | 3 +--
xen/include/asm-x86/current.h | 3 +--
xen/include/asm-x86/nops.h | 5 ++--
xen/include/asm-x86/spec_ctrl.h | 10 +++----
xen/include/asm-x86/spec_ctrl_asm.h | 52 ++++++++++++++++++++-----------------
7 files changed, 45 insertions(+), 42 deletions(-)
diff --git a/xen/arch/x86/acpi/power.c b/xen/arch/x86/acpi/power.c
index f7085d3..f3480aa 100644
--- a/xen/arch/x86/acpi/power.c
+++ b/xen/arch/x86/acpi/power.c
@@ -215,7 +215,7 @@ static int enter_state(u32 state)
ci = get_cpu_info();
spec_ctrl_enter_idle(ci);
/* Avoid NMI/#MC using MSR_SPEC_CTRL until we've reloaded microcode. */
- ci->bti_ist_info = 0;
+ ci->spec_ctrl_flags &= ~SCF_ist_wrmsr;
ACPI_FLUSH_CPU_CACHE();
@@ -256,7 +256,7 @@ static int enter_state(u32 state)
microcode_resume_cpu(0);
/* Re-enabled default NMI/#MC use of MSR_SPEC_CTRL. */
- ci->bti_ist_info = default_bti_ist_info;
+ ci->spec_ctrl_flags |= (default_spec_ctrl_flags & SCF_ist_wrmsr);
spec_ctrl_exit_idle(ci);
done:
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index 1143521..2d69910 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -39,7 +39,7 @@ static bool __initdata opt_rsb_native = true;
static bool __initdata opt_rsb_vmexit = true;
bool __read_mostly opt_ibpb = true;
uint8_t __read_mostly default_xen_spec_ctrl;
-uint8_t __read_mostly default_bti_ist_info;
+uint8_t __read_mostly default_spec_ctrl_flags;
static int __init parse_bti(const char *s)
{
@@ -293,7 +293,7 @@ void __init init_speculation_mitigations(void)
else
setup_force_cpu_cap(X86_FEATURE_XEN_IBRS_CLEAR);
- default_bti_ist_info |= BTI_IST_WRMSR;
+ default_spec_ctrl_flags |= SCF_ist_wrmsr;
}
/*
@@ -312,7 +312,7 @@ void __init init_speculation_mitigations(void)
if ( opt_rsb_native )
{
setup_force_cpu_cap(X86_FEATURE_RSB_NATIVE);
- default_bti_ist_info |= BTI_IST_RSB;
+ default_spec_ctrl_flags |= SCF_ist_rsb;
}
/*
@@ -326,7 +326,7 @@ void __init init_speculation_mitigations(void)
if ( !boot_cpu_has(X86_FEATURE_IBRSB) && !boot_cpu_has(X86_FEATURE_IBPB) )
opt_ibpb = false;
- /* (Re)init BSP state now that default_bti_ist_info has been calculated. */
+ /* (Re)init BSP state now that default_spec_ctrl_flags has been calculated. */
init_shadow_spec_ctrl_state();
print_details(thunk, caps);
@@ -334,6 +334,8 @@ void __init init_speculation_mitigations(void)
static void __init __maybe_unused build_assertions(void)
{
+ /* The optimised assembly relies on this alias. */
+ BUILD_BUG_ON(SCF_use_shadow != 1);
}
/*
diff --git a/xen/arch/x86/x86_64/asm-offsets.c b/xen/arch/x86/x86_64/asm-offsets.c
index 0726147..97242e5 100644
--- a/xen/arch/x86/x86_64/asm-offsets.c
+++ b/xen/arch/x86/x86_64/asm-offsets.c
@@ -143,8 +143,7 @@ void __dummy__(void)
OFFSET(CPUINFO_pv_cr3, struct cpu_info, pv_cr3);
OFFSET(CPUINFO_shadow_spec_ctrl, struct cpu_info, shadow_spec_ctrl);
OFFSET(CPUINFO_xen_spec_ctrl, struct cpu_info, xen_spec_ctrl);
- OFFSET(CPUINFO_use_shadow_spec_ctrl, struct cpu_info, use_shadow_spec_ctrl);
- OFFSET(CPUINFO_bti_ist_info, struct cpu_info, bti_ist_info);
+ OFFSET(CPUINFO_spec_ctrl_flags, struct cpu_info, spec_ctrl_flags);
DEFINE(CPUINFO_sizeof, sizeof(struct cpu_info));
BLANK();
diff --git a/xen/include/asm-x86/current.h b/xen/include/asm-x86/current.h
index d10b13c..7afff0e 100644
--- a/xen/include/asm-x86/current.h
+++ b/xen/include/asm-x86/current.h
@@ -57,8 +57,7 @@ struct cpu_info {
/* See asm-x86/spec_ctrl_asm.h for usage. */
unsigned int shadow_spec_ctrl;
uint8_t xen_spec_ctrl;
- bool use_shadow_spec_ctrl;
- uint8_t bti_ist_info;
+ uint8_t spec_ctrl_flags;
unsigned long __pad;
/* get_stack_bottom() must be 16-byte aligned */
diff --git a/xen/include/asm-x86/nops.h b/xen/include/asm-x86/nops.h
index 37f9819..b744895 100644
--- a/xen/include/asm-x86/nops.h
+++ b/xen/include/asm-x86/nops.h
@@ -62,10 +62,9 @@
#define ASM_NOP8 _ASM_MK_NOP(K8_NOP8)
#define ASM_NOP17 ASM_NOP8; ASM_NOP7; ASM_NOP2
-#define ASM_NOP21 ASM_NOP8; ASM_NOP8; ASM_NOP5
+#define ASM_NOP22 ASM_NOP8; ASM_NOP8; ASM_NOP6
#define ASM_NOP24 ASM_NOP8; ASM_NOP8; ASM_NOP8
-#define ASM_NOP29 ASM_NOP8; ASM_NOP8; ASM_NOP8; ASM_NOP5
-#define ASM_NOP32 ASM_NOP8; ASM_NOP8; ASM_NOP8; ASM_NOP8
+#define ASM_NOP33 ASM_NOP8; ASM_NOP8; ASM_NOP8; ASM_NOP7; ASM_NOP2
#define ASM_NOP40 ASM_NOP8; ASM_NOP8; ASM_NOP8; ASM_NOP8; ASM_NOP8
#define ASM_NOP_MAX 8
diff --git a/xen/include/asm-x86/spec_ctrl.h b/xen/include/asm-x86/spec_ctrl.h
index 5e4fc84..059e291 100644
--- a/xen/include/asm-x86/spec_ctrl.h
+++ b/xen/include/asm-x86/spec_ctrl.h
@@ -28,15 +28,15 @@ void init_speculation_mitigations(void);
extern bool opt_ibpb;
extern uint8_t default_xen_spec_ctrl;
-extern uint8_t default_bti_ist_info;
+extern uint8_t default_spec_ctrl_flags;
static inline void init_shadow_spec_ctrl_state(void)
{
struct cpu_info *info = get_cpu_info();
- info->shadow_spec_ctrl = info->use_shadow_spec_ctrl = 0;
+ info->shadow_spec_ctrl = 0;
info->xen_spec_ctrl = default_xen_spec_ctrl;
- info->bti_ist_info = default_bti_ist_info;
+ info->spec_ctrl_flags = default_spec_ctrl_flags;
}
/* WARNING! `ret`, `call *`, `jmp *` not safe after this call. */
@@ -50,7 +50,7 @@ static always_inline void spec_ctrl_enter_idle(struct cpu_info *info)
*/
info->shadow_spec_ctrl = val;
barrier();
- info->use_shadow_spec_ctrl = true;
+ info->spec_ctrl_flags |= SCF_use_shadow;
barrier();
asm volatile ( ALTERNATIVE(ASM_NOP3, "wrmsr", X86_FEATURE_XEN_IBRS_SET)
:: "a" (val), "c" (MSR_SPEC_CTRL), "d" (0) : "memory" );
@@ -65,7 +65,7 @@ static always_inline void spec_ctrl_exit_idle(struct cpu_info *info)
* Disable shadowing before updating the MSR. There are no SMP issues
* here; only local processor ordering concerns.
*/
- info->use_shadow_spec_ctrl = false;
+ info->spec_ctrl_flags &= ~SCF_use_shadow;
barrier();
asm volatile ( ALTERNATIVE(ASM_NOP3, "wrmsr", X86_FEATURE_XEN_IBRS_SET)
:: "a" (val), "c" (MSR_SPEC_CTRL), "d" (0) : "memory" );
diff --git a/xen/include/asm-x86/spec_ctrl_asm.h b/xen/include/asm-x86/spec_ctrl_asm.h
index 697da13..39fb4f8 100644
--- a/xen/include/asm-x86/spec_ctrl_asm.h
+++ b/xen/include/asm-x86/spec_ctrl_asm.h
@@ -20,9 +20,10 @@
#ifndef __X86_SPEC_CTRL_ASM_H__
#define __X86_SPEC_CTRL_ASM_H__
-/* Encoding of the bottom bits in cpuinfo.bti_ist_info */
-#define BTI_IST_WRMSR (1 << 1)
-#define BTI_IST_RSB (1 << 2)
+/* Encoding of cpuinfo.spec_ctrl_flags */
+#define SCF_use_shadow (1 << 0)
+#define SCF_ist_wrmsr (1 << 1)
+#define SCF_ist_rsb (1 << 2)
#ifdef __ASSEMBLY__
#include <asm/msr-index.h>
@@ -49,20 +50,20 @@
* after VMEXIT. The VMEXIT-specific code reads MSR_SPEC_CTRL and updates
* current before loading Xen's MSR_SPEC_CTRL setting.
*
- * Factor 2 is harder. We maintain a shadow_spec_ctrl value, and
- * use_shadow_spec_ctrl boolean per cpu. The synchronous use is:
+ * Factor 2 is harder. We maintain a shadow_spec_ctrl value, and a use_shadow
+ * boolean in the per cpu spec_ctrl_flags. The synchronous use is:
*
* 1) Store guest value in shadow_spec_ctrl
- * 2) Set use_shadow_spec_ctrl boolean
+ * 2) Set the use_shadow boolean
* 3) Load guest value into MSR_SPEC_CTRL
* 4) Exit to guest
* 5) Entry from guest
- * 6) Clear use_shadow_spec_ctrl boolean
+ * 6) Clear the use_shadow boolean
* 7) Load Xen's value into MSR_SPEC_CTRL
*
* The asynchronous use for interrupts/exceptions is:
* - Set/clear IBRS on entry to Xen
- * - On exit to Xen, check use_shadow_spec_ctrl
+ * - On exit to Xen, check use_shadow
* - If set, load shadow_spec_ctrl
*
* Therefore, an interrupt/exception which hits the synchronous path between
@@ -134,7 +135,7 @@
xor %edx, %edx
/* Clear SPEC_CTRL shadowing *before* loading Xen's value. */
- movb %dl, CPUINFO_use_shadow_spec_ctrl(%rsp)
+ andb $~SCF_use_shadow, CPUINFO_spec_ctrl_flags(%rsp)
/* Load Xen's intended value. */
mov $\ibrs_val, %eax
@@ -160,12 +161,14 @@
* block so calculate the position directly.
*/
.if \maybexen
+ xor %eax, %eax
/* Branchless `if ( !xen ) clear_shadowing` */
testb $3, UREGS_cs(%rsp)
- setz %al
- and %al, STACK_CPUINFO_FIELD(use_shadow_spec_ctrl)(%r14)
+ setnz %al
+ not %eax
+ and %al, STACK_CPUINFO_FIELD(spec_ctrl_flags)(%r14)
.else
- movb %dl, CPUINFO_use_shadow_spec_ctrl(%rsp)
+ andb $~SCF_use_shadow, CPUINFO_spec_ctrl_flags(%rsp)
.endif
/* Load Xen's intended value. */
@@ -184,8 +187,8 @@
*/
xor %edx, %edx
- cmpb %dl, STACK_CPUINFO_FIELD(use_shadow_spec_ctrl)(%rbx)
- je .L\@_skip
+ testb $SCF_use_shadow, STACK_CPUINFO_FIELD(spec_ctrl_flags)(%rbx)
+ jz .L\@_skip
mov STACK_CPUINFO_FIELD(shadow_spec_ctrl)(%rbx), %eax
mov $MSR_SPEC_CTRL, %ecx
@@ -206,7 +209,7 @@
mov %eax, CPUINFO_shadow_spec_ctrl(%rsp)
/* Set SPEC_CTRL shadowing *before* loading the guest value. */
- movb $1, CPUINFO_use_shadow_spec_ctrl(%rsp)
+ orb $SCF_use_shadow, CPUINFO_spec_ctrl_flags(%rsp)
mov $MSR_SPEC_CTRL, %ecx
xor %edx, %edx
@@ -217,7 +220,7 @@
#define SPEC_CTRL_ENTRY_FROM_VMEXIT \
ALTERNATIVE __stringify(ASM_NOP40), \
DO_OVERWRITE_RSB, X86_FEATURE_RSB_VMEXIT; \
- ALTERNATIVE_2 __stringify(ASM_NOP32), \
+ ALTERNATIVE_2 __stringify(ASM_NOP33), \
__stringify(DO_SPEC_CTRL_ENTRY_FROM_VMEXIT \
ibrs_val=SPEC_CTRL_IBRS), \
X86_FEATURE_XEN_IBRS_SET, \
@@ -229,7 +232,7 @@
#define SPEC_CTRL_ENTRY_FROM_PV \
ALTERNATIVE __stringify(ASM_NOP40), \
DO_OVERWRITE_RSB, X86_FEATURE_RSB_NATIVE; \
- ALTERNATIVE_2 __stringify(ASM_NOP21), \
+ ALTERNATIVE_2 __stringify(ASM_NOP22), \
__stringify(DO_SPEC_CTRL_ENTRY maybexen=0 \
ibrs_val=SPEC_CTRL_IBRS), \
X86_FEATURE_XEN_IBRS_SET, \
@@ -240,7 +243,7 @@
#define SPEC_CTRL_ENTRY_FROM_INTR \
ALTERNATIVE __stringify(ASM_NOP40), \
DO_OVERWRITE_RSB, X86_FEATURE_RSB_NATIVE; \
- ALTERNATIVE_2 __stringify(ASM_NOP29), \
+ ALTERNATIVE_2 __stringify(ASM_NOP33), \
__stringify(DO_SPEC_CTRL_ENTRY maybexen=1 \
ibrs_val=SPEC_CTRL_IBRS), \
X86_FEATURE_XEN_IBRS_SET, \
@@ -268,22 +271,23 @@
* This is logical merge of DO_OVERWRITE_RSB and DO_SPEC_CTRL_ENTRY
* maybexen=1, but with conditionals rather than alternatives.
*/
- movzbl STACK_CPUINFO_FIELD(bti_ist_info)(%r14), %eax
+ movzbl STACK_CPUINFO_FIELD(spec_ctrl_flags)(%r14), %eax
- testb $BTI_IST_RSB, %al
+ test $SCF_ist_rsb, %al
jz .L\@_skip_rsb
DO_OVERWRITE_RSB tmp=rdx /* Clobbers %rcx/%rdx */
.L\@_skip_rsb:
- testb $BTI_IST_WRMSR, %al
+ test $SCF_ist_wrmsr, %al
jz .L\@_skip_wrmsr
xor %edx, %edx
testb $3, UREGS_cs(%rsp)
- setz %dl
- and %dl, STACK_CPUINFO_FIELD(use_shadow_spec_ctrl)(%r14)
+ setnz %dl
+ not %edx
+ and %dl, STACK_CPUINFO_FIELD(spec_ctrl_flags)(%r14)
/* Load Xen's intended value. */
mov $MSR_SPEC_CTRL, %ecx
@@ -310,7 +314,7 @@ UNLIKELY_DISPATCH_LABEL(\@_serialise):
* Requires %rbx=stack_end
* Clobbers %rax, %rcx, %rdx
*/
- testb $BTI_IST_WRMSR, STACK_CPUINFO_FIELD(bti_ist_info)(%rbx)
+ testb $SCF_ist_wrmsr, STACK_CPUINFO_FIELD(spec_ctrl_flags)(%rbx)
jz .L\@_skip
DO_SPEC_CTRL_EXIT_TO_XEN
--
2.1.4

View file

@ -1,221 +0,0 @@
From 0b1aded85866f48cdede20c54d30cf593f8a83f7 Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Tue, 17 Apr 2018 14:15:04 +0100
Subject: [PATCH] x86/spec_ctrl: Fold the XEN_IBRS_{SET,CLEAR} ALTERNATIVES
together
Currently, the SPEC_CTRL_{ENTRY,EXIT}_* macros encode Xen's choice of
MSR_SPEC_CTRL as an immediate constant, and chooses between IBRS or not by
doubling up the entire alternative block.
There is now a variable holding Xen's choice of value, so use that and
simplify the alternatives.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Wei Liu <wei.liu2@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
Release-acked-by: Juergen Gross <jgross@suse.com>
(cherry picked from commit af949407eaba7af71067f23d5866cd0bf1f1144d)
---
xen/arch/x86/spec_ctrl.c | 12 +++++-----
xen/include/asm-x86/cpufeatures.h | 3 +--
xen/include/asm-x86/nops.h | 3 ++-
xen/include/asm-x86/spec_ctrl.h | 6 ++---
xen/include/asm-x86/spec_ctrl_asm.h | 45 +++++++++++++------------------------
5 files changed, 26 insertions(+), 43 deletions(-)
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index 2d69910..b62cfcc 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -112,8 +112,9 @@ static void __init print_details(enum ind_thunk thunk, uint64_t caps)
thunk == THUNK_RETPOLINE ? "RETPOLINE" :
thunk == THUNK_LFENCE ? "LFENCE" :
thunk == THUNK_JMP ? "JMP" : "?",
- boot_cpu_has(X86_FEATURE_XEN_IBRS_SET) ? " IBRS+" :
- boot_cpu_has(X86_FEATURE_XEN_IBRS_CLEAR) ? " IBRS-" : "",
+ boot_cpu_has(X86_FEATURE_SC_MSR) ?
+ default_xen_spec_ctrl & SPEC_CTRL_IBRS ? " IBRS+" :
+ " IBRS-" : "",
opt_ibpb ? " IBPB" : "",
boot_cpu_has(X86_FEATURE_RSB_NATIVE) ? " RSB_NATIVE" : "",
boot_cpu_has(X86_FEATURE_RSB_VMEXIT) ? " RSB_VMEXIT" : "");
@@ -285,13 +286,10 @@ void __init init_speculation_mitigations(void)
* need the IBRS entry/exit logic to virtualise IBRS support for
* guests.
*/
+ setup_force_cpu_cap(X86_FEATURE_SC_MSR);
+
if ( ibrs )
- {
default_xen_spec_ctrl |= SPEC_CTRL_IBRS;
- setup_force_cpu_cap(X86_FEATURE_XEN_IBRS_SET);
- }
- else
- setup_force_cpu_cap(X86_FEATURE_XEN_IBRS_CLEAR);
default_spec_ctrl_flags |= SCF_ist_wrmsr;
}
diff --git a/xen/include/asm-x86/cpufeatures.h b/xen/include/asm-x86/cpufeatures.h
index c9b1a48..ca58b0e 100644
--- a/xen/include/asm-x86/cpufeatures.h
+++ b/xen/include/asm-x86/cpufeatures.h
@@ -26,8 +26,7 @@ XEN_CPUFEATURE(LFENCE_DISPATCH, (FSCAPINTS+0)*32+12) /* lfence set as Dispatch S
XEN_CPUFEATURE(IND_THUNK_LFENCE,(FSCAPINTS+0)*32+13) /* Use IND_THUNK_LFENCE */
XEN_CPUFEATURE(IND_THUNK_JMP, (FSCAPINTS+0)*32+14) /* Use IND_THUNK_JMP */
XEN_CPUFEATURE(XEN_IBPB, (FSCAPINTS+0)*32+15) /* IBRSB || IBPB */
-XEN_CPUFEATURE(XEN_IBRS_SET, (FSCAPINTS+0)*32+16) /* IBRSB && IRBS set in Xen */
-XEN_CPUFEATURE(XEN_IBRS_CLEAR, (FSCAPINTS+0)*32+17) /* IBRSB && IBRS clear in Xen */
+XEN_CPUFEATURE(SC_MSR, (FSCAPINTS+0)*32+16) /* MSR_SPEC_CTRL used by Xen */
XEN_CPUFEATURE(RSB_NATIVE, (FSCAPINTS+0)*32+18) /* RSB overwrite needed for native */
XEN_CPUFEATURE(RSB_VMEXIT, (FSCAPINTS+0)*32+19) /* RSB overwrite needed for vmexit */
XEN_CPUFEATURE(NO_XPTI, (FSCAPINTS+0)*32+20) /* XPTI mitigation not in use */
diff --git a/xen/include/asm-x86/nops.h b/xen/include/asm-x86/nops.h
index b744895..913e9f0 100644
--- a/xen/include/asm-x86/nops.h
+++ b/xen/include/asm-x86/nops.h
@@ -62,9 +62,10 @@
#define ASM_NOP8 _ASM_MK_NOP(K8_NOP8)
#define ASM_NOP17 ASM_NOP8; ASM_NOP7; ASM_NOP2
-#define ASM_NOP22 ASM_NOP8; ASM_NOP8; ASM_NOP6
#define ASM_NOP24 ASM_NOP8; ASM_NOP8; ASM_NOP8
+#define ASM_NOP25 ASM_NOP8; ASM_NOP8; ASM_NOP7; ASM_NOP2
#define ASM_NOP33 ASM_NOP8; ASM_NOP8; ASM_NOP8; ASM_NOP7; ASM_NOP2
+#define ASM_NOP36 ASM_NOP8; ASM_NOP8; ASM_NOP8; ASM_NOP8; ASM_NOP4
#define ASM_NOP40 ASM_NOP8; ASM_NOP8; ASM_NOP8; ASM_NOP8; ASM_NOP8
#define ASM_NOP_MAX 8
diff --git a/xen/include/asm-x86/spec_ctrl.h b/xen/include/asm-x86/spec_ctrl.h
index 059e291..7d7c42e 100644
--- a/xen/include/asm-x86/spec_ctrl.h
+++ b/xen/include/asm-x86/spec_ctrl.h
@@ -52,14 +52,14 @@ static always_inline void spec_ctrl_enter_idle(struct cpu_info *info)
barrier();
info->spec_ctrl_flags |= SCF_use_shadow;
barrier();
- asm volatile ( ALTERNATIVE(ASM_NOP3, "wrmsr", X86_FEATURE_XEN_IBRS_SET)
+ asm volatile ( ALTERNATIVE(ASM_NOP3, "wrmsr", X86_FEATURE_SC_MSR)
:: "a" (val), "c" (MSR_SPEC_CTRL), "d" (0) : "memory" );
}
/* WARNING! `ret`, `call *`, `jmp *` not safe before this call. */
static always_inline void spec_ctrl_exit_idle(struct cpu_info *info)
{
- uint32_t val = SPEC_CTRL_IBRS;
+ uint32_t val = info->xen_spec_ctrl;
/*
* Disable shadowing before updating the MSR. There are no SMP issues
@@ -67,7 +67,7 @@ static always_inline void spec_ctrl_exit_idle(struct cpu_info *info)
*/
info->spec_ctrl_flags &= ~SCF_use_shadow;
barrier();
- asm volatile ( ALTERNATIVE(ASM_NOP3, "wrmsr", X86_FEATURE_XEN_IBRS_SET)
+ asm volatile ( ALTERNATIVE(ASM_NOP3, "wrmsr", X86_FEATURE_SC_MSR)
:: "a" (val), "c" (MSR_SPEC_CTRL), "d" (0) : "memory" );
}
diff --git a/xen/include/asm-x86/spec_ctrl_asm.h b/xen/include/asm-x86/spec_ctrl_asm.h
index 39fb4f8..17dd2cc 100644
--- a/xen/include/asm-x86/spec_ctrl_asm.h
+++ b/xen/include/asm-x86/spec_ctrl_asm.h
@@ -117,7 +117,7 @@
mov %\tmp, %rsp /* Restore old %rsp */
.endm
-.macro DO_SPEC_CTRL_ENTRY_FROM_VMEXIT ibrs_val:req
+.macro DO_SPEC_CTRL_ENTRY_FROM_VMEXIT
/*
* Requires %rbx=current, %rsp=regs/cpuinfo
* Clobbers %rax, %rcx, %rdx
@@ -138,11 +138,11 @@
andb $~SCF_use_shadow, CPUINFO_spec_ctrl_flags(%rsp)
/* Load Xen's intended value. */
- mov $\ibrs_val, %eax
+ movzbl CPUINFO_xen_spec_ctrl(%rsp), %eax
wrmsr
.endm
-.macro DO_SPEC_CTRL_ENTRY maybexen:req ibrs_val:req
+.macro DO_SPEC_CTRL_ENTRY maybexen:req
/*
* Requires %rsp=regs (also cpuinfo if !maybexen)
* Requires %r14=stack_end (if maybexen)
@@ -167,12 +167,12 @@
setnz %al
not %eax
and %al, STACK_CPUINFO_FIELD(spec_ctrl_flags)(%r14)
+ movzbl STACK_CPUINFO_FIELD(xen_spec_ctrl)(%r14), %eax
.else
andb $~SCF_use_shadow, CPUINFO_spec_ctrl_flags(%rsp)
+ movzbl CPUINFO_xen_spec_ctrl(%rsp), %eax
.endif
- /* Load Xen's intended value. */
- mov $\ibrs_val, %eax
wrmsr
.endm
@@ -220,47 +220,32 @@
#define SPEC_CTRL_ENTRY_FROM_VMEXIT \
ALTERNATIVE __stringify(ASM_NOP40), \
DO_OVERWRITE_RSB, X86_FEATURE_RSB_VMEXIT; \
- ALTERNATIVE_2 __stringify(ASM_NOP33), \
- __stringify(DO_SPEC_CTRL_ENTRY_FROM_VMEXIT \
- ibrs_val=SPEC_CTRL_IBRS), \
- X86_FEATURE_XEN_IBRS_SET, \
- __stringify(DO_SPEC_CTRL_ENTRY_FROM_VMEXIT \
- ibrs_val=0), \
- X86_FEATURE_XEN_IBRS_CLEAR
+ ALTERNATIVE __stringify(ASM_NOP36), \
+ DO_SPEC_CTRL_ENTRY_FROM_VMEXIT, X86_FEATURE_SC_MSR
/* Use after an entry from PV context (syscall/sysenter/int80/int82/etc). */
#define SPEC_CTRL_ENTRY_FROM_PV \
ALTERNATIVE __stringify(ASM_NOP40), \
DO_OVERWRITE_RSB, X86_FEATURE_RSB_NATIVE; \
- ALTERNATIVE_2 __stringify(ASM_NOP22), \
- __stringify(DO_SPEC_CTRL_ENTRY maybexen=0 \
- ibrs_val=SPEC_CTRL_IBRS), \
- X86_FEATURE_XEN_IBRS_SET, \
- __stringify(DO_SPEC_CTRL_ENTRY maybexen=0 ibrs_val=0), \
- X86_FEATURE_XEN_IBRS_CLEAR
+ ALTERNATIVE __stringify(ASM_NOP25), \
+ __stringify(DO_SPEC_CTRL_ENTRY maybexen=0), X86_FEATURE_SC_MSR
/* Use in interrupt/exception context. May interrupt Xen or PV context. */
#define SPEC_CTRL_ENTRY_FROM_INTR \
ALTERNATIVE __stringify(ASM_NOP40), \
DO_OVERWRITE_RSB, X86_FEATURE_RSB_NATIVE; \
- ALTERNATIVE_2 __stringify(ASM_NOP33), \
- __stringify(DO_SPEC_CTRL_ENTRY maybexen=1 \
- ibrs_val=SPEC_CTRL_IBRS), \
- X86_FEATURE_XEN_IBRS_SET, \
- __stringify(DO_SPEC_CTRL_ENTRY maybexen=1 ibrs_val=0), \
- X86_FEATURE_XEN_IBRS_CLEAR
+ ALTERNATIVE __stringify(ASM_NOP33), \
+ __stringify(DO_SPEC_CTRL_ENTRY maybexen=1), X86_FEATURE_SC_MSR
/* Use when exiting to Xen context. */
#define SPEC_CTRL_EXIT_TO_XEN \
- ALTERNATIVE_2 __stringify(ASM_NOP17), \
- DO_SPEC_CTRL_EXIT_TO_XEN, X86_FEATURE_XEN_IBRS_SET, \
- DO_SPEC_CTRL_EXIT_TO_XEN, X86_FEATURE_XEN_IBRS_CLEAR
+ ALTERNATIVE __stringify(ASM_NOP17), \
+ DO_SPEC_CTRL_EXIT_TO_XEN, X86_FEATURE_SC_MSR
/* Use when exiting to guest context. */
#define SPEC_CTRL_EXIT_TO_GUEST \
- ALTERNATIVE_2 __stringify(ASM_NOP24), \
- DO_SPEC_CTRL_EXIT_TO_GUEST, X86_FEATURE_XEN_IBRS_SET, \
- DO_SPEC_CTRL_EXIT_TO_GUEST, X86_FEATURE_XEN_IBRS_CLEAR
+ ALTERNATIVE __stringify(ASM_NOP24), \
+ DO_SPEC_CTRL_EXIT_TO_GUEST, X86_FEATURE_SC_MSR
/* TODO: Drop these when the alternatives infrastructure is NMI/#MC safe. */
.macro SPEC_CTRL_ENTRY_FROM_INTR_IST
--
2.1.4

View file

@ -1,273 +0,0 @@
From 5cc3611de7d09140e55caa2c2d120ad326fff937 Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Mon, 30 Apr 2018 14:20:23 +0100
Subject: [PATCH] x86/spec_ctrl: Rename bits of infrastructure to avoid NATIVE
and VMEXIT
In hindsight, using NATIVE and VMEXIT as naming terminology was not clever.
A future change wants to split SPEC_CTRL_EXIT_TO_GUEST into PV and HVM
specific implementations, and using VMEXIT as a term is completely wrong.
Take the opportunity to fix some stale documentation in spec_ctrl_asm.h. The
IST helpers were missing from the large comment block, and since
SPEC_CTRL_ENTRY_FROM_INTR_IST was introduced, we've gained a new piece of
functionality which currently depends on the fine grain control, which exists
in lieu of livepatching. Note this in the comment.
No functional change.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Wei Liu <wei.liu2@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
Release-acked-by: Juergen Gross <jgross@suse.com>
(cherry picked from commit d9822b8a38114e96e4516dc998f4055249364d5d)
---
xen/arch/x86/hvm/svm/entry.S | 4 ++--
xen/arch/x86/hvm/vmx/entry.S | 4 ++--
xen/arch/x86/spec_ctrl.c | 20 ++++++++++----------
xen/arch/x86/x86_64/compat/entry.S | 2 +-
xen/arch/x86/x86_64/entry.S | 2 +-
xen/include/asm-x86/cpufeatures.h | 4 ++--
xen/include/asm-x86/spec_ctrl_asm.h | 36 +++++++++++++++++++++++++-----------
7 files changed, 43 insertions(+), 29 deletions(-)
diff --git a/xen/arch/x86/hvm/svm/entry.S b/xen/arch/x86/hvm/svm/entry.S
index bf092fe..5e7c080 100644
--- a/xen/arch/x86/hvm/svm/entry.S
+++ b/xen/arch/x86/hvm/svm/entry.S
@@ -83,7 +83,7 @@ UNLIKELY_END(svm_trace)
mov VCPUMSR_spec_ctrl_raw(%rax), %eax
/* WARNING! `ret`, `call *`, `jmp *` not safe beyond this point. */
- SPEC_CTRL_EXIT_TO_GUEST /* Req: a=spec_ctrl %rsp=regs/cpuinfo, Clob: cd */
+ SPEC_CTRL_EXIT_TO_HVM /* Req: a=spec_ctrl %rsp=regs/cpuinfo, Clob: cd */
pop %r15
pop %r14
@@ -108,7 +108,7 @@ UNLIKELY_END(svm_trace)
GET_CURRENT(bx)
- SPEC_CTRL_ENTRY_FROM_VMEXIT /* Req: b=curr %rsp=regs/cpuinfo, Clob: acd */
+ SPEC_CTRL_ENTRY_FROM_HVM /* Req: b=curr %rsp=regs/cpuinfo, Clob: acd */
/* WARNING! `ret`, `call *`, `jmp *` not safe before this point. */
mov VCPU_svm_vmcb(%rbx),%rcx
diff --git a/xen/arch/x86/hvm/vmx/entry.S b/xen/arch/x86/hvm/vmx/entry.S
index e750544..aa2f103 100644
--- a/xen/arch/x86/hvm/vmx/entry.S
+++ b/xen/arch/x86/hvm/vmx/entry.S
@@ -38,7 +38,7 @@ ENTRY(vmx_asm_vmexit_handler)
movb $1,VCPU_vmx_launched(%rbx)
mov %rax,VCPU_hvm_guest_cr2(%rbx)
- SPEC_CTRL_ENTRY_FROM_VMEXIT /* Req: b=curr %rsp=regs/cpuinfo, Clob: acd */
+ SPEC_CTRL_ENTRY_FROM_HVM /* Req: b=curr %rsp=regs/cpuinfo, Clob: acd */
/* WARNING! `ret`, `call *`, `jmp *` not safe before this point. */
mov %rsp,%rdi
@@ -76,7 +76,7 @@ UNLIKELY_END(realmode)
mov VCPUMSR_spec_ctrl_raw(%rax), %eax
/* WARNING! `ret`, `call *`, `jmp *` not safe beyond this point. */
- SPEC_CTRL_EXIT_TO_GUEST /* Req: a=spec_ctrl %rsp=regs/cpuinfo, Clob: cd */
+ SPEC_CTRL_EXIT_TO_HVM /* Req: a=spec_ctrl %rsp=regs/cpuinfo, Clob: cd */
mov VCPU_hvm_guest_cr2(%rbx),%rax
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index b62cfcc..015a9e2 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -35,8 +35,8 @@ static enum ind_thunk {
THUNK_JMP,
} opt_thunk __initdata = THUNK_DEFAULT;
static int8_t __initdata opt_ibrs = -1;
-static bool __initdata opt_rsb_native = true;
-static bool __initdata opt_rsb_vmexit = true;
+static bool __initdata opt_rsb_pv = true;
+static bool __initdata opt_rsb_hvm = true;
bool __read_mostly opt_ibpb = true;
uint8_t __read_mostly default_xen_spec_ctrl;
uint8_t __read_mostly default_spec_ctrl_flags;
@@ -69,9 +69,9 @@ static int __init parse_bti(const char *s)
else if ( (val = parse_boolean("ibpb", s, ss)) >= 0 )
opt_ibpb = val;
else if ( (val = parse_boolean("rsb_native", s, ss)) >= 0 )
- opt_rsb_native = val;
+ opt_rsb_pv = val;
else if ( (val = parse_boolean("rsb_vmexit", s, ss)) >= 0 )
- opt_rsb_vmexit = val;
+ opt_rsb_hvm = val;
else
rc = -EINVAL;
@@ -116,8 +116,8 @@ static void __init print_details(enum ind_thunk thunk, uint64_t caps)
default_xen_spec_ctrl & SPEC_CTRL_IBRS ? " IBRS+" :
" IBRS-" : "",
opt_ibpb ? " IBPB" : "",
- boot_cpu_has(X86_FEATURE_RSB_NATIVE) ? " RSB_NATIVE" : "",
- boot_cpu_has(X86_FEATURE_RSB_VMEXIT) ? " RSB_VMEXIT" : "");
+ boot_cpu_has(X86_FEATURE_SC_RSB_PV) ? " RSB_NATIVE" : "",
+ boot_cpu_has(X86_FEATURE_SC_RSB_HVM) ? " RSB_VMEXIT" : "");
printk("XPTI: %s\n",
boot_cpu_has(X86_FEATURE_NO_XPTI) ? "disabled" : "enabled");
@@ -307,9 +307,9 @@ void __init init_speculation_mitigations(void)
* If a processors speculates to 32bit PV guest kernel mappings, it is
* speculating in 64bit supervisor mode, and can leak data.
*/
- if ( opt_rsb_native )
+ if ( opt_rsb_pv )
{
- setup_force_cpu_cap(X86_FEATURE_RSB_NATIVE);
+ setup_force_cpu_cap(X86_FEATURE_SC_RSB_PV);
default_spec_ctrl_flags |= SCF_ist_rsb;
}
@@ -317,8 +317,8 @@ void __init init_speculation_mitigations(void)
* HVM guests can always poison the RSB to point at Xen supervisor
* mappings.
*/
- if ( opt_rsb_vmexit )
- setup_force_cpu_cap(X86_FEATURE_RSB_VMEXIT);
+ if ( opt_rsb_hvm )
+ setup_force_cpu_cap(X86_FEATURE_SC_RSB_HVM);
/* Check we have hardware IBPB support before using it... */
if ( !boot_cpu_has(X86_FEATURE_IBRSB) && !boot_cpu_has(X86_FEATURE_IBPB) )
diff --git a/xen/arch/x86/x86_64/compat/entry.S b/xen/arch/x86/x86_64/compat/entry.S
index a47cb9d..6a27d98 100644
--- a/xen/arch/x86/x86_64/compat/entry.S
+++ b/xen/arch/x86/x86_64/compat/entry.S
@@ -166,7 +166,7 @@ ENTRY(compat_restore_all_guest)
mov VCPUMSR_spec_ctrl_raw(%rax), %eax
/* WARNING! `ret`, `call *`, `jmp *` not safe beyond this point. */
- SPEC_CTRL_EXIT_TO_GUEST /* Req: a=spec_ctrl %rsp=regs/cpuinfo, Clob: cd */
+ SPEC_CTRL_EXIT_TO_PV /* Req: a=spec_ctrl %rsp=regs/cpuinfo, Clob: cd */
RESTORE_ALL adj=8 compat=1
.Lft0: iretq
diff --git a/xen/arch/x86/x86_64/entry.S b/xen/arch/x86/x86_64/entry.S
index 41d3ec2..0a0763a 100644
--- a/xen/arch/x86/x86_64/entry.S
+++ b/xen/arch/x86/x86_64/entry.S
@@ -196,7 +196,7 @@ restore_all_guest:
mov %r15d, %eax
/* WARNING! `ret`, `call *`, `jmp *` not safe beyond this point. */
- SPEC_CTRL_EXIT_TO_GUEST /* Req: a=spec_ctrl %rsp=regs/cpuinfo, Clob: cd */
+ SPEC_CTRL_EXIT_TO_PV /* Req: a=spec_ctrl %rsp=regs/cpuinfo, Clob: cd */
RESTORE_ALL
testw $TRAP_syscall,4(%rsp)
diff --git a/xen/include/asm-x86/cpufeatures.h b/xen/include/asm-x86/cpufeatures.h
index ca58b0e..f9aa5d7 100644
--- a/xen/include/asm-x86/cpufeatures.h
+++ b/xen/include/asm-x86/cpufeatures.h
@@ -27,6 +27,6 @@ XEN_CPUFEATURE(IND_THUNK_LFENCE,(FSCAPINTS+0)*32+13) /* Use IND_THUNK_LFENCE */
XEN_CPUFEATURE(IND_THUNK_JMP, (FSCAPINTS+0)*32+14) /* Use IND_THUNK_JMP */
XEN_CPUFEATURE(XEN_IBPB, (FSCAPINTS+0)*32+15) /* IBRSB || IBPB */
XEN_CPUFEATURE(SC_MSR, (FSCAPINTS+0)*32+16) /* MSR_SPEC_CTRL used by Xen */
-XEN_CPUFEATURE(RSB_NATIVE, (FSCAPINTS+0)*32+18) /* RSB overwrite needed for native */
-XEN_CPUFEATURE(RSB_VMEXIT, (FSCAPINTS+0)*32+19) /* RSB overwrite needed for vmexit */
+XEN_CPUFEATURE(SC_RSB_PV, (FSCAPINTS+0)*32+18) /* RSB overwrite needed for PV */
+XEN_CPUFEATURE(SC_RSB_HVM, (FSCAPINTS+0)*32+19) /* RSB overwrite needed for HVM */
XEN_CPUFEATURE(NO_XPTI, (FSCAPINTS+0)*32+20) /* XPTI mitigation not in use */
diff --git a/xen/include/asm-x86/spec_ctrl_asm.h b/xen/include/asm-x86/spec_ctrl_asm.h
index 17dd2cc..3d156ed 100644
--- a/xen/include/asm-x86/spec_ctrl_asm.h
+++ b/xen/include/asm-x86/spec_ctrl_asm.h
@@ -72,11 +72,14 @@
*
* The following ASM fragments implement this algorithm. See their local
* comments for further details.
- * - SPEC_CTRL_ENTRY_FROM_VMEXIT
+ * - SPEC_CTRL_ENTRY_FROM_HVM
* - SPEC_CTRL_ENTRY_FROM_PV
* - SPEC_CTRL_ENTRY_FROM_INTR
+ * - SPEC_CTRL_ENTRY_FROM_INTR_IST
+ * - SPEC_CTRL_EXIT_TO_XEN_IST
* - SPEC_CTRL_EXIT_TO_XEN
- * - SPEC_CTRL_EXIT_TO_GUEST
+ * - SPEC_CTRL_EXIT_TO_PV
+ * - SPEC_CTRL_EXIT_TO_HVM
*/
.macro DO_OVERWRITE_RSB tmp=rax
@@ -117,7 +120,7 @@
mov %\tmp, %rsp /* Restore old %rsp */
.endm
-.macro DO_SPEC_CTRL_ENTRY_FROM_VMEXIT
+.macro DO_SPEC_CTRL_ENTRY_FROM_HVM
/*
* Requires %rbx=current, %rsp=regs/cpuinfo
* Clobbers %rax, %rcx, %rdx
@@ -217,23 +220,23 @@
.endm
/* Use after a VMEXIT from an HVM guest. */
-#define SPEC_CTRL_ENTRY_FROM_VMEXIT \
+#define SPEC_CTRL_ENTRY_FROM_HVM \
ALTERNATIVE __stringify(ASM_NOP40), \
- DO_OVERWRITE_RSB, X86_FEATURE_RSB_VMEXIT; \
+ DO_OVERWRITE_RSB, X86_FEATURE_SC_RSB_HVM; \
ALTERNATIVE __stringify(ASM_NOP36), \
- DO_SPEC_CTRL_ENTRY_FROM_VMEXIT, X86_FEATURE_SC_MSR
+ DO_SPEC_CTRL_ENTRY_FROM_HVM, X86_FEATURE_SC_MSR
/* Use after an entry from PV context (syscall/sysenter/int80/int82/etc). */
#define SPEC_CTRL_ENTRY_FROM_PV \
ALTERNATIVE __stringify(ASM_NOP40), \
- DO_OVERWRITE_RSB, X86_FEATURE_RSB_NATIVE; \
+ DO_OVERWRITE_RSB, X86_FEATURE_SC_RSB_PV; \
ALTERNATIVE __stringify(ASM_NOP25), \
__stringify(DO_SPEC_CTRL_ENTRY maybexen=0), X86_FEATURE_SC_MSR
/* Use in interrupt/exception context. May interrupt Xen or PV context. */
#define SPEC_CTRL_ENTRY_FROM_INTR \
ALTERNATIVE __stringify(ASM_NOP40), \
- DO_OVERWRITE_RSB, X86_FEATURE_RSB_NATIVE; \
+ DO_OVERWRITE_RSB, X86_FEATURE_SC_RSB_PV; \
ALTERNATIVE __stringify(ASM_NOP33), \
__stringify(DO_SPEC_CTRL_ENTRY maybexen=1), X86_FEATURE_SC_MSR
@@ -242,12 +245,22 @@
ALTERNATIVE __stringify(ASM_NOP17), \
DO_SPEC_CTRL_EXIT_TO_XEN, X86_FEATURE_SC_MSR
-/* Use when exiting to guest context. */
-#define SPEC_CTRL_EXIT_TO_GUEST \
+/* Use when exiting to PV guest context. */
+#define SPEC_CTRL_EXIT_TO_PV \
ALTERNATIVE __stringify(ASM_NOP24), \
DO_SPEC_CTRL_EXIT_TO_GUEST, X86_FEATURE_SC_MSR
-/* TODO: Drop these when the alternatives infrastructure is NMI/#MC safe. */
+/* Use when exiting to HVM guest context. */
+#define SPEC_CTRL_EXIT_TO_HVM \
+ ALTERNATIVE __stringify(ASM_NOP24), \
+ DO_SPEC_CTRL_EXIT_TO_GUEST, X86_FEATURE_SC_MSR
+
+/*
+ * Use in IST interrupt/exception context. May interrupt Xen or PV context.
+ * Fine grain control of SCF_ist_wrmsr is needed for safety in the S3 resume
+ * path to avoid using MSR_SPEC_CTRL before the microcode introducing it has
+ * been reloaded.
+ */
.macro SPEC_CTRL_ENTRY_FROM_INTR_IST
/*
* Requires %rsp=regs, %r14=stack_end
@@ -294,6 +307,7 @@ UNLIKELY_DISPATCH_LABEL(\@_serialise):
UNLIKELY_END(\@_serialise)
.endm
+/* Use when exiting to Xen in IST context. */
.macro SPEC_CTRL_EXIT_TO_XEN_IST
/*
* Requires %rbx=stack_end
--
2.1.4

View file

@ -1,71 +0,0 @@
From 811fcf5137abdcd5b9ea7e5212098adb5bedae0f Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Mon, 7 May 2018 14:06:16 +0100
Subject: [PATCH] x86/spec_ctrl: Elide MSR_SPEC_CTRL handling in idle context
when possible
If Xen is virtualising MSR_SPEC_CTRL handling for guests, but using 0 as its
own MSR_SPEC_CTRL value, spec_ctrl_{enter,exit}_idle() need not write to the
MSR.
Requested-by: Jan Beulich <JBeulich@suse.com>
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Wei Liu <wei.liu2@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
Release-acked-by: Juergen Gross <jgross@suse.com>
(cherry picked from commit 94df6e8588e35cc2028ccb3fd2921c6e6360605e)
---
xen/arch/x86/spec_ctrl.c | 4 ++++
xen/include/asm-x86/cpufeatures.h | 1 +
xen/include/asm-x86/spec_ctrl.h | 4 ++--
3 files changed, 7 insertions(+), 2 deletions(-)
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index 015a9e2..55ef79f 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -327,6 +327,10 @@ void __init init_speculation_mitigations(void)
/* (Re)init BSP state now that default_spec_ctrl_flags has been calculated. */
init_shadow_spec_ctrl_state();
+ /* If Xen is using any MSR_SPEC_CTRL settings, adjust the idle path. */
+ if ( default_xen_spec_ctrl )
+ setup_force_cpu_cap(X86_FEATURE_SC_MSR_IDLE);
+
print_details(thunk, caps);
}
diff --git a/xen/include/asm-x86/cpufeatures.h b/xen/include/asm-x86/cpufeatures.h
index f9aa5d7..32b7f04 100644
--- a/xen/include/asm-x86/cpufeatures.h
+++ b/xen/include/asm-x86/cpufeatures.h
@@ -30,3 +30,4 @@ XEN_CPUFEATURE(SC_MSR, (FSCAPINTS+0)*32+16) /* MSR_SPEC_CTRL used by Xe
XEN_CPUFEATURE(SC_RSB_PV, (FSCAPINTS+0)*32+18) /* RSB overwrite needed for PV */
XEN_CPUFEATURE(SC_RSB_HVM, (FSCAPINTS+0)*32+19) /* RSB overwrite needed for HVM */
XEN_CPUFEATURE(NO_XPTI, (FSCAPINTS+0)*32+20) /* XPTI mitigation not in use */
+XEN_CPUFEATURE(SC_MSR_IDLE, (FSCAPINTS+0)*32+21) /* SC_MSR && default_xen_spec_ctrl */
diff --git a/xen/include/asm-x86/spec_ctrl.h b/xen/include/asm-x86/spec_ctrl.h
index 7d7c42e..77f92ba 100644
--- a/xen/include/asm-x86/spec_ctrl.h
+++ b/xen/include/asm-x86/spec_ctrl.h
@@ -52,7 +52,7 @@ static always_inline void spec_ctrl_enter_idle(struct cpu_info *info)
barrier();
info->spec_ctrl_flags |= SCF_use_shadow;
barrier();
- asm volatile ( ALTERNATIVE(ASM_NOP3, "wrmsr", X86_FEATURE_SC_MSR)
+ asm volatile ( ALTERNATIVE(ASM_NOP3, "wrmsr", X86_FEATURE_SC_MSR_IDLE)
:: "a" (val), "c" (MSR_SPEC_CTRL), "d" (0) : "memory" );
}
@@ -67,7 +67,7 @@ static always_inline void spec_ctrl_exit_idle(struct cpu_info *info)
*/
info->spec_ctrl_flags &= ~SCF_use_shadow;
barrier();
- asm volatile ( ALTERNATIVE(ASM_NOP3, "wrmsr", X86_FEATURE_SC_MSR)
+ asm volatile ( ALTERNATIVE(ASM_NOP3, "wrmsr", X86_FEATURE_SC_MSR_IDLE)
:: "a" (val), "c" (MSR_SPEC_CTRL), "d" (0) : "memory" );
}
--
2.1.4

View file

@ -1,111 +0,0 @@
From 2acc4cba7eb2559bafdd4d8238466ad81322a35a Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Tue, 17 Apr 2018 14:15:04 +0100
Subject: [PATCH] x86/spec_ctrl: Split X86_FEATURE_SC_MSR into PV and HVM
variants
In order to separately control whether MSR_SPEC_CTRL is virtualised for PV and
HVM guests, split the feature used to control runtime alternatives into two.
Xen will use MSR_SPEC_CTRL itself if either of these features are active.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Wei Liu <wei.liu2@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
Release-acked-by: Juergen Gross <jgross@suse.com>
(cherry picked from commit fa9eb09d446a1279f5e861e6b84fa8675dabf148)
---
xen/arch/x86/spec_ctrl.c | 6 ++++--
xen/include/asm-x86/cpufeatures.h | 5 +++--
xen/include/asm-x86/spec_ctrl_asm.h | 12 ++++++------
3 files changed, 13 insertions(+), 10 deletions(-)
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index 55ef79f..a940308 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -112,7 +112,8 @@ static void __init print_details(enum ind_thunk thunk, uint64_t caps)
thunk == THUNK_RETPOLINE ? "RETPOLINE" :
thunk == THUNK_LFENCE ? "LFENCE" :
thunk == THUNK_JMP ? "JMP" : "?",
- boot_cpu_has(X86_FEATURE_SC_MSR) ?
+ (boot_cpu_has(X86_FEATURE_SC_MSR_PV) ||
+ boot_cpu_has(X86_FEATURE_SC_MSR_HVM)) ?
default_xen_spec_ctrl & SPEC_CTRL_IBRS ? " IBRS+" :
" IBRS-" : "",
opt_ibpb ? " IBPB" : "",
@@ -286,7 +287,8 @@ void __init init_speculation_mitigations(void)
* need the IBRS entry/exit logic to virtualise IBRS support for
* guests.
*/
- setup_force_cpu_cap(X86_FEATURE_SC_MSR);
+ setup_force_cpu_cap(X86_FEATURE_SC_MSR_PV);
+ setup_force_cpu_cap(X86_FEATURE_SC_MSR_HVM);
if ( ibrs )
default_xen_spec_ctrl |= SPEC_CTRL_IBRS;
diff --git a/xen/include/asm-x86/cpufeatures.h b/xen/include/asm-x86/cpufeatures.h
index 32b7f04..b90aa2d 100644
--- a/xen/include/asm-x86/cpufeatures.h
+++ b/xen/include/asm-x86/cpufeatures.h
@@ -26,8 +26,9 @@ XEN_CPUFEATURE(LFENCE_DISPATCH, (FSCAPINTS+0)*32+12) /* lfence set as Dispatch S
XEN_CPUFEATURE(IND_THUNK_LFENCE,(FSCAPINTS+0)*32+13) /* Use IND_THUNK_LFENCE */
XEN_CPUFEATURE(IND_THUNK_JMP, (FSCAPINTS+0)*32+14) /* Use IND_THUNK_JMP */
XEN_CPUFEATURE(XEN_IBPB, (FSCAPINTS+0)*32+15) /* IBRSB || IBPB */
-XEN_CPUFEATURE(SC_MSR, (FSCAPINTS+0)*32+16) /* MSR_SPEC_CTRL used by Xen */
+XEN_CPUFEATURE(SC_MSR_PV, (FSCAPINTS+0)*32+16) /* MSR_SPEC_CTRL used by Xen for PV */
+XEN_CPUFEATURE(SC_MSR_HVM, (FSCAPINTS+0)*32+17) /* MSR_SPEC_CTRL used by Xen for HVM */
XEN_CPUFEATURE(SC_RSB_PV, (FSCAPINTS+0)*32+18) /* RSB overwrite needed for PV */
XEN_CPUFEATURE(SC_RSB_HVM, (FSCAPINTS+0)*32+19) /* RSB overwrite needed for HVM */
XEN_CPUFEATURE(NO_XPTI, (FSCAPINTS+0)*32+20) /* XPTI mitigation not in use */
-XEN_CPUFEATURE(SC_MSR_IDLE, (FSCAPINTS+0)*32+21) /* SC_MSR && default_xen_spec_ctrl */
+XEN_CPUFEATURE(SC_MSR_IDLE, (FSCAPINTS+0)*32+21) /* (SC_MSR_PV || SC_MSR_HVM) && default_xen_spec_ctrl */
diff --git a/xen/include/asm-x86/spec_ctrl_asm.h b/xen/include/asm-x86/spec_ctrl_asm.h
index 3d156ed..c659f3f 100644
--- a/xen/include/asm-x86/spec_ctrl_asm.h
+++ b/xen/include/asm-x86/spec_ctrl_asm.h
@@ -224,36 +224,36 @@
ALTERNATIVE __stringify(ASM_NOP40), \
DO_OVERWRITE_RSB, X86_FEATURE_SC_RSB_HVM; \
ALTERNATIVE __stringify(ASM_NOP36), \
- DO_SPEC_CTRL_ENTRY_FROM_HVM, X86_FEATURE_SC_MSR
+ DO_SPEC_CTRL_ENTRY_FROM_HVM, X86_FEATURE_SC_MSR_HVM
/* Use after an entry from PV context (syscall/sysenter/int80/int82/etc). */
#define SPEC_CTRL_ENTRY_FROM_PV \
ALTERNATIVE __stringify(ASM_NOP40), \
DO_OVERWRITE_RSB, X86_FEATURE_SC_RSB_PV; \
ALTERNATIVE __stringify(ASM_NOP25), \
- __stringify(DO_SPEC_CTRL_ENTRY maybexen=0), X86_FEATURE_SC_MSR
+ __stringify(DO_SPEC_CTRL_ENTRY maybexen=0), X86_FEATURE_SC_MSR_PV
/* Use in interrupt/exception context. May interrupt Xen or PV context. */
#define SPEC_CTRL_ENTRY_FROM_INTR \
ALTERNATIVE __stringify(ASM_NOP40), \
DO_OVERWRITE_RSB, X86_FEATURE_SC_RSB_PV; \
ALTERNATIVE __stringify(ASM_NOP33), \
- __stringify(DO_SPEC_CTRL_ENTRY maybexen=1), X86_FEATURE_SC_MSR
+ __stringify(DO_SPEC_CTRL_ENTRY maybexen=1), X86_FEATURE_SC_MSR_PV
/* Use when exiting to Xen context. */
#define SPEC_CTRL_EXIT_TO_XEN \
ALTERNATIVE __stringify(ASM_NOP17), \
- DO_SPEC_CTRL_EXIT_TO_XEN, X86_FEATURE_SC_MSR
+ DO_SPEC_CTRL_EXIT_TO_XEN, X86_FEATURE_SC_MSR_PV
/* Use when exiting to PV guest context. */
#define SPEC_CTRL_EXIT_TO_PV \
ALTERNATIVE __stringify(ASM_NOP24), \
- DO_SPEC_CTRL_EXIT_TO_GUEST, X86_FEATURE_SC_MSR
+ DO_SPEC_CTRL_EXIT_TO_GUEST, X86_FEATURE_SC_MSR_PV
/* Use when exiting to HVM guest context. */
#define SPEC_CTRL_EXIT_TO_HVM \
ALTERNATIVE __stringify(ASM_NOP24), \
- DO_SPEC_CTRL_EXIT_TO_GUEST, X86_FEATURE_SC_MSR
+ DO_SPEC_CTRL_EXIT_TO_GUEST, X86_FEATURE_SC_MSR_HVM
/*
* Use in IST interrupt/exception context. May interrupt Xen or PV context.
--
2.1.4

View file

@ -1,134 +0,0 @@
From 5b223f41d59887ea5d13e2406597ff472ba6f2fc Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Wed, 9 May 2018 13:59:56 +0100
Subject: [PATCH] x86/spec_ctrl: Explicitly set Xen's default MSR_SPEC_CTRL
value
With the impending ability to disable MSR_SPEC_CTRL handling on a
per-guest-type basis, the first exit-from-guest may not have the side effect
of loading Xen's choice of value. Explicitly set Xen's default during the BSP
and AP boot paths.
For the BSP however, delay setting a non-zero MSR_SPEC_CTRL default until
after dom0 has been constructed when safe to do so. Oracle report that this
speeds up boots of some hardware by 50s.
"when safe to do so" is based on whether we are virtualised. A native boot
won't have any other code running in a position to mount an attack.
Reported-by: Zhenzhong Duan <zhenzhong.duan@oracle.com>
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Wei Liu <wei.liu2@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
Release-acked-by: Juergen Gross <jgross@suse.com>
(cherry picked from commit cb8c12020307b39a89273d7699e89000451987ab)
---
xen/arch/x86/setup.c | 7 +++++++
xen/arch/x86/smpboot.c | 8 ++++++++
xen/arch/x86/spec_ctrl.c | 32 ++++++++++++++++++++++++++++++++
xen/include/asm-x86/spec_ctrl.h | 2 ++
4 files changed, 49 insertions(+)
diff --git a/xen/arch/x86/setup.c b/xen/arch/x86/setup.c
index 482fe11..1995c4c 100644
--- a/xen/arch/x86/setup.c
+++ b/xen/arch/x86/setup.c
@@ -1746,6 +1746,13 @@ void __init noreturn __start_xen(unsigned long mbi_p)
setup_io_bitmap(dom0);
+ if ( bsp_delay_spec_ctrl )
+ {
+ get_cpu_info()->spec_ctrl_flags &= ~SCF_use_shadow;
+ barrier();
+ wrmsrl(MSR_SPEC_CTRL, default_xen_spec_ctrl);
+ }
+
/* Jump to the 1:1 virtual mappings of cpu0_stack. */
asm volatile ("mov %[stk], %%rsp; jmp %c[fn]" ::
[stk] "g" (__va(__pa(get_stack_bottom()))),
diff --git a/xen/arch/x86/smpboot.c b/xen/arch/x86/smpboot.c
index f81fc2c..ee8b183 100644
--- a/xen/arch/x86/smpboot.c
+++ b/xen/arch/x86/smpboot.c
@@ -351,6 +351,14 @@ void start_secondary(void *unused)
else
microcode_resume_cpu(cpu);
+ /*
+ * If MSR_SPEC_CTRL is available, apply Xen's default setting and discard
+ * any firmware settings. Note: MSR_SPEC_CTRL may only become available
+ * after loading microcode.
+ */
+ if ( boot_cpu_has(X86_FEATURE_IBRSB) )
+ wrmsrl(MSR_SPEC_CTRL, default_xen_spec_ctrl);
+
if ( xen_guest )
hypervisor_ap_setup();
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index a940308..3adec1a 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -38,6 +38,8 @@ static int8_t __initdata opt_ibrs = -1;
static bool __initdata opt_rsb_pv = true;
static bool __initdata opt_rsb_hvm = true;
bool __read_mostly opt_ibpb = true;
+
+bool __initdata bsp_delay_spec_ctrl;
uint8_t __read_mostly default_xen_spec_ctrl;
uint8_t __read_mostly default_spec_ctrl_flags;
@@ -334,6 +336,36 @@ void __init init_speculation_mitigations(void)
setup_force_cpu_cap(X86_FEATURE_SC_MSR_IDLE);
print_details(thunk, caps);
+
+ /*
+ * If MSR_SPEC_CTRL is available, apply Xen's default setting and discard
+ * any firmware settings. For performance reasons, when safe to do so, we
+ * delay applying non-zero settings until after dom0 has been constructed.
+ *
+ * "when safe to do so" is based on whether we are virtualised. A native
+ * boot won't have any other code running in a position to mount an
+ * attack.
+ */
+ if ( boot_cpu_has(X86_FEATURE_IBRSB) )
+ {
+ bsp_delay_spec_ctrl = !cpu_has_hypervisor && default_xen_spec_ctrl;
+
+ /*
+ * If delaying MSR_SPEC_CTRL setup, use the same mechanism as
+ * spec_ctrl_enter_idle(), by using a shadow value of zero.
+ */
+ if ( bsp_delay_spec_ctrl )
+ {
+ struct cpu_info *info = get_cpu_info();
+
+ info->shadow_spec_ctrl = 0;
+ barrier();
+ info->spec_ctrl_flags |= SCF_use_shadow;
+ barrier();
+ }
+
+ wrmsrl(MSR_SPEC_CTRL, bsp_delay_spec_ctrl ? 0 : default_xen_spec_ctrl);
+ }
}
static void __init __maybe_unused build_assertions(void)
diff --git a/xen/include/asm-x86/spec_ctrl.h b/xen/include/asm-x86/spec_ctrl.h
index 77f92ba..c6a38f4 100644
--- a/xen/include/asm-x86/spec_ctrl.h
+++ b/xen/include/asm-x86/spec_ctrl.h
@@ -27,6 +27,8 @@
void init_speculation_mitigations(void);
extern bool opt_ibpb;
+
+extern bool bsp_delay_spec_ctrl;
extern uint8_t default_xen_spec_ctrl;
extern uint8_t default_spec_ctrl_flags;
--
2.1.4

View file

@ -1,132 +0,0 @@
From bce7a2145abc3c7e5bfd7e2168714d194124a3ab Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Tue, 1 May 2018 11:59:03 +0100
Subject: [PATCH] x86/cpuid: Improvements to guest policies for speculative
sidechannel features
If Xen isn't virtualising MSR_SPEC_CTRL for guests, IBRSB shouldn't be
advertised. It is not currently possible to express this via the existing
command line options, but such an ability will be introduced.
Another useful option in some usecases is to offer IBPB without IBRS. When a
guest kernel is known to be compatible (uses retpoline and knows about the AMD
IBPB feature bit), an administrator with pre-Skylake hardware may wish to hide
IBRS. This allows the VM to have full protection, without Xen or the VM
needing to touch MSR_SPEC_CTRL, which can reduce the overhead of Spectre
mitigations.
Break the logic common to both PV and HVM CPUID calculations into a common
helper, to avoid duplication.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Wei Liu <wei.liu2@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
Release-acked-by: Juergen Gross <jgross@suse.com>
(cherry picked from commit cb06b308ec71b23f37a44f5e2351fe2cae0306e9)
---
xen/arch/x86/cpuid.c | 60 ++++++++++++++++++++++++++++++++--------------------
1 file changed, 37 insertions(+), 23 deletions(-)
diff --git a/xen/arch/x86/cpuid.c b/xen/arch/x86/cpuid.c
index b3c9ac6..b45b145 100644
--- a/xen/arch/x86/cpuid.c
+++ b/xen/arch/x86/cpuid.c
@@ -368,6 +368,28 @@ static void __init calculate_host_policy(void)
}
}
+static void __init guest_common_feature_adjustments(uint32_t *fs)
+{
+ /* Unconditionally claim to be able to set the hypervisor bit. */
+ __set_bit(X86_FEATURE_HYPERVISOR, fs);
+
+ /*
+ * If IBRS is offered to the guest, unconditionally offer STIBP. It is a
+ * nop on non-HT hardware, and has this behaviour to make heterogeneous
+ * setups easier to manage.
+ */
+ if ( test_bit(X86_FEATURE_IBRSB, fs) )
+ __set_bit(X86_FEATURE_STIBP, fs);
+
+ /*
+ * On hardware which supports IBRS/IBPB, we can offer IBPB independently
+ * of IBRS by using the AMD feature bit. An administrator may wish for
+ * performance reasons to offer IBPB without IBRS.
+ */
+ if ( host_cpuid_policy.feat.ibrsb )
+ __set_bit(X86_FEATURE_IBPB, fs);
+}
+
static void __init calculate_pv_max_policy(void)
{
struct cpuid_policy *p = &pv_max_cpuid_policy;
@@ -380,18 +402,14 @@ static void __init calculate_pv_max_policy(void)
for ( i = 0; i < ARRAY_SIZE(pv_featureset); ++i )
pv_featureset[i] &= pv_featuremask[i];
- /* Unconditionally claim to be able to set the hypervisor bit. */
- __set_bit(X86_FEATURE_HYPERVISOR, pv_featureset);
-
- /* On hardware with IBRS/IBPB support, there are further adjustments. */
- if ( test_bit(X86_FEATURE_IBRSB, pv_featureset) )
- {
- /* Offer STIBP unconditionally. It is a nop on non-HT hardware. */
- __set_bit(X86_FEATURE_STIBP, pv_featureset);
+ /*
+ * If Xen isn't virtualising MSR_SPEC_CTRL for PV guests because of
+ * administrator choice, hide the feature.
+ */
+ if ( !boot_cpu_has(X86_FEATURE_SC_MSR_PV) )
+ __clear_bit(X86_FEATURE_IBRSB, pv_featureset);
- /* AMD's IBPB is a subset of IBRS/IBPB. */
- __set_bit(X86_FEATURE_IBPB, pv_featureset);
- }
+ guest_common_feature_adjustments(pv_featureset);
sanitise_featureset(pv_featureset);
cpuid_featureset_to_policy(pv_featureset, p);
@@ -419,9 +437,6 @@ static void __init calculate_hvm_max_policy(void)
for ( i = 0; i < ARRAY_SIZE(hvm_featureset); ++i )
hvm_featureset[i] &= hvm_featuremask[i];
- /* Unconditionally claim to be able to set the hypervisor bit. */
- __set_bit(X86_FEATURE_HYPERVISOR, hvm_featureset);
-
/*
* Xen can provide an APIC emulation to HVM guests even if the host's APIC
* isn't enabled.
@@ -438,6 +453,13 @@ static void __init calculate_hvm_max_policy(void)
__set_bit(X86_FEATURE_SEP, hvm_featureset);
/*
+ * If Xen isn't virtualising MSR_SPEC_CTRL for HVM guests because of
+ * administrator choice, hide the feature.
+ */
+ if ( !boot_cpu_has(X86_FEATURE_SC_MSR_HVM) )
+ __clear_bit(X86_FEATURE_IBRSB, hvm_featureset);
+
+ /*
* With VT-x, some features are only supported by Xen if dedicated
* hardware support is also available.
*/
@@ -450,15 +472,7 @@ static void __init calculate_hvm_max_policy(void)
__clear_bit(X86_FEATURE_XSAVES, hvm_featureset);
}
- /* On hardware with IBRS/IBPB support, there are further adjustments. */
- if ( test_bit(X86_FEATURE_IBRSB, hvm_featureset) )
- {
- /* Offer STIBP unconditionally. It is a nop on non-HT hardware. */
- __set_bit(X86_FEATURE_STIBP, hvm_featureset);
-
- /* AMD's IBPB is a subset of IBRS/IBPB. */
- __set_bit(X86_FEATURE_IBPB, hvm_featureset);
- }
+ guest_common_feature_adjustments(hvm_featureset);
sanitise_featureset(hvm_featureset);
cpuid_featureset_to_policy(hvm_featureset, p);
--
2.1.4

View file

@ -1,344 +0,0 @@
From 952ff9f5590e37952d7dd3d89e16a47a238ab079 Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Thu, 26 Apr 2018 10:52:55 +0100
Subject: [PATCH] x86/spec_ctrl: Introduce a new `spec-ctrl=` command line
argument to replace `bti=`
In hindsight, the options for `bti=` aren't as flexible or useful as expected
(including several options which don't appear to behave as intended).
Changing the behaviour of an existing option is problematic for compatibility,
so introduce a new `spec-ctrl=` in the hopes that we can do better.
One common way of deploying Xen is with a single PV dom0 and all domUs being
HVM domains. In such a setup, an administrator who has weighed up the risks
may wish to forgo protection against malicious PV domains, to reduce the
overall performance hit. To cater for this usecase, `spec-ctrl=no-pv` will
disable all speculative protection for PV domains, while leaving all
speculative protection for HVM domains intact.
For coding clarity as much as anything else, the suboptions are grouped by
logical area; those which affect the alternatives blocks, and those which
affect Xen's in-hypervisor settings. See the xen-command-line.markdown for
full details of the new options.
While changing the command line options, take the time to change how the data
is reported to the user. The three DEBUG printks are upgraded to unilateral,
as they are all relevant pieces of information, and the old "mitigations:"
line is split in the two logical areas described above.
Sample output from booting with `spec-ctrl=no-pv` looks like:
(XEN) Speculative mitigation facilities:
(XEN) Hardware features: IBRS/IBPB STIBP IBPB
(XEN) Compiled-in support: INDIRECT_THUNK
(XEN) Xen settings: BTI-Thunk RETPOLINE, SPEC_CTRL: IBRS-, Other: IBPB
(XEN) Support for VMs: PV: None, HVM: MSR_SPEC_CTRL RSB
(XEN) XPTI (64-bit PV only): Dom0 enabled, DomU enabled
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Wei Liu <wei.liu2@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
Release-acked-by: Juergen Gross <jgross@suse.com>
(cherry picked from commit 3352afc26c497d26ecb70527db3cb29daf7b1422)
---
docs/misc/xen-command-line.markdown | 49 +++++++++++
xen/arch/x86/spec_ctrl.c | 160 ++++++++++++++++++++++++++++++------
2 files changed, 186 insertions(+), 23 deletions(-)
diff --git a/docs/misc/xen-command-line.markdown b/docs/misc/xen-command-line.markdown
index 6c673ee..43a6ddb 100644
--- a/docs/misc/xen-command-line.markdown
+++ b/docs/misc/xen-command-line.markdown
@@ -248,6 +248,9 @@ the NMI watchdog is also enabled.
### bti (x86)
> `= List of [ thunk=retpoline|lfence|jmp, ibrs=<bool>, ibpb=<bool>, rsb_{vmexit,native}=<bool> ]`
+**WARNING: This command line option is deprecated, and superseded by
+_spec-ctrl=_ - using both options in combination is undefined.**
+
Branch Target Injection controls. By default, Xen will pick the most
appropriate BTI mitigations based on compiled in support, loaded microcode,
and hardware details.
@@ -1698,6 +1701,52 @@ enforces the maximum theoretically necessary timeout of 670ms. Any number
is being interpreted as a custom timeout in milliseconds. Zero or boolean
false disable the quirk workaround, which is also the default.
+### spec-ctrl (x86)
+> `= List of [ <bool>, xen=<bool>, {pv,hvm,msr-sc,rsb}=<bool>,
+> bti-thunk=retpoline|lfence|jmp, {ibrs,ibpb}=<bool> ]`
+
+Controls for speculative execution sidechannel mitigations. By default, Xen
+will pick the most appropriate mitigations based on compiled in support,
+loaded microcode, and hardware details, and will virtualise appropriate
+mitigations for guests to use.
+
+**WARNING: Any use of this option may interfere with heuristics. Use with
+extreme care.**
+
+An overall boolean value, `spec-ctrl=no`, can be specified to turn off all
+mitigations, including pieces of infrastructure used to virtualise certain
+mitigation features for guests. Alternatively, a slightly more restricted
+`spec-ctrl=no-xen` can be used to turn off all of Xen's mitigations, while
+leaving the virtualisation support in place for guests to use. Use of a
+positive boolean value for either of these options is invalid.
+
+The booleans `pv=`, `hvm=`, `msr-sc=` and `rsb=` offer fine grained control
+over the alternative blocks used by Xen. These impact Xen's ability to
+protect itself, and Xen's ability to virtualise support for guests to use.
+
+* `pv=` and `hvm=` offer control over all suboptions for PV and HVM guests
+ respectively.
+* `msr-sc=` offers control over Xen's support for manipulating MSR\_SPEC\_CTRL
+ on entry and exit. These blocks are necessary to virtualise support for
+ guests and if disabled, guests will be unable to use IBRS/STIBP/etc.
+* `rsb=` offers control over whether to overwrite the Return Stack Buffer /
+ Return Address Stack on entry to Xen.
+
+If Xen was compiled with INDIRECT\_THUNK support, `bti-thunk=` can be used to
+select which of the thunks gets patched into the `__x86_indirect_thunk_%reg`
+locations. The default thunk is `retpoline` (generally preferred for Intel
+hardware), with the alternatives being `jmp` (a `jmp *%reg` gadget, minimal
+overhead), and `lfence` (an `lfence; jmp *%reg` gadget, preferred for AMD).
+
+On hardware supporting IBRS (Indirect Branch Restricted Speculation), the
+`ibrs=` option can be used to force or prevent Xen using the feature itself.
+If Xen is not using IBRS itself, functionality is still set up so IBRS can be
+virtualised for guests.
+
+On hardware supporting IBPB (Indirect Branch Prediction Barrier), the `ibpb=`
+option can be used to force (the default) or prevent Xen from issuing branch
+prediction barriers on vcpu context switches.
+
### sync\_console
> `= <boolean>`
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index 3adec1a..4f9282f 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -26,6 +26,13 @@
#include <asm/spec_ctrl.h>
#include <asm/spec_ctrl_asm.h>
+/* Cmdline controls for Xen's alternative blocks. */
+static bool __initdata opt_msr_sc_pv = true;
+static bool __initdata opt_msr_sc_hvm = true;
+static bool __initdata opt_rsb_pv = true;
+static bool __initdata opt_rsb_hvm = true;
+
+/* Cmdline controls for Xen's speculative settings. */
static enum ind_thunk {
THUNK_DEFAULT, /* Decide which thunk to use at boot time. */
THUNK_NONE, /* Missing compiler support for thunks. */
@@ -35,8 +42,6 @@ static enum ind_thunk {
THUNK_JMP,
} opt_thunk __initdata = THUNK_DEFAULT;
static int8_t __initdata opt_ibrs = -1;
-static bool __initdata opt_rsb_pv = true;
-static bool __initdata opt_rsb_hvm = true;
bool __read_mostly opt_ibpb = true;
bool __initdata bsp_delay_spec_ctrl;
@@ -84,8 +89,95 @@ static int __init parse_bti(const char *s)
}
custom_param("bti", parse_bti);
+static int __init parse_spec_ctrl(const char *s)
+{
+ const char *ss;
+ int val, rc = 0;
+
+ do {
+ ss = strchr(s, ',');
+ if ( !ss )
+ ss = strchr(s, '\0');
+
+ /* Global and Xen-wide disable. */
+ val = parse_bool(s, ss);
+ if ( !val )
+ {
+ opt_msr_sc_pv = false;
+ opt_msr_sc_hvm = false;
+
+ disable_common:
+ opt_rsb_pv = false;
+ opt_rsb_hvm = false;
+
+ opt_thunk = THUNK_JMP;
+ opt_ibrs = 0;
+ opt_ibpb = false;
+ }
+ else if ( val > 0 )
+ rc = -EINVAL;
+ else if ( (val = parse_boolean("xen", s, ss)) >= 0 )
+ {
+ if ( !val )
+ goto disable_common;
+
+ rc = -EINVAL;
+ }
+
+ /* Xen's alternative blocks. */
+ else if ( (val = parse_boolean("pv", s, ss)) >= 0 )
+ {
+ opt_msr_sc_pv = val;
+ opt_rsb_pv = val;
+ }
+ else if ( (val = parse_boolean("hvm", s, ss)) >= 0 )
+ {
+ opt_msr_sc_hvm = val;
+ opt_rsb_hvm = val;
+ }
+ else if ( (val = parse_boolean("msr-sc", s, ss)) >= 0 )
+ {
+ opt_msr_sc_pv = val;
+ opt_msr_sc_hvm = val;
+ }
+ else if ( (val = parse_boolean("rsb", s, ss)) >= 0 )
+ {
+ opt_rsb_pv = val;
+ opt_rsb_hvm = val;
+ }
+
+ /* Xen's speculative sidechannel mitigation settings. */
+ else if ( !strncmp(s, "bti-thunk=", 10) )
+ {
+ s += 10;
+
+ if ( !strncmp(s, "retpoline", ss - s) )
+ opt_thunk = THUNK_RETPOLINE;
+ else if ( !strncmp(s, "lfence", ss - s) )
+ opt_thunk = THUNK_LFENCE;
+ else if ( !strncmp(s, "jmp", ss - s) )
+ opt_thunk = THUNK_JMP;
+ else
+ rc = -EINVAL;
+ }
+ else if ( (val = parse_boolean("ibrs", s, ss)) >= 0 )
+ opt_ibrs = val;
+ else if ( (val = parse_boolean("ibpb", s, ss)) >= 0 )
+ opt_ibpb = val;
+ else
+ rc = -EINVAL;
+
+ s = ss + 1;
+ } while ( *ss );
+
+ return rc;
+}
+custom_param("spec-ctrl", parse_spec_ctrl);
+
static void __init print_details(enum ind_thunk thunk, uint64_t caps)
{
+ bool use_spec_ctrl = (boot_cpu_has(X86_FEATURE_SC_MSR_PV) ||
+ boot_cpu_has(X86_FEATURE_SC_MSR_HVM));
unsigned int _7d0 = 0, e8b = 0, tmp;
/* Collect diagnostics about available mitigations. */
@@ -94,10 +186,10 @@ static void __init print_details(enum ind_thunk thunk, uint64_t caps)
if ( boot_cpu_data.extended_cpuid_level >= 0x80000008 )
cpuid(0x80000008, &tmp, &e8b, &tmp, &tmp);
- printk(XENLOG_DEBUG "Speculative mitigation facilities:\n");
+ printk("Speculative mitigation facilities:\n");
/* Hardware features which pertain to speculative mitigations. */
- printk(XENLOG_DEBUG " Hardware features:%s%s%s%s%s%s\n",
+ printk(" Hardware features:%s%s%s%s%s%s\n",
(_7d0 & cpufeat_mask(X86_FEATURE_IBRSB)) ? " IBRS/IBPB" : "",
(_7d0 & cpufeat_mask(X86_FEATURE_STIBP)) ? " STIBP" : "",
(e8b & cpufeat_mask(X86_FEATURE_IBPB)) ? " IBPB" : "",
@@ -107,20 +199,31 @@ static void __init print_details(enum ind_thunk thunk, uint64_t caps)
/* Compiled-in support which pertains to BTI mitigations. */
if ( IS_ENABLED(CONFIG_INDIRECT_THUNK) )
- printk(XENLOG_DEBUG " Compiled-in support: INDIRECT_THUNK\n");
+ printk(" Compiled-in support: INDIRECT_THUNK\n");
- printk("BTI mitigations: Thunk %s, Others:%s%s%s%s\n",
+ /* Settings for Xen's protection, irrespective of guests. */
+ printk(" Xen settings: BTI-Thunk %s, SPEC_CTRL: %s, Other:%s\n",
thunk == THUNK_NONE ? "N/A" :
thunk == THUNK_RETPOLINE ? "RETPOLINE" :
thunk == THUNK_LFENCE ? "LFENCE" :
thunk == THUNK_JMP ? "JMP" : "?",
+ !use_spec_ctrl ? "No" :
+ (default_xen_spec_ctrl & SPEC_CTRL_IBRS) ? "IBRS+" : "IBRS-",
+ opt_ibpb ? " IBPB" : "");
+
+ /*
+ * Alternatives blocks for protecting against and/or virtualising
+ * mitigation support for guests.
+ */
+ printk(" Support for VMs: PV:%s%s%s, HVM:%s%s%s\n",
(boot_cpu_has(X86_FEATURE_SC_MSR_PV) ||
- boot_cpu_has(X86_FEATURE_SC_MSR_HVM)) ?
- default_xen_spec_ctrl & SPEC_CTRL_IBRS ? " IBRS+" :
- " IBRS-" : "",
- opt_ibpb ? " IBPB" : "",
- boot_cpu_has(X86_FEATURE_SC_RSB_PV) ? " RSB_NATIVE" : "",
- boot_cpu_has(X86_FEATURE_SC_RSB_HVM) ? " RSB_VMEXIT" : "");
+ boot_cpu_has(X86_FEATURE_SC_RSB_PV)) ? "" : " None",
+ boot_cpu_has(X86_FEATURE_SC_MSR_PV) ? " MSR_SPEC_CTRL" : "",
+ boot_cpu_has(X86_FEATURE_SC_RSB_PV) ? " RSB" : "",
+ (boot_cpu_has(X86_FEATURE_SC_MSR_HVM) ||
+ boot_cpu_has(X86_FEATURE_SC_RSB_HVM)) ? "" : " None",
+ boot_cpu_has(X86_FEATURE_SC_MSR_HVM) ? " MSR_SPEC_CTRL" : "",
+ boot_cpu_has(X86_FEATURE_SC_RSB_HVM) ? " RSB" : "");
printk("XPTI: %s\n",
boot_cpu_has(X86_FEATURE_NO_XPTI) ? "disabled" : "enabled");
@@ -212,7 +315,7 @@ static bool __init retpoline_safe(uint64_t caps)
void __init init_speculation_mitigations(void)
{
enum ind_thunk thunk = THUNK_DEFAULT;
- bool ibrs = false;
+ bool use_spec_ctrl = false, ibrs = false;
uint64_t caps = 0;
if ( boot_cpu_has(X86_FEATURE_ARCH_CAPS) )
@@ -282,20 +385,31 @@ void __init init_speculation_mitigations(void)
else if ( thunk == THUNK_JMP )
setup_force_cpu_cap(X86_FEATURE_IND_THUNK_JMP);
+ /*
+ * If we are on hardware supporting MSR_SPEC_CTRL, see about setting up
+ * the alternatives blocks so we can virtualise support for guests.
+ */
if ( boot_cpu_has(X86_FEATURE_IBRSB) )
{
- /*
- * Even if we've chosen to not have IBRS set in Xen context, we still
- * need the IBRS entry/exit logic to virtualise IBRS support for
- * guests.
- */
- setup_force_cpu_cap(X86_FEATURE_SC_MSR_PV);
- setup_force_cpu_cap(X86_FEATURE_SC_MSR_HVM);
+ if ( opt_msr_sc_pv )
+ {
+ use_spec_ctrl = true;
+ setup_force_cpu_cap(X86_FEATURE_SC_MSR_PV);
+ }
- if ( ibrs )
- default_xen_spec_ctrl |= SPEC_CTRL_IBRS;
+ if ( opt_msr_sc_hvm )
+ {
+ use_spec_ctrl = true;
+ setup_force_cpu_cap(X86_FEATURE_SC_MSR_HVM);
+ }
+
+ if ( use_spec_ctrl )
+ {
+ if ( ibrs )
+ default_xen_spec_ctrl |= SPEC_CTRL_IBRS;
- default_spec_ctrl_flags |= SCF_ist_wrmsr;
+ default_spec_ctrl_flags |= SCF_ist_wrmsr;
+ }
}
/*
--
2.1.4

View file

@ -1,123 +0,0 @@
From 918320daf34931cd5c1c0d9c439ce853f6575970 Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Thu, 26 Apr 2018 10:56:28 +0100
Subject: [PATCH] x86/AMD: Mitigations for GPZ SP4 - Speculative Store Bypass
AMD processors will execute loads and stores with the same base register in
program order, which is typically how a compiler emits code.
Therefore, by default no mitigating actions are taken, despite there being
corner cases which are vulnerable to the issue.
For performance testing, or for users with particularly sensitive workloads,
the `spec-ctrl=ssbd` command line option is available to force Xen to disable
Memory Disambiguation on applicable hardware.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
---
docs/misc/xen-command-line.markdown | 7 ++++++-
xen/arch/x86/cpu/amd.c | 20 ++++++++++++++++++++
xen/arch/x86/spec_ctrl.c | 3 +++
xen/include/asm-x86/spec_ctrl.h | 1 +
4 files changed, 30 insertions(+), 1 deletion(-)
diff --git a/docs/misc/xen-command-line.markdown b/docs/misc/xen-command-line.markdown
index 43a6ddb..4e0e580 100644
--- a/docs/misc/xen-command-line.markdown
+++ b/docs/misc/xen-command-line.markdown
@@ -1703,7 +1703,7 @@ false disable the quirk workaround, which is also the default.
### spec-ctrl (x86)
> `= List of [ <bool>, xen=<bool>, {pv,hvm,msr-sc,rsb}=<bool>,
-> bti-thunk=retpoline|lfence|jmp, {ibrs,ibpb}=<bool> ]`
+> bti-thunk=retpoline|lfence|jmp, {ibrs,ibpb,ssbd}=<bool> ]`
Controls for speculative execution sidechannel mitigations. By default, Xen
will pick the most appropriate mitigations based on compiled in support,
@@ -1747,6 +1747,11 @@ On hardware supporting IBPB (Indirect Branch Prediction Barrier), the `ibpb=`
option can be used to force (the default) or prevent Xen from issuing branch
prediction barriers on vcpu context switches.
+On hardware supporting SSBD (Speculative Store Bypass Disable), the `ssbd=`
+option can be used to force or prevent Xen using the feature itself. On AMD
+hardware, this is a global option applied at boot, and not virtualised for
+guest use.
+
### sync\_console
> `= <boolean>`
diff --git a/xen/arch/x86/cpu/amd.c b/xen/arch/x86/cpu/amd.c
index fc9677f..458a3fe 100644
--- a/xen/arch/x86/cpu/amd.c
+++ b/xen/arch/x86/cpu/amd.c
@@ -9,6 +9,7 @@
#include <asm/amd.h>
#include <asm/hvm/support.h>
#include <asm/setup.h> /* amd_init_cpu */
+#include <asm/spec_ctrl.h>
#include <asm/acpi.h>
#include <asm/apic.h>
@@ -594,6 +595,25 @@ static void init_amd(struct cpuinfo_x86 *c)
c->x86_capability);
}
+ /*
+ * If the user has explicitly chosen to disable Memory Disambiguation
+ * to mitigiate Speculative Store Bypass, poke the appropriate MSR.
+ */
+ if (opt_ssbd) {
+ int bit = -1;
+
+ switch (c->x86) {
+ case 0x15: bit = 54; break;
+ case 0x16: bit = 33; break;
+ case 0x17: bit = 10; break;
+ }
+
+ if (bit >= 0 && !rdmsr_safe(MSR_AMD64_LS_CFG, value)) {
+ value |= 1ull << bit;
+ wrmsr_safe(MSR_AMD64_LS_CFG, value);
+ }
+ }
+
/* MFENCE stops RDTSC speculation */
if (!cpu_has_lfence_dispatch)
__set_bit(X86_FEATURE_MFENCE_RDTSC, c->x86_capability);
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index 4f9282f..e326056 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -43,6 +43,7 @@ static enum ind_thunk {
} opt_thunk __initdata = THUNK_DEFAULT;
static int8_t __initdata opt_ibrs = -1;
bool __read_mostly opt_ibpb = true;
+bool __read_mostly opt_ssbd = false;
bool __initdata bsp_delay_spec_ctrl;
uint8_t __read_mostly default_xen_spec_ctrl;
@@ -164,6 +165,8 @@ static int __init parse_spec_ctrl(const char *s)
opt_ibrs = val;
else if ( (val = parse_boolean("ibpb", s, ss)) >= 0 )
opt_ibpb = val;
+ else if ( (val = parse_boolean("ssbd", s, ss)) >= 0 )
+ opt_ssbd = val;
else
rc = -EINVAL;
diff --git a/xen/include/asm-x86/spec_ctrl.h b/xen/include/asm-x86/spec_ctrl.h
index c6a38f4..4678a40 100644
--- a/xen/include/asm-x86/spec_ctrl.h
+++ b/xen/include/asm-x86/spec_ctrl.h
@@ -27,6 +27,7 @@
void init_speculation_mitigations(void);
extern bool opt_ibpb;
+extern bool opt_ssbd;
extern bool bsp_delay_spec_ctrl;
extern uint8_t default_xen_spec_ctrl;
--
2.1.4

View file

@ -1,224 +0,0 @@
From db6adc8e55dd43a1b4bb20e06a69475c503cb934 Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Wed, 28 Mar 2018 15:21:39 +0100
Subject: [PATCH] x86/Intel: Mitigations for GPZ SP4 - Speculative Store Bypass
To combat GPZ SP4 "Speculative Store Bypass", Intel have extended their
speculative sidechannel mitigations specification as follows:
* A feature bit to indicate that Speculative Store Bypass Disable is
supported.
* A new bit in MSR_SPEC_CTRL which, when set, disables memory disambiguation
in the pipeline.
* A new bit in MSR_ARCH_CAPABILITIES, which will be set in future hardware,
indicating that the hardware is not susceptible to Speculative Store Bypass
sidechannels.
For contemporary processors, this interface will be implemented via a
microcode update.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
---
docs/misc/xen-command-line.markdown | 12 +++++++-----
tools/libxl/libxl_cpuid.c | 1 +
tools/misc/xen-cpuid.c | 3 +--
xen/arch/x86/cpuid.c | 5 +++++
xen/arch/x86/spec_ctrl.c | 15 ++++++++++++---
xen/include/asm-x86/msr-index.h | 2 ++
xen/include/public/arch-x86/cpufeatureset.h | 1 +
xen/tools/gen-cpuid.py | 17 +++++++++++++----
8 files changed, 42 insertions(+), 14 deletions(-)
diff --git a/docs/misc/xen-command-line.markdown b/docs/misc/xen-command-line.markdown
index 4e0e580..107889d 100644
--- a/docs/misc/xen-command-line.markdown
+++ b/docs/misc/xen-command-line.markdown
@@ -496,9 +496,10 @@ accounting for hardware capabilities as enumerated via CPUID.
Currently accepted:
-The Speculation Control hardware features `ibrsb`, `stibp`, `ibpb` are used by
-default if avaiable. They can be ignored, e.g. `no-ibrsb`, at which point Xen
-won't use them itself, and won't offer them to guests.
+The Speculation Control hardware features `ibrsb`, `stibp`, `ibpb`, `ssbd` are
+used by default if available and applicable. They can be ignored,
+e.g. `no-ibrsb`, at which point Xen won't use them itself, and won't offer
+them to guests.
### cpuid\_mask\_cpu (AMD only)
> `= fam_0f_rev_c | fam_0f_rev_d | fam_0f_rev_e | fam_0f_rev_f | fam_0f_rev_g | fam_10_rev_b | fam_10_rev_c | fam_11_rev_b`
@@ -1728,7 +1729,7 @@ protect itself, and Xen's ability to virtualise support for guests to use.
respectively.
* `msr-sc=` offers control over Xen's support for manipulating MSR\_SPEC\_CTRL
on entry and exit. These blocks are necessary to virtualise support for
- guests and if disabled, guests will be unable to use IBRS/STIBP/etc.
+ guests and if disabled, guests will be unable to use IBRS/STIBP/SSBD/etc.
* `rsb=` offers control over whether to overwrite the Return Stack Buffer /
Return Address Stack on entry to Xen.
@@ -1750,7 +1751,8 @@ prediction barriers on vcpu context switches.
On hardware supporting SSBD (Speculative Store Bypass Disable), the `ssbd=`
option can be used to force or prevent Xen using the feature itself. On AMD
hardware, this is a global option applied at boot, and not virtualised for
-guest use.
+guest use. On Intel hardware, the feature is virtualised for guests,
+independently of Xen's choice of setting.
### sync\_console
> `= <boolean>`
diff --git a/tools/libxl/libxl_cpuid.c b/tools/libxl/libxl_cpuid.c
index 3a21f4e..7b0f594 100644
--- a/tools/libxl/libxl_cpuid.c
+++ b/tools/libxl/libxl_cpuid.c
@@ -205,6 +205,7 @@ int libxl_cpuid_parse_config(libxl_cpuid_policy_list *cpuid, const char* str)
{"ibrsb", 0x00000007, 0, CPUID_REG_EDX, 26, 1},
{"stibp", 0x00000007, 0, CPUID_REG_EDX, 27, 1},
{"arch-caps", 0x00000007, 0, CPUID_REG_EDX, 29, 1},
+ {"ssbd", 0x00000007, 0, CPUID_REG_EDX, 31, 1},
{"lahfsahf", 0x80000001, NA, CPUID_REG_ECX, 0, 1},
{"cmplegacy", 0x80000001, NA, CPUID_REG_ECX, 1, 1},
diff --git a/tools/misc/xen-cpuid.c b/tools/misc/xen-cpuid.c
index b1a46c6..2483a81 100644
--- a/tools/misc/xen-cpuid.c
+++ b/tools/misc/xen-cpuid.c
@@ -166,8 +166,7 @@ static const char *str_7d0[32] =
[26] = "ibrsb", [27] = "stibp",
[28] = "REZ", [29] = "arch_caps",
-
- [30 ... 31] = "REZ",
+ [30] = "REZ", [31] = "ssbd",
};
static struct {
diff --git a/xen/arch/x86/cpuid.c b/xen/arch/x86/cpuid.c
index b45b145..6a710b7 100644
--- a/xen/arch/x86/cpuid.c
+++ b/xen/arch/x86/cpuid.c
@@ -43,6 +43,11 @@ static int __init parse_xen_cpuid(const char *s)
if ( !val )
setup_clear_cpu_cap(X86_FEATURE_STIBP);
}
+ else if ( (val = parse_boolean("ssbd", s, ss)) >= 0 )
+ {
+ if ( !val )
+ setup_clear_cpu_cap(X86_FEATURE_SSBD);
+ }
else
rc = -EINVAL;
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index e326056..89e3825 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -192,26 +192,31 @@ static void __init print_details(enum ind_thunk thunk, uint64_t caps)
printk("Speculative mitigation facilities:\n");
/* Hardware features which pertain to speculative mitigations. */
- printk(" Hardware features:%s%s%s%s%s%s\n",
+ printk(" Hardware features:%s%s%s%s%s%s%s%s\n",
(_7d0 & cpufeat_mask(X86_FEATURE_IBRSB)) ? " IBRS/IBPB" : "",
(_7d0 & cpufeat_mask(X86_FEATURE_STIBP)) ? " STIBP" : "",
+ (_7d0 & cpufeat_mask(X86_FEATURE_SSBD)) ? " SSBD" : "",
(e8b & cpufeat_mask(X86_FEATURE_IBPB)) ? " IBPB" : "",
(caps & ARCH_CAPABILITIES_IBRS_ALL) ? " IBRS_ALL" : "",
(caps & ARCH_CAPABILITIES_RDCL_NO) ? " RDCL_NO" : "",
- (caps & ARCH_CAPS_RSBA) ? " RSBA" : "");
+ (caps & ARCH_CAPS_RSBA) ? " RSBA" : "",
+ (caps & ARCH_CAPS_SSB_NO) ? " SSB_NO" : "");
/* Compiled-in support which pertains to BTI mitigations. */
if ( IS_ENABLED(CONFIG_INDIRECT_THUNK) )
printk(" Compiled-in support: INDIRECT_THUNK\n");
/* Settings for Xen's protection, irrespective of guests. */
- printk(" Xen settings: BTI-Thunk %s, SPEC_CTRL: %s, Other:%s\n",
+ printk(" Xen settings: BTI-Thunk %s, SPEC_CTRL: %s%s, Other:%s\n",
thunk == THUNK_NONE ? "N/A" :
thunk == THUNK_RETPOLINE ? "RETPOLINE" :
thunk == THUNK_LFENCE ? "LFENCE" :
thunk == THUNK_JMP ? "JMP" : "?",
!use_spec_ctrl ? "No" :
(default_xen_spec_ctrl & SPEC_CTRL_IBRS) ? "IBRS+" : "IBRS-",
+ !use_spec_ctrl || !boot_cpu_has(X86_FEATURE_SSBD)
+ ? "" :
+ (default_xen_spec_ctrl & SPEC_CTRL_SSBD) ? " SSBD+" : " SSBD-",
opt_ibpb ? " IBPB" : "");
/*
@@ -415,6 +420,10 @@ void __init init_speculation_mitigations(void)
}
}
+ /* If we have SSBD available, see whether we should use it. */
+ if ( boot_cpu_has(X86_FEATURE_SSBD) && use_spec_ctrl && opt_ssbd )
+ default_xen_spec_ctrl |= SPEC_CTRL_SSBD;
+
/*
* PV guests can poison the RSB to any virtual address from which
* they can execute a call instruction. This is necessarily outside
diff --git a/xen/include/asm-x86/msr-index.h b/xen/include/asm-x86/msr-index.h
index 68fae91..93d6f4e 100644
--- a/xen/include/asm-x86/msr-index.h
+++ b/xen/include/asm-x86/msr-index.h
@@ -38,6 +38,7 @@
#define MSR_SPEC_CTRL 0x00000048
#define SPEC_CTRL_IBRS (_AC(1, ULL) << 0)
#define SPEC_CTRL_STIBP (_AC(1, ULL) << 1)
+#define SPEC_CTRL_SSBD (_AC(1, ULL) << 2)
#define MSR_PRED_CMD 0x00000049
#define PRED_CMD_IBPB (_AC(1, ULL) << 0)
@@ -46,6 +47,7 @@
#define ARCH_CAPABILITIES_RDCL_NO (_AC(1, ULL) << 0)
#define ARCH_CAPABILITIES_IBRS_ALL (_AC(1, ULL) << 1)
#define ARCH_CAPS_RSBA (_AC(1, ULL) << 2)
+#define ARCH_CAPS_SSB_NO (_AC(1, ULL) << 4)
/* Intel MSRs. Some also available on other CPUs */
#define MSR_IA32_PERFCTR0 0x000000c1
diff --git a/xen/include/public/arch-x86/cpufeatureset.h b/xen/include/public/arch-x86/cpufeatureset.h
index 8da5783..7acf822 100644
--- a/xen/include/public/arch-x86/cpufeatureset.h
+++ b/xen/include/public/arch-x86/cpufeatureset.h
@@ -245,6 +245,7 @@ XEN_CPUFEATURE(AVX512_4FMAPS, 9*32+ 3) /*A AVX512 Multiply Accumulation Single
XEN_CPUFEATURE(IBRSB, 9*32+26) /*A IBRS and IBPB support (used by Intel) */
XEN_CPUFEATURE(STIBP, 9*32+27) /*A! STIBP */
XEN_CPUFEATURE(ARCH_CAPS, 9*32+29) /* IA32_ARCH_CAPABILITIES MSR */
+XEN_CPUFEATURE(SSBD, 9*32+31) /* MSR_SPEC_CTRL.SSBD available */
#endif /* XEN_CPUFEATURE */
diff --git a/xen/tools/gen-cpuid.py b/xen/tools/gen-cpuid.py
index 613b909..65526ff 100755
--- a/xen/tools/gen-cpuid.py
+++ b/xen/tools/gen-cpuid.py
@@ -257,10 +257,19 @@ def crunch_numbers(state):
AVX512BW, AVX512VL, AVX512VBMI, AVX512_4VNNIW,
AVX512_4FMAPS, AVX512_VPOPCNTDQ],
- # Single Thread Indirect Branch Predictors enumerates a new bit in the
- # MSR enumerated by Indirect Branch Restricted Speculation/Indirect
- # Branch Prediction Barrier enumeration.
- IBRSB: [STIBP],
+ # The features:
+ # * Single Thread Indirect Branch Predictors
+ # * Speculative Store Bypass Disable
+ #
+ # enumerate new bits in MSR_SPEC_CTRL, which is enumerated by Indirect
+ # Branch Restricted Speculation/Indirect Branch Prediction Barrier.
+ #
+ # In practice, these features also enumerate the presense of
+ # MSR_SPEC_CTRL. However, no real hardware will exist with SSBD but
+ # not IBRSB, and we pass this MSR directly to guests. Treating them
+ # as dependent features simplifies Xen's logic, and prevents the guest
+ # from seeing implausible configurations.
+ IBRSB: [STIBP, SSBD],
}
deep_features = tuple(sorted(deps.keys()))
--
2.1.4

View file

@ -1,70 +0,0 @@
From 02d0027a89dc49875a41e939498936874a32360f Mon Sep 17 00:00:00 2001
From: Andrew Cooper <andrew.cooper3@citrix.com>
Date: Fri, 13 Apr 2018 15:42:34 +0000
Subject: [PATCH] x86/msr: Virtualise MSR_SPEC_CTRL.SSBD for guests to use
Almost all infrastructure is already in place. Update the reserved bits
calculation in guest_wrmsr(), and offer SSBD to guests by default.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
---
xen/arch/x86/msr.c | 8 ++++++--
xen/include/public/arch-x86/cpufeatureset.h | 2 +-
2 files changed, 7 insertions(+), 3 deletions(-)
diff --git a/xen/arch/x86/msr.c b/xen/arch/x86/msr.c
index 48d061d..21219c4 100644
--- a/xen/arch/x86/msr.c
+++ b/xen/arch/x86/msr.c
@@ -178,6 +178,8 @@ int guest_wrmsr(struct vcpu *v, uint32_t msr, uint64_t val)
switch ( msr )
{
+ uint64_t rsvd;
+
case MSR_INTEL_PLATFORM_INFO:
case MSR_ARCH_CAPABILITIES:
/* Read-only */
@@ -213,8 +215,10 @@ int guest_wrmsr(struct vcpu *v, uint32_t msr, uint64_t val)
* Note: SPEC_CTRL_STIBP is specified as safe to use (i.e. ignored)
* when STIBP isn't enumerated in hardware.
*/
+ rsvd = ~(SPEC_CTRL_IBRS | SPEC_CTRL_STIBP |
+ (cp->feat.ssbd ? SPEC_CTRL_SSBD : 0));
- if ( val & ~(SPEC_CTRL_IBRS | SPEC_CTRL_STIBP) )
+ if ( val & rsvd )
goto gp_fault; /* Rsvd bit set? */
vp->spec_ctrl.raw = val;
@@ -233,12 +237,12 @@ int guest_wrmsr(struct vcpu *v, uint32_t msr, uint64_t val)
case MSR_INTEL_MISC_FEATURES_ENABLES:
{
- uint64_t rsvd = ~0ull;
bool old_cpuid_faulting = vp->misc_features_enables.cpuid_faulting;
if ( !vp->misc_features_enables.available )
goto gp_fault;
+ rsvd = ~0ull;
if ( dp->plaform_info.cpuid_faulting )
rsvd &= ~MSR_MISC_FEATURES_CPUID_FAULTING;
diff --git a/xen/include/public/arch-x86/cpufeatureset.h b/xen/include/public/arch-x86/cpufeatureset.h
index 7acf822..c721c12 100644
--- a/xen/include/public/arch-x86/cpufeatureset.h
+++ b/xen/include/public/arch-x86/cpufeatureset.h
@@ -245,7 +245,7 @@ XEN_CPUFEATURE(AVX512_4FMAPS, 9*32+ 3) /*A AVX512 Multiply Accumulation Single
XEN_CPUFEATURE(IBRSB, 9*32+26) /*A IBRS and IBPB support (used by Intel) */
XEN_CPUFEATURE(STIBP, 9*32+27) /*A! STIBP */
XEN_CPUFEATURE(ARCH_CAPS, 9*32+29) /* IA32_ARCH_CAPABILITIES MSR */
-XEN_CPUFEATURE(SSBD, 9*32+31) /* MSR_SPEC_CTRL.SSBD available */
+XEN_CPUFEATURE(SSBD, 9*32+31) /*A MSR_SPEC_CTRL.SSBD available */
#endif /* XEN_CPUFEATURE */
--
2.1.4

View file

@ -1,52 +0,0 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: x86/mm: don't bypass preemption checks
While unlikely, it is not impossible for a multi-vCPU guest to leverage
bypasses of preemption checks to drive Xen into an unbounded loop.
This is XSA-264.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Andrew Cooper <andrew.cooper3@citrix.com>
--- a/xen/arch/x86/mm.c
+++ b/xen/arch/x86/mm.c
@@ -2526,7 +2526,7 @@ static int _put_page_type(struct page_in
nx = x & ~(PGT_validated|PGT_partial);
if ( unlikely((y = cmpxchg(&page->u.inuse.type_info,
x, nx)) != x) )
- continue;
+ goto maybe_preempt;
/* We cleared the 'valid bit' so we do the clean up. */
rc = _put_final_page_type(page, x, preemptible, ptpg);
ptpg = NULL;
@@ -2558,12 +2558,13 @@ static int _put_page_type(struct page_in
*/
cpu_relax();
y = page->u.inuse.type_info;
- continue;
+ goto maybe_preempt;
}
if ( likely((y = cmpxchg(&page->u.inuse.type_info, x, nx)) == x) )
break;
+ maybe_preempt:
if ( preemptible && hypercall_preempt_check() )
return -EINTR;
}
@@ -2676,12 +2677,11 @@ static int __get_page_type(struct page_i
if ( !(x & PGT_partial) )
{
/* Someone else is updating validation of this page. Wait... */
- while ( (y = page->u.inuse.type_info) == x )
- {
+ do {
if ( preemptible && hypercall_preempt_check() )
return -EINTR;
cpu_relax();
- }
+ } while ( (y = page->u.inuse.type_info) == x );
continue;
}
/* Type ref count was left at 1 when PGT_partial got set. */

View file

@ -1,104 +0,0 @@
From: Andrew Cooper <andrew.cooper3@citrix.com>
Subject: x86: Refine checks in #DB handler for faulting conditions
One of the fix for XSA-260 (c/s 75d6828bc2 "x86/traps: Fix handling of #DB
exceptions in hypervisor context") added some safety checks to help avoid
livelocks of #DB faults.
While a General Detect #DB exception does have fault semantics, hardware
clears %dr7.gd on entry to the handler, meaning that it is actually safe to
return to. Furthermore, %dr6.gd is guest controlled and sticky (never cleared
by hardware). A malicious PV guest can therefore trigger the fatal_trap() and
crash Xen.
Instruction breakpoints are more tricky. The breakpoint match bits in %dr6
are not sticky, but the Intel manual warns that they may be set for
non-enabled breakpoints, so add a breakpoint enabled check.
Beyond that, because of the restriction on the linear addresses PV guests can
set, and the fault (rather than trap) nature of instruction breakpoints
(i.e. can't be deferred by a MovSS shadow), there should be no way to
encounter an instruction breakpoint in Xen context. However, for extra
robustness, deal with this situation by clearing the breakpoint configuration,
rather than crashing.
This is XSA-265
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
diff --git a/xen/arch/x86/traps.c b/xen/arch/x86/traps.c
index e79ca88..3e05cf1 100644
--- a/xen/arch/x86/traps.c
+++ b/xen/arch/x86/traps.c
@@ -1809,6 +1809,13 @@ void do_debug(struct cpu_user_regs *regs)
if ( !guest_mode(regs) )
{
+ /*
+ * !!! WARNING !!!
+ *
+ * %dr6 is mostly guest controlled at this point. Any decsions base
+ * on its value must be crosschecked with non-guest controlled state.
+ */
+
if ( regs->eflags & X86_EFLAGS_TF )
{
/* In SYSENTER entry path we can't zap TF until EFLAGS is saved. */
@@ -1830,33 +1837,44 @@ void do_debug(struct cpu_user_regs *regs)
* Check for fault conditions. General Detect, and instruction
* breakpoints are faults rather than traps, at which point attempting
* to ignore and continue will result in a livelock.
+ *
+ * However, on entering the #DB handler, hardware clears %dr7.gd for
+ * us (as confirmed by the earlier %dr6 accesses succeeding), meaning
+ * that a real General Detect exception is restartable.
+ *
+ * PV guests are not permitted to point %dr{0..3} at Xen linear
+ * addresses, and Instruction Breakpoints (being faults) don't get
+ * delayed by a MovSS shadow, so we should never encounter one in
+ * hypervisor context.
+ *
+ * If however we do, safety measures need to be enacted. Use a big
+ * hammer and clear all debug settings.
*/
- if ( dr6 & DR_GENERAL_DETECT )
- {
- printk(XENLOG_ERR "Hit General Detect in Xen context\n");
- fatal_trap(regs, 0);
- }
-
if ( dr6 & (DR_TRAP3 | DR_TRAP2 | DR_TRAP1 | DR_TRAP0) )
{
- unsigned int bp, dr7 = read_debugreg(7) >> DR_CONTROL_SHIFT;
+ unsigned int bp, dr7 = read_debugreg(7);
for ( bp = 0; bp < 4; ++bp )
{
if ( (dr6 & (1u << bp)) && /* Breakpoint triggered? */
- ((dr7 & (3u << (bp * DR_CONTROL_SIZE))) == 0) /* Insn? */ )
+ (dr7 & (3u << (bp * DR_ENABLE_SIZE))) && /* Enabled? */
+ ((dr7 & (3u << ((bp * DR_CONTROL_SIZE) + /* Insn? */
+ DR_CONTROL_SHIFT))) == DR_RW_EXECUTE) )
{
+ ASSERT_UNREACHABLE();
+
printk(XENLOG_ERR
"Hit instruction breakpoint in Xen context\n");
- fatal_trap(regs, 0);
+ write_debugreg(7, 0);
+ break;
}
}
}
/*
- * Whatever caused this #DB should be a trap. Note it and continue.
- * Guests can trigger this in certain corner cases, so ensure the
- * message is ratelimited.
+ * Whatever caused this #DB should be restartable by this point. Note
+ * it and continue. Guests can trigger this in certain corner cases,
+ * so ensure the message is ratelimited.
*/
gprintk(XENLOG_WARNING,
"Hit #DB in Xen context: %04x:%p [%ps], stk %04x:%p, dr6 %lx\n",

View file

@ -1,78 +0,0 @@
From 82f98f8484f47163a06e4d5610dba6e5fc459e78 Mon Sep 17 00:00:00 2001
From: Ian Jackson <ian.jackson@eu.citrix.com>
Date: Wed, 13 Jun 2018 15:51:36 +0100
Subject: [PATCH 1/2] libxl: qemu_disk_scsi_drive_string: Break out common
parts of disk config
The generated configurations are identical apart from, in some cases,
reordering of the id=%s element. So, overall, no functional change.
This is part of XSA-266.
Reported-by: Andrew Reimers <andrew.reimers@orionvm.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Signed-off-by: Ian Jackson <Ian.Jackson@eu.citrix.com>
---
tools/libxl/libxl_dm.c | 13 +++++++------
1 file changed, 7 insertions(+), 6 deletions(-)
diff --git a/tools/libxl/libxl_dm.c b/tools/libxl/libxl_dm.c
index b51178b..28bbeb6 100644
--- a/tools/libxl/libxl_dm.c
+++ b/tools/libxl/libxl_dm.c
@@ -798,6 +798,7 @@ static char *qemu_disk_scsi_drive_string(libxl__gc *gc, const char *target_path,
int colo_mode)
{
char *drive = NULL;
+ char *common = GCSPRINTF("cache=writeback");
const char *exportname = disk->colo_export;
const char *active_disk = disk->active_disk;
const char *hidden_disk = disk->hidden_disk;
@@ -805,8 +806,8 @@ static char *qemu_disk_scsi_drive_string(libxl__gc *gc, const char *target_path,
switch (colo_mode) {
case LIBXL__COLO_NONE:
drive = libxl__sprintf
- (gc, "file=%s,if=scsi,bus=0,unit=%d,format=%s,cache=writeback",
- target_path, unit, format);
+ (gc, "%s,file=%s,if=scsi,bus=0,unit=%d,format=%s",
+ common, target_path, unit, format);
break;
case LIBXL__COLO_PRIMARY:
/*
@@ -819,13 +820,13 @@ static char *qemu_disk_scsi_drive_string(libxl__gc *gc, const char *target_path,
* vote-threshold=1
*/
drive = GCSPRINTF(
- "if=scsi,bus=0,unit=%d,cache=writeback,driver=quorum,"
+ "%s,if=scsi,bus=0,unit=%d,,driver=quorum,"
"id=%s,"
"children.0.file.filename=%s,"
"children.0.driver=%s,"
"read-pattern=fifo,"
"vote-threshold=1",
- unit, exportname, target_path, format);
+ common, unit, exportname, target_path, format);
break;
case LIBXL__COLO_SECONDARY:
/*
@@ -839,7 +840,7 @@ static char *qemu_disk_scsi_drive_string(libxl__gc *gc, const char *target_path,
* file.backing.backing=exportname,
*/
drive = GCSPRINTF(
- "if=scsi,id=top-colo,bus=0,unit=%d,cache=writeback,"
+ "%s,if=scsi,id=top-colo,bus=0,unit=%d,"
"driver=replication,"
"mode=secondary,"
"top-id=top-colo,"
@@ -848,7 +849,7 @@ static char *qemu_disk_scsi_drive_string(libxl__gc *gc, const char *target_path,
"file.backing.driver=qcow2,"
"file.backing.file.filename=%s,"
"file.backing.backing=%s",
- unit, active_disk, hidden_disk, exportname);
+ common, unit, active_disk, hidden_disk, exportname);
break;
default:
abort();
--
2.1.4

View file

@ -1,63 +0,0 @@
From ba3f1fa1ab6e83745682cac784e680a1abf7da7d Mon Sep 17 00:00:00 2001
From: Ian Jackson <ian.jackson@eu.citrix.com>
Date: Wed, 13 Jun 2018 15:54:53 +0100
Subject: [PATCH 2/2] libxl: restore passing "readonly=" to qemu for SCSI disks
A read-only check was introduced for XSA-142, commit ef6cb76026 ("libxl:
relax readonly check introduced by XSA-142 fix") added the passing of
the extra setting, but commit dab0539568 ("Introduce COLO mode and
refactor relevant function") dropped the passing of the setting again,
quite likely due to improper re-basing.
Restore the readonly= parameter to SCSI disks. For IDE disks this is
supposed to be rejected; add an assert. And there is a bare ad-hoc
disk drive string in libxl__build_device_model_args_new, which we also
update.
This is XSA-266.
Reported-by: Andrew Reimers <andrew.reimers@orionvm.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Signed-off-by: Ian Jackson <Ian.Jackson@eu.citrix.com>
---
tools/libxl/libxl_dm.c | 10 +++++++---
1 file changed, 7 insertions(+), 3 deletions(-)
diff --git a/tools/libxl/libxl_dm.c b/tools/libxl/libxl_dm.c
index 28bbeb6..3dc317a 100644
--- a/tools/libxl/libxl_dm.c
+++ b/tools/libxl/libxl_dm.c
@@ -798,7 +798,8 @@ static char *qemu_disk_scsi_drive_string(libxl__gc *gc, const char *target_path,
int colo_mode)
{
char *drive = NULL;
- char *common = GCSPRINTF("cache=writeback");
+ char *common = GCSPRINTF("cache=writeback,readonly=%s",
+ disk->readwrite ? "off" : "on");
const char *exportname = disk->colo_export;
const char *active_disk = disk->active_disk;
const char *hidden_disk = disk->hidden_disk;
@@ -867,6 +868,8 @@ static char *qemu_disk_ide_drive_string(libxl__gc *gc, const char *target_path,
const char *exportname = disk->colo_export;
const char *active_disk = disk->active_disk;
const char *hidden_disk = disk->hidden_disk;
+
+ assert(disk->readwrite); /* should have been checked earlier */
switch (colo_mode) {
case LIBXL__COLO_NONE:
@@ -1576,8 +1579,9 @@ static int libxl__build_device_model_args_new(libxl__gc *gc,
if (strncmp(disks[i].vdev, "sd", 2) == 0) {
if (colo_mode == LIBXL__COLO_SECONDARY) {
drive = libxl__sprintf
- (gc, "if=none,driver=%s,file=%s,id=%s",
- format, target_path, disks[i].colo_export);
+ (gc, "if=none,driver=%s,file=%s,id=%s,readonly=%s",
+ format, target_path, disks[i].colo_export,
+ disks[i].readwrite ? "off" : "on");
flexarray_append(dm_args, "-drive");
flexarray_append(dm_args, drive);
--
2.1.4

View file

@ -1,68 +0,0 @@
From: Andrew Cooper <andrew.cooper3@citrix.com>
Subject: x86: Support fully eager FPU context switching
This is controlled on a per-vcpu bases for flexibility.
This is part of XSA-267 / CVE-2018-3665
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
diff --git a/xen/arch/x86/i387.c b/xen/arch/x86/i387.c
index 8845252..50116d5 100644
--- a/xen/arch/x86/i387.c
+++ b/xen/arch/x86/i387.c
@@ -210,7 +210,7 @@ void vcpu_restore_fpu_eager(struct vcpu *v)
ASSERT(!is_idle_vcpu(v));
/* Restore nonlazy extended state (i.e. parts not tracked by CR0.TS). */
- if ( !v->arch.nonlazy_xstate_used )
+ if ( !v->arch.fully_eager_fpu && !v->arch.nonlazy_xstate_used )
return;
/* Avoid recursion */
@@ -221,11 +221,19 @@ void vcpu_restore_fpu_eager(struct vcpu *v)
* above) we also need to restore full state, to prevent subsequently
* saving state belonging to another vCPU.
*/
- if ( xstate_all(v) )
+ if ( v->arch.fully_eager_fpu || (v->arch.xsave_area && xstate_all(v)) )
{
- fpu_xrstor(v, XSTATE_ALL);
+ if ( cpu_has_xsave )
+ fpu_xrstor(v, XSTATE_ALL);
+ else
+ fpu_fxrstor(v);
+
v->fpu_initialised = 1;
v->fpu_dirtied = 1;
+
+ /* Xen doesn't need TS set, but the guest might. */
+ if ( is_pv_vcpu(v) && (v->arch.pv_vcpu.ctrlreg[0] & X86_CR0_TS) )
+ stts();
}
else
{
@@ -247,6 +255,8 @@ void vcpu_restore_fpu_lazy(struct vcpu *v)
if ( v->fpu_dirtied )
return;
+ ASSERT(!v->arch.fully_eager_fpu);
+
if ( cpu_has_xsave )
fpu_xrstor(v, XSTATE_LAZY);
else
diff --git a/xen/include/asm-x86/domain.h b/xen/include/asm-x86/domain.h
index 2ba21e1..7759332 100644
--- a/xen/include/asm-x86/domain.h
+++ b/xen/include/asm-x86/domain.h
@@ -569,6 +569,9 @@ struct arch_vcpu
* and thus should be saved/restored. */
bool_t nonlazy_xstate_used;
+ /* Restore all FPU state (lazy and non-lazy state) on context switch? */
+ bool fully_eager_fpu;
+
/*
* The SMAP check policy when updating runstate_guest(v) and the
* secondary system time.

View file

@ -1,220 +0,0 @@
From: Andrew Cooper <andrew.cooper3@citrix.com>
Subject: x86/spec-ctrl: Mitigations for LazyFPU
Intel Core processors since at least Nehalem speculate past #NM, which is the
mechanism by which lazy FPU context switching is implemented.
On affected processors, Xen must use fully eager FPU context switching to
prevent guests from being able to read FPU state (SSE/AVX/etc) from previously
scheduled vcpus.
This is part of XSA-267 / CVE-2018-3665
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
diff --git a/docs/misc/xen-command-line.markdown b/docs/misc/xen-command-line.markdown
index 5c13f6f..cb81a9c 100644
--- a/docs/misc/xen-command-line.markdown
+++ b/docs/misc/xen-command-line.markdown
@@ -1727,7 +1727,7 @@ false disable the quirk workaround, which is also the default.
### spec-ctrl (x86)
> `= List of [ <bool>, xen=<bool>, {pv,hvm,msr-sc,rsb}=<bool>,
-> bti-thunk=retpoline|lfence|jmp, {ibrs,ibpb,ssbd}=<bool> ]`
+> bti-thunk=retpoline|lfence|jmp, {ibrs,ibpb,ssbd,eager-fpu}=<bool> ]`
Controls for speculative execution sidechannel mitigations. By default, Xen
will pick the most appropriate mitigations based on compiled in support,
@@ -1777,6 +1777,11 @@ hardware, this is a global option applied at boot, and not virtualised for
guest use. On Intel hardware, the feature is virtualised for guests,
independently of Xen's choice of setting.
+On all hardware, the `eager-fpu=` option can be used to force or prevent Xen
+from using fully eager FPU context switches. This is currently implemented as
+a global control. By default, Xen will choose to use fully eager context
+switches on hardware believed to speculate past #NM exceptions.
+
### sync\_console
> `= <boolean>`
diff --git a/xen/arch/x86/i387.c b/xen/arch/x86/i387.c
index 50116d5..dbdf1b4 100644
--- a/xen/arch/x86/i387.c
+++ b/xen/arch/x86/i387.c
@@ -15,6 +15,7 @@
#include <asm/i387.h>
#include <asm/xstate.h>
#include <asm/asm_defns.h>
+#include <asm/spec_ctrl.h>
/*******************************/
/* FPU Restore Functions */
@@ -307,6 +308,8 @@ int vcpu_init_fpu(struct vcpu *v)
{
int rc;
+ v->arch.fully_eager_fpu = opt_eager_fpu;
+
if ( (rc = xstate_alloc_save_area(v)) != 0 )
return rc;
diff --git a/xen/arch/x86/spec_ctrl.c b/xen/arch/x86/spec_ctrl.c
index b5a7f9c..cf255ac 100644
--- a/xen/arch/x86/spec_ctrl.c
+++ b/xen/arch/x86/spec_ctrl.c
@@ -44,6 +44,7 @@ static enum ind_thunk {
static int8_t __initdata opt_ibrs = -1;
bool __read_mostly opt_ibpb = true;
bool __read_mostly opt_ssbd = false;
+int8_t __read_mostly opt_eager_fpu = -1;
bool __initdata bsp_delay_spec_ctrl;
uint8_t __read_mostly default_xen_spec_ctrl;
@@ -114,6 +115,7 @@ static int __init parse_spec_ctrl(const char *s)
opt_thunk = THUNK_JMP;
opt_ibrs = 0;
opt_ibpb = false;
+ opt_eager_fpu = 0;
}
else if ( val > 0 )
rc = -EINVAL;
@@ -167,6 +169,8 @@ static int __init parse_spec_ctrl(const char *s)
opt_ibpb = val;
else if ( (val = parse_boolean("ssbd", s, ss)) >= 0 )
opt_ssbd = val;
+ else if ( (val = parse_boolean("eager-fpu", s, ss)) >= 0 )
+ opt_eager_fpu = val;
else
rc = -EINVAL;
@@ -223,15 +227,19 @@ static void __init print_details(enum ind_thunk thunk, uint64_t caps)
* Alternatives blocks for protecting against and/or virtualising
* mitigation support for guests.
*/
- printk(" Support for VMs: PV:%s%s%s, HVM:%s%s%s\n",
+ printk(" Support for VMs: PV:%s%s%s%s, HVM:%s%s%s%s\n",
(boot_cpu_has(X86_FEATURE_SC_MSR_PV) ||
- boot_cpu_has(X86_FEATURE_SC_RSB_PV)) ? "" : " None",
+ boot_cpu_has(X86_FEATURE_SC_RSB_PV) ||
+ opt_eager_fpu) ? "" : " None",
boot_cpu_has(X86_FEATURE_SC_MSR_PV) ? " MSR_SPEC_CTRL" : "",
boot_cpu_has(X86_FEATURE_SC_RSB_PV) ? " RSB" : "",
+ opt_eager_fpu ? " EAGER_FPU" : "",
(boot_cpu_has(X86_FEATURE_SC_MSR_HVM) ||
- boot_cpu_has(X86_FEATURE_SC_RSB_HVM)) ? "" : " None",
+ boot_cpu_has(X86_FEATURE_SC_RSB_HVM) ||
+ opt_eager_fpu) ? "" : " None",
boot_cpu_has(X86_FEATURE_SC_MSR_HVM) ? " MSR_SPEC_CTRL" : "",
- boot_cpu_has(X86_FEATURE_SC_RSB_HVM) ? " RSB" : "");
+ boot_cpu_has(X86_FEATURE_SC_RSB_HVM) ? " RSB" : "",
+ opt_eager_fpu ? " EAGER_FPU" : "");
printk("XPTI: %s\n",
boot_cpu_has(X86_FEATURE_NO_XPTI) ? "disabled" : "enabled");
@@ -321,6 +329,82 @@ static bool __init retpoline_safe(uint64_t caps)
}
}
+/* Calculate whether this CPU speculates past #NM */
+static bool __init should_use_eager_fpu(void)
+{
+ /*
+ * Assume all unrecognised processors are ok. This is only known to
+ * affect Intel Family 6 processors.
+ */
+ if ( boot_cpu_data.x86_vendor != X86_VENDOR_INTEL ||
+ boot_cpu_data.x86 != 6 )
+ return false;
+
+ switch ( boot_cpu_data.x86_model )
+ {
+ /*
+ * Core processors since at least Nehalem are vulnerable.
+ */
+ case 0x1e: /* Nehalem */
+ case 0x1f: /* Auburndale / Havendale */
+ case 0x1a: /* Nehalem EP */
+ case 0x2e: /* Nehalem EX */
+ case 0x25: /* Westmere */
+ case 0x2c: /* Westmere EP */
+ case 0x2f: /* Westmere EX */
+ case 0x2a: /* SandyBridge */
+ case 0x2d: /* SandyBridge EP/EX */
+ case 0x3a: /* IvyBridge */
+ case 0x3e: /* IvyBridge EP/EX */
+ case 0x3c: /* Haswell */
+ case 0x3f: /* Haswell EX/EP */
+ case 0x45: /* Haswell D */
+ case 0x46: /* Haswell H */
+ case 0x3d: /* Broadwell */
+ case 0x47: /* Broadwell H */
+ case 0x4f: /* Broadwell EP/EX */
+ case 0x56: /* Broadwell D */
+ case 0x4e: /* Skylake M */
+ case 0x55: /* Skylake X */
+ case 0x5e: /* Skylake D */
+ case 0x66: /* Cannonlake */
+ case 0x67: /* Cannonlake? */
+ case 0x8e: /* Kabylake M */
+ case 0x9e: /* Kabylake D */
+ return true;
+
+ /*
+ * Atom processors are not vulnerable.
+ */
+ case 0x1c: /* Pineview */
+ case 0x26: /* Lincroft */
+ case 0x27: /* Penwell */
+ case 0x35: /* Cloverview */
+ case 0x36: /* Cedarview */
+ case 0x37: /* Baytrail / Valleyview (Silvermont) */
+ case 0x4d: /* Avaton / Rangely (Silvermont) */
+ case 0x4c: /* Cherrytrail / Brasswell */
+ case 0x4a: /* Merrifield */
+ case 0x5a: /* Moorefield */
+ case 0x5c: /* Goldmont */
+ case 0x5f: /* Denverton */
+ case 0x7a: /* Gemini Lake */
+ return false;
+
+ /*
+ * Knights processors are not vulnerable.
+ */
+ case 0x57: /* Knights Landing */
+ case 0x85: /* Knights Mill */
+ return false;
+
+ default:
+ printk("Unrecognised CPU model %#x - assuming vulnerable to LazyFPU\n",
+ boot_cpu_data.x86_model);
+ return true;
+ }
+}
+
void __init init_speculation_mitigations(void)
{
enum ind_thunk thunk = THUNK_DEFAULT;
@@ -519,6 +603,10 @@ void __init init_speculation_mitigations(void)
if ( !boot_cpu_has(X86_FEATURE_IBRSB) && !boot_cpu_has(X86_FEATURE_IBPB) )
opt_ibpb = false;
+ /* Check whether Eager FPU should be enabled by default. */
+ if ( opt_eager_fpu == -1 )
+ opt_eager_fpu = should_use_eager_fpu();
+
/* (Re)init BSP state now that default_spec_ctrl_flags has been calculated. */
init_shadow_spec_ctrl_state();
diff --git a/xen/include/asm-x86/spec_ctrl.h b/xen/include/asm-x86/spec_ctrl.h
index 91bed1b..5b40afb 100644
--- a/xen/include/asm-x86/spec_ctrl.h
+++ b/xen/include/asm-x86/spec_ctrl.h
@@ -28,6 +28,7 @@ void init_speculation_mitigations(void);
extern bool opt_ibpb;
extern bool opt_ssbd;
+extern int8_t opt_eager_fpu;
extern bool bsp_delay_spec_ctrl;
extern uint8_t default_xen_spec_ctrl;

30
xsa483.patch Normal file
View file

@ -0,0 +1,30 @@
From: Andrii Sultanov <andriy.sultanov@vates.tech>
Subject: tools/oxenstored: Reset quota when resetting permissions
The quota object contains both limits and the current node usage counts.
When a domain is torn down, the node data itself is cleaned up but the node
usage counts are not. A later domain reusing the same domid can create fewer
nodes before being deemed to be over quota.
Reset the count when the node permissions are cleaned up.
This is XSA-483 / CVE-2026-23556.
Signed-off-by: Andrii Sultanov <andriy.sultanov@vates.tech>
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
diff --git a/tools/ocaml/xenstored/store.ml b/tools/ocaml/xenstored/store.ml
index 9b8dd2812df0..aa9204ead3ec 100644
--- a/tools/ocaml/xenstored/store.ml
+++ b/tools/ocaml/xenstored/store.ml
@@ -465,7 +465,8 @@ let reset_permissions store domid =
if perms <> node.perms then
Logging.debug "store|node" "Changed permissions for node %s" (Node.get_name node);
Some { node with Node.perms }
- ) store.root
+ ) store.root;
+ store.quota <- Quota.del store.quota domid
type ops = {
store: t;

89
xsa484.patch Normal file
View file

@ -0,0 +1,89 @@
From 3d0d19ad17f29c64dde4a7baf392da4fd58f3654 Mon Sep 17 00:00:00 2001
From: Juergen Gross <jgross@suse.com>
Date: Mon, 16 Mar 2026 15:06:11 +0100
Subject: [PATCH] tools/xenstored: make conn_delete_all_transactions()
idempotent
conn_delete_all_transactions() should be callable in any context,
resetting ALL transaction related data.
This includes number of active transactions and the transaction
pointer in struct connection.
So reset conn->trans to NULL in conn_delete_all_transactions() and
do the cleanup for each transaction in destroy_transaction().
This avoids triggering the assert() in conn_delete_all_transactions()
in case e.g. ignore_connection() was called while an operation inside
a transaction was performed, or XS_RESET_WATCHES was called in a
transaction.
This is XSA-484 / CVE-2026-23557.
Reported-by: Andrii Sultanov <andriy.sultanov@vates.tech>
Fixes: 1f9d04fb021c ("xenstored: allow guest to shutdown all its watches/transactions")
Signed-off-by: Juergen Gross <jgross@suse.com>
---
tools/xenstored/transaction.c | 20 +++++++++-----------
1 file changed, 9 insertions(+), 11 deletions(-)
diff --git a/tools/xenstored/transaction.c b/tools/xenstored/transaction.c
index 167cd597fd..0825c48859 100644
--- a/tools/xenstored/transaction.c
+++ b/tools/xenstored/transaction.c
@@ -432,17 +432,23 @@ static int finalize_transaction(struct connection *conn,
static int destroy_transaction(void *_transaction)
{
struct transaction *trans = _transaction;
+ struct connection *conn = trans->conn;
struct accessed_node *i;
wrl_ntransactions--;
trace_destroy(trans, "transaction");
while ((i = list_top(&trans->accessed, struct accessed_node, list))) {
if (i->ta_node)
- db_delete(trans->conn, i->trans_name, NULL);
+ db_delete(conn, i->trans_name, NULL);
list_del(&i->list);
talloc_free(i);
}
+ list_del(&trans->list);
+ domain_transaction_dec(conn);
+ if (list_empty(&conn->transaction_list))
+ conn->ta_start_time = 0;
+
return 0;
}
@@ -523,10 +529,6 @@ int do_transaction_end(const void *ctx, struct connection *conn,
return ENOENT;
conn->transaction = NULL;
- list_del(&trans->list);
- domain_transaction_dec(conn);
- if (list_empty(&conn->transaction_list))
- conn->ta_start_time = 0;
chk_quota = trans->node_created && domain_is_unprivileged(conn);
@@ -572,14 +574,10 @@ void conn_delete_all_transactions(struct connection *conn)
struct transaction *trans;
while ((trans = list_top(&conn->transaction_list,
- struct transaction, list))) {
- list_del(&trans->list);
+ struct transaction, list)))
talloc_free(trans);
- }
-
- assert(conn->transaction == NULL);
- conn->ta_start_time = 0;
+ conn->transaction = NULL;
}
int check_transactions(struct hashtable *hash)
--
2.53.0

181
xsa486.patch Normal file
View file

@ -0,0 +1,181 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: gnttab: split gnttab_map_frame()
If a domain tries to map status frames in parallel to switching grant
table version from 2 to 1, the mapping operation may put in place P2M
entries referencing MFNs which gnttab_unpopulate_status_frames() is in the
process of freeing.
Ideally we would refcount pages when entered into P2M tables, but that's a
significant change. Extend the grant-table-locked region instead in
xenmem_add_to_physmap_one() (being the sole caller of gnttab_map_frame()),
such that a race with gnttab_unpopulate_status_frames() is no longer
possible.
This is XSA-486 / CVE-2026-23558.
Fixes: 5ce8fafa947c ("Dynamic grant-table sizing")
Fixes: a98dc13703e0 ("Introduce a grant_entry_v2 structure")
Reported-by: Rafal Wojtczuk <rafal.wojtczuk@7bulls.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
--- a/xen/arch/arm/mm.c
+++ b/xen/arch/arm/mm.c
@@ -174,12 +174,10 @@ int xenmem_add_to_physmap_one(
switch ( space )
{
case XENMAPSPACE_grant_table:
- rc = gnttab_map_frame(d, idx, gfn, &mfn);
+ rc = gnttab_map_frame_begin(d, idx, gfn, &mfn);
if ( rc )
return rc;
- /* Need to take care of the reference obtained in gnttab_map_frame(). */
- page = mfn_to_page(mfn);
t = p2m_ram_rw;
break;
@@ -281,10 +279,23 @@ int xenmem_add_to_physmap_one(
* to drop the reference we took earlier. In all other cases we need to
* drop any reference we took earlier (perhaps indirectly).
*/
- if ( space == XENMAPSPACE_gmfn_foreign ? rc : page != NULL )
+ switch ( space )
{
+ default:
+ if ( page )
+ put_page(page);
+ break;
+
+ case XENMAPSPACE_grant_table:
+ gnttab_map_frame_end(d, mfn);
+ break;
+
+ case XENMAPSPACE_gmfn_foreign:
+ if ( !rc )
+ break;
ASSERT(page != NULL);
put_page(page);
+ break;
}
return rc;
--- a/xen/arch/x86/mm/p2m.c
+++ b/xen/arch/x86/mm/p2m.c
@@ -2009,11 +2009,9 @@ int xenmem_add_to_physmap_one(
break;
case XENMAPSPACE_grant_table:
- rc = gnttab_map_frame(d, idx, gfn, &mfn);
+ rc = gnttab_map_frame_begin(d, idx, gfn, &mfn);
if ( rc )
return rc;
- /* Need to take care of the reference obtained in gnttab_map_frame(). */
- page = mfn_to_page(mfn);
break;
case XENMAPSPACE_gmfn:
@@ -2095,19 +2093,28 @@ int xenmem_add_to_physmap_one(
put_gfn(d, gfn_x(gfn));
put_both:
- /*
- * In the XENMAPSPACE_gmfn case, we took a ref of the gfn at the top.
- * We also may need to transfer ownership of the page reference to our
- * caller.
- */
- if ( space == XENMAPSPACE_gmfn )
+ switch ( space )
{
+ case XENMAPSPACE_gmfn:
+ /*
+ * We took a ref of the gfn at the top. We also may need to transfer
+ * ownership of the page reference to our caller.
+ */
put_gfn(d, gmfn);
if ( !rc && extra.ppage )
{
*extra.ppage = page;
page = NULL;
}
+ break;
+
+ case XENMAPSPACE_grant_table:
+ /*
+ * We (gnttab_map_frame_begin()) acquired a lock and took a ref of the
+ * page underlying the MFN at the top.
+ */
+ gnttab_map_frame_end(d, mfn);
+ break;
}
if ( page )
--- a/xen/common/grant_table.c
+++ b/xen/common/grant_table.c
@@ -4250,7 +4250,8 @@ int gnttab_acquire_resource(
return rc;
}
-int gnttab_map_frame(struct domain *d, unsigned long idx, gfn_t gfn, mfn_t *mfn)
+int gnttab_map_frame_begin(
+ struct domain *d, unsigned long idx, gfn_t gfn, mfn_t *mfn)
{
int rc = 0;
struct grant_table *gt = d->grant_table;
@@ -4288,11 +4289,19 @@ int gnttab_map_frame(struct domain *d, u
put_page(pg);
}
- grant_write_unlock(gt);
+ if ( rc )
+ grant_write_unlock(d->grant_table);
return rc;
}
+void gnttab_map_frame_end(struct domain *d, mfn_t mfn)
+{
+ put_page(mfn_to_page(mfn));
+
+ grant_write_unlock(d->grant_table);
+}
+
static void gnttab_usage_print(struct domain *rd)
{
int first = 1;
--- a/xen/include/xen/grant_table.h
+++ b/xen/include/xen/grant_table.h
@@ -60,8 +60,13 @@ int gnttab_release_mappings(struct domai
int mem_sharing_gref_to_gfn(struct grant_table *gt, grant_ref_t ref,
gfn_t *gfn, uint16_t *status);
-int gnttab_map_frame(struct domain *d, unsigned long idx, gfn_t gfn,
- mfn_t *mfn);
+/*
+ * These need to be used as a pair, as the first (in the success case) returns
+ * with a lock and page reference held which the second needs to drop.
+ */
+int gnttab_map_frame_begin(struct domain *d, unsigned long idx, gfn_t gfn,
+ mfn_t *mfn);
+void gnttab_map_frame_end(struct domain *d, mfn_t mfn);
unsigned int gnttab_resource_max_frames(const struct domain *d, unsigned int id);
@@ -100,12 +105,14 @@ static inline int mem_sharing_gref_to_gf
return -EINVAL;
}
-static inline int gnttab_map_frame(struct domain *d, unsigned long idx,
- gfn_t gfn, mfn_t *mfn)
+static inline int gnttab_map_frame_begin(struct domain *d, unsigned long idx,
+ gfn_t gfn, mfn_t *mfn)
{
return -EINVAL;
}
+static inline void gnttab_map_frame_end(struct domain *d, mfn_t mfn) {}
+
static inline unsigned int gnttab_resource_max_frames(
const struct domain *d, unsigned int id)
{

43
xsa490-4.21.patch Normal file
View file

@ -0,0 +1,43 @@
From: Andrew Cooper <andrew.cooper3@citrix.com>
Subject: x86/amd: Mitigate AMD-SN-7052
This is XSA-490 / CVE-2025-54518.
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
diff --git a/xen/arch/x86/cpu/amd.c b/xen/arch/x86/cpu/amd.c
index 1bb0766ebf13..b5bf2b732e8f 100644
--- a/xen/arch/x86/cpu/amd.c
+++ b/xen/arch/x86/cpu/amd.c
@@ -1116,11 +1116,25 @@ static void amd_check_bp_cfg(void)
{
uint64_t val, new = 0;
- /*
- * AMD Erratum #1485. Set bit 5, as instructed.
- */
- if (!cpu_has_hypervisor && boot_cpu_data.x86 == 0x19 && is_zen4_uarch())
- new |= (1 << 5);
+ if (!cpu_has_hypervisor) {
+ /*
+ * AMD Erratum #1485. If SMT is enabled and STIBP disabled,
+ * the CPU may fetch incorrect instruction bytes.
+ *
+ * Set bit 5, as instructed.
+ */
+ if (boot_cpu_data.x86 == 0x19 && is_zen4_uarch())
+ new |= (1 << 5);
+
+ /*
+ * AMD SB-7052. CPU OP Cache corruption, causing instructions
+ * to be executed at a higher privilege.
+ *
+ * Set bit 33, as instructed.
+ */
+ if (boot_cpu_data.x86 == 0x17 && is_zen2_uarch())
+ new |= (1UL << 33);
+ }
/*
* On hardware supporting SRSO_MSR_FIX, activate BP_SPEC_REDUCE by

211
xsa491-4.21.patch Normal file
View file

@ -0,0 +1,211 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: x86/HVM: add locking to I/O port translation list traversal
XEN_DOMCTL_ioport_mapping is usable by DM stubdoms, and hence we can't
assume the list to be left unaltered while the guest (really: the
hypervisor on behalf of the guest) is accessing it.
This is XSA-491 / CVE-2026-42487.
Fixes: 192c4dabc344 ("domctl and p2m changes for PCI passthru")
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
--- a/xen/arch/x86/domctl.c
+++ b/xen/arch/x86/domctl.c
@@ -663,6 +663,7 @@ long arch_do_domctl(
"ioport_map:add: dom%d gport=%x mport=%x nr=%x\n",
d->domain_id, fgp, fmp, np);
+ write_lock(&hvm->g2m_ioport_lock);
list_for_each_entry(g2m_ioport, &hvm->g2m_ioport_list, list)
if (g2m_ioport->mport == fmp )
{
@@ -684,11 +685,14 @@ long arch_do_domctl(
g2m_ioport->np = np;
list_add_tail(&g2m_ioport->list, &hvm->g2m_ioport_list);
}
+ write_unlock(&hvm->g2m_ioport_lock);
if ( !ret )
ret = ioports_permit_access(d, fmp, fmp + np - 1);
if ( ret && !found && g2m_ioport )
{
+ write_lock(&hvm->g2m_ioport_lock);
list_del(&g2m_ioport->list);
+ write_unlock(&hvm->g2m_ioport_lock);
xfree(g2m_ioport);
}
}
@@ -697,6 +701,8 @@ long arch_do_domctl(
printk(XENLOG_G_INFO
"ioport_map:remove: dom%d gport=%x mport=%x nr=%x\n",
d->domain_id, fgp, fmp, np);
+
+ write_lock(&hvm->g2m_ioport_lock);
list_for_each_entry(g2m_ioport, &hvm->g2m_ioport_list, list)
if ( g2m_ioport->mport == fmp )
{
@@ -704,6 +710,8 @@ long arch_do_domctl(
xfree(g2m_ioport);
break;
}
+ write_unlock(&hvm->g2m_ioport_lock);
+
ret = ioports_deny_access(d, fmp, fmp + np - 1);
if ( ret && is_hardware_domain(currd) )
printk(XENLOG_ERR
--- a/xen/arch/x86/hvm/emulate.c
+++ b/xen/arch/x86/hvm/emulate.c
@@ -160,7 +160,6 @@ void hvmemul_cancel(struct vcpu *v)
hvio->mmio_insn_bytes = 0;
hvio->mmio_access = (struct npfec){};
hvio->mmio_retry = false;
- hvio->g2m_ioport = NULL;
hvmemul_cache_disable(v);
}
--- a/xen/arch/x86/hvm/hvm.c
+++ b/xen/arch/x86/hvm/hvm.c
@@ -610,6 +610,7 @@ int hvm_domain_initialise(struct domain
spin_lock_init(&d->arch.hvm.irq_lock);
spin_lock_init(&d->arch.hvm.uc_lock);
spin_lock_init(&d->arch.hvm.write_map.lock);
+ rwlock_init(&d->arch.hvm.g2m_ioport_lock);
rwlock_init(&d->arch.hvm.mmcfg_lock);
INIT_LIST_HEAD(&d->arch.hvm.write_map.list);
INIT_LIST_HEAD(&d->arch.hvm.g2m_ioport_list);
--- a/xen/arch/x86/hvm/io.c
+++ b/xen/arch/x86/hvm/io.c
@@ -143,36 +143,56 @@ bool handle_pio(uint16_t port, unsigned
return true;
}
-static bool cf_check g2m_portio_accept(
- const struct hvm_io_handler *handler, const ioreq_t *p)
+/* NB: Returns with the lock held in the success case. */
+static const struct g2m_ioport *g2m_portio_find_and_lock(struct hvm_domain *hvm,
+ uint64_t addr,
+ uint32_t size)
{
- struct vcpu *curr = current;
- const struct hvm_domain *hvm = &curr->domain->arch.hvm;
- struct hvm_vcpu_io *hvio = &curr->arch.hvm.hvm_io;
- struct g2m_ioport *g2m_ioport;
- unsigned int start, end;
+ const struct g2m_ioport *g2m_ioport;
+
+ read_lock(&hvm->g2m_ioport_lock);
list_for_each_entry( g2m_ioport, &hvm->g2m_ioport_list, list )
{
- start = g2m_ioport->gport;
- end = start + g2m_ioport->np;
- if ( (p->addr >= start) && (p->addr + p->size <= end) )
- {
- hvio->g2m_ioport = g2m_ioport;
- return 1;
- }
+ unsigned int start = g2m_ioport->gport;
+
+ if ( addr >= start && addr + size <= start + g2m_ioport->np )
+ return g2m_ioport;
}
- return 0;
+ read_unlock(&hvm->g2m_ioport_lock);
+
+ return NULL;
+}
+
+static bool cf_check g2m_portio_accept(
+ const struct hvm_io_handler *handler, const ioreq_t *p)
+{
+ struct hvm_domain *hvm = &current->domain->arch.hvm;
+ const struct g2m_ioport *g2m_ioport =
+ g2m_portio_find_and_lock(hvm, p->addr, p->size);
+
+ if ( !g2m_ioport )
+ return false;
+
+ read_unlock(&hvm->g2m_ioport_lock);
+
+ return true;
}
static int cf_check g2m_portio_read(
const struct hvm_io_handler *handler, uint64_t addr, uint32_t size,
uint64_t *data)
{
- struct hvm_vcpu_io *hvio = &current->arch.hvm.hvm_io;
- const struct g2m_ioport *g2m_ioport = hvio->g2m_ioport;
- unsigned int mport = (addr - g2m_ioport->gport) + g2m_ioport->mport;
+ struct hvm_domain *hvm = &current->domain->arch.hvm;
+ const struct g2m_ioport *g2m_ioport =
+ g2m_portio_find_and_lock(hvm, addr, size);
+ unsigned int mport;
+
+ if ( !g2m_ioport )
+ return X86EMUL_RETRY;
+
+ mport = addr - g2m_ioport->gport + g2m_ioport->mport;
switch ( size )
{
@@ -189,6 +209,8 @@ static int cf_check g2m_portio_read(
BUG();
}
+ read_unlock(&hvm->g2m_ioport_lock);
+
return X86EMUL_OKAY;
}
@@ -196,9 +218,15 @@ static int cf_check g2m_portio_write(
const struct hvm_io_handler *handler, uint64_t addr, uint32_t size,
uint64_t data)
{
- struct hvm_vcpu_io *hvio = &current->arch.hvm.hvm_io;
- const struct g2m_ioport *g2m_ioport = hvio->g2m_ioport;
- unsigned int mport = (addr - g2m_ioport->gport) + g2m_ioport->mport;
+ struct hvm_domain *hvm = &current->domain->arch.hvm;
+ const struct g2m_ioport *g2m_ioport =
+ g2m_portio_find_and_lock(hvm, addr, size);
+ unsigned int mport;
+
+ if ( !g2m_ioport )
+ return X86EMUL_RETRY;
+
+ mport = addr - g2m_ioport->gport + g2m_ioport->mport;
switch ( size )
{
@@ -215,6 +243,8 @@ static int cf_check g2m_portio_write(
BUG();
}
+ read_unlock(&hvm->g2m_ioport_lock);
+
return X86EMUL_OKAY;
}
--- a/xen/arch/x86/include/asm/hvm/domain.h
+++ b/xen/arch/x86/include/asm/hvm/domain.h
@@ -125,6 +125,7 @@ struct hvm_domain {
/* List of guest to machine IO ports mapping. */
struct list_head g2m_ioport_list;
+ rwlock_t g2m_ioport_lock;
/* List of MMCFG regions trapped by Xen. */
struct list_head mmcfg_regions;
--- a/xen/arch/x86/include/asm/hvm/vcpu.h
+++ b/xen/arch/x86/include/asm/hvm/vcpu.h
@@ -54,8 +54,6 @@ struct hvm_vcpu_io {
unsigned long msix_unmask_address;
unsigned long msix_snoop_address;
unsigned long msix_snoop_gpa;
-
- const struct g2m_ioport *g2m_ioport;
};
struct nestedvcpu {

264
xsa492-4.21-01.patch Normal file
View file

@ -0,0 +1,264 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: sched: use sequence counter to enlighten vcpu_runstate_get()
Subsequently XEN_DOMCTL_getdomaininfo will want to invoke the function
without holding a lock, thus allowing parallel execution of potentially
many instances. As was learned from 228ab9992ffb ("domctl: improve
locking during domain destruction"), reverted by d0887cc6b16e, such
parallelism can result in severe lock contention on any (previously)
inner lock. To avoid taking that risk replace the use of the scheduler
lock in vcpu_runstate_get() by a newly introduced sequence counter.
Convert the "no lock if current" property to "use a local counter
instance", thus guaranteeing the loop to exit after the first iteration.
Skeleton and commentary of the seqcount implementation based on /
derived from Linux 6.11-rc.
To have runstate_seq placed next to runstate in struct vcpu, without
introducing a new obvious padding hole, yet while keeping the latter
adjacent to runstate_guest{,_area} as well, move runstate down a little.
This is part of XSA-492.
Requested-by: Andrew Cooper <andrew.cooper3@citrix.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Signed-off-by: Andrew Cooper <andrew.cooper3@citrix.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
Reviewed-by: Juergen Gross <jgross@suse.com>
--- a/xen/common/sched/core.c
+++ b/xen/common/sched/core.c
@@ -281,13 +281,18 @@ static inline void vcpu_runstate_change(
}
delta = new_entry_time - v->runstate.state_entry_time;
- if ( delta > 0 )
+
+ /* Serialization: ->schedule_lock (see ASSERT() above). */
+ with_seq_write(&v->runstate_seq)
{
- v->runstate.time[v->runstate.state] += delta;
- v->runstate.state_entry_time = new_entry_time;
- }
+ if ( delta > 0 )
+ {
+ v->runstate.time[v->runstate.state] += delta;
+ v->runstate.state_entry_time = new_entry_time;
+ }
- v->runstate.state = new_state;
+ v->runstate.state = new_state;
+ }
}
void sched_guest_idle(void (*idle) (void), unsigned int cpu)
@@ -307,30 +312,18 @@ void sched_guest_idle(void (*idle) (void
void vcpu_runstate_get(const struct vcpu *v,
struct vcpu_runstate_info *runstate)
{
- spinlock_t *lock;
- s_time_t delta;
- struct sched_unit *unit;
+ struct seqcount seq = SEQCNT_ZERO();
+ const struct seqcount *s = likely(v == current) ? &seq : &v->runstate_seq;
- rcu_read_lock(&sched_res_rculock);
-
- /*
- * Be careful in case of an idle vcpu: the assignment to a unit might
- * change even with the scheduling lock held, so be sure to use the
- * correct unit for locking in order to avoid triggering an ASSERT() in
- * the unlock function.
- */
- unit = is_idle_vcpu(v) ? get_sched_res(v->processor)->sched_unit_idle
- : v->sched_unit;
- lock = likely(v == current) ? NULL : unit_schedule_lock_irq(unit);
- memcpy(runstate, &v->runstate, sizeof(*runstate));
- delta = NOW() - runstate->state_entry_time;
- if ( delta > 0 )
- runstate->time[runstate->state] += delta;
-
- if ( unlikely(lock != NULL) )
- unit_schedule_unlock_irq(lock, unit);
+ until_seq_read(s)
+ {
+ s_time_t delta;
- rcu_read_unlock(&sched_res_rculock);
+ *runstate = v->runstate;
+ delta = NOW() - runstate->state_entry_time;
+ if ( delta > 0 )
+ runstate->time[runstate->state] += delta;
+ }
}
uint64_t get_cpu_idle_time(unsigned int cpu)
--- a/xen/include/xen/sched.h
+++ b/xen/include/xen/sched.h
@@ -16,6 +16,7 @@
#include <xen/radix-tree.h>
#include <xen/multicall.h>
#include <xen/nospec.h>
+#include <xen/seqcount.h>
#include <xen/tasklet.h>
#include <xen/mm.h>
#include <xen/smp.h>
@@ -198,7 +199,6 @@ struct vcpu
struct sched_unit *sched_unit;
- struct vcpu_runstate_info runstate;
#ifndef CONFIG_COMPAT
# define runstate_guest(v) ((v)->runstate_guest)
XEN_GUEST_HANDLE(vcpu_runstate_info_t) runstate_guest; /* guest address */
@@ -210,6 +210,8 @@ struct vcpu
} runstate_guest; /* guest address */
#endif
struct guest_area runstate_guest_area;
+ struct vcpu_runstate_info runstate;
+ struct seqcount runstate_seq;
unsigned int new_state;
/* Has the FPU been initialised? */
--- /dev/null
+++ b/xen/include/xen/seqcount.h
@@ -0,0 +1,139 @@
+/* SPDX-License-Identifier: GPL-2.0-only */
+#ifndef XEN_SEQCOUNT_H
+#define XEN_SEQCOUNT_H
+
+#include <xen/lib.h>
+#include <xen/nospec.h>
+
+#include <asm/atomic.h>
+#include <asm/system.h>
+
+/*
+ * Sequence counters (seqcount_t)
+ *
+ * This is the raw counting mechanism, without any writer protection.
+ *
+ * Write side critical sections must be serialized (and non-preemptible).
+ *
+ * If readers can be invoked from interrupt contexts, interrupts must also
+ * be respectively disabled before entering the write section.
+ *
+ * This mechanism can't be used if the protected data contains pointers,
+ * as the writer can invalidate a pointer that a reader is following.
+ */
+struct seqcount {
+ unsigned int sequence;
+};
+
+/*
+ * SEQCNT_ZERO() - initializer for seqcount_t
+ * @name: Name of the struct seqcount instance
+ */
+#define SEQCNT_ZERO() { .sequence = 0 }
+
+static inline unsigned int seqprop_sequence(const struct seqcount *s)
+{
+ return ACCESS_ONCE(s->sequence);
+}
+
+/*
+ * read_seqcount_begin() - begin a seqcount read critical section
+ * @s: Pointer to struct seqcount
+ *
+ * Return: count to be passed to read_seqcount_retry()
+ */
+static inline unsigned int _read_seqcount_begin(const struct seqcount *s)
+{
+ unsigned int seq;
+
+ while ((seq = seqprop_sequence(s)) & 1)
+ cpu_relax();
+
+ smp_rmb();
+
+ return seq;
+}
+
+static always_inline unsigned int read_seqcount_begin(const struct seqcount *s)
+{
+ unsigned int seq = _read_seqcount_begin(s);
+
+ block_lock_speculation();
+
+ return seq;
+}
+
+/*
+ * read_seqcount_retry() - end a seqcount read critical section
+ * @s: Pointer to struct seqcount
+ * @start: count, from read_seqcount_begin()
+ *
+ * read_seqcount_retry closes the read critical section of given struct
+ * seqcount. If the critical section was invalid, it must be ignored
+ * (and typically retried).
+ *
+ * Return: true if a read section retry is required, else false
+ */
+static inline bool _read_seqcount_retry(const struct seqcount *s,
+ unsigned int start)
+{
+ smp_rmb();
+ return unlikely(seqprop_sequence(s) != start);
+}
+
+static always_inline bool read_seqcount_retry(const struct seqcount *s,
+ unsigned int start)
+{
+ return lock_evaluate_nospec(_read_seqcount_retry(s, start));
+}
+
+/* Loops until a consistent count has been observed across the loop body. */
+#define until_seq_read(seq) \
+ for ( unsigned int retry_ = 1, count_; \
+ retry_ && (count_ = read_seqcount_begin(seq), true); \
+ retry_ = read_seqcount_retry(seq, count_) )
+
+/*
+ * write_seqcount_begin() - start a struct seqcount write side critical section
+ * @s: Pointer to struct seqcount
+ *
+ * Context: sequence counter write side sections must be serialized.
+ * If readers can be invoked from interrupt context, interrupts must be
+ * respectively disabled.
+ */
+static inline void write_seqcount_begin(struct seqcount *s)
+{
+ add_sized(&s->sequence, 1);
+ smp_wmb();
+}
+
+/*
+ * write_seqcount_end() - end a struct seqcount write side critical section
+ * @s: Pointer to seqcount
+ */
+static inline void write_seqcount_end(struct seqcount *s)
+{
+ smp_wmb();
+ add_sized(&s->sequence, 1);
+}
+
+/*
+ * Not really a loop, but we need write_seqcount_{begin,end}() in the correct
+ * position.
+ */
+#define with_seq_write(seq) \
+ for ( bool once_ = true; \
+ once_ && (write_seqcount_begin(seq), true); \
+ (write_seqcount_end(seq), once_ = false) )
+
+#endif /* XEN_SEQCOUNT_H */
+
+/*
+ * Local variables:
+ * mode: C
+ * c-file-style: "BSD"
+ * c-basic-offset: 4
+ * tab-width: 4
+ * indent-tabs-mode: nil
+ * End:
+ */

104
xsa492-4.21-02.patch Normal file
View file

@ -0,0 +1,104 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: domctl: handle XEN_DOMCTL_getdomaininfo without acquiring domctl lock
getdomaininfo() is not called under consistently the same lock. Thus,
with caller side locking irrelevant, it can as well be called with the
domctl lock not held. (Callers not pausing the domain they want to
retrieve information for already need to be aware that not all of the
data returned can be relied on as being consistent; most data will also
be stale by the time the caller gets to look at it.)
Move the handling not only ahead of acquiring the lock, but also ahead
of the XSM check, leveraging that the sub-op has its own hook.
While moving, convert an assignment to an assertion: The domain in
question was determined from the field which previously was "updated".
This is part of XSA-492.
Fixes: 5513bd0b4675 ("add xenstore domain flag to hypervisor")
Reported-by: Andrew Cooper <andrew.cooper3@citrix.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
Acked-by: Daniel P. Smith <dpsmith@apertussolutions.com>
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -318,6 +318,26 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
break;
}
+ /* Handle sub-ops not requiring the domctl lock. */
+ switch ( op->cmd )
+ {
+ case XEN_DOMCTL_getdomaininfo:
+ ret = xsm_getdomaininfo(XSM_XS_PRIV, d);
+ if ( !ret )
+ {
+ getdomaininfo(d, &op->u.getdomaininfo);
+
+ ASSERT(op->domain == op->u.getdomaininfo.domain);
+ copyback = true;
+ }
+
+ goto domctl_out_unlock_domonly;
+
+ default:
+ /* Everything else handled further down. */
+ break;
+ }
+
ret = xsm_domctl(XSM_OTHER, d, op->cmd,
/* SSIDRef only applicable for cmd == createdomain */
op->u.createdomain.ssidref);
@@ -516,17 +536,6 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
copyback = 1;
break;
- case XEN_DOMCTL_getdomaininfo:
- ret = xsm_getdomaininfo(XSM_XS_PRIV, d);
- if ( ret )
- break;
-
- getdomaininfo(d, &op->u.getdomaininfo);
-
- op->domain = op->u.getdomaininfo.domain;
- copyback = 1;
- break;
-
case XEN_DOMCTL_getvcpucontext:
{
vcpu_guest_context_u c = { .nat = NULL };
--- a/xen/include/xsm/dummy.h
+++ b/xen/include/xsm/dummy.h
@@ -172,9 +172,13 @@ static XSM_INLINE int cf_check xsm_domct
case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_unbind_pt_irq:
return xsm_default_action(XSM_DM_PRIV, current->domain, d);
- case XEN_DOMCTL_getdomaininfo:
case XEN_DOMCTL_get_domain_state:
return xsm_default_action(XSM_XS_PRIV, current->domain, d);
+
+ case XEN_DOMCTL_getdomaininfo:
+ ASSERT_UNREACHABLE();
+ return -EILSEQ;
+
default:
return xsm_default_action(XSM_PRIV, current->domain, d);
}
--- a/xen/xsm/flask/hooks.c
+++ b/xen/xsm/flask/hooks.c
@@ -682,8 +682,12 @@ static int cf_check flask_domctl(struct
*/
return avc_current_has_perm(ssidref, SECCLASS_DOMAIN, DOMAIN__CREATE, NULL);
- /* These have individual XSM hooks (common/domctl.c) */
+ /* These have individual XSM hooks and don't make it here. */
case XEN_DOMCTL_getdomaininfo:
+ ASSERT_UNREACHABLE();
+ return -EILSEQ;
+
+ /* These have individual XSM hooks (common/domctl.c) */
case XEN_DOMCTL_scheduler_op:
case XEN_DOMCTL_irq_permission:
case XEN_DOMCTL_iomem_permission:

87
xsa492-4.21-03.patch Normal file
View file

@ -0,0 +1,87 @@
From: Daniel P. Smith <dpsmith@apertussolutions.com>
Subject: domctl: protect locking for get_domain_state
When DOMID_INVALID is passed, the dom exec handler lock is being taken
without any check that the domain is even allowed to take the lock. This
allows for an unauthorized domain to DoS the get_domain_state domctl op.
Move to consider the op effectively being called against the hypervisor.
Thus it is the target of the call being invoked to identify the last
domain with a state change. The subsequent check of whether the source
domain is allowed the state of the last domain to change state is still
relevant.
This is part of XSA-492.
Signed-off-by: Daniel P. Smith <dpsmith@apertussolutions.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
--- a/tools/flask/policy/modules/xenstore.te
+++ b/tools/flask/policy/modules/xenstore.te
@@ -14,6 +14,7 @@ allow xenstore_t xen_t:xen writeconsole;
# Xenstore queries domaininfo on all domains
allow xenstore_t domain_type:domain getdomaininfo;
allow xenstore_t domain_type:domain2 get_domain_state;
+allow xenstore_t domxen_t:domain2 get_domain_state;
# As a shortcut, the following 3 rules are used instead of adding a domain_comms
# rule between xenstore_t and every domain type that talks to xenstore
--- a/xen/common/domain.c
+++ b/xen/common/domain.c
@@ -216,12 +216,8 @@ int get_domain_state(struct xen_domctl_g
if ( info->pad0 )
return -EINVAL;
- if ( d )
+ if ( d != dom_xen )
{
- rc = xsm_get_domain_state(XSM_XS_PRIV, d);
- if ( rc )
- return rc;
-
set_domain_state_info(info, d);
return 0;
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -304,13 +304,19 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
fallthrough;
case XEN_DOMCTL_test_assign_device:
case XEN_DOMCTL_vm_event_op:
- case XEN_DOMCTL_get_domain_state:
if ( op->domain == DOMID_INVALID )
{
d = NULL;
break;
}
fallthrough;
+ case XEN_DOMCTL_get_domain_state:
+ if ( op->domain == DOMID_INVALID )
+ {
+ d = dom_xen;
+ break;
+ }
+ fallthrough;
default:
d = rcu_lock_domain_by_id(op->domain);
if ( !d )
@@ -863,7 +869,9 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
break;
case XEN_DOMCTL_get_domain_state:
- ret = get_domain_state(&op->u.get_domain_state, d, &op->domain);
+ ret = xsm_get_domain_state(XSM_XS_PRIV, d);
+ if ( !ret )
+ ret = get_domain_state(&op->u.get_domain_state, d, &op->domain);
if ( !ret )
copyback = true;
break;
@@ -876,7 +884,7 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
domctl_lock_release();
domctl_out_unlock_domonly:
- if ( d && d != dom_io )
+ if ( d && !is_system_domain(d) )
rcu_unlock_domain(d);
if ( copyback && __copy_to_guest(u_domctl, op, 1) )

81
xsa492-4.21-04.patch Normal file
View file

@ -0,0 +1,81 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: domctl: handle XEN_DOMCTL_get_domain_state without acquiring domctl lock
get_domain_state() uses its own locking. Thus, with caller side locking
irrelevant, it can as well be called with the domctl lock not held.
Move the handling not only ahead of acquiring the lock, but also ahead
of the XSM check, leveraging that the sub-op has its own hook.
This is part of XSA-492.
Fixes: 3ad3df1bd0aa ("xen: add new domctl get_domain_state")
Reported-by: Andrew Cooper <andrew.cooper3@citrix.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Acked-by: Daniel P. Smith <dpsmith@apertussolutions.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -339,6 +339,14 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
goto domctl_out_unlock_domonly;
+ case XEN_DOMCTL_get_domain_state:
+ ret = xsm_get_domain_state(XSM_XS_PRIV, d);
+ if ( !ret )
+ ret = get_domain_state(&op->u.get_domain_state, d, &op->domain);
+ if ( !ret )
+ copyback = true;
+ goto domctl_out_unlock_domonly;
+
default:
/* Everything else handled further down. */
break;
@@ -868,14 +876,6 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
ret = -EOPNOTSUPP;
break;
- case XEN_DOMCTL_get_domain_state:
- ret = xsm_get_domain_state(XSM_XS_PRIV, d);
- if ( !ret )
- ret = get_domain_state(&op->u.get_domain_state, d, &op->domain);
- if ( !ret )
- copyback = true;
- break;
-
default:
ret = arch_do_domctl(op, d, u_domctl);
break;
--- a/xen/include/xsm/dummy.h
+++ b/xen/include/xsm/dummy.h
@@ -172,10 +172,9 @@ static XSM_INLINE int cf_check xsm_domct
case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_unbind_pt_irq:
return xsm_default_action(XSM_DM_PRIV, current->domain, d);
- case XEN_DOMCTL_get_domain_state:
- return xsm_default_action(XSM_XS_PRIV, current->domain, d);
case XEN_DOMCTL_getdomaininfo:
+ case XEN_DOMCTL_get_domain_state:
ASSERT_UNREACHABLE();
return -EILSEQ;
--- a/xen/xsm/flask/hooks.c
+++ b/xen/xsm/flask/hooks.c
@@ -684,6 +684,7 @@ static int cf_check flask_domctl(struct
/* These have individual XSM hooks and don't make it here. */
case XEN_DOMCTL_getdomaininfo:
+ case XEN_DOMCTL_get_domain_state:
ASSERT_UNREACHABLE();
return -EILSEQ;
@@ -694,7 +695,6 @@ static int cf_check flask_domctl(struct
case XEN_DOMCTL_memory_mapping:
case XEN_DOMCTL_set_target:
case XEN_DOMCTL_vm_event_op:
- case XEN_DOMCTL_get_domain_state:
/* These have individual XSM hooks (arch/../domctl.c) */
case XEN_DOMCTL_bind_pt_irq:

156
xsa492-4.21-05.patch Normal file
View file

@ -0,0 +1,156 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: domain: locking for iomem_caps accesses
In order to be able to pull at least the XEN_DOMCTL_iomem_mapping handling
out of the domctl-locked region, a separate (per-domain) lock is needed to
synchronize in particular with XEN_DOMCTL_iomem_permission.
Locking is added only as far as domctl-s are affected. Uses presently
outside of the domctl lock may want dealing with subsequently (perhaps
limited to non-__init code).
This is part of XSA-492.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
--- a/xen/common/domain.c
+++ b/xen/common/domain.c
@@ -518,10 +518,15 @@ static int late_hwdom_init(struct domain
* may be modified after this hypercall returns if a more complex
* device model is desired.
*/
+ write_lock(&dom0->caps_lock);
rangeset_swap(d->irq_caps, dom0->irq_caps);
rangeset_swap(d->iomem_caps, dom0->iomem_caps);
#ifdef CONFIG_X86
rangeset_swap(d->arch.ioport_caps, dom0->arch.ioport_caps);
+#endif
+ write_unlock(&dom0->caps_lock);
+
+#ifdef CONFIG_X86
setup_io_bitmap(d);
setup_io_bitmap(dom0);
#endif
@@ -873,6 +878,7 @@ struct domain *domain_create(domid_t dom
rspin_lock_init_prof(d, domain_lock);
rspin_lock_init_prof(d, page_alloc_lock);
spin_lock_init(&d->hypercall_deadlock_mutex);
+ rwlock_init(&d->caps_lock);
INIT_PAGE_LIST_HEAD(&d->page_list);
INIT_PAGE_LIST_HEAD(&d->extra_page_list);
INIT_PAGE_LIST_HEAD(&d->xenpage_list);
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -267,6 +267,35 @@ static struct vnuma_info *vnuma_init(con
return ERR_PTR(ret);
}
+void iocaps_double_lock(struct domain *d, bool write)
+{
+ struct domain *currd = current->domain;
+
+ if ( d->domain_id > currd->domain_id )
+ read_lock(&currd->caps_lock);
+
+ if ( write )
+ write_lock(&d->caps_lock);
+ else
+ read_lock(&d->caps_lock);
+
+ if ( d->domain_id < currd->domain_id )
+ read_lock(&currd->caps_lock);
+}
+
+void iocaps_double_unlock(struct domain *d, bool write)
+{
+ struct domain *currd = current->domain;
+
+ if ( d != currd )
+ read_unlock(&currd->caps_lock);
+
+ if ( write )
+ write_unlock(&d->caps_lock);
+ else
+ read_unlock(&d->caps_lock);
+}
+
static bool is_stable_domctl(uint32_t cmd)
{
return cmd == XEN_DOMCTL_get_domain_state;
@@ -687,6 +716,8 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
if ( (mfn + nr_mfns - 1) < mfn ) /* wrap? */
break;
+ iocaps_double_lock(d, true);
+
if ( !iomem_access_permitted(current->domain,
mfn, mfn + nr_mfns - 1) ||
xsm_iomem_permission(XSM_HOOK, d, mfn, mfn + nr_mfns - 1, allow) )
@@ -695,6 +726,8 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
ret = iomem_permit_access(d, mfn, mfn + nr_mfns - 1);
else
ret = iomem_deny_access(d, mfn, mfn + nr_mfns - 1);
+
+ iocaps_double_unlock(d, true);
break;
}
@@ -719,19 +752,15 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
break;
#endif
+ iocaps_double_lock(d, false);
+
ret = -EPERM;
if ( !iomem_access_permitted(current->domain, mfn, mfn_end) ||
- !iomem_access_permitted(d, mfn, mfn_end) )
- break;
-
- ret = xsm_iomem_mapping(XSM_HOOK, d, mfn, mfn_end, add);
- if ( ret )
- break;
-
- if ( !paging_mode_translate(d) )
- break;
-
- if ( add )
+ !iomem_access_permitted(d, mfn, mfn_end) ||
+ (ret = xsm_iomem_mapping(XSM_HOOK, d, mfn, mfn_end, add)) ||
+ !paging_mode_translate(d) )
+ /* Nothing. */;
+ else if ( add )
{
printk(XENLOG_G_DEBUG
"memory_map:add: dom%d gfn=%lx mfn=%lx nr=%lx\n",
@@ -755,6 +784,8 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
"memory_map: error %ld removing dom%d access to [%lx,%lx]\n",
ret, d->domain_id, mfn, mfn_end);
}
+
+ iocaps_double_unlock(d, false);
break;
}
--- a/xen/include/xen/iocap.h
+++ b/xen/include/xen/iocap.h
@@ -12,6 +12,9 @@
#include <asm/iocap.h>
#include <asm/p2m.h>
+void iocaps_double_lock(struct domain *d, bool write);
+void iocaps_double_unlock(struct domain *d, bool write);
+
static inline int iomem_permit_access(struct domain *d, unsigned long s,
unsigned long e)
{
--- a/xen/include/xen/sched.h
+++ b/xen/include/xen/sched.h
@@ -536,6 +536,7 @@ struct domain
#endif
/* I/O capabilities (access to IRQs and memory-mapped I/O). */
+ rwlock_t caps_lock;
struct rangeset *iomem_caps;
struct rangeset *irq_caps;

84
xsa492-4.21-06.patch Normal file
View file

@ -0,0 +1,84 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: x86/domain: locking for ioport_caps accesses
In order to be able to pull at least the XEN_DOMCTL_ioport_mapping
handling out of the domctl-locked region, the new separate (per-domain)
lock is used to synchronize in particular with
XEN_DOMCTL_ioport_permission.
Locking is added only as far as domctl-s are affected. Uses presently
outside of the domctl lock may want dealing with subsequently (perhaps
limited to non-__init code).
This is part of XSA-492.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
--- a/xen/arch/x86/domctl.c
+++ b/xen/arch/x86/domctl.c
@@ -233,6 +233,8 @@ long arch_do_domctl(
unsigned int np = domctl->u.ioport_permission.nr_ports;
int allow = domctl->u.ioport_permission.allow_access;
+ iocaps_double_lock(d, true);
+
if ( (fp + np) <= fp || (fp + np) > MAX_IOPORTS )
ret = -EINVAL;
else if ( !ioports_access_permitted(currd, fp, fp + np - 1) ||
@@ -242,6 +244,8 @@ long arch_do_domctl(
ret = ioports_permit_access(d, fp, fp + np - 1);
else
ret = ioports_deny_access(d, fp, fp + np - 1);
+
+ iocaps_double_unlock(d, true);
break;
}
@@ -648,16 +652,13 @@ long arch_do_domctl(
break;
}
- ret = -EPERM;
- if ( !ioports_access_permitted(currd, fmp, fmp + np - 1) )
- break;
-
- ret = xsm_ioport_mapping(XSM_HOOK, d, fmp, fmp + np - 1, add);
- if ( ret )
- break;
-
hvm = &d->arch.hvm;
- if ( add )
+ iocaps_double_lock(d, true);
+
+ if ( !ioports_access_permitted(currd, fmp, fmp + np - 1) ||
+ (ret = xsm_ioport_mapping(XSM_HOOK, d, fmp, fmp + np - 1, add)) )
+ ret = ret ?: -EPERM;
+ else if ( add )
{
printk(XENLOG_G_INFO
"ioport_map:add: dom%d gport=%x mport=%x nr=%x\n",
@@ -718,6 +720,8 @@ long arch_do_domctl(
"ioport_map: error %ld denying dom%d access to [%x,%x]\n",
ret, d->domain_id, fmp, fmp + np - 1);
}
+
+ iocaps_double_unlock(d, true);
break;
}
--- a/xen/arch/x86/setup.c
+++ b/xen/arch/x86/setup.c
@@ -2339,9 +2339,12 @@ void __hwdom_init setup_io_bitmap(struct
return;
bitmap_fill(d->arch.hvm.io_bitmap, 0x10000);
+
+ read_lock(&d->caps_lock);
if ( rangeset_report_ranges(d->arch.ioport_caps, 0, 0x10000,
io_bitmap_cb, d) )
BUG();
+ read_unlock(&d->caps_lock);
/*
* We need to trap 4-byte accesses to 0xcf8 (see admin_io_okay(),

202
xsa492-4.21-07.patch Normal file
View file

@ -0,0 +1,202 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: domain: locking for irq_caps accesses
In order to be able to pull at least the XEN_DOMCTL_{,un}bind_pt_irq
handling out of the domctl-locked region, a separate (per-domain) lock is
needed to synchronize in particular with XEN_DOMCTL_{irq,gsi}_permission.
Locking is added only as far as domctl-s are affected. Uses presently
outside of the domctl lock may want dealing with subsequently (perhaps
limited to non-__init code).
This is part of XSA-492.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
Reviewed-by: Julien Grall <julien@xen.org>
--- a/xen/arch/arm/domctl.c
+++ b/xen/arch/arm/domctl.c
@@ -76,6 +76,7 @@ long arch_do_domctl(struct xen_domctl *d
case XEN_DOMCTL_bind_pt_irq:
{
int rc;
+ struct domain *currd = current->domain;
struct xen_domctl_bind_pt_irq *bind = &domctl->u.bind_pt_irq;
uint32_t irq = bind->u.spi.spi;
uint32_t virq = bind->machine_irq;
@@ -107,21 +108,26 @@ long arch_do_domctl(struct xen_domctl *d
if ( rc )
return rc;
- if ( !irq_access_permitted(current->domain, irq) )
- return -EPERM;
+ read_lock(&currd->caps_lock);
- if ( !vgic_reserve_virq(d, virq) )
- return -EBUSY;
-
- rc = route_irq_to_guest(d, virq, irq, "routed IRQ");
- if ( rc )
- vgic_free_virq(d, virq);
+ if ( !irq_access_permitted(currd, irq) )
+ rc = -EPERM;
+ else if ( !vgic_reserve_virq(d, virq) )
+ rc = -EBUSY;
+ else
+ {
+ rc = route_irq_to_guest(d, virq, irq, "routed IRQ");
+ if ( rc )
+ vgic_free_virq(d, virq);
+ }
+ read_unlock(&currd->caps_lock);
return rc;
}
case XEN_DOMCTL_unbind_pt_irq:
{
int rc;
+ struct domain *currd = current->domain;
struct xen_domctl_bind_pt_irq *bind = &domctl->u.bind_pt_irq;
uint32_t irq = bind->u.spi.spi;
uint32_t virq = bind->machine_irq;
@@ -138,16 +144,15 @@ long arch_do_domctl(struct xen_domctl *d
if ( rc )
return rc;
- if ( !irq_access_permitted(current->domain, irq) )
- return -EPERM;
-
- rc = release_guest_irq(d, virq);
- if ( rc )
- return rc;
+ read_lock(&currd->caps_lock);
- vgic_free_virq(d, virq);
+ if ( !irq_access_permitted(currd, irq) )
+ rc = -EPERM;
+ else if ( !(rc = release_guest_irq(d, virq)) )
+ vgic_free_virq(d, virq);
- return 0;
+ read_unlock(&currd->caps_lock);
+ return rc;
}
case XEN_DOMCTL_vuart_op:
--- a/xen/arch/x86/domctl.c
+++ b/xen/arch/x86/domctl.c
@@ -267,16 +267,17 @@ long arch_do_domctl(
break;
}
- ret = -EPERM;
+ iocaps_double_lock(d, true);
+
if ( !irq_access_permitted(currd, irq) ||
xsm_irq_permission(XSM_HOOK, d, irq, flags) )
- break;
-
- if ( flags )
+ ret = -EPERM;
+ else if ( flags )
ret = irq_permit_access(d, irq);
else
ret = irq_deny_access(d, irq);
+ iocaps_double_unlock(d, true);
break;
}
@@ -579,20 +580,27 @@ long arch_do_domctl(
break;
irq = domain_pirq_to_irq(d, bind->machine_irq);
- ret = -EPERM;
- if ( irq <= 0 || !irq_access_permitted(currd, irq) )
- break;
+ if ( irq <= 0 )
+ ret = -EPERM;
- ret = -ESRCH;
- if ( is_iommu_enabled(d) )
+ read_lock(&currd->caps_lock);
+
+ if ( !irq_access_permitted(currd, irq) )
+ ret = -EPERM;
+ else if ( is_iommu_enabled(d) )
{
pcidevs_lock();
ret = pt_irq_create_bind(d, bind);
pcidevs_unlock();
+
+ if ( ret < 0 )
+ printk(XENLOG_G_ERR "pt_irq_create_bind failed (%ld) for %pd\n",
+ ret, d);
}
- if ( ret < 0 )
- printk(XENLOG_G_ERR "pt_irq_create_bind failed (%ld) for dom%d\n",
- ret, d->domain_id);
+ else
+ ret = -ESRCH;
+
+ read_unlock(&currd->caps_lock);
break;
}
@@ -605,23 +613,26 @@ long arch_do_domctl(
if ( !is_hvm_domain(d) )
break;
- ret = -EPERM;
- if ( irq <= 0 || !irq_access_permitted(currd, irq) )
- break;
-
ret = xsm_unbind_pt_irq(XSM_HOOK, d, bind);
if ( ret )
break;
- if ( is_iommu_enabled(d) )
+ read_lock(&currd->caps_lock);
+
+ if ( !irq_access_permitted(currd, irq) )
+ ret = -EPERM;
+ else if ( is_iommu_enabled(d) )
{
pcidevs_lock();
ret = pt_irq_destroy_bind(d, bind);
pcidevs_unlock();
+
+ if ( ret < 0 )
+ printk(XENLOG_G_ERR "pt_irq_destroy_bind failed (%ld) for %pd\n",
+ ret, d);
}
- if ( ret < 0 )
- printk(XENLOG_G_ERR "pt_irq_destroy_bind failed (%ld) for dom%d\n",
- ret, d->domain_id);
+
+ read_unlock(&currd->caps_lock);
break;
}
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -695,6 +695,9 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
ret = -EINVAL;
break;
}
+
+ iocaps_double_lock(d, true);
+
irq = pirq_access_permitted(current->domain, pirq);
if ( !irq || xsm_irq_permission(XSM_HOOK, d, irq, allow) )
ret = -EPERM;
@@ -702,6 +705,8 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
ret = irq_permit_access(d, irq);
else
ret = irq_deny_access(d, irq);
+
+ iocaps_double_unlock(d, true);
break;
}
#endif

85
xsa492-4.21-08.patch Normal file
View file

@ -0,0 +1,85 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: XSM/Flask: split the .iomem_mapping() hook
It's used twice in entirely different situations. The use in do_domctl()
wants to become an ordinary XSM_DM_PRIV invocation, while the one in vPCI
code need to remain XSM_HOOK (it may plausibly become XSM_TARGET). For
Flask, the same backing function will continue to be used for the time
being.
This is part of XSA-492.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Acked-by: Daniel P. Smith <dpsmith@apertussolutions.com>
--- a/xen/drivers/vpci/header.c
+++ b/xen/drivers/vpci/header.c
@@ -67,7 +67,7 @@ static int cf_check map_range(
return -EPERM;
}
- rc = xsm_iomem_mapping(XSM_HOOK, map->d, map_mfn, m_end, map->map);
+ rc = xsm_iomem_mapping_vpci(XSM_HOOK, map->d, map_mfn, m_end, map->map);
if ( rc )
{
printk(XENLOG_G_WARNING
--- a/xen/include/xsm/dummy.h
+++ b/xen/include/xsm/dummy.h
@@ -580,6 +580,13 @@ static XSM_INLINE int cf_check xsm_iomem
return xsm_default_action(action, current->domain, d);
}
+static XSM_INLINE int cf_check xsm_iomem_mapping_vpci(
+ XSM_DEFAULT_ARG struct domain *d, uint64_t s, uint64_t e, uint8_t allow)
+{
+ XSM_ASSERT_ACTION(XSM_HOOK);
+ return xsm_default_action(action, current->domain, d);
+}
+
static XSM_INLINE int cf_check xsm_pci_config_permission(
XSM_DEFAULT_ARG struct domain *d, uint32_t machine_bdf, uint16_t start,
uint16_t end, uint8_t access)
--- a/xen/include/xsm/xsm.h
+++ b/xen/include/xsm/xsm.h
@@ -118,6 +118,8 @@ struct xsm_ops {
uint8_t allow);
int (*iomem_mapping)(struct domain *d, uint64_t s, uint64_t e,
uint8_t allow);
+ int (*iomem_mapping_vpci)(struct domain *d, uint64_t s, uint64_t e,
+ uint8_t allow);
int (*pci_config_permission)(struct domain *d, uint32_t machine_bdf,
uint16_t start, uint16_t end, uint8_t access);
@@ -523,6 +525,12 @@ static inline int xsm_iomem_mapping(
return alternative_call(xsm_ops.iomem_mapping, d, s, e, allow);
}
+static inline int xsm_iomem_mapping_vpci(
+ xsm_default_t def, struct domain *d, uint64_t s, uint64_t e, uint8_t allow)
+{
+ return alternative_call(xsm_ops.iomem_mapping_vpci, d, s, e, allow);
+}
+
static inline int xsm_pci_config_permission(
xsm_default_t def, struct domain *d, uint32_t machine_bdf, uint16_t start,
uint16_t end, uint8_t access)
--- a/xen/xsm/dummy.c
+++ b/xen/xsm/dummy.c
@@ -76,6 +76,7 @@ static const struct xsm_ops __initconst_
.irq_permission = xsm_irq_permission,
.iomem_permission = xsm_iomem_permission,
.iomem_mapping = xsm_iomem_mapping,
+ .iomem_mapping_vpci = xsm_iomem_mapping_vpci,
.pci_config_permission = xsm_pci_config_permission,
.get_vnumainfo = xsm_get_vnumainfo,
--- a/xen/xsm/flask/hooks.c
+++ b/xen/xsm/flask/hooks.c
@@ -1950,6 +1950,7 @@ static const struct xsm_ops __initconst_
.irq_permission = flask_irq_permission,
.iomem_permission = flask_iomem_permission,
.iomem_mapping = flask_iomem_mapping,
+ .iomem_mapping_vpci = flask_iomem_mapping,
.pci_config_permission = flask_pci_config_permission,
.resource_plug_core = flask_resource_plug_core,

194
xsa492-4.21-09.patch Normal file
View file

@ -0,0 +1,194 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: domctl: handle XEN_DOMCTL_memory_mapping without acquiring domctl lock
With dedicated locking added, the domctl lock isn't required here anymore.
Move the re-purposed dedicated XSM check as early as possible.
Minimal "modernization": Switch "add" to bool and use %pd in log messages.
This is part of XSA-492.
Fixes: fda49f9b3fbb ("Add build option to allow more hypercalls from stubdoms")
Reported-by: Andrew Cooper <andrew.cooper3@citrix.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Acked-by: Daniel P. Smith <dpsmith@apertussolutions.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -376,6 +376,66 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
copyback = true;
goto domctl_out_unlock_domonly;
+ case XEN_DOMCTL_memory_mapping:
+ {
+ unsigned long gfn = op->u.memory_mapping.first_gfn;
+ unsigned long mfn = op->u.memory_mapping.first_mfn;
+ unsigned long nr_mfns = op->u.memory_mapping.nr_mfns;
+ unsigned long mfn_end = mfn + nr_mfns - 1;
+ bool add = op->u.memory_mapping.add_mapping;
+
+ ret = -EINVAL;
+ if ( mfn_end < mfn || /* Wrap? */
+ ((mfn | mfn_end) >> (paddr_bits - PAGE_SHIFT)) ||
+ (gfn + nr_mfns - 1) < gfn ) /* Wrap? */
+ goto domctl_out_unlock_domonly;
+
+ ret = xsm_iomem_mapping(XSM_DM_PRIV, d, mfn, mfn_end, add);
+ if ( ret || !paging_mode_translate(d) )
+ goto domctl_out_unlock_domonly;
+
+#ifndef CONFIG_X86 /* XXX ARM!? */
+ ret = -E2BIG;
+ /* Must break hypercall up as this could take a while. */
+ if ( nr_mfns > 64 )
+ goto domctl_out_unlock_domonly;
+#endif
+
+ iocaps_double_lock(d, false);
+
+ ret = -EPERM;
+ if ( !iomem_access_permitted(current->domain, mfn, mfn_end) ||
+ !iomem_access_permitted(d, mfn, mfn_end) )
+ /* Nothing. */;
+ else if ( add )
+ {
+ printk(XENLOG_G_DEBUG
+ "memory_map:add: %pd gfn=%lx mfn=%lx nr=%lx\n",
+ d, gfn, mfn, nr_mfns);
+
+ ret = map_mmio_regions(d, _gfn(gfn), nr_mfns, _mfn(mfn));
+ if ( ret < 0 )
+ printk(XENLOG_G_WARNING
+ "memory_map:fail: %pd gfn=%lx mfn=%lx nr=%lx ret:%ld\n",
+ d, gfn, mfn, nr_mfns, ret);
+ }
+ else
+ {
+ printk(XENLOG_G_DEBUG
+ "memory_map:remove: %pd gfn=%lx mfn=%lx nr=%lx\n",
+ d, gfn, mfn, nr_mfns);
+
+ ret = unmap_mmio_regions(d, _gfn(gfn), nr_mfns, _mfn(mfn));
+ if ( ret < 0 && is_hardware_domain(current->domain) )
+ printk(XENLOG_ERR
+ "memory_map: error %ld removing %pd access to [%lx,%lx]\n",
+ ret, d, mfn, mfn_end);
+ }
+
+ iocaps_double_unlock(d, false);
+ goto domctl_out_unlock_domonly;
+ }
+
default:
/* Everything else handled further down. */
break;
@@ -736,64 +796,6 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
break;
}
- case XEN_DOMCTL_memory_mapping:
- {
- unsigned long gfn = op->u.memory_mapping.first_gfn;
- unsigned long mfn = op->u.memory_mapping.first_mfn;
- unsigned long nr_mfns = op->u.memory_mapping.nr_mfns;
- unsigned long mfn_end = mfn + nr_mfns - 1;
- int add = op->u.memory_mapping.add_mapping;
-
- ret = -EINVAL;
- if ( mfn_end < mfn || /* wrap? */
- ((mfn | mfn_end) >> (paddr_bits - PAGE_SHIFT)) ||
- (gfn + nr_mfns - 1) < gfn ) /* wrap? */
- break;
-
-#ifndef CONFIG_X86 /* XXX ARM!? */
- ret = -E2BIG;
- /* Must break hypercall up as this could take a while. */
- if ( nr_mfns > 64 )
- break;
-#endif
-
- iocaps_double_lock(d, false);
-
- ret = -EPERM;
- if ( !iomem_access_permitted(current->domain, mfn, mfn_end) ||
- !iomem_access_permitted(d, mfn, mfn_end) ||
- (ret = xsm_iomem_mapping(XSM_HOOK, d, mfn, mfn_end, add)) ||
- !paging_mode_translate(d) )
- /* Nothing. */;
- else if ( add )
- {
- printk(XENLOG_G_DEBUG
- "memory_map:add: dom%d gfn=%lx mfn=%lx nr=%lx\n",
- d->domain_id, gfn, mfn, nr_mfns);
-
- ret = map_mmio_regions(d, _gfn(gfn), nr_mfns, _mfn(mfn));
- if ( ret < 0 )
- printk(XENLOG_G_WARNING
- "memory_map:fail: dom%d gfn=%lx mfn=%lx nr=%lx ret:%ld\n",
- d->domain_id, gfn, mfn, nr_mfns, ret);
- }
- else
- {
- printk(XENLOG_G_DEBUG
- "memory_map:remove: dom%d gfn=%lx mfn=%lx nr=%lx\n",
- d->domain_id, gfn, mfn, nr_mfns);
-
- ret = unmap_mmio_regions(d, _gfn(gfn), nr_mfns, _mfn(mfn));
- if ( ret < 0 && is_hardware_domain(current->domain) )
- printk(XENLOG_ERR
- "memory_map: error %ld removing dom%d access to [%lx,%lx]\n",
- ret, d->domain_id, mfn, mfn_end);
- }
-
- iocaps_double_unlock(d, false);
- break;
- }
-
case XEN_DOMCTL_settimeoffset:
domain_set_time_offset(d, op->u.settimeoffset.time_offset_seconds);
break;
--- a/xen/include/xsm/dummy.h
+++ b/xen/include/xsm/dummy.h
@@ -168,13 +168,13 @@ static XSM_INLINE int cf_check xsm_domct
switch ( cmd )
{
case XEN_DOMCTL_ioport_mapping:
- case XEN_DOMCTL_memory_mapping:
case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_unbind_pt_irq:
return xsm_default_action(XSM_DM_PRIV, current->domain, d);
case XEN_DOMCTL_getdomaininfo:
case XEN_DOMCTL_get_domain_state:
+ case XEN_DOMCTL_memory_mapping:
ASSERT_UNREACHABLE();
return -EILSEQ;
@@ -576,7 +576,7 @@ static XSM_INLINE int cf_check xsm_iomem
static XSM_INLINE int cf_check xsm_iomem_mapping(
XSM_DEFAULT_ARG struct domain *d, uint64_t s, uint64_t e, uint8_t allow)
{
- XSM_ASSERT_ACTION(XSM_HOOK);
+ XSM_ASSERT_ACTION(XSM_DM_PRIV);
return xsm_default_action(action, current->domain, d);
}
--- a/xen/xsm/flask/hooks.c
+++ b/xen/xsm/flask/hooks.c
@@ -685,6 +685,7 @@ static int cf_check flask_domctl(struct
/* These have individual XSM hooks and don't make it here. */
case XEN_DOMCTL_getdomaininfo:
case XEN_DOMCTL_get_domain_state:
+ case XEN_DOMCTL_memory_mapping:
ASSERT_UNREACHABLE();
return -EILSEQ;
@@ -692,7 +693,6 @@ static int cf_check flask_domctl(struct
case XEN_DOMCTL_scheduler_op:
case XEN_DOMCTL_irq_permission:
case XEN_DOMCTL_iomem_permission:
- case XEN_DOMCTL_memory_mapping:
case XEN_DOMCTL_set_target:
case XEN_DOMCTL_vm_event_op:

97
xsa492-4.21-10.patch Normal file
View file

@ -0,0 +1,97 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: domctl: handle XEN_DOMCTL_ioport_mapping without acquiring domctl lock
With dedicated locking added, the domctl lock isn't required here anymore.
As the handling is in arch-specific code (x86 only), almost no code is
being moved, but a 2nd (extensible to other sub-ops) invocation of
arch_do_domctl() is being added. Move just the re-purposed dedicated XSM
check as early as possible.
In flask_domctl() don't put #ifdef around the moved case label.
This is part of XSA-492.
Fixes: fda49f9b3fbb ("Add build option to allow more hypercalls from stubdoms")
Reported-by: Andrew Cooper <andrew.cooper3@citrix.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
Acked-by: Daniel P. Smith <dpsmith@apertussolutions.com>
--- a/xen/arch/x86/domctl.c
+++ b/xen/arch/x86/domctl.c
@@ -663,12 +663,15 @@ long arch_do_domctl(
break;
}
+ ret = xsm_ioport_mapping(XSM_DM_PRIV, d, fmp, fmp + np - 1, add);
+ if ( ret )
+ break;
+
hvm = &d->arch.hvm;
iocaps_double_lock(d, true);
- if ( !ioports_access_permitted(currd, fmp, fmp + np - 1) ||
- (ret = xsm_ioport_mapping(XSM_HOOK, d, fmp, fmp + np - 1, add)) )
- ret = ret ?: -EPERM;
+ if ( !ioports_access_permitted(currd, fmp, fmp + np - 1) )
+ ret = -EPERM;
else if ( add )
{
printk(XENLOG_G_INFO
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -436,6 +436,10 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
goto domctl_out_unlock_domonly;
}
+ case XEN_DOMCTL_ioport_mapping:
+ ret = arch_do_domctl(op, d, u_domctl);
+ goto domctl_out_unlock_domonly;
+
default:
/* Everything else handled further down. */
break;
--- a/xen/include/xsm/dummy.h
+++ b/xen/include/xsm/dummy.h
@@ -167,13 +167,13 @@ static XSM_INLINE int cf_check xsm_domct
XSM_ASSERT_ACTION(XSM_OTHER);
switch ( cmd )
{
- case XEN_DOMCTL_ioport_mapping:
case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_unbind_pt_irq:
return xsm_default_action(XSM_DM_PRIV, current->domain, d);
case XEN_DOMCTL_getdomaininfo:
case XEN_DOMCTL_get_domain_state:
+ case XEN_DOMCTL_ioport_mapping:
case XEN_DOMCTL_memory_mapping:
ASSERT_UNREACHABLE();
return -EILSEQ;
@@ -772,7 +772,7 @@ static XSM_INLINE int cf_check xsm_iopor
static XSM_INLINE int cf_check xsm_ioport_mapping(
XSM_DEFAULT_ARG struct domain *d, uint32_t s, uint32_t e, uint8_t allow)
{
- XSM_ASSERT_ACTION(XSM_HOOK);
+ XSM_ASSERT_ACTION(XSM_DM_PRIV);
return xsm_default_action(action, current->domain, d);
}
--- a/xen/xsm/flask/hooks.c
+++ b/xen/xsm/flask/hooks.c
@@ -685,6 +685,7 @@ static int cf_check flask_domctl(struct
/* These have individual XSM hooks and don't make it here. */
case XEN_DOMCTL_getdomaininfo:
case XEN_DOMCTL_get_domain_state:
+ case XEN_DOMCTL_ioport_mapping:
case XEN_DOMCTL_memory_mapping:
ASSERT_UNREACHABLE();
return -EILSEQ;
@@ -703,7 +704,6 @@ static int cf_check flask_domctl(struct
/* These have individual XSM hooks (arch/x86/domctl.c) */
case XEN_DOMCTL_shadow_op:
case XEN_DOMCTL_ioport_permission:
- case XEN_DOMCTL_ioport_mapping:
case XEN_DOMCTL_gsi_permission:
#endif
#ifdef CONFIG_HAS_PASSTHROUGH

128
xsa492-4.21-11.patch Normal file
View file

@ -0,0 +1,128 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: domctl: handle XEN_DOMCTL_{,un}bind_pt_irq without acquiring domctl lock
With dedicated locking added, the domctl lock isn't required here anymore.
(It also already isn't used when pt_irq_{create,destroy}_bind() are
invoked for PVH Dom0.) As the handling is in arch-specific code, no code
is being moved, but the 2nd (extensible to other sub-ops like the ones
here) invocation of arch_do_domctl() is being re-used.
This is part of XSA-492.
Fixes: fda49f9b3fbb ("Add build option to allow more hypercalls from stubdoms")
Reported-by: Andrew Cooper <andrew.cooper3@citrix.com>
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
Acked-by: Daniel P. Smith <dpsmith@apertussolutions.com>
Acked-by: Julien Grall <julien@xen.org>
--- a/xen/arch/arm/domctl.c
+++ b/xen/arch/arm/domctl.c
@@ -104,7 +104,7 @@ long arch_do_domctl(struct xen_domctl *d
if ( rc )
return rc;
- rc = xsm_bind_pt_irq(XSM_HOOK, d, bind);
+ rc = xsm_bind_pt_irq(XSM_DM_PRIV, d, bind);
if ( rc )
return rc;
@@ -140,7 +140,7 @@ long arch_do_domctl(struct xen_domctl *d
if ( irq != virq )
return -EINVAL;
- rc = xsm_unbind_pt_irq(XSM_HOOK, d, bind);
+ rc = xsm_unbind_pt_irq(XSM_DM_PRIV, d, bind);
if ( rc )
return rc;
--- a/xen/arch/x86/domctl.c
+++ b/xen/arch/x86/domctl.c
@@ -575,7 +575,7 @@ long arch_do_domctl(
if ( !is_hvm_domain(d) )
break;
- ret = xsm_bind_pt_irq(XSM_HOOK, d, bind);
+ ret = xsm_bind_pt_irq(XSM_DM_PRIV, d, bind);
if ( ret )
break;
@@ -613,7 +613,7 @@ long arch_do_domctl(
if ( !is_hvm_domain(d) )
break;
- ret = xsm_unbind_pt_irq(XSM_HOOK, d, bind);
+ ret = xsm_unbind_pt_irq(XSM_DM_PRIV, d, bind);
if ( ret )
break;
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -437,6 +437,8 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
}
case XEN_DOMCTL_ioport_mapping:
+ case XEN_DOMCTL_bind_pt_irq:
+ case XEN_DOMCTL_unbind_pt_irq:
ret = arch_do_domctl(op, d, u_domctl);
goto domctl_out_unlock_domonly;
--- a/xen/include/xsm/dummy.h
+++ b/xen/include/xsm/dummy.h
@@ -168,13 +168,11 @@ static XSM_INLINE int cf_check xsm_domct
switch ( cmd )
{
case XEN_DOMCTL_bind_pt_irq:
- case XEN_DOMCTL_unbind_pt_irq:
- return xsm_default_action(XSM_DM_PRIV, current->domain, d);
-
case XEN_DOMCTL_getdomaininfo:
case XEN_DOMCTL_get_domain_state:
case XEN_DOMCTL_ioport_mapping:
case XEN_DOMCTL_memory_mapping:
+ case XEN_DOMCTL_unbind_pt_irq:
ASSERT_UNREACHABLE();
return -EILSEQ;
@@ -541,14 +539,14 @@ static XSM_INLINE int cf_check xsm_unmap
static XSM_INLINE int cf_check xsm_bind_pt_irq(
XSM_DEFAULT_ARG struct domain *d, struct xen_domctl_bind_pt_irq *bind)
{
- XSM_ASSERT_ACTION(XSM_HOOK);
+ XSM_ASSERT_ACTION(XSM_DM_PRIV);
return xsm_default_action(action, current->domain, d);
}
static XSM_INLINE int cf_check xsm_unbind_pt_irq(
XSM_DEFAULT_ARG struct domain *d, struct xen_domctl_bind_pt_irq *bind)
{
- XSM_ASSERT_ACTION(XSM_HOOK);
+ XSM_ASSERT_ACTION(XSM_DM_PRIV);
return xsm_default_action(action, current->domain, d);
}
--- a/xen/xsm/flask/hooks.c
+++ b/xen/xsm/flask/hooks.c
@@ -683,10 +683,12 @@ static int cf_check flask_domctl(struct
return avc_current_has_perm(ssidref, SECCLASS_DOMAIN, DOMAIN__CREATE, NULL);
/* These have individual XSM hooks and don't make it here. */
+ case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_getdomaininfo:
case XEN_DOMCTL_get_domain_state:
case XEN_DOMCTL_ioport_mapping:
case XEN_DOMCTL_memory_mapping:
+ case XEN_DOMCTL_unbind_pt_irq:
ASSERT_UNREACHABLE();
return -EILSEQ;
@@ -697,9 +699,6 @@ static int cf_check flask_domctl(struct
case XEN_DOMCTL_set_target:
case XEN_DOMCTL_vm_event_op:
- /* These have individual XSM hooks (arch/../domctl.c) */
- case XEN_DOMCTL_bind_pt_irq:
- case XEN_DOMCTL_unbind_pt_irq:
#ifdef CONFIG_X86
/* These have individual XSM hooks (arch/x86/domctl.c) */
case XEN_DOMCTL_shadow_op:

172
xsa492-4.21-12.patch Normal file
View file

@ -0,0 +1,172 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: domctl: handle XEN_DOMCTL_io{mem,port}_permission without acquiring domctl lock
With dedicated locking added, the domctl lock isn't required here anymore.
As the I/O port handling is in arch-specific code (x86 only), no code is
being moved, but the 2nd invocation of arch_do_domctl() is re-used. Move
the re-purposed dedicated XSM checks as early as possible.
This is part of XSA-492.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
Acked-by: Daniel P. Smith <dpsmith@apertussolutions.com>
--- a/xen/arch/x86/domctl.c
+++ b/xen/arch/x86/domctl.c
@@ -233,12 +233,17 @@ long arch_do_domctl(
unsigned int np = domctl->u.ioport_permission.nr_ports;
int allow = domctl->u.ioport_permission.allow_access;
+ ret = -EINVAL;
+ if ( (fp + np) <= fp || (fp + np) > MAX_IOPORTS )
+ break;
+
+ ret = xsm_ioport_permission(XSM_PRIV, d, fp, fp + np - 1, allow);
+ if ( ret )
+ break;
+
iocaps_double_lock(d, true);
- if ( (fp + np) <= fp || (fp + np) > MAX_IOPORTS )
- ret = -EINVAL;
- else if ( !ioports_access_permitted(currd, fp, fp + np - 1) ||
- xsm_ioport_permission(XSM_HOOK, d, fp, fp + np - 1, allow) )
+ if ( !ioports_access_permitted(currd, fp, fp + np - 1) )
ret = -EPERM;
else if ( allow )
ret = ioports_permit_access(d, fp, fp + np - 1);
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -376,6 +376,34 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
copyback = true;
goto domctl_out_unlock_domonly;
+ case XEN_DOMCTL_iomem_permission:
+ {
+ unsigned long mfn = op->u.iomem_permission.first_mfn;
+ unsigned long nr_mfns = op->u.iomem_permission.nr_mfns;
+ bool allow = op->u.iomem_permission.allow_access;
+
+ ret = -EINVAL;
+ if ( (mfn + nr_mfns - 1) < mfn ) /* Wrap? */
+ goto domctl_out_unlock_domonly;
+
+ ret = xsm_iomem_permission(XSM_PRIV, d, mfn, mfn + nr_mfns - 1, allow);
+ if ( ret )
+ goto domctl_out_unlock_domonly;
+
+ iocaps_double_lock(d, true);
+
+ if ( !iomem_access_permitted(current->domain,
+ mfn, mfn + nr_mfns - 1) )
+ ret = -EPERM;
+ else if ( allow )
+ ret = iomem_permit_access(d, mfn, mfn + nr_mfns - 1);
+ else
+ ret = iomem_deny_access(d, mfn, mfn + nr_mfns - 1);
+
+ iocaps_double_unlock(d, true);
+ goto domctl_out_unlock_domonly;
+ }
+
case XEN_DOMCTL_memory_mapping:
{
unsigned long gfn = op->u.memory_mapping.first_gfn;
@@ -436,6 +464,7 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
goto domctl_out_unlock_domonly;
}
+ case XEN_DOMCTL_ioport_permission:
case XEN_DOMCTL_ioport_mapping:
case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_unbind_pt_irq:
@@ -777,31 +806,6 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
}
#endif
- case XEN_DOMCTL_iomem_permission:
- {
- unsigned long mfn = op->u.iomem_permission.first_mfn;
- unsigned long nr_mfns = op->u.iomem_permission.nr_mfns;
- int allow = op->u.iomem_permission.allow_access;
-
- ret = -EINVAL;
- if ( (mfn + nr_mfns - 1) < mfn ) /* wrap? */
- break;
-
- iocaps_double_lock(d, true);
-
- if ( !iomem_access_permitted(current->domain,
- mfn, mfn + nr_mfns - 1) ||
- xsm_iomem_permission(XSM_HOOK, d, mfn, mfn + nr_mfns - 1, allow) )
- ret = -EPERM;
- else if ( allow )
- ret = iomem_permit_access(d, mfn, mfn + nr_mfns - 1);
- else
- ret = iomem_deny_access(d, mfn, mfn + nr_mfns - 1);
-
- iocaps_double_unlock(d, true);
- break;
- }
-
case XEN_DOMCTL_settimeoffset:
domain_set_time_offset(d, op->u.settimeoffset.time_offset_seconds);
break;
--- a/xen/include/xsm/dummy.h
+++ b/xen/include/xsm/dummy.h
@@ -170,7 +170,9 @@ static XSM_INLINE int cf_check xsm_domct
case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_getdomaininfo:
case XEN_DOMCTL_get_domain_state:
+ case XEN_DOMCTL_iomem_permission:
case XEN_DOMCTL_ioport_mapping:
+ case XEN_DOMCTL_ioport_permission:
case XEN_DOMCTL_memory_mapping:
case XEN_DOMCTL_unbind_pt_irq:
ASSERT_UNREACHABLE();
@@ -567,7 +569,7 @@ static XSM_INLINE int cf_check xsm_irq_p
static XSM_INLINE int cf_check xsm_iomem_permission(
XSM_DEFAULT_ARG struct domain *d, uint64_t s, uint64_t e, uint8_t allow)
{
- XSM_ASSERT_ACTION(XSM_HOOK);
+ XSM_ASSERT_ACTION(XSM_PRIV);
return xsm_default_action(action, current->domain, d);
}
@@ -763,7 +765,7 @@ static XSM_INLINE int cf_check xsm_priv_
static XSM_INLINE int cf_check xsm_ioport_permission(
XSM_DEFAULT_ARG struct domain *d, uint32_t s, uint32_t e, uint8_t allow)
{
- XSM_ASSERT_ACTION(XSM_HOOK);
+ XSM_ASSERT_ACTION(XSM_PRIV);
return xsm_default_action(action, current->domain, d);
}
--- a/xen/xsm/flask/hooks.c
+++ b/xen/xsm/flask/hooks.c
@@ -686,7 +686,9 @@ static int cf_check flask_domctl(struct
case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_getdomaininfo:
case XEN_DOMCTL_get_domain_state:
+ case XEN_DOMCTL_iomem_permission:
case XEN_DOMCTL_ioport_mapping:
+ case XEN_DOMCTL_ioport_permission:
case XEN_DOMCTL_memory_mapping:
case XEN_DOMCTL_unbind_pt_irq:
ASSERT_UNREACHABLE();
@@ -695,14 +697,12 @@ static int cf_check flask_domctl(struct
/* These have individual XSM hooks (common/domctl.c) */
case XEN_DOMCTL_scheduler_op:
case XEN_DOMCTL_irq_permission:
- case XEN_DOMCTL_iomem_permission:
case XEN_DOMCTL_set_target:
case XEN_DOMCTL_vm_event_op:
#ifdef CONFIG_X86
/* These have individual XSM hooks (arch/x86/domctl.c) */
case XEN_DOMCTL_shadow_op:
- case XEN_DOMCTL_ioport_permission:
case XEN_DOMCTL_gsi_permission:
#endif
#ifdef CONFIG_HAS_PASSTHROUGH

163
xsa492-4.21-13.patch Normal file
View file

@ -0,0 +1,163 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: domctl: handle XEN_DOMCTL_{irq,gsi}_permission without acquiring domctl lock
With dedicated locking added, the domctl lock isn't required here anymore.
As the GSI handling is in arch-specific code (x86 only), no code is being
moved there; the 2nd invocation of arch_do_domctl() is re-used. Move the
re-purposed (XSM_HOOK -> XSM_PRIV, as xsm_domctl() is now bypassed)
dedicated XSM checks as early as possible.
This is part of XSA-492.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Acked-by: Daniel P. Smith <dpsmith@apertussolutions.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
--- a/xen/arch/x86/domctl.c
+++ b/xen/arch/x86/domctl.c
@@ -272,10 +272,13 @@ long arch_do_domctl(
break;
}
+ ret = xsm_irq_permission(XSM_PRIV, d, irq, flags);
+ if ( ret )
+ break;
+
iocaps_double_lock(d, true);
- if ( !irq_access_permitted(currd, irq) ||
- xsm_irq_permission(XSM_HOOK, d, irq, flags) )
+ if ( !irq_access_permitted(currd, irq) )
ret = -EPERM;
else if ( flags )
ret = irq_permit_access(d, irq);
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -464,8 +464,41 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
goto domctl_out_unlock_domonly;
}
+#ifdef CONFIG_HAS_PIRQ
+ case XEN_DOMCTL_irq_permission:
+ {
+ unsigned int pirq = op->u.irq_permission.pirq, irq;
+ bool allow = op->u.irq_permission.allow_access;
+
+ ret = -EINVAL;
+ if ( pirq >= current->domain->nr_pirqs )
+ goto domctl_out_unlock_domonly;
+
+ irq = domain_pirq_to_irq(current->domain, pirq);
+
+ ret = -EPERM;
+ if ( irq )
+ ret = xsm_irq_permission(XSM_PRIV, d, irq, allow);
+ if ( ret )
+ goto domctl_out_unlock_domonly;
+
+ iocaps_double_lock(d, true);
+
+ if ( !irq_access_permitted(current->domain, irq) )
+ ret = -EPERM;
+ else if ( allow )
+ ret = irq_permit_access(d, irq);
+ else
+ ret = irq_deny_access(d, irq);
+
+ iocaps_double_unlock(d, true);
+ goto domctl_out_unlock_domonly;
+ }
+#endif
+
case XEN_DOMCTL_ioport_permission:
case XEN_DOMCTL_ioport_mapping:
+ case XEN_DOMCTL_gsi_permission:
case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_unbind_pt_irq:
ret = arch_do_domctl(op, d, u_domctl);
@@ -779,33 +812,6 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
}
break;
-#ifdef CONFIG_HAS_PIRQ
- case XEN_DOMCTL_irq_permission:
- {
- unsigned int pirq = op->u.irq_permission.pirq, irq;
- int allow = op->u.irq_permission.allow_access;
-
- if ( pirq >= current->domain->nr_pirqs )
- {
- ret = -EINVAL;
- break;
- }
-
- iocaps_double_lock(d, true);
-
- irq = pirq_access_permitted(current->domain, pirq);
- if ( !irq || xsm_irq_permission(XSM_HOOK, d, irq, allow) )
- ret = -EPERM;
- else if ( allow )
- ret = irq_permit_access(d, irq);
- else
- ret = irq_deny_access(d, irq);
-
- iocaps_double_unlock(d, true);
- break;
- }
-#endif
-
case XEN_DOMCTL_settimeoffset:
domain_set_time_offset(d, op->u.settimeoffset.time_offset_seconds);
break;
--- a/xen/include/xsm/dummy.h
+++ b/xen/include/xsm/dummy.h
@@ -170,9 +170,11 @@ static XSM_INLINE int cf_check xsm_domct
case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_getdomaininfo:
case XEN_DOMCTL_get_domain_state:
+ case XEN_DOMCTL_gsi_permission:
case XEN_DOMCTL_iomem_permission:
case XEN_DOMCTL_ioport_mapping:
case XEN_DOMCTL_ioport_permission:
+ case XEN_DOMCTL_irq_permission:
case XEN_DOMCTL_memory_mapping:
case XEN_DOMCTL_unbind_pt_irq:
ASSERT_UNREACHABLE();
@@ -562,7 +564,7 @@ static XSM_INLINE int cf_check xsm_unmap
static XSM_INLINE int cf_check xsm_irq_permission(
XSM_DEFAULT_ARG struct domain *d, int pirq, uint8_t allow)
{
- XSM_ASSERT_ACTION(XSM_HOOK);
+ XSM_ASSERT_ACTION(XSM_PRIV);
return xsm_default_action(action, current->domain, d);
}
--- a/xen/xsm/flask/hooks.c
+++ b/xen/xsm/flask/hooks.c
@@ -686,9 +686,11 @@ static int cf_check flask_domctl(struct
case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_getdomaininfo:
case XEN_DOMCTL_get_domain_state:
+ case XEN_DOMCTL_gsi_permission:
case XEN_DOMCTL_iomem_permission:
case XEN_DOMCTL_ioport_mapping:
case XEN_DOMCTL_ioport_permission:
+ case XEN_DOMCTL_irq_permission:
case XEN_DOMCTL_memory_mapping:
case XEN_DOMCTL_unbind_pt_irq:
ASSERT_UNREACHABLE();
@@ -696,14 +698,12 @@ static int cf_check flask_domctl(struct
/* These have individual XSM hooks (common/domctl.c) */
case XEN_DOMCTL_scheduler_op:
- case XEN_DOMCTL_irq_permission:
case XEN_DOMCTL_set_target:
case XEN_DOMCTL_vm_event_op:
#ifdef CONFIG_X86
/* These have individual XSM hooks (arch/x86/domctl.c) */
case XEN_DOMCTL_shadow_op:
- case XEN_DOMCTL_gsi_permission:
#endif
#ifdef CONFIG_HAS_PASSTHROUGH
/*

179
xsa492-4.21-14.patch Normal file
View file

@ -0,0 +1,179 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: domctl/XSM: drop vm_event_control hook
Integrate the checking with xsm_domctl(). Care needs to be taken with the
GET_VERSION sub-op, which may be invoked with DOMID_INVALID, and which has
been (and continues to be) bypassing XSM checking.
Since the latter two parameters were unused, monitor_domctl() invoking the
hook was actually redundant with the earlier xsm_domctl() (as can be seen
nicely from the hunks changing xsm/flask/hooks.c).
As a positive side effect, permissions are then checked at the same early
point with and without Flask.
While folding XEN_DOMCTL_monitor_op and XEN_DOMCTL_vm_event_op in
flask_domctl(), also fold in XEN_DOMCTL_set_access_required.
This is part of XSA-492.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Acked-by: Daniel P. Smith <dpsmith@apertussolutions.com>
Reviewed-by: Roger Pau Monné <roger.pau@citrix.com>
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -496,6 +496,23 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
}
#endif
+ case XEN_DOMCTL_vm_event_op:
+ if ( op->u.vm_event_op.op == XEN_VM_EVENT_GET_VERSION )
+ {
+ /* No XSM check (and potentially d == NULL) here. */
+ ret = vm_event_domctl(d, &op->u.vm_event_op);
+ if ( !ret )
+ copyback = true;
+ goto domctl_out_unlock_domonly;
+ }
+ if ( !d )
+ {
+ ret = -ESRCH;
+ goto domctl_out_unlock_domonly;
+ }
+ /* Other sub-ops handled further down. */
+ break;
+
case XEN_DOMCTL_ioport_permission:
case XEN_DOMCTL_ioport_mapping:
case XEN_DOMCTL_gsi_permission:
--- a/xen/common/monitor.c
+++ b/xen/common/monitor.c
@@ -30,16 +30,11 @@
int monitor_domctl(struct domain *d, struct xen_domctl_monitor_op *mop)
{
- int rc;
bool requested_status = false;
if ( unlikely(current->domain == d) ) /* no domain_pause() */
return -EPERM;
- rc = xsm_vm_event_control(XSM_PRIV, d, mop->op, mop->event);
- if ( unlikely(rc) )
- return rc;
-
switch ( mop->op )
{
case XEN_DOMCTL_MONITOR_OP_ENABLE:
--- a/xen/common/vm_event.c
+++ b/xen/common/vm_event.c
@@ -603,11 +603,10 @@ int vm_event_domctl(struct domain *d, st
/* All other subops need to target a real domain. */
if ( unlikely(d == NULL) )
- return -ESRCH;
-
- rc = xsm_vm_event_control(XSM_PRIV, d, vec->mode, vec->op);
- if ( rc )
- return rc;
+ {
+ ASSERT_UNREACHABLE();
+ return -EILSEQ;
+ }
if ( unlikely(d == current->domain) ) /* no domain_pause() */
{
--- a/xen/include/xsm/dummy.h
+++ b/xen/include/xsm/dummy.h
@@ -652,13 +652,6 @@ static XSM_INLINE int cf_check xsm_hvm_a
}
}
-static XSM_INLINE int cf_check xsm_vm_event_control(
- XSM_DEFAULT_ARG struct domain *d, int mode, int op)
-{
- XSM_ASSERT_ACTION(XSM_PRIV);
- return xsm_default_action(action, current->domain, d);
-}
-
#ifdef CONFIG_VM_EVENT
static XSM_INLINE int cf_check xsm_mem_access(XSM_DEFAULT_ARG struct domain *d)
{
--- a/xen/include/xsm/xsm.h
+++ b/xen/include/xsm/xsm.h
@@ -157,8 +157,6 @@ struct xsm_ops {
int (*hvm_altp2mhvm_op)(struct domain *d, uint64_t mode, uint32_t op);
int (*get_vnumainfo)(struct domain *d);
- int (*vm_event_control)(struct domain *d, int mode, int op);
-
#ifdef CONFIG_VM_EVENT
int (*mem_access)(struct domain *d);
#endif
@@ -657,12 +655,6 @@ static inline int xsm_get_vnumainfo(xsm_
return alternative_call(xsm_ops.get_vnumainfo, d);
}
-static inline int xsm_vm_event_control(
- xsm_default_t def, struct domain *d, int mode, int op)
-{
- return alternative_call(xsm_ops.vm_event_control, d, mode, op);
-}
-
#ifdef CONFIG_VM_EVENT
static inline int xsm_mem_access(xsm_default_t def, struct domain *d)
{
--- a/xen/xsm/dummy.c
+++ b/xen/xsm/dummy.c
@@ -116,8 +116,6 @@ static const struct xsm_ops __initconst_
.remove_from_physmap = xsm_remove_from_physmap,
.map_gmfn_foreign = xsm_map_gmfn_foreign,
- .vm_event_control = xsm_vm_event_control,
-
#ifdef CONFIG_VM_EVENT
.mem_access = xsm_mem_access,
#endif
--- a/xen/xsm/flask/hooks.c
+++ b/xen/xsm/flask/hooks.c
@@ -699,7 +699,6 @@ static int cf_check flask_domctl(struct
/* These have individual XSM hooks (common/domctl.c) */
case XEN_DOMCTL_scheduler_op:
case XEN_DOMCTL_set_target:
- case XEN_DOMCTL_vm_event_op:
#ifdef CONFIG_X86
/* These have individual XSM hooks (arch/x86/domctl.c) */
@@ -793,9 +792,8 @@ static int cf_check flask_domctl(struct
return current_has_perm(d, SECCLASS_DOMAIN, DOMAIN__TRIGGER);
case XEN_DOMCTL_set_access_required:
- return current_has_perm(d, SECCLASS_DOMAIN2, DOMAIN2__VM_EVENT);
-
case XEN_DOMCTL_monitor_op:
+ case XEN_DOMCTL_vm_event_op:
return current_has_perm(d, SECCLASS_DOMAIN2, DOMAIN2__VM_EVENT);
case XEN_DOMCTL_debug_op:
@@ -1368,11 +1366,6 @@ static int cf_check flask_hvm_altp2mhvm_
return current_has_perm(d, SECCLASS_HVM, HVM__ALTP2MHVM_OP);
}
-static int cf_check flask_vm_event_control(struct domain *d, int mode, int op)
-{
- return current_has_perm(d, SECCLASS_DOMAIN2, DOMAIN2__VM_EVENT);
-}
-
#ifdef CONFIG_VM_EVENT
static int cf_check flask_mem_access(struct domain *d)
{
@@ -1971,8 +1964,6 @@ static const struct xsm_ops __initconst_
.do_xsm_op = do_flask_op,
.get_vnumainfo = flask_get_vnumainfo,
- .vm_event_control = flask_vm_event_control,
-
#ifdef CONFIG_VM_EVENT
.mem_access = flask_mem_access,
#endif

108
xsa492-4.21-15.patch Normal file
View file

@ -0,0 +1,108 @@
From: Jan Beulich <jbeulich@suse.com>
Subject: domctl/XSM: pass full struct xen_domctl to xsm_domctl()
Subsequently some sub-ops will want to inspect their sub-sub-ops. Plus
this way we don't need to pass SSIDref separately anymore for
domain_create.
This is part of XSA-492.
Signed-off-by: Jan Beulich <jbeulich@suse.com>
Acked-by: Daniel P. Smith <dpsmith@apertussolutions.com>
--- a/xen/arch/x86/mm/paging.c
+++ b/xen/arch/x86/mm/paging.c
@@ -735,7 +735,7 @@ long do_paging_domctl_cont(
if ( d == NULL )
return -ESRCH;
- ret = xsm_domctl(XSM_OTHER, d, op.cmd, 0 /* SSIDref not applicable */);
+ ret = xsm_domctl(XSM_OTHER, d, &op);
if ( !ret )
{
if ( domctl_lock_acquire() )
--- a/xen/common/domctl.c
+++ b/xen/common/domctl.c
@@ -526,9 +526,7 @@ long do_domctl(XEN_GUEST_HANDLE_PARAM(xe
break;
}
- ret = xsm_domctl(XSM_OTHER, d, op->cmd,
- /* SSIDRef only applicable for cmd == createdomain */
- op->u.createdomain.ssidref);
+ ret = xsm_domctl(XSM_OTHER, d, op);
if ( ret )
goto domctl_out_unlock_domonly;
--- a/xen/include/xsm/dummy.h
+++ b/xen/include/xsm/dummy.h
@@ -162,10 +162,10 @@ static XSM_INLINE int cf_check xsm_set_t
}
static XSM_INLINE int cf_check xsm_domctl(
- XSM_DEFAULT_ARG struct domain *d, unsigned int cmd, uint32_t ssidref)
+ XSM_DEFAULT_ARG struct domain *d, struct xen_domctl *op)
{
XSM_ASSERT_ACTION(XSM_OTHER);
- switch ( cmd )
+ switch ( op->cmd )
{
case XEN_DOMCTL_bind_pt_irq:
case XEN_DOMCTL_getdomaininfo:
--- a/xen/include/xsm/xsm.h
+++ b/xen/include/xsm/xsm.h
@@ -61,7 +61,7 @@ struct xsm_ops {
int (*sysctl_scheduler_op)(int op);
#endif
int (*set_target)(struct domain *d, struct domain *e);
- int (*domctl)(struct domain *d, unsigned int cmd, uint32_t ssidref);
+ int (*domctl)(struct domain *d, struct xen_domctl *op);
int (*sysctl)(int cmd);
int (*readconsole)(uint32_t clear);
@@ -260,9 +260,9 @@ static inline int xsm_set_target(
}
static inline int xsm_domctl(xsm_default_t def, struct domain *d,
- unsigned int cmd, uint32_t ssidref)
+ struct xen_domctl *op)
{
- return alternative_call(xsm_ops.domctl, d, cmd, ssidref);
+ return alternative_call(xsm_ops.domctl, d, op);
}
static inline int xsm_sysctl(xsm_default_t def, int cmd)
--- a/xen/xsm/flask/hooks.c
+++ b/xen/xsm/flask/hooks.c
@@ -667,10 +667,9 @@ static int cf_check flask_set_target(str
return rc;
}
-static int cf_check flask_domctl(struct domain *d, unsigned int cmd,
- uint32_t ssidref)
+static int cf_check flask_domctl(struct domain *d, struct xen_domctl *op)
{
- switch ( cmd )
+ switch ( op->cmd )
{
case XEN_DOMCTL_createdomain:
/*
@@ -680,7 +679,8 @@ static int cf_check flask_domctl(struct
* Note that d is NULL because we haven't even allocated memory for it
* this early in XEN_DOMCTL_createdomain.
*/
- return avc_current_has_perm(ssidref, SECCLASS_DOMAIN, DOMAIN__CREATE, NULL);
+ return avc_current_has_perm(op->u.createdomain.ssidref, SECCLASS_DOMAIN,
+ DOMAIN__CREATE, NULL);
/* These have individual XSM hooks and don't make it here. */
case XEN_DOMCTL_bind_pt_irq:
@@ -855,7 +855,7 @@ static int cf_check flask_domctl(struct
return current_has_perm(d, SECCLASS_DOMAIN2, DOMAIN2__SET_LLC_COLORS);
default:
- return avc_unknown_permission("domctl", cmd);
+ return avc_unknown_permission("domctl", op->cmd);
}
}

Some files were not shown because too many files have changed in this diff Show more