diff mbox

[edk2,05/10] ArmPkg: allow dynamic GIC base addresses

Message ID 1408994367-11143-6-git-send-email-ard.biesheuvel@linaro.org
State New
Headers show

Commit Message

Ard Biesheuvel Aug. 25, 2014, 7:19 p.m. UTC
Allow the PCDs gArmTokenSpaceGuid.PcdGicDistributorBase and
gArmTokenSpaceGuid.PcdGicInterruptInterfaceBase to be redeclared
as PcdsDynamic by the platform, so virtual machines can set these
properties during boot. As the PcdGet32() calls now call into the
PCD database, cache the values that are required during the handling
of interrupts.

Signed-off-by: Ard Biesheuvel <ard.biesheuvel@linaro.org>
---
 ArmPkg/ArmPkg.dec                   | 15 ++++++++-------
 ArmPkg/Drivers/ArmGic/ArmGicDxe.c   | 34 ++++++++++++++++++++--------------
 ArmPkg/Drivers/ArmGic/ArmGicDxe.inf |  4 +++-
 ArmPkg/Library/BdsLib/BdsLib.inf    |  2 +-
 4 files changed, 32 insertions(+), 23 deletions(-)
diff mbox

Patch

diff --git a/ArmPkg/ArmPkg.dec b/ArmPkg/ArmPkg.dec
index 9229c07df53c..b654e7ca4552 100644
--- a/ArmPkg/ArmPkg.dec
+++ b/ArmPkg/ArmPkg.dec
@@ -68,6 +68,14 @@ 
   # Define if the Power State Coordination Interface (PSCI) is supported by the Platform Trusted Firmware
   gArmTokenSpaceGuid.PcdArmPsciSupport|FALSE|BOOLEAN|0x00000033
 
+[PcdsDynamic.common,PcdsFixedAtBuild.common]
+  #
+  # ARM Generic Interrupt Controller
+  #
+  gArmTokenSpaceGuid.PcdGicDistributorBase|0|UINT32|0x0000000C
+  gArmTokenSpaceGuid.PcdGicInterruptInterfaceBase|0|UINT32|0x0000000D
+  gArmTokenSpaceGuid.PcdGicSgiIntId|0|UINT32|0x00000025
+
 [PcdsFixedAtBuild.common]
   gArmTokenSpaceGuid.PcdTrustzoneSupport|FALSE|BOOLEAN|0x00000006
 
@@ -81,13 +89,6 @@ 
   gArmTokenSpaceGuid.PcdCpuResetAddress|0x00000000|UINT32|0x00000005
 
   #
-  # ARM Generic Interrupt Controller
-  #
-  gArmTokenSpaceGuid.PcdGicDistributorBase|0|UINT32|0x0000000C
-  gArmTokenSpaceGuid.PcdGicInterruptInterfaceBase|0|UINT32|0x0000000D
-  gArmTokenSpaceGuid.PcdGicSgiIntId|0|UINT32|0x00000025
-
-  #
   # ARM Secure Firmware PCDs
   #
   gArmTokenSpaceGuid.PcdSecureFdBaseAddress|0|UINT32|0x00000015
diff --git a/ArmPkg/Drivers/ArmGic/ArmGicDxe.c b/ArmPkg/Drivers/ArmGic/ArmGicDxe.c
index 111ce144385b..42079f9e1f3a 100644
--- a/ArmPkg/Drivers/ArmGic/ArmGicDxe.c
+++ b/ArmPkg/Drivers/ArmGic/ArmGicDxe.c
@@ -47,6 +47,9 @@  extern EFI_HARDWARE_INTERRUPT_PROTOCOL gHardwareInterruptProtocol;
 //
 EFI_EVENT EfiExitBootServicesEvent      = (EFI_EVENT)NULL;
 
+UINTN mGicInterruptInterfaceBase        = 0;
+UINTN mGicDistributorBase               = 0;
+
 // Maximum Number of Interrupts
 UINTN mGicNumInterrupts                 = 0;
 
