Skip to content

Commit 2244782

Browse files
committed
Merge tag 'for-linus' of git://git.kernel.org/pub/scm/virt/kvm/kvm
Pull KVM fixes from Paolo Bonzini: "ARM fixes: - Another state update on exit to userspace fix - Prevent the creation of mixed 32/64 VMs - Fix regression with irqbypass not restarting the guest on failed connect - Fix regression with debug register decoding resulting in overlapping access - Commit exception state on exit to usrspace - Fix the MMU notifier return values - Add missing 'static' qualifiers in the new host stage-2 code x86 fixes: - fix guest missed wakeup with assigned devices - fix WARN reported by syzkaller - do not use BIT() in UAPI headers - make the kvm_amd.avic parameter bool PPC fixes: - make halt polling heuristics consistent with other architectures selftests: - various fixes - new performance selftest memslot_perf_test - test UFFD minor faults in demand_paging_test" * tag 'for-linus' of git://git.kernel.org/pub/scm/virt/kvm/kvm: (44 commits) selftests: kvm: fix overlapping addresses in memslot_perf_test KVM: X86: Kill off ctxt->ud KVM: X86: Fix warning caused by stale emulation context KVM: X86: Use kvm_get_linear_rip() in single-step and #DB/#BP interception KVM: x86/mmu: Fix comment mentioning skip_4k KVM: VMX: update vcpu posted-interrupt descriptor when assigning device KVM: rename KVM_REQ_PENDING_TIMER to KVM_REQ_UNBLOCK KVM: x86: add start_assignment hook to kvm_x86_ops KVM: LAPIC: Narrow the timer latency between wait_lapic_expire and world switch selftests: kvm: do only 1 memslot_perf_test run by default KVM: X86: Use _BITUL() macro in UAPI headers KVM: selftests: add shared hugetlbfs backing source type KVM: selftests: allow using UFFD minor faults for demand paging KVM: selftests: create alias mappings when using shared memory KVM: selftests: add shmem backing source type KVM: selftests: refactor vm_mem_backing_src_type flags KVM: selftests: allow different backing source types KVM: selftests: compute correct demand paging size KVM: selftests: simplify setup_demand_paging error handling KVM: selftests: Print a message if /dev/kvm is missing ...
2 parents 866c4b8 + 000ac42 commit 2244782

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

52 files changed

+1694
-287
lines changed

Documentation/virt/kvm/vcpu-requests.rst

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -118,10 +118,12 @@ KVM_REQ_MMU_RELOAD
118118
necessary to inform each VCPU to completely refresh the tables. This
119119
request is used for that.
120120

121-
KVM_REQ_PENDING_TIMER
121+
KVM_REQ_UNBLOCK
122122

123-
This request may be made from a timer handler run on the host on behalf
124-
of a VCPU. It informs the VCPU thread to inject a timer interrupt.
123+
This request informs the vCPU to exit kvm_vcpu_block. It is used for
124+
example from timer handlers that run on the host on behalf of a vCPU,
125+
or in order to update the interrupt routing and ensure that assigned
126+
devices will wake up the vCPU.
125127

126128
KVM_REQ_UNHALT
127129

arch/arm64/include/asm/kvm_asm.h

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,6 +63,7 @@
6363
#define __KVM_HOST_SMCCC_FUNC___pkvm_cpu_set_vector 18
6464
#define __KVM_HOST_SMCCC_FUNC___pkvm_prot_finalize 19
6565
#define __KVM_HOST_SMCCC_FUNC___pkvm_mark_hyp 20
66+
#define __KVM_HOST_SMCCC_FUNC___kvm_adjust_pc 21
6667

6768
#ifndef __ASSEMBLY__
6869

@@ -201,6 +202,8 @@ extern void __kvm_timer_set_cntvoff(u64 cntvoff);
201202

202203
extern int __kvm_vcpu_run(struct kvm_vcpu *vcpu);
203204

205+
extern void __kvm_adjust_pc(struct kvm_vcpu *vcpu);
206+
204207
extern u64 __vgic_v3_get_gic_config(void);
205208
extern u64 __vgic_v3_read_vmcr(void);
206209
extern void __vgic_v3_write_vmcr(u32 vmcr);

