3 Copyright (c) 2004 - 2014, Intel Corporation. All rights reserved.<BR>
5 SPDX-License-Identifier: BSD-2-Clause-Patent
16 PPI for reading SPD modules on DIMMs.
24 #include "Platformearlyinit.h"
26 #define DIMM_SOCKETS 4 // Total number of DIMM sockets allowed on
28 #define DIMM_SEGMENTS 1 // Total number of Segments Per DIMM.
29 #define MEMORY_CHANNELS 2 // Total number of memory channels
30 // populated on the system board
38 IN EFI_PEI_SERVICES
**PeiServices
,
39 IN PEI_PLATFORM_DIMM_PPI
*This
,
41 OUT PEI_PLATFORM_DIMM_STATE
*State
47 IN EFI_PEI_SERVICES
**PeiServices
,
48 IN PEI_PLATFORM_DIMM_PPI
*This
,
50 IN PEI_PLATFORM_DIMM_STATE
*State
56 IN EFI_PEI_SERVICES
**PeiServices
,
57 IN PEI_PLATFORM_DIMM_PPI
*This
,
64 static PEI_PLATFORM_DIMM_PPI mGchDimmPpi
= {
73 static EFI_PEI_PPI_DESCRIPTOR mPpiPlatformDimm
= {
74 (EFI_PEI_PPI_DESCRIPTOR_PPI
| EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST
),
75 &gPeiPlatformDimmPpiGuid
,
85 This function returns the current state of a single DIMM. Present indicates
86 that the DIMM slot is physically populated. Disabled indicates that the DIMM
89 @param PeiServices PEI services table pointer
90 @param This PPI pointer
91 @param Dimm DIMM to read from
92 @param State Pointer to a return buffer to be updated with the current state
95 @retval EFI_SUCCESS The function completed successfully.
101 IN EFI_PEI_SERVICES
**PeiServices
,
102 IN PEI_PLATFORM_DIMM_PPI
*This
,
104 OUT PEI_PLATFORM_DIMM_STATE
*State
110 PEI_ASSERT (PeiServices
, (Dimm
< This
->DimmSockets
));
113 // A failure here does not necessarily mean that no DIMM is present.
114 // Read a single byte. All we care about is the return status.
125 if (EFI_ERROR (Status
)) {
132 // BUGBUG: Update to check platform variable when it is available
142 This function updates the state of a single DIMM.
144 @param PeiServices PEI services table pointer
145 @param This PPI pointer
146 @param Dimm DIMM to set state for
147 @param State Pointer to the state information to set.
149 @retval EFI_SUCCESS The function completed successfully.
150 @retval EFI_UNSUPPORTED The function is not supported.
156 IN EFI_PEI_SERVICES
**PeiServices
,
157 IN PEI_PLATFORM_DIMM_PPI
*This
,
159 IN PEI_PLATFORM_DIMM_STATE
*State
162 return EFI_UNSUPPORTED
;
166 This function reads SPD information from a DIMM.
168 PeiServices PEI services table pointer
170 Dimm DIMM to read from
171 Offset Offset in DIMM
172 Count Number of bytes
175 @param EFI_SUCCESS The function completed successfully.
176 @param EFI_DEVICE_ERROR The DIMM being accessed reported a device error,
177 does not have an SPD module, or is not installed in
179 @retval EFI_TIMEOUT Time out trying to read the SPD module.
180 @retval EFI_INVALID_PARAMETER A parameter was outside the legal limits.
186 IN EFI_PEI_SERVICES
**PeiServices
,
187 IN PEI_PLATFORM_DIMM_PPI
*This
,
195 PEI_SMBUS_PPI
*Smbus
;
198 EFI_SMBUS_DEVICE_ADDRESS SlaveAddress
;
199 EFI_SMBUS_DEVICE_COMMAND Command
;
202 Status
= (**PeiServices
).LocatePpi (
204 &gPeiSmbusPpiGuid
, // GUID
206 NULL
, // EFI_PEI_PPI_DESCRIPTOR
209 ASSERT_PEI_ERROR (PeiServices
, Status
);
213 SlaveAddress
.SmbusDeviceAddress
= SMBUS_ADDR_CH_A_1
>> 1;
216 SlaveAddress
.SmbusDeviceAddress
= SMBUS_ADDR_CH_A_2
>> 1;
219 SlaveAddress
.SmbusDeviceAddress
= SMBUS_ADDR_CH_B_1
>> 1;
222 SlaveAddress
.SmbusDeviceAddress
= SMBUS_ADDR_CH_B_2
>> 1;
225 return EFI_INVALID_PARAMETER
;
231 // read the first serveral bytes to speed up following reading
233 for (Index1
= 0; Index1
< Index
; Index1
++) {
235 Command
= Offset
+ Index1
;
236 Status
= Smbus
->Execute (
246 if (EFI_ERROR(Status
)) {
253 // Now collect all the remaining bytes on 4 bytes block
255 for (; Index
< Count
; Index
+= 2) {
256 Command
= Index
+ Offset
;
258 Status
= Smbus
->Execute (
268 if (EFI_ERROR(Status
)) {
273 Command
= Index
+ Offset
;
275 Status
= Smbus
->Execute (
285 if (EFI_ERROR(Status
)) {
293 This function initializes the PEIM. It simply installs the DIMM PPI.
295 @param FfsHeader Not used by this function
296 @param PeiServices Pointer to PEI services table
298 @retval EFI_SUCCESS The function completed successfully.
304 IN EFI_PEI_SERVICES
**PeiServices
,
305 IN EFI_PEI_NOTIFY_DESCRIPTOR
*NotifyDescriptor
,
311 Status
= (**PeiServices
).InstallPpi (
315 ASSERT_PEI_ERROR (PeiServices
, Status
);