TianoCore EDK2 master
Loading...
Searching...
No Matches
UfsPciHcPei.c
Go to the documentation of this file.
1
10#include "UfsPciHcPei.h"
11
12EDKII_UFS_HOST_CONTROLLER_PPI mUfsHostControllerPpi = { GetUfsHcMmioBar };
13
14EFI_PEI_PPI_DESCRIPTOR mPpiList = {
15 (EFI_PEI_PPI_DESCRIPTOR_PPI | EFI_PEI_PPI_DESCRIPTOR_TERMINATE_LIST),
16 &gEdkiiPeiUfsHostControllerPpiGuid,
17 &mUfsHostControllerPpi
18};
19
32EFIAPI
35 IN UINT8 ControllerId,
36 OUT UINTN *MmioBar
37 )
38{
40
41 if ((This == NULL) || (MmioBar == NULL)) {
42 return EFI_INVALID_PARAMETER;
43 }
44
45 Private = UFS_HC_PEI_PRIVATE_DATA_FROM_THIS (This);
46
47 if (ControllerId >= Private->TotalUfsHcs) {
48 return EFI_INVALID_PARAMETER;
49 }
50
51 *MmioBar = (UINTN)Private->UfsHcPciAddr[ControllerId];
52
53 return EFI_SUCCESS;
54}
55
67EFIAPI
69 IN EFI_PEI_FILE_HANDLE FileHandle,
70 IN CONST EFI_PEI_SERVICES **PeiServices
71 )
72{
73 EFI_BOOT_MODE BootMode;
74 EFI_STATUS Status;
75 UINT16 Bus;
76 UINT16 Device;
77 UINT16 Function;
78 UINT32 Size;
79 UINT64 MmioSize;
80 UINT32 BarAddr;
81 UINT8 SubClass;
82 UINT8 BaseClass;
84
85 //
86 // Shadow this PEIM to run from memory
87 //
88 if (!EFI_ERROR (PeiServicesRegisterForShadow (FileHandle))) {
89 return EFI_SUCCESS;
90 }
91
92 Status = PeiServicesGetBootMode (&BootMode);
96 if (BootMode == BOOT_ON_S3_RESUME) {
97 return EFI_SUCCESS;
98 }
99
101 if (Private == NULL) {
102 DEBUG ((DEBUG_ERROR, "Failed to allocate memory for UFS_HC_PEI_PRIVATE_DATA! \n"));
103 return EFI_OUT_OF_RESOURCES;
104 }
105
106 Private->Signature = UFS_HC_PEI_SIGNATURE;
107 Private->UfsHostControllerPpi = mUfsHostControllerPpi;
108 Private->PpiList = mPpiList;
109 Private->PpiList.Ppi = &Private->UfsHostControllerPpi;
110
111 BarAddr = PcdGet32 (PcdUfsPciHostControllerMmioBase);
112 for (Bus = 0; Bus < 256; Bus++) {
113 for (Device = 0; Device < 32; Device++) {
114 for (Function = 0; Function < 8; Function++) {
115 SubClass = PciRead8 (PCI_LIB_ADDRESS (Bus, Device, Function, 0x0A));
116 BaseClass = PciRead8 (PCI_LIB_ADDRESS (Bus, Device, Function, 0x0B));
117
118 if ((SubClass == 0x09) && (BaseClass == PCI_CLASS_MASS_STORAGE)) {
119 //
120 // Get the Ufs Pci host controller's MMIO region size.
121 //
122 PciAnd16 (PCI_LIB_ADDRESS (Bus, Device, Function, PCI_COMMAND_OFFSET), (UINT16) ~(EFI_PCI_COMMAND_BUS_MASTER | EFI_PCI_COMMAND_MEMORY_SPACE));
123 PciWrite32 (PCI_LIB_ADDRESS (Bus, Device, Function, PCI_BASE_ADDRESSREG_OFFSET), 0xFFFFFFFF);
124 Size = PciRead32 (PCI_LIB_ADDRESS (Bus, Device, Function, PCI_BASE_ADDRESSREG_OFFSET));
125
126 switch (Size & 0x07) {
127 case 0x0:
128 //
129 // Memory space: anywhere in 32 bit address space
130 //
131 MmioSize = (~(Size & 0xFFFFFFF0)) + 1;
132 break;
133 case 0x4:
134 //
135 // Memory space: anywhere in 64 bit address space
136 //
137 MmioSize = Size & 0xFFFFFFF0;
138 PciWrite32 (PCI_LIB_ADDRESS (Bus, Device, Function, PCI_BASE_ADDRESSREG_OFFSET + 4), 0xFFFFFFFF);
139 Size = PciRead32 (PCI_LIB_ADDRESS (Bus, Device, Function, PCI_BASE_ADDRESSREG_OFFSET + 4));
140
141 //
142 // Fix the length to support some specific 64 bit BAR
143 //
144 Size |= ((UINT32)(-1) << HighBitSet32 (Size));
145
146 //
147 // Calculate the size of 64bit bar
148 //
149 MmioSize |= LShiftU64 ((UINT64)Size, 32);
150 MmioSize = (~(MmioSize)) + 1;
151
152 //
153 // Clean the high 32bits of this 64bit BAR to 0 as we only allow a 32bit BAR.
154 //
155 PciWrite32 (PCI_LIB_ADDRESS (Bus, Device, Function, PCI_BASE_ADDRESSREG_OFFSET + 4), 0);
156 break;
157 default:
158 //
159 // Unknown BAR type
160 //
161 ASSERT (FALSE);
162 continue;
163 }
164
165 //
166 // Assign resource to the Ufs Pci host controller's MMIO BAR.
167 // Enable the Ufs Pci host controller by setting BME and MSE bits of PCI_CMD register.
168 //
169 PciWrite32 (PCI_LIB_ADDRESS (Bus, Device, Function, PCI_BASE_ADDRESSREG_OFFSET), BarAddr);
170 PciOr16 (PCI_LIB_ADDRESS (Bus, Device, Function, PCI_COMMAND_OFFSET), (EFI_PCI_COMMAND_BUS_MASTER | EFI_PCI_COMMAND_MEMORY_SPACE));
171 //
172 // Record the allocated Mmio base address.
173 //
174 Private->UfsHcPciAddr[Private->TotalUfsHcs] = BarAddr;
175 Private->TotalUfsHcs++;
176 BarAddr += (UINT32)MmioSize;
177 ASSERT (Private->TotalUfsHcs < MAX_UFS_HCS);
178 }
179 }
180 }
181 }
182
186 Status = PeiServicesInstallPpi (&Private->PpiList);
187
188 ASSERT_EFI_ERROR (Status);
189 return Status;
190}
UINT64 UINTN
UINT64 EFIAPI LShiftU64(IN UINT64 Operand, IN UINTN Count)
Definition: LShiftU64.c:28
INTN EFIAPI HighBitSet32(IN UINT32 Operand)
Definition: HighBitSet32.c:27
VOID *EFIAPI AllocateZeroPool(IN UINTN AllocationSize)
EFI_STATUS EFIAPI PeiServicesGetBootMode(OUT EFI_BOOT_MODE *BootMode)
EFI_STATUS EFIAPI PeiServicesInstallPpi(IN CONST EFI_PEI_PPI_DESCRIPTOR *PpiList)
EFI_STATUS EFIAPI PeiServicesRegisterForShadow(IN EFI_PEI_FILE_HANDLE FileHandle)
#define NULL
Definition: Base.h:319
#define CONST
Definition: Base.h:259
#define FALSE
Definition: Base.h:307
#define IN
Definition: Base.h:279
#define OUT
Definition: Base.h:284
#define ASSERT_EFI_ERROR(StatusParameter)
Definition: DebugLib.h:462
#define DEBUG(Expression)
Definition: DebugLib.h:434
UINT32 EFIAPI PciRead32(IN UINTN Address)
Definition: PciLib.c:739
UINT8 EFIAPI PciRead8(IN UINTN Address)
Definition: PciLib.c:62
#define PCI_LIB_ADDRESS(Bus, Device, Function, Register)
Definition: PciLib.h:34
UINT16 EFIAPI PciAnd16(IN UINTN Address, IN UINT16 AndData)
Definition: PciLib.c:484
UINT32 EFIAPI PciWrite32(IN UINTN Address, IN UINT32 Value)
Definition: PciLib.c:765
UINT16 EFIAPI PciOr16(IN UINTN Address, IN UINT16 OrData)
Definition: PciLib.c:453
#define PcdGet32(TokenName)
Definition: PcdLib.h:362
#define EFI_PCI_COMMAND_MEMORY_SPACE
0x0002
Definition: Pci22.h:592
#define EFI_PCI_COMMAND_BUS_MASTER
0x0004
Definition: Pci22.h:593
UINT32 EFI_BOOT_MODE
Definition: PiBootMode.h:18
VOID * EFI_PEI_FILE_HANDLE
Definition: PiPeiCis.h:26
RETURN_STATUS EFI_STATUS
Definition: UefiBaseType.h:29
#define EFI_SUCCESS
Definition: UefiBaseType.h:112
EFI_STATUS EFIAPI GetUfsHcMmioBar(IN EDKII_UFS_HOST_CONTROLLER_PPI *This, IN UINT8 ControllerId, OUT UINTN *MmioBar)
Definition: UfsPciHcPei.c:33
EFI_STATUS EFIAPI InitializeUfsHcPeim(IN EFI_PEI_FILE_HANDLE FileHandle, IN CONST EFI_PEI_SERVICES **PeiServices)
Definition: UfsPciHcPei.c:68