From mboxrd@z Thu Jan 1 00:00:00 1970 Authentication-Results: mx.groups.io; dkim=pass header.i=@linaro.org header.s=google header.b=LyPLDCLl; spf=pass (domain: linaro.org, ip: 209.85.128.52, mailfrom: leif.lindholm@linaro.org) Received: from mail-wm1-f52.google.com (mail-wm1-f52.google.com [209.85.128.52]) by groups.io with SMTP; Thu, 05 Sep 2019 09:28:50 -0700 Received: by mail-wm1-f52.google.com with SMTP id r17so5391706wme.0 for ; Thu, 05 Sep 2019 09:28:49 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=date:from:to:subject:message-id:references:mime-version :content-disposition:in-reply-to:user-agent; bh=6lO0KYhWn0Mj4jFfZ6+qIygn5AwQOcgBkOwcdF5UGWM=; b=LyPLDCLlZOAunzUGAxTZO7HdirwI60Dc6T397BMrsIbdlLDfvCSU0cmPmjx4s0oLMJ i8ssdBR7fLT2738uQPqJDtNtyXjS+hCdhg1Op65s9gdhQRqd5PydNpDogGWq4z5vd0U9 ScZ1g5ufn0xbnYmlW6q0/AMOjY4EHR5zofqtfACDLjBPhjVFrPoRduuvGecvDrsWOHJJ Xjk8xE1dTw3LMqwYXMZ0SVhM3qT83m/4Z5tGGavgEvATN7jaBZ3hNO9QTdZywiimd5iH QQyDGWa5XYLRaORtUBv5n6u7X/qxYxA1VhD20ByO1YB6TA0e1noLCMFmxWeLWGINSbzc vgiA== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:date:from:to:subject:message-id:references :mime-version:content-disposition:in-reply-to:user-agent; bh=6lO0KYhWn0Mj4jFfZ6+qIygn5AwQOcgBkOwcdF5UGWM=; b=cCaVNJYwQjQ7RfwRFhOMEl/q+LI5kYpg2SF6Q22ntm0dxSNj9+9hdRR37FRnIb19bA NgglLck2vpl8goKhHw1DIlfofwjUrQbbEA4ORzDJA8xwYfij7fK9PTY9iFs3X1kfF5pw aCbL9xIGPda+UtHxRfaF+UGwo5TSaBVPKZq1vQwqUAZgV+NlLkVDIwPijFT9kEZlxaxt p7C9rKn2pQrpPYECnNqJvrUFOeMhAxS4lG+/GgLsuLNcwQ8CoN8TuQIyvzPLZ/J8T9A7 k9aPUauRpf8fQqM0D7PnobDRaIB8olqh2iZlaBphyav0I+0VNvzLV0kMIYYQ4IiuSUtH SjXw== X-Gm-Message-State: APjAAAWp7ggsNB5ievsqmBRSFk6aPgUKbIz9DTyAcEUjB3OAn6LGvq3Z C4tsOIymgoe4Pa4f6I1Lh7kBAA7Sv3U= X-Google-Smtp-Source: APXvYqz55LVcG7DIx7VEavwzCiRncYF4s3QzD9LFy9TMJUcIbOe1CjdxLPmZ/LswMQ0WhiNmZk81wg== X-Received: by 2002:a7b:cd97:: with SMTP id y23mr3360628wmj.74.1567700927625; Thu, 05 Sep 2019 09:28:47 -0700 (PDT) Return-Path: Received: from bivouac.eciton.net (bivouac.eciton.net. [2a00:1098:0:86:1000:23:0:2]) by smtp.gmail.com with ESMTPSA id a18sm4475598wrh.25.2019.09.05.09.28.46 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Thu, 05 Sep 2019 09:28:46 -0700 (PDT) Date: Thu, 5 Sep 2019 17:28:45 +0100 From: "Leif Lindholm" To: devel@edk2.groups.io, abner.chang@hpe.com Subject: Re: [edk2-devel] [edk2-staging/RISC-V-V2 PATCH v1 16/22]: RiscVPkg/CpuDxe: Add RISC-V CPU DXE driver. Message-ID: <20190905162845.GI29255@bivouac.eciton.net> References: <1567593797-26216-1-git-send-email-abner.chang@hpe.com> <1567593797-26216-17-git-send-email-abner.chang@hpe.com> MIME-Version: 1.0 In-Reply-To: <1567593797-26216-17-git-send-email-abner.chang@hpe.com> User-Agent: Mutt/1.10.1 (2018-07-13) Content-Type: text/plain; charset=us-ascii Content-Disposition: inline On Wed, Sep 04, 2019 at 06:43:11PM +0800, Abner Chang wrote: > The driver produces RISC-V EFI_CPU_ARCH_PROTOCOL and use RISC-V platform level timer library > > Due to RISC-V timer CSR is platform implementation specific, RISC-V CPU DXE driver invokes platform level timer library > to access to timer CSRs. No comments beyond PatchCheck.py, license/SPDX and contribution agreement. / Leif > Contributed-under: TianoCore Contribution Agreement 1.0 > Signed-off-by: Abner Chang > --- > RiscVPkg/Universal/CpuDxe/CpuDxe.c | 324 +++++++++++++++ > RiscVPkg/Universal/CpuDxe/CpuDxe.h | 212 ++++++++++ > RiscVPkg/Universal/CpuDxe/CpuDxe.inf | 66 +++ > RiscVPkg/Universal/CpuDxe/CpuDxe.uni | Bin 0 -> 1564 bytes > RiscVPkg/Universal/CpuDxe/CpuDxeExtra.uni | Bin 0 -> 1392 bytes > RiscVPkg/Universal/CpuDxe/CpuMp.h | 648 ++++++++++++++++++++++++++++++ > 6 files changed, 1250 insertions(+) > create mode 100644 RiscVPkg/Universal/CpuDxe/CpuDxe.c > create mode 100644 RiscVPkg/Universal/CpuDxe/CpuDxe.h > create mode 100644 RiscVPkg/Universal/CpuDxe/CpuDxe.inf > create mode 100644 RiscVPkg/Universal/CpuDxe/CpuDxe.uni > create mode 100644 RiscVPkg/Universal/CpuDxe/CpuDxeExtra.uni > create mode 100644 RiscVPkg/Universal/CpuDxe/CpuMp.h > > diff --git a/RiscVPkg/Universal/CpuDxe/CpuDxe.c b/RiscVPkg/Universal/CpuDxe/CpuDxe.c > new file mode 100644 > index 0000000..37d9bcf > --- /dev/null > +++ b/RiscVPkg/Universal/CpuDxe/CpuDxe.c > @@ -0,0 +1,324 @@ > +/** @file > + RISC-V CPU DXE driver. > + > + Copyright (c) 2016, Hewlett Packard Enterprise Development LP. All rights reserved.
> + > + This program and the accompanying materials are > + licensed and made available under the terms and conditions of the BSD License > + which accompanies this distribution. The full text of the license may be found at > + http://opensource.org/licenses/bsd-license.php > + > + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, > + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. > + > +**/ > + > +#include "CpuDxe.h" > + > +// > +// Global Variables > +// > +BOOLEAN InterruptState = FALSE; > +EFI_HANDLE mCpuHandle = NULL; > +BOOLEAN mIsFlushingGCD; > + > +EFI_CPU_ARCH_PROTOCOL gCpu = { > + CpuFlushCpuDataCache, > + CpuEnableInterrupt, > + CpuDisableInterrupt, > + CpuGetInterruptState, > + CpuInit, > + CpuRegisterInterruptHandler, > + CpuGetTimerValue, > + CpuSetMemoryAttributes, > + 1, // NumberOfTimers > + 4 // DmaBufferAlignment > +}; > + > +// > +// CPU Arch Protocol Functions > +// > + > +/** > + Flush CPU data cache. If the instruction cache is fully coherent > + with all DMA operations then function can just return EFI_SUCCESS. > + > + @param This Protocol instance structure > + @param Start Physical address to start flushing from. > + @param Length Number of bytes to flush. Round up to chipset > + granularity. > + @param FlushType Specifies the type of flush operation to perform. > + > + @retval EFI_SUCCESS If cache was flushed > + @retval EFI_UNSUPPORTED If flush type is not supported. > + @retval EFI_DEVICE_ERROR If requested range could not be flushed. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuFlushCpuDataCache ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + IN EFI_PHYSICAL_ADDRESS Start, > + IN UINT64 Length, > + IN EFI_CPU_FLUSH_TYPE FlushType > + ) > +{ > + return EFI_SUCCESS; > +} > + > + > +/** > + Enables CPU interrupts. > + > + @param This Protocol instance structure > + > + @retval EFI_SUCCESS If interrupts were enabled in the CPU > + @retval EFI_DEVICE_ERROR If interrupts could not be enabled on the CPU. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuEnableInterrupt ( > + IN EFI_CPU_ARCH_PROTOCOL *This > + ) > +{ > + EnableInterrupts (); > + InterruptState = TRUE; > + return EFI_SUCCESS; > +} > + > + > +/** > + Disables CPU interrupts. > + > + @param This Protocol instance structure > + > + @retval EFI_SUCCESS If interrupts were disabled in the CPU. > + @retval EFI_DEVICE_ERROR If interrupts could not be disabled on the CPU. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuDisableInterrupt ( > + IN EFI_CPU_ARCH_PROTOCOL *This > + ) > +{ > + DisableInterrupts (); > + InterruptState = FALSE; > + return EFI_SUCCESS; > +} > + > + > +/** > + Return the state of interrupts. > + > + @param This Protocol instance structure > + @param State Pointer to the CPU's current interrupt state > + > + @retval EFI_SUCCESS If interrupts were disabled in the CPU. > + @retval EFI_INVALID_PARAMETER State is NULL. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuGetInterruptState ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + OUT BOOLEAN *State > + ) > +{ > + if (State == NULL) { > + return EFI_INVALID_PARAMETER; > + } > + > + *State = InterruptState; > + return EFI_SUCCESS; > +} > + > + > +/** > + Generates an INIT to the CPU. > + > + @param This Protocol instance structure > + @param InitType Type of CPU INIT to perform > + > + @retval EFI_SUCCESS If CPU INIT occurred. This value should never be > + seen. > + @retval EFI_DEVICE_ERROR If CPU INIT failed. > + @retval EFI_UNSUPPORTED Requested type of CPU INIT not supported. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuInit ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + IN EFI_CPU_INIT_TYPE InitType > + ) > +{ > + return EFI_UNSUPPORTED; > +} > + > + > +/** > + Registers a function to be called from the CPU interrupt handler. > + > + @param This Protocol instance structure > + @param InterruptType Defines which interrupt to hook. IA-32 > + valid range is 0x00 through 0xFF > + @param InterruptHandler A pointer to a function of type > + EFI_CPU_INTERRUPT_HANDLER that is called > + when a processor interrupt occurs. A null > + pointer is an error condition. > + > + @retval EFI_SUCCESS If handler installed or uninstalled. > + @retval EFI_ALREADY_STARTED InterruptHandler is not NULL, and a handler > + for InterruptType was previously installed. > + @retval EFI_INVALID_PARAMETER InterruptHandler is NULL, and a handler for > + InterruptType was not previously installed. > + @retval EFI_UNSUPPORTED The interrupt specified by InterruptType > + is not supported. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuRegisterInterruptHandler ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + IN EFI_EXCEPTION_TYPE InterruptType, > + IN EFI_CPU_INTERRUPT_HANDLER InterruptHandler > + ) > +{ > + return RegisterCpuInterruptHandler (InterruptType, InterruptHandler); > +} > + > + > +/** > + Returns a timer value from one of the CPU's internal timers. There is no > + inherent time interval between ticks but is a function of the CPU frequency. > + > + @param This - Protocol instance structure. > + @param TimerIndex - Specifies which CPU timer is requested. > + @param TimerValue - Pointer to the returned timer value. > + @param TimerPeriod - A pointer to the amount of time that passes > + in femtoseconds (10-15) for each increment > + of TimerValue. If TimerValue does not > + increment at a predictable rate, then 0 is > + returned. The amount of time that has > + passed between two calls to GetTimerValue() > + can be calculated with the formula > + (TimerValue2 - TimerValue1) * TimerPeriod. > + This parameter is optional and may be NULL. > + > + @retval EFI_SUCCESS - If the CPU timer count was returned. > + @retval EFI_UNSUPPORTED - If the CPU does not have any readable timers. > + @retval EFI_DEVICE_ERROR - If an error occurred while reading the timer. > + @retval EFI_INVALID_PARAMETER - TimerIndex is not valid or TimerValue is NULL. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuGetTimerValue ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + IN UINT32 TimerIndex, > + OUT UINT64 *TimerValue, > + OUT UINT64 *TimerPeriod OPTIONAL > + ) > +{ > + if (TimerValue == NULL) { > + return EFI_INVALID_PARAMETER; > + } > + > + if (TimerIndex != 0) { > + return EFI_INVALID_PARAMETER; > + } > + > + *TimerValue = (UINT64)RiscVReadMachineTimer (); > + if (TimerPeriod != NULL) { > + *TimerPeriod = DivU64x32 ( > + 1000000000000000u, > + PcdGet64 (PcdRiscVMachineTimerFrequencyInHerz) > + ); > + } > + return EFI_SUCCESS; > +} > + > + > +/** > + Implementation of SetMemoryAttributes() service of CPU Architecture Protocol. > + > + This function modifies the attributes for the memory region specified by BaseAddress and > + Length from their current attributes to the attributes specified by Attributes. > + > + @param This The EFI_CPU_ARCH_PROTOCOL instance. > + @param BaseAddress The physical address that is the start address of a memory region. > + @param Length The size in bytes of the memory region. > + @param Attributes The bit mask of attributes to set for the memory region. > + > + @retval EFI_SUCCESS The attributes were set for the memory region. > + @retval EFI_ACCESS_DENIED The attributes for the memory resource range specified by > + BaseAddress and Length cannot be modified. > + @retval EFI_INVALID_PARAMETER Length is zero. > + Attributes specified an illegal combination of attributes that > + cannot be set together. > + @retval EFI_OUT_OF_RESOURCES There are not enough system resources to modify the attributes of > + the memory resource range. > + @retval EFI_UNSUPPORTED The processor does not support one or more bytes of the memory > + resource range specified by BaseAddress and Length. > + The bit mask of attributes is not support for the memory resource > + range specified by BaseAddress and Length. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuSetMemoryAttributes ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + IN EFI_PHYSICAL_ADDRESS BaseAddress, > + IN UINT64 Length, > + IN UINT64 Attributes > + ) > +{ > + DEBUG ((DEBUG_INFO, "%a:Set memory attributes not supported yet\n", __FUNCTION__)); > + ASSERT (FALSE); > + return EFI_UNSUPPORTED; > +} > + > +/** > + Initialize the state information for the CPU Architectural Protocol. > + > + @param ImageHandle Image handle this driver. > + @param SystemTable Pointer to the System Table. > + > + @retval EFI_SUCCESS Thread can be successfully created > + @retval EFI_OUT_OF_RESOURCES Cannot allocate protocol data structure > + @retval EFI_DEVICE_ERROR Cannot create the thread > + > +**/ > +EFI_STATUS > +EFIAPI > +InitializeCpu ( > + IN EFI_HANDLE ImageHandle, > + IN EFI_SYSTEM_TABLE *SystemTable > + ) > +{ > + EFI_STATUS Status; > + > + // > + // Machine mode handler is initiated in CpuExceptionHandlerLibConstructor in > + // CpuExecptionHandlerLib. > + // > + > + // > + // Make sure interrupts are disabled > + // > + DisableInterrupts (); > + > + // > + // Install CPU Architectural Protocol > + // > + Status = gBS->InstallMultipleProtocolInterfaces ( > + &mCpuHandle, > + &gEfiCpuArchProtocolGuid, &gCpu, > + NULL > + ); > + ASSERT_EFI_ERROR (Status); > + return Status; > +} > + > diff --git a/RiscVPkg/Universal/CpuDxe/CpuDxe.h b/RiscVPkg/Universal/CpuDxe/CpuDxe.h > new file mode 100644 > index 0000000..00f40ff > --- /dev/null > +++ b/RiscVPkg/Universal/CpuDxe/CpuDxe.h > @@ -0,0 +1,212 @@ > +/** @file > + RISC-V CPU DXE module header file. > + > + Copyright (c) 2016, Hewlett Packard Enterprise Development LP. All rights reserved.
> + > + This program and the accompanying materials are > + licensed and made available under the terms and conditions of the BSD License > + which accompanies this distribution. The full text of the license may be found at > + http://opensource.org/licenses/bsd-license.php > + > + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, > + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. > + > +**/ > + > +#ifndef _CPU_DXE_H_ > +#define _CPU_DXE_H_ > + > +#include > + > +#include > + > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include > +#include > + > +/** > + Flush CPU data cache. If the instruction cache is fully coherent > + with all DMA operations then function can just return EFI_SUCCESS. > + > + @param This Protocol instance structure > + @param Start Physical address to start flushing from. > + @param Length Number of bytes to flush. Round up to chipset > + granularity. > + @param FlushType Specifies the type of flush operation to perform. > + > + @retval EFI_SUCCESS If cache was flushed > + @retval EFI_UNSUPPORTED If flush type is not supported. > + @retval EFI_DEVICE_ERROR If requested range could not be flushed. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuFlushCpuDataCache ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + IN EFI_PHYSICAL_ADDRESS Start, > + IN UINT64 Length, > + IN EFI_CPU_FLUSH_TYPE FlushType > + ); > + > +/** > + Enables CPU interrupts. > + > + @param This Protocol instance structure > + > + @retval EFI_SUCCESS If interrupts were enabled in the CPU > + @retval EFI_DEVICE_ERROR If interrupts could not be enabled on the CPU. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuEnableInterrupt ( > + IN EFI_CPU_ARCH_PROTOCOL *This > + ); > + > +/** > + Disables CPU interrupts. > + > + @param This Protocol instance structure > + > + @retval EFI_SUCCESS If interrupts were disabled in the CPU. > + @retval EFI_DEVICE_ERROR If interrupts could not be disabled on the CPU. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuDisableInterrupt ( > + IN EFI_CPU_ARCH_PROTOCOL *This > + ); > + > +/** > + Return the state of interrupts. > + > + @param This Protocol instance structure > + @param State Pointer to the CPU's current interrupt state > + > + @retval EFI_SUCCESS If interrupts were disabled in the CPU. > + @retval EFI_INVALID_PARAMETER State is NULL. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuGetInterruptState ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + OUT BOOLEAN *State > + ); > + > +/** > + Generates an INIT to the CPU. > + > + @param This Protocol instance structure > + @param InitType Type of CPU INIT to perform > + > + @retval EFI_SUCCESS If CPU INIT occurred. This value should never be > + seen. > + @retval EFI_DEVICE_ERROR If CPU INIT failed. > + @retval EFI_UNSUPPORTED Requested type of CPU INIT not supported. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuInit ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + IN EFI_CPU_INIT_TYPE InitType > + ); > + > +/** > + Registers a function to be called from the CPU interrupt handler. > + > + @param This Protocol instance structure > + @param InterruptType Defines which interrupt to hook. IA-32 > + valid range is 0x00 through 0xFF > + @param InterruptHandler A pointer to a function of type > + EFI_CPU_INTERRUPT_HANDLER that is called > + when a processor interrupt occurs. A null > + pointer is an error condition. > + > + @retval EFI_SUCCESS If handler installed or uninstalled. > + @retval EFI_ALREADY_STARTED InterruptHandler is not NULL, and a handler > + for InterruptType was previously installed. > + @retval EFI_INVALID_PARAMETER InterruptHandler is NULL, and a handler for > + InterruptType was not previously installed. > + @retval EFI_UNSUPPORTED The interrupt specified by InterruptType > + is not supported. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuRegisterInterruptHandler ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + IN EFI_EXCEPTION_TYPE InterruptType, > + IN EFI_CPU_INTERRUPT_HANDLER InterruptHandler > + ); > + > +/** > + Returns a timer value from one of the CPU's internal timers. There is no > + inherent time interval between ticks but is a function of the CPU frequency. > + > + @param This - Protocol instance structure. > + @param TimerIndex - Specifies which CPU timer is requested. > + @param TimerValue - Pointer to the returned timer value. > + @param TimerPeriod - A pointer to the amount of time that passes > + in femtoseconds (10-15) for each increment > + of TimerValue. If TimerValue does not > + increment at a predictable rate, then 0 is > + returned. The amount of time that has > + passed between two calls to GetTimerValue() > + can be calculated with the formula > + (TimerValue2 - TimerValue1) * TimerPeriod. > + This parameter is optional and may be NULL. > + > + @retval EFI_SUCCESS - If the CPU timer count was returned. > + @retval EFI_UNSUPPORTED - If the CPU does not have any readable timers. > + @retval EFI_DEVICE_ERROR - If an error occurred while reading the timer. > + @retval EFI_INVALID_PARAMETER - TimerIndex is not valid or TimerValue is NULL. > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuGetTimerValue ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + IN UINT32 TimerIndex, > + OUT UINT64 *TimerValue, > + OUT UINT64 *TimerPeriod OPTIONAL > + ); > + > +/** > + Set memory cacheability attributes for given range of memeory. > + > + @param This Protocol instance structure > + @param BaseAddress Specifies the start address of the > + memory range > + @param Length Specifies the length of the memory range > + @param Attributes The memory cacheability for the memory range > + > + @retval EFI_SUCCESS If the cacheability of that memory range is > + set successfully > + @retval EFI_UNSUPPORTED If the desired operation cannot be done > + @retval EFI_INVALID_PARAMETER The input parameter is not correct, > + such as Length = 0 > + > +**/ > +EFI_STATUS > +EFIAPI > +CpuSetMemoryAttributes ( > + IN EFI_CPU_ARCH_PROTOCOL *This, > + IN EFI_PHYSICAL_ADDRESS BaseAddress, > + IN UINT64 Length, > + IN UINT64 Attributes > + ); > + > +#endif > + > diff --git a/RiscVPkg/Universal/CpuDxe/CpuDxe.inf b/RiscVPkg/Universal/CpuDxe/CpuDxe.inf > new file mode 100644 > index 0000000..93638e7 > --- /dev/null > +++ b/RiscVPkg/Universal/CpuDxe/CpuDxe.inf > @@ -0,0 +1,66 @@ > +## @file > +# RISC-V CPU DXE module. > +# > +# Copyright (c) 2016 - 2019, Hewlett Packard Enterprise Development LP. All rights reserved.
> +# This program and the accompanying materials > +# are licensed and made available under the terms and conditions of the BSD License > +# which accompanies this distribution. The full text of the license may be found at > +# http://opensource.org/licenses/bsd-license.php > +# > +# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, > +# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. > +# > +## > + > +[Defines] > + INF_VERSION = 0x00010005 > + BASE_NAME = CpuDxe > + MODULE_UNI_FILE = CpuDxe.uni > + FILE_GUID = 1A1E4886-9517-440e-9FDE-3BE44CEE2136 > + MODULE_TYPE = DXE_DRIVER > + VERSION_STRING = 1.0 > + > + ENTRY_POINT = InitializeCpu > + > +[Packages] > + MdePkg/MdePkg.dec > + MdeModulePkg/MdeModulePkg.dec > + RiscVPkg/RiscVPkg.dec > + > +[LibraryClasses] > + BaseLib > + BaseMemoryLib > + CpuLib > + DebugLib > + DxeServicesTableLib > + MemoryAllocationLib > + UefiBootServicesTableLib > + UefiDriverEntryPoint > + UefiLib > + CpuExceptionHandlerLib > + TimerLib > + SynchronizationLib > + HobLib > + ReportStatusCodeLib > + RiscVCpuLib > + RiscVPlatformTimerLib > + > +[Sources] > + CpuDxe.c > + CpuDxe.h > + > +[Protocols] > + gEfiCpuArchProtocolGuid ## PRODUCES > + > +[Guids] > + > +[Ppis] > + > +[Pcd] > + gUefiRiscVPkgTokenSpaceGuid.PcdRiscVMachineTimerFrequencyInHerz > + > +[Depex] > + TRUE > + > +[UserExtensions.TianoCore."ExtraFiles"] > + CpuDxeExtra.uni > diff --git a/RiscVPkg/Universal/CpuDxe/CpuDxe.uni b/RiscVPkg/Universal/CpuDxe/CpuDxe.uni > new file mode 100644 > index 0000000000000000000000000000000000000000..51e3c0c06df37e5abb4be67ca2bc73d5da4cbdd2 > GIT binary patch > literal 1564 > zcmb7^TW`}q5QXO%iT_}wFMyf^c;EpcMA90FfX2#&!c&!NYmwBI zvb?jG*)wO(&hF12O>0`j|Aa5HH#WD_7B;ho_JG;u)<$+@nO)i1ay-uM!V3H!*~A`W > zpW9P=W-siJ{(E-cI!56>iH-33Mw{D|_1G?%pE0^}tQGypj%jcB7anCvPhOFIw8R?N > z7Ap&E6@BHSnQ4FSd#8B5vbOc?^_F*;M`Qyyr+7ymHzS7}PD{okVu@LShq#FE1RhH~ > zwYFy8CH@gJqYd|z-U74=U-@bG0`H0Q7c=3O_}V?)M7W_ZrAIcV)xK+Ip zE>Xlxd{daD-d9c;Cs*xjTOUQG-Y%Dl>#b`sq5VDE6gEPX8bL3`S}~UPV|bQvbuK|y > z@t?C2&Pc4k z^;gV{@tj(HZ>0gs1%IVU)f-U5F}xBgscY|OTlR@@2US(6vIAy2)Y_0<>{<`)1RFCi > zO#(u74jt}Kj7Q&*yYy7kYHL{G3blr9`&gsH9d@Uz3$^PJBRj>b=gdx+?|>?du1D`N > z5_ioh<^W&$C~EL}i?5=8#eQH#%yoC;O_Y#DY+trG6?z9P5-LkEkGXNBZl#U z=JX$I>nGf!px+rtT`-2A#dZcG=_O@bs5OAkpS}Z5Q}^MViW$+W{!|lnu*9?mJ5@-* > zs%mn@oX)EcZrwgJIwFT5wng3O9_TjB=oKJ_dz@f1#u>927&Xu2-?LFID4yabTmA3L > c=Z71xlCjC;$Ke > > literal 0 > HcmV?d00001 > > diff --git a/RiscVPkg/Universal/CpuDxe/CpuDxeExtra.uni b/RiscVPkg/Universal/CpuDxe/CpuDxeExtra.uni > new file mode 100644 > index 0000000000000000000000000000000000000000..e6201a906ae37cfb24a6b501d9789d28f15b96f7 > GIT binary patch > literal 1392 > zcmZXU+iwz45XR@(#Q))hzNl$I`{08yMqpP zmpL=veCM0l{rjh34GX+)c!GVlYfEflSN76gVAWaM)^=x+Jz@=ZYAc)C7@x#`W0_$) > zx2>h@Z*6WH_G4DExADE@?8?Uiv6!>-we381ZZ~)adj zr%#5d{bEc#Pn>5-VJaRQXBsiy^Dbbqwk0cZ(GB`mXKr$`U{*wyUEEXr6rXzR49}0& > zvVnan6{+|S;jC=I^R7Ti;k0C5D6qvts)_Fu9!orRw#(HDSjMi9SV+}PnMYA#6R;*k > zi@%sj*#ckDvpmB+Yt?RS6Gp||5uwwRb-_f{NXh!NPGTm{1h2%`I$hBVRa}cIN9<3Z > zajCR;a4n{c|KBztrx3*<(@VKF>~-r2Jd3=lOEBpw{@0vjH4^Jby!Kf=S0+<)hu0*J > zU*#Hz)Aot7>a{Jk_~1RR{>apof9hJ-xqnJU8++<+uuR}Sv!lI}Iw&{1g(k(U` zt3G|yv#*RzJ7eEL(}1d)hgdsw+K5%`N{_6|9AmE#sw#B&x?()e9l6I!9j&p(EL@@1 > zm|MQr?y%$*><8!K)$@$nH_0SsUF;oDh0*iu19svrn{p2El8>@xUSIH4 z+&IsY-6FP&5~o7%phcg)QqG9)t>T}X^!Jf=m$|xqPzL1 zIs!k&rwhw7R>9E@sGz>2IaMDss^`=PNBE1MveiJ7c5STRu{FIv)W_<{DWf_@U#=>7 > Q;n)$D#Qz^D@j@xye-~NTv;Y7A > > literal 0 > HcmV?d00001 > > diff --git a/RiscVPkg/Universal/CpuDxe/CpuMp.h b/RiscVPkg/Universal/CpuDxe/CpuMp.h > new file mode 100644 > index 0000000..adb3ef3 > --- /dev/null > +++ b/RiscVPkg/Universal/CpuDxe/CpuMp.h > @@ -0,0 +1,648 @@ > +/** @file > + RISC-V CPU DXE MP definitions. > + > + Copyright (c) 2016, Hewlett Packard Enterprise Development LP. All rights reserved.
> + > + This program and the accompanying materials are > + licensed and made available under the terms and conditions of the BSD License > + which accompanies this distribution. The full text of the license may be found at > + http://opensource.org/licenses/bsd-license.php > + > + THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, > + WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. > + > +**/ > + > +#ifndef _CPU_MP_H_ > +#define _CPU_MP_H_ > + > +#include > +#include > +#include > +#include > +#include > +#include > + > +/** > + Initialize Multi-processor support. > + > +**/ > +VOID > +InitializeMpSupport ( > + VOID > + ); > + > +typedef > +VOID > +(EFIAPI *STACKLESS_AP_ENTRY_POINT)( > + VOID > + ); > + > +/** > + Starts the Application Processors and directs them to jump to the > + specified routine. > + > + The processor jumps to this code in flat mode, but the processor's > + stack is not initialized. > + > + @retval EFI_SUCCESS The APs were started > + > +**/ > +EFI_STATUS > +StartApsStackless ( > + VOID > + ); > + > +/** > + The AP entry point that the Startup-IPI target code will jump to. > + > + The processor jumps to this code in flat mode, but the processor's > + stack is not initialized. > + > +**/ > +VOID > +EFIAPI > +AsmApEntryPoint ( > + VOID > + ); > + > +/** > + Releases the lock preventing other APs from using the shared AP > + stack. > + > + Once the AP has transitioned to using a new stack, it can call this > + function to allow another AP to proceed with using the shared stack. > + > +**/ > +VOID > +EFIAPI > +AsmApDoneWithCommonStack ( > + VOID > + ); > + > +typedef enum { > + CpuStateIdle, > + CpuStateBlocked, > + CpuStateReady, > + CpuStateBusy, > + CpuStateFinished, > + CpuStateSleeping > +} CPU_STATE; > + > +/** > + Define Individual Processor Data block. > + > +**/ > +typedef struct { > + EFI_PROCESSOR_INFORMATION Info; > + SPIN_LOCK CpuDataLock; > + INTN LockSelf; > + volatile CPU_STATE State; > + > + volatile EFI_AP_PROCEDURE Procedure; > + volatile VOID* Parameter; > + BOOLEAN *Finished; > + INTN Timeout; > + EFI_EVENT WaitEvent; > + BOOLEAN TimeoutActive; > + EFI_EVENT CheckThisAPEvent; > + VOID *TopOfStack; > +} CPU_DATA_BLOCK; > + > +/** > + Define MP data block which consumes individual processor block. > + > +**/ > +typedef struct { > + CPU_DATA_BLOCK *CpuDatas; > + UINTN NumberOfProcessors; > + UINTN NumberOfEnabledProcessors; > + > + EFI_AP_PROCEDURE Procedure; > + VOID *ProcedureArgument; > + UINTN StartCount; > + UINTN FinishCount; > + BOOLEAN SingleThread; > + UINTN **FailedList; > + UINTN FailedListIndex; > + INTN Timeout; > + EFI_EVENT WaitEvent; > + BOOLEAN TimeoutActive; > + EFI_EVENT CheckAllAPsEvent; > +} MP_SYSTEM_DATA; > + > +/** > + This function is called by all processors (both BSP and AP) once and collects MP related data. > + > + @param Bsp TRUE if the CPU is BSP > + @param ProcessorNumber The specific processor number > + > + @retval EFI_SUCCESS Data for the processor collected and filled in > + > +**/ > +EFI_STATUS > +FillInProcessorInformation ( > + IN BOOLEAN Bsp, > + IN UINTN ProcessorNumber > + ); > + > +/** > + This service retrieves the number of logical processor in the platform > + and the number of those logical processors that are enabled on this boot. > + This service may only be called from the BSP. > + > + This function is used to retrieve the following information: > + - The number of logical processors that are present in the system. > + - The number of enabled logical processors in the system at the instant > + this call is made. > + > + Because MP Service Protocol provides services to enable and disable processors > + dynamically, the number of enabled logical processors may vary during the > + course of a boot session. > + > + If this service is called from an AP, then EFI_DEVICE_ERROR is returned. > + If NumberOfProcessors or NumberOfEnabledProcessors is NULL, then > + EFI_INVALID_PARAMETER is returned. Otherwise, the total number of processors > + is returned in NumberOfProcessors, the number of currently enabled processor > + is returned in NumberOfEnabledProcessors, and EFI_SUCCESS is returned. > + > + @param[in] This A pointer to the EFI_MP_SERVICES_PROTOCOL > + instance. > + @param[out] NumberOfProcessors Pointer to the total number of logical > + processors in the system, including the BSP > + and disabled APs. > + @param[out] NumberOfEnabledProcessors Pointer to the number of enabled logical > + processors that exist in system, including > + the BSP. > + > + @retval EFI_SUCCESS The number of logical processors and enabled > + logical processors was retrieved. > + @retval EFI_DEVICE_ERROR The calling processor is an AP. > + @retval EFI_INVALID_PARAMETER NumberOfProcessors is NULL. > + @retval EFI_INVALID_PARAMETER NumberOfEnabledProcessors is NULL. > + > +**/ > +EFI_STATUS > +EFIAPI > +GetNumberOfProcessors ( > + IN EFI_MP_SERVICES_PROTOCOL *This, > + OUT UINTN *NumberOfProcessors, > + OUT UINTN *NumberOfEnabledProcessors > + ); > + > +/** > + Gets detailed MP-related information on the requested processor at the > + instant this call is made. This service may only be called from the BSP. > + > + This service retrieves detailed MP-related information about any processor > + on the platform. Note the following: > + - The processor information may change during the course of a boot session. > + - The information presented here is entirely MP related. > + > + Information regarding the number of caches and their sizes, frequency of operation, > + slot numbers is all considered platform-related information and is not provided > + by this service. > + > + @param[in] This A pointer to the EFI_MP_SERVICES_PROTOCOL > + instance. > + @param[in] ProcessorNumber The handle number of processor. > + @param[out] ProcessorInfoBuffer A pointer to the buffer where information for > + the requested processor is deposited. > + > + @retval EFI_SUCCESS Processor information was returned. > + @retval EFI_DEVICE_ERROR The calling processor is an AP. > + @retval EFI_INVALID_PARAMETER ProcessorInfoBuffer is NULL. > + @retval EFI_NOT_FOUND The processor with the handle specified by > + ProcessorNumber does not exist in the platform. > + > +**/ > +EFI_STATUS > +EFIAPI > +GetProcessorInfo ( > + IN EFI_MP_SERVICES_PROTOCOL *This, > + IN UINTN ProcessorNumber, > + OUT EFI_PROCESSOR_INFORMATION *ProcessorInfoBuffer > + ); > + > +/** > + This service executes a caller provided function on all enabled APs. APs can > + run either simultaneously or one at a time in sequence. This service supports > + both blocking and non-blocking requests. The non-blocking requests use EFI > + events so the BSP can detect when the APs have finished. This service may only > + be called from the BSP. > + > + This function is used to dispatch all the enabled APs to the function specified > + by Procedure. If any enabled AP is busy, then EFI_NOT_READY is returned > + immediately and Procedure is not started on any AP. > + > + If SingleThread is TRUE, all the enabled APs execute the function specified by > + Procedure one by one, in ascending order of processor handle number. Otherwise, > + all the enabled APs execute the function specified by Procedure simultaneously. > + > + If WaitEvent is NULL, execution is in blocking mode. The BSP waits until all > + APs finish or TimeoutInMicroseconds expires. Otherwise, execution is in non-blocking > + mode, and the BSP returns from this service without waiting for APs. If a > + non-blocking mode is requested after the UEFI Event EFI_EVENT_GROUP_READY_TO_BOOT > + is signaled, then EFI_UNSUPPORTED must be returned. > + > + If the timeout specified by TimeoutInMicroseconds expires before all APs return > + from Procedure, then Procedure on the failed APs is terminated. All enabled APs > + are always available for further calls to EFI_MP_SERVICES_PROTOCOL.StartupAllAPs() > + and EFI_MP_SERVICES_PROTOCOL.StartupThisAP(). If FailedCpuList is not NULL, its > + content points to the list of processor handle numbers in which Procedure was > + terminated. > + > + Note: It is the responsibility of the consumer of the EFI_MP_SERVICES_PROTOCOL.StartupAllAPs() > + to make sure that the nature of the code that is executed on the BSP and the > + dispatched APs is well controlled. The MP Services Protocol does not guarantee > + that the Procedure function is MP-safe. Hence, the tasks that can be run in > + parallel are limited to certain independent tasks and well-controlled exclusive > + code. EFI services and protocols may not be called by APs unless otherwise > + specified. > + > + In blocking execution mode, BSP waits until all APs finish or > + TimeoutInMicroseconds expires. > + > + In non-blocking execution mode, BSP is freed to return to the caller and then > + proceed to the next task without having to wait for APs. The following > + sequence needs to occur in a non-blocking execution mode: > + > + -# The caller that intends to use this MP Services Protocol in non-blocking > + mode creates WaitEvent by calling the EFI CreateEvent() service. The caller > + invokes EFI_MP_SERVICES_PROTOCOL.StartupAllAPs(). If the parameter WaitEvent > + is not NULL, then StartupAllAPs() executes in non-blocking mode. It requests > + the function specified by Procedure to be started on all the enabled APs, > + and releases the BSP to continue with other tasks. > + -# The caller can use the CheckEvent() and WaitForEvent() services to check > + the state of the WaitEvent created in step 1. > + -# When the APs complete their task or TimeoutInMicroSecondss expires, the MP > + Service signals WaitEvent by calling the EFI SignalEvent() function. If > + FailedCpuList is not NULL, its content is available when WaitEvent is > + signaled. If all APs returned from Procedure prior to the timeout, then > + FailedCpuList is set to NULL. If not all APs return from Procedure before > + the timeout, then FailedCpuList is filled in with the list of the failed > + APs. The buffer is allocated by MP Service Protocol using AllocatePool(). > + It is the caller's responsibility to free the buffer with FreePool() service. > + -# This invocation of SignalEvent() function informs the caller that invoked > + EFI_MP_SERVICES_PROTOCOL.StartupAllAPs() that either all the APs completed > + the specified task or a timeout occurred. The contents of FailedCpuList > + can be examined to determine which APs did not complete the specified task > + prior to the timeout. > + > + @param[in] This A pointer to the EFI_MP_SERVICES_PROTOCOL > + instance. > + @param[in] Procedure A pointer to the function to be run on > + enabled APs of the system. See type > + EFI_AP_PROCEDURE. > + @param[in] SingleThread If TRUE, then all the enabled APs execute > + the function specified by Procedure one by > + one, in ascending order of processor handle > + number. If FALSE, then all the enabled APs > + execute the function specified by Procedure > + simultaneously. > + @param[in] WaitEvent The event created by the caller with CreateEvent() > + service. If it is NULL, then execute in > + blocking mode. BSP waits until all APs finish > + or TimeoutInMicroseconds expires. If it's > + not NULL, then execute in non-blocking mode. > + BSP requests the function specified by > + Procedure to be started on all the enabled > + APs, and go on executing immediately. If > + all return from Procedure, or TimeoutInMicroseconds > + expires, this event is signaled. The BSP > + can use the CheckEvent() or WaitForEvent() > + services to check the state of event. Type > + EFI_EVENT is defined in CreateEvent() in > + the Unified Extensible Firmware Interface > + Specification. > + @param[in] TimeoutInMicroseconds Indicates the time limit in microseconds for > + APs to return from Procedure, either for > + blocking or non-blocking mode. Zero means > + infinity. If the timeout expires before > + all APs return from Procedure, then Procedure > + on the failed APs is terminated. All enabled > + APs are available for next function assigned > + by EFI_MP_SERVICES_PROTOCOL.StartupAllAPs() > + or EFI_MP_SERVICES_PROTOCOL.StartupThisAP(). > + If the timeout expires in blocking mode, > + BSP returns EFI_TIMEOUT. If the timeout > + expires in non-blocking mode, WaitEvent > + is signaled with SignalEvent(). > + @param[in] ProcedureArgument The parameter passed into Procedure for > + all APs. > + @param[out] FailedCpuList If NULL, this parameter is ignored. Otherwise, > + if all APs finish successfully, then its > + content is set to NULL. If not all APs > + finish before timeout expires, then its > + content is set to address of the buffer > + holding handle numbers of the failed APs. > + The buffer is allocated by MP Service Protocol, > + and it's the caller's responsibility to > + free the buffer with FreePool() service. > + In blocking mode, it is ready for consumption > + when the call returns. In non-blocking mode, > + it is ready when WaitEvent is signaled. The > + list of failed CPU is terminated by > + END_OF_CPU_LIST. > + > + @retval EFI_SUCCESS In blocking mode, all APs have finished before > + the timeout expired. > + @retval EFI_SUCCESS In non-blocking mode, function has been dispatched > + to all enabled APs. > + @retval EFI_UNSUPPORTED A non-blocking mode request was made after the > + UEFI event EFI_EVENT_GROUP_READY_TO_BOOT was > + signaled. > + @retval EFI_DEVICE_ERROR Caller processor is AP. > + @retval EFI_NOT_STARTED No enabled APs exist in the system. > + @retval EFI_NOT_READY Any enabled APs are busy. > + @retval EFI_TIMEOUT In blocking mode, the timeout expired before > + all enabled APs have finished. > + @retval EFI_INVALID_PARAMETER Procedure is NULL. > + > +**/ > +EFI_STATUS > +EFIAPI > +StartupAllAPs ( > + IN EFI_MP_SERVICES_PROTOCOL *This, > + IN EFI_AP_PROCEDURE Procedure, > + IN BOOLEAN SingleThread, > + IN EFI_EVENT WaitEvent OPTIONAL, > + IN UINTN TimeoutInMicroseconds, > + IN VOID *ProcedureArgument OPTIONAL, > + OUT UINTN **FailedCpuList OPTIONAL > + ); > + > +/** > + This service lets the caller get one enabled AP to execute a caller-provided > + function. The caller can request the BSP to either wait for the completion > + of the AP or just proceed with the next task by using the EFI event mechanism. > + See EFI_MP_SERVICES_PROTOCOL.StartupAllAPs() for more details on non-blocking > + execution support. This service may only be called from the BSP. > + > + This function is used to dispatch one enabled AP to the function specified by > + Procedure passing in the argument specified by ProcedureArgument. If WaitEvent > + is NULL, execution is in blocking mode. The BSP waits until the AP finishes or > + TimeoutInMicroSecondss expires. Otherwise, execution is in non-blocking mode. > + BSP proceeds to the next task without waiting for the AP. If a non-blocking mode > + is requested after the UEFI Event EFI_EVENT_GROUP_READY_TO_BOOT is signaled, > + then EFI_UNSUPPORTED must be returned. > + > + If the timeout specified by TimeoutInMicroseconds expires before the AP returns > + from Procedure, then execution of Procedure by the AP is terminated. The AP is > + available for subsequent calls to EFI_MP_SERVICES_PROTOCOL.StartupAllAPs() and > + EFI_MP_SERVICES_PROTOCOL.StartupThisAP(). > + > + @param[in] This A pointer to the EFI_MP_SERVICES_PROTOCOL > + instance. > + @param[in] Procedure A pointer to the function to be run on > + enabled APs of the system. See type > + EFI_AP_PROCEDURE. > + @param[in] ProcessorNumber The handle number of the AP. The range is > + from 0 to the total number of logical > + processors minus 1. The total number of > + logical processors can be retrieved by > + EFI_MP_SERVICES_PROTOCOL.GetNumberOfProcessors(). > + @param[in] WaitEvent The event created by the caller with CreateEvent() > + service. If it is NULL, then execute in > + blocking mode. BSP waits until all APs finish > + or TimeoutInMicroseconds expires. If it's > + not NULL, then execute in non-blocking mode. > + BSP requests the function specified by > + Procedure to be started on all the enabled > + APs, and go on executing immediately. If > + all return from Procedure or TimeoutInMicroseconds > + expires, this event is signaled. The BSP > + can use the CheckEvent() or WaitForEvent() > + services to check the state of event. Type > + EFI_EVENT is defined in CreateEvent() in > + the Unified Extensible Firmware Interface > + Specification. > + @param[in] TimeoutInMicroseconds Indicates the time limit in microseconds for > + APs to return from Procedure, either for > + blocking or non-blocking mode. Zero means > + infinity. If the timeout expires before > + all APs return from Procedure, then Procedure > + on the failed APs is terminated. All enabled > + APs are available for next function assigned > + by EFI_MP_SERVICES_PROTOCOL.StartupAllAPs() > + or EFI_MP_SERVICES_PROTOCOL.StartupThisAP(). > + If the timeout expires in blocking mode, > + BSP returns EFI_TIMEOUT. If the timeout > + expires in non-blocking mode, WaitEvent > + is signaled with SignalEvent(). > + @param[in] ProcedureArgument The parameter passed into Procedure for > + all APs. > + @param[out] Finished If NULL, this parameter is ignored. In > + blocking mode, this parameter is ignored. > + In non-blocking mode, if AP returns from > + Procedure before the timeout expires, its > + content is set to TRUE. Otherwise, the > + value is set to FALSE. The caller can > + determine if the AP returned from Procedure > + by evaluating this value. > + > + @retval EFI_SUCCESS In blocking mode, specified AP finished before > + the timeout expires. > + @retval EFI_SUCCESS In non-blocking mode, the function has been > + dispatched to specified AP. > + @retval EFI_UNSUPPORTED A non-blocking mode request was made after the > + UEFI event EFI_EVENT_GROUP_READY_TO_BOOT was > + signaled. > + @retval EFI_DEVICE_ERROR The calling processor is an AP. > + @retval EFI_TIMEOUT In blocking mode, the timeout expired before > + the specified AP has finished. > + @retval EFI_NOT_READY The specified AP is busy. > + @retval EFI_NOT_FOUND The processor with the handle specified by > + ProcessorNumber does not exist. > + @retval EFI_INVALID_PARAMETER ProcessorNumber specifies the BSP or disabled AP. > + @retval EFI_INVALID_PARAMETER Procedure is NULL. > + > +**/ > +EFI_STATUS > +EFIAPI > +StartupThisAP ( > + IN EFI_MP_SERVICES_PROTOCOL *This, > + IN EFI_AP_PROCEDURE Procedure, > + IN UINTN ProcessorNumber, > + IN EFI_EVENT WaitEvent OPTIONAL, > + IN UINTN TimeoutInMicroseconds, > + IN VOID *ProcedureArgument OPTIONAL, > + OUT BOOLEAN *Finished OPTIONAL > + ); > + > +/** > + This service switches the requested AP to be the BSP from that point onward. > + This service changes the BSP for all purposes. This call can only be performed > + by the current BSP. > + > + This service switches the requested AP to be the BSP from that point onward. > + This service changes the BSP for all purposes. The new BSP can take over the > + execution of the old BSP and continue seamlessly from where the old one left > + off. This service may not be supported after the UEFI Event EFI_EVENT_GROUP_READY_TO_BOOT > + is signaled. > + > + If the BSP cannot be switched prior to the return from this service, then > + EFI_UNSUPPORTED must be returned. > + > + @param[in] This A pointer to the EFI_MP_SERVICES_PROTOCOL instance. > + @param[in] ProcessorNumber The handle number of AP that is to become the new > + BSP. The range is from 0 to the total number of > + logical processors minus 1. The total number of > + logical processors can be retrieved by > + EFI_MP_SERVICES_PROTOCOL.GetNumberOfProcessors(). > + @param[in] EnableOldBSP If TRUE, then the old BSP will be listed as an > + enabled AP. Otherwise, it will be disabled. > + > + @retval EFI_SUCCESS BSP successfully switched. > + @retval EFI_UNSUPPORTED Switching the BSP cannot be completed prior to > + this service returning. > + @retval EFI_UNSUPPORTED Switching the BSP is not supported. > + @retval EFI_SUCCESS The calling processor is an AP. > + @retval EFI_NOT_FOUND The processor with the handle specified by > + ProcessorNumber does not exist. > + @retval EFI_INVALID_PARAMETER ProcessorNumber specifies the current BSP or > + a disabled AP. > + @retval EFI_NOT_READY The specified AP is busy. > + > +**/ > +EFI_STATUS > +EFIAPI > +SwitchBSP ( > + IN EFI_MP_SERVICES_PROTOCOL *This, > + IN UINTN ProcessorNumber, > + IN BOOLEAN EnableOldBSP > + ); > + > +/** > + This service lets the caller enable or disable an AP from this point onward. > + This service may only be called from the BSP. > + > + This service allows the caller enable or disable an AP from this point onward. > + The caller can optionally specify the health status of the AP by Health. If > + an AP is being disabled, then the state of the disabled AP is implementation > + dependent. If an AP is enabled, then the implementation must guarantee that a > + complete initialization sequence is performed on the AP, so the AP is in a state > + that is compatible with an MP operating system. This service may not be supported > + after the UEFI Event EFI_EVENT_GROUP_READY_TO_BOOT is signaled. > + > + If the enable or disable AP operation cannot be completed prior to the return > + from this service, then EFI_UNSUPPORTED must be returned. > + > + @param[in] This A pointer to the EFI_MP_SERVICES_PROTOCOL instance. > + @param[in] ProcessorNumber The handle number of AP that is to become the new > + BSP. The range is from 0 to the total number of > + logical processors minus 1. The total number of > + logical processors can be retrieved by > + EFI_MP_SERVICES_PROTOCOL.GetNumberOfProcessors(). > + @param[in] EnableAP Specifies the new state for the processor for > + enabled, FALSE for disabled. > + @param[in] HealthFlag If not NULL, a pointer to a value that specifies > + the new health status of the AP. This flag > + corresponds to StatusFlag defined in > + EFI_MP_SERVICES_PROTOCOL.GetProcessorInfo(). Only > + the PROCESSOR_HEALTH_STATUS_BIT is used. All other > + bits are ignored. If it is NULL, this parameter > + is ignored. > + > + @retval EFI_SUCCESS The specified AP was enabled or disabled successfully. > + @retval EFI_UNSUPPORTED Enabling or disabling an AP cannot be completed > + prior to this service returning. > + @retval EFI_UNSUPPORTED Enabling or disabling an AP is not supported. > + @retval EFI_DEVICE_ERROR The calling processor is an AP. > + @retval EFI_NOT_FOUND Processor with the handle specified by ProcessorNumber > + does not exist. > + @retval EFI_INVALID_PARAMETER ProcessorNumber specifies the BSP. > + > +**/ > +EFI_STATUS > +EFIAPI > +EnableDisableAP ( > + IN EFI_MP_SERVICES_PROTOCOL *This, > + IN UINTN ProcessorNumber, > + IN BOOLEAN EnableAP, > + IN UINT32 *HealthFlag OPTIONAL > + ); > + > +/** > + This return the handle number for the calling processor. This service may be > + called from the BSP and APs. > + > + This service returns the processor handle number for the calling processor. > + The returned value is in the range from 0 to the total number of logical > + processors minus 1. The total number of logical processors can be retrieved > + with EFI_MP_SERVICES_PROTOCOL.GetNumberOfProcessors(). This service may be > + called from the BSP and APs. If ProcessorNumber is NULL, then EFI_INVALID_PARAMETER > + is returned. Otherwise, the current processors handle number is returned in > + ProcessorNumber, and EFI_SUCCESS is returned. > + > + @param[in] This A pointer to the EFI_MP_SERVICES_PROTOCOL instance. > + @param[out] ProcessorNumber The handle number of AP that is to become the new > + BSP. The range is from 0 to the total number of > + logical processors minus 1. The total number of > + logical processors can be retrieved by > + EFI_MP_SERVICES_PROTOCOL.GetNumberOfProcessors(). > + > + @retval EFI_SUCCESS The current processor handle number was returned > + in ProcessorNumber. > + @retval EFI_INVALID_PARAMETER ProcessorNumber is NULL. > + > +**/ > +EFI_STATUS > +EFIAPI > +WhoAmI ( > + IN EFI_MP_SERVICES_PROTOCOL *This, > + OUT UINTN *ProcessorNumber > + ); > + > +/** > + Terminate AP's task and set it to idle state. > + > + This function terminates AP's task due to timeout by sending INIT-SIPI, > + and sends it to idle state. > + > + @param CpuData the pointer to CPU_DATA_BLOCK of specified AP > + > +**/ > +VOID > +ResetProcessorToIdleState ( > + IN CPU_DATA_BLOCK *CpuData > + ); > + > +/** > + Prepares Startup Code for APs. > + This function prepares Startup Code for APs. > + > + @retval EFI_SUCCESS The APs were started > + @retval EFI_OUT_OF_RESOURCES Cannot allocate memory to start APs > + > +**/ > +EFI_STATUS > +PrepareAPStartupCode ( > + VOID > + ); > + > +/** > + Free the code buffer of startup AP. > + > +**/ > +VOID > +FreeApStartupCode ( > + VOID > + ); > + > +/** > + Resets the Application Processor and directs it to jump to the > + specified routine. > + > + The processor jumps to this code in flat mode, but the processor's > + stack is not initialized. > + > + @param ProcessorId the AP of ProcessorId was reset > +**/ > +VOID > +ResetApStackless ( > + IN UINT32 ProcessorId > + ); > + > +#endif // _CPU_MP_H_ > + > -- > 2.7.4 > > > >