• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /** @file
2 *
3 *  Copyright (c) 2011, ARM Limited. All rights reserved.
4 *  (C) Copyright 2015 Hewlett Packard Enterprise Development LP<BR>
5 *
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
10 *
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.
13 *
14 **/
15 
16 #include "Ebl.h"
17 
18 #include <Guid/GlobalVariable.h>
19 
20 EFI_STATUS
21 EFIAPI
EblGetCmd(IN UINTN Argc,IN CHAR8 ** Argv)22 EblGetCmd (
23   IN UINTN  Argc,
24   IN CHAR8  **Argv
25   )
26 {
27   EFI_STATUS        Status = EFI_INVALID_PARAMETER;
28   UINTN       Size;
29   VOID*       Value;
30   CHAR8*      AsciiVariableName = NULL;
31   CHAR16*     VariableName;
32   UINTN       VariableNameLen;
33   UINT32      Index;
34 
35   if (Argc == 1) {
36     AsciiPrint("Variable name is missing.\n");
37     return Status;
38   }
39 
40   for (Index = 1; Index < Argc; Index++) {
41     if (Argv[Index][0] == '-') {
42       AsciiPrint("Warning: '%a' not recognized.\n",Argv[Index]);
43     } else {
44       AsciiVariableName = Argv[Index];
45     }
46   }
47 
48   if (AsciiVariableName == NULL) {
49     AsciiPrint("Variable name is missing.\n");
50     return Status;
51   } else {
52     VariableNameLen = AsciiStrLen (AsciiVariableName) + 1;
53     VariableName = AllocatePool (VariableNameLen * sizeof (CHAR16));
54     AsciiStrToUnicodeStrS (AsciiVariableName, VariableName, VariableNameLen);
55   }
56 
57   // Try to get the variable size.
58   Value = NULL;
59   Size = 0;
60   Status = gRT->GetVariable (VariableName, &gEfiGlobalVariableGuid, NULL, &Size, Value);
61   if (Status == EFI_NOT_FOUND) {
62     AsciiPrint("Variable name '%s' not found.\n",VariableName);
63   } else if (Status == EFI_BUFFER_TOO_SMALL) {
64     // Get the environment variable value
65     Value = AllocatePool (Size);
66     if (Value == NULL) {
67       return EFI_OUT_OF_RESOURCES;
68     }
69 
70     Status = gRT->GetVariable ((CHAR16 *)VariableName, &gEfiGlobalVariableGuid, NULL, &Size, Value);
71     if (EFI_ERROR (Status)) {
72       AsciiPrint("Error: '%r'\n",Status);
73     } else {
74       AsciiPrint("%a=%a\n",AsciiVariableName,Value);
75     }
76     FreePool(Value);
77   } else {
78     AsciiPrint("Error: '%r'\n",Status);
79   }
80 
81   FreePool(VariableName);
82   return Status;
83 }
84 
85 EFI_STATUS
86 EFIAPI
EblSetCmd(IN UINTN Argc,IN CHAR8 ** Argv)87 EblSetCmd (
88   IN UINTN  Argc,
89   IN CHAR8  **Argv
90   )
91 {
92   EFI_STATUS    Status = EFI_INVALID_PARAMETER;
93   CHAR8*        AsciiVariableSetting = NULL;
94   CHAR8*        AsciiVariableName;
95   CHAR8*        AsciiValue;
96   UINT32        AsciiValueLength;
97   CHAR16*       VariableName;
98   UINTN         VariableNameLen;
99   UINT32        Index;
100   UINT32        EscapedQuotes = 0;
101   BOOLEAN       Volatile = FALSE;
102 
103   if (Argc == 1) {
104     AsciiPrint("Variable name is missing.\n");
105     return Status;
106   }
107 
108   for (Index = 1; Index < Argc; Index++) {
109     if (AsciiStrCmp(Argv[Index],"-v") == 0) {
110       Volatile = 0;
111     } else if (Argv[Index][0] == '-') {
112       AsciiPrint("Warning: '%a' not recognized.\n",Argv[Index]);
113     } else {
114       AsciiVariableSetting = Argv[Index];
115     }
116   }
117 
118   if (AsciiVariableSetting == NULL) {
119     AsciiPrint("Variable name is missing.\n");
120     return Status;
121   }
122 
123   // Check if it is a valid variable setting
124   AsciiValue = AsciiStrStr (AsciiVariableSetting,"=");
125   if (AsciiValue == NULL) {
126     //
127     // There is no value. It means this variable will be deleted
128     //
129 
130     // Convert VariableName into Unicode
131     VariableNameLen = AsciiStrLen (AsciiVariableSetting) + 1;
132     VariableName = AllocatePool (VariableNameLen * sizeof (CHAR16));
133     AsciiStrToUnicodeStrS (AsciiVariableSetting, VariableName, VariableNameLen);
134 
135     Status = gRT->SetVariable (
136                           VariableName,
137                           &gEfiGlobalVariableGuid,
138                           ( !Volatile ? EFI_VARIABLE_NON_VOLATILE : 0) |
139                           EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS,
140                           0,
141                           NULL
142                           );
143     if (!EFI_ERROR(Status)) {
144       AsciiPrint("Variable '%s' deleted\n",VariableName);
145     } else {
146       AsciiPrint("Variable setting is incorrect. It should be VariableName=Value\n");
147     }
148     return Status;
149   }
150 
151   AsciiValue[0] = '\0';
152   AsciiVariableName = AsciiVariableSetting;
153   AsciiValue++;
154 
155   // Clean AsciiValue from quote
156   if (AsciiValue[0] == '"') {
157     AsciiValue++;
158   }
159   AsciiValueLength = AsciiStrLen (AsciiValue);
160   if ((AsciiValue[AsciiValueLength-2] != '\\') && (AsciiValue[AsciiValueLength-1] == '"')) {
161     AsciiValue[AsciiValueLength-1] = '\0';
162   }
163 
164   // Clean AsciiValue from escaped quotes
165   for (Index = 0; Index < AsciiValueLength; Index++) {
166     if ((Index > 0) && (AsciiValue[Index-1] == '\\') && (AsciiValue[Index] == '"')) {
167       EscapedQuotes++;
168     }
169     AsciiValue[Index-EscapedQuotes] = AsciiValue[Index];
170   }
171   // Fill the end of the value with '\0'
172   for (Index = 0; Index < EscapedQuotes; Index++) {
173     AsciiValue[AsciiValueLength-1-Index] = '\0';
174   }
175 
176   // Convert VariableName into Unicode
177   VariableNameLen = AsciiStrLen (AsciiVariableName) + 1;
178   VariableName = AllocatePool (VariableNameLen * sizeof (CHAR16));
179   AsciiStrToUnicodeStrS (AsciiVariableName, VariableName, VariableNameLen);
180 
181   Status = gRT->SetVariable (
182                       VariableName,
183                       &gEfiGlobalVariableGuid,
184                       ( !Volatile ? EFI_VARIABLE_NON_VOLATILE : 0) |
185                       EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS,
186                       AsciiStrLen (AsciiValue)+1,
187                       AsciiValue
188                       );
189   if (!EFI_ERROR(Status)) {
190     AsciiPrint("'%a'='%a'\n",AsciiVariableName,AsciiValue);
191   }
192 
193   return Status;
194 }
195 
196 GLOBAL_REMOVE_IF_UNREFERENCED const EBL_COMMAND_TABLE mCmdVariableTemplate[] =
197 {
198   {
199     "get",
200     " ; get UEFI variable\n\r   [v]; verbose",
201     NULL,
202     EblGetCmd
203   },
204   {
205     "set",
206     " ; set UEFI variable\n\r   [v]; create volatile variable",
207     NULL,
208     EblSetCmd
209   }
210 };
211 
212 /**
213   Initialize the commands in this in this file
214 **/
215 VOID
EblInitializeVariableCmds(VOID)216 EblInitializeVariableCmds (
217   VOID
218   )
219 {
220   EblAddCommands (mCmdVariableTemplate, sizeof (mCmdVariableTemplate)/sizeof (EBL_COMMAND_TABLE));
221 }
222