]> git.proxmox.com Git - mirror_edk2.git/blame - MdeModulePkg/Bus/Pci/NvmExpressPei/NvmExpressPei.h
MdeModulePkg\UfsBlockIoPei: UFS MMIO address size support both 32/64 bits
[mirror_edk2.git] / MdeModulePkg / Bus / Pci / NvmExpressPei / NvmExpressPei.h
CommitLineData
b8b69433
HW
1/** @file\r
2 The NvmExpressPei driver is used to manage non-volatile memory subsystem\r
3 which follows NVM Express specification at PEI phase.\r
4\r
4104423a 5 Copyright (c) 2018 - 2019, Intel Corporation. All rights reserved.<BR>\r
b8b69433 6\r
9d510e61 7 SPDX-License-Identifier: BSD-2-Clause-Patent\r
b8b69433
HW
8\r
9**/\r
10\r
11#ifndef _NVM_EXPRESS_PEI_H_\r
12#define _NVM_EXPRESS_PEI_H_\r
13\r
14#include <PiPei.h>\r
15\r
16#include <IndustryStandard/Nvme.h>\r
17\r
18#include <Ppi/NvmExpressHostController.h>\r
19#include <Ppi/BlockIo.h>\r
20#include <Ppi/BlockIo2.h>\r
2e15b750 21#include <Ppi/StorageSecurityCommand.h>\r
ba3aa1c4 22#include <Ppi/NvmExpressPassThru.h>\r
b8b69433
HW
23#include <Ppi/IoMmu.h>\r
24#include <Ppi/EndOfPeiPhase.h>\r
25\r
26#include <Library/DebugLib.h>\r
27#include <Library/PeiServicesLib.h>\r
28#include <Library/MemoryAllocationLib.h>\r
29#include <Library/BaseMemoryLib.h>\r
30#include <Library/IoLib.h>\r
b8b69433
HW
31#include <Library/TimerLib.h>\r
32\r
33//\r
34// Structure forward declarations\r
35//\r
36typedef struct _PEI_NVME_NAMESPACE_INFO PEI_NVME_NAMESPACE_INFO;\r
37typedef struct _PEI_NVME_CONTROLLER_PRIVATE_DATA PEI_NVME_CONTROLLER_PRIVATE_DATA;\r
38\r
39#include "NvmExpressPeiHci.h"\r
40#include "NvmExpressPeiPassThru.h"\r
41#include "NvmExpressPeiBlockIo.h"\r
2e15b750 42#include "NvmExpressPeiStorageSecurity.h"\r
b8b69433
HW
43\r
44//\r
45// NVME PEI driver implementation related definitions\r
46//\r
47#define NVME_MAX_QUEUES 2 // Number of I/O queues supported by the driver, 1 for AQ, 1 for CQ\r
48#define NVME_ASQ_SIZE 1 // Number of admin submission queue entries, which is 0-based\r
49#define NVME_ACQ_SIZE 1 // Number of admin completion queue entries, which is 0-based\r
50#define NVME_CSQ_SIZE 63 // Number of I/O submission queue entries, which is 0-based\r
51#define NVME_CCQ_SIZE 63 // Number of I/O completion queue entries, which is 0-based\r
52#define NVME_PRP_SIZE (8) // Pages of PRP list\r
53\r
54#define NVME_MEM_MAX_PAGES \\r
55 ( \\r
56 1 /* ASQ */ + \\r
57 1 /* ACQ */ + \\r
58 1 /* SQs */ + \\r
59 1 /* CQs */ + \\r
60 NVME_PRP_SIZE) /* PRPs */\r
61\r
62#define NVME_ADMIN_QUEUE 0x00\r
63#define NVME_IO_QUEUE 0x01\r
64#define NVME_GENERIC_TIMEOUT 5000000 // Generic PassThru command timeout value, in us unit\r
65#define NVME_POLL_INTERVAL 100 // Poll interval for PassThru command, in us unit\r
66\r
67//\r
68// Nvme namespace data structure.\r
69//\r
70struct _PEI_NVME_NAMESPACE_INFO {\r
71 UINT32 NamespaceId;\r
72 UINT64 NamespaceUuid;\r
73 EFI_PEI_BLOCK_IO2_MEDIA Media;\r
74\r
75 PEI_NVME_CONTROLLER_PRIVATE_DATA *Controller;\r
76};\r
77\r
ba3aa1c4
MC
78#define NVME_CONTROLLER_NSID 0\r
79\r
b8b69433
HW
80//\r
81// Unique signature for private data structure.\r
82//\r
83#define NVME_PEI_CONTROLLER_PRIVATE_DATA_SIGNATURE SIGNATURE_32 ('N','V','P','C')\r
84\r
85//\r
86// Nvme controller private data structure.\r
87//\r
88struct _PEI_NVME_CONTROLLER_PRIVATE_DATA {\r
89 UINT32 Signature;\r
90 UINTN MmioBase;\r
ba3aa1c4 91 EFI_NVM_EXPRESS_PASS_THRU_MODE PassThruMode;\r
2e15b750
HW
92 UINTN DevicePathLength;\r
93 EFI_DEVICE_PATH_PROTOCOL *DevicePath;\r
94\r
b8b69433
HW
95 EFI_PEI_RECOVERY_BLOCK_IO_PPI BlkIoPpi;\r
96 EFI_PEI_RECOVERY_BLOCK_IO2_PPI BlkIo2Ppi;\r
2e15b750 97 EDKII_PEI_STORAGE_SECURITY_CMD_PPI StorageSecurityPpi;\r
ba3aa1c4 98 EDKII_PEI_NVM_EXPRESS_PASS_THRU_PPI NvmePassThruPpi;\r
b8b69433
HW
99 EFI_PEI_PPI_DESCRIPTOR BlkIoPpiList;\r
100 EFI_PEI_PPI_DESCRIPTOR BlkIo2PpiList;\r
2e15b750 101 EFI_PEI_PPI_DESCRIPTOR StorageSecurityPpiList;\r
ba3aa1c4 102 EFI_PEI_PPI_DESCRIPTOR NvmePassThruPpiList;\r
b8b69433
HW
103 EFI_PEI_NOTIFY_DESCRIPTOR EndOfPeiNotifyList;\r
104\r
105 //\r
106 // Pointer to identify controller data\r
107 //\r
108 NVME_ADMIN_CONTROLLER_DATA *ControllerData;\r
109\r
110 //\r
111 // (4 + NVME_PRP_SIZE) x 4kB aligned buffers will be carved out of this buffer\r
112 // 1st 4kB boundary is the start of the admin submission queue\r
113 // 2nd 4kB boundary is the start of the admin completion queue\r
114 // 3rd 4kB boundary is the start of I/O submission queue\r
115 // 4th 4kB boundary is the start of I/O completion queue\r
116 // 5th 4kB boundary is the start of PRP list buffers\r
117 //\r
118 VOID *Buffer;\r
119 VOID *BufferMapping;\r
120\r
121 //\r
122 // Pointers to 4kB aligned submission & completion queues\r
123 //\r
124 NVME_SQ *SqBuffer[NVME_MAX_QUEUES];\r
125 NVME_CQ *CqBuffer[NVME_MAX_QUEUES];\r
126\r
127 //\r
128 // Submission and completion queue indices\r
129 //\r
130 NVME_SQTDBL SqTdbl[NVME_MAX_QUEUES];\r
131 NVME_CQHDBL CqHdbl[NVME_MAX_QUEUES];\r
132\r
133 UINT8 Pt[NVME_MAX_QUEUES];\r
134 UINT16 Cid[NVME_MAX_QUEUES];\r
135\r
136 //\r
137 // Nvme controller capabilities\r
138 //\r
139 NVME_CAP Cap;\r
140\r
141 //\r
142 // Namespaces information on the controller\r
143 //\r
144 UINT32 ActiveNamespaceNum;\r
145 PEI_NVME_NAMESPACE_INFO *NamespaceInfo;\r
146};\r
147\r
2e15b750 148#define GET_NVME_PEIM_HC_PRIVATE_DATA_FROM_THIS_BLKIO(a) \\r
b8b69433 149 CR (a, PEI_NVME_CONTROLLER_PRIVATE_DATA, BlkIoPpi, NVME_PEI_CONTROLLER_PRIVATE_DATA_SIGNATURE)\r
2e15b750 150#define GET_NVME_PEIM_HC_PRIVATE_DATA_FROM_THIS_BLKIO2(a) \\r
b8b69433 151 CR (a, PEI_NVME_CONTROLLER_PRIVATE_DATA, BlkIo2Ppi, NVME_PEI_CONTROLLER_PRIVATE_DATA_SIGNATURE)\r
2e15b750
HW
152#define GET_NVME_PEIM_HC_PRIVATE_DATA_FROM_THIS_STROAGE_SECURITY(a) \\r
153 CR (a, PEI_NVME_CONTROLLER_PRIVATE_DATA, StorageSecurityPpi, NVME_PEI_CONTROLLER_PRIVATE_DATA_SIGNATURE)\r
ba3aa1c4
MC
154#define GET_NVME_PEIM_HC_PRIVATE_DATA_FROM_THIS_NVME_PASSTHRU(a) \\r
155 CR (a, PEI_NVME_CONTROLLER_PRIVATE_DATA, NvmePassThruPpi, NVME_PEI_CONTROLLER_PRIVATE_DATA_SIGNATURE)\r
2e15b750 156#define GET_NVME_PEIM_HC_PRIVATE_DATA_FROM_THIS_NOTIFY(a) \\r
b8b69433
HW
157 CR (a, PEI_NVME_CONTROLLER_PRIVATE_DATA, EndOfPeiNotifyList, NVME_PEI_CONTROLLER_PRIVATE_DATA_SIGNATURE)\r
158\r
159\r
4104423a
HW
160//\r
161// Internal functions\r
162//\r
b8b69433
HW
163\r
164/**\r
165 Allocates pages that are suitable for an OperationBusMasterCommonBuffer or\r
166 OperationBusMasterCommonBuffer64 mapping.\r
167\r
168 @param Pages The number of pages to allocate.\r
169 @param HostAddress A pointer to store the base system memory address of the\r
170 allocated range.\r
171 @param DeviceAddress The resulting map address for the bus master PCI controller to use to\r
172 access the hosts HostAddress.\r
173 @param Mapping A resulting value to pass to Unmap().\r
174\r
175 @retval EFI_SUCCESS The requested memory pages were allocated.\r
176 @retval EFI_UNSUPPORTED Attributes is unsupported. The only legal attribute bits are\r
177 MEMORY_WRITE_COMBINE and MEMORY_CACHED.\r
178 @retval EFI_INVALID_PARAMETER One or more parameters are invalid.\r
179 @retval EFI_OUT_OF_RESOURCES The memory pages could not be allocated.\r
180\r
181**/\r
182EFI_STATUS\r
183IoMmuAllocateBuffer (\r
184 IN UINTN Pages,\r
185 OUT VOID **HostAddress,\r
186 OUT EFI_PHYSICAL_ADDRESS *DeviceAddress,\r
187 OUT VOID **Mapping\r
188 );\r
189\r
190/**\r
191 Frees memory that was allocated with AllocateBuffer().\r
192\r
193 @param Pages The number of pages to free.\r
194 @param HostAddress The base system memory address of the allocated range.\r
195 @param Mapping The mapping value returned from Map().\r
196\r
197 @retval EFI_SUCCESS The requested memory pages were freed.\r
198 @retval EFI_INVALID_PARAMETER The memory range specified by HostAddress and Pages\r
199 was not allocated with AllocateBuffer().\r
200\r
201**/\r
202EFI_STATUS\r
203IoMmuFreeBuffer (\r
204 IN UINTN Pages,\r
205 IN VOID *HostAddress,\r
206 IN VOID *Mapping\r
207 );\r
208\r
209/**\r
210 Provides the controller-specific addresses required to access system memory from a\r
211 DMA bus master.\r
212\r
213 @param Operation Indicates if the bus master is going to read or write to system memory.\r
214 @param HostAddress The system memory address to map to the PCI controller.\r
215 @param NumberOfBytes On input the number of bytes to map. On output the number of bytes\r
216 that were mapped.\r
217 @param DeviceAddress The resulting map address for the bus master PCI controller to use to\r
218 access the hosts HostAddress.\r
219 @param Mapping A resulting value to pass to Unmap().\r
220\r
221 @retval EFI_SUCCESS The range was mapped for the returned NumberOfBytes.\r
222 @retval EFI_UNSUPPORTED The HostAddress cannot be mapped as a common buffer.\r
223 @retval EFI_INVALID_PARAMETER One or more parameters are invalid.\r
224 @retval EFI_OUT_OF_RESOURCES The request could not be completed due to a lack of resources.\r
225 @retval EFI_DEVICE_ERROR The system hardware could not map the requested address.\r
226\r
227**/\r
228EFI_STATUS\r
229IoMmuMap (\r
230 IN EDKII_IOMMU_OPERATION Operation,\r
231 IN VOID *HostAddress,\r
232 IN OUT UINTN *NumberOfBytes,\r
233 OUT EFI_PHYSICAL_ADDRESS *DeviceAddress,\r
234 OUT VOID **Mapping\r
235 );\r
236\r
237/**\r
238 Completes the Map() operation and releases any corresponding resources.\r
239\r
240 @param Mapping The mapping value returned from Map().\r
241\r
242 @retval EFI_SUCCESS The range was unmapped.\r
243 @retval EFI_INVALID_PARAMETER Mapping is not a value that was returned by Map().\r
244 @retval EFI_DEVICE_ERROR The data was not committed to the target system memory.\r
245**/\r
246EFI_STATUS\r
247IoMmuUnmap (\r
248 IN VOID *Mapping\r
249 );\r
250\r
251/**\r
252 One notified function to cleanup the allocated resources at the end of PEI.\r
253\r
254 @param[in] PeiServices Pointer to PEI Services Table.\r
255 @param[in] NotifyDescriptor Pointer to the descriptor for the Notification\r
256 event that caused this function to execute.\r
257 @param[in] Ppi Pointer to the PPI data associated with this function.\r
258\r
259 @retval EFI_SUCCESS The function completes successfully\r
260\r
261**/\r
262EFI_STATUS\r
263EFIAPI\r
264NvmePeimEndOfPei (\r
265 IN EFI_PEI_SERVICES **PeiServices,\r
266 IN EFI_PEI_NOTIFY_DESCRIPTOR *NotifyDescriptor,\r
267 IN VOID *Ppi\r
268 );\r
269\r
05fd2a92
HW
270/**\r
271 Get the size of the current device path instance.\r
272\r
273 @param[in] DevicePath A pointer to the EFI_DEVICE_PATH_PROTOCOL\r
274 structure.\r
275 @param[out] InstanceSize The size of the current device path instance.\r
276 @param[out] EntireDevicePathEnd Indicate whether the instance is the last\r
277 one in the device path strucure.\r
278\r
279 @retval EFI_SUCCESS The size of the current device path instance is fetched.\r
280 @retval Others Fails to get the size of the current device path instance.\r
281\r
282**/\r
283EFI_STATUS\r
284GetDevicePathInstanceSize (\r
285 IN EFI_DEVICE_PATH_PROTOCOL *DevicePath,\r
286 OUT UINTN *InstanceSize,\r
287 OUT BOOLEAN *EntireDevicePathEnd\r
288 );\r
289\r
2e15b750
HW
290/**\r
291 Check the validity of the device path of a NVM Express host controller.\r
292\r
293 @param[in] DevicePath A pointer to the EFI_DEVICE_PATH_PROTOCOL\r
294 structure.\r
295 @param[in] DevicePathLength The length of the device path.\r
296\r
297 @retval EFI_SUCCESS The device path is valid.\r
298 @retval EFI_INVALID_PARAMETER The device path is invalid.\r
299\r
300**/\r
301EFI_STATUS\r
302NvmeIsHcDevicePathValid (\r
303 IN EFI_DEVICE_PATH_PROTOCOL *DevicePath,\r
304 IN UINTN DevicePathLength\r
305 );\r
306\r
307/**\r
308 Build the device path for an Nvm Express device with given namespace identifier\r
309 and namespace extended unique identifier.\r
310\r
311 @param[in] Private A pointer to the PEI_NVME_CONTROLLER_PRIVATE_DATA\r
312 data structure.\r
313 @param[in] NamespaceId The given namespace identifier.\r
314 @param[in] NamespaceUuid The given namespace extended unique identifier.\r
315 @param[out] DevicePathLength The length of the device path in bytes specified\r
316 by DevicePath.\r
317 @param[out] DevicePath The device path of Nvm Express device.\r
318\r
319 @retval EFI_SUCCESS The operation succeeds.\r
320 @retval EFI_INVALID_PARAMETER The parameters are invalid.\r
321 @retval EFI_OUT_OF_RESOURCES The operation fails due to lack of resources.\r
322\r
323**/\r
324EFI_STATUS\r
325NvmeBuildDevicePath (\r
326 IN PEI_NVME_CONTROLLER_PRIVATE_DATA *Private,\r
327 IN UINT32 NamespaceId,\r
328 IN UINT64 NamespaceUuid,\r
329 OUT UINTN *DevicePathLength,\r
330 OUT EFI_DEVICE_PATH_PROTOCOL **DevicePath\r
331 );\r
332\r
05fd2a92
HW
333/**\r
334 Determine if a specific NVM Express controller can be skipped for S3 phase.\r
335\r
336 @param[in] HcDevicePath Device path of the controller.\r
337 @param[in] HcDevicePathLength Length of the device path specified by\r
338 HcDevicePath.\r
339\r
340 @retval The number of ports that need to be enumerated.\r
341\r
342**/\r
343BOOLEAN\r
344NvmeS3SkipThisController (\r
345 IN EFI_DEVICE_PATH_PROTOCOL *HcDevicePath,\r
346 IN UINTN HcDevicePathLength\r
347 );\r
348\r
b8b69433 349#endif\r