diff options
| author | Vladimir Murzin <vladimir.murzin@arm.com> | 2016-09-12 10:49:24 -0400 |
|---|---|---|
| committer | Christoffer Dall <christoffer.dall@linaro.org> | 2016-09-22 07:22:21 -0400 |
| commit | acda5430bee4621f218391d0bcfbe4412adb3554 (patch) | |
| tree | d279ce897d2666ca9481963dca9fc9aede6e85dd /virt/kvm | |
| parent | a078bedf17c2e43819fea54bdfd5793845142e3a (diff) | |
ARM: KVM: Support vgic-v3
This patch allows to build and use vgic-v3 in 32-bit mode.
Unfortunately, it can not be split in several steps without extra
stubs to keep patches independent and bisectable. For instance,
virt/kvm/arm/vgic/vgic-v3.c uses function from vgic-v3-sr.c, handling
access to GICv3 cpu interface from the guest requires vgic_v3.vgic_sre
to be already defined.
It is how support has been done:
* handle SGI requests from the guest
* report configured SRE on access to GICv3 cpu interface from the guest
* required vgic-v3 macros are provided via uapi.h
* static keys are used to select GIC backend
* to make vgic-v3 build KVM_ARM_VGIC_V3 guard is removed along with
the static inlines
Acked-by: Marc Zyngier <marc.zyngier@arm.com>
Reviewed-by: Christoffer Dall <christoffer.dall@linaro.org>
Signed-off-by: Vladimir Murzin <vladimir.murzin@arm.com>
Signed-off-by: Christoffer Dall <christoffer.dall@linaro.org>
Diffstat (limited to 'virt/kvm')
| -rw-r--r-- | virt/kvm/arm/vgic/vgic-kvm-device.c | 8 | ||||
| -rw-r--r-- | virt/kvm/arm/vgic/vgic-mmio.c | 2 | ||||
| -rw-r--r-- | virt/kvm/arm/vgic/vgic-mmio.h | 2 | ||||
| -rw-r--r-- | virt/kvm/arm/vgic/vgic.h | 54 |
4 files changed, 0 insertions, 66 deletions
diff --git a/virt/kvm/arm/vgic/vgic-kvm-device.c b/virt/kvm/arm/vgic/vgic-kvm-device.c index 89ef9bcc6de6..ce1f4ed9daf4 100644 --- a/virt/kvm/arm/vgic/vgic-kvm-device.c +++ b/virt/kvm/arm/vgic/vgic-kvm-device.c | |||
| @@ -71,7 +71,6 @@ int kvm_vgic_addr(struct kvm *kvm, unsigned long type, u64 *addr, bool write) | |||
| 71 | addr_ptr = &vgic->vgic_cpu_base; | 71 | addr_ptr = &vgic->vgic_cpu_base; |
| 72 | alignment = SZ_4K; | 72 | alignment = SZ_4K; |
| 73 | break; | 73 | break; |
| 74 | #ifdef CONFIG_KVM_ARM_VGIC_V3 | ||
| 75 | case KVM_VGIC_V3_ADDR_TYPE_DIST: | 74 | case KVM_VGIC_V3_ADDR_TYPE_DIST: |
| 76 | type_needed = KVM_DEV_TYPE_ARM_VGIC_V3; | 75 | type_needed = KVM_DEV_TYPE_ARM_VGIC_V3; |
| 77 | addr_ptr = &vgic->vgic_dist_base; | 76 | addr_ptr = &vgic->vgic_dist_base; |
| @@ -82,7 +81,6 @@ int kvm_vgic_addr(struct kvm *kvm, unsigned long type, u64 *addr, bool write) | |||
| 82 | addr_ptr = &vgic->vgic_redist_base; | 81 | addr_ptr = &vgic->vgic_redist_base; |
| 83 | alignment = SZ_64K; | 82 | alignment = SZ_64K; |
| 84 | break; | 83 | break; |
| 85 | #endif | ||
| 86 | default: | 84 | default: |
| 87 | r = -ENODEV; | 85 | r = -ENODEV; |
| 88 | goto out; | 86 | goto out; |
| @@ -219,7 +217,6 @@ int kvm_register_vgic_device(unsigned long type) | |||
| 219 | ret = kvm_register_device_ops(&kvm_arm_vgic_v2_ops, | 217 | ret = kvm_register_device_ops(&kvm_arm_vgic_v2_ops, |
| 220 | KVM_DEV_TYPE_ARM_VGIC_V2); | 218 | KVM_DEV_TYPE_ARM_VGIC_V2); |
| 221 | break; | 219 | break; |
| 222 | #ifdef CONFIG_KVM_ARM_VGIC_V3 | ||
| 223 | case KVM_DEV_TYPE_ARM_VGIC_V3: | 220 | case KVM_DEV_TYPE_ARM_VGIC_V3: |
| 224 | ret = kvm_register_device_ops(&kvm_arm_vgic_v3_ops, | 221 | ret = kvm_register_device_ops(&kvm_arm_vgic_v3_ops, |
| 225 | KVM_DEV_TYPE_ARM_VGIC_V3); | 222 | KVM_DEV_TYPE_ARM_VGIC_V3); |
| @@ -230,7 +227,6 @@ int kvm_register_vgic_device(unsigned long type) | |||
| 230 | ret = kvm_vgic_register_its_device(); | 227 | ret = kvm_vgic_register_its_device(); |
| 231 | #endif | 228 | #endif |
| 232 | break; | 229 | break; |
| 233 | #endif | ||
| 234 | } | 230 | } |
| 235 | 231 | ||
| 236 | return ret; | 232 | return ret; |
| @@ -434,8 +430,6 @@ struct kvm_device_ops kvm_arm_vgic_v2_ops = { | |||
| 434 | .has_attr = vgic_v2_has_attr, | 430 | .has_attr = vgic_v2_has_attr, |
| 435 | }; | 431 | }; |
| 436 | 432 | ||
| 437 | #ifdef CONFIG_KVM_ARM_VGIC_V3 | ||
| 438 | |||
| 439 | static int vgic_v3_set_attr(struct kvm_device *dev, | 433 | static int vgic_v3_set_attr(struct kvm_device *dev, |
| 440 | struct kvm_device_attr *attr) | 434 | struct kvm_device_attr *attr) |
| 441 | { | 435 | { |
| @@ -478,5 +472,3 @@ struct kvm_device_ops kvm_arm_vgic_v3_ops = { | |||
| 478 | .get_attr = vgic_v3_get_attr, | 472 | .get_attr = vgic_v3_get_attr, |
| 479 | .has_attr = vgic_v3_has_attr, | 473 | .has_attr = vgic_v3_has_attr, |
| 480 | }; | 474 | }; |
| 481 | |||
| 482 | #endif /* CONFIG_KVM_ARM_VGIC_V3 */ | ||
diff --git a/virt/kvm/arm/vgic/vgic-mmio.c b/virt/kvm/arm/vgic/vgic-mmio.c index 3bad3c5ed431..e18b30ddcdce 100644 --- a/virt/kvm/arm/vgic/vgic-mmio.c +++ b/virt/kvm/arm/vgic/vgic-mmio.c | |||
| @@ -550,11 +550,9 @@ int vgic_register_dist_iodev(struct kvm *kvm, gpa_t dist_base_address, | |||
| 550 | case VGIC_V2: | 550 | case VGIC_V2: |
| 551 | len = vgic_v2_init_dist_iodev(io_device); | 551 | len = vgic_v2_init_dist_iodev(io_device); |
| 552 | break; | 552 | break; |
| 553 | #ifdef CONFIG_KVM_ARM_VGIC_V3 | ||
| 554 | case VGIC_V3: | 553 | case VGIC_V3: |
| 555 | len = vgic_v3_init_dist_iodev(io_device); | 554 | len = vgic_v3_init_dist_iodev(io_device); |
| 556 | break; | 555 | break; |
| 557 | #endif | ||
| 558 | default: | 556 | default: |
| 559 | BUG_ON(1); | 557 | BUG_ON(1); |
| 560 | } | 558 | } |
diff --git a/virt/kvm/arm/vgic/vgic-mmio.h b/virt/kvm/arm/vgic/vgic-mmio.h index 80f92ceadef2..4c34d39d44a0 100644 --- a/virt/kvm/arm/vgic/vgic-mmio.h +++ b/virt/kvm/arm/vgic/vgic-mmio.h | |||
| @@ -162,12 +162,10 @@ unsigned int vgic_v2_init_dist_iodev(struct vgic_io_device *dev); | |||
| 162 | 162 | ||
| 163 | unsigned int vgic_v3_init_dist_iodev(struct vgic_io_device *dev); | 163 | unsigned int vgic_v3_init_dist_iodev(struct vgic_io_device *dev); |
| 164 | 164 | ||
| 165 | #ifdef CONFIG_KVM_ARM_VGIC_V3 | ||
| 166 | u64 vgic_sanitise_outer_cacheability(u64 reg); | 165 | u64 vgic_sanitise_outer_cacheability(u64 reg); |
| 167 | u64 vgic_sanitise_inner_cacheability(u64 reg); | 166 | u64 vgic_sanitise_inner_cacheability(u64 reg); |
| 168 | u64 vgic_sanitise_shareability(u64 reg); | 167 | u64 vgic_sanitise_shareability(u64 reg); |
| 169 | u64 vgic_sanitise_field(u64 reg, u64 field_mask, int field_shift, | 168 | u64 vgic_sanitise_field(u64 reg, u64 field_mask, int field_shift, |
| 170 | u64 (*sanitise_fn)(u64)); | 169 | u64 (*sanitise_fn)(u64)); |
| 171 | #endif | ||
| 172 | 170 | ||
| 173 | #endif | 171 | #endif |
diff --git a/virt/kvm/arm/vgic/vgic.h b/virt/kvm/arm/vgic/vgic.h index 100045f3d98a..9d9e014765a2 100644 --- a/virt/kvm/arm/vgic/vgic.h +++ b/virt/kvm/arm/vgic/vgic.h | |||
| @@ -72,7 +72,6 @@ static inline void vgic_get_irq_kref(struct vgic_irq *irq) | |||
| 72 | kref_get(&irq->refcount); | 72 | kref_get(&irq->refcount); |
| 73 | } | 73 | } |
| 74 | 74 | ||
| 75 | #ifdef CONFIG_KVM_ARM_VGIC_V3 | ||
| 76 | void vgic_v3_process_maintenance(struct kvm_vcpu *vcpu); | 75 | void vgic_v3_process_maintenance(struct kvm_vcpu *vcpu); |
| 77 | void vgic_v3_fold_lr_state(struct kvm_vcpu *vcpu); | 76 | void vgic_v3_fold_lr_state(struct kvm_vcpu *vcpu); |
| 78 | void vgic_v3_populate_lr(struct kvm_vcpu *vcpu, struct vgic_irq *irq, int lr); | 77 | void vgic_v3_populate_lr(struct kvm_vcpu *vcpu, struct vgic_irq *irq, int lr); |
| @@ -91,60 +90,7 @@ bool vgic_has_its(struct kvm *kvm); | |||
| 91 | int kvm_vgic_register_its_device(void); | 90 | int kvm_vgic_register_its_device(void); |
| 92 | void vgic_enable_lpis(struct kvm_vcpu *vcpu); | 91 | void vgic_enable_lpis(struct kvm_vcpu *vcpu); |
| 93 | int vgic_its_inject_msi(struct kvm *kvm, struct kvm_msi *msi); | 92 | int vgic_its_inject_msi(struct kvm *kvm, struct kvm_msi *msi); |
| 94 | #endif | ||
| 95 | |||
| 96 | #else | 93 | #else |
| 97 | static inline void vgic_v3_process_maintenance(struct kvm_vcpu *vcpu) | ||
| 98 | { | ||
| 99 | } | ||
| 100 | |||
| 101 | static inline void vgic_v3_fold_lr_state(struct kvm_vcpu *vcpu) | ||
| 102 | { | ||
| 103 | } | ||
| 104 | |||
| 105 | static inline void vgic_v3_populate_lr(struct kvm_vcpu *vcpu, | ||
| 106 | struct vgic_irq *irq, int lr) | ||
| 107 | { | ||
| 108 | } | ||
| 109 | |||
| 110 | static inline void vgic_v3_clear_lr(struct kvm_vcpu *vcpu, int lr) | ||
| 111 | { | ||
| 112 | } | ||
| 113 | |||
| 114 | static inline void vgic_v3_set_underflow(struct kvm_vcpu *vcpu) | ||
| 115 | { | ||
| 116 | } | ||
| 117 | |||
| 118 | static inline | ||
| 119 | void vgic_v3_set_vmcr(struct kvm_vcpu *vcpu, struct vgic_vmcr *vmcr) | ||
| 120 | { | ||
| 121 | } | ||
| 122 | |||
| 123 | static inline | ||
| 124 | void vgic_v3_get_vmcr(struct kvm_vcpu *vcpu, struct vgic_vmcr *vmcr) | ||
| 125 | { | ||
| 126 | } | ||
| 127 | |||
| 128 | static inline void vgic_v3_enable(struct kvm_vcpu *vcpu) | ||
| 129 | { | ||
| 130 | } | ||
| 131 | |||
| 132 | static inline int vgic_v3_probe(const struct gic_kvm_info *info) | ||
| 133 | { | ||
| 134 | return -ENODEV; | ||
| 135 | } | ||
| 136 | |||
| 137 | static inline int vgic_v3_map_resources(struct kvm *kvm) | ||
| 138 | { | ||
| 139 | return -ENODEV; | ||
| 140 | } | ||
| 141 | |||
| 142 | static inline int vgic_register_redist_iodevs(struct kvm *kvm, | ||
| 143 | gpa_t dist_base_address) | ||
| 144 | { | ||
| 145 | return -ENODEV; | ||
| 146 | } | ||
| 147 | |||
| 148 | static inline int vgic_register_its_iodevs(struct kvm *kvm) | 94 | static inline int vgic_register_its_iodevs(struct kvm *kvm) |
| 149 | { | 95 | { |
| 150 | return -ENODEV; | 96 | return -ENODEV; |