arch/arm64/include/asm/kvm_emulate.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -463,4 +463,9 @@ static __always_inline void kvm_incr_pc(struct kvm_vcpu *vcpu)
463463
vcpu->arch.flags |= KVM_ARM64_INCREMENT_PC;
464464
}
465465

466+
static inline bool vcpu_has_feature(struct kvm_vcpu *vcpu, int feature)
467+
{
468+
return test_bit(feature, vcpu->arch.features);
469+
}
470+
466471
#endif /* __ARM64_KVM_EMULATE_H__ */

arch/arm64/kvm/arm.c

Lines changed: 17 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -720,11 +720,13 @@ int kvm_arch_vcpu_ioctl_run(struct kvm_vcpu *vcpu)
720720
return ret;
721721
}
722722

723-
if (run->immediate_exit)
724-
return -EINTR;
725-
726723
vcpu_load(vcpu);
727724

725+
if (run->immediate_exit) {
726+
ret = -EINTR;
727+
goto out;
728+
}
729+
728730
kvm_sigset_activate(vcpu);
729731

730732
ret = 1;
@@ -897,6 +899,18 @@ int kvm_arch_vcpu_ioctl_run(struct kvm_vcpu *vcpu)
897899

898900
kvm_sigset_deactivate(vcpu);
899901

902+
out:
903+
/*
904+
* In the unlikely event that we are returning to userspace
905+
* with pending exceptions or PC adjustment, commit these
906+
* adjustments in order to give userspace a consistent view of
907+
* the vcpu state. Note that this relies on __kvm_adjust_pc()
908+
* being preempt-safe on VHE.
909+
*/
910+
if (unlikely(vcpu->arch.flags & (KVM_ARM64_PENDING_EXCEPTION |
911+
KVM_ARM64_INCREMENT_PC)))
912+
kvm_call_hyp(__kvm_adjust_pc, vcpu);
913+
900914
vcpu_put(vcpu);
901915
return ret;
902916
}

arch/arm64/kvm/hyp/exception.c

Lines changed: 17 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -296,7 +296,7 @@ static void enter_exception32(struct kvm_vcpu *vcpu, u32 mode, u32 vect_offset)
296296
*vcpu_pc(vcpu) = vect_offset;
297297
}
298298

299-
void kvm_inject_exception(struct kvm_vcpu *vcpu)
299+
static void kvm_inject_exception(struct kvm_vcpu *vcpu)
300300
{
301301
if (vcpu_el1_is_32bit(vcpu)) {
302302
switch (vcpu->arch.flags & KVM_ARM64_EXCEPT_MASK) {
@@ -329,3 +329,19 @@ void kvm_inject_exception(struct kvm_vcpu *vcpu)
329329
}
330330
}
331331
}
332+
333+
/*
334+
* Adjust the guest PC (and potentially exception state) depending on
335+
* flags provided by the emulation code.
336+
*/
337+
void __kvm_adjust_pc(struct kvm_vcpu *vcpu)
338+
{
339+
if (vcpu->arch.flags & KVM_ARM64_PENDING_EXCEPTION) {
340+
kvm_inject_exception(vcpu);
341+
vcpu->arch.flags &= ~(KVM_ARM64_PENDING_EXCEPTION |
342+
KVM_ARM64_EXCEPT_MASK);
343+
} else if (vcpu->arch.flags & KVM_ARM64_INCREMENT_PC) {
344+
kvm_skip_instr(vcpu);
345+
vcpu->arch.flags &= ~KVM_ARM64_INCREMENT_PC;
346+
}
347+
}

arch/arm64/kvm/hyp/include/hyp/adjust_pc.h

Lines changed: 0 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -13,8 +13,6 @@
1313
#include <asm/kvm_emulate.h>
1414
#include <asm/kvm_host.h>
1515

