From patchwork Fri Jan 21 15:58:53 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Aaron Lewis X-Patchwork-Id: 12719896 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 8D838C433FE for ; Fri, 21 Jan 2022 15:59:08 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1381725AbiAUP7I (ORCPT ); Fri, 21 Jan 2022 10:59:08 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36872 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1350816AbiAUP7H (ORCPT ); Fri, 21 Jan 2022 10:59:07 -0500 Received: from mail-pl1-x64a.google.com (mail-pl1-x64a.google.com [IPv6:2607:f8b0:4864:20::64a]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 1CAB6C06173B for ; Fri, 21 Jan 2022 07:59:07 -0800 (PST) Received: by mail-pl1-x64a.google.com with SMTP id p7-20020a1709026b8700b0014a8d8fbf6fso1704937plk.23 for ; Fri, 21 Jan 2022 07:59:07 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20210112; h=date:in-reply-to:message-id:mime-version:references:subject:from:to :cc; bh=OSc06xfKYUAuvW5ciiOedpL/kcEug72EnhuZ2g11vE4=; b=dzXKKZ19dnDIF5EhZCsiEvW+w2TAi3Qnub1rV0jyVX8FAXZD5mxzwsKOn+wm6f9xhF JXeGzMyVkzz1DTCS5sJIRDwuROBhvgCWroBG4YoFxNn7pcTxFtgsrdcmnTDoHv7+hxt0 XZg4w427lfDGbLQ4FZhzJDTVfP00AeV3/iclv5CVu1k3sIWveBlnXPF65lhHuFZ52YKz nmehgfAjy9indgffnXDm/4MnlsNIl5lo2as25pPuqh2E+MpU9szc4jLvJHigLbH1OjJf dm7lLKNHaU84YDlNhOK/tPJSlBPMFx6G1dnL6LDe/w82a8zWBaeapjgALWVuKBsbWTJe 1eNw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=x-gm-message-state:date:in-reply-to:message-id:mime-version :references:subject:from:to:cc; bh=OSc06xfKYUAuvW5ciiOedpL/kcEug72EnhuZ2g11vE4=; b=Tx1hEdqu4zkbE9JGHh74lJknRh1IwhQCsOhUD+lF+vOCgxJD4a9NwBCF4V+Bl4K39a piY67mI4KiR+4kiMNlF5UqHglsK4YwBN4slQmDcONa8C92Zmpkb2MPaQ+PFdQSQtiSQN x7JZBnxdBNV26d4nlcwmTKxx444wVxL2xDQh0/1WxPQJIKiCcUpOapPR7ky8wiKgqEEA Wr/tFnU6eXVQNjOKiSJjgn1Mc4C7947LR1J4qT0+C0Yixxryf4ZODk+WghY5u56XwSuU 2JgO6M07CBnqzTpW3r8WZ7meyXK/neSTBaSjcok+1ssQHw+olWiVWBfp2o5k912Kx0kR PH+w== X-Gm-Message-State: AOAM531SOkxzC3zV8obm9zk+WnlIcw0kpFickxQxk2ifa6Q+lEk/aBMv jmu7egNOJ0HuI4rm05huw2UwPnPf6Ii8kN8tbRny0gy5VurQG+afxBx5rozS26Lo/PY7FO9Qojq mIohQ+1V8gGTLyux/aECEsxfj+NC6/L8l/qWRLJQmuOHEXzOnrxZc76MAFxYo2POJMGxD X-Google-Smtp-Source: ABdhPJztK1kLgxC283f6p6V3YtiiwBIyh5BEfKy3ApQx23vaJek6n9BHHKRpoxWSHHWejPjchhpiU6iorbAw4Yig X-Received: from aaronlewis.c.googlers.com ([fda3:e722:ac3:cc00:7f:e700:c0a8:2675]) (user=aaronlewis job=sendgmr) by 2002:a17:903:41cf:b0:14b:5b0:484b with SMTP id u15-20020a17090341cf00b0014b05b0484bmr4633550ple.155.1642780746495; Fri, 21 Jan 2022 07:59:06 -0800 (PST) Date: Fri, 21 Jan 2022 15:58:53 +0000 In-Reply-To: <20220121155855.213852-1-aaronlewis@google.com> Message-Id: <20220121155855.213852-2-aaronlewis@google.com> Mime-Version: 1.0 References: <20220121155855.213852-1-aaronlewis@google.com> X-Mailer: git-send-email 2.35.0.rc0.227.g00780c9af4-goog Subject: [kvm-unit-tests PATCH v4 1/3] x86: Make exception_mnemonic() visible to the tests From: Aaron Lewis To: kvm@vger.kernel.org Cc: pbonzini@redhat.com, jmattson@google.com, seanjc@google.com, Aaron Lewis Precedence: bulk List-ID: X-Mailing-List: kvm@vger.kernel.org exception_mnemonic() is a useful function for more than just desc.c. Make it global, so it can be used in other KUT tests. Signed-off-by: Aaron Lewis Reviewed-by: Sean Christopherson --- lib/x86/desc.c | 2 +- lib/x86/desc.h | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/lib/x86/desc.c b/lib/x86/desc.c index 16b7256..c2eb16e 100644 --- a/lib/x86/desc.c +++ b/lib/x86/desc.c @@ -91,7 +91,7 @@ struct ex_record { extern struct ex_record exception_table_start, exception_table_end; -static const char* exception_mnemonic(int vector) +const char* exception_mnemonic(int vector) { switch(vector) { case 0: return "#DE"; diff --git a/lib/x86/desc.h b/lib/x86/desc.h index 9b81da0..ad6277b 100644 --- a/lib/x86/desc.h +++ b/lib/x86/desc.h @@ -224,6 +224,7 @@ void set_intr_alt_stack(int e, void *fn); void print_current_tss_info(void); handler handle_exception(u8 v, handler fn); void unhandled_exception(struct ex_regs *regs, bool cpu); +const char* exception_mnemonic(int vector); bool test_for_exception(unsigned int ex, void (*trigger_func)(void *data), void *data); From patchwork Fri Jan 21 15:58:54 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Aaron Lewis X-Patchwork-Id: 12719897 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id E925CC433EF for ; Fri, 21 Jan 2022 15:59:15 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1381736AbiAUP7P (ORCPT ); Fri, 21 Jan 2022 10:59:15 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36892 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1381742AbiAUP7M (ORCPT ); Fri, 21 Jan 2022 10:59:12 -0500 Received: from mail-pj1-x1049.google.com (mail-pj1-x1049.google.com [IPv6:2607:f8b0:4864:20::1049]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 49255C06173D for ; Fri, 21 Jan 2022 07:59:12 -0800 (PST) Received: by mail-pj1-x1049.google.com with SMTP id n23-20020a17090a161700b001b3ea76b406so8803577pja.5 for ; Fri, 21 Jan 2022 07:59:12 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20210112; h=date:in-reply-to:message-id:mime-version:references:subject:from:to :cc; bh=/nVQL044VkFMI3iybl+vKkbz76a4Xh01nLuzyZTcW1s=; b=Bna7dU48kinRNiRoyf0LD79h+hOUzztSeQBE8thzNLwTzn61mW8Ht6jbjzsnys6Sgl i6SrJFiZCt7XmF0saONNNwMwT+RoN6HpqzVcfAThj8TfVVbyBciFyKuBMAFRAvfZgHsv asnTXw5FgMWOJyINsTjEnEyTeQsSWn6uxkGMg/XbNB7IglI7smWuFdWeIkxabwYFKH4s k9Ffbev4uZSnTOvoAw6jiNj2DrEtA9MmUhpdsRQGZuEAAzUCM8Dik8Y4PImTGT/Vz778 32y7ChpjwEm/2AaZBQyix1WwXYvh25qqtWtRQs/VtPbgizC+3gKRXlvIbcUrsk10KBUy EPrw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=x-gm-message-state:date:in-reply-to:message-id:mime-version :references:subject:from:to:cc; bh=/nVQL044VkFMI3iybl+vKkbz76a4Xh01nLuzyZTcW1s=; b=i466eflt5yoicwzA7VZHeqeIYNSk116zI0KwL+8LmrTiW/tzv96mp2wMWBkRzK9YFw 52BTV7Kx/R0X9alsJ4SdgX5aN8i9XnPDJR2G7a/mF5k72s/QHCqbqf+Zyyzo3I8s4iqW LLkn/7wX1vsQlV+ctCcAJLBXXkgArshcyQYCWuqcS/ZPU488HN7l4KTNdxiWQkSO6g3u OMVDZFxpFCq4oe9MUiYBURsAHyvTwbDf7I7j+MpEjKU6fdzOwjdnVb3KcoY22GKz1LLp EMJUrnjigMnMPQ1YCVl39W2KZNchl0Ks97zaWICP0UTSh4wC0VudGH5vLNxduOH4Bahw nxMA== X-Gm-Message-State: AOAM531ZysNchqFqg/mavgTYq9C8rjjDXVcjcByaZXJTuhmjcNOdFtyW hTq5b4MO0k5yoyxYQIdAVelQ+baqGKlzujdl+d527aI0UhurKrI006NkiWJ1ILP5bvdTNGZgzIi UmJhUKyyt/F9nxX4DFd3xzCGGARYwFAFdP6Bq2OFQCdkb09SHDwq+5Nlekgs7vg5B5MkO X-Google-Smtp-Source: ABdhPJyHnGlwqmDaygCikL0cZEmljL8XZEPcmK4PWybzoYG8DPAwlhrDwmzhEKb5UHP7IcOfCGXCRc8H+hn3lfuF X-Received: from aaronlewis.c.googlers.com ([fda3:e722:ac3:cc00:7f:e700:c0a8:2675]) (user=aaronlewis job=sendgmr) by 2002:a62:8683:0:b0:4c7:2221:2f93 with SMTP id x125-20020a628683000000b004c722212f93mr4162122pfd.79.1642780751658; Fri, 21 Jan 2022 07:59:11 -0800 (PST) Date: Fri, 21 Jan 2022 15:58:54 +0000 In-Reply-To: <20220121155855.213852-1-aaronlewis@google.com> Message-Id: <20220121155855.213852-3-aaronlewis@google.com> Mime-Version: 1.0 References: <20220121155855.213852-1-aaronlewis@google.com> X-Mailer: git-send-email 2.35.0.rc0.227.g00780c9af4-goog Subject: [kvm-unit-tests PATCH v4 2/3] x86: Add support for running a nested guest multiple times in one test From: Aaron Lewis To: kvm@vger.kernel.org Cc: pbonzini@redhat.com, jmattson@google.com, seanjc@google.com, Aaron Lewis Precedence: bulk List-ID: X-Mailing-List: kvm@vger.kernel.org KUT has a limit of only being able to run one nested guest per vmx test. This is limiting and not necessary. Add support for allowing a test to run guest code multiple times. Signed-off-by: Aaron Lewis --- x86/vmx.c | 24 ++++++++++++++++++++++-- x86/vmx.h | 2 ++ 2 files changed, 24 insertions(+), 2 deletions(-) diff --git a/x86/vmx.c b/x86/vmx.c index f4fbb94..51eed8c 100644 --- a/x86/vmx.c +++ b/x86/vmx.c @@ -1884,15 +1884,35 @@ void test_add_teardown(test_teardown_func func, void *data) step->data = data; } +static void __test_set_guest(test_guest_func func) +{ + assert(current->v2); + v2_guest_main = func; +} + /* * Set the target of the first enter_guest call. Can only be called once per * test. Must be called before first enter_guest call. */ void test_set_guest(test_guest_func func) { - assert(current->v2); TEST_ASSERT_MSG(!v2_guest_main, "Already set guest func."); - v2_guest_main = func; + __test_set_guest(func); +} + +/* + * Set the target of the enter_guest call and reset the RIP so 'func' will + * start from the beginning. This can be called multiple times per test. + */ +void test_override_guest(test_guest_func func) +{ + __test_set_guest(func); + init_vmcs_guest(); +} + +void test_set_guest_finished(void) +{ + guest_finished = 1; } static void check_for_guest_termination(union exit_reason exit_reason) diff --git a/x86/vmx.h b/x86/vmx.h index 4423986..11cb665 100644 --- a/x86/vmx.h +++ b/x86/vmx.h @@ -1055,7 +1055,9 @@ void hypercall(u32 hypercall_no); typedef void (*test_guest_func)(void); typedef void (*test_teardown_func)(void *data); void test_set_guest(test_guest_func func); +void test_override_guest(test_guest_func func); void test_add_teardown(test_teardown_func func, void *data); void test_skip(const char *msg); +void test_set_guest_finished(void); #endif From patchwork Fri Jan 21 15:58:55 2022 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Aaron Lewis X-Patchwork-Id: 12719898 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id 00530C433FE for ; Fri, 21 Jan 2022 15:59:16 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1381732AbiAUP7Q (ORCPT ); Fri, 21 Jan 2022 10:59:16 -0500 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:36912 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1381727AbiAUP7P (ORCPT ); Fri, 21 Jan 2022 10:59:15 -0500 Received: from mail-pf1-x449.google.com (mail-pf1-x449.google.com [IPv6:2607:f8b0:4864:20::449]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 42975C06173B for ; Fri, 21 Jan 2022 07:59:15 -0800 (PST) Received: by mail-pf1-x449.google.com with SMTP id c23-20020aa78817000000b004be3f452a95so6278739pfo.19 for ; Fri, 21 Jan 2022 07:59:15 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=20210112; h=date:in-reply-to:message-id:mime-version:references:subject:from:to :cc:content-transfer-encoding; bh=e8l4oFvPoWvA9phQl8TvfOeE3zJv9n0shNsZrndBYsA=; b=LJCJlJKb56is3GDUbtigzRIfvQ+dVbLfoHTLS2MW6dlvp8olv5zAOzjhVTaIe+zQa0 kPJZyyjj+Qa0GOW121sn4SuCBt2zOgsciPGNlrim3OYfM4ZcFrdEsbp9jUmbaMOcUBxD dSMs6Rav3f9YJFrPU5zfM4c2l09UW5WW0NZwqIe7iKZDhpx5wMqWeRRMNVbSRzxtqgut 7/bgVisX5OKxwSsWaeKtCz3M2+5bhXuhaxYCc1LZGZVuH2QQVy6sEzSMteTkOJZ+Ee64 nrWP07SxUbu68oJzJi9TKE6Qe1Xa8vBiqUE2h7HVYUIEgwUuYvS1gfzBODQub6IUQRMX CDaA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=x-gm-message-state:date:in-reply-to:message-id:mime-version :references:subject:from:to:cc:content-transfer-encoding; bh=e8l4oFvPoWvA9phQl8TvfOeE3zJv9n0shNsZrndBYsA=; b=HQuPZWtPSKtyGkF5riojTzxCQajFoiFrp1KjuP6aYsXzf5WH8x5ZmMaGfqhsB3ksrJ GtzAMZWmVBAPgTXmA3Me3ByQLa8uBe7veoxrX1gx7SVVwaXuNjGberAgMf2uOajFWutV 3JeO0lFz4/8mH57v8bfA3fioiA3q/QpwSmAi/TRbWdhMUoEbNPEuW98ak4pJHDjxk0TF 2Z/uVRUlC/Z9LvAw4DpJJzk7nyqWGJuE9n11RlT67sEvCJ32OKbcqql8WOKUR3oFdv9X 9OOwCfXbxhVZUQ2pspBMP7gd30XBhUHq/oLGOMNr+A27rWBCG47Io8L8czen6LrXk605 jiSw== X-Gm-Message-State: AOAM531Jjxbq5qgDiCYjsGqjJqGnYuf7vlfYwJb9dzYYY3dAWOuvIHms pt5ixdxcbtu8yq+CJ35DJQ8W+XeUxQHojswfzG5qzP90h/zSTjekx3Ruw8jt9QHVI2/K0YtWkAb nj+soQEeiVpQ79wFjN3IzjrFCz2qXLSlh8gB2b67l+C0PZnihEcX6U+QIcwdoGhPU706N X-Google-Smtp-Source: ABdhPJypzIl9hZzMWqwYX1AxlQ7tICUNI9g7H5ALQgrUPN5A1qqZWcN47nki7GRDVJoLb9XBupjKISnHq1Iqp+WJ X-Received: from aaronlewis.c.googlers.com ([fda3:e722:ac3:cc00:7f:e700:c0a8:2675]) (user=aaronlewis job=sendgmr) by 2002:a05:6a00:10d5:b0:4bc:a0eb:c6a0 with SMTP id d21-20020a056a0010d500b004bca0ebc6a0mr4426282pfu.70.1642780754613; Fri, 21 Jan 2022 07:59:14 -0800 (PST) Date: Fri, 21 Jan 2022 15:58:55 +0000 In-Reply-To: <20220121155855.213852-1-aaronlewis@google.com> Message-Id: <20220121155855.213852-4-aaronlewis@google.com> Mime-Version: 1.0 References: <20220121155855.213852-1-aaronlewis@google.com> X-Mailer: git-send-email 2.35.0.rc0.227.g00780c9af4-goog Subject: [kvm-unit-tests PATCH v4 3/3] x86: Add test coverage for nested_vmx_reflect_vmexit() testing From: Aaron Lewis To: kvm@vger.kernel.org Cc: pbonzini@redhat.com, jmattson@google.com, seanjc@google.com, Aaron Lewis Precedence: bulk List-ID: X-Mailing-List: kvm@vger.kernel.org Add a framework and test cases to ensure exceptions that occur in L2 are forwarded to the correct place by nested_vmx_reflect_vmexit(). Add testing for exceptions: #GP, #UD, #DE, #DB, #BP, and #AC. Signed-off-by: Aaron Lewis Change-Id: I0196071571671f06165983b5055ed7382fa3e1fb --- x86/unittests.cfg | 9 +++- x86/vmx_tests.c | 129 ++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 137 insertions(+), 1 deletion(-) diff --git a/x86/unittests.cfg b/x86/unittests.cfg index 9a70ba3..6ec7a98 100644 --- a/x86/unittests.cfg +++ b/x86/unittests.cfg @@ -288,7 +288,7 @@ arch = i386 [vmx] file = vmx.flat -extra_params = -cpu max,+vmx -append "-exit_monitor_from_l2_test -ept_access* -vmx_smp* -vmx_vmcs_shadow_test -atomic_switch_overflow_msrs_test -vmx_init_signal_test -vmx_apic_passthrough_tpr_threshold_test -apic_reg_virt_test -virt_x2apic_mode_test -vmx_pf_exception_test -vmx_pf_no_vpid_test -vmx_pf_invvpid_test -vmx_pf_vpid_test" +extra_params = -cpu max,+vmx -append "-exit_monitor_from_l2_test -ept_access* -vmx_smp* -vmx_vmcs_shadow_test -atomic_switch_overflow_msrs_test -vmx_init_signal_test -vmx_apic_passthrough_tpr_threshold_test -apic_reg_virt_test -virt_x2apic_mode_test -vmx_pf_exception_test -vmx_pf_no_vpid_test -vmx_pf_invvpid_test -vmx_pf_vpid_test -vmx_exception_test" arch = x86_64 groups = vmx @@ -390,6 +390,13 @@ arch = x86_64 groups = vmx nested_exception check = /sys/module/kvm_intel/parameters/allow_smaller_maxphyaddr=Y +[vmx_exception_test] +file = vmx.flat +extra_params = -cpu max,+vmx -append vmx_exception_test +arch = x86_64 +groups = vmx nested_exception +timeout = 10 + [debug] file = debug.flat arch = x86_64 diff --git a/x86/vmx_tests.c b/x86/vmx_tests.c index 3d57ed6..af6f33b 100644 --- a/x86/vmx_tests.c +++ b/x86/vmx_tests.c @@ -21,6 +21,7 @@ #include "smp.h" #include "delay.h" #include "access.h" +#include "x86/usermode.h" #define VPID_CAP_INVVPID_TYPES_SHIFT 40 @@ -10701,6 +10702,133 @@ static void vmx_pf_vpid_test(void) __vmx_pf_vpid_test(invalidate_tlb_new_vpid, 1); } +static void vmx_l2_gp_test(void) +{ + *(volatile u64 *)NONCANONICAL = 0; +} + +static void vmx_l2_ud_test(void) +{ + asm volatile ("ud2"); +} + +static void vmx_l2_de_test(void) +{ + asm volatile ( + "xor %%eax, %%eax\n\t" + "xor %%ebx, %%ebx\n\t" + "xor %%edx, %%edx\n\t" + "idiv %%ebx\n\t" + ::: "eax", "ebx", "edx"); +} + +static void vmx_l2_bp_test(void) +{ + asm volatile ("int3"); +} + +static void vmx_l2_db_test(void) +{ + write_rflags(read_rflags() | X86_EFLAGS_TF); +} + +static uint64_t usermode_callback(void) +{ + /* Trigger an #AC by writing 8 bytes to a 4-byte aligned address. */ + asm volatile( + "sub $0x10, %rsp\n\t" + "movq $0, 0x4(%rsp)\n\t" + "add $0x10, %rsp\n\t"); + + return 0; +} + +static void vmx_l2_ac_test(void) +{ + bool raised_vector = false; + + write_cr0(read_cr0() | X86_CR0_AM); + write_rflags(read_rflags() | X86_EFLAGS_AC); + + run_in_user(usermode_callback, AC_VECTOR, 0, 0, 0, 0, &raised_vector); + report(raised_vector, "#AC vector raised from usermode in L2"); + vmcall(); +} + +struct vmx_exception_test { + u8 vector; + void (*guest_code)(void); +}; + +struct vmx_exception_test vmx_exception_tests[] = { + { GP_VECTOR, vmx_l2_gp_test }, + { UD_VECTOR, vmx_l2_ud_test }, + { DE_VECTOR, vmx_l2_de_test }, + { DB_VECTOR, vmx_l2_db_test }, + { BP_VECTOR, vmx_l2_bp_test }, + { AC_VECTOR, vmx_l2_ac_test }, +}; + +static u8 vmx_exception_test_vector; + +static void vmx_exception_handler(struct ex_regs *regs) +{ + report(regs->vector == vmx_exception_test_vector, + "Handling %s in L2's exception handler", + exception_mnemonic(vmx_exception_test_vector)); + vmcall(); +} + +static void handle_exception_in_l2(u8 vector) +{ + handler old_handler = handle_exception(vector, vmx_exception_handler); + + vmx_exception_test_vector = vector; + + enter_guest(); + report(vmcs_read(EXI_REASON) == VMX_VMCALL, + "%s handled by L2", exception_mnemonic(vector)); + + handle_exception(vector, old_handler); +} + +static void handle_exception_in_l1(u32 vector) +{ + u32 old_eb = vmcs_read(EXC_BITMAP); + + vmcs_write(EXC_BITMAP, old_eb | (1u << vector)); + + enter_guest(); + + report((vmcs_read(EXI_REASON) == VMX_EXC_NMI) && + ((vmcs_read(EXI_INTR_INFO) & 0xff) == vector), + "%s handled by L1", exception_mnemonic(vector)); + + vmcs_write(EXC_BITMAP, old_eb); +} + +static void vmx_exception_test(void) +{ + struct vmx_exception_test *t; + int i; + + for (i = 0; i < ARRAY_SIZE(vmx_exception_tests); i++) { + t = &vmx_exception_tests[i]; + + /* + * Override the guest code before each run even though it's the + * same code, the VMCS guest state needs to be reinitialized. + */ + test_override_guest(t->guest_code); + handle_exception_in_l2(t->vector); + + test_override_guest(t->guest_code); + handle_exception_in_l1(t->vector); + } + + test_set_guest_finished(); +} + #define TEST(name) { #name, .v2 = name } /* name/init/guest_main/exit_handler/syscall_handler/guest_regs */ @@ -10810,5 +10938,6 @@ struct vmx_test vmx_tests[] = { TEST(vmx_pf_no_vpid_test), TEST(vmx_pf_invvpid_test), TEST(vmx_pf_vpid_test), + TEST(vmx_exception_test), { NULL, NULL, NULL, NULL, NULL, {0} }, };