TianoCore EDK2 master
Loading...
Searching...
No Matches
SmramInternal.c
Go to the documentation of this file.
1
12#include <Library/DebugLib.h>
13#include <Library/PcdLib.h>
14#include <Library/PciLib.h>
15
16#include "SmramInternal.h"
17
18//
19// The value of PcdQ35TsegMbytes is saved into this variable at module startup.
20//
21UINT16 mQ35TsegMbytes;
22
23//
24// The value of PcdQ35SmramAtDefaultSmbase is saved into this variable at
25// module startup.
26//
27STATIC BOOLEAN mQ35SmramAtDefaultSmbase;
28
32VOID
34 VOID
35 )
36{
37 mQ35TsegMbytes = PcdGet16 (PcdQ35TsegMbytes);
38}
39
43VOID
45 VOID
46 )
47{
48 mQ35SmramAtDefaultSmbase = PcdGetBool (PcdQ35SmramAtDefaultSmbase);
49}
50
65VOID
67 OUT BOOLEAN *LockState,
68 OUT BOOLEAN *OpenState
69 )
70{
71 UINT8 SmramVal, EsmramcVal;
72
73 SmramVal = PciRead8 (DRAMC_REGISTER_Q35 (MCH_SMRAM));
74 EsmramcVal = PciRead8 (DRAMC_REGISTER_Q35 (MCH_ESMRAMC));
75
76 *LockState = !!(SmramVal & MCH_SMRAM_D_LCK);
77 *OpenState = !(EsmramcVal & MCH_ESMRAMC_T_EN);
78}
79
80//
81// The functions below follow the PEI_SMM_ACCESS_PPI and
82// EFI_SMM_ACCESS2_PROTOCOL member declarations. The PeiServices and This
83// pointers are removed (TSEG doesn't depend on them), and so is the
84// DescriptorIndex parameter (TSEG doesn't support range-wise locking).
85//
86// The LockState and OpenState members that are common to both
87// PEI_SMM_ACCESS_PPI and EFI_SMM_ACCESS2_PROTOCOL are taken and updated in
88// isolation from the rest of the (non-shared) members.
89//
90
92SmramAccessOpen (
93 OUT BOOLEAN *LockState,
94 OUT BOOLEAN *OpenState
95 )
96{
97 //
98 // Open TSEG by clearing T_EN.
99 //
100 PciAnd8 (
101 DRAMC_REGISTER_Q35 (MCH_ESMRAMC),
102 (UINT8)((~(UINT32)MCH_ESMRAMC_T_EN) & 0xff)
103 );
104
105 GetStates (LockState, OpenState);
106 if (!*OpenState) {
107 return EFI_DEVICE_ERROR;
108 }
109
110 return EFI_SUCCESS;
111}
112
114SmramAccessClose (
115 OUT BOOLEAN *LockState,
116 OUT BOOLEAN *OpenState
117 )
118{
119 //
120 // Close TSEG by setting T_EN.
121 //
122 PciOr8 (DRAMC_REGISTER_Q35 (MCH_ESMRAMC), MCH_ESMRAMC_T_EN);
123
124 GetStates (LockState, OpenState);
125 if (*OpenState) {
126 return EFI_DEVICE_ERROR;
127 }
128
129 return EFI_SUCCESS;
130}
131
133SmramAccessLock (
134 OUT BOOLEAN *LockState,
135 IN OUT BOOLEAN *OpenState
136 )
137{
138 if (*OpenState) {
139 return EFI_DEVICE_ERROR;
140 }
141
142 //
143 // Close & lock TSEG by setting T_EN and D_LCK.
144 //
145 PciOr8 (DRAMC_REGISTER_Q35 (MCH_ESMRAMC), MCH_ESMRAMC_T_EN);
146 PciOr8 (DRAMC_REGISTER_Q35 (MCH_SMRAM), MCH_SMRAM_D_LCK);
147
148 //
149 // Close & lock the SMRAM at the default SMBASE, if it exists.
150 //
151 if (mQ35SmramAtDefaultSmbase) {
152 PciWrite8 (
153 DRAMC_REGISTER_Q35 (MCH_DEFAULT_SMBASE_CTL),
154 MCH_DEFAULT_SMBASE_LCK
155 );
156 }
157
158 GetStates (LockState, OpenState);
159 if (*OpenState || !*LockState) {
160 return EFI_DEVICE_ERROR;
161 }
162
163 return EFI_SUCCESS;
164}
165
167SmramAccessGetCapabilities (
168 IN OUT UINTN *SmramMapSize,
169 IN OUT EFI_SMRAM_DESCRIPTOR *SmramMap
170 )
171{
172 UINTN BufferSize;
173 EFI_HOB_GUID_TYPE *GuidHob;
174 EFI_SMRAM_HOB_DESCRIPTOR_BLOCK *DescriptorBlock;
175 UINTN Index;
176
177 //
178 // Get Hob list
179 //
180 GuidHob = GetFirstGuidHob (&gEfiSmmSmramMemoryGuid);
181 DescriptorBlock = GET_GUID_HOB_DATA (GuidHob);
182 ASSERT (DescriptorBlock);
183
184 BufferSize = DescriptorBlock->NumberOfSmmReservedRegions * sizeof (EFI_SMRAM_DESCRIPTOR);
185
186 if (*SmramMapSize < BufferSize) {
187 *SmramMapSize = BufferSize;
188 return EFI_BUFFER_TOO_SMALL;
189 }
190
191 //
192 // Update SmramMapSize to real return SMRAM map size
193 //
194 *SmramMapSize = BufferSize;
195
196 //
197 // Use the hob to publish SMRAM capabilities
198 //
199 for (Index = 0; Index < DescriptorBlock->NumberOfSmmReservedRegions; Index++) {
200 SmramMap[Index].PhysicalStart = DescriptorBlock->Descriptor[Index].PhysicalStart;
201 SmramMap[Index].CpuStart = DescriptorBlock->Descriptor[Index].CpuStart;
202 SmramMap[Index].PhysicalSize = DescriptorBlock->Descriptor[Index].PhysicalSize;
203 SmramMap[Index].RegionState = DescriptorBlock->Descriptor[Index].RegionState;
204 }
205
206 return EFI_SUCCESS;
207}
UINT64 UINTN
VOID *EFIAPI GetFirstGuidHob(IN CONST EFI_GUID *Guid)
Definition: HobLib.c:215
#define STATIC
Definition: Base.h:264
#define IN
Definition: Base.h:279
#define OUT
Definition: Base.h:284
UINT8 EFIAPI PciRead8(IN UINTN Address)
Definition: PciLib.c:62
UINT8 EFIAPI PciAnd8(IN UINTN Address, IN UINT8 AndData)
Definition: PciLib.c:147
UINT8 EFIAPI PciOr8(IN UINTN Address, IN UINT8 OrData)
Definition: PciLib.c:117
UINT8 EFIAPI PciWrite8(IN UINTN Address, IN UINT8 Value)
Definition: PciLib.c:87
#define PcdGet16(TokenName)
Definition: PcdLib.h:349
#define PcdGetBool(TokenName)
Definition: PcdLib.h:401
VOID InitQ35SmramAtDefaultSmbase(VOID)
Definition: SmramInternal.c:44
VOID GetStates(OUT BOOLEAN *LockState, OUT BOOLEAN *OpenState)
Definition: SmramInternal.c:66
VOID InitQ35TsegMbytes(VOID)
Definition: SmramInternal.c:33
RETURN_STATUS EFI_STATUS
Definition: UefiBaseType.h:29
#define EFI_SUCCESS
Definition: UefiBaseType.h:112
EFI_PHYSICAL_ADDRESS CpuStart
Definition: PiMultiPhase.h:127
EFI_PHYSICAL_ADDRESS PhysicalStart
Definition: PiMultiPhase.h:122
EFI_SMRAM_DESCRIPTOR Descriptor[1]