x86/tlbflush: do not toggle the PGE CR4 bit unless necessary

When PCID is not available Xen does a full tlbflush by toggling the
PGE bit in CR4. This is not necessary if PGE is not enabled, since a
flush can be performed by writing to CR3 in that case.

Change the code in do_tlb_flush to only toggle the PGE bit in CR4 if
it's already enabled, otherwise do the tlb flush by writing to CR3.
This is relevant when running virtualized, since hypervisors don't
usually trap accesses to CR3 when using hardware assisted paging, but
do trap accesses to CR4 specially on AMD hardware, which makes such
accesses much more expensive.

Signed-off-by: Roger Pau Monné <roger.pau@citrix.com>
Reviewed-by: Jan Beulich <jbeulich@suse.com>
master commit: b5087a31ef
master date: 2019-12-03 14:15:35 +0100
This commit is contained in:
Roger Pau Monné authored and Jan Beulich committed 2020-01-15 14:23:36 +01:00
1 parent fe0496eab8
commit 01acc256eb
1 file changed
+5 -5
+5 -5
View File
@@ -83,7 +83,7 @@ static void post_flush(u32 t)
static void do_tlb_flush(void)
{
unsigned long flags;
unsigned long flags, cr4;
u32 t;
/* This non-reentrant function is sometimes called in interrupt context. */
@@ -93,13 +93,13 @@ static void do_tlb_flush(void)
if ( use_invpcid )
invpcid_flush_all();
else
else if ( (cr4 = read_cr4()) & X86_CR4_PGE )
{
unsigned long cr4 = read_cr4();
write_cr4(cr4 ^ X86_CR4_PGE);
write_cr4(cr4 & ~X86_CR4_PGE);
write_cr4(cr4);
}
else
write_cr3(read_cr3());
post_flush(t);
Reference in new issue
Block a user
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.