3 Copyright (c) 2013-2014, ARM Ltd. All rights reserved.<BR>
5 This program and the accompanying materials
6 are licensed and made available under the terms and conditions of the BSD License
7 which accompanies this distribution. The full text of the license may be found at
8 http://opensource.org/licenses/bsd-license.php
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
15 #include "ArmGicDxe.h"
20 IN EFI_EXCEPTION_TYPE InterruptType
,
21 IN EFI_SYSTEM_CONTEXT SystemContext
26 ExitBootServicesEvent (
32 // Making this global saves a few bytes in image size
34 EFI_HANDLE gHardwareInterruptHandle
= NULL
;
39 EFI_EVENT EfiExitBootServicesEvent
= (EFI_EVENT
)NULL
;
41 // Maximum Number of Interrupts
42 UINTN mGicNumInterrupts
= 0;
44 HARDWARE_INTERRUPT_HANDLER
*gRegisteredInterruptHandlers
= NULL
;
47 Register Handler for the specified interrupt source.
49 @param This Instance pointer for this protocol
50 @param Source Hardware source of the interrupt
51 @param Handler Callback for interrupt. NULL to unregister
53 @retval EFI_SUCCESS Source was updated to support Handler.
54 @retval EFI_DEVICE_ERROR Hardware could not be programmed.
59 RegisterInterruptSource (
60 IN EFI_HARDWARE_INTERRUPT_PROTOCOL
*This
,
61 IN HARDWARE_INTERRUPT_SOURCE Source
,
62 IN HARDWARE_INTERRUPT_HANDLER Handler
65 if (Source
>= mGicNumInterrupts
) {
67 return EFI_UNSUPPORTED
;
70 if ((Handler
== NULL
) && (gRegisteredInterruptHandlers
[Source
] == NULL
)) {
71 return EFI_INVALID_PARAMETER
;
74 if ((Handler
!= NULL
) && (gRegisteredInterruptHandlers
[Source
] != NULL
)) {
75 return EFI_ALREADY_STARTED
;
78 gRegisteredInterruptHandlers
[Source
] = Handler
;
80 // If the interrupt handler is unregistered then disable the interrupt
82 return This
->DisableInterruptSource (This
, Source
);
84 return This
->EnableInterruptSource (This
, Source
);
89 InstallAndRegisterInterruptService (
90 IN EFI_HARDWARE_INTERRUPT_PROTOCOL
*InterruptProtocol
,
91 IN EFI_CPU_INTERRUPT_HANDLER InterruptHandler
,
92 IN EFI_EVENT_NOTIFY ExitBootServicesEvent
96 EFI_CPU_ARCH_PROTOCOL
*Cpu
;
98 // Initialize the array for the Interrupt Handlers
99 gRegisteredInterruptHandlers
= (HARDWARE_INTERRUPT_HANDLER
*)AllocateZeroPool (sizeof(HARDWARE_INTERRUPT_HANDLER
) * mGicNumInterrupts
);
100 if (gRegisteredInterruptHandlers
== NULL
) {
101 return EFI_OUT_OF_RESOURCES
;
104 Status
= gBS
->InstallMultipleProtocolInterfaces (
105 &gHardwareInterruptHandle
,
106 &gHardwareInterruptProtocolGuid
, InterruptProtocol
,
109 if (EFI_ERROR (Status
)) {
114 // Get the CPU protocol that this driver requires.
116 Status
= gBS
->LocateProtocol (&gEfiCpuArchProtocolGuid
, NULL
, (VOID
**)&Cpu
);
117 if (EFI_ERROR (Status
)) {
122 // Unregister the default exception handler.
124 Status
= Cpu
->RegisterInterruptHandler (Cpu
, ARM_ARCH_EXCEPTION_IRQ
, NULL
);
125 if (EFI_ERROR (Status
)) {
130 // Register to receive interrupts
132 Status
= Cpu
->RegisterInterruptHandler (Cpu
, ARM_ARCH_EXCEPTION_IRQ
, InterruptHandler
);
133 if (EFI_ERROR (Status
)) {
137 // Register for an ExitBootServicesEvent
138 Status
= gBS
->CreateEvent (EVT_SIGNAL_EXIT_BOOT_SERVICES
, TPL_NOTIFY
, ExitBootServicesEvent
, NULL
, &EfiExitBootServicesEvent
);