> v3:
>    No change

> v2:
>    Add code to save/restore GDTR, IDTR and TR for AP.

In current implementation of CPU MP service, AP is initialized with data
copied from BSP. Stack switch required by Stack Guard feature needs different
GDT, IDT table and task gates for each logic processor. This patch adds GDTR,
IDTR and TR into structure CPU_VOLATILE_REGISTERS and related code in save
and restore methods. This can make sure that any changes to GDT, IDT and task
gate for an AP will be kept from overwritten by BSP settings.

Cc: Eric Dong <eric.d...@intel.com>
Cc: Laszlo Ersek <ler...@redhat.com>
Cc: Jiewen Yao <jiewen....@intel.com>
Suggested-by: Ayellet Wolman <ayellet.wol...@intel.com>
Contributed-under: TianoCore Contribution Agreement 1.1
Signed-off-by: Jian J Wang <jian.j.w...@intel.com>
---
 UefiCpuPkg/Library/MpInitLib/MpLib.c | 17 +++++++++++++++++
 UefiCpuPkg/Library/MpInitLib/MpLib.h |  3 +++
 2 files changed, 20 insertions(+)

diff --git a/UefiCpuPkg/Library/MpInitLib/MpLib.c 
b/UefiCpuPkg/Library/MpInitLib/MpLib.c
index 61b14c9843..0c2058a7b0 100644
--- a/UefiCpuPkg/Library/MpInitLib/MpLib.c
+++ b/UefiCpuPkg/Library/MpInitLib/MpLib.c
@@ -195,6 +195,10 @@ SaveVolatileRegisters (
     VolatileRegisters->Dr6 = AsmReadDr6 ();
     VolatileRegisters->Dr7 = AsmReadDr7 ();
   }
+
+  AsmReadGdtr (&VolatileRegisters->Gdtr);
+  AsmReadIdtr (&VolatileRegisters->Idtr);
+  VolatileRegisters->Tr = AsmReadTr ();
 }
 
 /**
@@ -211,6 +215,7 @@ RestoreVolatileRegisters (
   )
 {
   CPUID_VERSION_INFO_EDX        VersionInfoEdx;
+  IA32_TSS_DESCRIPTOR           *Tss;
 
   AsmWriteCr0 (VolatileRegisters->Cr0);
   AsmWriteCr3 (VolatileRegisters->Cr3);
@@ -231,6 +236,18 @@ RestoreVolatileRegisters (
       AsmWriteDr7 (VolatileRegisters->Dr7);
     }
   }
+
+  AsmWriteGdtr (&VolatileRegisters->Gdtr);
+  AsmWriteIdtr (&VolatileRegisters->Idtr);
+  if (VolatileRegisters->Tr != 0 &&
+      VolatileRegisters->Tr < VolatileRegisters->Gdtr.Limit) {
+    Tss = (IA32_TSS_DESCRIPTOR *)(VolatileRegisters->Gdtr.Base +
+                                  VolatileRegisters->Tr);
+    if (Tss->Bits.P == 1) {
+      Tss->Bits.Type &= 0xD;  // 1101 - Clear busy bit just in case
+      AsmWriteTr (VolatileRegisters->Tr);
+    }
+  }
 }
 
 /**
diff --git a/UefiCpuPkg/Library/MpInitLib/MpLib.h 
b/UefiCpuPkg/Library/MpInitLib/MpLib.h
index d13d5c06f5..685e96cbac 100644
--- a/UefiCpuPkg/Library/MpInitLib/MpLib.h
+++ b/UefiCpuPkg/Library/MpInitLib/MpLib.h
@@ -102,6 +102,9 @@ typedef struct {
   UINTN                          Dr3;
   UINTN                          Dr6;
   UINTN                          Dr7;
+  IA32_DESCRIPTOR                Gdtr;
+  IA32_DESCRIPTOR                Idtr;
+  UINT16                         Tr;
 } CPU_VOLATILE_REGISTERS;
 
 //
-- 
2.14.1.windows.1

_______________________________________________
edk2-devel mailing list
edk2-devel@lists.01.org
https://lists.01.org/mailman/listinfo/edk2-devel

Reply via email to