Add example of Name/Value pair var store to DriverSample
authorlgao4 <lgao4@6f19259b-4bc3-4df7-8a09-765794883524>
Thu, 11 Feb 2010 01:59:35 +0000 (01:59 +0000)
committerlgao4 <lgao4@6f19259b-4bc3-4df7-8a09-765794883524>
Thu, 11 Feb 2010 01:59:35 +0000 (01:59 +0000)
git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk@9975 6f19259b-4bc3-4df7-8a09-765794883524

edk2/MdeModulePkg/Universal/DriverSampleDxe/DriverSample.c
edk2/MdeModulePkg/Universal/DriverSampleDxe/DriverSample.h
edk2/MdeModulePkg/Universal/DriverSampleDxe/NVDataStruc.h
edk2/MdeModulePkg/Universal/DriverSampleDxe/Vfr.vfr
edk2/MdeModulePkg/Universal/DriverSampleDxe/VfrStrings.uni

index 3912946..52d9b83 100644 (file)
@@ -301,6 +301,38 @@ SetPassword (
   return Status;\r
 }\r
 \r
+/**\r
+ Update names of Name/Value storage to current language.\r
+\r
+ @param PrivateData   Points to the driver private data.\r
+\r
+ @retval EFI_SUCCESS   All names are successfully updated.\r
+ @retval EFI_NOT_FOUND Failed to get Name from HII database.\r
+\r
+**/\r
+EFI_STATUS\r
+LoadNameValueNames (\r
+  IN DRIVER_SAMPLE_PRIVATE_DATA      *PrivateData\r
+  )\r
+{\r
+  UINTN      Index;\r
+\r
+  //\r
+  // Get Name/Value name string of current language\r
+  //\r
+  for (Index = 0; Index < NAME_VALUE_NAME_NUMBER; Index++) {\r
+    PrivateData->NameValueName[Index] = HiiGetString (\r
+                                         PrivateData->HiiHandle[0],\r
+                                         PrivateData->NameStringId[Index],\r
+                                         NULL\r
+                                         );\r
+    if (PrivateData->NameValueName[Index] == NULL) {\r
+      return EFI_NOT_FOUND;\r
+    }\r
+  }\r
+\r
+  return EFI_SUCCESS;\r
+}\r
 \r
 /**\r
   This function allows a caller to extract the current configuration for one\r
@@ -344,6 +376,11 @@ ExtractConfig (
   EFI_STRING                       ConfigRequest;\r
   EFI_STRING                       ConfigRequestHdr;\r
   UINTN                            Size;\r
+  EFI_STRING                       Value;\r
+  UINTN                            ValueStrLen;\r
+  CHAR16                           BackupChar;\r
+  CHAR16                           *StrPointer;\r
+\r
 \r
   if (Progress == NULL || Results == NULL || Request == NULL) {\r
     return EFI_INVALID_PARAMETER;\r
@@ -394,10 +431,96 @@ ExtractConfig (
     // Check routing data in <ConfigHdr>.\r
     // Note: if only one Storage is used, then this checking could be skipped.\r
     //\r
-    if (!HiiIsConfigHdrMatch (Request, &mFormSetGuid, VariableName)) {\r
+    if (!HiiIsConfigHdrMatch (Request, &mFormSetGuid, NULL)) {\r
       return EFI_NOT_FOUND;\r
     }\r
     ConfigRequest = Request;\r
+\r
+    //\r
+    // Check if requesting Name/Value storage\r
+    //\r
+    if (StrStr (Request, L"OFFSET") == NULL) {\r
+      //\r
+      // Update Name/Value storage Names\r
+      //\r
+      Status = LoadNameValueNames (PrivateData);\r
+      if (EFI_ERROR (Status)) {\r
+        return Status;\r
+      }\r
+\r
+      //\r
+      // Allocate memory for <ConfigResp>, e.g. Name0=0x11, Name1=0x1234, Name2="ABCD"\r
+      // <Request>   ::=<ConfigHdr>&Name0&Name1&Name2\r
+      // <ConfigResp>::=<ConfigHdr>&Name0=11&Name1=1234&Name2=0041004200430044\r
+      //\r
+      BufferSize = (StrLen (Request) +\r
+        1 + sizeof (PrivateData->Configuration.NameValueVar0) * 2 +\r
+        1 + sizeof (PrivateData->Configuration.NameValueVar1) * 2 +\r
+        1 + sizeof (PrivateData->Configuration.NameValueVar2) * 2 + 1) * sizeof (CHAR16);\r
+      *Results = AllocateZeroPool (BufferSize);\r
+      ASSERT (*Results != NULL);\r
+      StrCpy (*Results, Request);\r
+      Value = *Results;\r
+\r
+      //\r
+      // Append value of NameValueVar0, type is UINT8\r
+      //\r
+      if ((Value = StrStr (*Results, PrivateData->NameValueName[0])) != NULL) {\r
+        Value += StrLen (PrivateData->NameValueName[0]);\r
+        ValueStrLen = ((sizeof (PrivateData->Configuration.NameValueVar0) * 2) + 1);\r
+        CopyMem (Value + ValueStrLen, Value, StrSize (Value));\r
+\r
+        BackupChar = Value[ValueStrLen];\r
+        *Value++   = L'=';\r
+        Value += UnicodeValueToString (\r
+                   Value, \r
+                   PREFIX_ZERO | RADIX_HEX, \r
+                   PrivateData->Configuration.NameValueVar0, \r
+                   sizeof (PrivateData->Configuration.NameValueVar0) * 2\r
+                   );\r
+        *Value = BackupChar;\r
+      }\r
+\r
+      //\r
+      // Append value of NameValueVar1, type is UINT16\r
+      //\r
+      if ((Value = StrStr (*Results, PrivateData->NameValueName[1])) != NULL) {\r
+        Value += StrLen (PrivateData->NameValueName[1]);\r
+        ValueStrLen = ((sizeof (PrivateData->Configuration.NameValueVar1) * 2) + 1);\r
+        CopyMem (Value + ValueStrLen, Value, StrSize (Value));\r
+\r
+        BackupChar = Value[ValueStrLen];\r
+        *Value++   = L'=';\r
+        Value += UnicodeValueToString (\r
+                  Value, \r
+                  PREFIX_ZERO | RADIX_HEX, \r
+                  PrivateData->Configuration.NameValueVar1, \r
+                  sizeof (PrivateData->Configuration.NameValueVar1) * 2\r
+                  );\r
+        *Value = BackupChar;\r
+      }\r
+\r
+      //\r
+      // Append value of NameValueVar2, type is CHAR16 *\r
+      //\r
+      if ((Value = StrStr (*Results, PrivateData->NameValueName[2])) != NULL) {\r
+        Value += StrLen (PrivateData->NameValueName[2]);\r
+        ValueStrLen = StrLen (PrivateData->Configuration.NameValueVar2) * 4 + 1;\r
+        CopyMem (Value + ValueStrLen, Value, StrSize (Value));\r
+\r
+        *Value++ = L'=';\r
+        //\r
+        // Convert Unicode String to Config String, e.g. "ABCD" => "0041004200430044"\r
+        //\r
+        StrPointer = (CHAR16 *) PrivateData->Configuration.NameValueVar2;\r
+        for (; *StrPointer != L'\0'; StrPointer++) {\r
+          Value += UnicodeValueToString (Value, PREFIX_ZERO | RADIX_HEX, *StrPointer, 4);\r
+        }\r
+      }\r
+\r
+      Progress = (EFI_STRING *) Request + StrLen (Request);\r
+      return EFI_SUCCESS;\r
+    }\r
   }\r
 \r
   //\r
@@ -451,6 +574,13 @@ RouteConfig (
   UINTN                            BufferSize;\r
   DRIVER_SAMPLE_PRIVATE_DATA       *PrivateData;\r
   EFI_HII_CONFIG_ROUTING_PROTOCOL  *HiiConfigRouting;\r
+  CHAR16                           *Value;\r
+  CHAR16                           *StrPtr;\r
+  CHAR16                           TemStr[5];\r
+  UINT8                            *DataBuffer;\r
+  UINT8                            DigitUint8;\r
+  UINTN                            Index;\r
+  CHAR16                           *StrBuffer;\r
 \r
   if (Configuration == NULL || Progress == NULL) {\r
     return EFI_INVALID_PARAMETER;\r
@@ -464,7 +594,7 @@ RouteConfig (
   // Check routing data in <ConfigHdr>.\r
   // Note: if only one Storage is used, then this checking could be skipped.\r
   //\r
-  if (!HiiIsConfigHdrMatch (Configuration, &mFormSetGuid, VariableName)) {\r
+  if (!HiiIsConfigHdrMatch (Configuration, &mFormSetGuid, NULL)) {\r
     return EFI_NOT_FOUND;\r
   }\r
 \r
@@ -483,6 +613,125 @@ RouteConfig (
     return Status;\r
   }\r
 \r
+  //\r
+  // Check if configuring Name/Value storage\r
+  //\r
+  if (StrStr (Configuration, L"OFFSET") == NULL) {\r
+    //\r
+    // Update Name/Value storage Names\r
+    //\r
+    Status = LoadNameValueNames (PrivateData);\r
+    if (EFI_ERROR (Status)) {\r
+      return Status;\r
+    }\r
+\r
+    //\r
+    // Convert value for NameValueVar0\r
+    //\r
+    if ((Value = StrStr (Configuration, PrivateData->NameValueName[0])) != NULL) {\r
+      //\r
+      // Skip "Name="\r
+      //\r
+      Value += StrLen (PrivateData->NameValueName[0]);\r
+      Value++;\r
+      //\r
+      // Get Value String\r
+      //\r
+      StrPtr = StrStr (Value, L"&");\r
+      if (StrPtr == NULL) {\r
+        StrPtr = Value + StrLen (Value);\r
+      }\r
+      //\r
+      // Convert Value to Buffer data\r
+      //\r
+      DataBuffer = (UINT8 *) &PrivateData->Configuration.NameValueVar0;\r
+      ZeroMem (TemStr, sizeof (TemStr));\r
+      for (Index = 0, StrPtr --; StrPtr >= Value; StrPtr --, Index ++) {\r
+        TemStr[0] = *StrPtr;\r
+        DigitUint8 = (UINT8) StrHexToUint64 (TemStr);\r
+        if ((Index & 1) == 0) {\r
+          DataBuffer [Index/2] = DigitUint8;\r
+        } else {\r
+          DataBuffer [Index/2] = (UINT8) ((UINT8) (DigitUint8 << 4) + DataBuffer [Index/2]);\r
+        }\r
+      }\r
+    }\r
+\r
+    //\r
+    // Convert value for NameValueVar1\r
+    //\r
+    if ((Value = StrStr (Configuration, PrivateData->NameValueName[1])) != NULL) {\r
+      //\r
+      // Skip "Name="\r
+      //\r
+      Value += StrLen (PrivateData->NameValueName[1]);\r
+      Value++;\r
+      //\r
+      // Get Value String\r
+      //\r
+      StrPtr = StrStr (Value, L"&");\r
+      if (StrPtr == NULL) {\r
+        StrPtr = Value + StrLen (Value);\r
+      }\r
+      //\r
+      // Convert Value to Buffer data\r
+      //\r
+      DataBuffer = (UINT8 *) &PrivateData->Configuration.NameValueVar1;\r
+      ZeroMem (TemStr, sizeof (TemStr));\r
+      for (Index = 0, StrPtr --; StrPtr >= Value; StrPtr --, Index ++) {\r
+        TemStr[0] = *StrPtr;\r
+        DigitUint8 = (UINT8) StrHexToUint64 (TemStr);\r
+        if ((Index & 1) == 0) {\r
+          DataBuffer [Index/2] = DigitUint8;\r
+        } else {\r
+          DataBuffer [Index/2] = (UINT8) ((UINT8) (DigitUint8 << 4) + DataBuffer [Index/2]);\r
+        }\r
+      }\r
+    }\r
+\r
+    //\r
+    // Convert value for NameValueVar2\r
+    //\r
+    if ((Value = StrStr (Configuration, PrivateData->NameValueName[2])) != NULL) {\r
+      //\r
+      // Skip "Name="\r
+      //\r
+      Value += StrLen (PrivateData->NameValueName[2]);\r
+      Value++;\r
+      //\r
+      // Get Value String\r
+      //\r
+      StrPtr = StrStr (Value, L"&");\r
+      if (StrPtr == NULL) {\r
+        StrPtr = Value + StrLen (Value);\r
+      }\r
+      //\r
+      // Convert Config String to Unicode String, e.g "0041004200430044" => "ABCD"\r
+      //\r
+      StrBuffer = (CHAR16 *) PrivateData->Configuration.NameValueVar2;\r
+      ZeroMem (TemStr, sizeof (TemStr));\r
+      while (Value < StrPtr) {\r
+        StrnCpy (TemStr, Value, 4);\r
+        *(StrBuffer++) = (CHAR16) StrHexToUint64 (TemStr);\r
+        Value += 4;\r
+      }\r
+      *StrBuffer = L'\0';\r
+    }\r
+\r
+    //\r
+    // Store Buffer Storage back to EFI variable\r
+    //\r
+    Status = gRT->SetVariable(\r
+      VariableName,\r
+      &mFormSetGuid,\r
+      EFI_VARIABLE_NON_VOLATILE | EFI_VARIABLE_BOOTSERVICE_ACCESS,\r
+      sizeof (DRIVER_SAMPLE_CONFIGURATION),\r
+      &PrivateData->Configuration\r
+      );\r
+\r
+    return Status;\r
+  }\r
+\r
   //\r
   // Convert <ConfigResp> to buffer data by helper function ConfigToBlock()\r
   //\r
@@ -1035,6 +1284,7 @@ DriverSampleInit (
                    NULL\r
                    );\r
   if (HiiHandle[1] == NULL) {\r
+    DriverSampleUnload (ImageHandle);\r
     return EFI_OUT_OF_RESOURCES;\r
   }\r
 \r
@@ -1047,9 +1297,19 @@ DriverSampleInit (
   NewString = L"700 Mhz";\r
 \r
   if (HiiSetString (HiiHandle[0], STRING_TOKEN (STR_CPU_STRING2), NewString, NULL) == 0) {\r
+    DriverSampleUnload (ImageHandle);\r
     return EFI_OUT_OF_RESOURCES;\r
   }\r
 \r
+  HiiSetString (HiiHandle[0], 0, NewString, NULL);\r
+\r
+  //\r
+  // Initialize Name/Value name String ID\r
+  //\r
+  PrivateData->NameStringId[0] = STR_NAME_VALUE_VAR_NAME0;\r
+  PrivateData->NameStringId[1] = STR_NAME_VALUE_VAR_NAME1;\r
+  PrivateData->NameStringId[2] = STR_NAME_VALUE_VAR_NAME2;\r
+\r
   //\r
   // Initialize configuration data\r
   //\r
@@ -1138,6 +1398,7 @@ DriverSampleUnload (
   IN EFI_HANDLE  ImageHandle\r
   )\r
 {\r
+  UINTN Index;\r
   if (DriverHandle[0] != NULL) {\r
     gBS->UninstallMultipleProtocolInterfaces (\r
             DriverHandle[0],\r
@@ -1169,6 +1430,11 @@ DriverSampleUnload (
   }\r
 \r
   if (PrivateData != NULL) {\r
+    for (Index = 0; Index < NAME_VALUE_NAME_NUMBER; Index++) {\r
+      if (PrivateData->NameValueName[Index] != NULL) {\r
+        FreePool (PrivateData->NameValueName[Index]);\r
+      }\r
+    }\r
     FreePool (PrivateData);\r
     PrivateData = NULL;\r
   }\r
index ebe40a2..86f41a1 100644 (file)
@@ -47,13 +47,6 @@ Revision History
 \r
 #include "NVDataStruc.h"\r
 \r
-//\r
-// This is the generated <AltResp> for defaults defined in VFR\r
-//\r
-extern UINT8 VfrMyIfrNVDataDefault0000[];\r
-extern UINT8 VfrMyIfrNVDataDefault0001[];\r
-extern UINT8 VfrMyIfrNVDataBlockName[];\r
-\r
 //\r
 // This is the generated IFR binary data for each formset defined in VFR.\r
 // This data array is ready to be used as input of HiiAddPackages() to\r
@@ -72,6 +65,11 @@ extern UINT8  DriverSampleStrings[];
 #define DYNAMIC_ONE_OF_VAR_OFFSET        OFFSET_OF (DRIVER_SAMPLE_CONFIGURATION, DynamicOneof)\r
 #define DYNAMIC_ORDERED_LIST_VAR_OFFSET  OFFSET_OF (DRIVER_SAMPLE_CONFIGURATION, DynamicOrderedList)\r
 \r
+//\r
+// Number of name in Name/Value storage\r
+//\r
+#define NAME_VALUE_NAME_NUMBER       3\r
+\r
 #define DRIVER_SAMPLE_PRIVATE_SIGNATURE SIGNATURE_32 ('D', 'S', 'p', 's')\r
 \r
 typedef struct {\r
@@ -82,6 +80,12 @@ typedef struct {
   DRIVER_SAMPLE_CONFIGURATION      Configuration;\r
   UINT8                            PasswordState;\r
 \r
+  //\r
+  // Name/Value storage Name list\r
+  //\r
+  EFI_STRING_ID                    NameStringId[NAME_VALUE_NAME_NUMBER];\r
+  EFI_STRING                       NameValueName[NAME_VALUE_NAME_NUMBER];\r
+\r
   //\r
   // Consumed protocol\r
   //\r
index bdc4a46..648b6db 100644 (file)
@@ -62,6 +62,10 @@ typedef struct {
   UINT8   DynamicRefresh;\r
   UINT8   DynamicOneof;\r
   UINT8   DynamicOrderedList[5];\r
+  UINT8   Reserved;\r
+  UINT8   NameValueVar0;\r
+  UINT16  NameValueVar1;\r
+  UINT16  NameValueVar2[20];\r
 } DRIVER_SAMPLE_CONFIGURATION;\r
 \r
 //\r
index 8a0a863..bc821a6 100644 (file)
@@ -89,6 +89,15 @@ formset
     varsize   = 1,                                // Size of the EFI variable\r
     guid      = FORMSET_GUID;                     // EFI variable GUID\r
 \r
+  //\r
+  // Define a Name/Value Storage (EFI_IFR_VARSTORE_NAME_VALUE)\r
+  //\r
+  namevaluevarstore MyNameValueVar,                // Define storage reference name in vfr\r
+    name = STRING_TOKEN(STR_NAME_VALUE_VAR_NAME0), // Define Name list of this storage, refer it by MyNameValueVar[0]\r
+    name = STRING_TOKEN(STR_NAME_VALUE_VAR_NAME1), // Define Name list of this storage, refer it by MyNameValueVar[1]\r
+    name = STRING_TOKEN(STR_NAME_VALUE_VAR_NAME2), // Define Name list of this storage, refer it by MyNameValueVar[2]\r
+    guid = FORMSET_GUID;                           // GUID of this Name/Value storage\r
+\r
   defaultstore MyStandardDefault,\r
     prompt      = STRING_TOKEN(STR_STANDARD_DEFAULT_PROMPT),\r
     attribute   = 0x0000;                         // Default ID: 0000 standard default\r
@@ -323,6 +332,41 @@ formset
 \r
     endnumeric;\r
 \r
+    //\r
+    // Define numeric using Name/Value Storage\r
+    //\r
+    numeric varid   = MyNameValueVar[0],     // This numeric take NameValueVar0 as storage\r
+            prompt  = STRING_TOKEN(STR_NAME_VALUE_VAR_NAME0),\r
+            help    = STRING_TOKEN(STR_NAME_VALUE_VAR_NAME0_HELP),\r
+            //\r
+            // Size should be defined for numeric when use Name/Value storage\r
+            // Valid value for numerice size are: NUMERIC_SIZE_1, NUMERIC_SIZE_2, NUMERIC_SIZE_4 and NUMERIC_SIZE_8\r
+            //\r
+            flags   = NUMERIC_SIZE_1,        // Size of this numeric is 1 byte\r
+            minimum = 0,\r
+            maximum = 0xff,\r
+            step    = 0,\r
+    endnumeric;\r
+\r
+    numeric varid   = MyNameValueVar[1],     // This numeric take NameValueVar1 as storage\r
+            prompt  = STRING_TOKEN(STR_NAME_VALUE_VAR_NAME1),\r
+            help    = STRING_TOKEN(STR_NAME_VALUE_VAR_NAME1_HELP),\r
+            flags   = NUMERIC_SIZE_2,        // Size of this numeric is 2 bytes\r
+            minimum = 0,\r
+            maximum = 0xffff,\r
+            step    = 0,\r
+    endnumeric;\r
+\r
+    //\r
+    // Define string using Name/Value Storage\r
+    //\r
+    string    varid    = MyNameValueVar[2],     // This string take NameValueVar2 as storage\r
+              prompt   = STRING_TOKEN(STR_NAME_VALUE_VAR_NAME2),\r
+              help     = STRING_TOKEN(STR_NAME_VALUE_VAR_NAME2_HELP),\r
+              minsize  = 2,\r
+              maxsize  = 0x14,\r
+    endstring;\r
+\r
     label LABEL_1_VALUE;\r
     label LABEL_2_VALUE;\r
 \r
index c687bf7..355538a 100644 (file)
Binary files a/edk2/MdeModulePkg/Universal/DriverSampleDxe/VfrStrings.uni and b/edk2/MdeModulePkg/Universal/DriverSampleDxe/VfrStrings.uni differ