2 Main file for attrib shell level 2 function.
4 Copyright (c) 2009 - 2013, 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 "UefiShellLevel2CommandsLib.h"
18 Function for 'cd' command.
20 @param[in] ImageHandle Handle to the Image (NULL if Internal).
21 @param[in] SystemTable Pointer to the System Table (NULL if Internal).
26 IN EFI_HANDLE ImageHandle
,
27 IN EFI_SYSTEM_TABLE
*SystemTable
32 CONST CHAR16
*Directory
;
37 SHELL_STATUS ShellStatus
;
38 SHELL_FILE_HANDLE Handle
;
43 ShellStatus
= SHELL_SUCCESS
;
47 Status
= CommandInit();
48 ASSERT_EFI_ERROR(Status
);
51 // initialize the shell lib (we must be in non-auto-init...)
53 Status
= ShellInitialize();
54 ASSERT_EFI_ERROR(Status
);
57 // parse the command line
59 Status
= ShellCommandLineParse (EmptyParamList
, &Package
, &ProblemParam
, TRUE
);
60 if (EFI_ERROR(Status
)) {
61 if (Status
== EFI_VOLUME_CORRUPTED
&& ProblemParam
!= NULL
) {
62 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_GEN_PROBLEM
), gShellLevel2HiiHandle
, ProblemParam
);
63 FreePool(ProblemParam
);
64 ShellStatus
= SHELL_INVALID_PARAMETER
;
73 if (ShellCommandLineGetFlag(Package
, L
"-?")) {
75 } else if (ShellCommandLineGetRawValue(Package
, 2) != NULL
) {
76 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_GEN_TOO_MANY
), gShellLevel2HiiHandle
);
77 ShellStatus
= SHELL_INVALID_PARAMETER
;
80 // remember that param 0 is the command name
81 // If there are 0 value parameters, then print the current directory
82 // else If there are 2 value parameters, then print the error message
83 // else If there is 1 value paramerer , then change the directory
85 Param1
= ShellCommandLineGetRawValue(Package
, 1);
88 // display the current directory
90 Directory
= ShellGetCurrentDir(NULL
);
91 if (Directory
!= NULL
) {
92 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_CD_PRINT
), gShellLevel2HiiHandle
, Directory
);
94 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_GEN_NO_CWD
), gShellLevel2HiiHandle
);
95 ShellStatus
= SHELL_NOT_FOUND
;
98 Param1Copy
= CatSPrint(NULL
, L
"%s", Param1
, NULL
);
99 if (Param1Copy
!= NULL
) {
100 Param1Copy
= PathCleanUpDirectories(Param1Copy
);
102 if (Param1Copy
!= NULL
) {
103 if (StrCmp(Param1Copy
, L
".") == 0) {
105 // nothing to do... change to current directory
107 } else if (StrCmp(Param1Copy
, L
"..") == 0) {
109 // Change up one directory...
111 Directory
= ShellGetCurrentDir(NULL
);
112 if (Directory
== NULL
) {
113 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_GEN_NO_CWD
), gShellLevel2HiiHandle
);
114 ShellStatus
= SHELL_NOT_FOUND
;
116 Drive
= GetFullyQualifiedPath(Directory
);
117 PathRemoveLastItem(Drive
);
119 if (ShellStatus
== SHELL_SUCCESS
&& Drive
!= NULL
) {
121 // change directory on current drive letter
123 Status
= gEfiShellProtocol
->SetCurDir(NULL
, Drive
);
124 if (Status
== EFI_NOT_FOUND
) {
125 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_CD_NF
), gShellLevel2HiiHandle
);
126 ShellStatus
= SHELL_NOT_FOUND
;
129 } else if (StrCmp(Param1Copy
, L
"\\") == 0) {
131 // Move to root of current drive
133 Directory
= ShellGetCurrentDir(NULL
);
134 if (Directory
== NULL
) {
135 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_GEN_NO_CWD
), gShellLevel2HiiHandle
);
136 ShellStatus
= SHELL_NOT_FOUND
;
138 Drive
= GetFullyQualifiedPath(Directory
);
139 while (PathRemoveLastItem(Drive
)) ;
141 if (ShellStatus
== SHELL_SUCCESS
&& Drive
!= NULL
) {
143 // change directory on current drive letter
145 Status
= gEfiShellProtocol
->SetCurDir(NULL
, Drive
);
146 if (Status
== EFI_NOT_FOUND
) {
147 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_CD_NF
), gShellLevel2HiiHandle
);
148 ShellStatus
= SHELL_NOT_FOUND
;
151 } else if (StrStr(Param1Copy
, L
":") == NULL
) {
153 // change directory without a drive identifier
155 if (ShellGetCurrentDir(NULL
) == NULL
) {
156 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_GEN_NO_CWD
), gShellLevel2HiiHandle
);
157 ShellStatus
= SHELL_NOT_FOUND
;
159 ASSERT((Drive
== NULL
&& DriveSize
== 0) || (Drive
!= NULL
));
160 Drive
= StrnCatGrow(&Drive
, &DriveSize
, ShellGetCurrentDir(NULL
), 0);
161 if (*Param1Copy
== L
'\\') {
162 while (PathRemoveLastItem(Drive
)) ;
163 Drive
= StrnCatGrow(&Drive
, &DriveSize
, Param1Copy
+1, 0);
165 Drive
= StrnCatGrow(&Drive
, &DriveSize
, Param1Copy
, 0);
168 // Verify that this is a valid directory
170 Status
= gEfiShellProtocol
->OpenFileByName(Drive
, &Handle
, EFI_FILE_MODE_READ
);
171 if (EFI_ERROR(Status
)) {
172 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_GEN_DIR_NF
), gShellLevel2HiiHandle
, Drive
);
173 ShellStatus
= SHELL_NOT_FOUND
;
174 } else if (EFI_ERROR(FileHandleIsDirectory(Handle
))) {
175 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_GEN_NOT_DIR
), gShellLevel2HiiHandle
, Drive
);
176 ShellStatus
= SHELL_NOT_FOUND
;
178 if (ShellStatus
== SHELL_SUCCESS
&& Drive
!= NULL
) {
180 // change directory on current drive letter
182 Status
= gEfiShellProtocol
->SetCurDir(NULL
, Drive
);
183 if (Status
== EFI_NOT_FOUND
) {
184 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_CD_NF
), gShellLevel2HiiHandle
);
185 ShellStatus
= SHELL_NOT_FOUND
;
188 if (Handle
!= NULL
) {
189 gEfiShellProtocol
->CloseFile(Handle
);
190 DEBUG_CODE(Handle
= NULL
;);
195 // change directory with a drive letter
197 Drive
= AllocateZeroPool(StrSize(Param1Copy
));
199 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_GEN_NO_MEM
), gShellLevel2HiiHandle
);
200 ShellStatus
= SHELL_OUT_OF_RESOURCES
;
202 Drive
= StrCpy(Drive
, Param1Copy
);
203 Path
= StrStr(Drive
, L
":");
204 ASSERT(Path
!= NULL
);
205 if (EFI_ERROR(ShellIsDirectory(Param1Copy
))) {
206 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_GEN_NOT_DIR
), gShellLevel2HiiHandle
, Param1Copy
);
207 ShellStatus
= SHELL_NOT_FOUND
;
208 } else if (*(Path
+1) == CHAR_NULL
) {
209 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_CD_NF
), gShellLevel2HiiHandle
);
210 ShellStatus
= SHELL_NOT_FOUND
;
212 *(Path
+1) = CHAR_NULL
;
213 if (Path
== Drive
+ StrLen(Drive
)) {
214 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_CD_NF
), gShellLevel2HiiHandle
);
215 ShellStatus
= SHELL_NOT_FOUND
;
217 Status
= gEfiShellProtocol
->SetCurDir(Drive
, Path
+2);
218 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_CD_PRINT
), gShellLevel2HiiHandle
, ShellGetCurrentDir(Drive
));
221 if (Status
== EFI_NOT_FOUND
) {
222 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_CD_NF
), gShellLevel2HiiHandle
);
223 Status
= SHELL_NOT_FOUND
;
224 } else if (EFI_ERROR(Status
)) {
225 ShellPrintHiiEx(-1, -1, NULL
, STRING_TOKEN (STR_GEN_DIR_NF
), gShellLevel2HiiHandle
, Param1Copy
);
226 Status
= SHELL_NOT_FOUND
;
231 FreePool(Param1Copy
);
239 // free the command line package
241 ShellCommandLineFreeVarList (Package
);
246 return (ShellStatus
);