1 /** @file
2 
3   Vfr common library functions.
4 
5 Copyright (c) 2004 - 2013, 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
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 #ifndef _VFRUTILITYLIB_H_
17 #define _VFRUTILITYLIB_H_
18 
19 #include "string.h"
20 #include "Common/UefiBaseTypes.h"
21 #include "EfiVfr.h"
22 #include "VfrError.h"
23 
24 extern BOOLEAN  VfrCompatibleMode;
25 
26 #define MAX_NAME_LEN                       64
27 #define MAX_STRING_LEN                     0x100
28 #define DEFAULT_ALIGN                      1
29 #define DEFAULT_PACK_ALIGN                 0x8
30 #define DEFAULT_NAME_TABLE_ITEMS           1024
31 
32 #define EFI_BITS_SHIFT_PER_UINT32          0x5
33 #define EFI_BITS_PER_UINT32                (1 << EFI_BITS_SHIFT_PER_UINT32)
34 
35 #define BUFFER_SAFE_FREE(Buf)              do { if ((Buf) != NULL) { delete (Buf); } } while (0);
36 
37 class CVfrBinaryOutput {
38 public:
39   virtual VOID WriteLine (IN FILE *, IN UINT32, IN CONST CHAR8 *, IN CHAR8 *, IN UINT32);
40   virtual VOID WriteEnd (IN FILE *, IN UINT32, IN CONST CHAR8 *, IN CHAR8 *, IN UINT32);
41 };
42 
43 UINT32
44 _STR2U32 (
45   IN CHAR8 *Str
46   );
47 
48 struct SConfigInfo {
49   UINT16             mOffset;
50   UINT16             mWidth;
51   UINT8              *mValue;
52   SConfigInfo        *mNext;
53 
54   SConfigInfo (IN UINT8, IN UINT16, IN UINT32, IN EFI_IFR_TYPE_VALUE);
55   ~SConfigInfo (VOID);
56 };
57 
58 struct SConfigItem {
59   CHAR8         *mName;         // varstore name
60   EFI_GUID      *mGuid;         // varstore guid, varstore name + guid deside one varstore
61   CHAR8         *mId;           // default ID
62   SConfigInfo   *mInfoStrList;  // list of Offset/Value in the varstore
63   SConfigItem   *mNext;
64 
65 public:
66   SConfigItem (IN CHAR8 *, IN EFI_GUID *, IN CHAR8 *);
67   SConfigItem (IN CHAR8 *, IN EFI_GUID *, IN CHAR8 *, IN UINT8, IN UINT16, IN UINT16, IN EFI_IFR_TYPE_VALUE);
68   virtual ~SConfigItem ();
69 };
70 
71 class CVfrBufferConfig {
72 private:
73   SConfigItem *mItemListHead;
74   SConfigItem *mItemListTail;
75   SConfigItem *mItemListPos;
76 
77 public:
78   CVfrBufferConfig (VOID);
79   virtual ~CVfrBufferConfig (VOID);
80 
81   virtual UINT8   Register (IN CHAR8 *, IN EFI_GUID *,IN CHAR8 *Info = NULL);
82   virtual VOID    Open (VOID);
83   virtual BOOLEAN Eof(VOID);
84   virtual UINT8   Select (IN CHAR8 *, IN EFI_GUID *, IN CHAR8 *Info = NULL);
85   virtual UINT8   Write (IN CONST CHAR8, IN CHAR8 *, IN EFI_GUID *, IN CHAR8 *, IN UINT8, IN UINT16, IN UINT32, IN EFI_IFR_TYPE_VALUE);
86 #if 0
87   virtual UINT8   Read (OUT CHAR8 **, OUT CHAR8 **, OUT CHAR8 **, OUT CHAR8 **, OUT CHAR8 **);
88 #endif
89   virtual VOID    Close (VOID);
90   virtual VOID    OutputCFile (IN FILE *, IN CHAR8 *);
91 };
92 
93 extern CVfrBufferConfig gCVfrBufferConfig;
94 
95 #define ALIGN_STUFF(Size, Align) ((Align) - (Size) % (Align))
96 #define INVALID_ARRAY_INDEX      0xFFFFFFFF
97 
98 struct SVfrDataType;
99 
100 struct SVfrDataField {
101   CHAR8                     mFieldName[MAX_NAME_LEN];
102   SVfrDataType              *mFieldType;
103   UINT32                    mOffset;
104   UINT32                    mArrayNum;
105   SVfrDataField             *mNext;
106 };
107 
108 struct SVfrDataType {
109   CHAR8                     mTypeName[MAX_NAME_LEN];
110   UINT8                     mType;
111   UINT32                    mAlign;
112   UINT32                    mTotalSize;
113   SVfrDataField             *mMembers;
114   SVfrDataType              *mNext;
115 };
116 
117 #define VFR_PACK_ASSIGN     0x01
118 #define VFR_PACK_SHOW       0x02
119 #define VFR_PACK_PUSH       0x04
120 #define VFR_PACK_POP        0x08
121 
122 #define PACKSTACK_MAX_SIZE  0x400
123 
124 struct SVfrPackStackNode {
125   CHAR8                     *mIdentifier;
126   UINT32                    mNumber;
127   SVfrPackStackNode         *mNext;
128 
SVfrPackStackNodeSVfrPackStackNode129   SVfrPackStackNode (IN CHAR8 *Identifier, IN UINT32 Number) {
130     mIdentifier = NULL;
131     mNumber     = Number;
132     mNext       = NULL;
133 
134     if (Identifier != NULL) {
135       mIdentifier = new CHAR8[strlen (Identifier) + 1];
136       strcpy (mIdentifier, Identifier);
137     }
138   }
139 
~SVfrPackStackNodeSVfrPackStackNode140   ~SVfrPackStackNode (VOID) {
141     if (mIdentifier != NULL) {
142       delete mIdentifier;
143     }
144     mNext = NULL;
145   }
146 
MatchSVfrPackStackNode147   bool Match (IN CHAR8 *Identifier) {
148     if (Identifier == NULL) {
149       return TRUE;
150     } else if (mIdentifier == NULL) {
151       return FALSE;
152     } else if (strcmp (Identifier, mIdentifier) == 0) {
153       return TRUE;
154     } else {
155       return FALSE;
156     }
157   }
158 };
159 
160 class CVfrVarDataTypeDB {
161 private:
162   UINT32                    mPackAlign;
163   SVfrPackStackNode         *mPackStack;
164 
165 public:
166   EFI_VFR_RETURN_CODE       Pack (IN UINT32, IN UINT8, IN CHAR8 *Identifier = NULL, IN UINT32 Number = DEFAULT_PACK_ALIGN);
167 
168 private:
169   SVfrDataType              *mDataTypeList;
170 
171   SVfrDataType              *mNewDataType;
172   SVfrDataType              *mCurrDataType;
173   SVfrDataField             *mCurrDataField;
174 
175   VOID InternalTypesListInit (VOID);
176   VOID RegisterNewType (IN SVfrDataType *);
177 
178   EFI_VFR_RETURN_CODE ExtractStructTypeName (IN CHAR8 *&, OUT CHAR8 *);
179   EFI_VFR_RETURN_CODE GetTypeField (IN CONST CHAR8 *, IN SVfrDataType *, IN SVfrDataField *&);
180   EFI_VFR_RETURN_CODE GetFieldOffset (IN SVfrDataField *, IN UINT32, OUT UINT32 &);
181   UINT8               GetFieldWidth (IN SVfrDataField *);
182   UINT32              GetFieldSize (IN SVfrDataField *, IN UINT32);
183 
184 public:
185   CVfrVarDataTypeDB (VOID);
186   ~CVfrVarDataTypeDB (VOID);
187 
188   VOID                DeclareDataTypeBegin (VOID);
189   EFI_VFR_RETURN_CODE SetNewTypeName (IN CHAR8 *);
190   EFI_VFR_RETURN_CODE DataTypeAddField (IN CHAR8 *, IN CHAR8 *, IN UINT32);
191   VOID                DeclareDataTypeEnd (VOID);
192 
193   EFI_VFR_RETURN_CODE GetDataType (IN CHAR8 *, OUT SVfrDataType **);
194   EFI_VFR_RETURN_CODE GetDataTypeSize (IN CHAR8 *, OUT UINT32 *);
195   EFI_VFR_RETURN_CODE GetDataTypeSize (IN UINT8, OUT UINT32 *);
196   EFI_VFR_RETURN_CODE GetDataFieldInfo (IN CHAR8 *, OUT UINT16 &, OUT UINT8 &, OUT UINT32 &);
197 
198   EFI_VFR_RETURN_CODE GetUserDefinedTypeNameList (OUT CHAR8 ***, OUT UINT32 *);
199   EFI_VFR_RETURN_CODE ExtractFieldNameAndArrary (IN CHAR8 *&, OUT CHAR8 *, OUT UINT32 &);
200 
201   BOOLEAN             IsTypeNameDefined (IN CHAR8 *);
202 
203   VOID                Dump(IN FILE *);
204   //
205   // First the declared
206   //
207   CHAR8               *mFirstNewDataTypeName;
208 #ifdef CVFR_VARDATATYPEDB_DEBUG
209   VOID ParserDB ();
210 #endif
211 };
212 
213 extern CVfrVarDataTypeDB  gCVfrVarDataTypeDB;
214 
215 typedef enum {
216   EFI_VFR_VARSTORE_INVALID,
217   EFI_VFR_VARSTORE_BUFFER,
218   EFI_VFR_VARSTORE_EFI,
219   EFI_VFR_VARSTORE_NAME
220 } EFI_VFR_VARSTORE_TYPE;
221 
222 struct SVfrVarStorageNode {
223   EFI_GUID                  mGuid;
224   CHAR8                     *mVarStoreName;
225   EFI_VARSTORE_ID           mVarStoreId;
226   BOOLEAN                   mAssignedFlag; //Create varstore opcode
227   struct SVfrVarStorageNode *mNext;
228 
229   EFI_VFR_VARSTORE_TYPE     mVarStoreType;
230   union {
231     // EFI Variable
232     struct {
233       EFI_STRING_ID           mEfiVarName;
234       UINT32                  mEfiVarSize;
235     } mEfiVar;
236 
237     // Buffer Storage
238     SVfrDataType            *mDataType;
239 
240     // NameValue Storage
241 	struct {
242       EFI_STRING_ID         *mNameTable;
243       UINT32                mTableSize;
244     } mNameSpace;
245   } mStorageInfo;
246 
247 public:
248   SVfrVarStorageNode (IN EFI_GUID *, IN CHAR8 *, IN EFI_VARSTORE_ID, IN EFI_STRING_ID, IN UINT32, IN BOOLEAN Flag = TRUE);
249   SVfrVarStorageNode (IN EFI_GUID *, IN CHAR8 *, IN EFI_VARSTORE_ID, IN SVfrDataType *, IN BOOLEAN Flag = TRUE);
250   SVfrVarStorageNode (IN CHAR8 *, IN EFI_VARSTORE_ID);
251   ~SVfrVarStorageNode (VOID);
252 };
253 
254 struct EFI_VARSTORE_INFO {
255   EFI_VARSTORE_ID           mVarStoreId;
256   union {
257     EFI_STRING_ID           mVarName;
258     UINT16                  mVarOffset;
259   } mInfo;
260   UINT8                     mVarType;
261   UINT32                    mVarTotalSize;
262 
263   EFI_VARSTORE_INFO (VOID);
264   EFI_VARSTORE_INFO (IN EFI_VARSTORE_INFO &);
265   BOOLEAN operator == (IN EFI_VARSTORE_INFO *);
266 };
267 
268 #define EFI_VARSTORE_ID_MAX              0xFFFF
269 #define EFI_FREE_VARSTORE_ID_BITMAP_SIZE ((EFI_VARSTORE_ID_MAX + 1) / EFI_BITS_PER_UINT32)
270 
271 class CVfrDataStorage {
272 private:
273   UINT32                    mFreeVarStoreIdBitMap[EFI_FREE_VARSTORE_ID_BITMAP_SIZE];
274 
275   struct SVfrVarStorageNode *mBufferVarStoreList;
276   struct SVfrVarStorageNode *mEfiVarStoreList;
277   struct SVfrVarStorageNode *mNameVarStoreList;
278 
279   struct SVfrVarStorageNode *mCurrVarStorageNode;
280   struct SVfrVarStorageNode *mNewVarStorageNode;
281 
282 private:
283 
284   EFI_VARSTORE_ID GetFreeVarStoreId (EFI_VFR_VARSTORE_TYPE VarType = EFI_VFR_VARSTORE_BUFFER);
285   BOOLEAN         ChekVarStoreIdFree (IN EFI_VARSTORE_ID);
286   VOID            MarkVarStoreIdUsed (IN EFI_VARSTORE_ID);
287   VOID            MarkVarStoreIdUnused (IN EFI_VARSTORE_ID);
288   EFI_VARSTORE_ID CheckGuidField (IN SVfrVarStorageNode *,
289                                   IN EFI_GUID *,
290                                   IN BOOLEAN *,
291                                   OUT EFI_VFR_RETURN_CODE *);
292 
293 public:
294   CVfrDataStorage ();
295   ~CVfrDataStorage ();
296 
GetBufferVarStoreList()297   SVfrVarStorageNode * GetBufferVarStoreList () {
298     return mBufferVarStoreList;
299   }
GetEfiVarStoreList()300   SVfrVarStorageNode * GetEfiVarStoreList () {
301     return mEfiVarStoreList;
302   }
303   EFI_VFR_RETURN_CODE DeclareNameVarStoreBegin (CHAR8 *, EFI_VARSTORE_ID);
304   EFI_VFR_RETURN_CODE NameTableAddItem (EFI_STRING_ID);
305   EFI_VFR_RETURN_CODE DeclareNameVarStoreEnd (EFI_GUID *);
306 
307   EFI_VFR_RETURN_CODE DeclareEfiVarStore (IN CHAR8 *, IN EFI_GUID *, IN EFI_STRING_ID, IN UINT32, IN BOOLEAN Flag = TRUE);
308 
309   EFI_VFR_RETURN_CODE DeclareBufferVarStore (IN CHAR8 *, IN EFI_GUID *, IN CVfrVarDataTypeDB *, IN CHAR8 *, IN EFI_VARSTORE_ID, IN BOOLEAN Flag = TRUE);
310 
311   EFI_VFR_RETURN_CODE GetVarStoreId (IN CHAR8 *, OUT EFI_VARSTORE_ID *, IN EFI_GUID *VarGuid = NULL);
312   EFI_VFR_VARSTORE_TYPE GetVarStoreType (IN EFI_VARSTORE_ID);
313   EFI_GUID *          GetVarStoreGuid (IN  EFI_VARSTORE_ID);
314   EFI_VFR_RETURN_CODE GetVarStoreName (IN EFI_VARSTORE_ID, OUT CHAR8 **);
315   EFI_VFR_RETURN_CODE GetVarStoreByDataType (IN CHAR8 *, OUT SVfrVarStorageNode **, IN EFI_GUID *VarGuid = NULL);
316 
317   EFI_VFR_RETURN_CODE GetBufferVarStoreDataTypeName (IN EFI_VARSTORE_ID, OUT CHAR8 **);
318   EFI_VFR_RETURN_CODE GetEfiVarStoreInfo (IN EFI_VARSTORE_INFO *);
319   EFI_VFR_RETURN_CODE GetNameVarStoreInfo (IN EFI_VARSTORE_INFO *, IN UINT32);
320 };
321 
322 #define EFI_QUESTION_ID_MAX              0xFFFF
323 #define EFI_FREE_QUESTION_ID_BITMAP_SIZE ((EFI_QUESTION_ID_MAX + 1) / EFI_BITS_PER_UINT32)
324 #define EFI_QUESTION_ID_INVALID          0x0
325 
326 #define DATE_YEAR_BITMASK                0x0000FFFF
327 #define DATE_MONTH_BITMASK               0x00FF0000
328 #define DATE_DAY_BITMASK                 0xFF000000
329 #define TIME_HOUR_BITMASK                0x000000FF
330 #define TIME_MINUTE_BITMASK              0x0000FF00
331 #define TIME_SECOND_BITMASK              0x00FF0000
332 
333 struct SVfrQuestionNode {
334   CHAR8                     *mName;
335   CHAR8                     *mVarIdStr;
336   EFI_QUESTION_ID           mQuestionId;
337   UINT32                    mBitMask;
338   SVfrQuestionNode          *mNext;
339   EFI_QUESION_TYPE          mQtype;
340 
341   SVfrQuestionNode (IN CHAR8 *, IN CHAR8 *, IN UINT32 BitMask = 0);
342   ~SVfrQuestionNode ();
343 };
344 
345 class CVfrQuestionDB {
346 private:
347   SVfrQuestionNode          *mQuestionList;
348   UINT32                    mFreeQIdBitMap[EFI_FREE_QUESTION_ID_BITMAP_SIZE];
349 
350 private:
351   EFI_QUESTION_ID GetFreeQuestionId (VOID);
352   BOOLEAN         ChekQuestionIdFree (IN EFI_QUESTION_ID);
353   VOID            MarkQuestionIdUsed (IN EFI_QUESTION_ID);
354   VOID            MarkQuestionIdUnused (IN EFI_QUESTION_ID);
355 
356 public:
357   CVfrQuestionDB ();
358   ~CVfrQuestionDB();
359 
360   EFI_VFR_RETURN_CODE RegisterQuestion (IN CHAR8 *, IN CHAR8 *, IN OUT EFI_QUESTION_ID &);
361   VOID                RegisterOldDateQuestion (IN CHAR8 *, IN CHAR8 *, IN CHAR8 *, IN OUT EFI_QUESTION_ID &);
362   VOID                RegisterNewDateQuestion (IN CHAR8 *, IN CHAR8 *, IN OUT EFI_QUESTION_ID &);
363   VOID                RegisterOldTimeQuestion (IN CHAR8 *, IN CHAR8 *, IN CHAR8 *, IN OUT EFI_QUESTION_ID &);
364   VOID                RegisterNewTimeQuestion (IN CHAR8 *, IN CHAR8 *, IN OUT EFI_QUESTION_ID &);
365   VOID                RegisterRefQuestion (IN CHAR8 *, IN CHAR8 *, IN OUT EFI_QUESTION_ID &);
366   EFI_VFR_RETURN_CODE UpdateQuestionId (IN EFI_QUESTION_ID, IN EFI_QUESTION_ID);
367   VOID                GetQuestionId (IN CHAR8 *, IN CHAR8 *, OUT EFI_QUESTION_ID &, OUT UINT32 &, OUT EFI_QUESION_TYPE *QType = NULL);
368   EFI_VFR_RETURN_CODE FindQuestion (IN EFI_QUESTION_ID);
369   EFI_VFR_RETURN_CODE FindQuestion (IN CHAR8 *);
370   VOID                PrintAllQuestion (IN VOID);
371   VOID                ResetInit (IN VOID);
372 
SetCompatibleMode(IN BOOLEAN Mode)373   VOID SetCompatibleMode (IN BOOLEAN Mode) {
374     VfrCompatibleMode = Mode;
375   }
376 };
377 
378 struct SVfrDefaultStoreNode {
379   EFI_IFR_DEFAULTSTORE      *mObjBinAddr;
380   CHAR8                     *mRefName;
381   EFI_STRING_ID             mDefaultStoreNameId;
382   UINT16                    mDefaultId;
383 
384   SVfrDefaultStoreNode      *mNext;
385 
386   SVfrDefaultStoreNode (IN EFI_IFR_DEFAULTSTORE *, IN CHAR8 *, IN EFI_STRING_ID, IN UINT16);
387   ~SVfrDefaultStoreNode();
388 };
389 
390 class CVfrDefaultStore {
391 private:
392   SVfrDefaultStoreNode      *mDefaultStoreList;
393 
394 public:
395   CVfrDefaultStore ();
396   ~CVfrDefaultStore ();
397 
398   EFI_VFR_RETURN_CODE RegisterDefaultStore (IN CHAR8 *, IN CHAR8 *, IN EFI_STRING_ID, IN UINT16);
399   EFI_VFR_RETURN_CODE ReRegisterDefaultStoreById (IN UINT16, IN CHAR8 *, IN EFI_STRING_ID);
400   BOOLEAN             DefaultIdRegistered (IN UINT16);
401   EFI_VFR_RETURN_CODE GetDefaultId (IN CHAR8 *, OUT UINT16 *);
402   EFI_VFR_RETURN_CODE BufferVarStoreAltConfigAdd (IN EFI_VARSTORE_ID, IN EFI_VARSTORE_INFO &, IN CHAR8 *, IN EFI_GUID *, IN UINT8, IN EFI_IFR_TYPE_VALUE);
403 };
404 
405 #define EFI_RULE_ID_START    0x01
406 #define EFI_RULE_ID_INVALID  0x00
407 
408 struct SVfrRuleNode {
409   UINT8                     mRuleId;
410   CHAR8                     *mRuleName;
411   SVfrRuleNode              *mNext;
412 
413   SVfrRuleNode(IN CHAR8 *, IN UINT8);
414   ~SVfrRuleNode();
415 };
416 
417 class CVfrRulesDB {
418 private:
419   SVfrRuleNode              *mRuleList;
420   UINT8                     mFreeRuleId;
421 
422 public:
423   CVfrRulesDB ();
424   ~CVfrRulesDB();
425 
426   VOID RegisterRule (IN CHAR8 *);
427   UINT8 GetRuleId (IN CHAR8 *);
428 };
429 
430 class CVfrStringDB {
431 private:
432   CHAR8   *mStringFileName;
433 
434   EFI_STATUS FindStringBlock (
435     IN  UINT8            *StringData,
436     IN  EFI_STRING_ID    StringId,
437     OUT UINT32           *StringTextOffset,
438     OUT UINT8            *BlockType
439     );
440 
441   UINT32 GetUnicodeStringTextSize (
442     IN  UINT8            *StringSrc
443     );
444 
445   BOOLEAN GetBestLanguage (
446     IN CONST CHAR8  *SupportedLanguages,
447     IN CHAR8        *Language
448     );
449 
450 public:
451   CVfrStringDB ();
452   ~CVfrStringDB ();
453 
454   VOID SetStringFileName (
455     IN CHAR8 *StringFileName
456     );
457 
458   CHAR8 * GetVarStoreNameFormStringId (
459     IN EFI_STRING_ID StringId
460     );
461 
462 };
463 
464 #endif
465