4 Copyright (c) 2016 - 2022, Hewlett Packard Enterprise Development LP. All rights reserved.<BR>
5 Copyright (c) 2022, Ventana Micro Systems Inc. All rights reserved.<BR>
7 SPDX-License-Identifier: BSD-2-Clause-Patent
16 STATIC BOOLEAN mInterruptState
= FALSE
;
17 STATIC EFI_HANDLE mCpuHandle
= NULL
;
18 STATIC UINTN mBootHartId
;
19 RISCV_EFI_BOOT_PROTOCOL gRiscvBootProtocol
;
24 @param This Protocol instance structure
25 @param BootHartId Pointer to the Boot Hart ID variable
27 @retval EFI_SUCCESS If BootHartId is returned
28 @retval EFI_INVALID_PARAMETER Either "BootHartId" is NULL or "This" is not
29 a valid RISCV_EFI_BOOT_PROTOCOL instance.
35 IN RISCV_EFI_BOOT_PROTOCOL
*This
,
39 if ((This
!= &gRiscvBootProtocol
) || (BootHartId
== NULL
)) {
40 return EFI_INVALID_PARAMETER
;
43 *BootHartId
= mBootHartId
;
47 RISCV_EFI_BOOT_PROTOCOL gRiscvBootProtocol
= {
48 RISCV_EFI_BOOT_PROTOCOL_LATEST_VERSION
,
52 EFI_CPU_ARCH_PROTOCOL gCpu
= {
58 CpuRegisterInterruptHandler
,
60 CpuSetMemoryAttributes
,
62 4 // DmaBufferAlignment
66 // CPU Arch Protocol Functions
70 Flush CPU data cache. If the instruction cache is fully coherent
71 with all DMA operations then function can just return EFI_SUCCESS.
73 @param This Protocol instance structure
74 @param Start Physical address to start flushing from.
75 @param Length Number of bytes to flush. Round up to chipset
77 @param FlushType Specifies the type of flush operation to perform.
79 @retval EFI_SUCCESS If cache was flushed
80 @retval EFI_UNSUPPORTED If flush type is not supported.
81 @retval EFI_DEVICE_ERROR If requested range could not be flushed.
86 CpuFlushCpuDataCache (
87 IN EFI_CPU_ARCH_PROTOCOL
*This
,
88 IN EFI_PHYSICAL_ADDRESS Start
,
90 IN EFI_CPU_FLUSH_TYPE FlushType
97 Enables CPU interrupts.
99 @param This Protocol instance structure
101 @retval EFI_SUCCESS If interrupts were enabled in the CPU
102 @retval EFI_DEVICE_ERROR If interrupts could not be enabled on the CPU.
108 IN EFI_CPU_ARCH_PROTOCOL
*This
112 mInterruptState
= TRUE
;
117 Disables CPU interrupts.
119 @param This Protocol instance structure
121 @retval EFI_SUCCESS If interrupts were disabled in the CPU.
122 @retval EFI_DEVICE_ERROR If interrupts could not be disabled on the CPU.
127 CpuDisableInterrupt (
128 IN EFI_CPU_ARCH_PROTOCOL
*This
131 DisableInterrupts ();
132 mInterruptState
= FALSE
;
137 Return the state of interrupts.
139 @param This Protocol instance structure
140 @param State Pointer to the CPU's current interrupt state
142 @retval EFI_SUCCESS If interrupts were disabled in the CPU.
143 @retval EFI_INVALID_PARAMETER State is NULL.
148 CpuGetInterruptState (
149 IN EFI_CPU_ARCH_PROTOCOL
*This
,
154 return EFI_INVALID_PARAMETER
;
157 *State
= mInterruptState
;
162 Generates an INIT to the CPU.
164 @param This Protocol instance structure
165 @param InitType Type of CPU INIT to perform
167 @retval EFI_SUCCESS If CPU INIT occurred. This value should never be
169 @retval EFI_DEVICE_ERROR If CPU INIT failed.
170 @retval EFI_UNSUPPORTED Requested type of CPU INIT not supported.
176 IN EFI_CPU_ARCH_PROTOCOL
*This
,
177 IN EFI_CPU_INIT_TYPE InitType
180 return EFI_UNSUPPORTED
;
184 Registers a function to be called from the CPU interrupt handler.
186 @param This Protocol instance structure
187 @param InterruptType Defines which interrupt to hook. IA-32
188 valid range is 0x00 through 0xFF
189 @param InterruptHandler A pointer to a function of type
190 EFI_CPU_INTERRUPT_HANDLER that is called
191 when a processor interrupt occurs. A null
192 pointer is an error condition.
194 @retval EFI_SUCCESS If handler installed or uninstalled.
195 @retval EFI_ALREADY_STARTED InterruptHandler is not NULL, and a handler
196 for InterruptType was previously installed.
197 @retval EFI_INVALID_PARAMETER InterruptHandler is NULL, and a handler for
198 InterruptType was not previously installed.
199 @retval EFI_UNSUPPORTED The interrupt specified by InterruptType
205 CpuRegisterInterruptHandler (
206 IN EFI_CPU_ARCH_PROTOCOL
*This
,
207 IN EFI_EXCEPTION_TYPE InterruptType
,
208 IN EFI_CPU_INTERRUPT_HANDLER InterruptHandler
211 return RegisterCpuInterruptHandler (InterruptType
, InterruptHandler
);
215 Returns a timer value from one of the CPU's internal timers. There is no
216 inherent time interval between ticks but is a function of the CPU frequency.
218 @param This - Protocol instance structure.
219 @param TimerIndex - Specifies which CPU timer is requested.
220 @param TimerValue - Pointer to the returned timer value.
221 @param TimerPeriod - A pointer to the amount of time that passes
222 in femtoseconds (10-15) for each increment
223 of TimerValue. If TimerValue does not
224 increment at a predictable rate, then 0 is
225 returned. The amount of time that has
226 passed between two calls to GetTimerValue()
227 can be calculated with the formula
228 (TimerValue2 - TimerValue1) * TimerPeriod.
229 This parameter is optional and may be NULL.
231 @retval EFI_SUCCESS - If the CPU timer count was returned.
232 @retval EFI_UNSUPPORTED - If the CPU does not have any readable timers.
233 @retval EFI_DEVICE_ERROR - If an error occurred while reading the timer.
234 @retval EFI_INVALID_PARAMETER - TimerIndex is not valid or TimerValue is NULL.
240 IN EFI_CPU_ARCH_PROTOCOL
*This
,
241 IN UINT32 TimerIndex
,
242 OUT UINT64
*TimerValue
,
243 OUT UINT64
*TimerPeriod OPTIONAL
246 if (TimerValue
== NULL
) {
247 return EFI_INVALID_PARAMETER
;
250 if (TimerIndex
!= 0) {
251 return EFI_INVALID_PARAMETER
;
254 *TimerValue
= (UINT64
)RiscVReadTimer ();
255 if (TimerPeriod
!= NULL
) {
256 *TimerPeriod
= DivU64x32 (
258 PcdGet64 (PcdCpuCoreCrystalClockFrequency
)
266 Implementation of SetMemoryAttributes() service of CPU Architecture Protocol.
268 This function modifies the attributes for the memory region specified by BaseAddress and
269 Length from their current attributes to the attributes specified by Attributes.
271 @param This The EFI_CPU_ARCH_PROTOCOL instance.
272 @param BaseAddress The physical address that is the start address of a memory region.
273 @param Length The size in bytes of the memory region.
274 @param Attributes The bit mask of attributes to set for the memory region.
276 @retval EFI_SUCCESS The attributes were set for the memory region.
277 @retval EFI_ACCESS_DENIED The attributes for the memory resource range specified by
278 BaseAddress and Length cannot be modified.
279 @retval EFI_INVALID_PARAMETER Length is zero.
280 Attributes specified an illegal combination of attributes that
281 cannot be set together.
282 @retval EFI_OUT_OF_RESOURCES There are not enough system resources to modify the attributes of
283 the memory resource range.
284 @retval EFI_UNSUPPORTED The processor does not support one or more bytes of the memory
285 resource range specified by BaseAddress and Length.
286 The bit mask of attributes is not support for the memory resource
287 range specified by BaseAddress and Length.
292 CpuSetMemoryAttributes (
293 IN EFI_CPU_ARCH_PROTOCOL
*This
,
294 IN EFI_PHYSICAL_ADDRESS BaseAddress
,
299 DEBUG ((DEBUG_INFO
, "%a: Set memory attributes not supported yet\n", __FUNCTION__
));
304 Initialize the state information for the CPU Architectural Protocol.
306 @param ImageHandle Image handle this driver.
307 @param SystemTable Pointer to the System Table.
309 @retval EFI_SUCCESS Thread can be successfully created
310 @retval EFI_OUT_OF_RESOURCES Cannot allocate protocol data structure
311 @retval EFI_DEVICE_ERROR Cannot create the thread
317 IN EFI_HANDLE ImageHandle
,
318 IN EFI_SYSTEM_TABLE
*SystemTable
322 EFI_RISCV_FIRMWARE_CONTEXT
*FirmwareContext
;
324 GetFirmwareContextPointer (&FirmwareContext
);
325 ASSERT (FirmwareContext
!= NULL
);
326 if (FirmwareContext
== NULL
) {
327 DEBUG ((DEBUG_ERROR
, "Failed to get the pointer of EFI_RISCV_FIRMWARE_CONTEXT\n"));
328 return EFI_NOT_FOUND
;
331 DEBUG ((DEBUG_INFO
, " %a: Firmware Context is at 0x%x.\n", __FUNCTION__
, FirmwareContext
));
333 mBootHartId
= FirmwareContext
->BootHartId
;
334 DEBUG ((DEBUG_INFO
, " %a: mBootHartId = 0x%x.\n", __FUNCTION__
, mBootHartId
));
336 InitializeCpuExceptionHandlers (NULL
);
339 // Make sure interrupts are disabled
341 DisableInterrupts ();
344 // Install Boot protocol
346 Status
= gBS
->InstallProtocolInterface (
348 &gRiscVEfiBootProtocolGuid
,
349 EFI_NATIVE_INTERFACE
,
352 ASSERT_EFI_ERROR (Status
);
355 // Install CPU Architectural Protocol
357 Status
= gBS
->InstallMultipleProtocolInterfaces (
359 &gEfiCpuArchProtocolGuid
,
363 ASSERT_EFI_ERROR (Status
);