diff options
author | mdkinney <mdkinney@6f19259b-4bc3-4df7-8a09-765794883524> | 2010-08-03 04:54:44 +0000 |
---|---|---|
committer | mdkinney <mdkinney@6f19259b-4bc3-4df7-8a09-765794883524> | 2010-08-03 04:54:44 +0000 |
commit | 0564ae5ee6fe168d464ff53609385dac8de89bab (patch) | |
tree | 28b8b128a65e3f1c01045442840b95035dc25fb3 | |
parent | 756ad8f8e9d3e345f1883546e2a3125203e234aa (diff) | |
download | edk2-0564ae5ee6fe168d464ff53609385dac8de89bab.zip edk2-0564ae5ee6fe168d464ff53609385dac8de89bab.tar.gz edk2-0564ae5ee6fe168d464ff53609385dac8de89bab.tar.bz2 |
Inherit entries from previous IDT when new IDT is installed.
Update CS in each inherited IDT entry to match CS for the new GDT.
git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@10765 6f19259b-4bc3-4df7-8a09-765794883524
-rw-r--r-- | UefiCpuPkg/CpuDxe/CpuDxe.c | 29 |
1 files changed, 23 insertions, 6 deletions
diff --git a/UefiCpuPkg/CpuDxe/CpuDxe.c b/UefiCpuPkg/CpuDxe/CpuDxe.c index 4546591..369fe65 100644 --- a/UefiCpuPkg/CpuDxe/CpuDxe.c +++ b/UefiCpuPkg/CpuDxe/CpuDxe.c @@ -1014,11 +1014,12 @@ InitInterruptDescriptorTable ( VOID
)
{
- EFI_STATUS Status;
- VOID *IdtPtrAlignmentBuffer;
- IA32_DESCRIPTOR *IdtPtr;
- UINTN Index;
- UINTN CurrentHandler;
+ EFI_STATUS Status;
+ VOID *IdtPtrAlignmentBuffer;
+ IA32_DESCRIPTOR *IdtPtr;
+ UINTN Index;
+ UINTN CurrentHandler;
+ IA32_DESCRIPTOR Idtr;
SetMem (ExternalVectorTable, sizeof(ExternalVectorTable), 0);
@@ -1028,7 +1029,6 @@ InitInterruptDescriptorTable ( CurrentHandler = (UINTN)AsmIdtVector00;
for (Index = 0; Index < INTERRUPT_VECTOR_NUMBER; Index ++, CurrentHandler += 0x08) {
gIdtTable[Index].Bits.OffsetLow = (UINT16)CurrentHandler;
- gIdtTable[Index].Bits.Selector = AsmReadCs();
gIdtTable[Index].Bits.Reserved_0 = 0;
gIdtTable[Index].Bits.GateType = IA32_IDT_GATE_TYPE_INTERRUPT_32;
gIdtTable[Index].Bits.OffsetHigh = (UINT16)(CurrentHandler >> 16);
@@ -1039,6 +1039,23 @@ InitInterruptDescriptorTable ( }
//
+ // Get original IDT address and size.
+ //
+ AsmReadIdtr ((IA32_DESCRIPTOR *) &Idtr);
+
+ //
+ // Copy original IDT entry.
+ //
+ CopyMem (&gIdtTable[0], (VOID *) Idtr.Base, Idtr.Limit + 1);
+
+ //
+ // Update all IDT enties to use cuurent CS value
+ //
+ for (Index = 0; Index < INTERRUPT_VECTOR_NUMBER; Index ++, CurrentHandler += 0x08) {
+ gIdtTable[Index].Bits.Selector = AsmReadCs();
+ }
+
+ //
// Load IDT Pointer
//
IdtPtrAlignmentBuffer = AllocatePool (sizeof (*IdtPtr) + 16);
|