]> git.proxmox.com Git - mirror_edk2.git/blame - ShellPkg/Library/UefiShellDebug1CommandsLib/Bcfg.c
Add check before use to make code run more safer.
[mirror_edk2.git] / ShellPkg / Library / UefiShellDebug1CommandsLib / Bcfg.c
CommitLineData
5d73d92f 1/** @file\r
3737ac2b 2 Main file for bcfg shell Debug1 function.\r
5d73d92f 3\r
3737ac2b 4 Copyright (c) 2010 - 2011, Intel Corporation. All rights reserved.<BR>\r
5d73d92f 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
15#include "UefiShellDebug1CommandsLib.h"\r
16#include <Guid/GlobalVariable.h>\r
17#include <Library/PrintLib.h>\r
18#include <Library/HandleParsingLib.h>\r
19#include <Library/DevicePathLib.h>\r
20\r
21typedef enum {\r
3737ac2b 22 BcfgTargetBootOrder = 0,\r
23 BcfgTargetDriverOrder = 1,\r
24 BcfgTargetMax = 2\r
5d73d92f 25} BCFG_OPERATION_TARGET;\r
26\r
27typedef enum {\r
3737ac2b 28 BcfgTypeDump = 0,\r
29 BcfgTypeAdd = 1,\r
30 BcfgTypeAddp = 2,\r
31 BcfgTypeAddh = 3,\r
32 BcfgTypeRm = 4,\r
33 BcfgTypeMv = 5,\r
34 BcfgTypeOpt = 6,\r
35 BcfgTypeMax = 7\r
5d73d92f 36} BCFG_OPERATION_TYPE;\r
37\r
38typedef struct {\r
39 BCFG_OPERATION_TARGET Target;\r
40 BCFG_OPERATION_TYPE Type;\r
41 UINT16 Number1;\r
42 UINT16 Number2;\r
43 UINTN HandleIndex;\r
44 CHAR16 *FileName;\r
45 CHAR16 *Description;\r
46 UINT16 *Order;\r
47 CONST CHAR16 *OptData;\r
48} BGFG_OPERATION;\r
49\r
6878e7a7 50/**\r
51 This function will populate the device path protocol parameter based on TheHandle.\r
52 \r
53 @param[in,out] DevPath On a sucessful return the device path to the handle.\r
54\r
55 @retval EFI_SUCCESS The device path was sucessfully returned.\r
56 @retval other A error from gBS->HandleProtocol.\r
57\r
58 @sa HandleProtocol\r
59**/\r
60EFI_STATUS\r
61EFIAPI\r
62GetDevicePathForDriverHandleDebug1 (\r
63 IN EFI_HANDLE TheHandle,\r
64 IN OUT EFI_DEVICE_PATH_PROTOCOL **FilePath\r
65 )\r
66{\r
67 EFI_STATUS Status;\r
68 EFI_LOADED_IMAGE_PROTOCOL *LoadedImage;\r
69 EFI_DEVICE_PATH_PROTOCOL *ImageDevicePath;\r
70\r
71 Status = gBS->OpenProtocol (\r
72 TheHandle,\r
73 &gEfiLoadedImageProtocolGuid,\r
74 (VOID**)&LoadedImage,\r
75 gImageHandle,\r
76 NULL,\r
77 EFI_OPEN_PROTOCOL_GET_PROTOCOL\r
78 );\r
79 if (!EFI_ERROR (Status)) {\r
80 Status = gBS->OpenProtocol (\r
81 LoadedImage->DeviceHandle,\r
82 &gEfiDevicePathProtocolGuid,\r
83 (VOID**)&ImageDevicePath,\r
84 gImageHandle,\r
85 NULL,\r
86 EFI_OPEN_PROTOCOL_GET_PROTOCOL\r
87 );\r
88 if (!EFI_ERROR (Status)) {\r
89// *DevPath = DuplicateDevicePath (ImageDevicePath);\r
90// *FilePath = DuplicateDevicePath (LoadedImage->FilePath);\r
91 *FilePath = AppendDevicePath(ImageDevicePath,LoadedImage->FilePath);\r
92 gBS->CloseProtocol(\r
93 LoadedImage->DeviceHandle,\r
94 &gEfiDevicePathProtocolGuid,\r
95 gImageHandle,\r
96 NULL);\r
97 }\r
98 gBS->CloseProtocol(\r
99 TheHandle,\r
100 &gEfiLoadedImageProtocolGuid,\r
101 gImageHandle,\r
102 NULL);\r
103 }\r
104 return (Status);\r
105}\r
106\r
3737ac2b 107/**\r
108 Function to add a option.\r
109\r
110 @param[in] Position The position to add Target at.\r
111 @param[in] File The file to make the target.\r
112 @param[in] Desc The description text.\r
113 @param[in] CurrentOrder The pointer to the current order of items.\r
114 @param[in] OrderCount The number if items in CurrentOrder.\r
115 @param[in] Target The info on the option to add.\r
116 @param[in] UseHandle TRUE to use HandleNumber, FALSE to use File and Desc.\r
117 @param[in] UsePath TRUE to convert to devicepath.\r
118 @param[in] HandleNumber The handle number to add.\r
119\r
120 @retval SHELL_SUCCESS The operation was successful.\r
121 @retval SHELL_INVALID_PARAMETER A parameter was invalid.\r
122**/\r
5d73d92f 123SHELL_STATUS\r
124EFIAPI\r
3737ac2b 125BcfgAddDebug1(\r
5d73d92f 126 IN UINTN Position,\r
127 IN CONST CHAR16 *File,\r
128 IN CONST CHAR16 *Desc,\r
129 IN CONST UINT16 *CurrentOrder,\r
130 IN CONST UINTN OrderCount,\r
131 IN CONST BCFG_OPERATION_TARGET Target,\r
132 IN CONST BOOLEAN UseHandle,\r
133 IN CONST BOOLEAN UsePath,\r
134 IN CONST UINTN HandleNumber\r
135 )\r
136{\r
137 EFI_STATUS Status;\r
3737ac2b 138 EFI_DEVICE_PATH_PROTOCOL *DevicePath;\r
139 EFI_DEVICE_PATH_PROTOCOL *FilePath;\r
140 EFI_DEVICE_PATH_PROTOCOL *FileNode;\r
6878e7a7 141// EFI_DEVICE_PATH_PROTOCOL *DevPath;\r
5d73d92f 142 CHAR16 *Str;\r
6878e7a7 143// CONST CHAR16 *StringWalker;\r
3737ac2b 144 UINT8 *TempByteBuffer;\r
145 UINT8 *TempByteStart;\r
5d73d92f 146 EFI_SHELL_FILE_INFO *Arg;\r
147 EFI_SHELL_FILE_INFO *FileList;\r
148 CHAR16 OptionStr[40];\r
149 UINTN DescSize, FilePathSize;\r
150 BOOLEAN Found;\r
151 UINTN TargetLocation;\r
152 UINTN Index;\r
153 EFI_HANDLE *Handles;\r
154 EFI_HANDLE CurHandle;\r
155 UINTN DriverBindingHandleCount;\r
156 UINTN ParentControllerHandleCount;\r
157 UINTN ChildControllerHandleCount;\r
158 SHELL_STATUS ShellStatus;\r
159 UINT16 *NewOrder;\r
160\r
161 if (!UseHandle) {\r
3737ac2b 162 if (File == NULL || Desc == NULL) {\r
163 return (SHELL_INVALID_PARAMETER);\r
164 }\r
5d73d92f 165 } else {\r
3737ac2b 166 if (HandleNumber == 0) {\r
167 return (SHELL_INVALID_PARAMETER);\r
168 }\r
5d73d92f 169 }\r
170\r
3737ac2b 171 if (Position > OrderCount) {\r
172 Position = OrderCount;\r
173 }\r
5d73d92f 174\r
175 Str = NULL;\r
176 FilePath = NULL;\r
177 FileNode = NULL;\r
178 FileList = NULL;\r
179 Handles = NULL;\r
180 ShellStatus = SHELL_SUCCESS;\r
181 TargetLocation = 0xFFFF;\r
182\r
5d73d92f 183 if (UseHandle) {\r
6878e7a7 184 CurHandle = ConvertHandleIndexToHandle(HandleNumber);\r
185 if (CurHandle == NULL) {\r
186 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, L"Handle Number");\r
5d73d92f 187 ShellStatus = SHELL_INVALID_PARAMETER;\r
188 } else {\r
6878e7a7 189 if (Target == BcfgTargetBootOrder) {\r
190 //\r
191 //Make sure that the handle should point to a real controller\r
192 //\r
193 Status = PARSE_HANDLE_DATABASE_UEFI_DRIVERS (\r
194 CurHandle,\r
195 &DriverBindingHandleCount,\r
196 NULL);\r
197\r
198 Status = PARSE_HANDLE_DATABASE_PARENTS (\r
199 CurHandle,\r
200 &ParentControllerHandleCount,\r
201 NULL);\r
202\r
203 Status = ParseHandleDatabaseForChildControllers (\r
204 CurHandle,\r
205 &ChildControllerHandleCount,\r
206 NULL);\r
207\r
208 if (DriverBindingHandleCount > 0\r
209 || ParentControllerHandleCount > 0\r
210 || ChildControllerHandleCount > 0) {\r
211 FilePath = NULL;\r
212 Status = gBS->HandleProtocol (\r
213 CurHandle,\r
214 &gEfiDevicePathProtocolGuid,\r
215 (VOID**)&FilePath);\r
216 }\r
217 if (EFI_ERROR (Status)) {\r
218 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_HANDLE), gShellDebug1HiiHandle, HandleNumber);\r
219 ShellStatus = SHELL_INVALID_PARAMETER;\r
220 }\r
221 } else {\r
222 //\r
223 //Make sure that the handle should point to driver, not a controller.\r
224 //\r
225 Status = PARSE_HANDLE_DATABASE_UEFI_DRIVERS (\r
226 CurHandle,\r
227 &DriverBindingHandleCount,\r
228 NULL);\r
229\r
230 Status = PARSE_HANDLE_DATABASE_PARENTS (\r
231 CurHandle,\r
232 &ParentControllerHandleCount,\r
233 NULL);\r
234\r
235 Status = ParseHandleDatabaseForChildControllers (\r
236 CurHandle,\r
237 &ChildControllerHandleCount,\r
238 NULL);\r
239\r
5d73d92f 240 Status = gBS->HandleProtocol (\r
241 CurHandle,\r
242 &gEfiDevicePathProtocolGuid,\r
243 (VOID**)&FilePath);\r
6878e7a7 244\r
245 if (DriverBindingHandleCount > 0\r
246 || ParentControllerHandleCount > 0\r
247 || ChildControllerHandleCount > 0\r
248 || !EFI_ERROR(Status) ) {\r
249 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, L"Handle Number");\r
250 ShellStatus = SHELL_INVALID_PARAMETER;\r
251 } else {\r
252 //\r
253 // Get the DevicePath from the loaded image information.\r
254 //\r
255 Status = GetDevicePathForDriverHandleDebug1(CurHandle, &FilePath);\r
256 }\r
5d73d92f 257 }\r
258 }\r
259 } else {\r
260 //\r
261 // Get file info\r
262 //\r
263 ShellOpenFileMetaArg ((CHAR16*)File, EFI_FILE_MODE_READ, &FileList);\r
264\r
3737ac2b 265 if (FileList == NULL) {\r
266 //\r
267 // If filename matched nothing fail\r
268 //\r
269 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_FILE_OPEN_FAIL), gShellDebug1HiiHandle, File);\r
270 ShellStatus = SHELL_INVALID_PARAMETER;\r
271 } else if (FileList->Link.ForwardLink != FileList->Link.BackLink) {\r
272 //\r
273 // If filename expanded to multiple names, fail\r
274 //\r
5d73d92f 275 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_FILE), gShellDebug1HiiHandle, File);\r
276 ShellStatus = SHELL_INVALID_PARAMETER;\r
277 } else {\r
278 Arg = (EFI_SHELL_FILE_INFO*)GetFirstNode(&FileList->Link);\r
279 if (EFI_ERROR(Arg->Status)) {\r
280 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_FILE_OPEN), gShellDebug1HiiHandle, File, Arg->Status);\r
281 ShellStatus = SHELL_INVALID_PARAMETER;\r
282 } else {\r
283 //\r
284 // Build FilePath to the filename\r
285 //\r
286\r
287 //\r
288 // get the device path\r
289 //\r
366f81a0 290 DevicePath = gEfiShellProtocol->GetDevicePathFromFilePath(Arg->FullName);\r
3737ac2b 291 if (DevicePath == NULL) {\r
5d73d92f 292 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_FILE_DP), gShellDebug1HiiHandle, Arg->FullName);\r
293 ShellStatus = SHELL_UNSUPPORTED;\r
294 } else {\r
6878e7a7 295/*\r
5d73d92f 296 if (UsePath) {\r
297 DevPath = DevicePath;\r
298 while (!IsDevicePathEnd(DevPath)) {\r
299 if ((DevicePathType(DevPath) == MEDIA_DEVICE_PATH) &&\r
300 (DevicePathSubType(DevPath) == MEDIA_HARDDRIVE_DP)) {\r
301\r
302 //\r
303 // If we find it use it instead\r
304 //\r
305 DevicePath = DevPath;\r
306 break;\r
307 }\r
308 DevPath = NextDevicePathNode(DevPath);\r
309 }\r
310 //\r
311 // append the file\r
312 //\r
3737ac2b 313 for(StringWalker=Arg->FullName; *StringWalker != CHAR_NULL && *StringWalker != ':'; StringWalker++);\r
314 FileNode = FileDevicePath(NULL, StringWalker+1);\r
5d73d92f 315 FilePath = AppendDevicePath(DevicePath, FileNode);\r
316 FreePool(FileNode);\r
317 } else {\r
6878e7a7 318*/\r
5d73d92f 319 FilePath = DuplicateDevicePath(DevicePath);\r
6878e7a7 320/*\r
5d73d92f 321 }\r
6878e7a7 322*/\r
5d73d92f 323 FreePool(DevicePath);\r
324 }\r
325 }\r
326 }\r
327 }\r
328\r
329\r
330 if (ShellStatus == SHELL_SUCCESS) {\r
331 //\r
332 // Find a free target ,a brute force implementation\r
333 //\r
334 Found = FALSE;\r
3737ac2b 335 for (TargetLocation=0; TargetLocation < 0xFFFF; TargetLocation++) {\r
5d73d92f 336 Found = TRUE;\r
337 for (Index=0; Index < OrderCount; Index++) {\r
338 if (CurrentOrder[Index] == TargetLocation) {\r
339 Found = FALSE;\r
340 break;\r
341 }\r
342 }\r
343\r
344 if (Found) {\r
345 break;\r
346 }\r
347 }\r
348\r
349 if (TargetLocation == 0xFFFF) {\r
350 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_TARGET_NF), gShellDebug1HiiHandle);\r
351 } else {\r
352 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_TARGET), gShellDebug1HiiHandle, TargetLocation);\r
353 }\r
354 }\r
355\r
356 if (ShellStatus == SHELL_SUCCESS) {\r
357 //\r
358 // Add the option\r
359 //\r
360 DescSize = StrSize(Desc);\r
361 FilePathSize = GetDevicePathSize (FilePath);\r
362\r
3737ac2b 363 TempByteBuffer = AllocateZeroPool(sizeof(UINT32) + sizeof(UINT16) + DescSize + FilePathSize);\r
33c031ee 364 if (TempByteBuffer != NULL) {\r
365 TempByteStart = TempByteBuffer;\r
366 *((UINT32 *) TempByteBuffer) = LOAD_OPTION_ACTIVE; // Attributes\r
367 TempByteBuffer += sizeof (UINT32);\r
5d73d92f 368\r
33c031ee 369 *((UINT16 *) TempByteBuffer) = (UINT16)FilePathSize; // FilePathListLength\r
370 TempByteBuffer += sizeof (UINT16);\r
5d73d92f 371\r
33c031ee 372 CopyMem (TempByteBuffer, Desc, DescSize);\r
373 TempByteBuffer += DescSize;\r
374 CopyMem (TempByteBuffer, FilePath, FilePathSize);\r
5d73d92f 375\r
33c031ee 376 UnicodeSPrint (OptionStr, sizeof(OptionStr), L"%s%04x", Target == BcfgTargetBootOrder?L"Boot":L"Driver", TargetLocation);\r
377 Status = gRT->SetVariable (\r
378 OptionStr,\r
379 &gEfiGlobalVariableGuid,\r
380 EFI_VARIABLE_NON_VOLATILE|EFI_VARIABLE_BOOTSERVICE_ACCESS|EFI_VARIABLE_RUNTIME_ACCESS,\r
381 sizeof(UINT32) + sizeof(UINT16) + DescSize + FilePathSize,\r
382 TempByteStart\r
383 );\r
384\r
385 FreePool(TempByteStart);\r
386 } else {\r
387 Status = EFI_OUT_OF_RESOURCES;\r
388 }\r
5d73d92f 389\r
390 if (EFI_ERROR(Status)) {\r
391 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_SET_VAR_FAIL), gShellDebug1HiiHandle, OptionStr, Status);\r
392 } else {\r
3737ac2b 393 NewOrder = AllocateZeroPool((OrderCount+1)*sizeof(NewOrder[0]));\r
5d73d92f 394 ASSERT(NewOrder != NULL);\r
395 CopyMem(NewOrder, CurrentOrder, (OrderCount)*sizeof(NewOrder[0]));\r
396\r
397 //\r
398 // Insert target into order list\r
399 //\r
400 for (Index=OrderCount; Index > Position; Index--) {\r
401 NewOrder[Index] = NewOrder[Index-1];\r
402 }\r
403\r
404 NewOrder[Position] = (UINT16) TargetLocation;\r
405 Status = gRT->SetVariable (\r
3737ac2b 406 Target == BcfgTargetBootOrder?L"BootOrder":L"DriverOrder",\r
5d73d92f 407 &gEfiGlobalVariableGuid,\r
408 EFI_VARIABLE_NON_VOLATILE|EFI_VARIABLE_BOOTSERVICE_ACCESS|EFI_VARIABLE_RUNTIME_ACCESS,\r
409 (OrderCount+1) * sizeof(UINT16),\r
410 NewOrder\r
411 );\r
412\r
413 FreePool(NewOrder);\r
414\r
415 if (EFI_ERROR(Status)) {\r
3737ac2b 416 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_WRITE_FAIL), gShellDebug1HiiHandle, Target == BcfgTargetBootOrder?L"BootOrder":L"DriverOrder", Status);\r
5d73d92f 417 ShellStatus = SHELL_INVALID_PARAMETER;\r
418 } else {\r
419 Print (L"bcfg: Add %s as %x\n", OptionStr, Position);\r
420 }\r
421 }\r
422 }\r
5d73d92f 423\r
424//\r
425//If always Free FilePath, will free devicepath in system when use "addh"\r
426//\r
5d73d92f 427 if (FilePath!=NULL && !UseHandle) {\r
428 FreePool (FilePath);\r
429 }\r
430\r
431 if (Str != NULL) {\r
432 FreePool(Str);\r
433 }\r
434\r
435 if (Handles != NULL) {\r
436 FreePool (Handles);\r
437 }\r
438\r
439 if (FileList != NULL) {\r
440 ShellCloseFileMetaArg (&FileList);\r
441 }\r
442\r
443 return (ShellStatus);\r
444}\r
445\r
3737ac2b 446/**\r
447 Funciton to remove an item.\r
448\r
449 @param[in] Target The target item to move.\r
450 @param[in] CurrentOrder The pointer to the current order of items.\r
451 @param[in] OrderCount The number if items in CurrentOrder.\r
452 @param[in] Location The current location of the Target.\r
453\r
454 @retval SHELL_SUCCESS The operation was successful.\r
455 @retval SHELL_INVALID_PARAMETER A parameter was invalid.\r
456**/\r
5d73d92f 457SHELL_STATUS\r
458EFIAPI\r
3737ac2b 459BcfgRemoveDebug1(\r
5d73d92f 460 IN CONST BCFG_OPERATION_TARGET Target,\r
461 IN CONST UINT16 *CurrentOrder,\r
462 IN CONST UINTN OrderCount,\r
6878e7a7 463 IN CONST UINT16 Location\r
5d73d92f 464 )\r
465{\r
466 CHAR16 VariableName[12];\r
467 UINT16 *NewOrder;\r
468 EFI_STATUS Status;\r
5d73d92f 469 UINTN NewCount;\r
470\r
6878e7a7 471 UnicodeSPrint(VariableName, sizeof(VariableName), L"%s%04x", Target == BcfgTargetBootOrder?L"Boot":L"Driver", CurrentOrder[Location]);\r
5d73d92f 472 Status = gRT->SetVariable(\r
473 VariableName,\r
474 (EFI_GUID*)&gEfiGlobalVariableGuid,\r
475 EFI_VARIABLE_NON_VOLATILE|EFI_VARIABLE_BOOTSERVICE_ACCESS|EFI_VARIABLE_RUNTIME_ACCESS,\r
476 0,\r
477 NULL);\r
478 if (EFI_ERROR(Status)) {\r
479 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_WRITE_FAIL), gShellDebug1HiiHandle, VariableName, Status);\r
480 return (SHELL_INVALID_PARAMETER);\r
481 }\r
3737ac2b 482 NewOrder = AllocateZeroPool(OrderCount*sizeof(CurrentOrder[0]));\r
33c031ee 483 if (NewOrder != NULL) {\r
484 NewCount = OrderCount;\r
485 CopyMem(NewOrder, CurrentOrder, OrderCount*sizeof(CurrentOrder[0]));\r
6878e7a7 486 CopyMem(NewOrder+Location, NewOrder+Location+1, (OrderCount - Location - 1)*sizeof(CurrentOrder[0]));\r
487 NewCount--;\r
488\r
33c031ee 489 Status = gRT->SetVariable(\r
490 Target == BcfgTargetBootOrder?(CHAR16*)L"BootOrder":(CHAR16*)L"DriverOrder",\r
491 (EFI_GUID*)&gEfiGlobalVariableGuid,\r
492 EFI_VARIABLE_NON_VOLATILE|EFI_VARIABLE_BOOTSERVICE_ACCESS|EFI_VARIABLE_RUNTIME_ACCESS,\r
493 NewCount*sizeof(NewOrder[0]),\r
494 NewOrder);\r
495 FreePool(NewOrder);\r
496 } else {\r
497 Status = EFI_OUT_OF_RESOURCES;\r
5d73d92f 498 }\r
5d73d92f 499 if (EFI_ERROR(Status)) {\r
3737ac2b 500 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_WRITE_FAIL), gShellDebug1HiiHandle, Target == BcfgTargetBootOrder?(CHAR16*)L"BootOrder":(CHAR16*)L"DriverOrder", Status);\r
5d73d92f 501 return (SHELL_INVALID_PARAMETER);\r
502 }\r
503 return (SHELL_SUCCESS);\r
504}\r
505\r
3737ac2b 506/**\r
507 Funciton to move a item to another location.\r
508\r
509 @param[in] Target The target item to move.\r
510 @param[in] CurrentOrder The pointer to the current order of items.\r
511 @param[in] OrderCount The number if items in CurrentOrder.\r
512 @param[in] OldLocation The current location of the Target.\r
513 @param[in] NewLocation The desired location of the Target.\r
514\r
515 @retval SHELL_SUCCESS The operation was successful.\r
516 @retval SHELL_INVALID_PARAMETER A parameter was invalid.\r
517**/\r
5d73d92f 518SHELL_STATUS\r
519EFIAPI\r
3737ac2b 520BcfgMoveDebug1(\r
5d73d92f 521 IN CONST BCFG_OPERATION_TARGET Target,\r
522 IN CONST UINT16 *CurrentOrder,\r
523 IN CONST UINTN OrderCount,\r
524 IN CONST UINT16 OldLocation,\r
525 IN CONST UINT16 NewLocation\r
526 )\r
527{\r
528 UINT16 *NewOrder;\r
529 EFI_STATUS Status;\r
530 UINT16 Temp;\r
531\r
3737ac2b 532 NewOrder = AllocateZeroPool(OrderCount*sizeof(CurrentOrder[0]));\r
5d73d92f 533 ASSERT(NewOrder != NULL);\r
534\r
535 Temp = CurrentOrder[OldLocation];\r
536 CopyMem(NewOrder, CurrentOrder, OrderCount*sizeof(CurrentOrder[0]));\r
537 CopyMem(NewOrder+OldLocation, NewOrder+OldLocation+1, (OrderCount - OldLocation - 1)*sizeof(CurrentOrder[0]));\r
538 CopyMem(NewOrder+NewLocation+1, NewOrder+NewLocation, (OrderCount - NewLocation - 1)*sizeof(CurrentOrder[0]));\r
539 NewOrder[NewLocation] = Temp;\r
540\r
541\r
542 Status = gRT->SetVariable(\r
3737ac2b 543 Target == BcfgTargetBootOrder?(CHAR16*)L"BootOrder":(CHAR16*)L"DriverOrder",\r
5d73d92f 544 (EFI_GUID*)&gEfiGlobalVariableGuid,\r
545 EFI_VARIABLE_NON_VOLATILE|EFI_VARIABLE_BOOTSERVICE_ACCESS|EFI_VARIABLE_RUNTIME_ACCESS,\r
546 OrderCount*sizeof(CurrentOrder[0]),\r
547 NewOrder);\r
548\r
549 FreePool(NewOrder);\r
550\r
551 if (EFI_ERROR(Status)) {\r
3737ac2b 552 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_WRITE_FAIL), gShellDebug1HiiHandle, Target == BcfgTargetBootOrder?(CHAR16*)L"BootOrder":(CHAR16*)L"DriverOrder", Status);\r
5d73d92f 553 return (SHELL_INVALID_PARAMETER);\r
554 }\r
555 return (SHELL_SUCCESS);\r
556}\r
557\r
f2ad804f 558/**\r
559 Function to add optional data to an option.\r
560\r
561 @param[in] OptData The optional data to add.\r
562 @param[in] Target The target of the operation.\r
563\r
564 @retval SHELL_SUCCESS The operation was succesful.\r
565**/\r
5d73d92f 566SHELL_STATUS\r
567EFIAPI\r
3737ac2b 568BcfgAddOptDebug1(\r
569 IN CONST CHAR16 *OptData,\r
570 IN CONST BCFG_OPERATION_TARGET Target\r
571 )\r
572{\r
573 ASSERT(OptData != NULL);\r
574 return SHELL_SUCCESS;\r
575}\r
576\r
577/**\r
578 Function to dump the Bcfg information.\r
579\r
580 @param[in] Op The operation.\r
581 @param[in] OrderCount How many to dump.\r
582 @param[in] CurrentOrder The pointer to the current order of items.\r
583 @param[in] VerboseOutput TRUE for extra output. FALSE otherwise.\r
584\r
585 @retval SHELL_SUCCESS The dump was successful.\r
586 @retval SHELL_INVALID_PARAMETER A parameter was invalid.\r
587**/\r
588SHELL_STATUS\r
589EFIAPI\r
590BcfgDisplayDumpDebug1(\r
5d73d92f 591 IN CONST CHAR16 *Op,\r
3737ac2b 592 IN CONST UINTN OrderCount,\r
593 IN CONST UINT16 *CurrentOrder,\r
5d73d92f 594 IN CONST BOOLEAN VerboseOutput\r
595 )\r
596{\r
597 EFI_STATUS Status;\r
598 UINT8 *Buffer;\r
599 UINTN BufferSize;\r
600 CHAR16 VariableName[12];\r
601 UINTN LoopVar;\r
602 UINTN LoopVar2;\r
603 CHAR16 *DevPathString;\r
604 VOID *DevPath;\r
605\r
3737ac2b 606 if (OrderCount == 0) {\r
607 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN(STR_BCFG_NONE), gShellDebug1HiiHandle);\r
608 return (SHELL_SUCCESS);\r
609 }\r
610\r
5d73d92f 611 for (LoopVar = 0 ; LoopVar < OrderCount ; LoopVar++) {\r
612 Buffer = NULL;\r
613 BufferSize = 0;\r
3737ac2b 614 UnicodeSPrint(VariableName, sizeof(VariableName), L"%s%04x", Op, CurrentOrder[LoopVar]);\r
5d73d92f 615\r
616 Status = gRT->GetVariable(\r
617 VariableName,\r
618 (EFI_GUID*)&gEfiGlobalVariableGuid,\r
619 NULL,\r
620 &BufferSize,\r
621 Buffer);\r
622 if (Status == EFI_BUFFER_TOO_SMALL) {\r
3737ac2b 623 Buffer = AllocateZeroPool(BufferSize);\r
5d73d92f 624 Status = gRT->GetVariable(\r
625 VariableName,\r
626 (EFI_GUID*)&gEfiGlobalVariableGuid,\r
627 NULL,\r
628 &BufferSize,\r
629 Buffer);\r
630 }\r
631\r
632 if (EFI_ERROR(Status) || Buffer == NULL) {\r
633 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_READ_FAIL), gShellDebug1HiiHandle, VariableName, Status);\r
634 return (SHELL_INVALID_PARAMETER);\r
635 }\r
636\r
6878e7a7 637 if ((*(UINT16*)(Buffer+4)) != 0) {\r
638 DevPath = AllocateZeroPool(*(UINT16*)(Buffer+4));\r
639 CopyMem(DevPath, Buffer+6+StrSize((CHAR16*)(Buffer+6)), *(UINT16*)(Buffer+4));\r
640 DevPathString = gDevPathToText->ConvertDevicePathToText(DevPath, TRUE, FALSE);\r
641 } else {\r
642 DevPath = NULL;\r
643 DevPathString = NULL;\r
644 }\r
5d73d92f 645 ShellPrintHiiEx(\r
646 -1,\r
647 -1,\r
648 NULL,\r
649 STRING_TOKEN(STR_BCFG_LOAD_OPTIONS),\r
650 gShellDebug1HiiHandle,\r
3737ac2b 651 LoopVar,\r
5d73d92f 652 VariableName,\r
653 (CHAR16*)(Buffer+6),\r
654 DevPathString,\r
655 (StrSize((CHAR16*)(Buffer+6)) + *(UINT16*)(Buffer+4) + 6) <= BufferSize?L'N':L'Y');\r
656 if (VerboseOutput) {\r
657 for (LoopVar2 = (StrSize((CHAR16*)(Buffer+6)) + *(UINT16*)(Buffer+4) + 6);LoopVar2<BufferSize;LoopVar2++){\r
658 ShellPrintEx(\r
659 -1,\r
660 -1,\r
661 NULL,\r
662 L"%02x",\r
663 Buffer[LoopVar2]);\r
664 }\r
665 ShellPrintEx(\r
666 -1,\r
667 -1,\r
668 NULL,\r
669 L"\r\n");\r
670 }\r
671\r
672 if (Buffer != NULL) {\r
673 FreePool(Buffer);\r
674 }\r
675 if (DevPath != NULL) {\r
676 FreePool(DevPath);\r
677 }\r
678 if (DevPathString != NULL) {\r
679 FreePool(DevPathString);\r
680 }\r
681 }\r
682 return (SHELL_SUCCESS);\r
683}\r
684\r
3737ac2b 685/**\r
686 Function to initialize the BCFG operation structure.\r
687\r
688 @param[in] Struct The stuct to initialize.\r
689**/\r
5d73d92f 690VOID\r
691EFIAPI\r
3737ac2b 692InitBcfgStructDebug1(\r
5d73d92f 693 IN BGFG_OPERATION *Struct\r
694 )\r
695{\r
696 ASSERT(Struct != NULL);\r
3737ac2b 697 Struct->Target = BcfgTargetMax;\r
698 Struct->Type = BcfgTypeMax;\r
5d73d92f 699 Struct->Number1 = 0;\r
700 Struct->Number2 = 0;\r
701 Struct->HandleIndex = 0;\r
702 Struct->FileName = NULL;\r
703 Struct->Description = NULL;\r
704 Struct->Order = NULL;\r
705 Struct->OptData = NULL;\r
706}\r
707\r
708\r
709STATIC CONST SHELL_PARAM_ITEM ParamList[] = {\r
710 {L"-v", TypeFlag},\r
711 {L"-opt", TypeMaxValue},\r
712 {NULL, TypeMax}\r
713 };\r
714\r
715/**\r
716 Function for 'bcfg' command.\r
717\r
718 @param[in] ImageHandle Handle to the Image (NULL if Internal).\r
719 @param[in] SystemTable Pointer to the System Table (NULL if Internal).\r
720**/\r
721SHELL_STATUS\r
722EFIAPI\r
723ShellCommandRunBcfg (\r
724 IN EFI_HANDLE ImageHandle,\r
725 IN EFI_SYSTEM_TABLE *SystemTable\r
726 )\r
727{\r
728 EFI_STATUS Status;\r
729 LIST_ENTRY *Package;\r
730 CHAR16 *ProblemParam;\r
731 SHELL_STATUS ShellStatus;\r
732 UINTN ParamNumber;\r
733 CONST CHAR16 *CurrentParam;\r
734 BGFG_OPERATION CurrentOperation;\r
735 UINTN Length;\r
3737ac2b 736 UINT64 Intermediate;\r
5d73d92f 737\r
738 Length = 0;\r
739 ProblemParam = NULL;\r
740 Package = NULL;\r
741 ShellStatus = SHELL_SUCCESS;\r
742\r
3737ac2b 743 InitBcfgStructDebug1(&CurrentOperation);\r
5d73d92f 744\r
745 //\r
746 // initialize the shell lib (we must be in non-auto-init...)\r
747 //\r
748 Status = ShellInitialize();\r
749 ASSERT_EFI_ERROR(Status);\r
750\r
751 Status = CommandInit();\r
752 ASSERT_EFI_ERROR(Status);\r
753\r
754 //\r
755 // parse the command line\r
756 //\r
757 Status = ShellCommandLineParse (ParamList, &Package, &ProblemParam, TRUE);\r
758 if (EFI_ERROR(Status)) {\r
759 if (Status == EFI_VOLUME_CORRUPTED && ProblemParam != NULL) {\r
760 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, ProblemParam);\r
761 FreePool(ProblemParam);\r
762 ShellStatus = SHELL_INVALID_PARAMETER;\r
763 } else {\r
764 ASSERT(FALSE);\r
765 }\r
766 } else {\r
3737ac2b 767 //\r
768 // Read in if we are doing -OPT\r
769 //\r
770 if (ShellCommandLineGetFlag(Package, L"-opt")) {\r
771 CurrentOperation.OptData = ShellCommandLineGetValue(Package, L"-opt");\r
772 if (CurrentOperation.OptData == NULL) {\r
773 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM_VAL), gShellDebug1HiiHandle, L"-opt");\r
774 ShellStatus = SHELL_INVALID_PARAMETER;\r
775 }\r
776 CurrentOperation.Type = BcfgTypeOpt;\r
777 }\r
778\r
5d73d92f 779 //\r
780 // small block to read the target of the operation\r
781 //\r
3737ac2b 782 if ((ShellCommandLineGetCount(Package) < 3 && CurrentOperation.Type != BcfgTypeOpt) ||\r
783 (ShellCommandLineGetCount(Package) < 2 && CurrentOperation.Type == BcfgTypeOpt)\r
784 ){\r
5d73d92f 785 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_TOO_FEW), gShellDebug1HiiHandle);\r
786 ShellStatus = SHELL_INVALID_PARAMETER;\r
787 } else if (gUnicodeCollation->StriColl(gUnicodeCollation, (CHAR16*)ShellCommandLineGetRawValue(Package, 1), L"driver") == 0) {\r
3737ac2b 788 CurrentOperation.Target = BcfgTargetDriverOrder;\r
5d73d92f 789 } else if (gUnicodeCollation->StriColl(gUnicodeCollation, (CHAR16*)ShellCommandLineGetRawValue(Package, 1), L"boot") == 0) {\r
3737ac2b 790 CurrentOperation.Target = BcfgTargetBootOrder;\r
5d73d92f 791 } else {\r
792 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_NO_DRIVER_BOOT), gShellDebug1HiiHandle);\r
793 ShellStatus = SHELL_INVALID_PARAMETER;\r
794 }\r
795\r
5d73d92f 796\r
797 //\r
798 // Read in the boot or driver order environment variable (not needed for opt)\r
799 //\r
3737ac2b 800 if (ShellStatus == SHELL_SUCCESS && CurrentOperation.Target < BcfgTargetMax && CurrentOperation.Type != BcfgTypeOpt) {\r
5d73d92f 801 Length = 0;\r
802 Status = gRT->GetVariable(\r
3737ac2b 803 CurrentOperation.Target == BcfgTargetBootOrder?(CHAR16*)L"BootOrder":(CHAR16*)L"DriverOrder",\r
5d73d92f 804 (EFI_GUID*)&gEfiGlobalVariableGuid,\r
805 NULL,\r
806 &Length,\r
807 CurrentOperation.Order);\r
808 if (Status == EFI_BUFFER_TOO_SMALL) {\r
3737ac2b 809 CurrentOperation.Order = AllocateZeroPool(Length+(4*sizeof(CurrentOperation.Order[0])));\r
5d73d92f 810 Status = gRT->GetVariable(\r
3737ac2b 811 CurrentOperation.Target == BcfgTargetBootOrder?(CHAR16*)L"BootOrder":(CHAR16*)L"DriverOrder",\r
5d73d92f 812 (EFI_GUID*)&gEfiGlobalVariableGuid,\r
813 NULL,\r
814 &Length,\r
815 CurrentOperation.Order);\r
816 }\r
817 }\r
818\r
819 //\r
820 // large block to read the type of operation and verify parameter types for the info.\r
821 //\r
3737ac2b 822 if (ShellStatus == SHELL_SUCCESS && CurrentOperation.Target < BcfgTargetMax) {\r
5d73d92f 823 for (ParamNumber = 2 ; ParamNumber < ShellCommandLineGetCount(Package) && ShellStatus == SHELL_SUCCESS; ParamNumber++) {\r
824 CurrentParam = ShellCommandLineGetRawValue(Package, ParamNumber);\r
825 if (gUnicodeCollation->StriColl(gUnicodeCollation, (CHAR16*)CurrentParam, L"dump") == 0) {\r
3737ac2b 826 CurrentOperation.Type = BcfgTypeDump;\r
5d73d92f 827 } else if (ShellCommandLineGetFlag(Package, L"-v")) {\r
828 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, L"-v (without dump)");\r
829 ShellStatus = SHELL_INVALID_PARAMETER;\r
830 } else if (gUnicodeCollation->StriColl(gUnicodeCollation, (CHAR16*)CurrentParam, L"add") == 0) {\r
831 if ((ParamNumber + 3) >= ShellCommandLineGetCount(Package)) {\r
832 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_TOO_FEW), gShellDebug1HiiHandle);\r
833 ShellStatus = SHELL_INVALID_PARAMETER;\r
834 }\r
3737ac2b 835 CurrentOperation.Type = BcfgTypeAdd;\r
5d73d92f 836 CurrentParam = ShellCommandLineGetRawValue(Package, ++ParamNumber);\r
837 if (CurrentParam == NULL || !ShellIsHexOrDecimalNumber(CurrentParam, TRUE, FALSE)) {\r
838 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, CurrentParam);\r
839 ShellStatus = SHELL_INVALID_PARAMETER;\r
840 } else {\r
3737ac2b 841 Status = ShellConvertStringToUint64(CurrentParam, &Intermediate, TRUE, FALSE);\r
842 CurrentOperation.Number1 = (UINT16)Intermediate;\r
5d73d92f 843 ASSERT(CurrentOperation.FileName == NULL);\r
844 CurrentOperation.FileName = StrnCatGrow(&CurrentOperation.FileName , NULL, ShellCommandLineGetRawValue(Package, ++ParamNumber), 0);\r
845 ASSERT(CurrentOperation.Description == NULL);\r
846 CurrentOperation.Description = StrnCatGrow(&CurrentOperation.Description, NULL, ShellCommandLineGetRawValue(Package, ++ParamNumber), 0);\r
847 }\r
848 } else if (gUnicodeCollation->StriColl(gUnicodeCollation, (CHAR16*)CurrentParam, L"addp") == 0) {\r
849 if ((ParamNumber + 3) >= ShellCommandLineGetCount(Package)) {\r
850 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_TOO_FEW), gShellDebug1HiiHandle);\r
851 ShellStatus = SHELL_INVALID_PARAMETER;\r
852 }\r
3737ac2b 853 CurrentOperation.Type = BcfgTypeAddp;\r
5d73d92f 854 CurrentParam = ShellCommandLineGetRawValue(Package, ++ParamNumber);\r
855 if (CurrentParam == NULL || !ShellIsHexOrDecimalNumber(CurrentParam, TRUE, FALSE)) {\r
856 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, CurrentParam);\r
857 ShellStatus = SHELL_INVALID_PARAMETER;\r
858 } else {\r
3737ac2b 859 Status = ShellConvertStringToUint64(CurrentParam, &Intermediate, TRUE, FALSE);\r
860 CurrentOperation.Number1 = (UINT16)Intermediate;\r
5d73d92f 861 ASSERT(CurrentOperation.FileName == NULL);\r
862 CurrentOperation.FileName = StrnCatGrow(&CurrentOperation.FileName , NULL, ShellCommandLineGetRawValue(Package, ++ParamNumber), 0);\r
863 ASSERT(CurrentOperation.Description == NULL);\r
864 CurrentOperation.Description = StrnCatGrow(&CurrentOperation.Description, NULL, ShellCommandLineGetRawValue(Package, ++ParamNumber), 0);\r
865 }\r
866 } else if (gUnicodeCollation->StriColl(gUnicodeCollation, (CHAR16*)CurrentParam, L"addh") == 0) {\r
867 if ((ParamNumber + 3) >= ShellCommandLineGetCount(Package)) {\r
868 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_TOO_FEW), gShellDebug1HiiHandle);\r
869 ShellStatus = SHELL_INVALID_PARAMETER;\r
870 }\r
3737ac2b 871 CurrentOperation.Type = BcfgTypeAddh;\r
5d73d92f 872 CurrentParam = ShellCommandLineGetRawValue(Package, ++ParamNumber);\r
873 if (CurrentParam == NULL || !ShellIsHexOrDecimalNumber(CurrentParam, TRUE, FALSE)) {\r
874 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, CurrentParam);\r
875 ShellStatus = SHELL_INVALID_PARAMETER;\r
876 } else {\r
3737ac2b 877 Status = ShellConvertStringToUint64(CurrentParam, &Intermediate, TRUE, FALSE);\r
878 CurrentOperation.Number1 = (UINT16)Intermediate;\r
5d73d92f 879 CurrentParam = ShellCommandLineGetRawValue(Package, ++ParamNumber);\r
880 if (CurrentParam == NULL || !ShellIsHexOrDecimalNumber(CurrentParam, TRUE, FALSE)) {\r
881 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, CurrentParam);\r
882 ShellStatus = SHELL_INVALID_PARAMETER;\r
883 } else {\r
3737ac2b 884 Status = ShellConvertStringToUint64(CurrentParam, &Intermediate, TRUE, FALSE);\r
885 CurrentOperation.HandleIndex = (UINT16)Intermediate;\r
5d73d92f 886 ASSERT(CurrentOperation.Description == NULL);\r
887 CurrentOperation.Description = StrnCatGrow(&CurrentOperation.Description, NULL, ShellCommandLineGetRawValue(Package, ++ParamNumber), 0);\r
888 }\r
889 }\r
890 } else if (gUnicodeCollation->StriColl(gUnicodeCollation, (CHAR16*)CurrentParam, L"rm") == 0) {\r
891 if ((ParamNumber + 1) >= ShellCommandLineGetCount(Package)) {\r
892 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_TOO_FEW), gShellDebug1HiiHandle);\r
893 ShellStatus = SHELL_INVALID_PARAMETER;\r
894 }\r
3737ac2b 895 CurrentOperation.Type = BcfgTypeRm;\r
5d73d92f 896 CurrentParam = ShellCommandLineGetRawValue(Package, ++ParamNumber);\r
897 if (CurrentParam == NULL || !ShellIsHexOrDecimalNumber(CurrentParam, TRUE, FALSE)) {\r
898 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, CurrentParam);\r
899 ShellStatus = SHELL_INVALID_PARAMETER;\r
900 } else {\r
3737ac2b 901 Status = ShellConvertStringToUint64(CurrentParam, &Intermediate, TRUE, FALSE);\r
902 CurrentOperation.Number1 = (UINT16)Intermediate;\r
5d73d92f 903 if (CurrentOperation.Number1 > (Length / sizeof(CurrentOperation.Order[0]))){\r
904 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_NUMB_RANGE), gShellDebug1HiiHandle, Length / sizeof(CurrentOperation.Order[0]));\r
905 ShellStatus = SHELL_INVALID_PARAMETER;\r
906 }\r
907 }\r
908 } else if (gUnicodeCollation->StriColl(gUnicodeCollation, (CHAR16*)CurrentParam, L"mv") == 0) {\r
909 if ((ParamNumber + 2) >= ShellCommandLineGetCount(Package)) {\r
910 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_TOO_FEW), gShellDebug1HiiHandle);\r
911 ShellStatus = SHELL_INVALID_PARAMETER;\r
912 }\r
3737ac2b 913 CurrentOperation.Type = BcfgTypeMv;\r
5d73d92f 914 CurrentParam = ShellCommandLineGetRawValue(Package, ++ParamNumber);\r
915 if (CurrentParam == NULL || !ShellIsHexOrDecimalNumber(CurrentParam, TRUE, FALSE)) {\r
916 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, CurrentParam);\r
917 ShellStatus = SHELL_INVALID_PARAMETER;\r
918 } else {\r
3737ac2b 919 Status = ShellConvertStringToUint64(CurrentParam, &Intermediate, TRUE, FALSE);\r
920 CurrentOperation.Number1 = (UINT16)Intermediate;\r
5d73d92f 921 if (CurrentOperation.Number1 > (Length / sizeof(CurrentOperation.Order[0]))){\r
922 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_NUMB_RANGE), gShellDebug1HiiHandle, Length / sizeof(CurrentOperation.Order[0]));\r
923 ShellStatus = SHELL_INVALID_PARAMETER;\r
924 }\r
925 CurrentParam = ShellCommandLineGetRawValue(Package, ++ParamNumber);\r
926 if (CurrentParam == NULL || !ShellIsHexOrDecimalNumber(CurrentParam, TRUE, FALSE)) {\r
927 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, CurrentParam);\r
928 ShellStatus = SHELL_INVALID_PARAMETER;\r
929 } else {\r
3737ac2b 930 Status = ShellConvertStringToUint64(CurrentParam, &Intermediate, TRUE, FALSE);\r
931 CurrentOperation.Number2 = (UINT16)Intermediate;\r
5d73d92f 932 }\r
933 if (CurrentOperation.Number2 == CurrentOperation.Number1\r
934 ||CurrentOperation.Number1 > (Length / sizeof(CurrentOperation.Order[0]))\r
935 ||CurrentOperation.Number2 > (Length / sizeof(CurrentOperation.Order[0]))\r
936 ){\r
937 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_BCFG_NUMB_RANGE), gShellDebug1HiiHandle, Length / sizeof(CurrentOperation.Order[0]));\r
938 ShellStatus = SHELL_INVALID_PARAMETER;\r
939 }\r
940 }\r
941 } else {\r
942 ShellPrintHiiEx(-1, -1, NULL, STRING_TOKEN (STR_GEN_PROBLEM), gShellDebug1HiiHandle, CurrentParam);\r
943 ShellStatus = SHELL_INVALID_PARAMETER;\r
944 }\r
945 }\r
946 }\r
3737ac2b 947 if (ShellStatus == SHELL_SUCCESS && CurrentOperation.Target < BcfgTargetMax && CurrentOperation.Type < BcfgTypeMax) {\r
5d73d92f 948 //\r
949 // we have all the info. Do the work\r
950 //\r
951 switch (CurrentOperation.Type) {\r
3737ac2b 952 case BcfgTypeDump:\r
953 ShellStatus = BcfgDisplayDumpDebug1(\r
954 CurrentOperation.Target == BcfgTargetBootOrder?L"Boot":L"Driver",\r
5d73d92f 955 Length / sizeof(CurrentOperation.Order[0]),\r
3737ac2b 956 CurrentOperation.Order,\r
5d73d92f 957 ShellCommandLineGetFlag(Package, L"-v"));\r
958 break;\r
3737ac2b 959 case BcfgTypeMv:\r
960 ShellStatus = BcfgMoveDebug1(\r
5d73d92f 961 CurrentOperation.Target,\r
962 CurrentOperation.Order,\r
963 Length / sizeof(CurrentOperation.Order[0]),\r
964 CurrentOperation.Number1,\r
965 CurrentOperation.Number2);\r
966 break;\r
3737ac2b 967 case BcfgTypeRm:\r
968 ShellStatus = BcfgRemoveDebug1(\r
5d73d92f 969 CurrentOperation.Target,\r
970 CurrentOperation.Order,\r
971 Length / sizeof(CurrentOperation.Order[0]),\r
972 CurrentOperation.Number1);\r
973 break;\r
3737ac2b 974 case BcfgTypeAdd:\r
975 case BcfgTypeAddp:\r
976 case BcfgTypeAddh:\r
977 ShellStatus = BcfgAddDebug1(\r
5d73d92f 978 CurrentOperation.Number1,\r
979 CurrentOperation.FileName,\r
980 CurrentOperation.Description,\r
981 CurrentOperation.Order,\r
3737ac2b 982 Length / sizeof(CurrentOperation.Order[0]),\r
5d73d92f 983 CurrentOperation.Target,\r
3737ac2b 984 (BOOLEAN)(CurrentOperation.Type == BcfgTypeAddh),\r
985 (BOOLEAN)(CurrentOperation.Type == BcfgTypeAddp),\r
5d73d92f 986 CurrentOperation.HandleIndex);\r
987 break;\r
3737ac2b 988 case BcfgTypeOpt:\r
989 ShellStatus = BcfgAddOptDebug1(\r
990 CurrentOperation.OptData,\r
991 CurrentOperation.Target);\r
992 break;\r
5d73d92f 993 default:\r
994 ASSERT(FALSE);\r
995 }\r
996 }\r
997 }\r
998\r
999 if (Package != NULL) {\r
1000 ShellCommandLineFreeVarList (Package);\r
1001 }\r
1002 if (CurrentOperation.FileName != NULL) {\r
1003 FreePool(CurrentOperation.FileName);\r
1004 }\r
1005 if (CurrentOperation.Description != NULL) {\r
1006 FreePool(CurrentOperation.Description);\r
1007 }\r
1008 if (CurrentOperation.Order != NULL) {\r
1009 FreePool(CurrentOperation.Order);\r
1010 }\r
1011\r
1012 return (ShellStatus);\r
1013}\r