4. Calls MRC to initialize memory and install a PPI notify to do post memory initialization.\r
This file contains the main entrypoint of the PEIM.\r
\r
-Copyright (c) 2013 Intel Corporation.\r
+Copyright (c) 2013 - 2016 Intel Corporation.\r
\r
-This program and the accompanying materials\r
-are licensed and made available under the terms and conditions of the BSD License\r
-which accompanies this distribution. The full text of the license may be found at\r
-http://opensource.org/licenses/bsd-license.php\r
-\r
-THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
-WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
+SPDX-License-Identifier: BSD-2-Clause-Patent\r
\r
**/\r
\r
SaveBarReg = PciRead32 (DevPcieAddr + R_IOH_MAC_MEMBAR);\r
\r
//\r
- // Use predefined tempory memory resource\r
+ // Use predefined temporary memory resource\r
//\r
PciWrite32 ( DevPcieAddr + R_IOH_MAC_MEMBAR, Bar0);\r
PciWrite8 ( DevPcieAddr + PCI_COMMAND_OFFSET, EFI_PCI_COMMAND_MEMORY_SPACE);\r
PciWrite16 (DevPcieAddr + PCI_COMMAND_OFFSET, SaveCmdReg);\r
}\r
\r
+/**\r
+ Initialize state of I2C GPIO expanders.\r
+\r
+ @param PlatformType Platform type for GPIO expander init.\r
+\r
+**/\r
+EFI_STATUS\r
+EarlyPlatformConfigGpioExpanders (\r
+ IN CONST EFI_PLATFORM_TYPE PlatformType,\r
+ EFI_BOOT_MODE BootMode\r
+ )\r
+{\r
+ EFI_STATUS Status;\r
+ EFI_I2C_DEVICE_ADDRESS I2CSlaveAddress;\r
+ UINTN Length;\r
+ UINTN ReadLength;\r
+ UINT8 Buffer[2];\r
+\r
+ //\r
+ // Configure GPIO expanders for Galileo Gen 2\r
+ // Route I2C pins to Arduino header\r
+ // Set all GPIO expander pins connected to the Reset Button as inputs\r
+ //\r
+ if (PlatformType == GalileoGen2) {\r
+ //\r
+ // Configure AMUX1_IN (EXP2.P1_4) as an output\r
+ //\r
+ PlatformPcal9555GpioSetDir (\r
+ GALILEO_GEN2_IOEXP2_7BIT_SLAVE_ADDR, // IO Expander 2.\r
+ 12, // P1-4.\r
+ FALSE // Configure as output\r
+ );\r
+\r
+ //\r
+ // Set AMUX1_IN(EXP2.P1_4) low to route I2C to Arduino Shield connector\r
+ //\r
+ PlatformPcal9555GpioSetLevel (\r
+ GALILEO_GEN2_IOEXP2_7BIT_SLAVE_ADDR, // IO Expander 2.\r
+ 12, // P1-4. \r
+ FALSE // Set pin low\r
+ );\r
+\r
+ //\r
+ // Configure Reset Button(EXP1.P1_7) as an input\r
+ //\r
+ PlatformPcal9555GpioSetDir (\r
+ GALILEO_GEN2_IOEXP1_7BIT_SLAVE_ADDR, // IO Expander 1.\r
+ 15, // P1-7.\r
+ TRUE\r
+ );\r
+\r
+ //\r
+ // Disable pullup on Reset Button(EXP1.P1_7)\r
+ //\r
+ PlatformPcal9555GpioDisablePull (\r
+ GALILEO_GEN2_IOEXP1_7BIT_SLAVE_ADDR, // IO Expander 1.\r
+ 15 // P1-7.\r
+ );\r
+\r
+ //\r
+ // Configure Reset Button(EXP2.P1_7) as an input\r
+ //\r
+ PlatformPcal9555GpioSetDir (\r
+ GALILEO_GEN2_IOEXP2_7BIT_SLAVE_ADDR, // IO Expander 2.\r
+ 15, // P1-7.\r
+ TRUE\r
+ );\r
+\r
+ //\r
+ // Disable pullup on Reset Button(EXP2.P1_7)\r
+ //\r
+ PlatformPcal9555GpioDisablePull (\r
+ GALILEO_GEN2_IOEXP2_7BIT_SLAVE_ADDR, // IO Expander 2.\r
+ 15 // P1-7.\r
+ );\r
+\r
+ if (BootMode != BOOT_IN_RECOVERY_MODE) {\r
+ //\r
+ // Read state of Reset Button - EXP2.P1_7\r
+ // This GPIO is pulled high when the button is not pressed\r
+ // This GPIO reads low when button is pressed\r
+ //\r
+ if (!PlatformPcal9555GpioGetState (\r
+ GALILEO_GEN2_IOEXP2_7BIT_SLAVE_ADDR, // IO Expander 2\r
+ 15 // P1-7\r
+ )) {\r
+ DEBUG ((EFI_D_INFO, " Force Recovery mode and reset\n"));\r
+\r
+ //\r
+ // Set 'B_CFG_STICKY_RW_FORCE_RECOVERY' sticky bit so we know we need to do a recovery following warm reset\r
+ //\r
+ QNCAltPortWrite (\r
+ QUARK_SCSS_SOC_UNIT_SB_PORT_ID,\r
+ QUARK_SCSS_SOC_UNIT_CFG_STICKY_RW,\r
+ QNCAltPortRead (QUARK_SCSS_SOC_UNIT_SB_PORT_ID, QUARK_SCSS_SOC_UNIT_CFG_STICKY_RW) | B_CFG_STICKY_RW_FORCE_RECOVERY\r
+ );\r
+ ResetWarm();\r
+ }\r
+ }\r
+ }\r
+\r
+ //\r
+ // Configure GPIO expanders for Galileo Gen 2\r
+ // Set all GPIO expander pins connected to the Reset Button as inputs\r
+ // Route I2C pins to Arduino header\r
+ //\r
+ if (PlatformType == Galileo) {\r
+ //\r
+ // Detect the I2C Slave Address of the GPIO Expander\r
+ //\r
+ if (PlatformLegacyGpioGetLevel (R_QNC_GPIO_RGLVL_RESUME_WELL, GALILEO_DETERMINE_IOEXP_SLA_RESUMEWELL_GPIO)) {\r
+ I2CSlaveAddress.I2CDeviceAddress = GALILEO_IOEXP_J2HI_7BIT_SLAVE_ADDR;\r
+ } else {\r
+ I2CSlaveAddress.I2CDeviceAddress = GALILEO_IOEXP_J2LO_7BIT_SLAVE_ADDR;\r
+ }\r
+ DEBUG ((EFI_D_INFO, "Galileo GPIO Expender Slave Address = %02x\n", I2CSlaveAddress.I2CDeviceAddress));\r
+\r
+ //\r
+ // Set I2C_MUX (GPORT1_BIT5) low to route I2C to Arduino Shield connector\r
+ //\r
+\r
+ //\r
+ // Select GPIO Expander GPORT1\r
+ //\r
+ Length = 2;\r
+ Buffer[0] = 0x18; //sub-address\r
+ Buffer[1] = 0x01; //data\r
+ Status = I2cWriteMultipleByte (\r
+ I2CSlaveAddress,\r
+ EfiI2CSevenBitAddrMode,\r
+ &Length,\r
+ &Buffer\r
+ );\r
+ ASSERT_EFI_ERROR (Status);\r
+\r
+ //\r
+ // Read "Pin Direction" of GPIO Expander GPORT1\r
+ //\r
+ Length = 1;\r
+ ReadLength = 1;\r
+ Buffer[1] = 0x1C;\r
+ Status = I2cReadMultipleByte (\r
+ I2CSlaveAddress,\r
+ EfiI2CSevenBitAddrMode,\r
+ &Length,\r
+ &ReadLength,\r
+ &Buffer[1]\r
+ );\r
+ ASSERT_EFI_ERROR (Status);\r
+\r
+ //\r
+ // Configure GPIO Expander GPORT1_BIT5 as an output\r
+ //\r
+ Length = 2;\r
+ Buffer[0] = 0x1C; //sub-address\r
+ Buffer[1] = (UINT8)(Buffer[1] & (~BIT5)); //data\r
+\r
+ Status = I2cWriteMultipleByte (\r
+ I2CSlaveAddress,\r
+ EfiI2CSevenBitAddrMode,\r
+ &Length,\r
+ &Buffer\r
+ );\r
+ ASSERT_EFI_ERROR (Status);\r
+\r
+ //\r
+ // Set GPIO Expander GPORT1_BIT5 low\r
+ //\r
+ Length = 2;\r
+ Buffer[0] = 0x09; //sub-address\r
+ Buffer[1] = (UINT8)(~BIT5); //data\r
+\r
+ Status = I2cWriteMultipleByte (\r
+ I2CSlaveAddress,\r
+ EfiI2CSevenBitAddrMode,\r
+ &Length,\r
+ &Buffer\r
+ );\r
+ ASSERT_EFI_ERROR (Status);\r
+\r
+ //\r
+ // Configure RESET_N_SHLD (GPORT5_BIT0) and SW_RESET_N_SHLD (GPORT5_BIT1) as inputs\r
+ //\r
+\r
+ //\r
+ // Select GPIO Expander GPORT5\r
+ //\r
+ Length = 2;\r
+ Buffer[0] = 0x18;\r
+ Buffer[1] = 0x05;\r
+ Status = I2cWriteMultipleByte (\r
+ I2CSlaveAddress,\r
+ EfiI2CSevenBitAddrMode,\r
+ &Length,\r
+ &Buffer\r
+ );\r
+ ASSERT_EFI_ERROR (Status);\r
+\r
+ //\r
+ // Read "Pin Direction" of GPIO Expander GPORT5\r
+ //\r
+ Length = 1;\r
+ ReadLength = 1;\r
+ Buffer[1] = 0x1C;\r
+ Status = I2cReadMultipleByte (\r
+ I2CSlaveAddress,\r
+ EfiI2CSevenBitAddrMode,\r
+ &Length,\r
+ &ReadLength,\r
+ &Buffer[1]\r
+ );\r
+ ASSERT_EFI_ERROR (Status);\r
+\r
+ //\r
+ // Configure GPIO Expander GPORT5_BIT0 and GPORT5_BIT1 as inputs\r
+ //\r
+ Length = 2;\r
+ Buffer[0] = 0x1C;\r
+ Buffer[1] = Buffer[1] | BIT0 | BIT1;\r
+ Status = I2cWriteMultipleByte (\r
+ I2CSlaveAddress,\r
+ EfiI2CSevenBitAddrMode,\r
+ &Length,\r
+ &Buffer\r
+ );\r
+ ASSERT_EFI_ERROR (Status);\r
+\r
+ if (BootMode != BOOT_IN_RECOVERY_MODE) {\r
+ //\r
+ // Read state of RESET_N_SHLD (GPORT5_BIT0)\r
+ //\r
+ Buffer[1] = 5;\r
+ Length = 1;\r
+ ReadLength = 1;\r
+ Status = I2cReadMultipleByte (\r
+ I2CSlaveAddress,\r
+ EfiI2CSevenBitAddrMode,\r
+ &Length,\r
+ &ReadLength,\r
+ &Buffer[1]\r
+ );\r
+ ASSERT_EFI_ERROR (Status);\r
+\r
+ //\r
+ // Return the state of GPORT5_BIT0\r
+ //\r
+ if ((Buffer[1] & BIT0) == 0) {\r
+ DEBUG ((EFI_D_INFO, " Force Recovery mode and reset\n"));\r
+\r
+ //\r
+ // Set 'B_CFG_STICKY_RW_FORCE_RECOVERY' sticky bit so we know we need to do a recovery following warm reset\r
+ //\r
+ QNCAltPortWrite (\r
+ QUARK_SCSS_SOC_UNIT_SB_PORT_ID,\r
+ QUARK_SCSS_SOC_UNIT_CFG_STICKY_RW,\r
+ QNCAltPortRead (QUARK_SCSS_SOC_UNIT_SB_PORT_ID, QUARK_SCSS_SOC_UNIT_CFG_STICKY_RW) | B_CFG_STICKY_RW_FORCE_RECOVERY\r
+ );\r
+ ResetWarm();\r
+ }\r
+ }\r
+ }\r
+\r
+ return EFI_SUCCESS;\r
+}\r
+\r
/**\r
This is the entrypoint of PEIM\r
\r
DEBUG ((EFI_D_INFO, "Platform Erratas After MRC\n"));\r
PlatformErratasPostMrc ();\r
\r
+ //\r
+ //\r
+ //\r
+ DEBUG ((EFI_D_INFO, "EarlyPlatformConfigGpioExpanders ()\n"));\r
+ EarlyPlatformConfigGpioExpanders (PlatformType, BootMode);\r
+\r
//\r
// Now that all of the pre-permanent memory activities have\r
// been taken care of, post a call-back for the permanent-memory\r
\r
//\r
// Check if RMU reset system due to access violations.\r
- // RMU updates a SOC Unit register before reseting the system.\r
+ // RMU updates a SOC Unit register before resetting the system.\r
//\r
RegValue = QNCAltPortRead (QUARK_SCSS_SOC_UNIT_SB_PORT_ID, QUARK_SCSS_SOC_UNIT_CFG_STICKY_RW);\r
if ((RegValue & B_CFG_STICKY_RW_VIOLATION) != 0) {\r
//\r
if (CheckForResetDueToErrors (TRUE)) {\r
if(FeaturePcdGet (WaitIfResetDueToError)) {\r
- DEBUG ((EFI_D_ERROR, "Press any key to continue.\n"));\r
- PlatformDebugPortGetChar8 ();\r
+ DEBUG ((EFI_D_ERROR, "Wait 10 seconds.\n"));\r
+ MicroSecondDelay(10000000);\r
}\r
}\r
\r
SaveBarReg = PciRead32 (DevPcieAddr + PcdGet8 (PcdIohGpioBarRegister));\r
\r
//\r
- // Use predefined tempory memory resource.\r
+ // Use predefined temporary memory resource.\r
//\r
PciWrite32 ( DevPcieAddr + PcdGet8 (PcdIohGpioBarRegister), IohGpioBase);\r
PciWrite8 ( DevPcieAddr + PCI_COMMAND_OFFSET, EFI_PCI_COMMAND_MEMORY_SPACE);\r