forked from torvalds/linux
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge tag 'for-linus' of git://git.kernel.org/pub/scm/virt/kvm/kvm
Pull kvm fixes from Paolo Bonzini: "More x86 fixes: - Logic bugs in CR0 writes and Hyper-V hypercalls - Don't use Enlightened MSR Bitmap for L3 - Remove user-triggerable WARN Plus a few selftest fixes and a regression test for the user-triggerable WARN" * tag 'for-linus' of git://git.kernel.org/pub/scm/virt/kvm/kvm: selftests: KVM: Add test to verify KVM doesn't explode on "bad" I/O KVM: x86: Don't WARN if userspace mucks with RCX during string I/O exit KVM: X86: Raise #GP when clearing CR0_PG in 64 bit mode selftests: KVM: avoid failures due to reserved HyperTransport region KVM: x86: Ignore sparse banks size for an "all CPUs", non-sparse IPI req KVM: x86: Wait for IPIs to be delivered when handling Hyper-V TLB flush hypercall KVM: x86: selftests: svm_int_ctl_test: fix intercept calculation KVM: nVMX: Don't use Enlightened MSR Bitmap for L3
- Loading branch information
Showing
11 changed files
with
223 additions
and
17 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,114 @@ | ||
// SPDX-License-Identifier: GPL-2.0 | ||
#include <fcntl.h> | ||
#include <stdio.h> | ||
#include <stdlib.h> | ||
#include <string.h> | ||
#include <sys/ioctl.h> | ||
|
||
#include "test_util.h" | ||
|
||
#include "kvm_util.h" | ||
#include "processor.h" | ||
|
||
#define VCPU_ID 1 | ||
|
||
static void guest_ins_port80(uint8_t *buffer, unsigned int count) | ||
{ | ||
unsigned long end; | ||
|
||
if (count == 2) | ||
end = (unsigned long)buffer + 1; | ||
else | ||
end = (unsigned long)buffer + 8192; | ||
|
||
asm volatile("cld; rep; insb" : "+D"(buffer), "+c"(count) : "d"(0x80) : "memory"); | ||
GUEST_ASSERT_1(count == 0, count); | ||
GUEST_ASSERT_2((unsigned long)buffer == end, buffer, end); | ||
} | ||
|
||
static void guest_code(void) | ||
{ | ||
uint8_t buffer[8192]; | ||
int i; | ||
|
||
/* | ||
* Special case tests. main() will adjust RCX 2 => 1 and 3 => 8192 to | ||
* test that KVM doesn't explode when userspace modifies the "count" on | ||
* a userspace I/O exit. KVM isn't required to play nice with the I/O | ||
* itself as KVM doesn't support manipulating the count, it just needs | ||
* to not explode or overflow a buffer. | ||
*/ | ||
guest_ins_port80(buffer, 2); | ||
guest_ins_port80(buffer, 3); | ||
|
||
/* Verify KVM fills the buffer correctly when not stuffing RCX. */ | ||
memset(buffer, 0, sizeof(buffer)); | ||
guest_ins_port80(buffer, 8192); | ||
for (i = 0; i < 8192; i++) | ||
GUEST_ASSERT_2(buffer[i] == 0xaa, i, buffer[i]); | ||
|
||
GUEST_DONE(); | ||
} | ||
|
||
int main(int argc, char *argv[]) | ||
{ | ||
struct kvm_regs regs; | ||
struct kvm_run *run; | ||
struct kvm_vm *vm; | ||
struct ucall uc; | ||
int rc; | ||
|
||
/* Tell stdout not to buffer its content */ | ||
setbuf(stdout, NULL); | ||
|
||
/* Create VM */ | ||
vm = vm_create_default(VCPU_ID, 0, guest_code); | ||
run = vcpu_state(vm, VCPU_ID); | ||
|
||
memset(®s, 0, sizeof(regs)); | ||
|
||
while (1) { | ||
rc = _vcpu_run(vm, VCPU_ID); | ||
|
||
TEST_ASSERT(rc == 0, "vcpu_run failed: %d\n", rc); | ||
TEST_ASSERT(run->exit_reason == KVM_EXIT_IO, | ||
"Unexpected exit reason: %u (%s),\n", | ||
run->exit_reason, | ||
exit_reason_str(run->exit_reason)); | ||
|
||
if (get_ucall(vm, VCPU_ID, &uc)) | ||
break; | ||
|
||
TEST_ASSERT(run->io.port == 0x80, | ||
"Expected I/O at port 0x80, got port 0x%x\n", run->io.port); | ||
|
||
/* | ||
* Modify the rep string count in RCX: 2 => 1 and 3 => 8192. | ||
* Note, this abuses KVM's batching of rep string I/O to avoid | ||
* getting stuck in an infinite loop. That behavior isn't in | ||
* scope from a testing perspective as it's not ABI in any way, | ||
* i.e. it really is abusing internal KVM knowledge. | ||
*/ | ||
vcpu_regs_get(vm, VCPU_ID, ®s); | ||
if (regs.rcx == 2) | ||
regs.rcx = 1; | ||
if (regs.rcx == 3) | ||
regs.rcx = 8192; | ||
memset((void *)run + run->io.data_offset, 0xaa, 4096); | ||
vcpu_regs_set(vm, VCPU_ID, ®s); | ||
} | ||
|
||
switch (uc.cmd) { | ||
case UCALL_DONE: | ||
break; | ||
case UCALL_ABORT: | ||
TEST_FAIL("%s at %s:%ld : argN+1 = 0x%lx, argN+2 = 0x%lx", | ||
(const char *)uc.args[0], __FILE__, uc.args[1], | ||
uc.args[2], uc.args[3]); | ||
default: | ||
TEST_FAIL("Unknown ucall %lu", uc.cmd); | ||
} | ||
|
||
kvm_vm_free(vm); | ||
return 0; | ||
} |