]> git.proxmox.com Git - mirror_edk2.git/blame - ArmPlatformPkg/ArmVExpressPkg/ArmVExpressDxe/ArmFvpDxe.c
ArmPlatformPkg/ArmVExpressDxe: Change FDT default file names.
[mirror_edk2.git] / ArmPlatformPkg / ArmVExpressPkg / ArmVExpressDxe / ArmFvpDxe.c
CommitLineData
94caa81c 1/** @file\r
2\r
04f1a709 3 Copyright (c) 2013-2015, ARM Ltd. All rights reserved.<BR>\r
94caa81c 4\r
5 This program and the accompanying materials\r
6 are licensed and made available under the terms and conditions of the BSD License\r
7 which accompanies this distribution. The full text of the license may be found at\r
8 http://opensource.org/licenses/bsd-license.php\r
9\r
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
12\r
13**/\r
14\r
dff72027
OM
15#include "ArmVExpressInternal.h"\r
16\r
f66eab9b
OM
17#include <PiDxe.h>\r
18#include <Library/BaseMemoryLib.h>\r
94caa81c 19#include <Library/VirtioMmioDeviceLib.h>\r
ced216f8 20#include <Library/ArmShellCmdLib.h>\r
04f1a709 21#include <Library/MemoryAllocationLib.h>\r
f66eab9b
OM
22#include <Library/DevicePathLib.h>\r
23\r
24#include <Protocol/FirmwareVolume2.h>\r
94caa81c 25\r
26#define ARM_FVP_BASE_VIRTIO_BLOCK_BASE 0x1c130000\r
b836204e 27STATIC CONST CHAR16 *mFdtFallbackName = L"fdt.dtb";\r
94caa81c 28\r
29#pragma pack(1)\r
30typedef struct {\r
31 VENDOR_DEVICE_PATH Vendor;\r
32 EFI_DEVICE_PATH_PROTOCOL End;\r
33} VIRTIO_BLK_DEVICE_PATH;\r
34#pragma pack()\r
35\r
36VIRTIO_BLK_DEVICE_PATH mVirtioBlockDevicePath =\r
37{\r
38 {\r
39 {\r
40 HARDWARE_DEVICE_PATH,\r
41 HW_VENDOR_DP,\r
42 {\r
43 (UINT8)( sizeof(VENDOR_DEVICE_PATH) ),\r
44 (UINT8)((sizeof(VENDOR_DEVICE_PATH)) >> 8)\r
45 }\r
46 },\r
47 EFI_CALLER_ID_GUID,\r
48 },\r
49 {\r
50 END_DEVICE_PATH_TYPE,\r
51 END_ENTIRE_DEVICE_PATH_SUBTYPE,\r
52 {\r
53 sizeof (EFI_DEVICE_PATH_PROTOCOL),\r
54 0\r
55 }\r
56 }\r
57};\r
58\r
f66eab9b
OM
59STATIC\r
60EFI_STATUS\r
61InternalFindFdtByGuid (\r
62 IN OUT EFI_DEVICE_PATH **FdtDevicePath,\r
63 IN CONST EFI_GUID *FdtGuid\r
64 )\r
65{\r
66 MEDIA_FW_VOL_FILEPATH_DEVICE_PATH FileDevicePath;\r
67 EFI_HANDLE *HandleBuffer;\r
68 UINTN HandleCount;\r
69 UINTN Index;\r
70 EFI_FIRMWARE_VOLUME2_PROTOCOL *FvProtocol;\r
71 EFI_GUID NameGuid;\r
72 UINTN Size;\r
73 VOID *Key;\r
74 EFI_FV_FILETYPE FileType;\r
75 EFI_FV_FILE_ATTRIBUTES Attributes;\r
76 EFI_DEVICE_PATH *FvDevicePath;\r
77 EFI_STATUS Status;\r
78\r
79 if (FdtGuid == NULL) {\r
80 return EFI_NOT_FOUND;\r
81 }\r
82\r
83 EfiInitializeFwVolDevicepathNode (&FileDevicePath, FdtGuid);\r
84\r
85 HandleBuffer = NULL;\r
86 Status = gBS->LocateHandleBuffer (\r
87 ByProtocol,\r
88 &gEfiFirmwareVolume2ProtocolGuid,\r
89 NULL,\r
90 &HandleCount,\r
91 &HandleBuffer\r
92 );\r
93 if (EFI_ERROR (Status)) {\r
94 return Status;\r
95 }\r
96\r
97 for (Index = 0; Index < HandleCount; Index++) {\r
98 Status = gBS->HandleProtocol (\r
99 HandleBuffer[Index],\r
100 &gEfiFirmwareVolume2ProtocolGuid,\r
101 (VOID **) &FvProtocol\r
102 );\r
103 if (EFI_ERROR (Status)) {\r
104 return Status;\r
105 }\r
106\r
107 // Allocate Key\r
108 Key = AllocatePool (FvProtocol->KeySize);\r
109 ASSERT (Key != NULL);\r
110 ZeroMem (Key, FvProtocol->KeySize);\r
111\r
112 do {\r
113 FileType = EFI_FV_FILETYPE_RAW;\r
114 Status = FvProtocol->GetNextFile (FvProtocol, Key, &FileType, &NameGuid, &Attributes, &Size);\r
115 if (Status == EFI_NOT_FOUND) {\r
116 break;\r
117 }\r
118 if (EFI_ERROR (Status)) {\r
119 return Status;\r
120 }\r
121\r
122 //\r
123 // Check whether this file is the one we are looking for. If so,\r
124 // create a device path for it and return it to the caller.\r
125 //\r
126 if (CompareGuid (&NameGuid, FdtGuid)) {\r
127 Status = gBS->HandleProtocol (HandleBuffer[Index], &gEfiDevicePathProtocolGuid, (VOID **)&FvDevicePath);\r
128 if (!EFI_ERROR (Status)) {\r
129 *FdtDevicePath = AppendDevicePathNode (FvDevicePath,\r
130 (EFI_DEVICE_PATH_PROTOCOL *)&FileDevicePath);\r
131 }\r
132 goto Done;\r
133 }\r
134 } while (TRUE);\r
135 FreePool (Key);\r
136 }\r
137\r
138 if (Index == HandleCount) {\r
139 Status = EFI_NOT_FOUND;\r
140 }\r
141 return Status;\r
142\r
143Done:\r
144 FreePool (Key);\r
145 return Status;\r
146}\r
147\r
04f1a709
RC
148/**\r
149 * Generic UEFI Entrypoint for 'ArmFvpDxe' driver\r
150 * See UEFI specification for the details of the parameters\r
151 */\r
94caa81c 152EFI_STATUS\r
153EFIAPI\r
154ArmFvpInitialise (\r
155 IN EFI_HANDLE ImageHandle,\r
156 IN EFI_SYSTEM_TABLE *SystemTable\r
157 )\r
158{\r
04f1a709 159 EFI_STATUS Status;\r
b836204e
OM
160 CONST ARM_VEXPRESS_PLATFORM *Platform;\r
161 BOOLEAN NeedFallback;\r
162 UINTN TextDevicePathBaseSize;\r
04f1a709 163 UINTN TextDevicePathSize;\r
b836204e 164 CHAR16 *TextDevicePath;\r
04f1a709 165 VOID *Buffer;\r
f66eab9b 166 EFI_DEVICE_PATH *FdtDevicePath;\r
94caa81c 167\r
b836204e
OM
168 Status = gBS->InstallProtocolInterface (\r
169 &ImageHandle,\r
170 &gEfiDevicePathProtocolGuid, EFI_NATIVE_INTERFACE,\r
171 &mVirtioBlockDevicePath\r
172 );\r
94caa81c 173 if (EFI_ERROR (Status)) {\r
174 return Status;\r
175 }\r
176\r
04f1a709
RC
177 Status = ArmVExpressGetPlatform (&Platform);\r
178 if (!EFI_ERROR (Status)) {\r
f66eab9b
OM
179 FdtDevicePath = NULL;\r
180 Status = InternalFindFdtByGuid (&FdtDevicePath, Platform->FdtGuid);\r
181 if (!EFI_ERROR (Status)) {\r
182 TextDevicePath = ConvertDevicePathToText (FdtDevicePath, FALSE, FALSE);\r
183 if (TextDevicePath != NULL) {\r
184 TextDevicePathSize = StrSize (TextDevicePath);\r
185 }\r
186 FreePool (FdtDevicePath);\r
187 } else {\r
b836204e
OM
188 //\r
189 // In the case of the FVP base and foundation platforms, two default\r
190 // text device paths for the FDT are defined. The first one, like every\r
191 // other platform, ends with a file name that identifies the platform. The\r
192 // second one ends with the fallback file name "fdt.dtb" for historical\r
193 // backward compatibility reasons.\r
194 //\r
195 NeedFallback = (Platform->Id == ARM_FVP_BASE) ||\r
196 (Platform->Id == ARM_FVP_FOUNDATION);\r
197\r
198 TextDevicePathBaseSize = StrSize ((CHAR16*)PcdGetPtr (PcdFvpFdtDevicePathsBase)) - sizeof (CHAR16);\r
199 TextDevicePathSize = TextDevicePathBaseSize + StrSize (Platform->FdtName);\r
200 if (NeedFallback) {\r
201 TextDevicePathSize += TextDevicePathBaseSize + StrSize (mFdtFallbackName);\r
202 }\r
f66eab9b
OM
203\r
204 TextDevicePath = AllocatePool (TextDevicePathSize);\r
205 if (TextDevicePath != NULL) {\r
206 StrCpy (TextDevicePath, ((CHAR16*)PcdGetPtr (PcdFvpFdtDevicePathsBase)));\r
207 StrCat (TextDevicePath, Platform->FdtName);\r
b836204e
OM
208\r
209 if (NeedFallback) {\r
210 StrCat (TextDevicePath, L";");\r
211 StrCat (TextDevicePath, ((CHAR16*)PcdGetPtr (PcdFvpFdtDevicePathsBase)));\r
212 StrCat (TextDevicePath, mFdtFallbackName);\r
213 }\r
f66eab9b
OM
214 }\r
215 }\r
04f1a709 216 if (TextDevicePath != NULL) {\r
04f1a709
RC
217 Buffer = PcdSetPtr (PcdFdtDevicePaths, &TextDevicePathSize, TextDevicePath);\r
218 if (Buffer == NULL) {\r
219 DEBUG ((\r
220 EFI_D_ERROR,\r
221 "ArmFvpDxe: Setting of FDT device path in PcdFdtDevicePaths failed - %r\n", EFI_BUFFER_TOO_SMALL\r
222 ));\r
223 }\r
224 FreePool (TextDevicePath);\r
b836204e
OM
225 } else {\r
226 DEBUG ((\r
227 EFI_D_ERROR,\r
228 "ArmFvpDxe: Setting of FDT device path in PcdFdtDevicePaths failed - %r\n", EFI_OUT_OF_RESOURCES\r
229 ));\r
04f1a709
RC
230 }\r
231 }\r
232\r
94caa81c 233 // Declare the Virtio BlockIo device\r
234 Status = VirtioMmioInstallDevice (ARM_FVP_BASE_VIRTIO_BLOCK_BASE, ImageHandle);\r
235 if (EFI_ERROR (Status)) {\r
236 DEBUG ((EFI_D_ERROR, "ArmFvpDxe: Failed to install Virtio block device\n"));\r
237 }\r
238\r
ced216f8
HL
239 // Install dynamic Shell command to run baremetal binaries.\r
240 Status = ShellDynCmdRunAxfInstall (ImageHandle);\r
241 if (EFI_ERROR (Status)) {\r
242 DEBUG ((EFI_D_ERROR, "ArmFvpDxe: Failed to install ShellDynCmdRunAxf\n"));\r
243 }\r
244\r
94caa81c 245 return Status;\r
246}\r