summaryrefslogtreecommitdiff
path: root/MdeModulePkg/Universal/CapsuleRuntimeDxe
diff options
context:
space:
mode:
Diffstat (limited to 'MdeModulePkg/Universal/CapsuleRuntimeDxe')
-rw-r--r--MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf76
-rw-r--r--MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.msa95
-rw-r--r--MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleService.c264
-rw-r--r--MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleService.h68
4 files changed, 503 insertions, 0 deletions
diff --git a/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf b/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf
new file mode 100644
index 0000000000..23ad32720e
--- /dev/null
+++ b/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.inf
@@ -0,0 +1,76 @@
+#/** @file
+# Component description file for Capsule module.
+#
+# CapsuleRuntime module provides capsule runtime services
+# Copyright (c) 2006 - 2007, Intel Corporation
+#
+# 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 Section - statements that will be processed to create a Makefile.
+#
+################################################################################
+[Defines]
+ INF_VERSION = 0x00010005
+ BASE_NAME = CapsuleRuntimeDxe
+ FILE_GUID = 42857F0A-13F2-4B21-8A23-53D3F714B840
+ MODULE_TYPE = DXE_RUNTIME_DRIVER
+ VERSION_STRING = 1.0
+ EDK_RELEASE_VERSION = 0x00020000
+ EFI_SPECIFICATION_VERSION = 0x00020000
+
+ ENTRY_POINT = CapsuleServiceInitialize
+
+#
+# The following information is for reference only and not required by the build tools.
+#
+# VALID_ARCHITECTURES = IA32 X64 IPF EBC
+#
+
+################################################################################
+#
+# Sources Section - list of files that are required for the build to succeed.
+#
+################################################################################
+
+[Sources.common]
+ CapsuleService.h
+ CapsuleService.c
+
+[Packages]
+ MdePkg/MdePkg.dec
+
+[LibraryClasses]
+ UefiBootServicesTableLib
+ MemoryAllocationLib
+ BaseMemoryLib
+ PcdLib
+ DebugLib
+ UefiRuntimeLib
+ DxeServicesTableLib
+ UefiDriverEntryPoint
+
+[Guids]
+ gEfiCapsuleVendorGuid # SOMETIMES_CONSUMED
+
+[Protocols]
+ gEfiCapsuleArchProtocolGuid # PROTOCOL ALWAYS_CONSUMED
+
+[PcdsFeatureFlag.common]
+ PcdSupportUpdateCapsuleRest|gEfiMdeModulePkgTokenSpaceGuid
+
+[PcdsFixedAtBuild.common]
+ PcdMaxSizeNonPopulateCapsule|gEfiMdeModulePkgTokenSpaceGuid
+ PcdMaxSizePopulateCapsule|gEfiMdeModulePkgTokenSpaceGuid
+
+[Depex]
+ gEfiVariableArchProtocolGuid
diff --git a/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.msa b/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.msa
new file mode 100644
index 0000000000..346cc7f32f
--- /dev/null
+++ b/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleRuntimeDxe.msa
@@ -0,0 +1,95 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<ModuleSurfaceArea xmlns="http://www.TianoCore.org/2006/Edk2.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
+ <MsaHeader>
+ <ModuleName>CapsuleRuntime</ModuleName>
+ <ModuleType>DXE_RUNTIME_DRIVER</ModuleType>
+ <GuidValue>42857F0A-13F2-4B21-8A23-53D3F714B840</GuidValue>
+ <Version>1.0</Version>
+ <Abstract>Component description file for Capsule module.</Abstract>
+ <Description>CapsuleRuntime module provides capsule runtime services</Description>
+ <Copyright>Copyright (c) 2006 - 2007, Intel Corporation</Copyright>
+ <License>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.</License>
+ <Specification>FRAMEWORK_BUILD_PACKAGING_SPECIFICATION 0x00000052</Specification>
+ </MsaHeader>
+ <ModuleDefinitions>
+ <SupportedArchitectures>IA32 X64 IPF EBC</SupportedArchitectures>
+ <BinaryModule>false</BinaryModule>
+ <OutputFileBasename>CapsuleRuntime</OutputFileBasename>
+ </ModuleDefinitions>
+ <LibraryClassDefinitions>
+ <LibraryClass Usage="ALWAYS_CONSUMED">
+ <Keyword>UefiDriverEntryPoint</Keyword>
+ </LibraryClass>
+ <LibraryClass Usage="ALWAYS_CONSUMED">
+ <Keyword>DxeServicesTableLib</Keyword>
+ </LibraryClass>
+ <LibraryClass Usage="ALWAYS_CONSUMED">
+ <Keyword>UefiRuntimeLib</Keyword>
+ </LibraryClass>
+ <LibraryClass Usage="ALWAYS_CONSUMED">
+ <Keyword>DebugLib</Keyword>
+ </LibraryClass>
+ <LibraryClass Usage="ALWAYS_CONSUMED">
+ <Keyword>PcdLib</Keyword>
+ </LibraryClass>
+ <LibraryClass Usage="ALWAYS_CONSUMED">
+ <Keyword>BaseMemoryLib</Keyword>
+ </LibraryClass>
+ <LibraryClass Usage="ALWAYS_CONSUMED">
+ <Keyword>MemoryAllocationLib</Keyword>
+ </LibraryClass>
+ <LibraryClass Usage="ALWAYS_CONSUMED">
+ <Keyword>UefiBootServicesTableLib</Keyword>
+ </LibraryClass>
+ </LibraryClassDefinitions>
+ <SourceFiles>
+ <Filename>Capsule.c</Filename>
+ <Filename>CapsuleService.c</Filename>
+ <Filename>CapsuleService.h</Filename>
+ <Filename>Capsule.dxs</Filename>
+ </SourceFiles>
+ <PackageDependencies>
+ <Package PackageGuid="1E73767F-8F52-4603-AEB4-F29B510B6766"/>
+ <Package PackageGuid="2759ded5-bb57-4b06-af4f-c398fa552719"/>
+ <Package PackageGuid="BA0D78D6-2CAF-414b-BD4D-B6762A894288"/>
+ </PackageDependencies>
+ <Protocols>
+ <Protocol Usage="ALWAYS_CONSUMED">
+ <ProtocolCName>gEfiCapsuleArchProtocolGuid</ProtocolCName>
+ </Protocol>
+ </Protocols>
+ <Guids>
+ <GuidCNames Usage="SOMETIMES_CONSUMED">
+ <GuidCName>gEfiCapsuleVendorGuid</GuidCName>
+ </GuidCNames>
+ </Guids>
+ <Externs>
+ <Specification>EFI_SPECIFICATION_VERSION 0x00020000</Specification>
+ <Specification>EDK_RELEASE_VERSION 0x00020000</Specification>
+ <Extern>
+ <ModuleEntryPoint>CapsuleServiceInitialize</ModuleEntryPoint>
+ </Extern>
+ </Externs>
+ <PcdCoded>
+ <PcdEntry PcdItemType="FEATURE_FLAG">
+ <C_Name>PcdSupportUpdateCapsuleRest</C_Name>
+ <TokenSpaceGuidCName>gEfiEdkModulePkgTokenSpaceGuid</TokenSpaceGuidCName>
+ <HelpText>Indicate whether platform can support update capsule across a system reset</HelpText>
+ </PcdEntry>
+ <PcdEntry PcdItemType="FIXED_AT_BUILD">
+ <C_Name>PcdMaxSizePopulateCapsule</C_Name>
+ <TokenSpaceGuidCName>gEfiEdkModulePkgTokenSpaceGuid</TokenSpaceGuidCName>
+ <HelpText>Indicate the max size the platform can support in case of populated capsules</HelpText>
+ </PcdEntry>
+ <PcdEntry PcdItemType="FIXED_AT_BUILD">
+ <C_Name>PcdMaxSizeNonPopulateCapsule</C_Name>
+ <TokenSpaceGuidCName>gEfiEdkModulePkgTokenSpaceGuid</TokenSpaceGuidCName>
+ <HelpText>Indicate the max size the platform can support in case of non-populated capsules</HelpText>
+ </PcdEntry>
+ </PcdCoded>
+</ModuleSurfaceArea>
diff --git a/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleService.c b/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleService.c
new file mode 100644
index 0000000000..5a923cda34
--- /dev/null
+++ b/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleService.c
@@ -0,0 +1,264 @@
+/*++
+
+Copyright (c) 2006 - 2007, Intel Corporation
+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.
+
+Module Name:
+
+ CapsuleService.c
+
+Abstract:
+
+ Capsule Runtime Service.
+
+--*/
+
+#include "CapsuleService.h"
+
+EFI_STATUS
+EFIAPI
+UpdateCapsule (
+ IN EFI_CAPSULE_HEADER **CapsuleHeaderArray,
+ IN UINTN CapsuleCount,
+ IN EFI_PHYSICAL_ADDRESS ScatterGatherList OPTIONAL
+ )
+/*++
+
+Routine Description:
+
+ This code finds whether the capsules need reset to update, if not, update immediately.
+
+Arguments:
+
+ CapsuleHeaderArray A array of pointers to capsule headers passed in
+ CapsuleCount The number of capsule
+ ScatterGatherList Physical address of datablock list points to capsule
+
+Returns:
+
+ EFI STATUS
+ EFI_SUCCESS Valid capsule was passed.If CAPSULE_FLAG_PERSIT_ACROSS_RESET is
+ not set, the capsule has been successfully processed by the firmware.
+ If it set, the ScattlerGatherList is successfully to be set.
+ EFI_INVALID_PARAMETER CapsuleCount is less than 1,CapsuleGuid is not supported.
+ EFI_DEVICE_ERROR Failed to SetVariable or AllocatePool or ProcessFirmwareVolume.
+
+--*/
+{
+ UINTN CapsuleSize;
+ UINTN ArrayNumber;
+ VOID *BufferPtr;
+ EFI_STATUS Status;
+ EFI_HANDLE FvHandle;
+ EFI_CAPSULE_HEADER *CapsuleHeader;
+
+ if (CapsuleCount < 1) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ BufferPtr = NULL;
+ CapsuleHeader = NULL;
+
+ for (ArrayNumber = 0; ArrayNumber < CapsuleCount; ArrayNumber++) {
+ CapsuleHeader = CapsuleHeaderArray[ArrayNumber];
+ if ((CapsuleHeader->Flags & (CAPSULE_FLAGS_PERSIST_ACROSS_RESET | CAPSULE_FLAGS_POPULATE_SYSTEM_TABLE)) == CAPSULE_FLAGS_POPULATE_SYSTEM_TABLE) {
+ return EFI_INVALID_PARAMETER;
+ }
+ if ((CapsuleHeader->Flags & CAPSULE_FLAGS_POPULATE_SYSTEM_TABLE) == 0) {
+ return EFI_UNSUPPORTED;
+ }
+ }
+
+ //
+ //Assume that capsules have the same flags on reseting or not.
+ //
+ CapsuleHeader = CapsuleHeaderArray[0];
+
+ if ((CapsuleHeader->Flags & CAPSULE_FLAGS_PERSIST_ACROSS_RESET) != 0) {
+ //
+ //Check if the platform supports update capsule across a system reset
+ //
+ if (!FeaturePcdGet(PcdSupportUpdateCapsuleRest)) {
+ return EFI_UNSUPPORTED;
+ }
+
+ if (ScatterGatherList == 0) {
+ return EFI_INVALID_PARAMETER;
+ } else {
+ Status = EfiSetVariable (
+ EFI_CAPSULE_VARIABLE_NAME,
+ &gEfiCapsuleVendorGuid,
+ EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_BOOTSERVICE_ACCESS,
+ sizeof (UINTN),
+ (VOID *) &ScatterGatherList
+ );
+ if (Status != EFI_SUCCESS) {
+ return EFI_DEVICE_ERROR;
+ }
+ }
+ return EFI_SUCCESS;
+ }
+
+ //
+ //The rest occurs in the condition of non-reset mode
+ //
+ if (EfiAtRuntime ()) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ //Here should be in the boot-time
+ //
+ for (ArrayNumber = 0; ArrayNumber < CapsuleCount ; ArrayNumber++) {
+ CapsuleHeader = CapsuleHeaderArray[ArrayNumber];
+ CapsuleSize = CapsuleHeader->CapsuleImageSize - CapsuleHeader->HeaderSize;
+
+ BufferPtr = AllocatePool (CapsuleSize);
+ if (BufferPtr == NULL) {
+ return EFI_DEVICE_ERROR;
+ }
+
+ CopyMem (BufferPtr, (UINT8*)CapsuleHeader+ CapsuleHeader->HeaderSize, CapsuleSize);
+
+ //
+ //Call DXE service ProcessFirmwareVolume to process immediatelly
+ //
+ Status = gDS->ProcessFirmwareVolume (BufferPtr, CapsuleSize, &FvHandle);
+ if (Status != EFI_SUCCESS) {
+ FreePool (BufferPtr);
+ return EFI_DEVICE_ERROR;
+ }
+ gDS->Dispatch ();
+ FreePool (BufferPtr);
+ }
+
+ return EFI_SUCCESS;
+}
+
+
+
+EFI_STATUS
+EFIAPI
+QueryCapsuleCapabilities (
+ IN EFI_CAPSULE_HEADER **CapsuleHeaderArray,
+ IN UINTN CapsuleCount,
+ OUT UINT64 *MaxiumCapsuleSize,
+ OUT EFI_RESET_TYPE *ResetType
+ )
+/*++
+
+Routine Description:
+
+ This code is to query about capsule capability.
+
+Arguments:
+
+ CapsuleHeaderArray A array of pointers to capsule headers passed in
+ CapsuleCount The number of capsule
+ MaxiumCapsuleSize Max capsule size is supported
+ ResetType Reset type the capsule indicates, if reset is not needed,return EfiResetCold.
+ If reset is needed, return EfiResetWarm.
+
+Returns:
+
+ EFI STATUS
+ EFI_SUCCESS Valid answer returned
+ EFI_INVALID_PARAMETER MaxiumCapsuleSize is NULL,ResetType is NULL.CapsuleCount is less than 1,CapsuleGuid is not supported.
+ EFI_UNSUPPORTED The capsule type is not supported.
+
+--*/
+{
+ UINTN ArrayNumber;
+ EFI_CAPSULE_HEADER *CapsuleHeader;
+
+ if (CapsuleCount < 1) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ if ((MaxiumCapsuleSize == NULL) ||(ResetType == NULL)) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ CapsuleHeader = NULL;
+
+ for (ArrayNumber = 0; ArrayNumber < CapsuleCount; ArrayNumber++) {
+ CapsuleHeader = CapsuleHeaderArray[ArrayNumber];
+ if ((CapsuleHeader->Flags & (CAPSULE_FLAGS_PERSIST_ACROSS_RESET | CAPSULE_FLAGS_POPULATE_SYSTEM_TABLE)) == CAPSULE_FLAGS_POPULATE_SYSTEM_TABLE) {
+ return EFI_INVALID_PARAMETER;
+ }
+ if ((CapsuleHeader->Flags & CAPSULE_FLAGS_POPULATE_SYSTEM_TABLE) == 0) {
+ return EFI_UNSUPPORTED;
+ }
+ }
+
+ //
+ //Assume that capsules have the same flags on reseting or not.
+ //
+ CapsuleHeader = CapsuleHeaderArray[0];
+ if ((CapsuleHeader->Flags & CAPSULE_FLAGS_PERSIST_ACROSS_RESET) != 0) {
+ //
+ //Check if the platform supports update capsule across a system reset
+ //
+ if (!FeaturePcdGet(PcdSupportUpdateCapsuleRest)) {
+ return EFI_UNSUPPORTED;
+ }
+ *ResetType = EfiResetWarm;
+ *MaxiumCapsuleSize = FixedPcdGet32(PcdMaxSizePopulateCapsule);
+ } else {
+ *ResetType = EfiResetCold;
+ *MaxiumCapsuleSize = FixedPcdGet32(PcdMaxSizeNonPopulateCapsule);
+ }
+ return EFI_SUCCESS;
+}
+
+
+EFI_STATUS
+EFIAPI
+CapsuleServiceInitialize (
+ IN EFI_HANDLE ImageHandle,
+ IN EFI_SYSTEM_TABLE *SystemTable
+ )
+/*++
+
+Routine Description:
+
+ This code is capsule runtime service initialization.
+
+Arguments:
+
+ ImageHandle The image handle
+ SystemTable The system table.
+
+Returns:
+
+ EFI STATUS
+
+--*/
+{
+ EFI_STATUS Status;
+ EFI_HANDLE NewHandle;
+
+ SystemTable->RuntimeServices->UpdateCapsule = UpdateCapsule;
+ SystemTable->RuntimeServices->QueryCapsuleCapabilities = QueryCapsuleCapabilities;
+
+ //
+ // Now install the Capsule Architectural Protocol on a new handle
+ //
+ NewHandle = NULL;
+
+ Status = gBS->InstallMultipleProtocolInterfaces (
+ &NewHandle,
+ &gEfiCapsuleArchProtocolGuid,
+ NULL,
+ NULL
+ );
+ ASSERT_EFI_ERROR (Status);
+
+ return EFI_SUCCESS;
+}
diff --git a/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleService.h b/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleService.h
new file mode 100644
index 0000000000..8e02b63279
--- /dev/null
+++ b/MdeModulePkg/Universal/CapsuleRuntimeDxe/CapsuleService.h
@@ -0,0 +1,68 @@
+/*++
+
+Copyright (c) 2006, Intel Corporation
+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.
+
+Module Name:
+
+ CapsuleService.h
+
+Abstract:
+
+ Capsule Runtime Service
+
+--*/
+
+#ifndef _CAPSULE_RUNTIME_H_
+#define _CAPSULE_RUNTIME_H_
+
+//
+// The package level header files this module uses
+//
+#include <PiDxe.h>
+//
+// The protocols, PPI and GUID defintions for this module
+//
+#include <Protocol/Capsule.h>
+#include <Guid/CapsuleVendor.h>
+//
+// The Library classes this module consumes
+//
+#include <Library/UefiDriverEntryPoint.h>
+#include <Library/DxeServicesTableLib.h>
+#include <Library/UefiRuntimeLib.h>
+#include <Library/DebugLib.h>
+#include <Library/PcdLib.h>
+#include <Library/BaseMemoryLib.h>
+#include <Library/MemoryAllocationLib.h>
+#include <Library/UefiBootServicesTableLib.h>
+
+#include <Common/CapsuleName.h>
+
+extern EFI_GUID gEfiCapsuleGuid;
+
+EFI_STATUS
+EFIAPI
+UpdateCapsule(
+ IN EFI_CAPSULE_HEADER **CapsuleHeaderArray,
+ IN UINTN CapsuleCount,
+ IN EFI_PHYSICAL_ADDRESS ScatterGatherList OPTIONAL
+ );
+
+EFI_STATUS
+EFIAPI
+QueryCapsuleCapabilities(
+ IN EFI_CAPSULE_HEADER **CapsuleHeaderArray,
+ IN UINTN CapsuleCount,
+ OUT UINT64 *MaxiumCapsuleSize,
+ OUT EFI_RESET_TYPE *ResetType
+ );
+
+#endif
+