]> git.proxmox.com Git - mirror_edk2.git/blob - ShellPkg/Library/UefiShellDebug1CommandsLib/UefiShellDebug1CommandsLib.c
ShellPkg: stop using EFI_HANDLE in place of EFI_HII_HANDLE
[mirror_edk2.git] / ShellPkg / Library / UefiShellDebug1CommandsLib / UefiShellDebug1CommandsLib.c
1 /** @file
2 Main file for NULL named library for debug1 profile shell command functions.
3
4 Copyright (c) 2010 - 2018, Intel Corporation. All rights reserved.<BR>
5 SPDX-License-Identifier: BSD-2-Clause-Patent
6
7 **/
8
9 #include "UefiShellDebug1CommandsLib.h"
10 #include <Library/BcfgCommandLib.h>
11
12 STATIC CONST CHAR16 mFileName[] = L"Debug1Commands";
13 EFI_HII_HANDLE gShellDebug1HiiHandle = NULL;
14
15 /**
16 Gets the debug file name. This will be used if HII is not working.
17
18 @retval NULL No file is available.
19 @return The NULL-terminated filename to get help from.
20 **/
21 CONST CHAR16*
22 EFIAPI
23 ShellCommandGetManFileNameDebug1 (
24 VOID
25 )
26 {
27 return (mFileName);
28 }
29
30 /**
31 Constructor for the Shell Debug1 Commands library.
32
33 @param ImageHandle the image handle of the process
34 @param SystemTable the EFI System Table pointer
35
36 @retval EFI_SUCCESS the shell command handlers were installed sucessfully
37 @retval EFI_UNSUPPORTED the shell level required was not found.
38 **/
39 EFI_STATUS
40 EFIAPI
41 UefiShellDebug1CommandsLibConstructor (
42 IN EFI_HANDLE ImageHandle,
43 IN EFI_SYSTEM_TABLE *SystemTable
44 )
45 {
46 //
47 // check our bit of the profiles mask
48 //
49 if ((PcdGet8(PcdShellProfileMask) & BIT1) == 0) {
50 return (EFI_SUCCESS);
51 }
52
53 //
54 // install the HII stuff.
55 //
56 gShellDebug1HiiHandle = HiiAddPackages (&gShellDebug1HiiGuid, gImageHandle, UefiShellDebug1CommandsLibStrings, NULL);
57 if (gShellDebug1HiiHandle == NULL) {
58 return (EFI_DEVICE_ERROR);
59 }
60
61 //
62 // install our shell command handlers that are always installed
63 //
64 ShellCommandRegisterCommandName(L"setsize", ShellCommandRunSetSize , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_SETSIZE) );
65 ShellCommandRegisterCommandName(L"comp", ShellCommandRunComp , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_COMP) );
66 ShellCommandRegisterCommandName(L"mode", ShellCommandRunMode , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_MODE) );
67 ShellCommandRegisterCommandName(L"memmap", ShellCommandRunMemMap , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_MEMMAP) );
68 ShellCommandRegisterCommandName(L"eficompress", ShellCommandRunEfiCompress , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_EFICOMPRESS) );
69 ShellCommandRegisterCommandName(L"efidecompress", ShellCommandRunEfiDecompress , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_EFIDCOMPRESS) );
70 ShellCommandRegisterCommandName(L"dmem", ShellCommandRunDmem , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_DMEM) );
71 ShellCommandRegisterCommandName(L"loadpcirom", ShellCommandRunLoadPciRom , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_LOAD_PCI_ROM) );
72 ShellCommandRegisterCommandName(L"mm", ShellCommandRunMm , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_MM) );
73 ShellCommandRegisterCommandName(L"setvar", ShellCommandRunSetVar , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_SETVAR) );
74 ShellCommandRegisterCommandName(L"sermode", ShellCommandRunSerMode , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_SERMODE) );
75 ShellCommandRegisterCommandName(L"pci", ShellCommandRunPci , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_PCI) );
76 ShellCommandRegisterCommandName(L"smbiosview", ShellCommandRunSmbiosView , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_SMBIOSVIEW) );
77 ShellCommandRegisterCommandName(L"dmpstore", ShellCommandRunDmpStore , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_DMPSTORE) );
78 ShellCommandRegisterCommandName(L"dblk", ShellCommandRunDblk , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_DBLK) );
79 ShellCommandRegisterCommandName(L"edit", ShellCommandRunEdit , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_EDIT) );
80 ShellCommandRegisterCommandName(L"hexedit", ShellCommandRunHexEdit , ShellCommandGetManFileNameDebug1, 0, L"Debug1", TRUE, gShellDebug1HiiHandle, STRING_TOKEN(STR_GET_HELP_HEXEDIT) );
81
82 ShellCommandRegisterAlias(L"dmem", L"mem");
83
84 BcfgLibraryRegisterBcfgCommand(ImageHandle, SystemTable, L"Debug1");
85
86 return (EFI_SUCCESS);
87 }
88
89 /**
90 Destructor for the library. free any resources.
91
92 @param ImageHandle The image handle of the process.
93 @param SystemTable The EFI System Table pointer.
94 **/
95 EFI_STATUS
96 EFIAPI
97 UefiShellDebug1CommandsLibDestructor (
98 IN EFI_HANDLE ImageHandle,
99 IN EFI_SYSTEM_TABLE *SystemTable
100 )
101 {
102 if (gShellDebug1HiiHandle != NULL) {
103 HiiRemovePackages(gShellDebug1HiiHandle);
104 }
105
106 BcfgLibraryUnregisterBcfgCommand(ImageHandle, SystemTable);
107 return (EFI_SUCCESS);
108 }
109
110
111 /**
112 Function returns a system configuration table that is stored in the
113 EFI System Table based on the provided GUID.
114
115 @param[in] TableGuid A pointer to the table's GUID type.
116 @param[in, out] Table On exit, a pointer to a system configuration table.
117
118 @retval EFI_SUCCESS A configuration table matching TableGuid was found.
119 @retval EFI_NOT_FOUND A configuration table matching TableGuid was not found.
120 **/
121 EFI_STATUS
122 GetSystemConfigurationTable (
123 IN EFI_GUID *TableGuid,
124 IN OUT VOID **Table
125 )
126 {
127 UINTN Index;
128 ASSERT (Table != NULL);
129
130 for (Index = 0; Index < gST->NumberOfTableEntries; Index++) {
131 if (CompareGuid (TableGuid, &(gST->ConfigurationTable[Index].VendorGuid))) {
132 *Table = gST->ConfigurationTable[Index].VendorTable;
133 return EFI_SUCCESS;
134 }
135 }
136
137 return EFI_NOT_FOUND;
138 }
139
140 /**
141 Clear the line at the specified Row.
142
143 @param[in] Row The row number to be cleared ( start from 1 )
144 @param[in] LastCol The last printable column.
145 @param[in] LastRow The last printable row.
146 **/
147 VOID
148 EditorClearLine (
149 IN UINTN Row,
150 IN UINTN LastCol,
151 IN UINTN LastRow
152 )
153 {
154 UINTN Col;
155 CHAR16 Line[200];
156
157 if (Row == 0) {
158 Row = 1;
159 }
160
161 //
162 // prepare a blank line
163 // If max column is larger, split to multiple prints.
164 //
165 SetMem16 (Line, sizeof (Line), L' ');
166 Line[ARRAY_SIZE (Line) - 1] = CHAR_NULL;
167
168 for (Col = 1; Col <= LastCol; Col += ARRAY_SIZE (Line) - 1) {
169 if (Col + ARRAY_SIZE (Line) - 1 > LastCol) {
170 if (Row == LastRow) {
171 //
172 // if CHAR_NULL is still at position LastCol, it will cause first line error
173 //
174 Line[(LastCol - 1) % (ARRAY_SIZE (Line) - 1)] = CHAR_NULL;
175 } else {
176 Line[LastCol % (ARRAY_SIZE (Line) - 1)] = CHAR_NULL;
177 }
178 }
179
180 //
181 // print out the blank line
182 //
183 ShellPrintEx ((INT32) Col - 1, (INT32) Row - 1, Line);
184 }
185 }
186
187 /**
188 Determine if the character is valid for a filename.
189
190 @param[in] Ch The character to test.
191
192 @retval TRUE The character is valid.
193 @retval FALSE The character is not valid.
194 **/
195 BOOLEAN
196 IsValidFileNameChar (
197 IN CONST CHAR16 Ch
198 )
199 {
200 //
201 // See if there are any illegal characters within the name
202 //
203 if (Ch < 0x20 || Ch == L'\"' || Ch == L'*' || Ch == L'/' || Ch == L'<' || Ch == L'>' || Ch == L'?' || Ch == L'|') {
204 return FALSE;
205 }
206
207 return TRUE;
208 }
209
210 /**
211 Check if file name has illegal characters.
212
213 @param Name The filename to check.
214
215 @retval TRUE The filename is ok.
216 @retval FALSE The filename is not ok.
217 **/
218 BOOLEAN
219 IsValidFileName (
220 IN CONST CHAR16 *Name
221 )
222 {
223
224 UINTN Index;
225 UINTN Len;
226
227 //
228 // check the length of Name
229 //
230 for (Len = 0, Index = StrLen (Name) - 1; Index + 1 != 0; Index--, Len++) {
231 if (Name[Index] == '\\' || Name[Index] == ':') {
232 break;
233 }
234 }
235
236 if (Len == 0 || Len > 255) {
237 return FALSE;
238 }
239 //
240 // check whether any char in Name not appears in valid file name char
241 //
242 for (Index = 0; Index < StrLen (Name); Index++) {
243 if (!IsValidFileNameChar (Name[Index])) {
244 return FALSE;
245 }
246 }
247
248 return TRUE;
249 }
250
251 /**
252 Find a filename that is valid (not taken) with the given extension.
253
254 @param[in] Extension The file extension.
255
256 @retval NULL Something went wrong.
257 @return the valid filename.
258 **/
259 CHAR16 *
260 EditGetDefaultFileName (
261 IN CONST CHAR16 *Extension
262 )
263 {
264 EFI_STATUS Status;
265 UINTN Suffix;
266 CHAR16 *FileNameTmp;
267
268 Suffix = 0;
269
270 do {
271 FileNameTmp = CatSPrint (NULL, L"NewFile%d.%s", Suffix, Extension);
272
273 //
274 // after that filename changed to path
275 //
276 Status = ShellFileExists (FileNameTmp);
277
278 if (Status == EFI_NOT_FOUND) {
279 return FileNameTmp;
280 }
281
282 FreePool (FileNameTmp);
283 FileNameTmp = NULL;
284 Suffix++;
285 } while (Suffix != 0);
286
287 FreePool (FileNameTmp);
288 return NULL;
289 }
290
291 /**
292 Read a file into an allocated buffer. The buffer is the responsibility
293 of the caller to free.
294
295 @param[in] FileName The filename of the file to open.
296 @param[out] Buffer Upon successful return, the pointer to the
297 address of the allocated buffer.
298 @param[out] BufferSize If not NULL, then the pointer to the size
299 of the allocated buffer.
300 @param[out] ReadOnly Upon successful return TRUE if the file is
301 read only. FALSE otherwise.
302
303 @retval EFI_NOT_FOUND The filename did not represent a file in the
304 file system.
305 @retval EFI_SUCCESS The file was read into the buffer.
306 @retval EFI_OUT_OF_RESOURCES A memory allocation failed.
307 @retval EFI_LOAD_ERROR The file read operation failed.
308 @retval EFI_INVALID_PARAMETER A parameter was invalid.
309 @retval EFI_INVALID_PARAMETER FileName was NULL.
310 @retval EFI_INVALID_PARAMETER FileName was a directory.
311 **/
312 EFI_STATUS
313 ReadFileIntoBuffer (
314 IN CONST CHAR16 *FileName,
315 OUT VOID **Buffer,
316 OUT UINTN *BufferSize OPTIONAL,
317 OUT BOOLEAN *ReadOnly
318 )
319 {
320 VOID *InternalBuffer;
321 UINTN FileSize;
322 SHELL_FILE_HANDLE FileHandle;
323 BOOLEAN CreateFile;
324 EFI_STATUS Status;
325 EFI_FILE_INFO *Info;
326
327 InternalBuffer = NULL;
328 FileSize = 0;
329 FileHandle = NULL;
330 CreateFile = FALSE;
331 Status = EFI_SUCCESS;
332 Info = NULL;
333
334 if (FileName == NULL || Buffer == NULL || ReadOnly == NULL) {
335 return (EFI_INVALID_PARAMETER);
336 }
337
338 //
339 // try to open the file
340 //
341 Status = ShellOpenFileByName (FileName, &FileHandle, EFI_FILE_MODE_READ, 0);
342
343 if (!EFI_ERROR(Status)) {
344 ASSERT(CreateFile == FALSE);
345 if (FileHandle == NULL) {
346 return EFI_LOAD_ERROR;
347 }
348
349 Info = ShellGetFileInfo(FileHandle);
350
351 if (Info->Attribute & EFI_FILE_DIRECTORY) {
352 FreePool (Info);
353 return EFI_INVALID_PARAMETER;
354 }
355
356 if (Info->Attribute & EFI_FILE_READ_ONLY) {
357 *ReadOnly = TRUE;
358 } else {
359 *ReadOnly = FALSE;
360 }
361 //
362 // get file size
363 //
364 FileSize = (UINTN) Info->FileSize;
365
366 FreePool (Info);
367 } else if (Status == EFI_NOT_FOUND) {
368 //
369 // file not exists. add create and try again
370 //
371 Status = ShellOpenFileByName (FileName, &FileHandle, EFI_FILE_MODE_READ|EFI_FILE_MODE_WRITE|EFI_FILE_MODE_CREATE, 0);
372 if (EFI_ERROR (Status)) {
373 return Status;
374 } else {
375 //
376 // it worked. now delete it and move on with the name (now validated)
377 //
378 Status = ShellDeleteFile (&FileHandle);
379 if (Status == EFI_WARN_DELETE_FAILURE) {
380 Status = EFI_ACCESS_DENIED;
381 }
382 if (EFI_ERROR (Status)) {
383 return Status;
384 }
385 }
386 //
387 // file doesn't exist, so set CreateFile to TRUE and can't be read-only
388 //
389 CreateFile = TRUE;
390 *ReadOnly = FALSE;
391 }
392
393 //
394 // the file exists
395 //
396 if (!CreateFile) {
397 //
398 // allocate buffer to read file
399 //
400 InternalBuffer = AllocateZeroPool (FileSize);
401 if (InternalBuffer == NULL) {
402 return EFI_OUT_OF_RESOURCES;
403 }
404 //
405 // read file into InternalBuffer
406 //
407 Status = ShellReadFile (FileHandle, &FileSize, InternalBuffer);
408 ShellCloseFile(&FileHandle);
409 FileHandle = NULL;
410 if (EFI_ERROR (Status)) {
411 SHELL_FREE_NON_NULL (InternalBuffer);
412 return EFI_LOAD_ERROR;
413 }
414 }
415 *Buffer = InternalBuffer;
416 if (BufferSize != NULL) {
417 *BufferSize = FileSize;
418 }
419 return (EFI_SUCCESS);
420
421 }