16-
void kvm_inject_exception(struct kvm_vcpu *vcpu);
17-
1816
static inline void kvm_skip_instr(struct kvm_vcpu *vcpu)
1917
{
2018
if (vcpu_mode_is_32bit(vcpu)) {
@@ -43,22 +41,6 @@ static inline void __kvm_skip_instr(struct kvm_vcpu *vcpu)
4341
write_sysreg_el2(*vcpu_pc(vcpu), SYS_ELR);
4442
}
4543

46-
/*
47-
* Adjust the guest PC on entry, depending on flags provided by EL1
48-
* for the purpose of emulation (MMIO, sysreg) or exception injection.
49-
*/
50-
static inline void __adjust_pc(struct kvm_vcpu *vcpu)
51-
{
52-
if (vcpu->arch.flags & KVM_ARM64_PENDING_EXCEPTION) {
53-
kvm_inject_exception(vcpu);
54-
vcpu->arch.flags &= ~(KVM_ARM64_PENDING_EXCEPTION |
55-
KVM_ARM64_EXCEPT_MASK);
56-
} else if (vcpu->arch.flags & KVM_ARM64_INCREMENT_PC) {
57-
kvm_skip_instr(vcpu);
58-
vcpu->arch.flags &= ~KVM_ARM64_INCREMENT_PC;
59-
}
60-
}
61-
6244
/*
6345
* Skip an instruction while host sysregs are live.
6446
* Assumes host is always 64-bit.

arch/arm64/kvm/hyp/nvhe/hyp-main.c

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,13 @@ static void handle___kvm_vcpu_run(struct kvm_cpu_context *host_ctxt)
2828
cpu_reg(host_ctxt, 1) = __kvm_vcpu_run(kern_hyp_va(vcpu));
2929
}
3030

31+
static void handle___kvm_adjust_pc(struct kvm_cpu_context *host_ctxt)
32+
{
33+
DECLARE_REG(struct kvm_vcpu *, vcpu, host_ctxt, 1);
34+
35+
__kvm_adjust_pc(kern_hyp_va(vcpu));
36+
}
37+
3138
static void handle___kvm_flush_vm_context(struct kvm_cpu_context *host_ctxt)
3239
{
3340
__kvm_flush_vm_context();
@@ -170,6 +177,7 @@ typedef void (*hcall_t)(struct kvm_cpu_context *);
170177

171178
static const hcall_t host_hcall[] = {
172179
HANDLE_FUNC(__kvm_vcpu_run),
180+
HANDLE_FUNC(__kvm_adjust_pc),
173181
HANDLE_FUNC(__kvm_flush_vm_context),
174182
HANDLE_FUNC(__kvm_tlb_flush_vmid_ipa),
175183
HANDLE_FUNC(__kvm_tlb_flush_vmid),

arch/arm64/kvm/hyp/nvhe/mem_protect.c

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -23,8 +23,8 @@
2323
extern unsigned long hyp_nr_cpus;
2424
struct host_kvm host_kvm;
2525

26-
struct hyp_pool host_s2_mem;
27-
struct hyp_pool host_s2_dev;
26+
static struct hyp_pool host_s2_mem;
27+
static struct hyp_pool host_s2_dev;
2828

2929
/*
3030
* Copies of the host's CPU features registers holding sanitized values.

arch/arm64/kvm/hyp/nvhe/setup.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@
1717
#include <nvhe/trap_handler.h>
1818

1919
struct hyp_pool hpool;
20-
struct kvm_pgtable_mm_ops pkvm_pgtable_mm_ops;
2120
unsigned long hyp_nr_cpus;
2221

2322
#define hyp_percpu_size ((unsigned long)__per_cpu_end - \
@@ -27,6 +26,7 @@ static void *vmemmap_base;
2726
static void *hyp_pgt_base;
2827
static void *host_s2_mem_pgt_base;
2928
static void *host_s2_dev_pgt_base;
29+
static struct kvm_pgtable_mm_ops pkvm_pgtable_mm_ops;
3030

3131
static int divide_memory_pool(void *virt, unsigned long size)
3232
{

arch/arm64/kvm/hyp/nvhe/switch.c

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,6 @@
44
* Author: Marc Zyngier <[email protected]>
55
*/
66

7-
#include <hyp/adjust_pc.h>
87
#include <hyp/switch.h>
98
#include <hyp/sysreg-sr.h>
109

@@ -201,7 +200,7 @@ int __kvm_vcpu_run(struct kvm_vcpu *vcpu)
201200
*/
202201
__debug_save_host_buffers_nvhe(vcpu);
203202

204-
__adjust_pc(vcpu);
203+
__kvm_adjust_pc(vcpu);
205204

206205
/*
207206
* We must restore the 32-bit state before the sysregs, thanks

0 commit comments

Comments
 (0)