diff options
author | Vladimir Murzin <vladimir.murzin@arm.com> | 2016-11-02 07:55:34 -0400 |
---|---|---|
committer | Marc Zyngier <marc.zyngier@arm.com> | 2016-11-14 05:32:54 -0500 |
commit | 2988509dd8a0e9c2b64192a46ec2fe8211af6d3c (patch) | |
tree | 10d3d4a9c17e13cf4603949bd768ea5a4ae2f0c1 | |
parent | e29bd6f26703088930a5b3595623cf155ddea600 (diff) |
ARM: KVM: Support vGICv3 ITS
This patch allows to build and use vGICv3 ITS in 32-bit mode.
Signed-off-by: Vladimir Murzin <vladimir.murzin@arm.com>
Reviewed-by: Andre Przywara <andre.przywara@arm.com>
Reviewed-by: Marc Zyngier <marc.zyngier@arm.com>
Signed-off-by: Marc Zyngier <marc.zyngier@arm.com>
-rw-r--r-- | Documentation/virtual/kvm/api.txt | 2 | ||||
-rw-r--r-- | arch/arm/include/uapi/asm/kvm.h | 2 | ||||
-rw-r--r-- | arch/arm/kvm/Kconfig | 1 | ||||
-rw-r--r-- | arch/arm/kvm/Makefile | 1 | ||||
-rw-r--r-- | arch/arm/kvm/arm.c | 6 | ||||
-rw-r--r-- | arch/arm64/kvm/Kconfig | 4 | ||||
-rw-r--r-- | arch/arm64/kvm/reset.c | 6 | ||||
-rw-r--r-- | virt/kvm/arm/vgic/vgic-kvm-device.c | 2 | ||||
-rw-r--r-- | virt/kvm/arm/vgic/vgic-mmio-v3.c | 2 | ||||
-rw-r--r-- | virt/kvm/arm/vgic/vgic.h | 26 |
10 files changed, 11 insertions, 41 deletions
diff --git a/Documentation/virtual/kvm/api.txt b/Documentation/virtual/kvm/api.txt index 739db9ab16b2..2feeae6a4c3f 100644 --- a/Documentation/virtual/kvm/api.txt +++ b/Documentation/virtual/kvm/api.txt | |||
@@ -2198,7 +2198,7 @@ after pausing the vcpu, but before it is resumed. | |||
2198 | 4.71 KVM_SIGNAL_MSI | 2198 | 4.71 KVM_SIGNAL_MSI |
2199 | 2199 | ||
2200 | Capability: KVM_CAP_SIGNAL_MSI | 2200 | Capability: KVM_CAP_SIGNAL_MSI |
2201 | Architectures: x86 arm64 | 2201 | Architectures: x86 arm arm64 |
2202 | Type: vm ioctl | 2202 | Type: vm ioctl |
2203 | Parameters: struct kvm_msi (in) | 2203 | Parameters: struct kvm_msi (in) |
2204 | Returns: >0 on delivery, 0 if guest blocked the MSI, and -1 on error | 2204 | Returns: >0 on delivery, 0 if guest blocked the MSI, and -1 on error |
diff --git a/arch/arm/include/uapi/asm/kvm.h b/arch/arm/include/uapi/asm/kvm.h index b38c10c73579..af05f8e0903e 100644 --- a/arch/arm/include/uapi/asm/kvm.h +++ b/arch/arm/include/uapi/asm/kvm.h | |||
@@ -87,9 +87,11 @@ struct kvm_regs { | |||
87 | /* Supported VGICv3 address types */ | 87 | /* Supported VGICv3 address types */ |
88 | #define KVM_VGIC_V3_ADDR_TYPE_DIST 2 | 88 | #define KVM_VGIC_V3_ADDR_TYPE_DIST 2 |
89 | #define KVM_VGIC_V3_ADDR_TYPE_REDIST 3 | 89 | #define KVM_VGIC_V3_ADDR_TYPE_REDIST 3 |
90 | #define KVM_VGIC_ITS_ADDR_TYPE 4 | ||
90 | 91 | ||
91 | #define KVM_VGIC_V3_DIST_SIZE SZ_64K | 92 | #define KVM_VGIC_V3_DIST_SIZE SZ_64K |
92 | #define KVM_VGIC_V3_REDIST_SIZE (2 * SZ_64K) | 93 | #define KVM_VGIC_V3_REDIST_SIZE (2 * SZ_64K) |
94 | #define KVM_VGIC_V3_ITS_SIZE (2 * SZ_64K) | ||
93 | 95 | ||
94 | #define KVM_ARM_VCPU_POWER_OFF 0 /* CPU is started in OFF state */ | 96 | #define KVM_ARM_VCPU_POWER_OFF 0 /* CPU is started in OFF state */ |
95 | #define KVM_ARM_VCPU_PSCI_0_2 1 /* CPU uses PSCI v0.2 */ | 97 | #define KVM_ARM_VCPU_PSCI_0_2 1 /* CPU uses PSCI v0.2 */ |
diff --git a/arch/arm/kvm/Kconfig b/arch/arm/kvm/Kconfig index 3e1cd0452d67..90d0176fb30d 100644 --- a/arch/arm/kvm/Kconfig +++ b/arch/arm/kvm/Kconfig | |||
@@ -34,6 +34,7 @@ config KVM | |||
34 | select HAVE_KVM_IRQFD | 34 | select HAVE_KVM_IRQFD |
35 | select HAVE_KVM_IRQCHIP | 35 | select HAVE_KVM_IRQCHIP |
36 | select HAVE_KVM_IRQ_ROUTING | 36 | select HAVE_KVM_IRQ_ROUTING |
37 | select HAVE_KVM_MSI | ||
37 | depends on ARM_VIRT_EXT && ARM_LPAE && ARM_ARCH_TIMER | 38 | depends on ARM_VIRT_EXT && ARM_LPAE && ARM_ARCH_TIMER |
38 | ---help--- | 39 | ---help--- |
39 | Support hosting virtualized guest machines. | 40 | Support hosting virtualized guest machines. |
diff --git a/arch/arm/kvm/Makefile b/arch/arm/kvm/Makefile index f19842ea5418..d571243ab4d1 100644 --- a/arch/arm/kvm/Makefile +++ b/arch/arm/kvm/Makefile | |||
@@ -32,5 +32,6 @@ obj-y += $(KVM)/arm/vgic/vgic-mmio.o | |||
32 | obj-y += $(KVM)/arm/vgic/vgic-mmio-v2.o | 32 | obj-y += $(KVM)/arm/vgic/vgic-mmio-v2.o |
33 | obj-y += $(KVM)/arm/vgic/vgic-mmio-v3.o | 33 | obj-y += $(KVM)/arm/vgic/vgic-mmio-v3.o |
34 | obj-y += $(KVM)/arm/vgic/vgic-kvm-device.o | 34 | obj-y += $(KVM)/arm/vgic/vgic-kvm-device.o |
35 | obj-y += $(KVM)/arm/vgic/vgic-its.o | ||
35 | obj-y += $(KVM)/irqchip.o | 36 | obj-y += $(KVM)/irqchip.o |
36 | obj-y += $(KVM)/arm/arch_timer.o | 37 | obj-y += $(KVM)/arm/arch_timer.o |
diff --git a/arch/arm/kvm/arm.c b/arch/arm/kvm/arm.c index 19b5f5c1c0ff..8f92efa8460e 100644 --- a/arch/arm/kvm/arm.c +++ b/arch/arm/kvm/arm.c | |||
@@ -221,6 +221,12 @@ int kvm_vm_ioctl_check_extension(struct kvm *kvm, long ext) | |||
221 | case KVM_CAP_MAX_VCPUS: | 221 | case KVM_CAP_MAX_VCPUS: |
222 | r = KVM_MAX_VCPUS; | 222 | r = KVM_MAX_VCPUS; |
223 | break; | 223 | break; |
224 | case KVM_CAP_MSI_DEVID: | ||
225 | if (!kvm) | ||
226 | r = -EINVAL; | ||
227 | else | ||
228 | r = kvm->arch.vgic.msis_require_devid; | ||
229 | break; | ||
224 | default: | 230 | default: |
225 | r = kvm_arch_dev_ioctl_check_extension(kvm, ext); | 231 | r = kvm_arch_dev_ioctl_check_extension(kvm, ext); |
226 | break; | 232 | break; |
diff --git a/arch/arm64/kvm/Kconfig b/arch/arm64/kvm/Kconfig index 6eaf12c1d627..52cb7ad9b2fd 100644 --- a/arch/arm64/kvm/Kconfig +++ b/arch/arm64/kvm/Kconfig | |||
@@ -16,9 +16,6 @@ menuconfig VIRTUALIZATION | |||
16 | 16 | ||
17 | if VIRTUALIZATION | 17 | if VIRTUALIZATION |
18 | 18 | ||
19 | config KVM_ARM_VGIC_V3_ITS | ||
20 | bool | ||
21 | |||
22 | config KVM | 19 | config KVM |
23 | bool "Kernel-based Virtual Machine (KVM) support" | 20 | bool "Kernel-based Virtual Machine (KVM) support" |
24 | depends on OF | 21 | depends on OF |
@@ -34,7 +31,6 @@ config KVM | |||
34 | select KVM_VFIO | 31 | select KVM_VFIO |
35 | select HAVE_KVM_EVENTFD | 32 | select HAVE_KVM_EVENTFD |
36 | select HAVE_KVM_IRQFD | 33 | select HAVE_KVM_IRQFD |
37 | select KVM_ARM_VGIC_V3_ITS | ||
38 | select KVM_ARM_PMU if HW_PERF_EVENTS | 34 | select KVM_ARM_PMU if HW_PERF_EVENTS |
39 | select HAVE_KVM_MSI | 35 | select HAVE_KVM_MSI |
40 | select HAVE_KVM_IRQCHIP | 36 | select HAVE_KVM_IRQCHIP |
diff --git a/arch/arm64/kvm/reset.c b/arch/arm64/kvm/reset.c index 5bc460884639..e95d4f68bf54 100644 --- a/arch/arm64/kvm/reset.c +++ b/arch/arm64/kvm/reset.c | |||
@@ -86,12 +86,6 @@ int kvm_arch_dev_ioctl_check_extension(struct kvm *kvm, long ext) | |||
86 | case KVM_CAP_VCPU_ATTRIBUTES: | 86 | case KVM_CAP_VCPU_ATTRIBUTES: |
87 | r = 1; | 87 | r = 1; |
88 | break; | 88 | break; |
89 | case KVM_CAP_MSI_DEVID: | ||
90 | if (!kvm) | ||
91 | r = -EINVAL; | ||
92 | else | ||
93 | r = kvm->arch.vgic.msis_require_devid; | ||
94 | break; | ||
95 | default: | 89 | default: |
96 | r = 0; | 90 | r = 0; |
97 | } | 91 | } |
diff --git a/virt/kvm/arm/vgic/vgic-kvm-device.c b/virt/kvm/arm/vgic/vgic-kvm-device.c index ce1f4ed9daf4..fbe87a63d250 100644 --- a/virt/kvm/arm/vgic/vgic-kvm-device.c +++ b/virt/kvm/arm/vgic/vgic-kvm-device.c | |||
@@ -221,11 +221,9 @@ int kvm_register_vgic_device(unsigned long type) | |||
221 | ret = kvm_register_device_ops(&kvm_arm_vgic_v3_ops, | 221 | ret = kvm_register_device_ops(&kvm_arm_vgic_v3_ops, |
222 | KVM_DEV_TYPE_ARM_VGIC_V3); | 222 | KVM_DEV_TYPE_ARM_VGIC_V3); |
223 | 223 | ||
224 | #ifdef CONFIG_KVM_ARM_VGIC_V3_ITS | ||
225 | if (ret) | 224 | if (ret) |
226 | break; | 225 | break; |
227 | ret = kvm_vgic_register_its_device(); | 226 | ret = kvm_vgic_register_its_device(); |
228 | #endif | ||
229 | break; | 227 | break; |
230 | } | 228 | } |
231 | 229 | ||
diff --git a/virt/kvm/arm/vgic/vgic-mmio-v3.c b/virt/kvm/arm/vgic/vgic-mmio-v3.c index 0d3c76a4208b..50f42f0f8c4f 100644 --- a/virt/kvm/arm/vgic/vgic-mmio-v3.c +++ b/virt/kvm/arm/vgic/vgic-mmio-v3.c | |||
@@ -42,7 +42,6 @@ u64 update_64bit_reg(u64 reg, unsigned int offset, unsigned int len, | |||
42 | return reg | ((u64)val << lower); | 42 | return reg | ((u64)val << lower); |
43 | } | 43 | } |
44 | 44 | ||
45 | #ifdef CONFIG_KVM_ARM_VGIC_V3_ITS | ||
46 | bool vgic_has_its(struct kvm *kvm) | 45 | bool vgic_has_its(struct kvm *kvm) |
47 | { | 46 | { |
48 | struct vgic_dist *dist = &kvm->arch.vgic; | 47 | struct vgic_dist *dist = &kvm->arch.vgic; |
@@ -52,7 +51,6 @@ bool vgic_has_its(struct kvm *kvm) | |||
52 | 51 | ||
53 | return dist->has_its; | 52 | return dist->has_its; |
54 | } | 53 | } |
55 | #endif | ||
56 | 54 | ||
57 | static unsigned long vgic_mmio_read_v3_misc(struct kvm_vcpu *vcpu, | 55 | static unsigned long vgic_mmio_read_v3_misc(struct kvm_vcpu *vcpu, |
58 | gpa_t addr, unsigned int len) | 56 | gpa_t addr, unsigned int len) |
diff --git a/virt/kvm/arm/vgic/vgic.h b/virt/kvm/arm/vgic/vgic.h index 9d9e014765a2..859f65c6e056 100644 --- a/virt/kvm/arm/vgic/vgic.h +++ b/virt/kvm/arm/vgic/vgic.h | |||
@@ -84,37 +84,11 @@ int vgic_v3_probe(const struct gic_kvm_info *info); | |||
84 | int vgic_v3_map_resources(struct kvm *kvm); | 84 | int vgic_v3_map_resources(struct kvm *kvm); |
85 | int vgic_register_redist_iodevs(struct kvm *kvm, gpa_t dist_base_address); | 85 | int vgic_register_redist_iodevs(struct kvm *kvm, gpa_t dist_base_address); |
86 | 86 | ||
87 | #ifdef CONFIG_KVM_ARM_VGIC_V3_ITS | ||
88 | int vgic_register_its_iodevs(struct kvm *kvm); | 87 | int vgic_register_its_iodevs(struct kvm *kvm); |
89 | bool vgic_has_its(struct kvm *kvm); | 88 | bool vgic_has_its(struct kvm *kvm); |
90 | int kvm_vgic_register_its_device(void); | 89 | int kvm_vgic_register_its_device(void); |
91 | void vgic_enable_lpis(struct kvm_vcpu *vcpu); | 90 | void vgic_enable_lpis(struct kvm_vcpu *vcpu); |
92 | int vgic_its_inject_msi(struct kvm *kvm, struct kvm_msi *msi); | 91 | int vgic_its_inject_msi(struct kvm *kvm, struct kvm_msi *msi); |
93 | #else | ||
94 | static inline int vgic_register_its_iodevs(struct kvm *kvm) | ||
95 | { | ||
96 | return -ENODEV; | ||
97 | } | ||
98 | |||
99 | static inline bool vgic_has_its(struct kvm *kvm) | ||
100 | { | ||
101 | return false; | ||
102 | } | ||
103 | |||
104 | static inline int kvm_vgic_register_its_device(void) | ||
105 | { | ||
106 | return -ENODEV; | ||
107 | } | ||
108 | |||
109 | static inline void vgic_enable_lpis(struct kvm_vcpu *vcpu) | ||
110 | { | ||
111 | } | ||
112 | |||
113 | static inline int vgic_its_inject_msi(struct kvm *kvm, struct kvm_msi *msi) | ||
114 | { | ||
115 | return -ENODEV; | ||
116 | } | ||
117 | #endif | ||
118 | 92 | ||
119 | int kvm_register_vgic_device(unsigned long type); | 93 | int kvm_register_vgic_device(unsigned long type); |
120 | int vgic_lazy_init(struct kvm *kvm); | 94 | int vgic_lazy_init(struct kvm *kvm); |