2 EFI_FILE_PROTOCOL wrappers for other items (Like Environment Variables,
3 StdIn, StdOut, StdErr, etc...).
5 Copyright (c) 2009 - 2010, Intel Corporation. All rights reserved.<BR>
6 This program and the accompanying materials
7 are licensed and made available under the terms and conditions of the BSD License
8 which accompanies this distribution. The full text of the license may be found at
9 http://opensource.org/licenses/bsd-license.php
11 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
17 #include "FileHandleInternal.h"
20 File style interface for console (Open).
22 @param[in] This Ignored.
23 @param[out] NewHandle Ignored.
24 @param[in] FileName Ignored.
25 @param[in] OpenMode Ignored.
26 @param[in] Attributes Ignored.
32 FileInterfaceOpenNotFound(
33 IN EFI_FILE_PROTOCOL
*This
,
34 OUT EFI_FILE_PROTOCOL
**NewHandle
,
40 return (EFI_NOT_FOUND
);
44 File style interface for console (Close, Delete, & Flush)
46 @param[in] This Ignored.
52 FileInterfaceNopGeneric(
53 IN EFI_FILE_PROTOCOL
*This
60 File style interface for console (GetPosition).
62 @param[in] This Ignored.
63 @param[out] Position Ignored.
65 @retval EFI_UNSUPPORTED
69 FileInterfaceNopGetPosition(
70 IN EFI_FILE_PROTOCOL
*This
,
74 return (EFI_UNSUPPORTED
);
78 File style interface for console (SetPosition).
80 @param[in] This Ignored.
81 @param[in] Position Ignored.
83 @retval EFI_UNSUPPORTED
87 FileInterfaceNopSetPosition(
88 IN EFI_FILE_PROTOCOL
*This
,
92 return (EFI_UNSUPPORTED
);
96 File style interface for console (GetInfo).
98 @param[in] This Ignored.
99 @param[in] InformationType Ignored.
100 @param[in,out] BufferSize Ignored.
101 @param[out] Buffer Ignored.
103 @retval EFI_UNSUPPORTED
107 FileInterfaceNopGetInfo(
108 IN EFI_FILE_PROTOCOL
*This
,
109 IN EFI_GUID
*InformationType
,
110 IN OUT UINTN
*BufferSize
,
114 return (EFI_UNSUPPORTED
);
118 File style interface for console (SetInfo).
120 @param[in] This Ignored.
121 @param[in] InformationType Ignored.
122 @param[in] BufferSize Ignored.
123 @param[in] Buffer Ignored.
125 @retval EFI_UNSUPPORTED
129 FileInterfaceNopSetInfo(
130 IN EFI_FILE_PROTOCOL
*This
,
131 IN EFI_GUID
*InformationType
,
136 return (EFI_UNSUPPORTED
);
140 File style interface for StdOut (Write).
142 Writes data to the screen.
144 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
145 @param[in,out] BufferSize Size in bytes of Buffer.
146 @param[in] Buffer The pointer to the buffer to write.
148 @retval EFI_UNSUPPORTED No output console is supported.
149 @return A return value from gST->ConOut->OutputString.
153 FileInterfaceStdOutWrite(
154 IN EFI_FILE_PROTOCOL
*This
,
155 IN OUT UINTN
*BufferSize
,
159 if (ShellInfoObject
.ShellInitSettings
.BitUnion
.Bits
.NoConsoleOut
) {
160 return (EFI_UNSUPPORTED
);
162 return (gST
->ConOut
->OutputString(gST
->ConOut
, Buffer
));
167 File style interface for StdIn (Write).
169 @param[in] This Ignored.
170 @param[in] BufferSize Ignored.
171 @param[in] Buffer Ignored.
173 @retval EFI_UNSUPPORTED
177 FileInterfaceStdInWrite(
178 IN EFI_FILE_PROTOCOL
*This
,
179 IN OUT UINTN
*BufferSize
,
183 return (EFI_UNSUPPORTED
);
187 File style interface for console StdErr (Write).
189 Writes error to the error output.
191 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
192 @param[in,out] BufferSize Size in bytes of Buffer.
193 @param[in] Buffer The pointer to the buffer to write.
195 @return A return value from gST->StdErr->OutputString.
199 FileInterfaceStdErrWrite(
200 IN EFI_FILE_PROTOCOL
*This
,
201 IN OUT UINTN
*BufferSize
,
205 return (gST
->StdErr
->OutputString(gST
->StdErr
, Buffer
));
209 File style interface for console StdOut (Read).
211 @param[in] This Ignored.
212 @param[in,out] BufferSize Ignored.
213 @param[out] Buffer Ignored.
215 @retval EFI_UNSUPPORTED
219 FileInterfaceStdOutRead(
220 IN EFI_FILE_PROTOCOL
*This
,
221 IN OUT UINTN
*BufferSize
,
225 return (EFI_UNSUPPORTED
);
229 File style interface for console StdErr (Read).
231 @param[in] This Ignored.
232 @param[in,out] BufferSize Ignored.
233 @param[out] Buffer Ignored.
235 @retval EFI_UNSUPPORTED
239 FileInterfaceStdErrRead(
240 IN EFI_FILE_PROTOCOL
*This
,
241 IN OUT UINTN
*BufferSize
,
245 return (EFI_UNSUPPORTED
);
249 File style interface for NUL file (Read).
251 @param[in] This Ignored.
252 @param[in,out] BufferSize Ignored.
253 @param[in] Buffer Ignored.
259 FileInterfaceNulRead(
260 IN EFI_FILE_PROTOCOL
*This
,
261 IN OUT UINTN
*BufferSize
,
265 return (EFI_SUCCESS
);
269 File style interface for NUL file (Write).
271 @param[in] This Ignored.
272 @param[in,out] BufferSize Ignored.
273 @param[in] Buffer Ignored.
279 FileInterfaceNulWrite(
280 IN EFI_FILE_PROTOCOL
*This
,
281 IN OUT UINTN
*BufferSize
,
285 return (EFI_SUCCESS
);
289 File style interface for console (Read).
291 This will return a single line of input from the console.
293 @param This A pointer to the EFI_FILE_PROTOCOL instance that is the
294 file handle to read data from. Not used.
295 @param BufferSize On input, the size of the Buffer. On output, the amount
296 of data returned in Buffer. In both cases, the size is
298 @param Buffer The buffer into which the data is read.
301 @retval EFI_SUCCESS The data was read.
302 @retval EFI_NO_MEDIA The device has no medium.
303 @retval EFI_DEVICE_ERROR The device reported an error.
304 @retval EFI_DEVICE_ERROR An attempt was made to read from a deleted file.
305 @retval EFI_DEVICE_ERROR On entry, the current file position is beyond the end of the file.
306 @retval EFI_VOLUME_CORRUPTED The file system structures are corrupted.
307 @retval EFI_BUFFER_TOO_SMALL The BufferSize is too small to read the current directory
308 entry. BufferSize has been updated with the size
309 needed to complete the request.
310 @retval EFI_OUT_OF_RESOURCES A memory allocation failed.
314 FileInterfaceStdInRead(
315 IN EFI_FILE_PROTOCOL
*This
,
316 IN OUT UINTN
*BufferSize
,
320 CHAR16
*CurrentString
;
322 UINTN Column
; // Column of current cursor
323 UINTN Row
; // Row of current cursor
324 UINTN StartColumn
; // Column at the beginning of the line
325 UINTN Update
; // Line index for update
326 UINTN Delete
; // Num of chars to delete from console after update
327 UINTN StringLen
; // Total length of the line
328 UINTN StringCurPos
; // Line index corresponding to the cursor
329 UINTN MaxStr
; // Maximum possible line length
331 UINTN TotalColumn
; // Num of columns in the console
332 UINTN TotalRow
; // Num of rows in the console
334 UINTN OutputLength
; // Length of the update string
335 UINTN TailRow
; // Row of end of line
336 UINTN TailColumn
; // Column of end of line
339 BUFFER_LIST
*LinePos
;
343 BOOLEAN InTabScrolling
; // Whether in TAB-completion state
344 EFI_SHELL_FILE_INFO
*FoundFileList
;
345 EFI_SHELL_FILE_INFO
*TabLinePos
;
346 EFI_SHELL_FILE_INFO
*TempPos
;
348 CHAR16
*TabOutputStr
;
349 BOOLEAN InQuotationMode
;
351 UINTN TabPos
; // Start index of the string to search for TAB completion.
352 UINTN TabUpdatePos
; // Start index of the string updated by TAB stroke
358 // If buffer is not large enough to hold a CHAR16, return minimum buffer size
360 if (*BufferSize
< sizeof (CHAR16
) * 2) {
361 *BufferSize
= sizeof (CHAR16
) * 2;
362 return (EFI_BUFFER_TOO_SMALL
);
366 CurrentString
= Buffer
;
372 LinePos
= NewPos
= (BUFFER_LIST
*)(&ShellInfoObject
.ViewingSettings
.CommandHistory
);
374 InTabScrolling
= FALSE
;
375 Status
= EFI_SUCCESS
;
377 FoundFileList
= NULL
;
385 TabStr
= AllocateZeroPool (*BufferSize
);
386 if (TabStr
== NULL
) {
387 return EFI_OUT_OF_RESOURCES
;
389 TabOutputStr
= AllocateZeroPool (*BufferSize
);
390 if (TabOutputStr
== NULL
) {
392 return EFI_OUT_OF_RESOURCES
;
396 // Get the screen setting and the current cursor location
398 Column
= StartColumn
= gST
->ConOut
->Mode
->CursorColumn
;
399 Row
= gST
->ConOut
->Mode
->CursorRow
;
400 gST
->ConOut
->QueryMode (gST
->ConOut
, gST
->ConOut
->Mode
->Mode
, &TotalColumn
, &TotalRow
);
403 // Limit the line length to the buffer size or the minimun size of the
404 // screen. (The smaller takes effect)
406 MaxStr
= TotalColumn
* (TotalRow
- 1) - StartColumn
;
407 if (MaxStr
> *BufferSize
/ sizeof (CHAR16
)) {
408 MaxStr
= *BufferSize
/ sizeof (CHAR16
);
410 ZeroMem (CurrentString
, MaxStr
* sizeof (CHAR16
));
415 gBS
->WaitForEvent (1, &gST
->ConIn
->WaitForKey
, &EventIndex
);
416 Status
= gST
->ConIn
->ReadKeyStroke (gST
->ConIn
, &Key
);
417 if (EFI_ERROR (Status
)) {
422 // Press PageUp or PageDown to scroll the history screen up or down.
423 // Press any other key to quit scrolling.
425 if (Key
.UnicodeChar
== 0 && (Key
.ScanCode
== SCAN_PAGE_UP
|| Key
.ScanCode
== SCAN_PAGE_DOWN
)) {
426 if (Key
.ScanCode
== SCAN_PAGE_UP
) {
427 ConsoleLoggerDisplayHistory(FALSE
, 0, ShellInfoObject
.ConsoleInfo
);
428 } else if (Key
.ScanCode
== SCAN_PAGE_DOWN
) {
429 ConsoleLoggerDisplayHistory(TRUE
, 0, ShellInfoObject
.ConsoleInfo
);
435 ConsoleLoggerStopHistory(ShellInfoObject
.ConsoleInfo
);
441 // If we are quitting TAB scrolling...
443 if (InTabScrolling
&& Key
.UnicodeChar
!= CHAR_TAB
) {
444 if (FoundFileList
!= NULL
) {
445 ShellInfoObject
.NewEfiShellProtocol
->FreeFileList (&FoundFileList
);
446 DEBUG_CODE(FoundFileList
= NULL
;);
448 InTabScrolling
= FALSE
;
451 switch (Key
.UnicodeChar
) {
452 case CHAR_CARRIAGE_RETURN
:
454 // All done, print a newline at the end of the string
456 TailRow
= Row
+ (StringLen
- StringCurPos
+ Column
) / TotalColumn
;
457 TailColumn
= (StringLen
- StringCurPos
+ Column
) % TotalColumn
;
458 ShellPrintEx ((INT32
)TailColumn
, (INT32
)TailRow
, L
"%N\n");
463 if (StringCurPos
!= 0) {
465 // If not move back beyond string beginning, move all characters behind
466 // the current position one character forward
469 Update
= StringCurPos
;
471 CopyMem (CurrentString
+ StringCurPos
, CurrentString
+ StringCurPos
+ 1, sizeof (CHAR16
) * (StringLen
- StringCurPos
));
474 // Adjust the current column and row
476 MoveCursorBackward (TotalColumn
, &Column
, &Row
);
482 // handle auto complete of file and directory names...
484 if (InTabScrolling
) {
485 ASSERT(FoundFileList
!= NULL
);
486 ASSERT(TabLinePos
!= NULL
);
487 TabLinePos
= (EFI_SHELL_FILE_INFO
*)GetNextNode(&(FoundFileList
->Link
), &TabLinePos
->Link
);
488 if (IsNull(&(FoundFileList
->Link
), &TabLinePos
->Link
)) {
489 TabLinePos
= (EFI_SHELL_FILE_INFO
*)GetNextNode(&(FoundFileList
->Link
), &TabLinePos
->Link
);
494 InQuotationMode
= FALSE
;
495 for (Index
= 0; Index
< StringLen
; Index
++) {
496 if (CurrentString
[Index
] == L
'\"') {
497 InQuotationMode
= (BOOLEAN
)(!InQuotationMode
);
499 if (CurrentString
[Index
] == L
' ' && !InQuotationMode
) {
501 TabUpdatePos
= Index
+ 1;
503 if (CurrentString
[Index
] == L
'\\') {
504 TabUpdatePos
= Index
+ 1;
507 if (StrStr(CurrentString
+ TabPos
, L
":") == NULL
) {
508 Cwd
= ShellInfoObject
.NewEfiShellProtocol
->GetCurDir(NULL
);
511 if (TabStr
[StrLen(TabStr
)-1] == L
'\\' && *(CurrentString
+ TabPos
) == L
'\\' ) {
512 TabStr
[StrLen(TabStr
)-1] = CHAR_NULL
;
514 StrnCat(TabStr
, CurrentString
+ TabPos
, (StringLen
- TabPos
) * sizeof (CHAR16
));
517 StrnCat(TabStr
, CurrentString
+ TabPos
, (StringLen
- TabPos
) * sizeof (CHAR16
));
520 StrCpy(TabStr
, CurrentString
+ TabPos
);
522 StrCat(TabStr
, L
"*");
523 FoundFileList
= NULL
;
524 // TabStr = CleanPath(TabStr);
525 Status
= ShellInfoObject
.NewEfiShellProtocol
->FindFiles(TabStr
, &FoundFileList
);
526 for ( TempStr
= CurrentString
528 ; TempStr
++); // note the ';'... empty for loop
530 // make sure we have a list before we do anything more...
532 if (EFI_ERROR (Status
) || FoundFileList
== NULL
) {
533 InTabScrolling
= FALSE
;
538 // enumerate through the list of files
540 for ( TempPos
= (EFI_SHELL_FILE_INFO
*)GetFirstNode(&(FoundFileList
->Link
))
541 ; !IsNull(&FoundFileList
->Link
, &TempPos
->Link
)
542 ; TempPos
= (EFI_SHELL_FILE_INFO
*)GetNextNode(&(FoundFileList
->Link
), &(TempPos
->Link
))
545 // If "cd" is typed, only directory name will be auto-complete filled
546 // in either case . and .. will be removed.
548 if ((((TempStr
[0] == L
'c' || TempStr
[0] == L
'C') &&
549 (TempStr
[1] == L
'd' || TempStr
[1] == L
'D')
550 ) && ((ShellIsDirectory(TempPos
->FullName
) != EFI_SUCCESS
)
551 ||(StrCmp(TempPos
->FileName
, L
".") == 0)
552 ||(StrCmp(TempPos
->FileName
, L
"..") == 0)
553 )) || ((StrCmp(TempPos
->FileName
, L
".") == 0)
554 ||(StrCmp(TempPos
->FileName
, L
"..") == 0))){
555 TabLinePos
= TempPos
;
556 TempPos
= (EFI_SHELL_FILE_INFO
*)(RemoveEntryList(&(TempPos
->Link
))->BackLink
);
557 InternalFreeShellFileInfoNode(TabLinePos
);
560 if (FoundFileList
!= NULL
&& !IsListEmpty(&FoundFileList
->Link
)) {
561 TabLinePos
= (EFI_SHELL_FILE_INFO
*)GetFirstNode(&FoundFileList
->Link
);
562 InTabScrolling
= TRUE
;
564 FreePool(FoundFileList
);
565 FoundFileList
= NULL
;
572 if (Key
.UnicodeChar
>= ' ') {
574 // If we are at the buffer's end, drop the key
576 if (StringLen
== MaxStr
- 1 && (ShellInfoObject
.ViewingSettings
.InsertMode
|| StringCurPos
== StringLen
)) {
580 // If in insert mode, make space by moving each other character 1
581 // space higher in the array
583 if (ShellInfoObject
.ViewingSettings
.InsertMode
) {
584 CopyMem(CurrentString
+ StringCurPos
+ 1, CurrentString
+ StringCurPos
, (StringLen
- StringCurPos
)*sizeof(CurrentString
[0]));
587 CurrentString
[StringCurPos
] = Key
.UnicodeChar
;
588 Update
= StringCurPos
;
596 switch (Key
.ScanCode
) {
599 // Move characters behind current position one character forward
601 if (StringLen
!= 0) {
602 Update
= StringCurPos
;
604 CopyMem (CurrentString
+ StringCurPos
, CurrentString
+ StringCurPos
+ 1, sizeof (CHAR16
) * (StringLen
- StringCurPos
));
610 // Prepare to print the previous command
612 NewPos
= (BUFFER_LIST
*)GetPreviousNode(&ShellInfoObject
.ViewingSettings
.CommandHistory
.Link
, &LinePos
->Link
);
613 if (IsNull(&ShellInfoObject
.ViewingSettings
.CommandHistory
.Link
, &LinePos
->Link
)) {
614 NewPos
= (BUFFER_LIST
*)GetPreviousNode(&ShellInfoObject
.ViewingSettings
.CommandHistory
.Link
, &LinePos
->Link
);
620 // Prepare to print the next command
622 NewPos
= (BUFFER_LIST
*)GetNextNode(&ShellInfoObject
.ViewingSettings
.CommandHistory
.Link
, &LinePos
->Link
);
623 if (NewPos
== (BUFFER_LIST
*)(&ShellInfoObject
.ViewingSettings
.CommandHistory
)) {
624 NewPos
= (BUFFER_LIST
*)GetNextNode(&ShellInfoObject
.ViewingSettings
.CommandHistory
.Link
, &LinePos
->Link
);
630 // Adjust current cursor position
632 if (StringCurPos
!= 0) {
634 MoveCursorBackward (TotalColumn
, &Column
, &Row
);
640 // Adjust current cursor position
642 if (StringCurPos
< StringLen
) {
644 MoveCursorForward (TotalColumn
, TotalRow
, &Column
, &Row
);
650 // Move current cursor position to the beginning of the command line
652 Row
-= (StringCurPos
+ StartColumn
) / TotalColumn
;
653 Column
= StartColumn
;
659 // Move current cursor position to the end of the command line
661 TailRow
= Row
+ (StringLen
- StringCurPos
+ Column
) / TotalColumn
;
662 TailColumn
= (StringLen
- StringCurPos
+ Column
) % TotalColumn
;
665 StringCurPos
= StringLen
;
670 // Prepare to clear the current command line
672 CurrentString
[0] = 0;
675 Row
-= (StringCurPos
+ StartColumn
) / TotalColumn
;
676 Column
= StartColumn
;
682 // Toggle the SEnvInsertMode flag
684 ShellInfoObject
.ViewingSettings
.InsertMode
= (BOOLEAN
)!ShellInfoObject
.ViewingSettings
.InsertMode
;
689 // Print command history
691 PrintCommandHistory (TotalColumn
, TotalRow
, 4);
692 *CurrentString
= CHAR_NULL
;
703 // If we are in auto-complete mode, we are preparing to print
704 // the next file or directory name
706 if (InTabScrolling
) {
708 // Adjust the column and row to the start of TAB-completion string.
710 Column
= (StartColumn
+ TabUpdatePos
) % TotalColumn
;
711 Row
-= (StartColumn
+ StringCurPos
) / TotalColumn
- (StartColumn
+ TabUpdatePos
) / TotalColumn
;
712 OutputLength
= StrLen (TabLinePos
->FileName
);
714 // if the output string contains blank space, quotation marks L'\"'
715 // should be added to the output.
717 if (StrStr(TabLinePos
->FileName
, L
" ") != NULL
){
718 TabOutputStr
[0] = L
'\"';
719 CopyMem (TabOutputStr
+ 1, TabLinePos
->FileName
, OutputLength
* sizeof (CHAR16
));
720 TabOutputStr
[OutputLength
+ 1] = L
'\"';
721 TabOutputStr
[OutputLength
+ 2] = CHAR_NULL
;
723 CopyMem (TabOutputStr
, TabLinePos
->FileName
, OutputLength
* sizeof (CHAR16
));
724 TabOutputStr
[OutputLength
] = CHAR_NULL
;
726 OutputLength
= StrLen (TabOutputStr
) < MaxStr
- 1 ? StrLen (TabOutputStr
) : MaxStr
- 1;
727 CopyMem (CurrentString
+ TabUpdatePos
, TabOutputStr
, OutputLength
* sizeof (CHAR16
));
728 CurrentString
[TabUpdatePos
+ OutputLength
] = CHAR_NULL
;
729 StringCurPos
= TabUpdatePos
+ OutputLength
;
730 Update
= TabUpdatePos
;
731 if (StringLen
> TabUpdatePos
+ OutputLength
) {
732 Delete
= StringLen
- TabUpdatePos
- OutputLength
;
737 // If we have a new position, we are preparing to print a previous or
740 if (NewPos
!= (BUFFER_LIST
*)(&ShellInfoObject
.ViewingSettings
.CommandHistory
)) {
741 Column
= StartColumn
;
742 Row
-= (StringCurPos
+ StartColumn
) / TotalColumn
;
745 NewPos
= (BUFFER_LIST
*)(&ShellInfoObject
.ViewingSettings
.CommandHistory
);
747 OutputLength
= StrLen (LinePos
->Buffer
) < MaxStr
- 1 ? StrLen (LinePos
->Buffer
) : MaxStr
- 1;
748 CopyMem (CurrentString
, LinePos
->Buffer
, OutputLength
* sizeof (CHAR16
));
749 CurrentString
[OutputLength
] = CHAR_NULL
;
751 StringCurPos
= OutputLength
;
754 // Draw new input string
757 if (StringLen
> OutputLength
) {
759 // If old string was longer, blank its tail
761 Delete
= StringLen
- OutputLength
;
765 // If we need to update the output do so now
767 if (Update
!= (UINTN
) -1) {
768 ShellPrintEx ((INT32
)Column
, (INT32
)Row
, L
"%s%.*s", CurrentString
+ Update
, Delete
, L
"");
769 StringLen
= StrLen (CurrentString
);
772 SetMem (CurrentString
+ StringLen
, Delete
* sizeof (CHAR16
), CHAR_NULL
);
775 if (StringCurPos
> StringLen
) {
776 StringCurPos
= StringLen
;
782 // After using print to reflect newly updates, if we're not using
783 // BACKSPACE and DELETE, we need to move the cursor position forward,
784 // so adjust row and column here.
786 if (Key
.UnicodeChar
!= CHAR_BACKSPACE
&& !(Key
.UnicodeChar
== 0 && Key
.ScanCode
== SCAN_DELETE
)) {
788 // Calulate row and column of the tail of current string
790 TailRow
= Row
+ (StringLen
- StringCurPos
+ Column
+ OutputLength
) / TotalColumn
;
791 TailColumn
= (StringLen
- StringCurPos
+ Column
+ OutputLength
) % TotalColumn
;
794 // If the tail of string reaches screen end, screen rolls up, so if
795 // Row does not equal TailRow, Row should be decremented
797 // (if we are recalling commands using UPPER and DOWN key, and if the
798 // old command is too long to fit the screen, TailColumn must be 79.
800 if (TailColumn
== 0 && TailRow
>= TotalRow
&& Row
!= TailRow
) {
804 // Calculate the cursor position after current operation. If cursor
805 // reaches line end, update both row and column, otherwise, only
806 // column will be changed.
808 if (Column
+ OutputLength
>= TotalColumn
) {
809 SkipLength
= OutputLength
- (TotalColumn
- Column
);
811 Row
+= SkipLength
/ TotalColumn
+ 1;
812 if (Row
> TotalRow
- 1) {
816 Column
= SkipLength
% TotalColumn
;
818 Column
+= OutputLength
;
825 // Set the cursor position for this key
827 gST
->ConOut
->SetCursorPosition (gST
->ConOut
, Column
, Row
);
830 if (CurrentString
!= NULL
&& StrLen(CurrentString
) > 0) {
832 // add the line to the history buffer
834 AddLineToCommandHistory(CurrentString
);
838 FreePool (TabOutputStr
);
840 // Return the data to the caller
842 *BufferSize
= StringLen
* sizeof (CHAR16
);
845 // if this was used it should be deallocated by now...
846 // prevent memory leaks...
848 ASSERT(FoundFileList
== NULL
);
854 // FILE sytle interfaces for StdIn/StdOut/StdErr
856 EFI_FILE_PROTOCOL FileInterfaceStdIn
= {
858 FileInterfaceOpenNotFound
,
859 FileInterfaceNopGeneric
,
860 FileInterfaceNopGeneric
,
861 FileInterfaceStdInRead
,
862 FileInterfaceStdInWrite
,
863 FileInterfaceNopGetPosition
,
864 FileInterfaceNopSetPosition
,
865 FileInterfaceNopGetInfo
,
866 FileInterfaceNopSetInfo
,
867 FileInterfaceNopGeneric
870 EFI_FILE_PROTOCOL FileInterfaceStdOut
= {
872 FileInterfaceOpenNotFound
,
873 FileInterfaceNopGeneric
,
874 FileInterfaceNopGeneric
,
875 FileInterfaceStdOutRead
,
876 FileInterfaceStdOutWrite
,
877 FileInterfaceNopGetPosition
,
878 FileInterfaceNopSetPosition
,
879 FileInterfaceNopGetInfo
,
880 FileInterfaceNopSetInfo
,
881 FileInterfaceNopGeneric
884 EFI_FILE_PROTOCOL FileInterfaceStdErr
= {
886 FileInterfaceOpenNotFound
,
887 FileInterfaceNopGeneric
,
888 FileInterfaceNopGeneric
,
889 FileInterfaceStdErrRead
,
890 FileInterfaceStdErrWrite
,
891 FileInterfaceNopGetPosition
,
892 FileInterfaceNopSetPosition
,
893 FileInterfaceNopGetInfo
,
894 FileInterfaceNopSetInfo
,
895 FileInterfaceNopGeneric
898 EFI_FILE_PROTOCOL FileInterfaceNulFile
= {
900 FileInterfaceOpenNotFound
,
901 FileInterfaceNopGeneric
,
902 FileInterfaceNopGeneric
,
903 FileInterfaceNulRead
,
904 FileInterfaceNulWrite
,
905 FileInterfaceNopGetPosition
,
906 FileInterfaceNopSetPosition
,
907 FileInterfaceNopGetInfo
,
908 FileInterfaceNopSetInfo
,
909 FileInterfaceNopGeneric
916 // This is identical to EFI_FILE_PROTOCOL except for the additional member
923 EFI_FILE_CLOSE Close
;
924 EFI_FILE_DELETE Delete
;
926 EFI_FILE_WRITE Write
;
927 EFI_FILE_GET_POSITION GetPosition
;
928 EFI_FILE_SET_POSITION SetPosition
;
929 EFI_FILE_GET_INFO GetInfo
;
930 EFI_FILE_SET_INFO SetInfo
;
931 EFI_FILE_FLUSH Flush
;
933 } EFI_FILE_PROTOCOL_ENVIRONMENT
;
934 //ANSI compliance helper to get size of the struct.
935 #define SIZE_OF_EFI_FILE_PROTOCOL_ENVIRONMENT EFI_FIELD_OFFSET (EFI_FILE_PROTOCOL_ENVIRONMENT, Name)
938 File style interface for Environment Variable (Close).
940 Frees the memory for this object.
942 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
948 FileInterfaceEnvClose(
949 IN EFI_FILE_PROTOCOL
*This
952 FreePool((EFI_FILE_PROTOCOL_ENVIRONMENT
*)This
);
953 return (EFI_SUCCESS
);
957 File style interface for Environment Variable (Delete).
959 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
961 @retval The return value from FileInterfaceEnvClose().
965 FileInterfaceEnvDelete(
966 IN EFI_FILE_PROTOCOL
*This
969 SHELL_DELETE_ENVIRONMENT_VARIABLE(((EFI_FILE_PROTOCOL_ENVIRONMENT
*)This
)->Name
);
970 return (FileInterfaceEnvClose(This
));
974 File style interface for Environment Variable (Read).
976 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
977 @param[in,out] BufferSize Size in bytes of Buffer.
978 @param[out] Buffer The pointer to the buffer to fill.
980 @retval EFI_SUCCESS The data was read.
984 FileInterfaceEnvRead(
985 IN EFI_FILE_PROTOCOL
*This
,
986 IN OUT UINTN
*BufferSize
,
990 return (SHELL_GET_ENVIRONMENT_VARIABLE(
991 ((EFI_FILE_PROTOCOL_ENVIRONMENT
*)This
)->Name
,
997 File style interface for Volatile Environment Variable (Write).
999 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
1000 @param[in,out] BufferSize Size in bytes of Buffer.
1001 @param[in] Buffer The pointer to the buffer to write.
1003 @retval EFI_SUCCESS The data was read.
1007 FileInterfaceEnvVolWrite(
1008 IN EFI_FILE_PROTOCOL
*This
,
1009 IN OUT UINTN
*BufferSize
,
1020 Status
= SHELL_GET_ENVIRONMENT_VARIABLE(((EFI_FILE_PROTOCOL_ENVIRONMENT
*)This
)->Name
, &NewSize
, NewBuffer
);
1021 if (Status
== EFI_BUFFER_TOO_SMALL
){
1022 NewBuffer
= AllocateZeroPool(NewSize
+ *BufferSize
+ sizeof(CHAR16
));
1023 Status
= SHELL_GET_ENVIRONMENT_VARIABLE(((EFI_FILE_PROTOCOL_ENVIRONMENT
*)This
)->Name
, &NewSize
, NewBuffer
);
1025 if (!EFI_ERROR(Status
) && NewBuffer
!= NULL
) {
1026 while (((CHAR16
*)NewBuffer
)[NewSize
/2] == CHAR_NULL
) {
1028 // We want to overwrite the CHAR_NULL
1032 CopyMem((UINT8
*)NewBuffer
+ NewSize
+ 2, Buffer
, *BufferSize
);
1033 Status
= SHELL_SET_ENVIRONMENT_VARIABLE_V(((EFI_FILE_PROTOCOL_ENVIRONMENT
*)This
)->Name
, StrSize(NewBuffer
), NewBuffer
);
1034 FreePool(NewBuffer
);
1037 SHELL_FREE_NON_NULL(NewBuffer
);
1038 return (SHELL_SET_ENVIRONMENT_VARIABLE_V(((EFI_FILE_PROTOCOL_ENVIRONMENT
*)This
)->Name
, *BufferSize
, Buffer
));
1044 File style interface for Non Volatile Environment Variable (Write).
1046 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
1047 @param[in,out] BufferSize Size in bytes of Buffer.
1048 @param[in] Buffer The pointer to the buffer to write.
1050 @retval EFI_SUCCESS The data was read.
1054 FileInterfaceEnvNonVolWrite(
1055 IN EFI_FILE_PROTOCOL
*This
,
1056 IN OUT UINTN
*BufferSize
,
1067 Status
= SHELL_GET_ENVIRONMENT_VARIABLE(((EFI_FILE_PROTOCOL_ENVIRONMENT
*)This
)->Name
, &NewSize
, NewBuffer
);
1068 if (Status
== EFI_BUFFER_TOO_SMALL
){
1069 NewBuffer
= AllocateZeroPool(NewSize
+ *BufferSize
);
1070 Status
= SHELL_GET_ENVIRONMENT_VARIABLE(((EFI_FILE_PROTOCOL_ENVIRONMENT
*)This
)->Name
, &NewSize
, NewBuffer
);
1072 if (!EFI_ERROR(Status
)) {
1073 CopyMem((UINT8
*)NewBuffer
+ NewSize
, Buffer
, *BufferSize
);
1074 return (SHELL_SET_ENVIRONMENT_VARIABLE_NV(
1075 ((EFI_FILE_PROTOCOL_ENVIRONMENT
*)This
)->Name
,
1076 NewSize
+ *BufferSize
,
1079 return (SHELL_SET_ENVIRONMENT_VARIABLE_NV(
1080 ((EFI_FILE_PROTOCOL_ENVIRONMENT
*)This
)->Name
,
1087 Creates a EFI_FILE_PROTOCOL (almost) object for using to access
1088 environment variables through file operations.
1090 @param EnvName The name of the Environment Variable to be operated on.
1092 @retval NULL Memory could not be allocated.
1093 @return other a pointer to an EFI_FILE_PROTOCOL structure
1097 CreateFileInterfaceEnv(
1098 IN CONST CHAR16
*EnvName
1101 EFI_FILE_PROTOCOL_ENVIRONMENT
*EnvFileInterface
;
1103 if (EnvName
== NULL
) {
1110 EnvFileInterface
= AllocateZeroPool(sizeof(EFI_FILE_PROTOCOL_ENVIRONMENT
)+StrSize(EnvName
));
1111 if (EnvFileInterface
== NULL
){
1116 // Assign the generic members
1118 EnvFileInterface
->Revision
= EFI_FILE_REVISION
;
1119 EnvFileInterface
->Open
= FileInterfaceOpenNotFound
;
1120 EnvFileInterface
->Close
= FileInterfaceEnvClose
;
1121 EnvFileInterface
->GetPosition
= FileInterfaceNopGetPosition
;
1122 EnvFileInterface
->SetPosition
= FileInterfaceNopSetPosition
;
1123 EnvFileInterface
->GetInfo
= FileInterfaceNopGetInfo
;
1124 EnvFileInterface
->SetInfo
= FileInterfaceNopSetInfo
;
1125 EnvFileInterface
->Flush
= FileInterfaceNopGeneric
;
1126 EnvFileInterface
->Delete
= FileInterfaceEnvDelete
;
1127 EnvFileInterface
->Read
= FileInterfaceEnvRead
;
1129 StrCpy(EnvFileInterface
->Name
, EnvName
);
1132 // Assign the different members for Volatile and Non-Volatile variables
1134 if (IsVolatileEnv(EnvName
)) {
1135 EnvFileInterface
->Write
= FileInterfaceEnvVolWrite
;
1137 EnvFileInterface
->Write
= FileInterfaceEnvNonVolWrite
;
1139 return ((EFI_FILE_PROTOCOL
*)EnvFileInterface
);
1143 Move the cursor position one character backward.
1145 @param[in] LineLength Length of a line. Get it by calling QueryMode
1146 @param[in,out] Column Current column of the cursor position
1147 @param[in,out] Row Current row of the cursor position
1151 MoveCursorBackward (
1152 IN UINTN LineLength
,
1153 IN OUT UINTN
*Column
,
1158 // If current column is 0, move to the last column of the previous line,
1159 // otherwise, just decrement column.
1162 *Column
= LineLength
- 1;
1172 Move the cursor position one character forward.
1174 @param[in] LineLength Length of a line.
1175 @param[in] TotalRow Total row of a screen
1176 @param[in,out] Column Current column of the cursor position
1177 @param[in,out] Row Current row of the cursor position
1182 IN UINTN LineLength
,
1184 IN OUT UINTN
*Column
,
1189 // Increment Column.
1190 // If this puts column past the end of the line, move to first column
1194 if (*Column
>= LineLength
) {
1196 if ((*Row
) < TotalRow
- 1) {
1203 Prints out each previously typed command in the command list history log.
1205 When each screen is full it will pause for a key before continuing.
1207 @param[in] TotalCols How many columns are on the screen
1208 @param[in] TotalRows How many rows are on the screen
1209 @param[in] StartColumn which column to start at
1213 PrintCommandHistory (
1214 IN CONST UINTN TotalCols
,
1215 IN CONST UINTN TotalRows
,
1216 IN CONST UINTN StartColumn
1224 ShellPrintEx (-1, -1, L
"\n");
1228 // go through history list...
1230 for ( Node
= (BUFFER_LIST
*)GetFirstNode(&ShellInfoObject
.ViewingSettings
.CommandHistory
.Link
)
1231 ; !IsNull(&ShellInfoObject
.ViewingSettings
.CommandHistory
.Link
, &Node
->Link
)
1232 ; Node
= (BUFFER_LIST
*)GetNextNode(&ShellInfoObject
.ViewingSettings
.CommandHistory
.Link
, &Node
->Link
)
1235 LineCount
= ((StrLen (Node
->Buffer
) + StartColumn
+ 1) / TotalCols
) + 1;
1237 if (LineNumber
+ LineCount
>= TotalRows
) {
1238 ShellPromptForResponseHii(
1239 ShellPromptResponseTypeEnterContinue
,
1240 STRING_TOKEN (STR_SHELL_ENTER_TO_CONT
),
1241 ShellInfoObject
.HiiHandle
,
1246 ShellPrintEx (-1, -1, L
"%2d. %s\n", Index
, Node
->Buffer
);
1247 LineNumber
+= LineCount
;
1257 // This is identical to EFI_FILE_PROTOCOL except for the additional members
1258 // for the buffer, size, and position.
1264 EFI_FILE_CLOSE Close
;
1265 EFI_FILE_DELETE Delete
;
1267 EFI_FILE_WRITE Write
;
1268 EFI_FILE_GET_POSITION GetPosition
;
1269 EFI_FILE_SET_POSITION SetPosition
;
1270 EFI_FILE_GET_INFO GetInfo
;
1271 EFI_FILE_SET_INFO SetInfo
;
1272 EFI_FILE_FLUSH Flush
;
1277 } EFI_FILE_PROTOCOL_MEM
;
1280 File style interface for Mem (SetPosition).
1282 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
1283 @param[out] Position The position to set.
1285 @retval EFI_SUCCESS The position was successfully changed.
1286 @retval EFI_INVALID_PARAMETER The Position was invalid.
1290 FileInterfaceMemSetPosition(
1291 IN EFI_FILE_PROTOCOL
*This
,
1295 if (Position
<= ((EFI_FILE_PROTOCOL_MEM
*)This
)->BufferSize
) {
1296 ((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
= Position
;
1297 return (EFI_SUCCESS
);
1299 return (EFI_INVALID_PARAMETER
);
1304 File style interface for Mem (GetPosition).
1306 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
1307 @param[out] Position The pointer to the position.
1309 @retval EFI_SUCCESS The position was retrieved.
1313 FileInterfaceMemGetPosition(
1314 IN EFI_FILE_PROTOCOL
*This
,
1315 OUT UINT64
*Position
1318 *Position
= ((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
;
1319 return (EFI_SUCCESS
);
1323 File style interface for Mem (Write).
1325 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
1326 @param[in,out] BufferSize Size in bytes of Buffer.
1327 @param[in] Buffer The pointer to the buffer to write.
1329 @retval EFI_SUCCESS The data was written.
1333 FileInterfaceMemWrite(
1334 IN EFI_FILE_PROTOCOL
*This
,
1335 IN OUT UINTN
*BufferSize
,
1340 if (((EFI_FILE_PROTOCOL_MEM
*)This
)->Unicode
) {
1344 if ((UINTN
)(((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
+ (*BufferSize
)) > (UINTN
)(((EFI_FILE_PROTOCOL_MEM
*)This
)->BufferSize
)) {
1345 ((EFI_FILE_PROTOCOL_MEM
*)This
)->Buffer
= ReallocatePool((UINTN
)(((EFI_FILE_PROTOCOL_MEM
*)This
)->BufferSize
), (UINTN
)(((EFI_FILE_PROTOCOL_MEM
*)This
)->BufferSize
) + (*BufferSize
) + 10, ((EFI_FILE_PROTOCOL_MEM
*)This
)->Buffer
);
1346 ((EFI_FILE_PROTOCOL_MEM
*)This
)->BufferSize
+= (*BufferSize
) + 10;
1348 CopyMem(((UINT8
*)((EFI_FILE_PROTOCOL_MEM
*)This
)->Buffer
) + ((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
, Buffer
, *BufferSize
);
1349 ((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
+= (*BufferSize
);
1350 return (EFI_SUCCESS
);
1355 AsciiBuffer
= AllocatePool(*BufferSize
);
1356 AsciiSPrint(AsciiBuffer
, *BufferSize
, "%S", Buffer
);
1357 if ((UINTN
)(((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
+ AsciiStrSize(AsciiBuffer
)) > (UINTN
)(((EFI_FILE_PROTOCOL_MEM
*)This
)->BufferSize
)) {
1358 ((EFI_FILE_PROTOCOL_MEM
*)This
)->Buffer
= ReallocatePool((UINTN
)(((EFI_FILE_PROTOCOL_MEM
*)This
)->BufferSize
), (UINTN
)(((EFI_FILE_PROTOCOL_MEM
*)This
)->BufferSize
) + AsciiStrSize(AsciiBuffer
) + 10, ((EFI_FILE_PROTOCOL_MEM
*)This
)->Buffer
);
1359 ((EFI_FILE_PROTOCOL_MEM
*)This
)->BufferSize
+= AsciiStrSize(AsciiBuffer
) + 10;
1361 CopyMem(((UINT8
*)((EFI_FILE_PROTOCOL_MEM
*)This
)->Buffer
) + ((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
, AsciiBuffer
, AsciiStrSize(AsciiBuffer
));
1362 ((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
+= AsciiStrSize(AsciiBuffer
);
1363 FreePool(AsciiBuffer
);
1364 return (EFI_SUCCESS
);
1369 File style interface for Mem (Read).
1371 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
1372 @param[in,out] BufferSize Size in bytes of Buffer.
1373 @param[in] Buffer The pointer to the buffer to fill.
1375 @retval EFI_SUCCESS The data was read.
1379 FileInterfaceMemRead(
1380 IN EFI_FILE_PROTOCOL
*This
,
1381 IN OUT UINTN
*BufferSize
,
1385 if (*BufferSize
> (UINTN
)((((EFI_FILE_PROTOCOL_MEM
*)This
)->BufferSize
) - (UINTN
)(((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
))) {
1386 (*BufferSize
) = (UINTN
)((((EFI_FILE_PROTOCOL_MEM
*)This
)->BufferSize
) - (UINTN
)(((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
));
1388 CopyMem(Buffer
, ((UINT8
*)((EFI_FILE_PROTOCOL_MEM
*)This
)->Buffer
) + ((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
, (*BufferSize
));
1389 ((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
= ((EFI_FILE_PROTOCOL_MEM
*)This
)->Position
+ (*BufferSize
);
1390 return (EFI_SUCCESS
);
1394 File style interface for Mem (Close).
1396 Frees all memory associated with this object.
1398 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
1400 @retval EFI_SUCCESS The 'file' was closed.
1404 FileInterfaceMemClose(
1405 IN EFI_FILE_PROTOCOL
*This
1408 SHELL_FREE_NON_NULL(((EFI_FILE_PROTOCOL_MEM
*)This
)->Buffer
);
1409 SHELL_FREE_NON_NULL((EFI_FILE_PROTOCOL_MEM
*)This
);
1410 return (EFI_SUCCESS
);
1414 Creates a EFI_FILE_PROTOCOL (almost) object for using to access
1415 a file entirely in memory through file operations.
1417 @param[in] Unicode Boolean value with TRUE for Unicode and FALSE for Ascii.
1419 @retval NULL Memory could not be allocated.
1420 @return other A pointer to an EFI_FILE_PROTOCOL structure.
1424 CreateFileInterfaceMem(
1425 IN CONST BOOLEAN Unicode
1428 EFI_FILE_PROTOCOL_MEM
*FileInterface
;
1433 FileInterface
= AllocateZeroPool(sizeof(EFI_FILE_PROTOCOL_MEM
));
1434 if (FileInterface
== NULL
){
1439 // Assign the generic members
1441 FileInterface
->Revision
= EFI_FILE_REVISION
;
1442 FileInterface
->Open
= FileInterfaceOpenNotFound
;
1443 FileInterface
->Close
= FileInterfaceMemClose
;
1444 FileInterface
->GetPosition
= FileInterfaceMemGetPosition
;
1445 FileInterface
->SetPosition
= FileInterfaceMemSetPosition
;
1446 FileInterface
->GetInfo
= FileInterfaceNopGetInfo
;
1447 FileInterface
->SetInfo
= FileInterfaceNopSetInfo
;
1448 FileInterface
->Flush
= FileInterfaceNopGeneric
;
1449 FileInterface
->Delete
= FileInterfaceNopGeneric
;
1450 FileInterface
->Read
= FileInterfaceMemRead
;
1451 FileInterface
->Write
= FileInterfaceMemWrite
;
1452 FileInterface
->Unicode
= Unicode
;
1454 ASSERT(FileInterface
->Buffer
== NULL
);
1455 ASSERT(FileInterface
->BufferSize
== 0);
1456 ASSERT(FileInterface
->Position
== 0);
1458 return ((EFI_FILE_PROTOCOL
*)FileInterface
);
1464 EFI_FILE_CLOSE Close
;
1465 EFI_FILE_DELETE Delete
;
1467 EFI_FILE_WRITE Write
;
1468 EFI_FILE_GET_POSITION GetPosition
;
1469 EFI_FILE_SET_POSITION SetPosition
;
1470 EFI_FILE_GET_INFO GetInfo
;
1471 EFI_FILE_SET_INFO SetInfo
;
1472 EFI_FILE_FLUSH Flush
;
1474 EFI_FILE_PROTOCOL
*Orig
;
1475 } EFI_FILE_PROTOCOL_FILE
;
1478 File style interface for File (Close).
1480 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
1482 @retval EFI_SUCCESS The file was closed.
1486 FileInterfaceFileClose(
1487 IN EFI_FILE_PROTOCOL
*This
1490 ((EFI_FILE_PROTOCOL_FILE
*)This
)->Orig
->Close(((EFI_FILE_PROTOCOL_FILE
*)This
)->Orig
);
1492 return (EFI_SUCCESS
);
1496 File style interface for File (Write).
1498 If the file was opened with ASCII mode the data will be processed through
1499 AsciiSPrint before writing.
1501 @param[in] This The pointer to the EFI_FILE_PROTOCOL object.
1502 @param[in] BufferSize Size in bytes of Buffer.
1503 @param[in] Buffer The pointer to the buffer to write.
1505 @retval EFI_SUCCESS The data was written.
1509 FileInterfaceFileWrite(
1510 IN EFI_FILE_PROTOCOL
*This
,
1511 IN OUT UINTN
*BufferSize
,
1518 if (((EFI_FILE_PROTOCOL_FILE
*)This
)->Unicode
) {
1522 return (((EFI_FILE_PROTOCOL_FILE
*)This
)->Orig
->Write(((EFI_FILE_PROTOCOL_FILE
*)This
)->Orig
, BufferSize
, Buffer
));
1527 AsciiBuffer
= AllocatePool(*BufferSize
);
1528 AsciiSPrint(AsciiBuffer
, *BufferSize
, "%S", Buffer
);
1529 Size
= AsciiStrSize(AsciiBuffer
) - 1; // (we dont need the null terminator)
1530 Status
= (((EFI_FILE_PROTOCOL_FILE
*)This
)->Orig
->Write(((EFI_FILE_PROTOCOL_FILE
*)This
)->Orig
, &Size
, AsciiBuffer
));
1531 FreePool(AsciiBuffer
);
1537 Create a file interface with unicode information.
1539 This will create a new EFI_FILE_PROTOCOL identical to the Templace
1540 except that the new one has Unicode and Ascii knowledge.
1542 @param[in] Template A pointer to the EFI_FILE_PROTOCOL object.
1543 @param[in] Unicode TRUE for UCS-2, FALSE for ASCII.
1545 @return a new EFI_FILE_PROTOCOL object to be used instead of the template.
1548 CreateFileInterfaceFile(
1549 IN CONST EFI_FILE_PROTOCOL
*Template
,
1550 IN CONST BOOLEAN Unicode
1553 EFI_FILE_PROTOCOL_FILE
*NewOne
;
1555 NewOne
= AllocatePool(sizeof(EFI_FILE_PROTOCOL_FILE
));
1556 CopyMem(NewOne
, Template
, sizeof(EFI_FILE_PROTOCOL_FILE
));
1557 NewOne
->Orig
= (EFI_FILE_PROTOCOL
*)Template
;
1558 NewOne
->Unicode
= Unicode
;
1559 NewOne
->Close
= FileInterfaceFileClose
;
1560 NewOne
->Write
= FileInterfaceFileWrite
;
1562 return ((EFI_FILE_PROTOCOL
*)NewOne
);