3 Copyright (c) 2010, Intel Corporation. All rights reserved.<BR>
5 This program and the accompanying materials
6 are licensed and made available under the terms and conditions
7 of the BSD License which accompanies this distribution. The
8 full text of the license may be found at
9 http://opensource.org/licenses/bsd-license.php
11 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
17 #include <Library/UefiDriverEntryPoint.h>
18 #include <Library/UefiBootServicesTableLib.h>
19 #include <Library/UefiRuntimeServicesTableLib.h>
20 #include <Library/SmmServicesTableLib.h>
21 #include <Library/BaseLib.h>
22 #include <Library/BaseMemoryLib.h>
23 #include <Library/DebugLib.h>
24 #include <Library/LockBoxLib.h>
25 #include <Protocol/SmmReadyToLock.h>
26 #include <Protocol/SmmCommunication.h>
27 #include <Protocol/SmmAccess2.h>
28 #include <Protocol/LockBox.h>
29 #include <Guid/SmmLockBox.h>
31 BOOLEAN mLocked
= FALSE
;
33 EFI_SMRAM_DESCRIPTOR
*mSmramRanges
;
34 UINTN mSmramRangeCount
;
37 This function check if the address is in SMRAM.
39 @param Buffer the buffer address to be checked.
40 @param Length the buffer length to be checked.
42 @retval TRUE this address is in SMRAM.
43 @retval FALSE this address is NOT in SMRAM.
47 IN EFI_PHYSICAL_ADDRESS Buffer
,
53 for (Index
= 0; Index
< mSmramRangeCount
; Index
++) {
54 if (((Buffer
>= mSmramRanges
[Index
].CpuStart
) && (Buffer
< mSmramRanges
[Index
].CpuStart
+ mSmramRanges
[Index
].PhysicalSize
)) ||
55 ((mSmramRanges
[Index
].CpuStart
>= Buffer
) && (mSmramRanges
[Index
].CpuStart
< Buffer
+ Length
))) {
64 Dispatch function for SMM lock box save.
66 @param LockBoxParameterSave parameter of lock box save
70 IN EFI_SMM_LOCK_BOX_PARAMETER_SAVE
*LockBoxParameterSave
79 DEBUG ((EFI_D_ERROR
, "SmmLockBox Locked!\n"));
80 LockBoxParameterSave
->Header
.ReturnStatus
= (UINT64
)EFI_ACCESS_DENIED
;
87 Status
= SaveLockBox (
88 &LockBoxParameterSave
->Guid
,
89 (VOID
*)(UINTN
)LockBoxParameterSave
->Buffer
,
90 (UINTN
)LockBoxParameterSave
->Length
92 LockBoxParameterSave
->Header
.ReturnStatus
= (UINT64
)Status
;
97 Dispatch function for SMM lock box set attributes.
99 @param LockBoxParameterSetAttributes parameter of lock box set attributes
102 SmmLockBoxSetAttributes (
103 IN EFI_SMM_LOCK_BOX_PARAMETER_SET_ATTRIBUTES
*LockBoxParameterSetAttributes
112 DEBUG ((EFI_D_ERROR
, "SmmLockBox Locked!\n"));
113 LockBoxParameterSetAttributes
->Header
.ReturnStatus
= (UINT64
)EFI_ACCESS_DENIED
;
120 Status
= SetLockBoxAttributes (
121 &LockBoxParameterSetAttributes
->Guid
,
122 LockBoxParameterSetAttributes
->Attributes
124 LockBoxParameterSetAttributes
->Header
.ReturnStatus
= (UINT64
)Status
;
129 Dispatch function for SMM lock box update.
131 @param LockBoxParameterUpdate parameter of lock box update
135 IN EFI_SMM_LOCK_BOX_PARAMETER_UPDATE
*LockBoxParameterUpdate
144 DEBUG ((EFI_D_ERROR
, "SmmLockBox Locked!\n"));
145 LockBoxParameterUpdate
->Header
.ReturnStatus
= (UINT64
)EFI_ACCESS_DENIED
;
152 Status
= UpdateLockBox (
153 &LockBoxParameterUpdate
->Guid
,
154 (UINTN
)LockBoxParameterUpdate
->Offset
,
155 (VOID
*)(UINTN
)LockBoxParameterUpdate
->Buffer
,
156 (UINTN
)LockBoxParameterUpdate
->Length
158 LockBoxParameterUpdate
->Header
.ReturnStatus
= (UINT64
)Status
;
163 Dispatch function for SMM lock box restore.
165 @param LockBoxParameterRestore parameter of lock box restore
169 IN EFI_SMM_LOCK_BOX_PARAMETER_RESTORE
*LockBoxParameterRestore
177 if (IsAddressInSmram (LockBoxParameterRestore
->Buffer
, LockBoxParameterRestore
->Length
)) {
178 DEBUG ((EFI_D_ERROR
, "SmmLockBox Restore address in SMRAM!\n"));
179 LockBoxParameterRestore
->Header
.ReturnStatus
= (UINT64
)EFI_ACCESS_DENIED
;
186 Status
= RestoreLockBox (
187 &LockBoxParameterRestore
->Guid
,
188 (VOID
*)(UINTN
)LockBoxParameterRestore
->Buffer
,
189 (UINTN
*)&LockBoxParameterRestore
->Length
191 LockBoxParameterRestore
->Header
.ReturnStatus
= (UINT64
)Status
;
196 Dispatch function for SMM lock box restore all in place.
198 @param LockBoxParameterRestoreAllInPlace parameter of lock box restore all in place
201 SmmLockBoxRestoreAllInPlace (
202 IN EFI_SMM_LOCK_BOX_PARAMETER_RESTORE_ALL_IN_PLACE
*LockBoxParameterRestoreAllInPlace
207 Status
= RestoreAllLockBoxInPlace ();
208 LockBoxParameterRestoreAllInPlace
->Header
.ReturnStatus
= (UINT64
)Status
;
213 Dispatch function for a Software SMI handler.
215 @param DispatchHandle The unique handle assigned to this handler by SmiHandlerRegister().
216 @param Context Points to an optional handler context which was specified when the
217 handler was registered.
218 @param CommBuffer A pointer to a collection of data in memory that will
219 be conveyed from a non-SMM environment into an SMM environment.
220 @param CommBufferSize The size of the CommBuffer.
222 @retval EFI_SUCCESS Command is handled successfully.
228 IN EFI_HANDLE DispatchHandle
,
229 IN CONST VOID
*Context OPTIONAL
,
230 IN OUT VOID
*CommBuffer OPTIONAL
,
231 IN OUT UINTN
*CommBufferSize OPTIONAL
234 EFI_SMM_LOCK_BOX_PARAMETER_HEADER
*LockBoxParameterHeader
;
236 DEBUG ((EFI_D_ERROR
, "SmmLockBox SmmLockBoxHandler Enter\n"));
238 LockBoxParameterHeader
= (EFI_SMM_LOCK_BOX_PARAMETER_HEADER
*)((UINTN
)CommBuffer
);
240 LockBoxParameterHeader
->ReturnStatus
= (UINT64
)-1;
242 DEBUG ((EFI_D_ERROR
, "SmmLockBox LockBoxParameterHeader - %x\n", (UINTN
)LockBoxParameterHeader
));
244 DEBUG ((EFI_D_ERROR
, "SmmLockBox Command - %x\n", (UINTN
)LockBoxParameterHeader
->Command
));
246 switch (LockBoxParameterHeader
->Command
) {
247 case EFI_SMM_LOCK_BOX_COMMAND_SAVE
:
248 SmmLockBoxSave ((EFI_SMM_LOCK_BOX_PARAMETER_SAVE
*)(UINTN
)LockBoxParameterHeader
);
250 case EFI_SMM_LOCK_BOX_COMMAND_UPDATE
:
251 SmmLockBoxUpdate ((EFI_SMM_LOCK_BOX_PARAMETER_UPDATE
*)(UINTN
)LockBoxParameterHeader
);
253 case EFI_SMM_LOCK_BOX_COMMAND_RESTORE
:
254 SmmLockBoxRestore ((EFI_SMM_LOCK_BOX_PARAMETER_RESTORE
*)(UINTN
)LockBoxParameterHeader
);
256 case EFI_SMM_LOCK_BOX_COMMAND_SET_ATTRIBUTES
:
257 SmmLockBoxSetAttributes ((EFI_SMM_LOCK_BOX_PARAMETER_SET_ATTRIBUTES
*)(UINTN
)LockBoxParameterHeader
);
259 case EFI_SMM_LOCK_BOX_COMMAND_RESTORE_ALL_IN_PLACE
:
260 SmmLockBoxRestoreAllInPlace ((EFI_SMM_LOCK_BOX_PARAMETER_RESTORE_ALL_IN_PLACE
*)(UINTN
)LockBoxParameterHeader
);
266 LockBoxParameterHeader
->Command
= (UINT32
)-1;
268 DEBUG ((EFI_D_ERROR
, "SmmLockBox SmmLockBoxHandler Exit\n"));
274 Smm Ready To Lock event notification handler.
276 It sets a flag indicating that SMRAM has been locked.
278 @param[in] Protocol Points to the protocol's unique identifier.
279 @param[in] Interface Points to the interface instance.
280 @param[in] Handle The handle on which the interface was installed.
282 @retval EFI_SUCCESS Notification handler runs successfully.
286 SmmReadyToLockEventNotify (
287 IN CONST EFI_GUID
*Protocol
,
297 Entry Point for LockBox SMM driver.
299 @param[in] ImageHandle Image handle of this driver.
300 @param[in] SystemTable A Pointer to the EFI System Table.
303 @return Others Some error occurs.
307 SmmLockBoxEntryPoint (
308 IN EFI_HANDLE ImageHandle
,
309 IN EFI_SYSTEM_TABLE
*SystemTable
313 EFI_HANDLE DispatchHandle
;
315 EFI_SMM_ACCESS2_PROTOCOL
*SmmAccess
;
319 // Get SMRAM information
321 Status
= gBS
->LocateProtocol (&gEfiSmmAccess2ProtocolGuid
, NULL
, (VOID
**)&SmmAccess
);
322 ASSERT_EFI_ERROR (Status
);
325 Status
= SmmAccess
->GetCapabilities (SmmAccess
, &Size
, NULL
);
326 ASSERT (Status
== EFI_BUFFER_TOO_SMALL
);
328 Status
= gSmst
->SmmAllocatePool (
329 EfiRuntimeServicesData
,
331 (VOID
**)&mSmramRanges
333 ASSERT_EFI_ERROR (Status
);
335 Status
= SmmAccess
->GetCapabilities (SmmAccess
, &Size
, mSmramRanges
);
336 ASSERT_EFI_ERROR (Status
);
338 mSmramRangeCount
= Size
/ sizeof (EFI_SMRAM_DESCRIPTOR
);
341 // Register LockBox communication handler
343 Status
= gSmst
->SmiHandlerRegister (
345 &gEfiSmmLockBoxCommunicationGuid
,
348 ASSERT_EFI_ERROR (Status
);
351 // Register SMM Ready To Lock Protocol notification
353 Status
= gSmst
->SmmRegisterProtocolNotify (
354 &gEfiSmmReadyToLockProtocolGuid
,
355 SmmReadyToLockEventNotify
,
358 ASSERT_EFI_ERROR (Status
);
361 // Install NULL to DXE data base as notify
364 Status
= gBS
->InstallProtocolInterface (
366 &gEfiLockBoxProtocolGuid
,
367 EFI_NATIVE_INTERFACE
,
370 ASSERT_EFI_ERROR (Status
);