Home | History | Annotate | Download | only in SmBiosMiscDxe
      1 /*++
      2 
      3 Copyright (c) 2009 - 2014, Intel Corporation. All rights reserved.<BR>
      4 
      5   This program and the accompanying materials are licensed and made available under
      6   the terms and conditions of the BSD License that accompanies this distribution.
      7   The full text of the license may be found at
      8   http://opensource.org/licenses/bsd-license.php.
      9 
     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.
     12 
     13 
     14 
     15 Module Name:
     16 
     17   MiscSystemManufacturerFunction.c
     18 
     19 Abstract:
     20 
     21   This driver parses the mMiscSubclassDataTable structure and reports
     22   any generated data.
     23 
     24 --*/
     25 
     26 
     27 #include "CommonHeader.h"
     28 #include "MiscSubclassDriver.h"
     29 #include <Protocol/DxeSmmReadyToLock.h>
     30 #include <Library/NetLib.h>
     31 #include "Library/DebugLib.h"
     32 #include <Uefi/UefiBaseType.h>
     33 #include <Guid/PlatformInfo.h>
     34 
     35 
     36 extern EFI_PLATFORM_INFO_HOB *mPlatformInfo;
     37 
     38 
     39 /**
     40 
     41   Publish the smbios type 1.
     42 
     43   @param Event      Event whose notification function is being invoked (gEfiDxeSmmReadyToLockProtocolGuid).
     44   @param Context    Pointer to the notification functions context, which is implementation dependent.
     45 
     46   @retval None
     47 
     48 **/
     49 EFI_STATUS
     50 EFIAPI
     51 AddSmbiosManuCallback (
     52   IN EFI_EVENT  Event,
     53   IN VOID       *Context
     54   )
     55 {
     56 
     57   CHAR8                             *OptionalStrStart;
     58   UINTN                             ManuStrLen;
     59   UINTN                             VerStrLen;
     60   UINTN                             PdNameStrLen;
     61   UINTN                             SerialNumStrLen;
     62   UINTN                             SkuNumberStrLen;
     63   UINTN				                FamilyNameStrLen;
     64   EFI_STATUS                        Status;
     65   EFI_STRING                        Manufacturer;
     66   EFI_STRING                        ProductName;
     67   EFI_STRING                        Version;
     68   EFI_STRING                        SerialNumber;
     69   EFI_STRING                        SkuNumber;
     70   EFI_STRING			            FamilyName;
     71   STRING_REF                        TokenToGet;
     72   EFI_SMBIOS_HANDLE                 SmbiosHandle;
     73   SMBIOS_TABLE_TYPE1                *SmbiosRecord;
     74   EFI_MISC_SYSTEM_MANUFACTURER      *ForType1InputData;
     75   EFI_SMBIOS_PROTOCOL               *Smbios;
     76   CHAR16                            Buffer[40];
     77 
     78   CHAR16                            *MacStr;
     79   EFI_HANDLE                        *Handles;
     80   UINTN                             BufferSize;
     81   CHAR16                            PlatformNameBuffer[40];
     82 
     83   ForType1InputData = (EFI_MISC_SYSTEM_MANUFACTURER *)Context;
     84 
     85   //
     86   // First check for invalid parameters.
     87   //
     88   if (Context == NULL || mPlatformInfo == NULL) {
     89     return EFI_INVALID_PARAMETER;
     90   }
     91 
     92   Status = gBS->LocateProtocol (&gEfiSmbiosProtocolGuid, NULL, (VOID *) &Smbios);
     93   ASSERT_EFI_ERROR (Status);
     94 
     95 
     96   if (BOARD_ID_MINNOW2_TURBOT == mPlatformInfo->BoardId) {
     97     // Detect the board is Turbot board platform
     98     UnicodeSPrint (PlatformNameBuffer, sizeof (PlatformNameBuffer),L"%s",L"Minnowboard Turbot ");
     99   } else {
    100     UnicodeSPrint (PlatformNameBuffer, sizeof (PlatformNameBuffer),L"%s",L"Minnowboard Max ");
    101   }
    102 
    103   //
    104   // Silicon Steppings
    105   //
    106   switch (PchStepping()) {
    107     case PchA0:
    108       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s%s", PlatformNameBuffer, L"A0 PLATFORM");
    109       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_PRODUCT_NAME), Buffer, NULL);
    110       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s",L"A0");
    111       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_VERSION), Buffer, NULL);
    112       DEBUG ((EFI_D_ERROR, "A0 Stepping Detected\n"));
    113       break;
    114     case PchA1:
    115       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s%s", PlatformNameBuffer, L"A1 PLATFORM");
    116       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_PRODUCT_NAME), Buffer, NULL);
    117       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s",L"A1");
    118       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_VERSION), Buffer, NULL);
    119       DEBUG ((EFI_D_ERROR, "A1 Stepping Detected\n"));
    120       break;
    121     case PchB0:
    122       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s%s", PlatformNameBuffer, L"B0 PLATFORM");
    123       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_PRODUCT_NAME), Buffer, NULL);
    124       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s",L"B0");
    125       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_VERSION), Buffer, NULL);
    126       DEBUG ((EFI_D_ERROR, "B0 Stepping Detected\n"));
    127       break;
    128     case PchB1:
    129       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s%s", PlatformNameBuffer, L"B1 PLATFORM");
    130       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_PRODUCT_NAME), Buffer, NULL);
    131       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s",L"B1");
    132       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_VERSION), Buffer, NULL);
    133       DEBUG ((EFI_D_ERROR, "B1 Stepping Detected\n"));
    134       break;
    135     case PchB2:
    136       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s%s", PlatformNameBuffer, L"B2 PLATFORM");
    137       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_PRODUCT_NAME), Buffer, NULL);
    138       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s",L"B2");
    139       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_VERSION), Buffer, NULL);
    140       DEBUG ((EFI_D_ERROR, "B2 Stepping Detected\n"));
    141       break;
    142     case PchB3:
    143       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s%s", PlatformNameBuffer, L"B3 PLATFORM");
    144       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_PRODUCT_NAME), Buffer, NULL);
    145       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s",L"B3");
    146       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_VERSION), Buffer, NULL);
    147       DEBUG ((EFI_D_ERROR, "B3 Stepping Detected\n"));
    148       break;
    149     case PchC0:
    150       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s%s", PlatformNameBuffer, L"C0 PLATFORM");
    151       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_PRODUCT_NAME), Buffer, NULL);
    152       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s",L"C0");
    153       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_VERSION), Buffer, NULL);
    154       DEBUG ((EFI_D_ERROR, "C0 Stepping Detected\n"));
    155       break;
    156    case PchD0:
    157       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s%s", PlatformNameBuffer, L"D0 PLATFORM");
    158       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_PRODUCT_NAME), Buffer, NULL);
    159       UnicodeSPrint (Buffer, sizeof (Buffer),L"%s",L"D0");
    160       HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_VERSION), Buffer, NULL);
    161       DEBUG ((EFI_D_ERROR, "D0 Stepping Detected\n"));
    162       break;
    163     default:
    164       DEBUG ((EFI_D_ERROR, "Unknow Stepping Detected\n"));
    165       break;
    166     }
    167 
    168   if (BOARD_ID_MINNOW2_TURBOT == mPlatformInfo->BoardId) {
    169     UnicodeSPrint (Buffer, sizeof (Buffer),L"ADI");
    170     HiiSetString(mHiiHandle,STRING_TOKEN(STR_MISC_SYSTEM_MANUFACTURER), Buffer, NULL);
    171   }
    172   TokenToGet = STRING_TOKEN (STR_MISC_SYSTEM_MANUFACTURER);
    173   Manufacturer = SmbiosMiscGetString (TokenToGet);
    174   ManuStrLen = StrLen(Manufacturer);
    175   if (ManuStrLen > SMBIOS_STRING_MAX_LENGTH) {
    176     return EFI_UNSUPPORTED;
    177   }
    178 
    179   TokenToGet = STRING_TOKEN (STR_MISC_SYSTEM_PRODUCT_NAME);
    180   ProductName = SmbiosMiscGetString (TokenToGet);
    181   PdNameStrLen = StrLen(ProductName);
    182   if (PdNameStrLen > SMBIOS_STRING_MAX_LENGTH) {
    183     return EFI_UNSUPPORTED;
    184   }
    185 
    186   TokenToGet = STRING_TOKEN (STR_MISC_SYSTEM_VERSION);
    187   Version = SmbiosMiscGetString (TokenToGet);
    188   VerStrLen = StrLen(Version);
    189   if (VerStrLen > SMBIOS_STRING_MAX_LENGTH) {
    190     return EFI_UNSUPPORTED;
    191   }
    192 
    193   //
    194   //Get handle infomation
    195   //
    196   BufferSize = 0;
    197   Handles = NULL;
    198   Status = gBS->LocateHandle (
    199                   ByProtocol,
    200                   &gEfiSimpleNetworkProtocolGuid,
    201                   NULL,
    202                   &BufferSize,
    203                   Handles
    204                   );
    205 
    206   if (Status == EFI_BUFFER_TOO_SMALL) {
    207   	Handles = AllocateZeroPool(BufferSize);
    208   	if (Handles == NULL) {
    209   		return (EFI_OUT_OF_RESOURCES);
    210   	}
    211   	Status = gBS->LocateHandle(
    212   	                ByProtocol,
    213   	                &gEfiSimpleNetworkProtocolGuid,
    214   	                NULL,
    215   	                &BufferSize,
    216   	                Handles
    217   	                );
    218  }
    219 
    220   //
    221   //Get the MAC string
    222   //
    223   Status = NetLibGetMacString (
    224              *Handles,
    225              NULL,
    226              &MacStr
    227              );
    228   if (EFI_ERROR (Status)) {
    229     return Status;
    230   }
    231   SerialNumber = MacStr;
    232   SerialNumStrLen = StrLen(SerialNumber);
    233   if (SerialNumStrLen > SMBIOS_STRING_MAX_LENGTH) {
    234     return EFI_UNSUPPORTED;
    235   }
    236   TokenToGet = STRING_TOKEN (STR_MISC_SYSTEM_SKU_NUMBER);
    237   SkuNumber = SmbiosMiscGetString (TokenToGet);
    238   SkuNumberStrLen = StrLen(SkuNumber);
    239   if (SkuNumberStrLen > SMBIOS_STRING_MAX_LENGTH) {
    240     return EFI_UNSUPPORTED;
    241   }
    242   TokenToGet = STRING_TOKEN (STR_MISC_SYSTEM_FAMILY_NAME1);
    243   FamilyName = SmbiosMiscGetString (TokenToGet);
    244   FamilyNameStrLen = StrLen(FamilyName);
    245   if (FamilyNameStrLen > SMBIOS_STRING_MAX_LENGTH) {
    246     return EFI_UNSUPPORTED;
    247   }
    248 
    249   //
    250   // Two zeros following the last string.
    251   //
    252   SmbiosRecord = AllocatePool(sizeof (SMBIOS_TABLE_TYPE1) + ManuStrLen + 1 + PdNameStrLen + 1 + VerStrLen + 1 + SerialNumStrLen + 1 + SkuNumberStrLen + 1 + FamilyNameStrLen + 1 + 1);
    253   ZeroMem(SmbiosRecord, sizeof (SMBIOS_TABLE_TYPE1) + ManuStrLen + 1 + PdNameStrLen + 1 + VerStrLen + 1 + SerialNumStrLen + 1 + SkuNumberStrLen + 1 + FamilyNameStrLen + 1 + 1);
    254 
    255   SmbiosRecord->Hdr.Type = EFI_SMBIOS_TYPE_SYSTEM_INFORMATION;
    256   SmbiosRecord->Hdr.Length = sizeof (SMBIOS_TABLE_TYPE1);
    257 
    258   //
    259   // Make handle chosen by smbios protocol.add automatically.
    260   //
    261   SmbiosRecord->Hdr.Handle = 0;
    262 
    263   //
    264   // Manu will be the 1st optional string following the formatted structure.
    265   //
    266   SmbiosRecord->Manufacturer = 1;
    267 
    268   //
    269   // ProductName will be the 2nd optional string following the formatted structure.
    270   //
    271   SmbiosRecord->ProductName = 2;
    272 
    273   //
    274   // Version will be the 3rd optional string following the formatted structure.
    275   //
    276   SmbiosRecord->Version = 3;
    277 
    278   //
    279   // Version will be the 4th optional string following the formatted structure.
    280   //
    281   SmbiosRecord->SerialNumber = 4;
    282 
    283   SmbiosRecord->SKUNumber= 5;
    284   SmbiosRecord->Family= 6;
    285 
    286   //
    287   // Unique UUID
    288   //
    289   ForType1InputData->SystemUuid.Data1 = PcdGet32 (PcdProductSerialNumber);
    290   ForType1InputData->SystemUuid.Data4[0] = PcdGet8 (PcdEmmcManufacturerId);
    291 
    292   CopyMem ((UINT8 *) (&SmbiosRecord->Uuid),&ForType1InputData->SystemUuid,16);
    293 
    294   SmbiosRecord->WakeUpType = (UINT8)ForType1InputData->SystemWakeupType;
    295 
    296   OptionalStrStart = (CHAR8 *)(SmbiosRecord + 1);
    297   UnicodeStrToAsciiStr(Manufacturer, OptionalStrStart);
    298   UnicodeStrToAsciiStr(ProductName, OptionalStrStart + ManuStrLen + 1);
    299   UnicodeStrToAsciiStr(Version, OptionalStrStart + ManuStrLen + 1 + PdNameStrLen + 1);
    300   UnicodeStrToAsciiStr(SerialNumber, OptionalStrStart + ManuStrLen + 1 + PdNameStrLen + 1 + VerStrLen + 1);
    301 
    302   UnicodeStrToAsciiStr(SkuNumber, OptionalStrStart + ManuStrLen + 1 + PdNameStrLen + 1 +  VerStrLen + 1 + SerialNumStrLen + 1);
    303   UnicodeStrToAsciiStr(FamilyName, OptionalStrStart + ManuStrLen + 1 + PdNameStrLen + 1 + VerStrLen + 1 + SerialNumStrLen + 1 + SkuNumberStrLen +1);
    304 
    305   //
    306   // Now we have got the full smbios record, call smbios protocol to add this record.
    307   //
    308   SmbiosHandle = SMBIOS_HANDLE_PI_RESERVED;
    309   Status = Smbios-> Add(
    310                       Smbios,
    311                       NULL,
    312                       &SmbiosHandle,
    313                       (EFI_SMBIOS_TABLE_HEADER *) SmbiosRecord
    314                       );
    315   FreePool(SmbiosRecord);
    316   return Status;
    317 }
    318 
    319 /**
    320   This function makes boot time changes to the contents of the
    321   MiscSystemManufacturer (Type 1).
    322 
    323   @param  RecordData                 Pointer to copy of RecordData from the Data Table.
    324 
    325   @retval EFI_SUCCESS                All parameters were valid.
    326   @retval EFI_UNSUPPORTED            Unexpected RecordType value.
    327   @retval EFI_INVALID_PARAMETER      Invalid parameter was found.
    328 
    329 **/
    330 MISC_SMBIOS_TABLE_FUNCTION(MiscSystemManufacturer)
    331 {
    332   EFI_STATUS                    Status;
    333   static BOOLEAN                CallbackIsInstalledManu = FALSE;
    334   VOID                           *AddSmbiosManuCallbackNotifyReg;
    335   EFI_EVENT                      AddSmbiosManuCallbackEvent;
    336 
    337 
    338   if (CallbackIsInstalledManu == FALSE) {
    339     CallbackIsInstalledManu = TRUE;        	// Prevent more than 1 callback.
    340     DEBUG ((EFI_D_INFO, "Create Smbios Manu callback.\n"));
    341 
    342   //
    343   // gEfiDxeSmmReadyToLockProtocolGuid is ready
    344   //
    345   Status = gBS->CreateEvent (
    346                   EVT_NOTIFY_SIGNAL,
    347                   TPL_CALLBACK,
    348                   (EFI_EVENT_NOTIFY)AddSmbiosManuCallback,
    349                   RecordData,
    350                   &AddSmbiosManuCallbackEvent
    351                   );
    352 
    353   ASSERT_EFI_ERROR (Status);
    354   if (EFI_ERROR (Status)) {
    355     return Status;
    356 
    357   }
    358 
    359   Status = gBS->RegisterProtocolNotify (
    360                   &gEfiDxeSmmReadyToLockProtocolGuid,
    361                   AddSmbiosManuCallbackEvent,
    362                   &AddSmbiosManuCallbackNotifyReg
    363                   );
    364 
    365   return Status;
    366   }
    367 
    368   return EFI_SUCCESS;
    369 
    370 }
    371