From patchwork Fri Mar 31 13:57:06 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Mathias Krause X-Patchwork-Id: 13196018 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 5E3C1C76196 for ; Fri, 31 Mar 2023 13:57:34 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S232509AbjCaN5d (ORCPT ); Fri, 31 Mar 2023 09:57:33 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:56706 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S231311AbjCaN5b (ORCPT ); Fri, 31 Mar 2023 09:57:31 -0400 Received: from mail-ed1-x533.google.com (mail-ed1-x533.google.com [IPv6:2a00:1450:4864:20::533]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id CF677C669 for ; Fri, 31 Mar 2023 06:57:26 -0700 (PDT) Received: by mail-ed1-x533.google.com with SMTP id x3so89860643edb.10 for ; Fri, 31 Mar 2023 06:57:26 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=grsecurity.net; s=grsec; t=1680271045; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=XE1yojV/hoOkVZOn9CEqppzBj+fchtb54t/c0FawRuY=; b=PqyLujmpdRa8jFLDJ6RXmtdY96zL9V9h7GKJAPWwiJgYI9hUR5lyFW3tIT/Q+83R+F iKgoQjY2WbVBJavwKfh/VEW64PP2JsyKLUrMQjzHT539LdvOP3tBf2EqaJsvwKks/jpO 7ULVuN77HsvvcAdhdk6uXrAwXiz3y2PzywsD0VzO53uXw1+HPtw1nUqXOEDCKh26L4Bv A7muV7XRrki6yTC0Pl7iezDhFcf5z0sd4P56OXxKLNq16+7ngFo4vqKufncHKk6Ewale U9Qam1jLJKsZw7pNlCx66UlvQES22p73/M2mj783F+3nfE86kGha/4GXK7Rlx05vdppo ikjg== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; t=1680271045; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=XE1yojV/hoOkVZOn9CEqppzBj+fchtb54t/c0FawRuY=; b=kdz5D31qelbxno4F9S8TJ9WJF14sX0ywwtrVFozYqlgN8AbgJi/f9ErBFqt8QAuJpd MH6+da28O1bP9iXhMGQpmzvwdSBlQQ0gmHXZXvz19KVHdyB6PcfpMDuBLxKHX7r6IOoK O2NIW7pSgVFUugsXkKHCnUVbThENL/1t6+xMCPos/KTYET3APY/6AqkAM7jVZRYHGrNU 2GjiQHg/6lf4Nu0uY7jRnwfpKxt9bYT5jZl5sXz7Kenw3Ys1SESlyjyb0uTGHaLlXdsf VfGR1m8jORpg0MtRfLpSrnMGUJMBqlxA7ZyUfuX47eyJ9OCON1XGVBl2h9rnr+XPMlLX Wk+A== X-Gm-Message-State: AAQBX9eQvq7Dvom4TgkWxd+JuFJX7RN+s6CMp1utD5tXM565HLgC5Uip bX6WshnzeuHVDuH3gtOmZUK+huClEh/aXonTYL19kA== X-Google-Smtp-Source: AKy350a3szEhvmYZeCnhK2KUegckCTBDTnbEA5dOwzcIyIDIEbmsMFuFNGN6L/4suwykEUbZ0vSZcA== X-Received: by 2002:a17:906:ac1:b0:92d:9767:8e0a with SMTP id z1-20020a1709060ac100b0092d97678e0amr24377466ejf.13.1680271044523; Fri, 31 Mar 2023 06:57:24 -0700 (PDT) Received: from nuc.fritz.box (p200300f6af1a510052e55a748e5a73cd.dip0.t-ipconnect.de. [2003:f6:af1a:5100:52e5:5a74:8e5a:73cd]) by smtp.gmail.com with ESMTPSA id ay20-20020a170906d29400b00928de86245fsm996888ejb.135.2023.03.31.06.57.23 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 31 Mar 2023 06:57:24 -0700 (PDT) From: Mathias Krause To: kvm@vger.kernel.org Cc: Mathias Krause Subject: [kvm-unit-tests PATCH v2 1/4] x86: Use existing CR0.WP / CR4.SMEP bit definitions Date: Fri, 31 Mar 2023 15:57:06 +0200 Message-Id: <20230331135709.132713-2-minipli@grsecurity.net> X-Mailer: git-send-email 2.39.2 In-Reply-To: <20230331135709.132713-1-minipli@grsecurity.net> References: <20230331135709.132713-1-minipli@grsecurity.net> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: kvm@vger.kernel.org Use the existing bit definitions from x86/processor.h instead of defining our own. Signed-off-by: Mathias Krause --- x86/access.c | 11 ++++------- x86/pks.c | 5 ++--- x86/pku.c | 5 ++--- 3 files changed, 8 insertions(+), 13 deletions(-) diff --git a/x86/access.c b/x86/access.c index 4dfec23073f7..203353a3f74f 100644 --- a/x86/access.c +++ b/x86/access.c @@ -20,9 +20,6 @@ static int invalid_mask; #define PT_BASE_ADDR_MASK ((pt_element_t)((((pt_element_t)1 << 36) - 1) & PAGE_MASK)) #define PT_PSE_BASE_ADDR_MASK (PT_BASE_ADDR_MASK & ~(1ull << 21)) -#define CR0_WP_MASK (1UL << 16) -#define CR4_SMEP_MASK (1UL << 20) - #define PFERR_PRESENT_MASK (1U << 0) #define PFERR_WRITE_MASK (1U << 1) #define PFERR_USER_MASK (1U << 2) @@ -239,9 +236,9 @@ static void set_cr0_wp(int wp) { unsigned long cr0 = shadow_cr0; - cr0 &= ~CR0_WP_MASK; + cr0 &= ~X86_CR0_WP; if (wp) - cr0 |= CR0_WP_MASK; + cr0 |= X86_CR0_WP; if (cr0 != shadow_cr0) { write_cr0(cr0); shadow_cr0 = cr0; @@ -272,9 +269,9 @@ static unsigned set_cr4_smep(ac_test_t *at, int smep) unsigned long cr4 = shadow_cr4; unsigned r; - cr4 &= ~CR4_SMEP_MASK; + cr4 &= ~X86_CR4_SMEP; if (smep) - cr4 |= CR4_SMEP_MASK; + cr4 |= X86_CR4_SMEP; if (cr4 == shadow_cr4) return 0; diff --git a/x86/pks.c b/x86/pks.c index ef95fb96c597..bda15efc546d 100644 --- a/x86/pks.c +++ b/x86/pks.c @@ -5,7 +5,6 @@ #include "x86/vm.h" #include "x86/msr.h" -#define CR0_WP_MASK (1UL << 16) #define PTE_PKEY_BIT 59 #define SUPER_BASE (1 << 23) #define SUPER_VAR(v) (*((__typeof__(&(v))) (((unsigned long)&v) + SUPER_BASE))) @@ -18,9 +17,9 @@ static void set_cr0_wp(int wp) { unsigned long cr0 = read_cr0(); - cr0 &= ~CR0_WP_MASK; + cr0 &= ~X86_CR0_WP; if (wp) - cr0 |= CR0_WP_MASK; + cr0 |= X86_CR0_WP; write_cr0(cr0); } diff --git a/x86/pku.c b/x86/pku.c index 51ff412cef82..6c0d72cc6f81 100644 --- a/x86/pku.c +++ b/x86/pku.c @@ -5,7 +5,6 @@ #include "x86/vm.h" #include "x86/msr.h" -#define CR0_WP_MASK (1UL << 16) #define PTE_PKEY_BIT 59 #define USER_BASE (1 << 23) #define USER_VAR(v) (*((__typeof__(&(v))) (((unsigned long)&v) + USER_BASE))) @@ -18,9 +17,9 @@ static void set_cr0_wp(int wp) { unsigned long cr0 = read_cr0(); - cr0 &= ~CR0_WP_MASK; + cr0 &= ~X86_CR0_WP; if (wp) - cr0 |= CR0_WP_MASK; + cr0 |= X86_CR0_WP; write_cr0(cr0); } From patchwork Fri Mar 31 13:57:07 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Mathias Krause X-Patchwork-Id: 13196017 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 41E5AC761AF for ; Fri, 31 Mar 2023 13:57:33 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S232404AbjCaN5c (ORCPT ); Fri, 31 Mar 2023 09:57:32 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:56708 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S232119AbjCaN5b (ORCPT ); Fri, 31 Mar 2023 09:57:31 -0400 Received: from mail-ed1-x535.google.com (mail-ed1-x535.google.com [IPv6:2a00:1450:4864:20::535]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id CC850CA2E for ; Fri, 31 Mar 2023 06:57:27 -0700 (PDT) Received: by mail-ed1-x535.google.com with SMTP id eh3so89857723edb.11 for ; Fri, 31 Mar 2023 06:57:27 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=grsecurity.net; s=grsec; t=1680271046; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=29EJFXydcv/KKtfone2szoiYAFJhB160ko5K2W2bkyY=; b=A8YZPGp2rY+tKBTGPcC+/qBhtUqj+YNRhqLiQRujB+7SzkVhRsm7IzCaoKJJxjmLW4 mqK1qDLvwT3EbXkJkj/6CWx0VVlAiXqNSyT57cxd16b1fQKkacKkz4zhnGA+C8e8Qlcm 2ubhANcUayyhY2sqFGRz8xEh1Zq29+z7tbOExMjsUo27ptoW4A5iZvm2t+iT9rvDES2S EbTNTvTq7fxDEol0267TfTXlDbwQPLTx02iFWlrvCOlHHu61SpeWfCvnka/TgsTUEx9+ ViPJO/thMR7qB0nqFTJyT4wiYrr00DH5BXrRPR9bEQc/U90B0lgOoOFwiar6N6Glo4ok DyjA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; t=1680271046; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=29EJFXydcv/KKtfone2szoiYAFJhB160ko5K2W2bkyY=; b=40ZN6JxzocFyy4bCgfW5+ylezum1eOBmfIwp9a4OzJYYEdHVDArURnhs0YmD9tTG7O bI+uXzgrWiOQmiOLMzXfn40FqJqBaU5aT2P4WRf1qSK+X0WVZsveJED9rv4KKK5GMCWc QL54XvzrJIu+rsZqxn7m8Gwl09NC0oQrv+HQMykjmhqMPKcWiQewcIClE75zTsUZPLng BuByYdWChN9Kgoud0i0tWGEtR1ygjnpxEhlZFf8feVo0Kb4CgtMAI36+YLCFGpq4as6T 9zT1rUx+7g2J0XOnlg1w5zKoYWjnclMXS0ipBj2UThe/nRwmyH3Ddq/28WTkmLcUfxoG +PJQ== X-Gm-Message-State: AAQBX9djzKQuRURa775063GMBdBxlTcObauIm69BhBS2y+BZ5tTbCpHE eY7JvZ6u+v/7ruo/8lxO/w+gAfdzeJjhhYfTNjUP3A== X-Google-Smtp-Source: AKy350ZhBJd4TClGivE25/45dmy7AoKpnME3lDCbVJeoDrjxc2fTplWXutTcbne06XdGWuRZDpqNLg== X-Received: by 2002:a17:906:1d0a:b0:8b1:7b10:61d5 with SMTP id n10-20020a1709061d0a00b008b17b1061d5mr28772455ejh.33.1680271046085; Fri, 31 Mar 2023 06:57:26 -0700 (PDT) Received: from nuc.fritz.box (p200300f6af1a510052e55a748e5a73cd.dip0.t-ipconnect.de. [2003:f6:af1a:5100:52e5:5a74:8e5a:73cd]) by smtp.gmail.com with ESMTPSA id ay20-20020a170906d29400b00928de86245fsm996888ejb.135.2023.03.31.06.57.25 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 31 Mar 2023 06:57:25 -0700 (PDT) From: Mathias Krause To: kvm@vger.kernel.org Cc: Mathias Krause Subject: [kvm-unit-tests PATCH v2 2/4] x86/access: CR0.WP toggling write to r/o data test Date: Fri, 31 Mar 2023 15:57:07 +0200 Message-Id: <20230331135709.132713-3-minipli@grsecurity.net> X-Mailer: git-send-email 2.39.2 In-Reply-To: <20230331135709.132713-1-minipli@grsecurity.net> References: <20230331135709.132713-1-minipli@grsecurity.net> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: kvm@vger.kernel.org We already have tests that verify a write access to an r/o page is successful when CR0.WP=0, but we lack a test that explicitly verifies that the same access will fail after we set CR0.WP=1 without flushing any associated TLB entries either explicitly (INVLPG) or implicitly (write to CR3). Add such a test. Signed-off-by: Mathias Krause --- x86/access.c | 56 ++++++++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 54 insertions(+), 2 deletions(-) diff --git a/x86/access.c b/x86/access.c index 203353a3f74f..d1ec99b4fa73 100644 --- a/x86/access.c +++ b/x86/access.c @@ -575,9 +575,10 @@ fault: at->expected_error &= ~PFERR_FETCH_MASK; } -static void ac_set_expected_status(ac_test_t *at) +static void __ac_set_expected_status(ac_test_t *at, bool flush) { - invlpg(at->virt); + if (flush) + invlpg(at->virt); if (at->ptep) at->expected_pte = *at->ptep; @@ -599,6 +600,11 @@ static void ac_set_expected_status(ac_test_t *at) ac_emulate_access(at, at->flags); } +static void ac_set_expected_status(ac_test_t *at) +{ + __ac_set_expected_status(at, true); +} + static pt_element_t ac_get_pt(ac_test_t *at, int i, pt_element_t *ptep) { pt_element_t pte; @@ -1061,6 +1067,51 @@ err: return 0; } +static int check_write_cr0wp(ac_pt_env_t *pt_env) +{ + ac_test_t at; + int err = 0; + + ac_test_init(&at, 0xffff923042007000ul, pt_env); + at.flags = AC_PDE_PRESENT_MASK | AC_PTE_PRESENT_MASK | + AC_PDE_ACCESSED_MASK | AC_PTE_ACCESSED_MASK | + AC_ACCESS_WRITE_MASK; + ac_test_setup_ptes(&at); + + /* + * Under VMX the guest might own the CR0.WP bit, requiring KVM to + * manually keep track of its state where needed, e.g. in the guest + * page table walker. + * + * We load CR0.WP with the inverse value of what would be used during + * the access test and toggle EFER.NX to flush and rebuild the current + * MMU context based on that value. + */ + + set_cr0_wp(1); + set_efer_nx(1); + set_efer_nx(0); + + if (!ac_test_do_access(&at)) { + printf("%s: CR0.WP=0 r/o write fail\n", __FUNCTION__); + err++; + } + + at.flags |= AC_CPU_CR0_WP_MASK; + __ac_set_expected_status(&at, false); + + set_cr0_wp(0); + set_efer_nx(1); + set_efer_nx(0); + + if (!ac_test_do_access(&at)) { + printf("%s: CR0.WP=1 r/o write deny fail\n", __FUNCTION__); + err++; + } + + return err == 0; +} + static int check_effective_sp_permissions(ac_pt_env_t *pt_env) { unsigned long ptr1 = 0xffff923480000000; @@ -1150,6 +1201,7 @@ const ac_test_fn ac_test_cases[] = check_pfec_on_prefetch_pte, check_large_pte_dirty_for_nowp, check_smep_andnot_wp, + check_write_cr0wp, check_effective_sp_permissions, }; From patchwork Fri Mar 31 13:57:08 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Mathias Krause X-Patchwork-Id: 13196019 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 B891DC77B62 for ; Fri, 31 Mar 2023 13:57:35 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S232540AbjCaN5e (ORCPT ); Fri, 31 Mar 2023 09:57:34 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:56710 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S232186AbjCaN5b (ORCPT ); Fri, 31 Mar 2023 09:57:31 -0400 Received: from mail-ed1-x532.google.com (mail-ed1-x532.google.com [IPv6:2a00:1450:4864:20::532]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 9C246DBCB for ; Fri, 31 Mar 2023 06:57:28 -0700 (PDT) Received: by mail-ed1-x532.google.com with SMTP id x3so89861001edb.10 for ; Fri, 31 Mar 2023 06:57:28 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=grsecurity.net; s=grsec; t=1680271047; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=/W/3TX1trWbw7cm7tHRSUUT7TeiRpxFpONHIB9AwQIA=; b=NeP+fza4Hflo5YJNfbIjHIZXleW1lKi7+vRLnOTckZVIr/e+EFxMgj1xgslsMRvJZf 4L9qciexH44vu23fMpPIAHPZVU/nw4IjLhoN2vSbMzqhyJNR0lBq2pNaoVmGhLIdys+R UtBsXdDCyQZnGCGrklIXibjlZBQMP6jYQL6KksMt2QFeU6bRxSLvfhG5S0MBOjPY6CUL AHIHKZqUF/JQNVbTpaPk57jTxNs/0fV1jRzHmWiwkXVsJms6BCs3tpxozUvVpEFaPJ3w 3R6RlDi+6/TH+GJcWGP2WrqLK2gud10p26mZVmVtAsH8drXZ4dI/tRTKVNsDFk4Slttl mumw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; t=1680271047; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=/W/3TX1trWbw7cm7tHRSUUT7TeiRpxFpONHIB9AwQIA=; b=D9E1lJQnu8vplTI81U17Fx/MU2FBL5AAWuvd8YnzbV7G70ttPyR+T3Bb41MUVxEWz7 H8NYY/9vBaN8Q5ySAUsZg1VmL1azezoeR9mzW6p0TqfFyyVzvCUIPGlsX5RqNTvBYVzp 9X+NgIH+pxJBAjMg/yKXHZWbiDVZDm50IzhDKeJzuQ6+MDHfXE5LyiMG+R6DuDLgUoSA emtjVN34avsVN1YwCYcFVCQWdTbV96SlofytP763o76lOjhEwIzYJsJKmY3YdR8qu12X pWHB3T3Up1P8tHOq68lEPvt/VnjSTzf3UJLdHveBf9xSNKew3g1HuPPvBqF2dkXw+TJX ZxRA== X-Gm-Message-State: AAQBX9elL1HomYldE/r+kySRnvH7wCAZB8LqBYCzQrzLfUWn/eIyPRBJ lptzHVFURj6Qm3/kqNiZflbFmNIW9Hj1ZJZXLkRSfQ== X-Google-Smtp-Source: AKy350ZCN1rEifz1w1qTC4AqvYeihja0MNDXlHd35XYs1FVg+HYIWBoISzK3hR/3plBa9v0pl6VeGw== X-Received: by 2002:a17:907:6d27:b0:932:cfbc:7613 with SMTP id sa39-20020a1709076d2700b00932cfbc7613mr31422121ejc.24.1680271046844; Fri, 31 Mar 2023 06:57:26 -0700 (PDT) Received: from nuc.fritz.box (p200300f6af1a510052e55a748e5a73cd.dip0.t-ipconnect.de. [2003:f6:af1a:5100:52e5:5a74:8e5a:73cd]) by smtp.gmail.com with ESMTPSA id ay20-20020a170906d29400b00928de86245fsm996888ejb.135.2023.03.31.06.57.26 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 31 Mar 2023 06:57:26 -0700 (PDT) From: Mathias Krause To: kvm@vger.kernel.org Cc: Mathias Krause Subject: [kvm-unit-tests PATCH v2 3/4] x86/access: Forced emulation support Date: Fri, 31 Mar 2023 15:57:08 +0200 Message-Id: <20230331135709.132713-4-minipli@grsecurity.net> X-Mailer: git-send-email 2.39.2 In-Reply-To: <20230331135709.132713-1-minipli@grsecurity.net> References: <20230331135709.132713-1-minipli@grsecurity.net> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: kvm@vger.kernel.org Add support to enforce access tests to be handled by the emulator, if supported by KVM. Exclude it from the ac_test_exec() test, though, to not slow it down too much. Signed-off-by: Mathias Krause --- x86/access.c | 37 ++++++++++++++++++++++++++++++++----- 1 file changed, 32 insertions(+), 5 deletions(-) diff --git a/x86/access.c b/x86/access.c index d1ec99b4fa73..ae5e7d8e8892 100644 --- a/x86/access.c +++ b/x86/access.c @@ -82,6 +82,13 @@ enum { AC_CPU_CR4_SMEP_BIT, AC_CPU_CR4_PKE_BIT, + NR_AC_TEST_FLAGS, + + /* + * synthetic flags follow, won't be exercised by ac_test_exec(). + */ + AC_FEP_BIT, + NR_AC_FLAGS }; @@ -121,6 +128,8 @@ enum { #define AC_CPU_CR4_SMEP_MASK (1 << AC_CPU_CR4_SMEP_BIT) #define AC_CPU_CR4_PKE_MASK (1 << AC_CPU_CR4_PKE_BIT) +#define AC_FEP_MASK (1 << AC_FEP_BIT) + const char *ac_names[] = { [AC_PTE_PRESENT_BIT] = "pte.p", [AC_PTE_ACCESSED_BIT] = "pte.a", @@ -152,6 +161,7 @@ const char *ac_names[] = { [AC_CPU_CR0_WP_BIT] = "cr0.wp", [AC_CPU_CR4_SMEP_BIT] = "cr4.smep", [AC_CPU_CR4_PKE_BIT] = "cr4.pke", + [AC_FEP_BIT] = "fep", }; static inline void *va(pt_element_t phys) @@ -190,6 +200,7 @@ typedef struct { static void ac_test_show(ac_test_t *at); +static bool fep_available; static unsigned long shadow_cr0; static unsigned long shadow_cr3; static unsigned long shadow_cr4; @@ -396,7 +407,7 @@ static void ac_test_init(ac_test_t *at, unsigned long virt, ac_pt_env_t *pt_env) static int ac_test_bump_one(ac_test_t *at) { at->flags = ((at->flags | invalid_mask) + 1) & ~invalid_mask; - return at->flags < (1 << NR_AC_FLAGS); + return at->flags < (1 << NR_AC_TEST_FLAGS); } #define F(x) ((flags & x##_MASK) != 0) @@ -799,10 +810,13 @@ static int ac_test_do_access(ac_test_t *at) if (F(AC_ACCESS_TWICE)) { asm volatile ("mov $fixed2, %%rsi \n\t" - "mov (%[addr]), %[reg] \n\t" + "cmp $0, %[fep] \n\t" + "jz 1f \n\t" + KVM_FEP + "1: mov (%[addr]), %[reg] \n\t" "fixed2:" : [reg]"=r"(r), [fault]"=a"(fault), "=b"(e) - : [addr]"r"(at->virt) + : [addr]"r"(at->virt), [fep]"r"(F(AC_FEP)) : "rsi"); fault = 0; } @@ -823,9 +837,15 @@ static int ac_test_do_access(ac_test_t *at) "jnz 2f \n\t" "cmp $0, %[write] \n\t" "jnz 1f \n\t" - "mov (%[addr]), %[reg] \n\t" + "cmp $0, %[fep] \n\t" + "jz 0f \n\t" + KVM_FEP + "0: mov (%[addr]), %[reg] \n\t" "jmp done \n\t" - "1: mov %[reg], (%[addr]) \n\t" + "1: cmp $0, %[fep] \n\t" + "jz 0f \n\t" + KVM_FEP + "0: mov %[reg], (%[addr]) \n\t" "jmp done \n\t" "2: call *%[addr] \n\t" "done: \n" @@ -843,6 +863,7 @@ static int ac_test_do_access(ac_test_t *at) [write]"r"(F(AC_ACCESS_WRITE)), [user]"r"(F(AC_ACCESS_USER)), [fetch]"r"(F(AC_ACCESS_FETCH)), + [fep]"r"(F(AC_FEP)), [user_ds]"i"(USER_DS), [user_cs]"i"(USER_CS), [user_stack_top]"r"(user_stack + sizeof user_stack), @@ -1228,6 +1249,12 @@ int ac_test_run(int pt_levels) invalid_mask |= AC_PTE_BIT36_MASK; } + fep_available = is_fep_available(); + if (!fep_available) { + printf("FEP not available, skipping emulation tests\n"); + invalid_mask |= AC_FEP_MASK; + } + ac_env_int(&pt_env, pt_levels); ac_test_init(&at, 0xffff923400000000ul, &pt_env); From patchwork Fri Mar 31 13:57:09 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Mathias Krause X-Patchwork-Id: 13196020 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 B3B29C761A6 for ; Fri, 31 Mar 2023 13:57:36 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S232546AbjCaN5g (ORCPT ); Fri, 31 Mar 2023 09:57:36 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:56712 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S229629AbjCaN5b (ORCPT ); Fri, 31 Mar 2023 09:57:31 -0400 Received: from mail-ed1-x52d.google.com (mail-ed1-x52d.google.com [IPv6:2a00:1450:4864:20::52d]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 3B77BEF81 for ; Fri, 31 Mar 2023 06:57:29 -0700 (PDT) Received: by mail-ed1-x52d.google.com with SMTP id ew6so89878074edb.7 for ; Fri, 31 Mar 2023 06:57:29 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=grsecurity.net; s=grsec; t=1680271047; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to; bh=P2ecs728xz8eViS6nyVKhqitH9aCAjKZcKOdrIrAaoo=; b=Z5+sJCH6Rdpn4imX4E2kh7GtAC06BaNjDvKp13hIOuvKgI4S4RFhRIWjIkVf0S/GaA lHPN4JDS4rtdyBqVQantSbktQoOtW4CSpESCdm9j5lafgt9M0/AqD+k5lp7/qRSF4yxD FL3L07t6DD6B8u6fQ1LjA0aL6Kh8v0vhQtx2u4GtBZU/yigUTotN2S6MjEj6mDdniij0 PVEHqmeXuDuI9ekrmDO+YUvqozouvq+uohu9VQiRrgAQPbsaU8I4uSgsfCHLZqrc+MiK 7jmOvGBf1+MIhSsI/wb/7kf0nQOOkJzROb1PZxDMx4tUmRiRXeZAa6M7j6Et0A/QUzN8 qovA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; t=1680271047; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-message-state:from:to:cc :subject:date:message-id:reply-to; bh=P2ecs728xz8eViS6nyVKhqitH9aCAjKZcKOdrIrAaoo=; b=MHoNJL7x8Fpv1yl5VGg79p8khVTCceEv2WQtr24ZrOV7DhIrKgx5LXwUekzQSMOJ5+ oVJL0AGoy3MNx4vuxd1pzKpsvRWVzzMDfgTTe57ZZ7fGYXDpXk4mI/9VWQ1c6uJ3dTMT Mout9wtVR9J5+PoxfECUsbiuvQ3A+cbAmdHZGZmoSf0NTH2mfVDw+Vk0fJN1eDrGvBa3 j2QLbnRXQV3t6YvsQq1fz58wZwzs4QGqg6GiWCbKrWjQR/Oo3XZ4S3CCoSFc2HW4Eely 3Wgl1JSWb2c8NKj9FHqb/ji2BaQ9fWe0rw5Rs503IJ7TSzT6iUFf37exvsFppkoBfgDQ K9rg== X-Gm-Message-State: AAQBX9cXcNwxcdN791RrswlAq4aiMB5YmsJEsIwFur2FzjXgJxzSwzjU eu2PjZxM8z6/hH/M6k7ex4zVyON6q/E4wR6xvMlxSA== X-Google-Smtp-Source: AKy350ZYlmhmYtoBoflC7KfeCuy34iMYnLOMdGiG+d/kCb3yilfoqrCbLl9wrxF96O9jVBLyPjsIfQ== X-Received: by 2002:a50:ed8b:0:b0:502:3ea3:fc24 with SMTP id h11-20020a50ed8b000000b005023ea3fc24mr9918033edr.17.1680271047533; Fri, 31 Mar 2023 06:57:27 -0700 (PDT) Received: from nuc.fritz.box (p200300f6af1a510052e55a748e5a73cd.dip0.t-ipconnect.de. [2003:f6:af1a:5100:52e5:5a74:8e5a:73cd]) by smtp.gmail.com with ESMTPSA id ay20-20020a170906d29400b00928de86245fsm996888ejb.135.2023.03.31.06.57.26 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Fri, 31 Mar 2023 06:57:27 -0700 (PDT) From: Mathias Krause To: kvm@vger.kernel.org Cc: Mathias Krause Subject: [kvm-unit-tests PATCH v2 4/4] x86/access: Try emulation for CR0.WP test as well Date: Fri, 31 Mar 2023 15:57:09 +0200 Message-Id: <20230331135709.132713-5-minipli@grsecurity.net> X-Mailer: git-send-email 2.39.2 In-Reply-To: <20230331135709.132713-1-minipli@grsecurity.net> References: <20230331135709.132713-1-minipli@grsecurity.net> MIME-Version: 1.0 Precedence: bulk List-ID: X-Mailing-List: kvm@vger.kernel.org Enhance the CR.WP toggling test to do additional tests via the emulator as these used to trigger bugs when CR0.WP is guest owned. Link: https://lore.kernel.org/kvm/ea3a8fbc-2bf8-7442-e498-3e5818384c83@grsecurity.net/ Signed-off-by: Mathias Krause --- x86/access.c | 46 +++++++++++++++++++++++++++++++--------------- 1 file changed, 31 insertions(+), 15 deletions(-) diff --git a/x86/access.c b/x86/access.c index ae5e7d8e8892..21967434bc18 100644 --- a/x86/access.c +++ b/x86/access.c @@ -1107,27 +1107,43 @@ static int check_write_cr0wp(ac_pt_env_t *pt_env) * We load CR0.WP with the inverse value of what would be used during * the access test and toggle EFER.NX to flush and rebuild the current * MMU context based on that value. + * + * This used to trigger a bug in the emulator we try to test via FEP. */ + for (;;) { + const char *fep = (at.flags & AC_FEP_MASK) ? "FEP " : ""; - set_cr0_wp(1); - set_efer_nx(1); - set_efer_nx(0); + set_cr0_wp(1); + set_efer_nx(1); + set_efer_nx(0); - if (!ac_test_do_access(&at)) { - printf("%s: CR0.WP=0 r/o write fail\n", __FUNCTION__); - err++; - } + if (!ac_test_do_access(&at)) { + printf("%s: %sCR0.WP=0 r/o write fail\n", __FUNCTION__, fep); + err++; + } - at.flags |= AC_CPU_CR0_WP_MASK; - __ac_set_expected_status(&at, false); + at.flags |= AC_CPU_CR0_WP_MASK; + __ac_set_expected_status(&at, false); - set_cr0_wp(0); - set_efer_nx(1); - set_efer_nx(0); + set_cr0_wp(0); + set_efer_nx(1); + set_efer_nx(0); - if (!ac_test_do_access(&at)) { - printf("%s: CR0.WP=1 r/o write deny fail\n", __FUNCTION__); - err++; + if (!ac_test_do_access(&at)) { + printf("%s: %sCR0.WP=1 r/o write deny fail\n", __FUNCTION__, fep); + err++; + } + + if (!fep_available) + break; + + if (at.flags & AC_FEP_MASK) + break; + + /* Re-test via the emulator */ + at.flags |= AC_FEP_MASK; + at.flags ^= AC_CPU_CR0_WP_MASK; + __ac_set_expected_status(&at, false); } return err == 0;