lkml.org 
[lkml]   [2022]   [Jun]   [2]   [last100]   RSS Feed
Views: [wrap][no wrap]   [headers]  [forward] 
 
Messages in this thread
    Patch in this message
    /
    Date
    Subject[PATCH v2 107/144] KVM: selftests: Convert steal_time away from VCPU_ID
    From
    Convert steal_time to use vm_create_with_vcpus() and pass around a
    'struct kvm_vcpu' object instead of requiring that the index into the
    array of vCPUs for a given vCPU is also the ID of the vCPU.

    Signed-off-by: Sean Christopherson <seanjc@google.com>
    ---
    tools/testing/selftests/kvm/steal_time.c | 123 ++++++++++++-----------
    1 file changed, 62 insertions(+), 61 deletions(-)

    diff --git a/tools/testing/selftests/kvm/steal_time.c b/tools/testing/selftests/kvm/steal_time.c
    index fd3533582509..7a6645464925 100644
    --- a/tools/testing/selftests/kvm/steal_time.c
    +++ b/tools/testing/selftests/kvm/steal_time.c
    @@ -58,36 +58,34 @@ static void guest_code(int cpu)
    GUEST_DONE();
    }

    -static void steal_time_init(struct kvm_vm *vm)
    +static bool is_steal_time_supported(struct kvm_vcpu *vcpu)
    {
    - int i;
    + struct kvm_cpuid_entry2 *cpuid = kvm_get_supported_cpuid_entry(KVM_CPUID_FEATURES);

    - if (!(kvm_get_supported_cpuid_entry(KVM_CPUID_FEATURES)->eax &
    - KVM_FEATURE_STEAL_TIME)) {
    - print_skip("steal-time not supported");
    - exit(KSFT_SKIP);
    - }
    + return cpuid && (cpuid->eax & KVM_FEATURE_STEAL_TIME);
    +}

    - for (i = 0; i < NR_VCPUS; ++i) {
    - int ret;
    +static void steal_time_init(struct kvm_vcpu *vcpu, uint32_t i)
    +{
    + int ret;

    - /* ST_GPA_BASE is identity mapped */
    - st_gva[i] = (void *)(ST_GPA_BASE + i * STEAL_TIME_SIZE);
    - sync_global_to_guest(vm, st_gva[i]);
    + /* ST_GPA_BASE is identity mapped */
    + st_gva[i] = (void *)(ST_GPA_BASE + i * STEAL_TIME_SIZE);
    + sync_global_to_guest(vcpu->vm, st_gva[i]);

    - ret = _vcpu_set_msr(vm, i, MSR_KVM_STEAL_TIME, (ulong)st_gva[i] | KVM_STEAL_RESERVED_MASK);
    - TEST_ASSERT(ret == 0, "Bad GPA didn't fail");
    + ret = _vcpu_set_msr(vcpu->vm, vcpu->id, MSR_KVM_STEAL_TIME,
    + (ulong)st_gva[i] | KVM_STEAL_RESERVED_MASK);
    + TEST_ASSERT(ret == 0, "Bad GPA didn't fail");

    - vcpu_set_msr(vm, i, MSR_KVM_STEAL_TIME, (ulong)st_gva[i] | KVM_MSR_ENABLED);
    - }
    + vcpu_set_msr(vcpu->vm, vcpu->id, MSR_KVM_STEAL_TIME, (ulong)st_gva[i] | KVM_MSR_ENABLED);
    }

    -static void steal_time_dump(struct kvm_vm *vm, uint32_t vcpuid)
    +static void steal_time_dump(struct kvm_vm *vm, uint32_t vcpu_idx)
    {
    - struct kvm_steal_time *st = addr_gva2hva(vm, (ulong)st_gva[vcpuid]);
    + struct kvm_steal_time *st = addr_gva2hva(vm, (ulong)st_gva[vcpu_idx]);
    int i;

    - pr_info("VCPU%d:\n", vcpuid);
    + pr_info("VCPU%d:\n", vcpu_idx);
    pr_info(" steal: %lld\n", st->steal);
    pr_info(" version: %d\n", st->version);
    pr_info(" flags: %d\n", st->flags);
    @@ -158,49 +156,50 @@ static void guest_code(int cpu)
    GUEST_DONE();
    }

    -static void steal_time_init(struct kvm_vm *vm)
    +static bool is_steal_time_supported(struct kvm_vcpu *vcpu)
    {
    struct kvm_device_attr dev = {
    .group = KVM_ARM_VCPU_PVTIME_CTRL,
    .attr = KVM_ARM_VCPU_PVTIME_IPA,
    };
    - int i, ret;

    - ret = __vcpu_ioctl(vm, 0, KVM_HAS_DEVICE_ATTR, &dev);
    - if (ret != 0 && errno == ENXIO) {
    - print_skip("steal-time not supported");
    - exit(KSFT_SKIP);
    - }
    -
    - for (i = 0; i < NR_VCPUS; ++i) {
    - uint64_t st_ipa;
    + return !__vcpu_ioctl(vcpu->vm, vcpu->id, KVM_HAS_DEVICE_ATTR, &dev);
    +}

    - vcpu_ioctl(vm, i, KVM_HAS_DEVICE_ATTR, &dev);
    +static void steal_time_init(struct kvm_vcpu *vcpu, uint32_t i)
    +{
    + struct kvm_vm *vm = vcpu->vm;
    + uint64_t st_ipa;
    + int ret;

    - dev.addr = (uint64_t)&st_ipa;
    + struct kvm_device_attr dev = {
    + .group = KVM_ARM_VCPU_PVTIME_CTRL,
    + .attr = KVM_ARM_VCPU_PVTIME_IPA,
    + .addr = (uint64_t)&st_ipa,
    + };

    - /* ST_GPA_BASE is identity mapped */
    - st_gva[i] = (void *)(ST_GPA_BASE + i * STEAL_TIME_SIZE);
    - sync_global_to_guest(vm, st_gva[i]);
    + vcpu_ioctl(vm, vcpu->id, KVM_HAS_DEVICE_ATTR, &dev);

    - st_ipa = (ulong)st_gva[i] | 1;
    - ret = __vcpu_ioctl(vm, i, KVM_SET_DEVICE_ATTR, &dev);
    - TEST_ASSERT(ret == -1 && errno == EINVAL, "Bad IPA didn't report EINVAL");
    + /* ST_GPA_BASE is identity mapped */
    + st_gva[i] = (void *)(ST_GPA_BASE + i * STEAL_TIME_SIZE);
    + sync_global_to_guest(vm, st_gva[i]);

    - st_ipa = (ulong)st_gva[i];
    - vcpu_ioctl(vm, i, KVM_SET_DEVICE_ATTR, &dev);
    + st_ipa = (ulong)st_gva[i] | 1;
    + ret = __vcpu_ioctl(vm, vcpu->id, KVM_SET_DEVICE_ATTR, &dev);
    + TEST_ASSERT(ret == -1 && errno == EINVAL, "Bad IPA didn't report EINVAL");

    - ret = __vcpu_ioctl(vm, i, KVM_SET_DEVICE_ATTR, &dev);
    - TEST_ASSERT(ret == -1 && errno == EEXIST, "Set IPA twice without EEXIST");
    + st_ipa = (ulong)st_gva[i];
    + vcpu_ioctl(vm, vcpu->id, KVM_SET_DEVICE_ATTR, &dev);

    - }
    + ret = __vcpu_ioctl(vm, vcpu->id, KVM_SET_DEVICE_ATTR, &dev);
    + TEST_ASSERT(ret == -1 && errno == EEXIST, "Set IPA twice without EEXIST");
    }

    -static void steal_time_dump(struct kvm_vm *vm, uint32_t vcpuid)
    +static void steal_time_dump(struct kvm_vm *vm, uint32_t vcpu_idx)
    {
    - struct st_time *st = addr_gva2hva(vm, (ulong)st_gva[vcpuid]);
    + struct st_time *st = addr_gva2hva(vm, (ulong)st_gva[vcpu_idx]);

    - pr_info("VCPU%d:\n", vcpuid);
    + pr_info("VCPU%d:\n", vcpu_idx);
    pr_info(" rev: %d\n", st->rev);
    pr_info(" attr: %d\n", st->attr);
    pr_info(" st_time: %ld\n", st->st_time);
    @@ -224,15 +223,13 @@ static void *do_steal_time(void *arg)
    return NULL;
    }

    -static void run_vcpu(struct kvm_vm *vm, uint32_t vcpuid)
    +static void run_vcpu(struct kvm_vcpu *vcpu)
    {
    struct ucall uc;

    - vcpu_args_set(vm, vcpuid, 1, vcpuid);
    + vcpu_run(vcpu->vm, vcpu->id);

    - vcpu_ioctl(vm, vcpuid, KVM_RUN, NULL);
    -
    - switch (get_ucall(vm, vcpuid, &uc)) {
    + switch (get_ucall(vcpu->vm, vcpu->id, &uc)) {
    case UCALL_SYNC:
    case UCALL_DONE:
    break;
    @@ -241,12 +238,13 @@ static void run_vcpu(struct kvm_vm *vm, uint32_t vcpuid)
    __FILE__, uc.args[1]);
    default:
    TEST_ASSERT(false, "Unexpected exit: %s",
    - exit_reason_str(vcpu_state(vm, vcpuid)->exit_reason));
    + exit_reason_str(vcpu->run->exit_reason));
    }
    }

    int main(int ac, char **av)
    {
    + struct kvm_vcpu *vcpus[NR_VCPUS];
    struct kvm_vm *vm;
    pthread_attr_t attr;
    pthread_t thread;
    @@ -266,26 +264,29 @@ int main(int ac, char **av)
    pthread_attr_setaffinity_np(&attr, sizeof(cpu_set_t), &cpuset);
    pthread_setaffinity_np(pthread_self(), sizeof(cpu_set_t), &cpuset);

    - /* Create a one VCPU guest and an identity mapped memslot for the steal time structure */
    - vm = vm_create_default(0, 0, guest_code);
    + /* Create a VM and an identity mapped memslot for the steal time structure */
    + vm = vm_create_with_vcpus(NR_VCPUS, guest_code, vcpus);
    gpages = vm_calc_num_guest_pages(VM_MODE_DEFAULT, STEAL_TIME_SIZE * NR_VCPUS);
    vm_userspace_mem_region_add(vm, VM_MEM_SRC_ANONYMOUS, ST_GPA_BASE, 1, gpages, 0);
    virt_map(vm, ST_GPA_BASE, ST_GPA_BASE, gpages);
    ucall_init(vm, NULL);

    - /* Add the rest of the VCPUs */
    - for (i = 1; i < NR_VCPUS; ++i)
    - vm_vcpu_add(vm, i, guest_code);
    -
    - steal_time_init(vm);
    + if (!is_steal_time_supported(vcpus[0])) {
    + print_skip("steal-time not supported");
    + exit(KSFT_SKIP);
    + }

    /* Run test on each VCPU */
    for (i = 0; i < NR_VCPUS; ++i) {
    + steal_time_init(vcpus[i], i);
    +
    + vcpu_args_set(vm, vcpus[i]->id, 1, i);
    +
    /* First VCPU run initializes steal-time */
    - run_vcpu(vm, i);
    + run_vcpu(vcpus[i]);

    /* Second VCPU run, expect guest stolen time to be <= run_delay */
    - run_vcpu(vm, i);
    + run_vcpu(vcpus[i]);
    sync_global_from_guest(vm, guest_stolen_time[i]);
    stolen_time = guest_stolen_time[i];
    run_delay = get_run_delay();
    @@ -306,7 +307,7 @@ int main(int ac, char **av)
    MIN_RUN_DELAY_NS, run_delay);

    /* Run VCPU again to confirm stolen time is consistent with run_delay */
    - run_vcpu(vm, i);
    + run_vcpu(vcpus[i]);
    sync_global_from_guest(vm, guest_stolen_time[i]);
    stolen_time = guest_stolen_time[i] - stolen_time;
    TEST_ASSERT(stolen_time >= run_delay,
    --
    2.36.1.255.ge46751e96f-goog
    \
     
     \ /
      Last update: 2022-06-03 02:58    [W:4.099 / U:0.644 seconds]
    ©2003-2020 Jasper Spaans|hosted at Digital Ocean and TransIP|Read the blog|Advertise on this site