2 Member functions of EFI_SHELL_PARAMETERS_PROTOCOL and functions for creation,
3 manipulation, and initialization of EFI_SHELL_PARAMETERS_PROTOCOL.
5 Copyright (c) 2013 Hewlett-Packard Development Company, L.P.
6 Copyright (c) 2009 - 2014, Intel Corporation. All rights reserved.<BR>
7 This program and the accompanying materials
8 are licensed and made available under the terms and conditions of the BSD License
9 which accompanies this distribution. The full text of the license may be found at
10 http://opensource.org/licenses/bsd-license.php
12 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
13 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
20 return the next parameter from a command line string;
22 This function moves the next parameter from Walker into TempParameter and moves
23 Walker up past that parameter for recursive calling. When the final parameter
24 is moved *Walker will be set to NULL;
26 Temp Parameter must be large enough to hold the parameter before calling this
29 @param[in, out] Walker pointer to string of command line. Adjusted to
30 reminaing command line on return
31 @param[in, out] TempParameter pointer to string of command line item extracted.
38 CHAR16
**TempParameter
44 ASSERT(Walker
!= NULL
);
45 ASSERT(*Walker
!= NULL
);
46 ASSERT(TempParameter
!= NULL
);
47 ASSERT(*TempParameter
!= NULL
);
50 // make sure we dont have any leading spaces
52 while ((*Walker
)[0] == L
' ') {
57 // make sure we still have some params now...
59 if (StrLen(*Walker
) == 0) {
60 ASSERT((*Walker
)[0] == CHAR_NULL
);
66 // we have a quoted parameter
67 // could be the last parameter, but SHOULD have a trailing quote
69 if ((*Walker
)[0] == L
'\"') {
71 for (TempLoc
= *Walker
+ 1 ; TempLoc
!= NULL
&& *TempLoc
!= CHAR_NULL
; TempLoc
++) {
72 if (*TempLoc
== L
'^' && *(TempLoc
+1) == L
'\"') {
74 } else if (*TempLoc
== L
'\"') {
80 if (NextDelim
- ((*Walker
)+1) == 0) {
84 StrCpy(*TempParameter
, L
"");
85 *Walker
= NextDelim
+ 1;
86 } else if (NextDelim
!= NULL
) {
87 StrnCpy(*TempParameter
, (*Walker
)+1, NextDelim
- ((*Walker
)+1));
88 *Walker
= NextDelim
+ 1;
91 // last one... someone forgot the training quote!
93 StrCpy(*TempParameter
, *Walker
);
96 for (TempLoc
= *TempParameter
; TempLoc
!= NULL
&& *TempLoc
!= CHAR_NULL
; TempLoc
++) {
97 if (*TempLoc
== L
'^' && *(TempLoc
+1) == L
'\"') {
98 CopyMem(TempLoc
, TempLoc
+1, StrSize(TempLoc
) - sizeof(TempLoc
[0]));
103 // we have a regular parameter (no quote) OR
104 // we have the final parameter (no trailing space)
106 NextDelim
= StrStr((*Walker
), L
" ");
107 if (NextDelim
!= NULL
) {
108 StrnCpy(*TempParameter
, *Walker
, NextDelim
- (*Walker
));
109 (*TempParameter
)[NextDelim
- (*Walker
)] = CHAR_NULL
;
110 *Walker
= NextDelim
+1;
115 StrCpy(*TempParameter
, *Walker
);
118 for (NextDelim
= *TempParameter
; NextDelim
!= NULL
&& *NextDelim
!= CHAR_NULL
; NextDelim
++) {
119 if (*NextDelim
== L
'^' && *(NextDelim
+1) == L
'^') {
120 CopyMem(NextDelim
, NextDelim
+1, StrSize(NextDelim
) - sizeof(NextDelim
[0]));
123 while ((*TempParameter
)[StrLen(*TempParameter
)-1] == L
' ') {
124 (*TempParameter
)[StrLen(*TempParameter
)-1] = CHAR_NULL
;
126 while ((*TempParameter
)[0] == L
' ') {
127 CopyMem(*TempParameter
, (*TempParameter
)+1, StrSize(*TempParameter
) - sizeof((*TempParameter
)[0]));
134 Function to populate Argc and Argv.
136 This function parses the CommandLine and divides it into standard C style Argc/Argv
137 parameters for inclusion in EFI_SHELL_PARAMETERS_PROTOCOL. this supports space
138 delimited and quote surrounded parameter definition.
140 @param[in] CommandLine String of command line to parse
141 @param[in, out] Argv pointer to array of strings; one for each parameter
142 @param[in, out] Argc pointer to number of strings in Argv array
144 @return EFI_SUCCESS the operation was sucessful
145 @return EFI_OUT_OF_RESOURCES a memory allocation failed.
149 ParseCommandLineToArgs(
150 IN CONST CHAR16
*CommandLine
,
151 IN OUT CHAR16
***Argv
,
156 CHAR16
*TempParameter
;
161 ASSERT(Argc
!= NULL
);
162 ASSERT(Argv
!= NULL
);
164 if (CommandLine
== NULL
|| StrLen(CommandLine
)==0) {
167 return (EFI_SUCCESS
);
170 Size
= StrSize(CommandLine
);
171 TempParameter
= AllocateZeroPool(Size
);
172 if (TempParameter
== NULL
) {
173 return (EFI_OUT_OF_RESOURCES
);
177 , Walker
= (CHAR16
*)CommandLine
178 ; Walker
!= NULL
&& *Walker
!= CHAR_NULL
179 ; GetNextParameter(&Walker
, &TempParameter
)
184 Walker = (CHAR16*)CommandLine;
185 while(Walker != NULL) {
186 GetNextParameter(&Walker, &TempParameter);
191 // lets allocate the pointer array
193 (*Argv
) = AllocateZeroPool((Count
)*sizeof(CHAR16
*));
195 SHELL_FREE_NON_NULL(TempParameter
);
196 return (EFI_OUT_OF_RESOURCES
);
200 Walker
= (CHAR16
*)CommandLine
;
201 while(Walker
!= NULL
&& *Walker
!= CHAR_NULL
) {
202 SetMem16(TempParameter
, Size
, CHAR_NULL
);
203 GetNextParameter(&Walker
, &TempParameter
);
204 NewParam
= AllocateZeroPool(StrSize(TempParameter
));
205 ASSERT(NewParam
!= NULL
);
206 StrCpy(NewParam
, TempParameter
);
207 ((CHAR16
**)(*Argv
))[(*Argc
)] = NewParam
;
210 ASSERT(Count
>= (*Argc
));
211 SHELL_FREE_NON_NULL(TempParameter
);
212 return (EFI_SUCCESS
);
216 creates a new EFI_SHELL_PARAMETERS_PROTOCOL instance and populates it and then
217 installs it on our handle and if there is an existing version of the protocol
218 that one is cached for removal later.
220 @param[in, out] NewShellParameters on a successful return, a pointer to pointer
221 to the newly installed interface.
222 @param[in, out] RootShellInstance on a successful return, pointer to boolean.
223 TRUE if this is the root shell instance.
225 @retval EFI_SUCCESS the operation completed successfully.
226 @return other the operation failed.
227 @sa ReinstallProtocolInterface
228 @sa InstallProtocolInterface
229 @sa ParseCommandLineToArgs
233 CreatePopulateInstallShellParametersProtocol (
234 IN OUT EFI_SHELL_PARAMETERS_PROTOCOL
**NewShellParameters
,
235 IN OUT BOOLEAN
*RootShellInstance
239 EFI_LOADED_IMAGE_PROTOCOL
*LoadedImage
;
240 CHAR16
*FullCommandLine
;
244 FullCommandLine
= NULL
;
248 // Assert for valid parameters
250 ASSERT(NewShellParameters
!= NULL
);
251 ASSERT(RootShellInstance
!= NULL
);
254 // See if we have a shell parameters placed on us
256 Status
= gBS
->OpenProtocol (
258 &gEfiShellParametersProtocolGuid
,
259 (VOID
**) &ShellInfoObject
.OldShellParameters
,
262 EFI_OPEN_PROTOCOL_GET_PROTOCOL
265 // if we don't then we must be the root shell (error is expected)
267 if (EFI_ERROR (Status
)) {
268 *RootShellInstance
= TRUE
;
272 // Allocate the new structure
274 *NewShellParameters
= AllocateZeroPool(sizeof(EFI_SHELL_PARAMETERS_PROTOCOL
));
275 if ((*NewShellParameters
) == NULL
) {
276 return (EFI_OUT_OF_RESOURCES
);
280 // get loaded image protocol
282 Status
= gBS
->OpenProtocol (
284 &gEfiLoadedImageProtocolGuid
,
285 (VOID
**) &LoadedImage
,
288 EFI_OPEN_PROTOCOL_GET_PROTOCOL
290 ASSERT_EFI_ERROR(Status
);
292 // Build the full command line
294 Status
= SHELL_GET_ENVIRONMENT_VARIABLE(L
"ShellOpt", &Size
, FullCommandLine
);
295 if (Status
== EFI_BUFFER_TOO_SMALL
) {
296 FullCommandLine
= AllocateZeroPool(Size
+ LoadedImage
->LoadOptionsSize
);
297 Status
= SHELL_GET_ENVIRONMENT_VARIABLE(L
"ShellOpt", &Size
, FullCommandLine
);
299 if (Status
== EFI_NOT_FOUND
) {
301 // no parameters via environment... ok
304 if (EFI_ERROR(Status
)) {
308 if (Size
== 0 && LoadedImage
->LoadOptionsSize
!= 0) {
309 ASSERT(FullCommandLine
== NULL
);
311 // Now we need to include a NULL terminator in the size.
313 Size
= LoadedImage
->LoadOptionsSize
+ sizeof(FullCommandLine
[0]);
314 FullCommandLine
= AllocateZeroPool(Size
);
316 if (FullCommandLine
!= NULL
) {
317 CopyMem (FullCommandLine
, LoadedImage
->LoadOptions
, LoadedImage
->LoadOptionsSize
);
319 // Populate Argc and Argv
321 Status
= ParseCommandLineToArgs(FullCommandLine
,
322 &(*NewShellParameters
)->Argv
,
323 &(*NewShellParameters
)->Argc
);
325 FreePool(FullCommandLine
);
327 ASSERT_EFI_ERROR(Status
);
329 (*NewShellParameters
)->Argv
= NULL
;
330 (*NewShellParameters
)->Argc
= 0;
334 // Populate the 3 faked file systems...
336 if (*RootShellInstance
) {
337 (*NewShellParameters
)->StdIn
= &FileInterfaceStdIn
;
338 (*NewShellParameters
)->StdOut
= &FileInterfaceStdOut
;
339 (*NewShellParameters
)->StdErr
= &FileInterfaceStdErr
;
340 Status
= gBS
->InstallProtocolInterface(&gImageHandle
,
341 &gEfiShellParametersProtocolGuid
,
342 EFI_NATIVE_INTERFACE
,
343 (VOID
*)(*NewShellParameters
));
346 // copy from the existing ones
348 (*NewShellParameters
)->StdIn
= ShellInfoObject
.OldShellParameters
->StdIn
;
349 (*NewShellParameters
)->StdOut
= ShellInfoObject
.OldShellParameters
->StdOut
;
350 (*NewShellParameters
)->StdErr
= ShellInfoObject
.OldShellParameters
->StdErr
;
351 Status
= gBS
->ReinstallProtocolInterface(gImageHandle
,
352 &gEfiShellParametersProtocolGuid
,
353 (VOID
*)ShellInfoObject
.OldShellParameters
,
354 (VOID
*)(*NewShellParameters
));
361 frees all memory used by createion and installation of shell parameters protocol
362 and if there was an old version installed it will restore that one.
364 @param NewShellParameters the interface of EFI_SHELL_PARAMETERS_PROTOCOL that is
367 @retval EFI_SUCCESS the cleanup was successful
368 @return other the cleanup failed
369 @sa ReinstallProtocolInterface
370 @sa UninstallProtocolInterface
374 CleanUpShellParametersProtocol (
375 IN OUT EFI_SHELL_PARAMETERS_PROTOCOL
*NewShellParameters
382 // If the old exists we need to restore it
384 if (ShellInfoObject
.OldShellParameters
!= NULL
) {
385 Status
= gBS
->ReinstallProtocolInterface(gImageHandle
,
386 &gEfiShellParametersProtocolGuid
,
387 (VOID
*)NewShellParameters
,
388 (VOID
*)ShellInfoObject
.OldShellParameters
);
389 DEBUG_CODE(ShellInfoObject
.OldShellParameters
= NULL
;);
392 // No old one, just uninstall us...
394 Status
= gBS
->UninstallProtocolInterface(gImageHandle
,
395 &gEfiShellParametersProtocolGuid
,
396 (VOID
*)NewShellParameters
);
398 if (NewShellParameters
->Argv
!= NULL
) {
399 for ( LoopCounter
= 0
400 ; LoopCounter
< NewShellParameters
->Argc
403 FreePool(NewShellParameters
->Argv
[LoopCounter
]);
405 FreePool(NewShellParameters
->Argv
);
407 FreePool(NewShellParameters
);
412 Determin if a file name represents a unicode file.
414 @param[in] FileName Pointer to the filename to open.
416 @retval EFI_SUCCESS The file is a unicode file.
417 @return An error upon failure.
422 IN CONST CHAR16
*FileName
425 SHELL_FILE_HANDLE Handle
;
427 UINT64 OriginalFilePosition
;
431 Status
= gEfiShellProtocol
->OpenFileByName(FileName
, &Handle
, EFI_FILE_MODE_READ
);
432 if (EFI_ERROR(Status
)) {
435 gEfiShellProtocol
->GetFilePosition(Handle
, &OriginalFilePosition
);
436 gEfiShellProtocol
->SetFilePosition(Handle
, 0);
437 CharSize
= sizeof(CHAR16
);
438 Status
= gEfiShellProtocol
->ReadFile(Handle
, &CharSize
, &CharBuffer
);
439 if (EFI_ERROR(Status
) || CharBuffer
!= gUnicodeFileTag
) {
440 Status
= EFI_BUFFER_TOO_SMALL
;
442 gEfiShellProtocol
->SetFilePosition(Handle
, OriginalFilePosition
);
443 gEfiShellProtocol
->CloseFile(Handle
);
448 Strips out quotes sections of a string.
450 All of the characters between quotes is replaced with spaces.
452 @param[in, out] TheString A pointer to the string to update.
457 IN OUT CHAR16
*TheString
462 for (RemoveNow
= FALSE
; TheString
!= NULL
&& *TheString
!= CHAR_NULL
; TheString
++) {
463 if (*TheString
== L
'^' && *(TheString
+ 1) == L
'\"') {
465 } else if (*TheString
== L
'\"') {
466 RemoveNow
= (BOOLEAN
)!RemoveNow
;
467 } else if (RemoveNow
) {
474 Calcualte the 32-bit CRC in a EFI table using the service provided by the
477 @param Hdr Pointer to an EFI standard header
482 IN OUT EFI_TABLE_HEADER
*Hdr
490 // If gBS->CalculateCrce32 () == CoreEfiNotAvailableYet () then
491 // Crc will come back as zero if we set it to zero here
494 gBS
->CalculateCrc32 ((UINT8
*)Hdr
, Hdr
->HeaderSize
, &Crc
);
499 Fix a string to only have the file name, removing starting at the first space of whatever is quoted.
501 @param[in] FileName The filename to start with.
503 @retval NULL FileName was invalid.
504 @return The modified FileName.
513 CHAR16
*TempLocation
;
515 if (FileName
== NULL
) {
519 if (FileName
[0] == L
'\"') {
521 if ((TempLocation
= StrStr(Copy
, L
"\"")) != NULL
) {
522 TempLocation
[0] = CHAR_NULL
;
526 while(Copy
[0] == L
' ') {
529 if ((TempLocation
= StrStr(Copy
, L
" ")) != NULL
) {
530 TempLocation
[0] = CHAR_NULL
;
534 if (Copy
[0] == CHAR_NULL
) {
542 Fix a string to only have the environment variable name, removing starting at the first space of whatever is quoted and removing the leading and trailing %.
544 @param[in] FileName The filename to start with.
546 @retval NULL FileName was invalid.
547 @return The modified FileName.
556 CHAR16
*TempLocation
;
560 if (FileName
[0] == L
'%') {
562 if ((TempLocation
= StrStr(Copy
, L
"%")) != NULL
) {
563 TempLocation
[0] = CHAR_NULL
;
567 return (FixFileName(Copy
));
571 Remove the unicode file tag from the begining of the file buffer since that will not be
577 IN SHELL_FILE_HANDLE
*Handle
583 CharSize
= sizeof(CHAR16
);
585 gEfiShellProtocol
->ReadFile(*Handle
, &CharSize
, &CharBuffer
);
586 if (CharBuffer
!= gUnicodeFileTag
) {
587 gEfiShellProtocol
->SetFilePosition(*Handle
, 0);
589 return (EFI_SUCCESS
);
593 Funcion will replace the current StdIn and StdOut in the ShellParameters protocol
594 structure by parsing NewCommandLine. The current values are returned to the
597 This will also update the system table.
599 @param[in, out] ShellParameters Pointer to parameter structure to modify.
600 @param[in] NewCommandLine The new command line to parse and use.
601 @param[out] OldStdIn Pointer to old StdIn.
602 @param[out] OldStdOut Pointer to old StdOut.
603 @param[out] OldStdErr Pointer to old StdErr.
604 @param[out] SystemTableInfo Pointer to old system table information.
606 @retval EFI_SUCCESS Operation was sucessful, Argv and Argc are valid.
607 @retval EFI_OUT_OF_RESOURCES A memory allocation failed.
611 UpdateStdInStdOutStdErr(
612 IN OUT EFI_SHELL_PARAMETERS_PROTOCOL
*ShellParameters
,
613 IN CHAR16
*NewCommandLine
,
614 OUT SHELL_FILE_HANDLE
*OldStdIn
,
615 OUT SHELL_FILE_HANDLE
*OldStdOut
,
616 OUT SHELL_FILE_HANDLE
*OldStdErr
,
617 OUT SYSTEM_TABLE_INFO
*SystemTableInfo
620 CHAR16
*CommandLineCopy
;
621 CHAR16
*CommandLineWalker
;
622 CHAR16
*StdErrFileName
;
623 CHAR16
*StdOutFileName
;
624 CHAR16
*StdInFileName
;
625 CHAR16
*StdInVarName
;
626 CHAR16
*StdOutVarName
;
627 CHAR16
*StdErrVarName
;
629 SHELL_FILE_HANDLE TempHandle
;
639 CHAR16
*FirstLocation
;
645 StdOutVarName
= NULL
;
646 StdErrVarName
= NULL
;
647 StdErrFileName
= NULL
;
648 StdInFileName
= NULL
;
649 StdOutFileName
= NULL
;
652 CommandLineCopy
= NULL
;
653 FirstLocation
= NULL
;
655 if (ShellParameters
== NULL
|| SystemTableInfo
== NULL
|| OldStdIn
== NULL
|| OldStdOut
== NULL
|| OldStdErr
== NULL
) {
656 return (EFI_INVALID_PARAMETER
);
659 SystemTableInfo
->ConIn
= gST
->ConIn
;
660 SystemTableInfo
->ConInHandle
= gST
->ConsoleInHandle
;
661 SystemTableInfo
->ConOut
= gST
->ConOut
;
662 SystemTableInfo
->ConOutHandle
= gST
->ConsoleOutHandle
;
663 SystemTableInfo
->ErrOut
= gST
->StdErr
;
664 SystemTableInfo
->ErrOutHandle
= gST
->StandardErrorHandle
;
665 *OldStdIn
= ShellParameters
->StdIn
;
666 *OldStdOut
= ShellParameters
->StdOut
;
667 *OldStdErr
= ShellParameters
->StdErr
;
669 if (NewCommandLine
== NULL
) {
670 return (EFI_SUCCESS
);
673 CommandLineCopy
= StrnCatGrow(&CommandLineCopy
, NULL
, NewCommandLine
, 0);
674 if (CommandLineCopy
== NULL
) {
675 return (EFI_OUT_OF_RESOURCES
);
677 Status
= EFI_SUCCESS
;
679 FirstLocation
= CommandLineCopy
+ StrLen(CommandLineCopy
);
681 StripQuotes(CommandLineCopy
);
683 if (!IsListEmpty(&ShellInfoObject
.SplitList
.Link
)) {
684 Split
= (SPLIT_LIST
*)GetFirstNode(&ShellInfoObject
.SplitList
.Link
);
685 if (Split
!= NULL
&& Split
->SplitStdIn
!= NULL
) {
686 ShellParameters
->StdIn
= Split
->SplitStdIn
;
688 if (Split
!= NULL
&& Split
->SplitStdOut
!= NULL
) {
689 ShellParameters
->StdOut
= Split
->SplitStdOut
;
693 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" 2>>v ")) != NULL
) {
694 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
695 SetMem16(CommandLineWalker
, 12, L
' ');
696 StdErrVarName
= CommandLineWalker
+= 6;
698 if (StrStr(CommandLineWalker
, L
" 2>>v ") != NULL
) {
699 Status
= EFI_NOT_FOUND
;
702 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" 1>>v ")) != NULL
) {
703 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
704 SetMem16(CommandLineWalker
, 12, L
' ');
705 StdOutVarName
= CommandLineWalker
+= 6;
707 if (StrStr(CommandLineWalker
, L
" 1>>v ") != NULL
) {
708 Status
= EFI_NOT_FOUND
;
710 } else if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" >>v ")) != NULL
) {
711 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
712 SetMem16(CommandLineWalker
, 10, L
' ');
713 StdOutVarName
= CommandLineWalker
+= 5;
715 if (StrStr(CommandLineWalker
, L
" >>v ") != NULL
) {
716 Status
= EFI_NOT_FOUND
;
718 } else if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" >v ")) != NULL
) {
719 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
720 SetMem16(CommandLineWalker
, 8, L
' ');
721 StdOutVarName
= CommandLineWalker
+= 4;
723 if (StrStr(CommandLineWalker
, L
" >v ") != NULL
) {
724 Status
= EFI_NOT_FOUND
;
727 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" 1>>a ")) != NULL
) {
728 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
729 SetMem16(CommandLineWalker
, 12, L
' ');
730 StdOutFileName
= CommandLineWalker
+= 6;
733 if (StrStr(CommandLineWalker
, L
" 1>>a ") != NULL
) {
734 Status
= EFI_NOT_FOUND
;
737 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" 1>> ")) != NULL
) {
738 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
739 SetMem16(CommandLineWalker
, 10, L
' ');
740 if (StdOutFileName
!= NULL
) {
741 Status
= EFI_INVALID_PARAMETER
;
743 StdOutFileName
= CommandLineWalker
+= 5;
746 if (StrStr(CommandLineWalker
, L
" 1>> ") != NULL
) {
747 Status
= EFI_NOT_FOUND
;
750 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" >> ")) != NULL
) {
751 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
752 SetMem16(CommandLineWalker
, 8, L
' ');
753 if (StdOutFileName
!= NULL
) {
754 Status
= EFI_INVALID_PARAMETER
;
756 StdOutFileName
= CommandLineWalker
+= 4;
759 if (StrStr(CommandLineWalker
, L
" >> ") != NULL
) {
760 Status
= EFI_NOT_FOUND
;
763 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" >>a ")) != NULL
) {
764 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
765 SetMem16(CommandLineWalker
, 10, L
' ');
766 if (StdOutFileName
!= NULL
) {
767 Status
= EFI_INVALID_PARAMETER
;
769 StdOutFileName
= CommandLineWalker
+= 5;
773 if (StrStr(CommandLineWalker
, L
" >>a ") != NULL
) {
774 Status
= EFI_NOT_FOUND
;
777 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" 1>a ")) != NULL
) {
778 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
779 SetMem16(CommandLineWalker
, 10, L
' ');
780 if (StdOutFileName
!= NULL
) {
781 Status
= EFI_INVALID_PARAMETER
;
783 StdOutFileName
= CommandLineWalker
+= 5;
787 if (StrStr(CommandLineWalker
, L
" 1>a ") != NULL
) {
788 Status
= EFI_NOT_FOUND
;
791 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" >a ")) != NULL
) {
792 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
793 SetMem16(CommandLineWalker
, 8, L
' ');
794 if (StdOutFileName
!= NULL
) {
795 Status
= EFI_INVALID_PARAMETER
;
797 StdOutFileName
= CommandLineWalker
+= 4;
801 if (StrStr(CommandLineWalker
, L
" >a ") != NULL
) {
802 Status
= EFI_NOT_FOUND
;
805 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" 2>> ")) != NULL
) {
806 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
807 SetMem16(CommandLineWalker
, 10, L
' ');
808 if (StdErrFileName
!= NULL
) {
809 Status
= EFI_INVALID_PARAMETER
;
811 StdErrFileName
= CommandLineWalker
+= 5;
814 if (StrStr(CommandLineWalker
, L
" 2>> ") != NULL
) {
815 Status
= EFI_NOT_FOUND
;
819 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" 2>v ")) != NULL
) {
820 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
821 SetMem16(CommandLineWalker
, 10, L
' ');
822 if (StdErrVarName
!= NULL
) {
823 Status
= EFI_INVALID_PARAMETER
;
825 StdErrVarName
= CommandLineWalker
+= 5;
828 if (StrStr(CommandLineWalker
, L
" 2>v ") != NULL
) {
829 Status
= EFI_NOT_FOUND
;
832 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" 1>v ")) != NULL
) {
833 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
834 SetMem16(CommandLineWalker
, 10, L
' ');
835 if (StdOutVarName
!= NULL
) {
836 Status
= EFI_INVALID_PARAMETER
;
838 StdOutVarName
= CommandLineWalker
+= 5;
841 if (StrStr(CommandLineWalker
, L
" 1>v ") != NULL
) {
842 Status
= EFI_NOT_FOUND
;
845 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" 2>a ")) != NULL
) {
846 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
847 SetMem16(CommandLineWalker
, 10, L
' ');
848 if (StdErrFileName
!= NULL
) {
849 Status
= EFI_INVALID_PARAMETER
;
851 StdErrFileName
= CommandLineWalker
+= 5;
855 if (StrStr(CommandLineWalker
, L
" 2>a ") != NULL
) {
856 Status
= EFI_NOT_FOUND
;
859 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" 2> ")) != NULL
) {
860 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
861 SetMem16(CommandLineWalker
, 8, L
' ');
862 if (StdErrFileName
!= NULL
) {
863 Status
= EFI_INVALID_PARAMETER
;
865 StdErrFileName
= CommandLineWalker
+= 4;
868 if (StrStr(CommandLineWalker
, L
" 2> ") != NULL
) {
869 Status
= EFI_NOT_FOUND
;
873 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" 1> ")) != NULL
) {
874 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
875 SetMem16(CommandLineWalker
, 8, L
' ');
876 if (StdOutFileName
!= NULL
) {
877 Status
= EFI_INVALID_PARAMETER
;
879 StdOutFileName
= CommandLineWalker
+= 4;
882 if (StrStr(CommandLineWalker
, L
" 1> ") != NULL
) {
883 Status
= EFI_NOT_FOUND
;
887 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" > ")) != NULL
) {
888 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
889 SetMem16(CommandLineWalker
, 6, L
' ');
890 if (StdOutFileName
!= NULL
) {
891 Status
= EFI_INVALID_PARAMETER
;
893 StdOutFileName
= CommandLineWalker
+= 3;
896 if (StrStr(CommandLineWalker
, L
" > ") != NULL
) {
897 Status
= EFI_NOT_FOUND
;
901 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" < ")) != NULL
) {
902 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
903 SetMem16(CommandLineWalker
, 6, L
' ');
904 if (StdInFileName
!= NULL
) {
905 Status
= EFI_INVALID_PARAMETER
;
907 StdInFileName
= CommandLineWalker
+= 3;
909 if (StrStr(CommandLineWalker
, L
" < ") != NULL
) {
910 Status
= EFI_NOT_FOUND
;
913 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" <a ")) != NULL
) {
914 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
915 SetMem16(CommandLineWalker
, 8, L
' ');
916 if (StdInFileName
!= NULL
) {
917 Status
= EFI_INVALID_PARAMETER
;
919 StdInFileName
= CommandLineWalker
+= 4;
922 if (StrStr(CommandLineWalker
, L
" <a ") != NULL
) {
923 Status
= EFI_NOT_FOUND
;
926 if (!EFI_ERROR(Status
) && (CommandLineWalker
= StrStr(CommandLineCopy
, L
" <v ")) != NULL
) {
927 FirstLocation
= MIN(CommandLineWalker
, FirstLocation
);
928 SetMem16(CommandLineWalker
, 8, L
' ');
929 if (StdInVarName
!= NULL
) {
930 Status
= EFI_INVALID_PARAMETER
;
932 StdInVarName
= CommandLineWalker
+= 4;
934 if (StrStr(CommandLineWalker
, L
" <v ") != NULL
) {
935 Status
= EFI_NOT_FOUND
;
940 // re-populate the string to support any filenames that were in quotes.
942 StrCpy(CommandLineCopy
, NewCommandLine
);
944 if (FirstLocation
!= CommandLineCopy
+ StrLen(CommandLineCopy
)
945 && ((UINTN
)(FirstLocation
- CommandLineCopy
) < StrLen(NewCommandLine
))
947 *(NewCommandLine
+ (UINTN
)(FirstLocation
- CommandLineCopy
)) = CHAR_NULL
;
950 if (!EFI_ERROR(Status
)) {
952 if (StdErrFileName
!= NULL
) {
953 if ((StdErrFileName
= FixFileName(StdErrFileName
)) == NULL
) {
954 Status
= EFI_INVALID_PARAMETER
;
957 if (StdOutFileName
!= NULL
) {
958 if ((StdOutFileName
= FixFileName(StdOutFileName
)) == NULL
) {
959 Status
= EFI_INVALID_PARAMETER
;
962 if (StdInFileName
!= NULL
) {
963 if ((StdInFileName
= FixFileName(StdInFileName
)) == NULL
) {
964 Status
= EFI_INVALID_PARAMETER
;
967 if (StdErrVarName
!= NULL
) {
968 if ((StdErrVarName
= FixVarName(StdErrVarName
)) == NULL
) {
969 Status
= EFI_INVALID_PARAMETER
;
972 if (StdOutVarName
!= NULL
) {
973 if ((StdOutVarName
= FixVarName(StdOutVarName
)) == NULL
) {
974 Status
= EFI_INVALID_PARAMETER
;
977 if (StdInVarName
!= NULL
) {
978 if ((StdInVarName
= FixVarName(StdInVarName
)) == NULL
) {
979 Status
= EFI_INVALID_PARAMETER
;
984 // Verify not the same and not duplicating something from a split
988 // Check that no 2 filenames are the same
990 (StdErrFileName
!= NULL
&& StdOutFileName
!= NULL
&& StringNoCaseCompare(&StdErrFileName
, &StdOutFileName
) == 0)
991 ||(StdErrFileName
!= NULL
&& StdInFileName
!= NULL
&& StringNoCaseCompare(&StdErrFileName
, &StdInFileName
) == 0)
992 ||(StdOutFileName
!= NULL
&& StdInFileName
!= NULL
&& StringNoCaseCompare(&StdOutFileName
, &StdInFileName
) == 0)
994 // Check that no 2 variable names are the same
996 ||(StdErrVarName
!= NULL
&& StdInVarName
!= NULL
&& StringNoCaseCompare(&StdErrVarName
, &StdInVarName
) == 0)
997 ||(StdOutVarName
!= NULL
&& StdInVarName
!= NULL
&& StringNoCaseCompare(&StdOutVarName
, &StdInVarName
) == 0)
998 ||(StdErrVarName
!= NULL
&& StdOutVarName
!= NULL
&& StringNoCaseCompare(&StdErrVarName
, &StdOutVarName
) == 0)
1000 // When a split (using | operator) is in place some are not allowed
1002 ||(Split
!= NULL
&& Split
->SplitStdIn
!= NULL
&& (StdInVarName
!= NULL
|| StdInFileName
!= NULL
))
1003 ||(Split
!= NULL
&& Split
->SplitStdOut
!= NULL
&& (StdOutVarName
!= NULL
|| StdOutFileName
!= NULL
))
1005 // Check that nothing is trying to be output to 2 locations.
1007 ||(StdErrFileName
!= NULL
&& StdErrVarName
!= NULL
)
1008 ||(StdOutFileName
!= NULL
&& StdOutVarName
!= NULL
)
1009 ||(StdInFileName
!= NULL
&& StdInVarName
!= NULL
)
1011 // Check for no volatile environment variables
1013 ||(StdErrVarName
!= NULL
&& !IsVolatileEnv(StdErrVarName
))
1014 ||(StdOutVarName
!= NULL
&& !IsVolatileEnv(StdOutVarName
))
1016 // Cant redirect during a reconnect operation.
1018 ||(StrStr(NewCommandLine
, L
"connect -r") != NULL
1019 && (StdOutVarName
!= NULL
|| StdOutFileName
!= NULL
|| StdErrFileName
!= NULL
|| StdErrVarName
!= NULL
))
1021 // Check that filetypes (Unicode/Ascii) do not change during an append
1023 ||(StdOutFileName
!= NULL
&& OutUnicode
&& OutAppend
&& (!EFI_ERROR(ShellFileExists(StdOutFileName
)) && EFI_ERROR(IsUnicodeFile(StdOutFileName
))))
1024 ||(StdErrFileName
!= NULL
&& ErrUnicode
&& ErrAppend
&& (!EFI_ERROR(ShellFileExists(StdErrFileName
)) && EFI_ERROR(IsUnicodeFile(StdErrFileName
))))
1025 ||(StdOutFileName
!= NULL
&& !OutUnicode
&& OutAppend
&& (!EFI_ERROR(ShellFileExists(StdOutFileName
)) && !EFI_ERROR(IsUnicodeFile(StdOutFileName
))))
1026 ||(StdErrFileName
!= NULL
&& !ErrUnicode
&& ErrAppend
&& (!EFI_ERROR(ShellFileExists(StdErrFileName
)) && !EFI_ERROR(IsUnicodeFile(StdErrFileName
))))
1028 Status
= EFI_INVALID_PARAMETER
;
1029 ShellParameters
->StdIn
= *OldStdIn
;
1030 ShellParameters
->StdOut
= *OldStdOut
;
1031 ShellParameters
->StdErr
= *OldStdErr
;
1032 } else if (!EFI_ERROR(Status
)){
1034 // Open the Std<Whatever> and we should not have conflicts here...
1040 if (StdErrFileName
!= NULL
) {
1043 // delete existing file.
1045 ShellInfoObject
.NewEfiShellProtocol
->DeleteFileByName(StdErrFileName
);
1047 Status
= ShellOpenFileByName(StdErrFileName
, &TempHandle
, EFI_FILE_MODE_WRITE
|EFI_FILE_MODE_READ
|EFI_FILE_MODE_CREATE
,0);
1048 if (!ErrAppend
&& ErrUnicode
&& !EFI_ERROR(Status
)) {
1050 // Write out the gUnicodeFileTag
1052 Size
= sizeof(CHAR16
);
1053 TagBuffer
[0] = gUnicodeFileTag
;
1054 TagBuffer
[1] = CHAR_NULL
;
1055 ShellInfoObject
.NewEfiShellProtocol
->WriteFile(TempHandle
, &Size
, TagBuffer
);
1057 if (!ErrUnicode
&& !EFI_ERROR(Status
)) {
1058 TempHandle
= CreateFileInterfaceFile(TempHandle
, FALSE
);
1059 ASSERT(TempHandle
!= NULL
);
1061 if (!EFI_ERROR(Status
)) {
1062 ShellParameters
->StdErr
= TempHandle
;
1063 gST
->StdErr
= CreateSimpleTextOutOnFile(TempHandle
, &gST
->StandardErrorHandle
, gST
->StdErr
);
1070 if (!EFI_ERROR(Status
) && StdOutFileName
!= NULL
) {
1073 // delete existing file.
1075 ShellInfoObject
.NewEfiShellProtocol
->DeleteFileByName(StdOutFileName
);
1077 Status
= ShellOpenFileByName(StdOutFileName
, &TempHandle
, EFI_FILE_MODE_WRITE
|EFI_FILE_MODE_READ
|EFI_FILE_MODE_CREATE
,0);
1078 if (TempHandle
== NULL
) {
1079 Status
= EFI_INVALID_PARAMETER
;
1081 if (StrStr(StdOutFileName
, L
"NUL")==StdOutFileName
) {
1083 } else if (!OutAppend
&& OutUnicode
&& !EFI_ERROR(Status
)) {
1085 // Write out the gUnicodeFileTag
1087 Size
= sizeof(CHAR16
);
1088 TagBuffer
[0] = gUnicodeFileTag
;
1089 TagBuffer
[1] = CHAR_NULL
;
1090 ShellInfoObject
.NewEfiShellProtocol
->WriteFile(TempHandle
, &Size
, TagBuffer
);
1091 } else if (OutAppend
) {
1093 // Move to end of file
1095 Status
= ShellInfoObject
.NewEfiShellProtocol
->GetFileSize(TempHandle
, &FileSize
);
1096 if (!EFI_ERROR(Status
)) {
1097 Status
= ShellInfoObject
.NewEfiShellProtocol
->SetFilePosition(TempHandle
, FileSize
);
1100 if (!OutUnicode
&& !EFI_ERROR(Status
)) {
1101 TempHandle
= CreateFileInterfaceFile(TempHandle
, FALSE
);
1102 ASSERT(TempHandle
!= NULL
);
1104 if (!EFI_ERROR(Status
)) {
1105 ShellParameters
->StdOut
= TempHandle
;
1106 gST
->ConOut
= CreateSimpleTextOutOnFile(TempHandle
, &gST
->ConsoleOutHandle
, gST
->ConOut
);
1114 if (!EFI_ERROR(Status
) && StdOutVarName
!= NULL
) {
1117 // delete existing variable.
1119 SHELL_SET_ENVIRONMENT_VARIABLE_V(StdOutVarName
, 0, L
"");
1121 TempHandle
= CreateFileInterfaceEnv(StdOutVarName
);
1122 ASSERT(TempHandle
!= NULL
);
1123 ShellParameters
->StdOut
= TempHandle
;
1124 gST
->ConOut
= CreateSimpleTextOutOnFile(TempHandle
, &gST
->ConsoleOutHandle
, gST
->ConOut
);
1130 if (!EFI_ERROR(Status
) && StdErrVarName
!= NULL
) {
1133 // delete existing variable.
1135 SHELL_SET_ENVIRONMENT_VARIABLE_V(StdErrVarName
, 0, L
"");
1137 TempHandle
= CreateFileInterfaceEnv(StdErrVarName
);
1138 ASSERT(TempHandle
!= NULL
);
1139 ShellParameters
->StdErr
= TempHandle
;
1140 gST
->StdErr
= CreateSimpleTextOutOnFile(TempHandle
, &gST
->StandardErrorHandle
, gST
->StdErr
);
1146 if (!EFI_ERROR(Status
) && StdInVarName
!= NULL
) {
1147 TempHandle
= CreateFileInterfaceEnv(StdInVarName
);
1148 if (TempHandle
== NULL
) {
1149 Status
= EFI_OUT_OF_RESOURCES
;
1152 TempHandle
= CreateFileInterfaceFile(TempHandle
, FALSE
);
1155 if (TempHandle
== NULL
|| ((EFI_FILE_PROTOCOL
*)TempHandle
)->Read(TempHandle
, &Size
, NULL
) != EFI_BUFFER_TOO_SMALL
) {
1156 Status
= EFI_INVALID_PARAMETER
;
1158 ShellParameters
->StdIn
= TempHandle
;
1159 gST
->ConIn
= CreateSimpleTextInOnFile(TempHandle
, &gST
->ConsoleInHandle
);
1165 // StdIn from a file
1167 if (!EFI_ERROR(Status
) && StdInFileName
!= NULL
) {
1168 Status
= ShellOpenFileByName(
1175 // Chop off the 0xFEFF if it's there...
1177 RemoveFileTag(&TempHandle
);
1178 } else if (!EFI_ERROR(Status
)) {
1180 // Create the ASCII->Unicode conversion layer
1182 TempHandle
= CreateFileInterfaceFile(TempHandle
, FALSE
);
1184 if (!EFI_ERROR(Status
)) {
1185 ShellParameters
->StdIn
= TempHandle
;
1186 gST
->ConIn
= CreateSimpleTextInOnFile(TempHandle
, &gST
->ConsoleInHandle
);
1191 FreePool(CommandLineCopy
);
1193 CalculateEfiHdrCrc(&gST
->Hdr
);
1195 if (gST
->ConIn
== NULL
||gST
->ConOut
== NULL
) {
1196 Status
= EFI_OUT_OF_RESOURCES
;
1199 if (Status
== EFI_NOT_FOUND
) {
1200 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_SHELL_REDUNDA_REDIR
), ShellInfoObject
.HiiHandle
);
1201 } else if (EFI_ERROR(Status
)) {
1202 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_SHELL_INVALID_REDIR
), ShellInfoObject
.HiiHandle
);
1209 Funcion will replace the current StdIn and StdOut in the ShellParameters protocol
1210 structure with StdIn and StdOut. The current values are de-allocated.
1212 @param[in, out] ShellParameters Pointer to parameter structure to modify.
1213 @param[in] OldStdIn Pointer to old StdIn.
1214 @param[in] OldStdOut Pointer to old StdOut.
1215 @param[in] OldStdErr Pointer to old StdErr.
1216 @param[in] SystemTableInfo Pointer to old system table information.
1220 RestoreStdInStdOutStdErr (
1221 IN OUT EFI_SHELL_PARAMETERS_PROTOCOL
*ShellParameters
,
1222 IN SHELL_FILE_HANDLE
*OldStdIn
,
1223 IN SHELL_FILE_HANDLE
*OldStdOut
,
1224 IN SHELL_FILE_HANDLE
*OldStdErr
,
1225 IN SYSTEM_TABLE_INFO
*SystemTableInfo
1230 if (ShellParameters
== NULL
1234 ||SystemTableInfo
== NULL
) {
1235 return (EFI_INVALID_PARAMETER
);
1237 if (!IsListEmpty(&ShellInfoObject
.SplitList
.Link
)) {
1238 Split
= (SPLIT_LIST
*)GetFirstNode(&ShellInfoObject
.SplitList
.Link
);
1242 if (ShellParameters
->StdIn
!= *OldStdIn
) {
1243 if ((Split
!= NULL
&& Split
->SplitStdIn
!= ShellParameters
->StdIn
) || Split
== NULL
) {
1244 gEfiShellProtocol
->CloseFile(ShellParameters
->StdIn
);
1246 ShellParameters
->StdIn
= *OldStdIn
;
1248 if (ShellParameters
->StdOut
!= *OldStdOut
) {
1249 if ((Split
!= NULL
&& Split
->SplitStdOut
!= ShellParameters
->StdOut
) || Split
== NULL
) {
1250 gEfiShellProtocol
->CloseFile(ShellParameters
->StdOut
);
1252 ShellParameters
->StdOut
= *OldStdOut
;
1254 if (ShellParameters
->StdErr
!= *OldStdErr
) {
1255 gEfiShellProtocol
->CloseFile(ShellParameters
->StdErr
);
1256 ShellParameters
->StdErr
= *OldStdErr
;
1259 if (gST
->ConIn
!= SystemTableInfo
->ConIn
) {
1260 CloseSimpleTextInOnFile(gST
->ConIn
);
1261 gST
->ConIn
= SystemTableInfo
->ConIn
;
1262 gST
->ConsoleInHandle
= SystemTableInfo
->ConInHandle
;
1264 if (gST
->ConOut
!= SystemTableInfo
->ConOut
) {
1265 CloseSimpleTextOutOnFile(gST
->ConOut
);
1266 gST
->ConOut
= SystemTableInfo
->ConOut
;
1267 gST
->ConsoleOutHandle
= SystemTableInfo
->ConOutHandle
;
1269 if (gST
->StdErr
!= SystemTableInfo
->ErrOut
) {
1270 CloseSimpleTextOutOnFile(gST
->StdErr
);
1271 gST
->StdErr
= SystemTableInfo
->ErrOut
;
1272 gST
->StandardErrorHandle
= SystemTableInfo
->ErrOutHandle
;
1275 CalculateEfiHdrCrc(&gST
->Hdr
);
1277 return (EFI_SUCCESS
);
1280 Funcion will replace the current Argc and Argv in the ShellParameters protocol
1281 structure by parsing NewCommandLine. The current values are returned to the
1284 If OldArgv or OldArgc is NULL then that value is not returned.
1286 @param[in, out] ShellParameters Pointer to parameter structure to modify.
1287 @param[in] NewCommandLine The new command line to parse and use.
1288 @param[out] OldArgv Pointer to old list of parameters.
1289 @param[out] OldArgc Pointer to old number of items in Argv list.
1291 @retval EFI_SUCCESS Operation was sucessful, Argv and Argc are valid.
1292 @retval EFI_OUT_OF_RESOURCES A memory allocation failed.
1297 IN OUT EFI_SHELL_PARAMETERS_PROTOCOL
*ShellParameters
,
1298 IN CONST CHAR16
*NewCommandLine
,
1299 OUT CHAR16
***OldArgv OPTIONAL
,
1300 OUT UINTN
*OldArgc OPTIONAL
1303 ASSERT(ShellParameters
!= NULL
);
1305 if (OldArgc
!= NULL
) {
1306 *OldArgc
= ShellParameters
->Argc
;
1308 if (OldArgc
!= NULL
) {
1309 *OldArgv
= ShellParameters
->Argv
;
1312 return (ParseCommandLineToArgs(NewCommandLine
, &(ShellParameters
->Argv
), &(ShellParameters
->Argc
)));
1316 Funcion will replace the current Argc and Argv in the ShellParameters protocol
1317 structure with Argv and Argc. The current values are de-allocated and the
1318 OldArgv must not be deallocated by the caller.
1320 @param[in, out] ShellParameters pointer to parameter structure to modify
1321 @param[in] OldArgv pointer to old list of parameters
1322 @param[in] OldArgc pointer to old number of items in Argv list
1327 IN OUT EFI_SHELL_PARAMETERS_PROTOCOL
*ShellParameters
,
1328 IN CHAR16
***OldArgv
,
1333 ASSERT(ShellParameters
!= NULL
);
1334 ASSERT(OldArgv
!= NULL
);
1335 ASSERT(OldArgc
!= NULL
);
1337 if (ShellParameters
->Argv
!= NULL
) {
1338 for ( LoopCounter
= 0
1339 ; LoopCounter
< ShellParameters
->Argc
1342 FreePool(ShellParameters
->Argv
[LoopCounter
]);
1344 FreePool(ShellParameters
->Argv
);
1346 ShellParameters
->Argv
= *OldArgv
;
1348 ShellParameters
->Argc
= *OldArgc
;