@@ -124,7 +127,7 @@  EnableInterruptSource (
   RegShift = Source % 32;
 
   // Write set-enable register
-  MmioWrite32 (PcdGet32(PcdGicDistributorBase) + ARM_GIC_ICDISER + (4*RegOffset), 1 << RegShift);
+  MmioWrite32 (mGicDistributorBase + ARM_GIC_ICDISER + (4*RegOffset), 1 << RegShift);
   
   return EFI_SUCCESS;
 }
@@ -159,7 +162,7 @@  DisableInterruptSource (
   RegShift = Source % 32;
 
   // Write set-enable register
-  MmioWrite32 (PcdGet32(PcdGicDistributorBase) + ARM_GIC_ICDICER + (4*RegOffset), 1 << RegShift);
+  MmioWrite32 (mGicDistributorBase + ARM_GIC_ICDICER + (4*RegOffset), 1 << RegShift);
   
   return EFI_SUCCESS;
 }
@@ -195,7 +198,7 @@  GetInterruptSourceState (
   RegOffset = Source / 32;
   RegShift = Source % 32;
     
-  if ((MmioRead32 (PcdGet32(PcdGicDistributorBase) + ARM_GIC_ICDISER + (4*RegOffset)) & (1<<RegShift)) == 0) {
+  if ((MmioRead32 (mGicDistributorBase + ARM_GIC_ICDISER + (4*RegOffset)) & (1<<RegShift)) == 0) {
     *InterruptState = FALSE;
   } else {
     *InterruptState = TRUE;
@@ -227,7 +230,7 @@  EndOfInterrupt (
     return EFI_UNSUPPORTED;
   }
 
-  MmioWrite32 (PcdGet32(PcdGicInterruptInterfaceBase) + ARM_GIC_ICCEIOR, Source);
+  MmioWrite32 (mGicInterruptInterfaceBase + ARM_GIC_ICCEIOR, Source);
   return EFI_SUCCESS;
 }
 
@@ -252,7 +255,7 @@  IrqInterruptHandler (
   UINT32                      GicInterrupt;
   HARDWARE_INTERRUPT_HANDLER  InterruptHandler;
 
-  GicInterrupt = MmioRead32 (PcdGet32(PcdGicInterruptInterfaceBase) + ARM_GIC_ICCIAR);
+  GicInterrupt = MmioRead32 (mGicInterruptInterfaceBase + ARM_GIC_ICCIAR);
 
   // Special Interrupts (ID1020-ID1023) have an Interrupt ID greater than the number of interrupt (ie: Spurious interrupt).
   if (GicInterrupt >= mGicNumInterrupts) {
@@ -315,11 +318,11 @@  ExitBootServicesEvent (
   }
 
   // Disable Gic Interface
-  MmioWrite32 (PcdGet32(PcdGicInterruptInterfaceBase) + ARM_GIC_ICCICR, 0x0);
-  MmioWrite32 (PcdGet32(PcdGicInterruptInterfaceBase) + ARM_GIC_ICCPMR, 0x0);
+  MmioWrite32 (mGicInterruptInterfaceBase + ARM_GIC_ICCICR, 0x0);
+  MmioWrite32 (mGicInterruptInterfaceBase + ARM_GIC_ICCPMR, 0x0);
 
   // Disable Gic Distributor
-  MmioWrite32 (PcdGet32(PcdGicDistributorBase) + ARM_GIC_ICDDCR, 0x0);
+  MmioWrite32 (mGicDistributorBase + ARM_GIC_ICDDCR, 0x0);
 }
 
 /**
@@ -349,7 +352,10 @@  InterruptDxeInitialize (
   // Make sure the Interrupt Controller Protocol is not already installed in the system.
   ASSERT_PROTOCOL_ALREADY_INSTALLED (NULL, &gHardwareInterruptProtocolGuid);
 
-  mGicNumInterrupts = ArmGicGetMaxNumInterrupts (PcdGet32(PcdGicDistributorBase));
+  mGicInterruptInterfaceBase = PcdGet32(PcdGicInterruptInterfaceBase);
+  mGicDistributorBase = PcdGet32(PcdGicDistributorBase);
+  mGicNumInterrupts = ArmGicGetMaxNumInterrupts (mGicDistributorBase);
+  ASSERT(mGicNumInterrupts < 4096);
 
   for (Index = 0; Index < mGicNumInterrupts; Index++) {
     DisableInterruptSource (&gHardwareInterruptProtocol, Index);
@@ -358,7 +364,7 @@  InterruptDxeInitialize (
     RegOffset = Index / 4;
     RegShift = (Index % 4) * 8;
     MmioAndThenOr32 (
-      PcdGet32(PcdGicDistributorBase) + ARM_GIC_ICDIPR + (4*RegOffset),
+      mGicDistributorBase + ARM_GIC_ICDIPR + (4*RegOffset),
       ~(0xff << RegShift), 
       ARM_GIC_DEFAULT_PRIORITY << RegShift
       );
@@ -387,16 +393,16 @@  InterruptDxeInitialize (
   }
 
   // Set binary point reg to 0x7 (no preemption)
-  MmioWrite32 (PcdGet32(PcdGicInterruptInterfaceBase) + ARM_GIC_ICCBPR, 0x7);
+  MmioWrite32 (mGicInterruptInterfaceBase + ARM_GIC_ICCBPR, 0x7);
 
   // Set priority mask reg to 0xff to allow all priorities through
-  MmioWrite32 (PcdGet32(PcdGicInterruptInterfaceBase) + ARM_GIC_ICCPMR, 0xff);
+  MmioWrite32 (mGicInterruptInterfaceBase + ARM_GIC_ICCPMR, 0xff);
   
   // Enable gic cpu interface
-  MmioWrite32 (PcdGet32(PcdGicInterruptInterfaceBase) + ARM_GIC_ICCICR, 0x1);
+  MmioWrite32 (mGicInterruptInterfaceBase + ARM_GIC_ICCICR, 0x1);
 
   // Enable gic distributor
-  MmioWrite32 (PcdGet32(PcdGicDistributorBase) + ARM_GIC_ICDDCR, 0x1);
+  MmioWrite32 (mGicDistributorBase + ARM_GIC_ICDDCR, 0x1);
   
   // Initialize the array for the Interrupt Handlers
   gRegisteredInterruptHandlers = (HARDWARE_INTERRUPT_HANDLER*)AllocateZeroPool (sizeof(HARDWARE_INTERRUPT_HANDLER) * mGicNumInterrupts);
diff --git a/ArmPkg/Drivers/ArmGic/ArmGicDxe.inf b/ArmPkg/Drivers/ArmGic/ArmGicDxe.inf
index 9dc557a03729..0ccd9935bc9e 100644
--- a/ArmPkg/Drivers/ArmGic/ArmGicDxe.inf
+++ b/ArmPkg/Drivers/ArmGic/ArmGicDxe.inf
@@ -41,15 +41,17 @@ 
   MemoryAllocationLib
   UefiDriverEntryPoint
   IoLib
+  PcdLib
 
 [Protocols]
   gHardwareInterruptProtocolGuid
   gEfiCpuArchProtocolGuid
   
-[FixedPcd.common]
+[Pcd]
   gArmTokenSpaceGuid.PcdGicDistributorBase
   gArmTokenSpaceGuid.PcdGicInterruptInterfaceBase
   
+[FixedPcd]
   gArmTokenSpaceGuid.PcdArmPrimaryCore
 
 [Depex]
diff --git a/ArmPkg/Library/BdsLib/BdsLib.inf b/ArmPkg/Library/BdsLib/BdsLib.inf
index 6158fba5919a..ce9300d00efc 100644
--- a/ArmPkg/Library/BdsLib/BdsLib.inf
+++ b/ArmPkg/Library/BdsLib/BdsLib.inf
@@ -91,7 +91,7 @@ 
 [FixedPcd.ARM]
   gArmTokenSpaceGuid.PcdArmLinuxAtagMaxOffset
 
-[FixedPcd.AARCH64]
+[Pcd.AARCH64]
   gArmTokenSpaceGuid.PcdGicDistributorBase
   gArmTokenSpaceGuid.PcdGicSgiIntId