x86: VMX: Check EPT AD bits when enabled in ept_access_paddr()
PATCH 1/1 x86: VMX: Check EPT AD bits when enabled in ept_access_paddr()
Modify the test helper, ept_access_paddr(), to test the correctness of the L1's EPT AD bits when enabled. After a successful guest access, assert that the accessed bit (bit 8) has been set on all EPT entries which were used in the translation of the guest-physical address.
Since ept_access_paddr() tests an EPT mapping that backs a guest paging structure, processor accesses are treated as writes and the dirty bit (bit 9) is set accordingly. Assert that the dirty bit is set on the leaf EPT entry.
--- x86/vmx_tests.c | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+)
x86/vmx_tests.c +18 -0
@@ -1135,6 +1135,11 @@ static void ept_disable_ad_bits(void)vmcs_write (EPTP , eptp); } +static int ept_ad_enabled (void ) +{ +return eptp &EPTP_AD_FLAG ; +} +static void ept_enable_ad_bits_or_skip_test (void ) {if (!ept_ad_bits_supported ())
@@ -2500,6 +2505,8 @@ static void ept_access_paddr(unsigned long ept_access, unsigned long pte_ad,unsigned long *ptep;unsigned long gpa;unsigned long orig_epte; +unsigned long epte; +int i;/* Modify the guest PTE mapping data->gva according to @pte_ad. */ ptep =get_pte_level (current_page_table (), data->gva,/*level=*/ 1 );
@@ -2536,6 +2543,17 @@ static void ept_access_paddr(unsigned long ept_access, unsigned long pte_ad,do_ept_access_op (op); }else {do_ept_access_op (op); +if (ept_ad_enabled ()) { +for (i =EPT_PAGE_LEVEL ; i >0 ; i--) { +TEST_ASSERT (get_ept_pte (pml4, gpa, i, &epte)); +TEST_ASSERT (epte &EPT_ACCESS_FLAG ); +if (i ==1 ) +TEST_ASSERT (epte &EPT_DIRTY_FLAG ); +else +TEST_ASSERT_EQ (epte &EPT_DIRTY_FLAG ,0 ); + } + } +ept_untwiddle (gpa,/*level=*/ 1 , orig_epte); }
Signature · 1 line
2.24.0.432.g9d3f5f5b63-goog
Quoted 49 lines · Oliver Upton
Modify the test helper,
ept_access_paddr(), to test the correctness of the L1's EPT AD bits when enabled. After a successful guest access, assert that the accessed bit (bit 8) has been set on all EPT entries which were used in the translation of the guest-physical address.Since
ept_access_paddr()tests an EPT mapping that backs a guest paging structure, processor accesses are treated as writes and the dirty bit (bit 9) is set accordingly. Assert that the dirty bit is set on the leaf EPT entry.Signed-off-by Oliver Upton <[email protected]>--- x86/vmx_tests.c | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+)x86/vmx_tests.c +11
-0@@ -1135,6 +1135,11 @@ static void ept_disable_ad_bits(void)vmcs_write (EPTP , eptp); } +static int ept_ad_enabled (void ) +{ +return eptp &EPTP_AD_FLAG ; +} +static void ept_enable_ad_bits_or_skip_test (void ) {if (!ept_ad_bits_supported ())@@ -2500,6 +2505,8 @@ static void ept_access_paddr(unsigned long ept_access, unsigned long pte_ad,unsigned long *ptep;unsigned long gpa;unsigned long orig_epte; +unsigned long epte; +int i;/* Modify the guest PTE mapping data->gva according to @pte_ad. */ ptep =get_pte_level (current_page_table (), data->gva,/*level=*/ 1 );@@ -2536,6 +2543,17 @@ static void ept_access_paddr(unsigned long ept_access, unsigned long pte_ad,do_ept_access_op (op); }else {do_ept_access_op (op); +if (ept_ad_enabled ()) { +for (i =EPT_PAGE_LEVEL ; i >0 ; i--) { +TEST_ASSERT (get_ept_pte (pml4, gpa, i, &epte)); +TEST_ASSERT (epte &EPT_ACCESS_FLAG );
x86/vmx_tests.c static void ept_access_paddr(unsigned long ept_access, unsigned long pte_ad, · line 2559
Quoted 10 lines
x86/vmx_tests.c +7
-0+if (i ==1 ) +TEST_ASSERT (epte &EPT_DIRTY_FLAG ); +else +TEST_ASSERT_EQ (epte &EPT_DIRTY_FLAG ,0 ); + } + } +ept_untwiddle (gpa,/*level=*/ 1 , orig_epte); }
Queued, thanks.
Paolo