Exemple #1
0
VOID
ClearP2PBusMaster(
  )
{
  UINT8             Command;
  UINT8             Index;

  for (Index = 0; Index < sizeof(mPciBm)/sizeof(EFI_PCI_BUS_MASTER); Index++) {
    Command = MmioRead8 (
                MmPciAddress (0,
                  DEFAULT_PCI_BUS_NUMBER_PCH,
                  mPciBm[Index].Device,
                  mPciBm[Index].Function,
                  PCI_COMMAND_OFFSET
                )
              );
    Command &= ~EFI_PCI_COMMAND_BUS_MASTER;
    MmioWrite8 (
      MmPciAddress (0,
        DEFAULT_PCI_BUS_NUMBER_PCH,
        mPciBm[Index].Device,
        mPciBm[Index].Function,
        PCI_COMMAND_OFFSET
      ),
      Command
    );
  }
}
Exemple #2
0
VOID
EFIAPI
PlatformSpecificInit (
  VOID
  )
{
  UINTN                 XhciPciMmBase;
  EFI_PHYSICAL_ADDRESS  XhciMemBaseAddress;

  XhciPciMmBase   = MmPciAddress (
                      0,
                      0,
                      xhci_path.Device,
                      xhci_path.Function,
                      0
                      );


  XhciMemBaseAddress = MmioRead32 ((UINTN) (XhciPciMmBase + R_XHCI_MEM_BASE)) & B_XHCI_MEM_BASE_BA;
  DEBUG ((DEBUG_INFO, "XhciPciMmBase=%x, XhciMemBaseAddress=%x\n", XhciPciMmBase, XhciMemBaseAddress));

  MmioWrite32 ((UINTN)(XhciMemBaseAddress + R_XHCI_MEM_DUAL_ROLE_CFG0), 0x1310800);

  return;
}
Exemple #3
0
VOID
XhciSwitchSwid(BOOLEAN enable)
{
  UINTN                             XhciPciMmBase;
  EFI_PHYSICAL_ADDRESS              XhciMemBaseAddress;
  UINT32                            DualRoleCfg0;
  UINT32                            DualRoleCfg1;

  XhciPciMmBase = MmPciAddress (0, 0, xhci_path.Device, xhci_path.Function, 0);
  XhciMemBaseAddress = MmioRead32 ((UINTN) (XhciPciMmBase + R_XHCI_MEM_BASE)) & B_XHCI_MEM_BASE_BA;
  DEBUG ((DEBUG_INFO, "XhciPciMmBase=%x, XhciMemBaseAddress=%x\n", XhciPciMmBase, XhciMemBaseAddress));

  DualRoleCfg0 = MmioRead32 ((UINTN)(XhciMemBaseAddress + R_XHCI_MEM_DUAL_ROLE_CFG0));
  if (enable) {
    DualRoleCfg0 = DualRoleCfg0 | (1 << 24) | (1 << 21) | (1 << 20);
    DEBUG ((DEBUG_INFO, "DualRoleCfg0 : Set SW ID : 0x%x \n", DualRoleCfg0));
  }
  else {
    DualRoleCfg0 = DualRoleCfg0 & ~(1 << 24) & ~(1 << 21) & ~(1 << 20);
    DEBUG ((DEBUG_INFO, "DualRoleCfg0 : Clear SW ID : 0x%x \n", DualRoleCfg0));
  }
  MmioWrite32 ((UINTN)(XhciMemBaseAddress + R_XHCI_MEM_DUAL_ROLE_CFG0), DualRoleCfg0);

  DualRoleCfg1 = MmioRead32 ((UINTN)(XhciMemBaseAddress + R_XHCI_MEM_DUAL_ROLE_CFG1));
  DEBUG ((DEBUG_INFO, "DualRoleCfg1 : 0x%x \n", DualRoleCfg1));
}
Exemple #4
0
/**
  USB initialization before boot to OS

  @param[in] UsbConfig            The PCH Platform Policy for USB configuration

**/
VOID
UsbInitAtBoot (
  IN     PCH_USB_CONFIG              *UsbConfig
)
{
  UINTN                         XhciPciMmBase;
  UINT32                        XhciMmioBase;

  DEBUG ((EFI_D_INFO, "UsbInitAtBoot() - Start\n"));

  if ((UsbConfig->SsicPortSettings[0].Enable == PCH_DEVICE_DISABLE) &&
      (UsbConfig->SsicPortSettings[1].Enable == PCH_DEVICE_DISABLE)) {
    DEBUG ((EFI_D_INFO, "UsbInitAtBoot() - SsicPortSettings[0] & SsicPortSettings[1] - Disabled\n"));
    XhciPciMmBase = MmPciAddress (
                      0,
                      0,
                      PCI_DEVICE_NUMBER_PCH_XHCI,
                      PCI_FUNCTION_NUMBER_PCH_XHCI,
                      0
                      );

    XhciMmioBase = MmioRead32 (XhciPciMmBase + R_PCH_XHCI_MEM_BASE) & B_PCH_XHCI_MEM_BASE_BA;

    //
    // SSIC port 0: PORT_UNUSED=1 PROG_DONE=1
    // SSIC port 1: PORT_UNUSED=0 PROG_DONE=1
    //

    //
    // Set Port 0 un-used
    //
    MmioOr32 (
      (XhciMmioBase + 0x880C),
      (UINT32) (BIT31)
      );
    //
    // Clear Port 1 un-used
    //
    MmioAnd32 (
      (XhciMmioBase + 0x883C),
      (UINT32) ~(BIT31)
      );

    //
    // Set PROG_DONE bit,
    // xHCIBAR + 0x880C [30] = 1b and xHCIBAR + 0x883C [30] = 1b.
    //
    MmioOr32 (
      (XhciMmioBase + 0x880C),
      (UINT32) (BIT30)
      );
    MmioOr32 (
      (XhciMmioBase + 0x883C),
      (UINT32) (BIT30)
      );
  }
  DEBUG ((EFI_D_INFO, "UsbInitAtBoot() - End\n"));
}
Exemple #5
0
UINT32 
DetermineCompatibleBoard (
  void
  )
{
  UINTN PciD31F0RegBase = 0;
  UINT32 GpioValue = 0;
  UINT32 TmpVal = 0;
  UINT32 MmioConf0 = 0;
  UINT32 MmioPadval = 0;
  UINT32 PConf0Offset = 0x200; //GPIO_S5_4 pad_conf0 register offset
  UINT32 PValueOffset = 0x208; //GPIO_S5_4 pad_value register offset
  UINT32 SSUSOffset = 0x2000;
  UINT32 IoBase = 0;

  DEBUG ((EFI_D_ERROR, "DetermineCompatibleBoard() Entry\n"));
  PciD31F0RegBase = MmPciAddress (0,
                      0,
                      PCI_DEVICE_NUMBER_PCH_LPC,
                      PCI_FUNCTION_NUMBER_PCH_LPC,
                      0
                    );
  IoBase = MmioRead32 (PciD31F0RegBase + R_PCH_LPC_IO_BASE) & B_PCH_LPC_IO_BASE_BAR;
  
  MmioConf0 = IoBase + SSUSOffset + PConf0Offset;
  MmioPadval = IoBase + SSUSOffset + PValueOffset;
  //0xFED0E200/0xFED0E208 is pad_Conf/pad_val register address of GPIO_S5_4
  DEBUG ((EFI_D_ERROR, "MmioConf0[0x%x], MmioPadval[0x%x]\n", MmioConf0, MmioPadval));
  
  MmioWrite32 (MmioConf0, 0x2003CC00);  

  TmpVal = MmioRead32 (MmioPadval);
  TmpVal &= ~0x6; //Clear bit 1:2
  TmpVal |= 0x2; // Set the pin as GPI
  MmioWrite32 (MmioPadval, TmpVal); 

  GpioValue = MmioRead32 (MmioPadval);

  DEBUG ((EFI_D_ERROR, "Gpio_S5_4 value is 0x%x\n", GpioValue));
  return (GpioValue & 0x1);
}
Exemple #6
0
EFI_STATUS
SaveRuntimeScriptTable (
  VOID
  )
{
  SMM_PCI_IO_ADDRESS    PciAddress;
  UINT32                Data32;
  UINT16                Data16;
  UINT8                 Data8;
  UINT8                 Mask;
  UINTN                 Index;
  UINTN                 Offset;
  UINT8                 RegTable[] = {

	  //
    //Bus  ,   Dev,  Func,    DMI
	  //
      0x00 ,  0x00,  0x00,

	  //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
	  //
      0x00 ,  0x08,  0x00,  0x00,  0x30,  0x00,  0x00,  0xa0,

	  //
    //Bus  ,   Dev,  Func,    LPC device
	  //
      0x00 ,  0x1F,  0x00,

	  //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0x00 ,  0x08,  0x00,  0x07,  0x00,  0x00,  0x90,  0x00,

	  //
    //Bus  ,   Dev,  Func,    PCIE device
	 //
      0x00 ,  0x1C,  0x00,

	  //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0xC0 ,  0x83,  0x30,  0x00,  0x00,  0x00,  0x00,  0x00,

	  //
    //Bus  ,   Dev,  Func,    PCIE device
    //
	  0x00 ,  0x1C,  0x00,

	  //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0x03 ,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,

	  //
    //Bus  ,   Dev,  Func,    SATA device
	  //
      0x00 ,  0x13,  0x00,

	  //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0xf4 ,  0xab,  0x27,  0x10,  0xf1,  0x1d,  0x00,  0x40,

    //
    //Bus  ,   Dev,  Func,    EHCI device
    //
     0x00 ,  0x1D,  0x00,

    //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
     0x10 ,  0x88,  0x00,  0x00,  0x00,  0x00,  0x00,  0x80,

    //
    //Bus  ,   Dev,  Func,    SMBUS device
    //
     0x00 ,  0x1f,  0x03,

    //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0x10 ,  0x89,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,

    //
    //Bus  ,   Dev,  Func,    SMBUS device
    //
      0x00 ,  0x1f,  0x03,

    //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0x02 ,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,

    //
    //Bus  ,   Dev,  Func,    VGA bus1
    //
      0x01 ,  0x00,  0x00,

    //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0x58 ,  0x81,  0x18,  0x01,  0xb0,  0x00,  0x00,  0x00,

    //
    //Bus  ,   Dev,  Func,    VGA bus1
    //
      0x01 ,  0x00,  0x00,

    //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0x02 ,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,

    //
    //Bus  ,   Dev,  Func,    VGA bus1 function 1
    //
      0x01 ,  0x00,  0x01,

    //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0x51 ,  0x80,  0x80,  0x01,  0x00,  0x00,  0x00,  0x00,

    //
    //Bus  ,   Dev,  Func,    VGA bus1 function 1
    //
      0x01 ,  0x00,  0x01,

    //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0x02 ,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,

    //
    //Bus  ,   Dev,  Func,    IGD bus0 function 0
    //
      0x00 ,  0x02,  0x00,

    //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0x42 ,  0x81,  0x00,  0x00,  0x00,  0x00,  0x20,  0x00,

    //
    //Bus  ,   Dev,  Func,    USB bus0 function 0
    //
      0x00 ,  0x16,  0x00,

    //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0x32 ,  0x80,  0x00,  0x00,  0x00,  0x00,  0x00,  0x00,

    //
    //Bus  ,   Dev,  Func,    HD Audio bus0 function 0
    //
      0x00 ,  0x1B,  0x00,

    //
    //00-1F, 20-3F, 40-5F, 60-7F, 80-9F, A0-BF, C0-DF, E0-FF
    //
      0x00 ,  0x00,  0x00,  0x00,  0x00,  0x00,  0x02,  0x00,

    //
    //0xFF indicates the end of the table
    //
      0xFF
 };

  //
  // These registers have to set in byte order
  //
  UINT8                 ExtReg[] = { 0x9E, 0x9D };  // SMRAM settings



  //
  // Save PCI-Host bridge settings (0, 0, 0). 0x90, 94 and 9c are changed by CSM
  // and vital to S3 resume. That's why we put save code here
  //
  PciAddress.Bus      = 0;
  PciAddress.Device   = 0;
  PciAddress.Function = 0;
  PciAddress.ExtendedRegister = 0;

  for (Index = 0; Index < 2; Index++) {
    //
    // Read SRAM setting from Pci(0, 0, 0)
    //
    PciAddress.Register = ExtReg[Index];
    Data8 = MmioRead8 (
              MmPciAddress (0,
                PciAddress.Bus,
                PciAddress.Device,
                PciAddress.Function,
                PciAddress.Register
              )
            );

    //
    // Save latest settings to runtime script table
    //
    S3BootScriptSavePciCfgWrite(
      S3BootScriptWidthUint8,
      *(UINT64*)&PciAddress,
      1,
      &Data8
      );
  }


  //
  // Save PCI-Host bridge settings (0, 0, 0). 0x90, 94 and 9c are changed by CSM
  // and vital to S3 resume. That's why we put save code here
  //
  Index = 0;
  while (RegTable[Index] != 0xFF) {

    PciAddress.Bus      = RegTable[Index++];
    PciAddress.Device   = RegTable[Index++];
    PciAddress.Function = RegTable[Index++];
    PciAddress.Register = 0;
    PciAddress.ExtendedRegister = 0;

    Data16 = MmioRead16 (
              MmPciAddress (0,
                PciAddress.Bus,
                PciAddress.Device,
                PciAddress.Function,
                PciAddress.Register
              )
            );

    if (Data16 == 0xFFFF) {
      Index+=8;
      continue;
    }

    for (Offset = 0, Mask = 0x01; Offset < 256; Offset+=4, Mask<<=1) {

      if (Mask == 0x00) {
        Mask = 0x01;
      }

      if (RegTable[Index + Offset/32] & Mask ) {

        PciAddress.Register = (UINT8)Offset;
        Data32 = MmioRead32 (MmPciAddress (0, PciAddress.Bus, PciAddress.Device, PciAddress.Function, PciAddress.Register));

        //
        // Save latest settings to runtime script table
        //
        S3BootScriptSavePciCfgWrite (
          S3BootScriptWidthUint32,
          *(UINT64*)&PciAddress,
          1,
          &Data32
        );
      }
    }

    Index += 8;

  }


  //
  // Save I/O ports to S3 script table
  //

  //
  // Selftest KBC
  //
  Data8 = 0xAA;
  S3BootScriptSaveIoWrite (
    S3BootScriptWidthUint8,
    0x64,
    (UINTN)1,
    &Data8
    );

  Data32 = IoRead32(mAcpiBaseAddr + R_PCH_SMI_EN);

  S3BootScriptSaveIoWrite (
      S3BootScriptWidthUint32,
      (mAcpiBaseAddr + R_PCH_SMI_EN),
      1,
      &Data32
      );

  //
  // Save B_ICH_TCO_CNT_LOCK so it will be done on S3 resume path.
  //
  Data16 = IoRead16(mAcpiBaseAddr + R_PCH_TCO_CNT);

  S3BootScriptSaveIoWrite (
      S3BootScriptWidthUint16,
      mAcpiBaseAddr + R_PCH_TCO_CNT,
      1,
      &Data16
      );


  return EFI_SUCCESS;
}
Exemple #7
0
/**
  Do any final initialization on SATA controller

  @param[in] PchPlatformPolicy    The PCH Platform Policy protocol instance
  @param[in] IsSetS3BootScript    Is this function called for S3 boot script save

  @retval EFI_SUCCESS             The function completed successfully
**/
EFI_STATUS
ConfigureSataAtBoot (
  IN DXE_PCH_PLATFORM_POLICY_PROTOCOL *PchPlatformPolicy,
  IN BOOLEAN                          IsSetS3BootScript
  )
{
  UINT8                             Index;
  UINT32                            AhciBar;
  UINTN                             PciD19F0RegBase;
  UINT16                            SataModeSelect;
  UINT32                            PxSctlDet;
  UINT32                            PxCmdSud;
  UINT32                            OrgCmdWord;
  UINT32                            Data32And;
  UINT32                            Data32Or;

  DEBUG ((EFI_D_INFO, "ConfigureSataAtBoot() Start\n"));
  //
  // eSATA port support only up to Gen2
  //
  PciD19F0RegBase = MmPciAddress (0, PchPlatformPolicy->BusNumber, PCI_DEVICE_NUMBER_PCH_SATA, PCI_FUNCTION_NUMBER_PCH_SATA, 0);
  //
  // Make sure SATA device exists.
  //
  if (MmioRead16 (PciD19F0RegBase + R_PCH_SATA_ID) != 0xFFFF) {
    SataModeSelect  = MmioRead16 (PciD19F0RegBase + R_PCH_SATA_MAP) & B_PCH_SATA_MAP_SMS_MASK;
    if ((SataModeSelect == V_PCH_SATA_MAP_SMS_AHCI) ||
        (SataModeSelect == V_PCH_SATA_MAP_SMS_RAID)) {
      AhciBar = MmioRead32 (PciD19F0RegBase + R_PCH_SATA_ABAR) & B_PCH_SATA_ABAR_BA;
      //
      // Make sure the AhciBar is valid.
      //
      if ((AhciBar != 0x00000000) && (AhciBar != B_PCH_SATA_ABAR_BA)) {
        //
        // Keep original CMD word, and enable MSE
        //
        OrgCmdWord = MmioRead32 (PciD19F0RegBase + R_PCH_SATA_COMMAND);
        if ((OrgCmdWord & B_PCH_SATA_COMMAND_MSE) == 0) {
          Data32And = (UINT32) 0xFFFFFFFF;
          Data32Or  = (UINT32) B_PCH_SATA_COMMAND_MSE;
          if (!IsSetS3BootScript) {
            MmioOr32 ((PciD19F0RegBase + R_PCH_SATA_COMMAND), Data32Or);
          } else {
            //
            // Set S3 Boot Script
            //
            S3BootScriptSaveMemReadWrite (
              EfiBootScriptWidthUint32,
              (UINTN) (PciD19F0RegBase + R_PCH_SATA_COMMAND),
              &Data32Or,  /// Data to be ORed
              &Data32And  /// Data to be ANDed
              );
          }
        }
        for (Index = 0; Index < PCH_AHCI_MAX_PORTS; Index++) {
          if (PchPlatformPolicy->SataConfig->PortSettings[Index].External == PCH_DEVICE_ENABLE) {
            PxSctlDet = MmioRead32(AhciBar + (R_PCH_SATA_AHCI_P0SCTL + (0x80 * Index))) & B_PCH_SATA_AHCI_PXSCTL_DET;
            PxCmdSud = MmioRead32(AhciBar + (R_PCH_SATA_AHCI_P0CMD  + (0x80 * Index))) & B_PCH_SATA_AHCI_PxCMD_SUD;
            //
            // Limit speed to Gen2
            //
            Data32And = (UINT32)~(B_PCH_SATA_AHCI_PXSCTL_SPD);
            Data32Or  = (UINT32) V_PCH_SATA_AHCI_PXSCTL_SPD_2;
            if (!IsSetS3BootScript) {
              MmioAndThenOr32 (
                (UINTN) (AhciBar + (R_PCH_SATA_AHCI_P0SCTL + (0x80 * Index))),
                Data32And,
                Data32Or
                );
            } else {
              //
              // Set S3 Boot Script
              //
              S3BootScriptSaveMemReadWrite (
                EfiBootScriptWidthUint32,
                (UINTN) (AhciBar + (R_PCH_SATA_AHCI_P0SCTL + (0x80 * Index))),
                &Data32Or,  /// Data to be ORed
                &Data32And  /// Data to be ANDed
                );
            }
            //
            // If port is not offline, and it's spin up, need to port reset.
            // After port reset, clear the SERR.
            // - Set DET=1, and then set DET=0.
            // - Finally, set FRE=1.
            //
            if ((PxSctlDet == V_PCH_SATA_AHCI_PXSCTL_DET_0) &&
                (PxCmdSud == B_PCH_SATA_AHCI_PxCMD_SUD))
            {
              if (!IsSetS3BootScript) {
                MmioOr32 (AhciBar + (R_PCH_SATA_AHCI_P0SCTL + (0x80 * Index)), V_PCH_SATA_AHCI_PXSCTL_DET_1);
                PchPmTimerStall (1000);
                MmioAnd32(AhciBar + (R_PCH_SATA_AHCI_P0SCTL + (0x80 * Index)), (UINT32) ~(B_PCH_SATA_AHCI_PXSCTL_DET));
                MmioWrite32 (AhciBar + (R_PCH_SATA_AHCI_P0SERR + (0x80 * Index)), (UINT32)~0u);
                MmioOr32 (AhciBar + (R_PCH_SATA_AHCI_P0CMD + (0x80 * Index)), B_PCH_SATA_AHCI_PxCMD_FRE);
              } else {
                //
                // Set S3 Boot Script
                //
                Data32And = (UINT32) 0xFFFFFFFF;
                Data32Or  = (UINT32) V_PCH_SATA_AHCI_PXSCTL_DET_1;
                S3BootScriptSaveMemReadWrite (
                  EfiBootScriptWidthUint32,
                  (UINTN) (AhciBar + (R_PCH_SATA_AHCI_P0SCTL + (0x80 * Index))),
                  &Data32Or,  /// Data to be ORed
                  &Data32And  /// Data to be ANDed
                  );
                S3BootScriptSaveStall (1000);
                Data32And = (UINT32) ~(B_PCH_SATA_AHCI_PXSCTL_DET);
                Data32Or  = (UINT32) 0x00000000;
                S3BootScriptSaveMemReadWrite (
                  EfiBootScriptWidthUint32,
                  (UINTN) (AhciBar + (R_PCH_SATA_AHCI_P0SCTL + (0x80 * Index))),
                  &Data32Or,  /// Data to be ORed
                  &Data32And  /// Data to be ANDed
                  );
                Data32And = (UINT32) 0xFFFFFFFF;
                Data32Or  = (UINT32) 0xFFFFFFFF;
                S3BootScriptSaveMemReadWrite (
                  EfiBootScriptWidthUint32,
                  (UINTN) (AhciBar + (R_PCH_SATA_AHCI_P0SERR + (0x80 * Index))),
                  &Data32Or,  /// Data to be ORed
                  &Data32And  /// Data to be ANDed
                  );
                Data32And = (UINT32) 0xFFFFFFFF;
                Data32Or  = (UINT32) B_PCH_SATA_AHCI_PxCMD_FRE;
                S3BootScriptSaveMemReadWrite (
                  EfiBootScriptWidthUint32,
                  (UINTN) (AhciBar + (R_PCH_SATA_AHCI_P0CMD + (0x80 * Index))),
                  &Data32Or,  /// Data to be ORed
                  &Data32And  /// Data to be ANDed
                  );
              }
            }
            //
            // If port is offline, and it's not spin up, meets the power bug.
            // Need to do the W/A to spin up the port and then spin down.
            // Then entering back to offline and listen.
            // - Set DET=0, SUD=1, and then set SUD=0, DET=4.
            //
            if ((PxSctlDet == V_PCH_SATA_AHCI_PXSCTL_DET_4) &&
                (PxCmdSud == 0))
            {
              if (!IsSetS3BootScript) {
                MmioAnd32(AhciBar + (R_PCH_SATA_AHCI_P0SCTL + (0x80 * Index)), (UINT32) ~(B_PCH_SATA_AHCI_PXSCTL_DET));
                MmioOr32 (AhciBar + (R_PCH_SATA_AHCI_P0CMD  + (0x80 * Index)), B_PCH_SATA_AHCI_PxCMD_SUD);
                PchPmTimerStall (1000);
                MmioAnd32(AhciBar + (R_PCH_SATA_AHCI_P0CMD  + (0x80 * Index)), (UINT32) ~(B_PCH_SATA_AHCI_PxCMD_SUD));
                MmioOr32 (AhciBar + (R_PCH_SATA_AHCI_P0SCTL + (0x80 * Index)), V_PCH_SATA_AHCI_PXSCTL_DET_4);
              } else {
                //
                // Set S3 Boot Script
                //
                Data32And = (UINT32) ~(B_PCH_SATA_AHCI_PXSCTL_DET);
                Data32Or  = (UINT32) 0x00000000;
                S3BootScriptSaveMemReadWrite (
                  EfiBootScriptWidthUint32,
                  (UINTN) (AhciBar + (R_PCH_SATA_AHCI_P0SCTL + (0x80 * Index))),
                  &Data32Or,  /// Data to be ORed
                  &Data32And  /// Data to be ANDed
                  );
                Data32And = (UINT32) 0xFFFFFFFF;
                Data32Or  = (UINT32) B_PCH_SATA_AHCI_PxCMD_SUD;
                S3BootScriptSaveMemReadWrite (
                  EfiBootScriptWidthUint32,
                  (UINTN) (AhciBar + (R_PCH_SATA_AHCI_P0CMD + (0x80 * Index))),
                  &Data32Or,  /// Data to be ORed
                  &Data32And  /// Data to be ANDed
                  );
                S3BootScriptSaveStall (1000);
                Data32And = (UINT32) ~(B_PCH_SATA_AHCI_PxCMD_SUD);
                Data32Or  = (UINT32) 0x00000000;
                S3BootScriptSaveMemReadWrite (
                  EfiBootScriptWidthUint32,
                  (UINTN) (AhciBar + (R_PCH_SATA_AHCI_P0CMD + (0x80 * Index))),
                  &Data32Or,  /// Data to be ORed
                  &Data32And  /// Data to be ANDed
                  );
                Data32And = (UINT32) 0xFFFFFFFF;
                Data32Or  = (UINT32) V_PCH_SATA_AHCI_PXSCTL_DET_4;
                S3BootScriptSaveMemReadWrite (
                  EfiBootScriptWidthUint32,
                  (UINTN) (AhciBar + (R_PCH_SATA_AHCI_P0SCTL + (0x80 * Index))),
                  &Data32Or,  /// Data to be ORed
                  &Data32And  /// Data to be ANDed
                  );
              }
            }
          }
        }
        //
        // Restore original CMD word.
        //
        if ((OrgCmdWord & B_PCH_SATA_COMMAND_MSE) == 0) {
          Data32And = (UINT32) 0xFFFFFFFF;
          Data32Or  = (UINT32) OrgCmdWord;
          if (!IsSetS3BootScript) {
            MmioWrite32 ((PciD19F0RegBase + R_PCH_SATA_COMMAND), Data32Or);
          } else {
            S3BootScriptSaveMemReadWrite (
              EfiBootScriptWidthUint32,
              (UINTN) (PciD19F0RegBase + R_PCH_SATA_COMMAND),
              &Data32Or,  /// Data to be ORed
              &Data32And  /// Data to be ANDed
              );
          }
        }
      } // AhciBar is vaild
    } // SATA mode is AHCI or RAID
  } // if D19F0 is existed

  DEBUG ((EFI_D_INFO, "ConfigureSataAtBoot() End\n"));
  return EFI_SUCCESS;
}
/**
  Perform flash write operation with progress indicator.  The start and end
  completion percentage values are passed into this function.  If the requested
  flash write operation is broken up, then completion percentage between the
  start and end values may be passed to the provided Progress function.  The
  caller of this function is required to call the Progress function for the
  start and end completion percentage values.  This allows the Progress,
  StartPercentage, and EndPercentage parameters to be ignored if the requested
  flash write operation can not be broken up

  @param[in] FirmwareType      The type of firmware.
  @param[in] FlashAddress      The address of flash device to be accessed.
  @param[in] FlashAddressType  The type of flash device address.
  @param[in] Buffer            The pointer to the data buffer.
  @param[in] Length            The length of data buffer in bytes.
  @param[in] Progress          A function used report the progress of the
                               firmware update.  This is an optional parameter
                               that may be NULL.
  @param[in] StartPercentage   The start completion percentage value that may
                               be used to report progress during the flash
                               write operation.
  @param[in] EndPercentage     The end completion percentage value that may
                               be used to report progress during the flash
                               write operation.

  @retval EFI_SUCCESS           The operation returns successfully.
  @retval EFI_WRITE_PROTECTED   The flash device is read only.
  @retval EFI_UNSUPPORTED       The flash device access is unsupported.
  @retval EFI_INVALID_PARAMETER The input parameter is not valid.
**/
EFI_STATUS
EFIAPI
PerformFlashWriteWithProgress (
  IN PLATFORM_FIRMWARE_TYPE                         FirmwareType,
  IN EFI_PHYSICAL_ADDRESS                           FlashAddress,
  IN FLASH_ADDRESS_TYPE                             FlashAddressType,
  IN VOID                                           *Buffer,
  IN UINTN                                          Length,
  IN EFI_FIRMWARE_MANAGEMENT_UPDATE_IMAGE_PROGRESS  Progress,        OPTIONAL
  IN UINTN                                          StartPercentage,
  IN UINTN                                          EndPercentage
  )
{
  EFI_STATUS            Status = EFI_SUCCESS;
  UINTN               Index;
  EFI_PHYSICAL_ADDRESS  Address;
  UINTN                 CountOfBlocks;
  EFI_TPL               OldTpl;
  BOOLEAN               FlashError;
  UINT8                 *Buf;
  UINTN                 LpcBaseAddress;
  UINT8                 Data8Or;
  UINT8                 Data8And;
  UINT8                 BiosCntl;

  Index             = 0;
  Address           = 0;
  CountOfBlocks     = 0;
  FlashError        = FALSE;
  Buf               = Buffer;

  DEBUG((DEBUG_INFO | DEBUG_ERROR, "PerformFlashWrite - 0x%x(%x) - 0x%x\n", (UINTN)FlashAddress, (UINTN)FlashAddressType, Length));
  if (FlashAddressType == FlashAddressTypeRelativeAddress) {
    FlashAddress = FlashAddress + mInternalFdAddress;
  }

  CountOfBlocks = (UINTN) (Length / BLOCK_SIZE);
  Address = FlashAddress;

  LpcBaseAddress = MmPciAddress (0,
                    DEFAULT_PCI_BUS_NUMBER_PCH,
                    PCI_DEVICE_NUMBER_PCH_LPC,
                    PCI_FUNCTION_NUMBER_PCH_LPC,
                    0
                    );
  BiosCntl = MmioRead8 (LpcBaseAddress + R_PCH_LPC_BIOS_CNTL);
  if ((BiosCntl & B_PCH_LPC_BIOS_CNTL_SMM_BWP) == B_PCH_LPC_BIOS_CNTL_SMM_BWP) {
    ///
    /// Clear SMM_BWP bit (D31:F0:RegDCh[5])
    ///
    Data8And  = (UINT8) ~B_PCH_LPC_BIOS_CNTL_SMM_BWP;
    Data8Or   = 0x00;

    MmioAndThenOr8 (
      LpcBaseAddress + R_PCH_LPC_BIOS_CNTL,
      Data8And,
      Data8Or
      );
    DEBUG((DEBUG_INFO, "PerformFlashWrite Clear SMM_BWP bit\n"));
  }

    //
    // Raise TPL to TPL_NOTIFY to block any event handler,
    // while still allowing RaiseTPL(TPL_NOTIFY) within
    // output driver during Print()
    //
    OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
    for (Index = 0; Index < CountOfBlocks; Index++) {
      if (Progress != NULL) {
        Progress (StartPercentage + ((Index * (EndPercentage - StartPercentage)) / CountOfBlocks));
      }
      //
      // Handle block based on address and contents.
      //
      if (!EFI_ERROR (InternalCompareBlock (Address, Buf))) {
        DEBUG((DEBUG_INFO, "Skipping block at 0x%lx (already programmed)\n", Address));
      } else {
        //
        // Make updating process uninterruptable,
        // so that the flash memory area is not accessed by other entities
        // which may interfere with the updating process
        //
        Status  = InternalEraseBlock (Address);
        if (EFI_ERROR(Status)) {
          gBS->RestoreTPL (OldTpl);
          FlashError = TRUE;
          goto Done;
        }
        Status = InternalWriteBlock (
                  Address,
                  Buf,
                  (UINT32)(Length > BLOCK_SIZE ? BLOCK_SIZE : Length)
                  );
        if (EFI_ERROR(Status)) {
          gBS->RestoreTPL (OldTpl);
          FlashError = TRUE;
          goto Done;
        }
      }

      //
      // Move to next block to update.
      //
      Address += BLOCK_SIZE;
      Buf += BLOCK_SIZE;
      if (Length > BLOCK_SIZE) {
        Length -= BLOCK_SIZE;
      } else {
        Length = 0;
      }
    }
    gBS->RestoreTPL (OldTpl);

Done:
  if ((BiosCntl & B_PCH_LPC_BIOS_CNTL_SMM_BWP) == B_PCH_LPC_BIOS_CNTL_SMM_BWP) {
    //
    // Restore original control setting
    //
    MmioWrite8 (LpcBaseAddress + R_PCH_LPC_BIOS_CNTL, BiosCntl);
  }

  if (Progress != NULL) {
    Progress (EndPercentage);
  }

  return EFI_SUCCESS;
}
Exemple #9
0
VOID
PchBaseInit (
  VOID
  )
{
  //
  // Program ACPI Power Management I/O Space Base Address
  //
  MmioWrite16 (
    MmPciAddress (0,
      DEFAULT_PCI_BUS_NUMBER_PCH,
      PCI_DEVICE_NUMBER_PCH_LPC,
      PCI_FUNCTION_NUMBER_PCH_LPC,
      R_PCH_LPC_ACPI_BASE
    ),
    (UINT16)((ACPI_BASE_ADDRESS & B_PCH_LPC_ACPI_BASE_BAR) | B_PCH_LPC_ACPI_BASE_EN)
  );

  //
  // Program GPIO Base Address
  //
  MmioWrite16 (
    MmPciAddress (0,
      DEFAULT_PCI_BUS_NUMBER_PCH,
      PCI_DEVICE_NUMBER_PCH_LPC,
      PCI_FUNCTION_NUMBER_PCH_LPC,
      R_PCH_LPC_GPIO_BASE
    ),
    (UINT16)((GPIO_BASE_ADDRESS & B_PCH_LPC_GPIO_BASE_BAR) | B_PCH_LPC_GPIO_BASE_EN)
  );

  //
  // Set PMC Base Address
  //
  MmioWrite32 (
    MmPciAddress (0,
      DEFAULT_PCI_BUS_NUMBER_PCH,
      PCI_DEVICE_NUMBER_PCH_LPC,
      PCI_FUNCTION_NUMBER_PCH_LPC,
      R_PCH_LPC_PMC_BASE
    ),
    (UINT32)((PMC_BASE_ADDRESS & B_PCH_LPC_PMC_BASE_BAR) | B_PCH_LPC_PMC_BASE_EN)
  );

  //
  // Set IO Base Address
  //
  MmioWrite32 (
    MmPciAddress (0,
      DEFAULT_PCI_BUS_NUMBER_PCH,
      PCI_DEVICE_NUMBER_PCH_LPC,
      PCI_FUNCTION_NUMBER_PCH_LPC,
      R_PCH_LPC_IO_BASE
    ),
    (UINT32)((IO_BASE_ADDRESS & B_PCH_LPC_IO_BASE_BAR) | B_PCH_LPC_IO_BASE_EN)
  );

  //
  // Set ILB Base Address
  //
  MmioWrite32 (
    MmPciAddress (0,
      DEFAULT_PCI_BUS_NUMBER_PCH,
      PCI_DEVICE_NUMBER_PCH_LPC,
      PCI_FUNCTION_NUMBER_PCH_LPC,
      R_PCH_LPC_ILB_BASE
    ),
    (UINT32)((ILB_BASE_ADDRESS & B_PCH_LPC_ILB_BASE_BAR) | B_PCH_LPC_ILB_BASE_EN)
  );

  //
  // Set PUnit Base Address
  //
  MmioWrite32 (
    MmPciAddress (0,
      DEFAULT_PCI_BUS_NUMBER_PCH,
      PCI_DEVICE_NUMBER_PCH_LPC,
      PCI_FUNCTION_NUMBER_PCH_LPC,
      R_PCH_LPC_PUNIT_BASE
    ),
    (UINT32)((PUNIT_BASE_ADDRESS & B_PCH_LPC_PUNIT_BASE_BAR) | B_PCH_LPC_PUNIT_BASE_EN)
  );

  //
  // Set SPI Base Address
  //
  MmioWrite32 (
    MmPciAddress (0,
      DEFAULT_PCI_BUS_NUMBER_PCH,
      PCI_DEVICE_NUMBER_PCH_LPC,
      PCI_FUNCTION_NUMBER_PCH_LPC,
      R_PCH_LPC_SPI_BASE
    ),
    (UINT32)((SPI_BASE_ADDRESS & B_PCH_LPC_SPI_BASE_BAR) | B_PCH_LPC_SPI_BASE_EN)
  );

  //
  // Set Root Complex Base Address
  //
  MmioWrite32 (
    MmPciAddress (0,
      DEFAULT_PCI_BUS_NUMBER_PCH,
      PCI_DEVICE_NUMBER_PCH_LPC,
      PCI_FUNCTION_NUMBER_PCH_LPC,
      R_PCH_LPC_RCBA
    ),
    (UINT32)((RCBA_BASE_ADDRESS & B_PCH_LPC_RCBA_BAR) | B_PCH_LPC_RCBA_EN)
  );

  //
  // Set MPHY Base Address
  //
  MmioWrite32 (
    MmPciAddress (0,
      DEFAULT_PCI_BUS_NUMBER_PCH,
      PCI_DEVICE_NUMBER_PCH_LPC,
      PCI_FUNCTION_NUMBER_PCH_LPC,
      R_PCH_LPC_MPHY_BASE
    ),
    (UINT32)((MPHY_BASE_ADDRESS & B_PCH_LPC_MPHY_BASE_BAR) | B_PCH_LPC_MPHY_BASE_EN)
  );
  MmioWrite16 (
    MmPciAddress (0,
      DEFAULT_PCI_BUS_NUMBER_PCH,
      PCI_DEVICE_NUMBER_PCH_SMBUS,
      PCI_FUNCTION_NUMBER_PCH_SMBUS,
      R_PCH_SMBUS_BASE
    ),
    (UINT16)(SMBUS_BASE_ADDRESS & B_PCH_SMBUS_BASE_BAR)
  );

  MmioOr8 (
    MmPciAddress (0,
      DEFAULT_PCI_BUS_NUMBER_PCH,
      PCI_DEVICE_NUMBER_PCH_SMBUS,
      PCI_FUNCTION_NUMBER_PCH_SMBUS,
      R_PCH_SMBUS_PCICMD
    ),
    B_PCH_SMBUS_PCICMD_IOSE
  );

}
Exemple #10
0
/**
  Initializes the host controller to execute I2C commands.

  @param I2cControllerIndex Index of I2C controller in LPSS device. 0 represents I2C0, which is PCI function 1 of LPSS device.   
                                
  @return EFI_SUCCESS       Opcode initialization on the I2C host controller completed.
  @return EFI_DEVICE_ERROR  Device error, operation failed.
**/
EFI_STATUS
I2CInit (
  UINT8 I2cControllerIndex, 
  UINT16 SlaveAddress
  )
{
  EFI_STATUS   Status;
  UINT32       NumTries = 0;
  UINTN        I2CBaseAddress;
  UINT16       I2cMode;
  UINTN        PciMmBase=0;


  PciMmBase = MmPciAddress (
                0,
                DEFAULT_PCI_BUS_NUMBER_PCH,
                PCI_DEVICE_NUMBER_PCH_LPSS_I2C,
                (I2cControllerIndex + 1),
                0
                );

  I2CBaseAddress = I2CLibPeiMmioRead32 (PciMmBase+R_PCH_LPSS_I2C_BAR);

  //
  //  Verify the parameters
  //
  if (1023 < SlaveAddress ) {
    Status =  EFI_INVALID_PARAMETER;
    DEBUG((EFI_D_INFO,"I2cStartRequest Exit with Status %r\r\n", Status));
    return Status;
  }

  if(I2CBaseAddress ==  (PEI_TEPM_LPSS_I2C0_BAR + I2cControllerIndex * PCI_CONFIG_SPACE_SIZE)) {
    return EFI_SUCCESS;
  }
  ProgramPciLpssI2C();

  I2CBaseAddress = (UINT32) (PEI_TEPM_LPSS_I2C0_BAR + I2cControllerIndex * PCI_CONFIG_SPACE_SIZE);
  DEBUG ((EFI_D_ERROR, "I2CBaseAddress = 0x%x \n",I2CBaseAddress));
  NumTries = 10000; // 1 seconds
  while ((1 == ( I2CLibPeiMmioRead32 ( I2CBaseAddress + R_IC_STATUS) & STAT_MST_ACTIVITY ))) {
    MicroSecondDelay(10);
    NumTries --;
    if(0 == NumTries)
      return EFI_DEVICE_ERROR;
  }

  Status = I2cDisable (I2cControllerIndex);
  DEBUG((EFI_D_INFO, "I2cDisable Status = %r\r\n", Status));

  I2cBusFrequencySet(I2CBaseAddress, 400 * 1000, &I2cMode);//Set I2cMode

  I2CLibPeiMmioWrite16(I2CBaseAddress + R_IC_INTR_MASK, 0x0);
  if (0x7F < SlaveAddress) {
    SlaveAddress = (SlaveAddress & 0x3ff ) | IC_TAR_10BITADDR_MASTER;
  }
  I2CLibPeiMmioWrite16 (I2CBaseAddress + R_IC_TAR, (UINT16) SlaveAddress );
  I2CLibPeiMmioWrite16 (I2CBaseAddress + R_IC_RX_TL, 0);
  I2CLibPeiMmioWrite16 (I2CBaseAddress + R_IC_TX_TL, 0 );
  I2CLibPeiMmioWrite16 (I2CBaseAddress + R_IC_CON, I2cMode);

  Status = I2cEnable(I2cControllerIndex);
  DEBUG((EFI_D_INFO, "I2cEnable Status = %r\r\n", Status));
  I2CLibPeiMmioRead16 ( I2CBaseAddress + R_IC_CLR_TX_ABRT );
  
  return EFI_SUCCESS;
}
Exemple #11
0
/**
  Programe all I2C controllers on LPSS. 
  
  I2C0 is function 1 of LPSS. I2C1 is function 2 of LPSS, etc..

  @param   VOID

  @return  EFI_SUCCESS
**/
EFI_STATUS
ProgramPciLpssI2C (
  VOID
  )
{
  UINT32       PmcBase;
  UINT32       DevID;
  UINTN        PciMmBase=0;
  UINTN        Index;
  UINTN        Bar0;
  UINTN        Bar1;
  DEBUG ((EFI_D_INFO, "Pei ProgramPciLpssI2C() Start\n"));
  
  //
  // Set the VLV Function Disable Register to ZERO
  //
  PmcBase         = I2CLibPeiMmioRead32(PciD31F0RegBase + R_PCH_LPC_PMC_BASE) & B_PCH_LPC_PMC_BASE_BAR;
  
  if(I2CLibPeiMmioRead32(PmcBase + R_PCH_PMC_FUNC_DIS)&
      (B_PCH_PMC_FUNC_DIS_LPSS2_FUNC1 | B_PCH_PMC_FUNC_DIS_LPSS2_FUNC2
       | B_PCH_PMC_FUNC_DIS_LPSS2_FUNC3 | B_PCH_PMC_FUNC_DIS_LPSS2_FUNC4 | B_PCH_PMC_FUNC_DIS_LPSS2_FUNC5
       | B_PCH_PMC_FUNC_DIS_LPSS2_FUNC6 | B_PCH_PMC_FUNC_DIS_LPSS2_FUNC7)) {
    I2CLibPeiMmioWrite32(
      PmcBase+R_PCH_PMC_FUNC_DIS,
      I2CLibPeiMmioRead32(PmcBase + R_PCH_PMC_FUNC_DIS)& \
      ~(B_PCH_PMC_FUNC_DIS_LPSS2_FUNC1 | B_PCH_PMC_FUNC_DIS_LPSS2_FUNC2 \
        | B_PCH_PMC_FUNC_DIS_LPSS2_FUNC3 | B_PCH_PMC_FUNC_DIS_LPSS2_FUNC4 \
        | B_PCH_PMC_FUNC_DIS_LPSS2_FUNC5 | B_PCH_PMC_FUNC_DIS_LPSS2_FUNC6|B_PCH_PMC_FUNC_DIS_LPSS2_FUNC7)
      );
    DEBUG ((EFI_D_INFO, "ProgramPciLpssI2C() enable all I2C controllers\n"));
  }

  for(Index = 0; Index < LPSS_PCI_DEVICE_NUMBER; Index ++) {

    PciMmBase = MmPciAddress (
                  0,
                  DEFAULT_PCI_BUS_NUMBER_PCH,
                  PCI_DEVICE_NUMBER_PCH_LPSS_I2C,
                  Index,
                  0
                  );
    DevID =  I2CLibPeiMmioRead32(PciMmBase);

    Bar0 = PEI_TEPM_LPSS_DMA_BAR + (Index * PCI_CONFIG_SPACE_SIZE);
    Bar1 = Bar0 + 0x8000;

    DEBUG((EFI_D_ERROR, "Program Pci Lpss I2C Device  Function=%x DevID=%08x\n", Index, DevID));
    
    //
    // Check if device present
    //
    if (DevID  != 0xFFFFFFFF)  {
      if(!(I2CLibPeiMmioRead32 (PciMmBase + R_PCH_LPSS_I2C_STSCMD) & B_PCH_LPSS_I2C_STSCMD_MSE)) {
        //
        // Program BAR 0
        //
        I2CLibPeiMmioWrite32((UINTN) (PciMmBase + R_PCH_LPSS_I2C_BAR), (UINT32)(Bar0 & B_PCH_LPSS_I2C_BAR_BA));
        
        DEBUG ((EFI_D_ERROR, "I2CBaseAddress1 = 0x%x \n",I2CLibPeiMmioRead32 (PciMmBase+R_PCH_LPSS_I2C_BAR)));
        
        //
        // Program BAR 1
        //
        I2CLibPeiMmioWrite32 ((UINTN)(PciMmBase + R_PCH_LPSS_I2C_BAR1), (UINT32)(Bar1 & B_PCH_LPSS_I2C_BAR1_BA));
        DEBUG ((EFI_D_ERROR, "I2CBaseAddress1 = 0x%x \n",I2CLibPeiMmioRead32(PciMmBase+R_PCH_LPSS_I2C_BAR1)));
        
        //
        // Bus Master Enable & Memory Space Enable
        //
        I2CLibPeiMmioWrite32((UINTN) (PciMmBase + R_PCH_LPSS_I2C_STSCMD), (UINT32)(B_PCH_LPSS_I2C_STSCMD_BME | B_PCH_LPSS_I2C_STSCMD_MSE));
      }
      
      //
      // Release Resets
      //
      I2CLibPeiMmioWrite32 (Bar0 + R_PCH_LPIO_I2C_MEM_RESETS, (B_PCH_LPIO_I2C_MEM_RESETS_FUNC | B_PCH_LPIO_I2C_MEM_RESETS_APB));
      
      //
      // Activate Clocks
      //
      I2CLibPeiMmioWrite32 (Bar0 + R_PCH_LPSS_I2C_MEM_PCP, 0x80020003);//No use for A0

      DEBUG ((EFI_D_INFO, "ProgramPciLpssI2C() Programmed()\n"));
    }

  }
  
  DEBUG ((EFI_D_INFO, "Pei ProgramPciLpssI2C() End\n"));

  return EFI_SUCCESS;
}
EFI_STATUS
UpdatePlatformInformation (
  CHAR16 *SECVer, CHAR16 *uCodeVer, CHAR16 *GOPVer, CHAR16 *MrcVer,
  CHAR16 *PmcVer, CHAR16 *UlpmcVer, CHAR16 *PunitVer, CHAR16 *SocVer,
  CHAR16 *BoardVer, CHAR16 *FabVer, CHAR16 *CpuFlavorString, CHAR16 *BiosVer,
  CHAR16 *PmicVer, CHAR16 *TouchVer, CHAR16 *SecureBootMode, CHAR16 *BootModeString,
  CHAR16 *SpeedStepMode, CHAR16 *MaxCState, CHAR16 *CpuTurbo, CHAR16 *GfxTurbo,
  CHAR16 *S0ix, CHAR16 *RC6
)
{
  UINT32                   MicroCodeVersion;
  CHAR16                   Buffer[SMBIOS_STRING_MAX_LENGTH + 2];
  EFI_STATUS               Status;
  UINT8                    CpuFlavor=0;
  EFI_PEI_HOB_POINTERS     GuidHob;
  EFI_PLATFORM_INFO_HOB    *mPlatformInfo=NULL;
  UINTN                    NumHandles;
  EFI_HANDLE                        *HandleBuffer;
  UINTN                             Index;
  DXE_PCH_PLATFORM_POLICY_PROTOCOL  *PchPlatformPolicy;
  UINTN                             PciD31F0RegBase;
  UINT8                             count;
  UINT8                             Data8;
  UINT8                             Data8_1;

  CHAR16                            Name[40];
  UINT32                            MrcVersion;
  CHAR16                            *Version;
  SYSTEM_CONFIGURATION              SystemConfiguration;
  EFI_BOOT_MODE                     BootMode;
  UINTN                             VarSize;
  EFI_PLATFORM_INFO_HOB             *mPlatformInfo;
  
  Version                           = AllocateZeroPool (SMBIOS_STRING_MAX_LENGTH + 2);

  //
  // Get the System configuration
  //
  CopyMem (&SystemConfiguration, PcdGetPtr (PcdSystemConfiguration), sizeof(SYSTEM_CONFIGURATION));

  //
  // Get the HOB list.  If it is not present, then ASSERT.
  //
  mPlatformInfo = PcdGetPtr (PcdPlatformInfo);

  GetSeCVersion (SECVer);
  Status = GetBiosVersionDateTime (Version, NULL, NULL);
  UnicodeSPrint (Buffer, sizeof (Buffer), L"%s", Version);
  FreePool(Version);
  StrCpy (BiosVer, Buffer);

  Status = TGetGOPDriverName(Name);

  if(!EFI_ERROR(Status))
  {
    StrCpy (GOPVer, Name);
  }

  //
  //CpuFlavor
  //
  //CHV
  //CHV-DC Tablet        000
  //CHV-QC Notebook      001
  //CHV-QC Desktop       010

  //CPU flavor
  CpuFlavor = RShiftU64 (EfiReadMsr (MSR_IA32_PLATFORM_ID), 50) & 0x07;

  switch(CpuFlavor){
    case 0x0:
        UnicodeSPrint (Buffer, sizeof (Buffer), L"%s (%01x)", L"CHV-DC Tablet", CpuFlavor);
        StrCpy (CpuFlavorString, Buffer);
        break;
    case 0x01:
#if (TABLET_PF_ENABLE == 1)
        UnicodeSPrint (Buffer, sizeof (Buffer), L"%s (%01x)", L"CHV-QC Tablet", CpuFlavor);
#else
        UnicodeSPrint (Buffer, sizeof (Buffer), L"%s (%01x)", L"CHV-QC Notebook", CpuFlavor);
#endif
        StrCpy (CpuFlavorString, Buffer);
        break;
    case 0x02:
        UnicodeSPrint (Buffer, sizeof (Buffer), L"%s (%01x)", L"CHV-QC Desktop", CpuFlavor);
        StrCpy (CpuFlavorString, Buffer);
        break;
    case 0x03:
        UnicodeSPrint (Buffer, sizeof (Buffer), L"%s (%01x)", L"CHV-QC Notebook", CpuFlavor);
        StrCpy (CpuFlavorString, Buffer);
        break;
    default:
        UnicodeSPrint (Buffer, sizeof (Buffer), L"%s (%01x)", L"Unknown CPU", CpuFlavor);
        StrCpy (CpuFlavorString, Buffer);
        break;
  }

  if ( NULL != mPlatformInfo) {
    //
    // Board Id
    //
    UnicodeSPrint (Buffer, sizeof (Buffer), L"%x", mPlatformInfo->BoardId);
    StrCpy (BoardVer, Buffer);

    //
    // FAB ID
    //
    UnicodeSPrint (Buffer, sizeof (Buffer), L"%x", mPlatformInfo->FABID);
    StrCpy (FabVer, Buffer);
  }

  //
  //Update MRC Version
  //
  MrcVersion = MmioRead32 (MmPciAddress (0, 0, 0, 0, 0xF0));
  MrcVersion &= 0xffff;
  Index = EfiValueToString (Buffer, MrcVersion/100, PREFIX_ZERO, 0);
  StrCat (Buffer, L".");
  EfiValueToString (Buffer + Index + 1, (MrcVersion%100)/10, PREFIX_ZERO, 0);
  EfiValueToString (Buffer + Index + 2, (MrcVersion%100)%10, PREFIX_ZERO, 0);
  StrCpy (MrcVer, Buffer);

  //
  //Update Soc Version
  //

  //
  // Retrieve all instances of PCH Platform Policy protocol
  //
  Status = gBS->LocateHandleBuffer (
                  ByProtocol,
                  &gDxePchPlatformPolicyProtocolGuid,
                  NULL,
                  &NumHandles,
                  &HandleBuffer
                  );
  if (!EFI_ERROR (Status)) {
    //
    // Find the matching PCH Policy protocol
    //
    for (Index = 0; Index < NumHandles; Index++) {
      Status = gBS->HandleProtocol (
                      HandleBuffer[Index],
                      &gDxePchPlatformPolicyProtocolGuid,
                      &PchPlatformPolicy
                      );
      if (!EFI_ERROR (Status)) {
        PciD31F0RegBase = MmPciAddress (
                            0,
                            PchPlatformPolicy->BusNumber,
                            PCI_DEVICE_NUMBER_PCH_LPC,
                            PCI_FUNCTION_NUMBER_PCH_LPC,
                            0
                          );

         Data8 = MmioRead8 (PciD31F0RegBase + R_PCH_LPC_RID_CC) & B_PCH_LPC_RID_STEPPING_MASK;
         count = sizeof (SBRevisionTable) / sizeof (SBRevisionTable[0]);
         for (Index = 0; Index < count; Index++) {
           if(Data8 == SBRevisionTable[Index].RevId) {
              UnicodeSPrint (Buffer, sizeof (Buffer), L"%02x %a", Data8, SBRevisionTable[Index].String);
              StrCpy (SocVer, Buffer);
             break;
           }
         }
        break;
      }
    }
  }

  //
  // Microcode Revision
  //
  EfiWriteMsr (EFI_MSR_IA32_BIOS_SIGN_ID, 0);
  EfiCpuid (EFI_CPUID_VERSION_INFO, NULL);
  MicroCodeVersion = (UINT32) RShiftU64 (EfiReadMsr (EFI_MSR_IA32_BIOS_SIGN_ID), 32);
  UnicodeSPrint (Buffer, sizeof (Buffer), L"%x", MicroCodeVersion);
  StrCpy (uCodeVer, Buffer);

  //
  //Secure boot
  //
  Data8 = SystemConfiguration.SecureBoot;
  UnicodeSPrint (Buffer, sizeof(Buffer), L"%x", Data8);
  StrCpy (SecureBootMode, Buffer);

  //
  //Bootmode
  //
  BootMode = GetBootModeHob();
  UnicodeSPrint (Buffer, sizeof(Buffer), L"%x", BootMode);
  StrCpy (BootModeString, Buffer);

  //
  //SpeedStep
  //
  Data8 = SystemConfiguration.EnableGv;
  UnicodeSPrint (Buffer, sizeof(Buffer), L"%x", Data8);
  StrCpy (SpeedStepMode, Buffer);

  //
  //CPU Turbo
  //
  Data8 = SystemConfiguration.TurboModeEnable;
  UnicodeSPrint (Buffer, sizeof(Buffer), L"%x", Data8);
  StrCpy (CpuTurbo, Buffer);

  //
  //CState
  //
  Data8 = SystemConfiguration.MaxCState;
  UnicodeSPrint (Buffer, sizeof(Buffer), L"%x", Data8);
  StrCpy (MaxCState, Buffer);

  //
  //GFX Turbo
  //
  Data8 = SystemConfiguration.IgdTurboEnabled;
  UnicodeSPrint (Buffer, sizeof(Buffer), L"%x", Data8);
  StrCpy (GfxTurbo, Buffer);

  //
  //S0ix
  //
  Data8 = SystemConfiguration.S0ix;
  UnicodeSPrint (Buffer, sizeof(Buffer), L"%x", Data8);
  StrCpy (S0ix, Buffer);

  //
  //RC6
  //
  Data8 = SystemConfiguration.EnableRenderStandby;
  UnicodeSPrint (Buffer, sizeof(Buffer), L"%x", Data8);
  StrCpy (RC6, Buffer);

  //
  // Punit Version
  //
  Data8 = (UINT8) EfiReadMsr (0x667);
  UnicodeSPrint (Buffer, sizeof (Buffer), L"0x%x", Data8);
  StrCpy (PunitVer, Buffer);

  //
  // PMC Version
  //
  Data8 = (UINT8)((MmioRead32 (PMC_BASE_ADDRESS + R_PCH_PMC_PRSTS)>>16)&0x00FF);
  Data8_1 = (UINT8)((MmioRead32 (PMC_BASE_ADDRESS + R_PCH_PMC_PRSTS)>>24)&0x00FF);
  UnicodeSPrint (Buffer, sizeof (Buffer), L"0x%X_%X", Data8_1, Data8);
  StrCpy (PmcVer, Buffer);

  TGetTouchFirmwareVersion(TouchVer);

  return EFI_SUCCESS;
}
Exemple #13
0
/**
  This function get I2Cx controller base address (BAR0).

  @param I2cControllerIndex  Bus Number of I2C controller.

  @return I2C BAR. 
**/
UINTN
GetI2cBarAddr(
  IN    UINT8 I2cControllerIndex
  )
{
  EFI_STATUS           Status;
  EFI_GLOBAL_NVS_AREA_PROTOCOL  *GlobalNvsArea;
  UINTN  AcpiBaseAddr;
  UINTN  PciMmBase=0;

  ASSERT(gBS!=NULL);

  Status = gBS->LocateProtocol (
                  &gEfiGlobalNvsAreaProtocolGuid,
                  NULL,
                  &GlobalNvsArea
                  );
                  
  //
  // PCI mode from PEI ( Global NVS is not ready).
  //
  if (EFI_ERROR(Status)) {
    DEBUG ((EFI_D_INFO, "GetI2cBarAddr() gEfiGlobalNvsAreaProtocolGuid:%r\n", Status));
    //
    // Global NVS is not ready.
    //
    return 0;
  }

  AcpiBaseAddr =  *(UINTN*)((CHAR8*)GlobalNvsArea->Area + mI2cNvsBaseAddress[I2cControllerIndex + 1]);
  
  //
  //PCI mode from DXE (global NVS protocal) to LPSS OnReadytoBoot(swith to ACPI).
  //
  if(AcpiBaseAddr==0) {
    PciMmBase = MmPciAddress (
                  mLpssPciDeviceList[I2cControllerIndex + 1].Segment,
                  mLpssPciDeviceList[I2cControllerIndex + 1].BusNum,
                  mLpssPciDeviceList[I2cControllerIndex + 1].DeviceNum,
                  mLpssPciDeviceList[I2cControllerIndex + 1].FunctionNum,
                  0
                  );
    DEBUG((EFI_D_ERROR, "\nGetI2cBarAddr() I2C Device %x %x %x PciMmBase:%x\n", \
           mLpssPciDeviceList[I2cControllerIndex + 1].BusNum, \
           mLpssPciDeviceList[I2cControllerIndex + 1].DeviceNum, \
           mLpssPciDeviceList[I2cControllerIndex + 1].FunctionNum, PciMmBase));

    if (MmioRead32 (PciMmBase) != 0xFFFFFFFF)    {
      if((MmioRead32 (PciMmBase+R_PCH_LPSS_I2C_STSCMD)& B_PCH_LPSS_I2C_STSCMD_MSE)) {
        //
        // Get the address allocted.
        //
        mLpssPciDeviceList[I2cControllerIndex + 1].Bar0=MmioRead32 (PciMmBase+R_PCH_LPSS_I2C_BAR);     
        mLpssPciDeviceList[I2cControllerIndex + 1].Bar1=MmioRead32 (PciMmBase+R_PCH_LPSS_I2C_BAR1);
      }
    }
    AcpiBaseAddr =mLpssPciDeviceList[I2cControllerIndex+1].Bar0;
  }
  
  //
  // ACPI mode from BDS: LPSS OnReadytoBoot
  //
  else {
    DEBUG ((EFI_D_INFO, "GetI2cBarAddr() NVS Varialable is updated by this LIB or LPSS  \n"));
  }
  
  DEBUG ((EFI_D_INFO, "GetI2cBarAddr() I2cControllerIndex+1 0x%x AcpiBaseAddr:0x%x \n", (I2cControllerIndex + 1), AcpiBaseAddr));
  return AcpiBaseAddr;
}
Exemple #14
0
/**
  This function enables I2C controllers.

  @param I2cControllerIndex  Bus Number of I2C controllers.

  @return Result of the I2C initialization.
**/
EFI_STATUS
ProgramPciLpssI2C (
  IN  UINT8 I2cControllerIndex
  )
{
  UINT32                        PmcBase;
  UINTN                         PciMmBase=0;
  EFI_STATUS                    Status;
  EFI_GLOBAL_NVS_AREA_PROTOCOL  *GlobalNvsArea;

  UINT32 PmcFunctionDsiable[]= {
    B_PCH_PMC_FUNC_DIS_LPSS2_FUNC1,
    B_PCH_PMC_FUNC_DIS_LPSS2_FUNC2,
    B_PCH_PMC_FUNC_DIS_LPSS2_FUNC3,
    B_PCH_PMC_FUNC_DIS_LPSS2_FUNC4,
    B_PCH_PMC_FUNC_DIS_LPSS2_FUNC5,
    B_PCH_PMC_FUNC_DIS_LPSS2_FUNC6,
    B_PCH_PMC_FUNC_DIS_LPSS2_FUNC7
  };

  DEBUG ((EFI_D_INFO, "ProgramPciLpssI2C() Start\n"));

  //
  // Set the VLV Function Disable Register to ZERO
  //
  PmcBase = MmioRead32 (PCI_D31F0_REG_BASE + R_PCH_LPC_PMC_BASE) & B_PCH_LPC_PMC_BASE_BAR;
  if(MmioRead32(PmcBase+R_PCH_PMC_FUNC_DIS)&PmcFunctionDsiable[I2cControllerIndex]) {
    DEBUG ((EFI_D_INFO, "ProgramPciLpssI2C() End:I2C[%x] is disabled\n",I2cControllerIndex));
    return EFI_NOT_READY;
  }
  
  DEBUG ((EFI_D_INFO, "ProgramPciLpssI2C()------------I2cControllerIndex=%x,PMC=%x\n",I2cControllerIndex,MmioRead32(PmcBase+R_PCH_PMC_FUNC_DIS)));

  {
    PciMmBase = MmPciAddress (
                  mLpssPciDeviceList[I2cControllerIndex+1].Segment,
                  mLpssPciDeviceList[I2cControllerIndex+1].BusNum,
                  mLpssPciDeviceList[I2cControllerIndex+1].DeviceNum,
                  mLpssPciDeviceList[I2cControllerIndex+1].FunctionNum,
                  0
                  );
                  
    DEBUG((EFI_D_ERROR, "Program Pci Lpss I2C Device  %x %x %x PciMmBase:%x\n", \
           mLpssPciDeviceList[I2cControllerIndex+1].BusNum, \
           mLpssPciDeviceList[I2cControllerIndex+1].DeviceNum, \
           mLpssPciDeviceList[I2cControllerIndex+1].FunctionNum, PciMmBase));

    if (MmioRead32 (PciMmBase) != 0xFFFFFFFF)     {
      if((MmioRead32 (PciMmBase+R_PCH_LPSS_I2C_STSCMD)& B_PCH_LPSS_I2C_STSCMD_MSE)) {
        //
        // Get the address allocted.
        //
        mLpssPciDeviceList[I2cControllerIndex+1].Bar0=MmioRead32 (PciMmBase+R_PCH_LPSS_I2C_BAR);     
        mLpssPciDeviceList[I2cControllerIndex+1].Bar1=MmioRead32 (PciMmBase+R_PCH_LPSS_I2C_BAR1);
        DEBUG((EFI_D_ERROR, "ProgramPciLpssI2C() bar0:0x%x bar1:0x%x\n",mLpssPciDeviceList[I2cControllerIndex+1].Bar0, mLpssPciDeviceList[I2cControllerIndex+1].Bar1));
      } else {
        
        //
        // Program BAR 0
        //
        ASSERT (((mLpssPciDeviceList[I2cControllerIndex+1].Bar0 & B_PCH_LPSS_I2C_BAR_BA) == mLpssPciDeviceList[I2cControllerIndex+1].Bar0) && (mLpssPciDeviceList[I2cControllerIndex+1].Bar0 != 0));
        MmioWrite32 ((UINTN) (PciMmBase + R_PCH_LPSS_I2C_BAR), (UINT32) (mLpssPciDeviceList[I2cControllerIndex+1].Bar0 & B_PCH_LPSS_I2C_BAR_BA));
       
        //
        // Program BAR 1
        //
        ASSERT (((mLpssPciDeviceList[I2cControllerIndex+1].Bar1 & B_PCH_LPSS_I2C_BAR1_BA) == mLpssPciDeviceList[I2cControllerIndex+1].Bar1) && (mLpssPciDeviceList[I2cControllerIndex+1].Bar1 != 0));
        MmioWrite32 ((UINTN) (PciMmBase + R_PCH_LPSS_I2C_BAR1), (UINT32) (mLpssPciDeviceList[I2cControllerIndex+1].Bar1 & B_PCH_LPSS_I2C_BAR1_BA));
        
        //
        // Bus Master Enable & Memory Space Enable
        //
        MmioOr32 ((UINTN) (PciMmBase + R_PCH_LPSS_I2C_STSCMD), (UINT32) (B_PCH_LPSS_I2C_STSCMD_BME | B_PCH_LPSS_I2C_STSCMD_MSE));
        ASSERT (MmioRead32 (mLpssPciDeviceList[I2cControllerIndex+1].Bar0) != 0xFFFFFFFF);
      }
      
      //
      // Release Resets
      //
      MmioWrite32 (mLpssPciDeviceList[I2cControllerIndex+1].Bar0 + R_PCH_LPIO_I2C_MEM_RESETS,(B_PCH_LPIO_I2C_MEM_RESETS_FUNC | B_PCH_LPIO_I2C_MEM_RESETS_APB));
      
      //
      // Activate Clocks
      //
      MmioWrite32 (mLpssPciDeviceList[I2cControllerIndex+1].Bar0 + R_PCH_LPSS_I2C_MEM_PCP,0x80020003);//No use for A0

      DEBUG ((EFI_D_INFO, "ProgramPciLpssI2C() Programmed()\n"));
    }
    
    //
    // BDS: already switched to ACPI mode
    //
    else {
      ASSERT(gBS!=NULL);
      Status = gBS->LocateProtocol (
                      &gEfiGlobalNvsAreaProtocolGuid,
                      NULL,
                      &GlobalNvsArea
                      );
      if (EFI_ERROR(Status)) {
        DEBUG ((EFI_D_INFO, "GetI2cBarAddr() gEfiGlobalNvsAreaProtocolGuid:%r\n", Status));
        //
        // gEfiGlobalNvsAreaProtocolGuid is not ready.
        //
        return 0;
      }
      mLpssPciDeviceList[I2cControllerIndex + 1].Bar0 = *(UINTN*)((CHAR8*)GlobalNvsArea->Area + mI2cNvsBaseAddress[I2cControllerIndex + 1]);
      DEBUG ((EFI_D_INFO, "ProgramPciLpssI2C(): is switched to ACPI 0x:%x \n",mLpssPciDeviceList[I2cControllerIndex + 1].Bar0));
    }
  }
  
  DEBUG ((EFI_D_INFO, "ProgramPciLpssI2C() End\n"));

  return EFI_SUCCESS;
}