2 Functions to deal with file buffer.
4 Copyright (c) 2005 - 2011, Intel Corporation. All rights reserved. <BR>
5 This program and the accompanying materials
6 are licensed and made available under the terms and conditions of the BSD License
7 which accompanies this distribution. The full text of the license may be found at
8 http://opensource.org/licenses/bsd-license.php
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
15 #include "HexEditor.h"
17 extern EFI_HANDLE HImageHandleBackup
;
18 extern HEFI_EDITOR_BUFFER_IMAGE HBufferImage
;
20 extern BOOLEAN HBufferImageNeedRefresh
;
21 extern BOOLEAN HBufferImageOnlyLineNeedRefresh
;
22 extern BOOLEAN HBufferImageMouseNeedRefresh
;
24 extern HEFI_EDITOR_GLOBAL_EDITOR HMainEditor
;
26 HEFI_EDITOR_FILE_IMAGE HFileImage
;
27 HEFI_EDITOR_FILE_IMAGE HFileImageBackupVar
;
30 // for basic initialization of HFileImage
32 HEFI_EDITOR_BUFFER_IMAGE HFileImageConst
= {
46 Initialization function for HFileImage
60 // basically initialize the HFileImage
62 CopyMem (&HFileImage
, &HFileImageConst
, sizeof (HFileImage
));
67 sizeof (HFileImageBackupVar
)
81 Backup function for HFileImage
82 Only a few fields need to be backup.
83 This is for making the file buffer refresh
97 SHELL_FREE_NON_NULL (HFileImageBackupVar
.FileName
);
98 HFileImageBackupVar
.FileName
= CatSPrint(NULL
, L
"%s", HFileImage
.FileName
);
99 if (HFileImageBackupVar
.FileName
== NULL
) {
100 return EFI_OUT_OF_RESOURCES
;
114 Cleanup function for HFileImage
127 SHELL_FREE_NON_NULL (HFileImage
.FileName
);
128 SHELL_FREE_NON_NULL (HFileImageBackupVar
.FileName
);
134 HFileImageSetFileName (
141 Set FileName field in HFileImage
145 Str -- File name to set
158 // free the old file name
160 SHELL_FREE_NON_NULL (HFileImage
.FileName
);
164 HFileImage
.FileName
= AllocateZeroPool (2 * (Size
+ 1));
165 if (HFileImage
.FileName
== NULL
) {
166 return EFI_OUT_OF_RESOURCES
;
169 for (Index
= 0; Index
< Size
; Index
++) {
170 HFileImage
.FileName
[Index
] = Str
[Index
];
173 HFileImage
.FileName
[Size
] = L
'\0';
179 HFileImageGetFileInfo (
180 IN EFI_FILE_HANDLE Handle
,
182 OUT EFI_FILE_INFO
**InfoOut
188 Get this file's information
192 Handle - in NT32 mode Directory handle, in other mode File Handle
193 FileName - The file name
194 InfoOut - parameter to pass file information out
209 Size
= SIZE_OF_EFI_FILE_INFO
+ 1024;
210 Info
= AllocateZeroPool (Size
);
212 return EFI_OUT_OF_RESOURCES
;
215 // get file information
217 Status
= Handle
->GetInfo (Handle
, &gEfiFileInfoGuid
, &Size
, Info
);
218 if (EFI_ERROR (Status
)) {
219 return EFI_LOAD_ERROR
;
222 *InfoOut
= (EFI_FILE_INFO
*) Info
;
230 IN CONST CHAR16
*FileName
,
237 Read a file from disk into HBufferImage
241 FileName -- filename to read
242 Recover -- if is for recover, no information print
252 HEFI_EDITOR_LINE
*Line
;
254 CHAR16
*UnicodeBuffer
;
258 // variable initialization
263 // in this function, when you return error ( except EFI_OUT_OF_RESOURCES )
264 // you should set status string
265 // since this function maybe called before the editorhandleinput loop
266 // so any error will cause editor return
267 // so if you want to print the error status
268 // you should set the status string
270 Status
= ReadFileIntoBuffer (FileName
, (VOID
**)&Buffer
, &HFileImage
.Size
, &HFileImage
.ReadOnly
);
271 if (EFI_ERROR(Status
)) {
272 UnicodeBuffer
= CatSPrint(NULL
, L
"Read error on file &s: %r", FileName
, Status
);
273 if (UnicodeBuffer
== NULL
) {
274 SHELL_FREE_NON_NULL(Buffer
);
275 return EFI_OUT_OF_RESOURCES
;
278 StatusBarSetStatusString (UnicodeBuffer
);
279 FreePool (UnicodeBuffer
);
282 HFileImageSetFileName (FileName
);
285 // free the old lines
289 Status
= HBufferImageBufferToList (Buffer
, HFileImage
.Size
);
290 SHELL_FREE_NON_NULL (Buffer
);
291 if (EFI_ERROR (Status
)) {
292 StatusBarSetStatusString (L
"Error parsing file.");
296 HBufferImage
.DisplayPosition
.Row
= 2;
297 HBufferImage
.DisplayPosition
.Column
= 10;
298 HBufferImage
.MousePosition
.Row
= 2;
299 HBufferImage
.MousePosition
.Column
= 10;
300 HBufferImage
.LowVisibleRow
= 1;
301 HBufferImage
.HighBits
= TRUE
;
302 HBufferImage
.BufferPosition
.Row
= 1;
303 HBufferImage
.BufferPosition
.Column
= 1;
304 HBufferImage
.BufferType
= FileTypeFileBuffer
;
307 UnicodeBuffer
= CatSPrint(NULL
, L
"%d Lines Read", HBufferImage
.NumLines
);
308 if (UnicodeBuffer
== NULL
) {
309 SHELL_FREE_NON_NULL(Buffer
);
310 return EFI_OUT_OF_RESOURCES
;
313 StatusBarSetStatusString (UnicodeBuffer
);
314 FreePool (UnicodeBuffer
);
316 HMainEditor
.SelectStart
= 0;
317 HMainEditor
.SelectEnd
= 0;
323 if (HBufferImage
.Lines
!= 0) {
324 HBufferImage
.CurrentLine
= CR (HBufferImage
.ListHead
->ForwardLink
, HEFI_EDITOR_LINE
, Link
, EFI_EDITOR_LINE_LIST
);
327 // create a dummy line
329 Line
= HBufferImageCreateLine ();
331 SHELL_FREE_NON_NULL(Buffer
);
332 return EFI_OUT_OF_RESOURCES
;
335 HBufferImage
.CurrentLine
= Line
;
338 HBufferImage
.Modified
= FALSE
;
339 HBufferImageNeedRefresh
= TRUE
;
340 HBufferImageOnlyLineNeedRefresh
= FALSE
;
341 HBufferImageMouseNeedRefresh
= TRUE
;
354 Save lines in HBufferImage to disk
358 FileName - The file name
370 HEFI_EDITOR_LINE
*Line
;
374 SHELL_FILE_HANDLE FileHandle
;
378 EDIT_FILE_TYPE BufferTypeBackup
;
380 BufferTypeBackup
= HBufferImage
.BufferType
;
381 HBufferImage
.BufferType
= FileTypeFileBuffer
;
384 // if is the old file
386 if (HFileImage
.FileName
!= NULL
&& FileName
!= NULL
&& StrCmp (FileName
, HFileImage
.FileName
) == 0) {
388 // check whether file exists on disk
390 if (ShellIsFile(FileName
) == EFI_SUCCESS
) {
392 // current file exists on disk
393 // so if not modified, then not save
395 if (HBufferImage
.Modified
== FALSE
) {
399 // if file is read-only, set error
401 if (HFileImage
.ReadOnly
== TRUE
) {
402 StatusBarSetStatusString (L
"Read Only File Can Not Be Saved");
408 if (ShellIsDirectory(FileName
) == EFI_SUCCESS
) {
409 StatusBarSetStatusString (L
"Directory Can Not Be Saved");
410 return EFI_LOAD_ERROR
;
413 Status
= ShellOpenFileByName (FileName
, &FileHandle
, EFI_FILE_MODE_READ
|EFI_FILE_MODE_WRITE
, 0);
415 if (!EFI_ERROR (Status
)) {
417 // the file exits, delete it
419 Status
= ShellDeleteFile (&FileHandle
);
420 if (EFI_ERROR (Status
) || Status
== EFI_WARN_DELETE_FAILURE
) {
421 StatusBarSetStatusString (L
"Write File Failed");
422 return EFI_LOAD_ERROR
;
427 // write all the lines back to disk
431 for (Link
= HBufferImage
.ListHead
->ForwardLink
; Link
!= HBufferImage
.ListHead
; Link
= Link
->ForwardLink
) {
432 Line
= CR (Link
, HEFI_EDITOR_LINE
, Link
, EFI_EDITOR_LINE_LIST
);
434 if (Line
->Size
!= 0) {
435 TotalSize
+= Line
->Size
;
438 // end of if Line -> Size != 0
445 Buffer
= AllocateZeroPool (TotalSize
);
446 if (Buffer
== NULL
) {
447 return EFI_OUT_OF_RESOURCES
;
451 for (Link
= HBufferImage
.ListHead
->ForwardLink
; Link
!= HBufferImage
.ListHead
; Link
= Link
->ForwardLink
) {
452 Line
= CR (Link
, HEFI_EDITOR_LINE
, Link
, EFI_EDITOR_LINE_LIST
);
454 if (Line
->Size
!= 0) {
455 CopyMem (Ptr
, Line
->Buffer
, Line
->Size
);
459 // end of if Line -> Size != 0
464 Status
= ShellOpenFileByName (FileName
, &FileHandle
, EFI_FILE_MODE_READ
|EFI_FILE_MODE_WRITE
|EFI_FILE_MODE_CREATE
, 0);
466 if (EFI_ERROR (Status
)) {
467 StatusBarSetStatusString (L
"Create File Failed");
468 return EFI_LOAD_ERROR
;
471 Status
= ShellWriteFile (FileHandle
, &TotalSize
, Buffer
);
473 if (EFI_ERROR (Status
)) {
474 ShellDeleteFile (&FileHandle
);
475 return EFI_LOAD_ERROR
;
478 ShellCloseFile(&FileHandle
);
480 HBufferImage
.Modified
= FALSE
;
485 Str
= CatSPrint(NULL
, L
"%d Lines Wrote", NumLines
);
486 StatusBarSetStatusString (Str
);
490 // now everything is ready , you can set the new file name to filebuffer
492 if (BufferTypeBackup
!= FileTypeFileBuffer
|| StringNoCaseCompare (&FileName
, &HFileImage
.FileName
) != 0) {
496 HFileImageSetFileName (FileName
);
497 if (HFileImage
.FileName
== NULL
) {
498 return EFI_OUT_OF_RESOURCES
;
502 HFileImage
.ReadOnly
= FALSE
;