EDK2 doxygen online documents - Firmware Encoding Index 1
EDK2 doxygen online documents - Firmware Encoding Index

MdePkg/Library/DxeRuntimeExtendedSalLib/ExtendedSalLib.c

Go to the documentation of this file.
00001 
00015 #include <PiDxe.h>
00016 
00017 #include <Protocol/ExtendedSalBootService.h>
00018 #include <Protocol/ExtendedSalServiceClasses.h>
00019 #include <Guid/EventGroup.h>
00020 
00021 #include <Library/ExtendedSalLib.h>
00022 #include <Library/UefiBootServicesTableLib.h>
00023 #include <Library/UefiRuntimeServicesTableLib.h>
00024 #include <Library/UefiRuntimeLib.h>
00025 #include <Library/DebugLib.h>
00026 
00039 SAL_RETURN_REGS
00040 EFIAPI
00041 SetEsalVirtualEntryPoint (
00042   IN  UINT64  EntryPoint,
00043   IN  UINT64  Gp
00044   );
00045 
00058 SAL_RETURN_REGS
00059 EFIAPI
00060 SetEsalPhysicalEntryPoint (
00061   IN  UINT64  EntryPoint,
00062   IN  UINT64  Gp
00063   );
00064 
00077 SAL_RETURN_REGS
00078 EFIAPI
00079 GetEsalEntryPoint (
00080   VOID
00081   );
00082 
00083 EXTENDED_SAL_BOOT_SERVICE_PROTOCOL  *mEsalBootService = NULL;
00084 EFI_PLABEL                          mPlabel;
00085 EFI_EVENT                           mEfiVirtualNotifyEvent;
00086 
00099 VOID
00100 EFIAPI
00101 ExtendedSalVirtualNotifyEvent (
00102   IN EFI_EVENT        Event,
00103   IN VOID             *Context
00104   )
00105 {
00106   UINT64  PhysicalEntryPoint;
00107 
00108   PhysicalEntryPoint = mPlabel.EntryPoint;
00109 
00110   gRT->ConvertPointer (0x0, (VOID **) &mPlabel.EntryPoint);
00111 
00112   mPlabel.GP += mPlabel.EntryPoint - PhysicalEntryPoint;
00113 
00114   SetEsalVirtualEntryPoint (mPlabel.EntryPoint, mPlabel.GP);
00115 }
00116 
00128 EFI_STATUS
00129 DxeSalLibInitialize (
00130   VOID
00131   )
00132 {
00133   EFI_PLABEL  *Plabel;
00134   EFI_STATUS  Status;
00135 
00136   //
00137   // The protocol contains a function pointer, which is an indirect procedure call.
00138   // An indirect procedure call goes through a plabel, and pointer to a function is
00139   // a pointer to a plabel. To implement indirect procedure calls that can work in
00140   // both physical and virtual mode, two plabels are required (one physical and one
00141   // virtual). So lets grap the physical PLABEL for the EsalEntryPoint and store it
00142   // away. We cache it in a module global, so we can register the vitrual version.
00143   //
00144   Status = gBS->LocateProtocol (&gEfiExtendedSalBootServiceProtocolGuid, NULL, (VOID **) &mEsalBootService);
00145   ASSERT_EFI_ERROR (Status);
00146 
00147   Plabel              = (EFI_PLABEL *) (UINTN) mEsalBootService->ExtendedSalProc;
00148   mPlabel.EntryPoint  = Plabel->EntryPoint;
00149   mPlabel.GP          = Plabel->GP;
00150   //
00151   // Stores the physical plabel of ESAL entrypoint where GetEsalEntryPoint() can easily retrieve.
00152   //
00153   SetEsalPhysicalEntryPoint (mPlabel.EntryPoint, mPlabel.GP);
00154 
00155   return EFI_SUCCESS;
00156 }
00157 
00172 EFI_STATUS
00173 EFIAPI
00174 DxeRuntimeExtendedSalLibConstruct (
00175   IN EFI_HANDLE           ImageHandle,
00176   IN EFI_SYSTEM_TABLE     *SystemTable
00177   )
00178 {
00179   EFI_STATUS  Status;
00180 
00181   //
00182   // Register notify function for EVT_SIGNAL_VIRTUAL_ADDRESS_CHANGE
00183   //
00184   ASSERT (gBS != NULL);
00185 
00186   DxeSalLibInitialize ();
00187 
00188   Status = gBS->CreateEventEx (
00189                   EVT_NOTIFY_SIGNAL,
00190                   TPL_NOTIFY,
00191                   ExtendedSalVirtualNotifyEvent,
00192                   NULL,
00193                   &gEfiEventVirtualAddressChangeGuid,
00194                   &mEfiVirtualNotifyEvent
00195                   );
00196 
00197   ASSERT_EFI_ERROR (Status);
00198 
00199   return EFI_SUCCESS;
00200 }
00201 
00214 EFI_STATUS
00215 EFIAPI
00216 DxeRuntimeExtendedSalLibDeconstruct (
00217   IN EFI_HANDLE        ImageHandle,
00218   IN EFI_SYSTEM_TABLE  *SystemTable
00219   )
00220 {
00221   EFI_STATUS  Status;
00222 
00223   //
00224   // Close SetVirtualAddressMap () notify function
00225   //
00226   ASSERT (gBS != NULL);
00227   Status = gBS->CloseEvent (mEfiVirtualNotifyEvent);
00228   ASSERT_EFI_ERROR (Status);
00229 
00230   return EFI_SUCCESS;
00231 }
00232 
00249 EFI_STATUS
00250 RegisterEsalFunction (
00251   IN  UINT64                                    FunctionId,
00252   IN  UINT64                                    ClassGuidLo,
00253   IN  UINT64                                    ClassGuidHi,
00254   IN  SAL_INTERNAL_EXTENDED_SAL_PROC            Function,
00255   IN  VOID                                      *ModuleGlobal
00256   )
00257 {
00258   return mEsalBootService->RegisterExtendedSalProc (
00259                              mEsalBootService,
00260                              ClassGuidLo,
00261                              ClassGuidHi,
00262                              FunctionId,
00263                              Function,
00264                              ModuleGlobal
00265                              );
00266 }
00267 
00286 EFI_STATUS
00287 EFIAPI
00288 RegisterEsalClass (
00289   IN  CONST UINT64    ClassGuidLo,
00290   IN  CONST UINT64    ClassGuidHi,
00291   IN  VOID            *ModuleGlobal,  OPTIONAL
00292   ...
00293   )
00294 {
00295   VA_LIST                         Args;
00296   EFI_STATUS                      Status;
00297   SAL_INTERNAL_EXTENDED_SAL_PROC  Function;
00298   UINT64                          FunctionId;
00299   EFI_HANDLE                      NewHandle;
00300   EFI_GUID                        ClassGuid;
00301 
00302   VA_START (Args, ModuleGlobal);
00303 
00304   //
00305   // Register all functions of the class to register.
00306   //
00307   Status = EFI_SUCCESS;
00308   while (!EFI_ERROR (Status)) {
00309     Function = (SAL_INTERNAL_EXTENDED_SAL_PROC) VA_ARG (Args, SAL_INTERNAL_EXTENDED_SAL_PROC);
00310     //
00311     // NULL serves as the end mark of function list
00312     //
00313     if (Function == NULL) {
00314       break;
00315     }
00316 
00317     FunctionId  = VA_ARG (Args, UINT64);
00318 
00319     Status      = RegisterEsalFunction (FunctionId, ClassGuidLo, ClassGuidHi, Function, ModuleGlobal);
00320   }
00321 
00322   if (EFI_ERROR (Status)) {
00323     return Status;
00324   }
00325 
00326   NewHandle = NULL;
00327   *((UINT64 *)(&ClassGuid) + 0) = ClassGuidLo;
00328   *((UINT64 *)(&ClassGuid) + 1) = ClassGuidHi;
00329   return gBS->InstallProtocolInterface (
00330                 &NewHandle,
00331                 &ClassGuid,
00332                 EFI_NATIVE_INTERFACE,
00333                 NULL
00334                 );
00335 }
00336 
00361 SAL_RETURN_REGS
00362 EFIAPI
00363 EsalCall (
00364   IN  UINT64    ClassGuidLo,
00365   IN  UINT64    ClassGuidHi,
00366   IN  UINT64    FunctionId,
00367   IN  UINT64    Arg2,
00368   IN  UINT64    Arg3,
00369   IN  UINT64    Arg4,
00370   IN  UINT64    Arg5,
00371   IN  UINT64    Arg6,
00372   IN  UINT64    Arg7,
00373   IN  UINT64    Arg8
00374   )
00375 {
00376   SAL_RETURN_REGS       ReturnReg;
00377   EXTENDED_SAL_PROC     EsalProc;
00378 
00379   //
00380   // Get the entrypoint of Extended SAL
00381   //
00382   ReturnReg = GetEsalEntryPoint ();
00383   if (*(UINT64 *)ReturnReg.r9 == 0 && *(UINT64 *)(ReturnReg.r9 + 8) == 0) {
00384     //
00385     // The ESAL Entry Point could not be initialized
00386     //
00387     ReturnReg.Status = EFI_SAL_ERROR;
00388     return ReturnReg;
00389   }
00390 
00391   //
00392   // Test PSR.it which is BIT36
00393   //
00394   if ((ReturnReg.r11 & BIT36) != 0) {
00395     //
00396     // Virtual mode plabel to entry point
00397     //
00398     EsalProc = (EXTENDED_SAL_PROC) ReturnReg.r10;
00399   } else {
00400     //
00401     // Physical mode plabel to entry point
00402     //
00403     EsalProc = (EXTENDED_SAL_PROC) ReturnReg.r9;
00404   }
00405 
00406   return EsalProc (
00407            ClassGuidLo,
00408            ClassGuidHi,
00409            FunctionId,
00410            Arg2,
00411            Arg3,
00412            Arg4,
00413            Arg5,
00414            Arg6,
00415            Arg7,
00416            Arg8
00417            );
00418 }
00419 
00433 SAL_RETURN_REGS
00434 EFIAPI
00435 EsalStall (
00436   IN UINTN  Microseconds
00437   )
00438 {
00439   return EsalCall (
00440            EFI_EXTENDED_SAL_STALL_SERVICES_PROTOCOL_GUID_LO, 
00441            EFI_EXTENDED_SAL_STALL_SERVICES_PROTOCOL_GUID_HI, 
00442            StallFunctionId, 
00443            Microseconds, 
00444            0, 
00445            0, 
00446            0, 
00447            0, 
00448            0, 
00449            0
00450            );
00451 }
00452 
00469 SAL_RETURN_REGS
00470 EFIAPI
00471 EsalSetNewPalEntry (
00472   IN BOOLEAN  PhysicalAddress,
00473   IN UINT64   PalEntryPoint
00474   )
00475 {
00476   return EsalCall (
00477            EFI_EXTENDED_SAL_PAL_SERVICES_PROTOCOL_GUID_LO, 
00478            EFI_EXTENDED_SAL_PAL_SERVICES_PROTOCOL_GUID_HI,
00479            SetNewPalEntryFunctionId, 
00480            PhysicalAddress, 
00481            PalEntryPoint, 
00482            0, 
00483            0, 
00484            0, 
00485            0, 
00486            0
00487            );
00488 }
00489 
00507 SAL_RETURN_REGS
00508 EFIAPI
00509 EsalGetNewPalEntry (
00510   IN BOOLEAN  PhysicalAddress
00511   )
00512 {
00513   return EsalCall (
00514            EFI_EXTENDED_SAL_PAL_SERVICES_PROTOCOL_GUID_LO,
00515            EFI_EXTENDED_SAL_PAL_SERVICES_PROTOCOL_GUID_HI,
00516            GetNewPalEntryFunctionId, 
00517            PhysicalAddress, 
00518            0, 
00519            0, 
00520            0, 
00521            0, 
00522            0, 
00523            0
00524            );
00525 }
00526 
00545 SAL_RETURN_REGS
00546 EFIAPI
00547 EsalGetStateBuffer (
00548   IN  UINT64  McaType,
00549   OUT UINT8   **McaBuffer,
00550   OUT UINTN   *BufferSize
00551   )
00552 {
00553   SAL_RETURN_REGS Regs;
00554 
00555   Regs = EsalCall (
00556            EFI_EXTENDED_SAL_MCA_LOG_SERVICES_PROTOCOL_GUID_LO,
00557            EFI_EXTENDED_SAL_MCA_LOG_SERVICES_PROTOCOL_GUID_HI,
00558            EsalGetStateBufferFunctionId, 
00559            McaType, 
00560            0, 
00561            0, 
00562            0, 
00563            0, 
00564            0, 
00565            0
00566            );
00567 
00568   *McaBuffer  = (UINT8 *) Regs.r9;
00569   *BufferSize = Regs.r10;
00570 
00571   return Regs;
00572 }
00573 
00585 SAL_RETURN_REGS
00586 EFIAPI
00587 EsalSaveStateBuffer (
00588   IN  UINT64  McaType
00589   )
00590 {
00591   return EsalCall (
00592            EFI_EXTENDED_SAL_MCA_LOG_SERVICES_PROTOCOL_GUID_LO,
00593            EFI_EXTENDED_SAL_MCA_LOG_SERVICES_PROTOCOL_GUID_HI,
00594            EsalSaveStateBufferFunctionId, 
00595            McaType, 
00596            0, 
00597            0, 
00598            0, 
00599            0, 
00600            0, 
00601            0
00602            );
00603 }
00604 
00620 SAL_RETURN_REGS
00621 EFIAPI
00622 EsalGetVectors (
00623   IN  UINT64  VectorType
00624   )
00625 {
00626   return EsalCall (
00627            EFI_EXTENDED_SAL_BASE_SERVICES_PROTOCOL_GUID_LO,
00628            EFI_EXTENDED_SAL_BASE_SERVICES_PROTOCOL_GUID_HI,
00629            EsalGetVectorsFunctionId, 
00630            VectorType, 
00631            0, 
00632            0, 
00633            0, 
00634            0, 
00635            0, 
00636            0
00637            );
00638 }
00639 
00657 SAL_RETURN_REGS
00658 EFIAPI
00659 EsalMcGetParams (
00660   IN  UINT64  ParamInfoType
00661   )
00662 {
00663   return EsalCall (
00664            EFI_EXTENDED_SAL_BASE_SERVICES_PROTOCOL_GUID_LO,
00665            EFI_EXTENDED_SAL_BASE_SERVICES_PROTOCOL_GUID_HI,
00666            EsalMcGetParamsFunctionId, 
00667            ParamInfoType, 
00668            0, 
00669            0, 
00670            0, 
00671            0, 
00672            0, 
00673            0
00674            );
00675 }
00676 
00688 SAL_RETURN_REGS
00689 EFIAPI
00690 EsalMcGetMcParams (
00691   VOID
00692   )
00693 {
00694   return EsalCall (
00695            EFI_EXTENDED_SAL_BASE_SERVICES_PROTOCOL_GUID_LO,
00696            EFI_EXTENDED_SAL_BASE_SERVICES_PROTOCOL_GUID_HI,
00697            EsalMcGetMcParamsFunctionId, 
00698            0, 
00699            0, 
00700            0, 
00701            0, 
00702            0, 
00703            0, 
00704            0
00705            );
00706 }
00707 
00719 SAL_RETURN_REGS
00720 EFIAPI
00721 EsalGetMcCheckinFlags (
00722   IN  UINT64  CpuIndex
00723   )
00724 {
00725   return EsalCall (
00726            EFI_EXTENDED_SAL_BASE_SERVICES_PROTOCOL_GUID_LO,
00727            EFI_EXTENDED_SAL_BASE_SERVICES_PROTOCOL_GUID_HI,
00728            EsalGetMcCheckinFlagsFunctionId, 
00729            CpuIndex, 
00730            0, 
00731            0, 
00732            0, 
00733            0, 
00734            0, 
00735            0
00736            );
00737 }
00738 
00755 SAL_RETURN_REGS
00756 EFIAPI
00757 EsalAddCpuData (
00758   IN UINT64   CpuGlobalId,
00759   IN BOOLEAN  Enabled,
00760   IN UINT64   PalCompatibility
00761   )
00762 {
00763   return EsalCall (
00764            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_LO,
00765            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_HI,
00766            AddCpuDataFunctionId, 
00767            CpuGlobalId, 
00768            Enabled, 
00769            PalCompatibility, 
00770            0, 
00771            0, 
00772            0, 
00773            0
00774            );
00775 }
00776 
00789 SAL_RETURN_REGS
00790 EFIAPI
00791 EsalRemoveCpuData (
00792   IN UINT64  CpuGlobalId
00793   )
00794 {
00795   return EsalCall (
00796            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_LO,
00797            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_HI,
00798            RemoveCpuDataFunctionId, 
00799            CpuGlobalId, 
00800            0, 
00801            0, 
00802            0, 
00803            0, 
00804            0, 
00805            0
00806            );
00807 }
00808 
00825 SAL_RETURN_REGS
00826 EFIAPI
00827 EsalModifyCpuData (
00828   IN UINT64   CpuGlobalId,
00829   IN BOOLEAN  Enabled,
00830   IN UINT64   PalCompatibility
00831   )
00832 {
00833   return EsalCall (
00834            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_LO,
00835            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_HI,
00836            ModifyCpuDataFunctionId, 
00837            CpuGlobalId, 
00838            Enabled, 
00839            PalCompatibility, 
00840            0, 
00841            0, 
00842            0, 
00843            0
00844            );
00845 }
00846 
00861 SAL_RETURN_REGS
00862 EFIAPI
00863 EsalGetCpuDataById (
00864   IN UINT64   CpuGlobalId,
00865   IN BOOLEAN  IndexByEnabledCpu
00866   )
00867 {
00868   return EsalCall (
00869            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_LO,
00870            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_HI,
00871            GetCpuDataByIDFunctionId, 
00872            CpuGlobalId, 
00873            IndexByEnabledCpu, 
00874            0, 
00875            0, 
00876            0, 
00877            0, 
00878            0
00879            );
00880 }
00881 
00896 SAL_RETURN_REGS
00897 EFIAPI
00898 EsalGetCpuDataByIndex (
00899   IN UINT64   Index,
00900   IN BOOLEAN  IndexByEnabledCpu
00901   )
00902 {
00903   return EsalCall (
00904            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_LO,
00905            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_HI,
00906            GetCpuDataByIndexFunctionId, 
00907            Index, 
00908            IndexByEnabledCpu, 
00909            0, 
00910            0, 
00911            0, 
00912            0, 
00913            0
00914            );
00915 }
00916 
00930 SAL_RETURN_REGS
00931 EFIAPI
00932 EsalWhoAmI (
00933   IN BOOLEAN  IndexByEnabledCpu
00934   )
00935 {
00936   return EsalCall (
00937            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_LO,
00938            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_HI,
00939            CurrentProcInfoFunctionId, 
00940            IndexByEnabledCpu, 
00941            0, 
00942            0, 
00943            0, 
00944            0, 
00945            0, 
00946            0
00947            );
00948 }
00949 
00960 SAL_RETURN_REGS
00961 EFIAPI
00962 EsalNumProcessors (
00963   VOID
00964   )
00965 {
00966   return EsalCall (
00967            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_LO,
00968            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_HI,
00969            NumProcessorsFunctionId, 
00970            0, 
00971            0, 
00972            0, 
00973            0, 
00974            0, 
00975            0, 
00976            0
00977            );
00978 }
00979 
00994 SAL_RETURN_REGS
00995 EFIAPI
00996 EsalSetMinState (
00997   IN UINT64                CpuGlobalId,
00998   IN EFI_PHYSICAL_ADDRESS  MinStatePointer
00999   )
01000 {
01001   return EsalCall (
01002            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_LO,
01003            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_HI,
01004            SetMinStateFunctionId, 
01005            CpuGlobalId, 
01006            MinStatePointer, 
01007            0, 
01008            0, 
01009            0, 
01010            0, 
01011            0
01012            );
01013 }
01014 
01027 SAL_RETURN_REGS
01028 EFIAPI
01029 EsalGetMinState (
01030   IN UINT64  CpuGlobalId
01031   )
01032 {
01033   return EsalCall (
01034            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_LO,
01035            EFI_EXTENDED_SAL_MP_SERVICES_PROTOCOL_GUID_HI,
01036            GetMinStateFunctionId, 
01037            CpuGlobalId, 
01038            0, 
01039            0, 
01040            0, 
01041            0, 
01042            0, 
01043            0
01044            );
01045 }
01046 
01061 SAL_RETURN_REGS
01062 EFIAPI
01063 EsalMcaGetStateInfo (
01064   IN  UINT64                CpuGlobalId,
01065   OUT EFI_PHYSICAL_ADDRESS  *StateBufferPointer,
01066   OUT UINT64                *RequiredStateBufferSize
01067   )
01068 {
01069   SAL_RETURN_REGS  Regs;
01070 
01071   Regs = EsalCall (
01072            EFI_EXTENDED_SAL_MCA_SERVICES_PROTOCOL_GUID_LO,
01073            EFI_EXTENDED_SAL_MCA_SERVICES_PROTOCOL_GUID_HI,
01074            McaGetStateInfoFunctionId, 
01075            CpuGlobalId, 
01076            0, 
01077            0, 
01078            0, 
01079            0, 
01080            0, 
01081            0
01082            );
01083 
01084   *StateBufferPointer      = (EFI_PHYSICAL_ADDRESS) Regs.r9;
01085   *RequiredStateBufferSize = (UINT64) Regs.r10;
01086 
01087   return Regs;
01088 }
01089 
01103 SAL_RETURN_REGS
01104 EFIAPI
01105 EsalMcaRegisterCpu (
01106   IN UINT64                CpuGlobalId,
01107   IN EFI_PHYSICAL_ADDRESS  StateBufferPointer
01108   )
01109 {
01110   return EsalCall (
01111            EFI_EXTENDED_SAL_MCA_SERVICES_PROTOCOL_GUID_LO,
01112            EFI_EXTENDED_SAL_MCA_SERVICES_PROTOCOL_GUID_HI,
01113            McaRegisterCpuFunctionId, 
01114            CpuGlobalId, 
01115            StateBufferPointer, 
01116            0, 
01117            0, 
01118            0, 
01119            0, 
01120            0
01121            );
01122 }
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Defines