EFI_STATUS InitializeMMCHS ( VOID ) { UINT8 Data; EFI_STATUS Status; DEBUG ((DEBUG_BLKIO, "InitializeMMCHS()\n")); // Select Device group to belong to P1 device group in Power IC. Data = DEV_GRP_P1; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, VMMC1_DEV_GRP), 1, &Data); ASSERT_EFI_ERROR(Status); // Configure voltage regulator for MMC1 in Power IC to output 3.0 voltage. Data = VSEL_3_00V; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, VMMC1_DEDICATED_REG), 1, &Data); ASSERT_EFI_ERROR(Status); // After ramping up voltage, set VDDS stable bit to indicate that voltage level is stable. MmioOr32 (CONTROL_PBIAS_LITE, (PBIASLITEVMODE0 | PBIASLITEPWRDNZ0 | PBIASSPEEDCTRL0 | PBIASLITEVMODE1 | PBIASLITEWRDNZ1)); // Enable WP GPIO MmioAndThenOr32 (GPIO1_BASE + GPIO_OE, ~BIT23, BIT23); // Enable Card Detect Data = CARD_DETECT_ENABLE; gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID2, TPS65950_GPIO_CTRL), 1, &Data); return Status; }
STATIC VOID ConfigureUSBHost ( VOID ) { EFI_STATUS Status; UINT8 Data = 0; // Take USB host out of force-standby mode MmioWrite32 (UHH_SYSCONFIG, UHH_SYSCONFIG_MIDLEMODE_NO_STANDBY | UHH_SYSCONFIG_CLOCKACTIVITY_ON | UHH_SYSCONFIG_SIDLEMODE_NO_STANDBY | UHH_SYSCONFIG_ENAWAKEUP_ENABLE | UHH_SYSCONFIG_AUTOIDLE_ALWAYS_RUN); MmioWrite32 (UHH_HOSTCONFIG, UHH_HOSTCONFIG_P3_CONNECT_STATUS_DISCONNECT | UHH_HOSTCONFIG_P2_CONNECT_STATUS_DISCONNECT | UHH_HOSTCONFIG_P1_CONNECT_STATUS_DISCONNECT | UHH_HOSTCONFIG_ENA_INCR_ALIGN_DISABLE | UHH_HOSTCONFIG_ENA_INCR16_ENABLE | UHH_HOSTCONFIG_ENA_INCR8_ENABLE | UHH_HOSTCONFIG_ENA_INCR4_ENABLE | UHH_HOSTCONFIG_AUTOPPD_ON_OVERCUR_EN_ON | UHH_HOSTCONFIG_P1_ULPI_BYPASS_ULPI_MODE); // USB reset (GPIO 147 - Port 5 pin 19) output high MmioAnd32 (GPIO5_BASE + GPIO_OE, ~BIT19); MmioWrite32 (GPIO5_BASE + GPIO_SETDATAOUT, BIT19); // Get the Power IC protocol Status = gBS->LocateProtocol (&gEmbeddedExternalDeviceProtocolGuid, NULL, (VOID **)&gTPS65950); ASSERT_EFI_ERROR (Status); // Power the USB PHY Data = VAUX_DEV_GRP_P1; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, VAUX2_DEV_GRP), 1, &Data); ASSERT_EFI_ERROR(Status); Data = VAUX_DEDICATED_18V; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, VAUX2_DEDICATED), 1, &Data); ASSERT_EFI_ERROR (Status); // Enable power to the USB hub Status = gTPS65950->Read (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID3, LEDEN), 1, &Data); ASSERT_EFI_ERROR (Status); // LEDAON controls the power to the USB host, PWM is disabled Data &= ~LEDAPWM; Data |= LEDAON; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID3, LEDEN), 1, &Data); ASSERT_EFI_ERROR (Status); }
EFI_STATUS InitializeMMCHS ( VOID ) { UINT8 Data; EFI_STATUS Status; DEBUG ((DEBUG_BLKIO, "InitializeMMCHS()\n")); // Disconnect PBIAS prior to voltage change MmioAnd32 (CONTROL_PBIAS_LITE, ~(PBIASPWRDNZ | PBIASLITEPWRDNZ)); // Disable VMMC LDO Data = VMMC_CFG_STATE_OFF; Status = gTWL6030->Write (gTWL6030, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID1, VMMC_CFG_STATE), 1, &Data); ASSERT_EFI_ERROR(Status); // Wait for stabilization gBS->Stall(500); // Configure VMMC LDO to output 3.0 voltage. Data = VSEL_3_00V; Status = gTWL6030->Write (gTWL6030, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID1, VMMC_CFG_VOLTAGE), 1, &Data); ASSERT_EFI_ERROR(Status); // Enable VMMC LDO Data = VMMC_CFG_STATE_ON; Status = gTWL6030->Write (gTWL6030, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID1, VMMC_CFG_STATE), 1, &Data); ASSERT_EFI_ERROR(Status); // Wait for stabilization gBS->Stall(500); // PBIAS in normal operating mode (not HiZ) MmioAnd32 (CONTROL_PBIAS_LITE, ~PBIASHIZ); // Select VMODE=3V and connect VDDS_MMC1 to PBIAS MmioOr32 (CONTROL_PBIAS_LITE, (PBIASVMODE3V|PBIASLITEPWRDNZ)); // Wait for PBIAS supply detection gBS->Stall(100); // Connect pads MmioOr32 (CONTROL_PBIAS_LITE, PBIASPWRDNZ); // Stop here if supply detector did not sense 3V ASSERT( !(MmioRead32(CONTROL_PBIAS_LITE) & PBIASVMODEERR) ); return Status; }
EFI_STATUS HwInitializeDisplay ( UINTN VramBaseAddress, UINTN VramSize ) { EFI_STATUS Status; UINT8 Data; EFI_TPL OldTpl; EMBEDDED_EXTERNAL_DEVICE *gTPS65950; // Enable power lines used by TFP410 Status = gBS->LocateProtocol (&gEmbeddedExternalDeviceProtocolGuid, NULL, (VOID **)&gTPS65950); ASSERT_EFI_ERROR (Status); OldTpl = gBS->RaiseTPL(TPL_NOTIFY); Data = VAUX_DEV_GRP_P1; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, VPLL2_DEV_GRP), 1, &Data); ASSERT_EFI_ERROR(Status); Data = VAUX_DEDICATED_18V; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, VPLL2_DEDICATED), 1, &Data); ASSERT_EFI_ERROR (Status); // Power up TFP410 (set GPIO2 on TPS - for BeagleBoard-xM) Status = gTPS65950->Read (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID2, GPIODATADIR1), 1, &Data); ASSERT_EFI_ERROR (Status); Data |= BIT2; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID2, GPIODATADIR1), 1, &Data); ASSERT_EFI_ERROR (Status); Data = BIT2; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID2, SETGPIODATAOUT1), 1, &Data); ASSERT_EFI_ERROR (Status); gBS->RestoreTPL(OldTpl); // Power up TFP410 (set GPIO 170 - for older BeagleBoards) MmioAnd32 (GPIO6_BASE + GPIO_OE, ~BIT10); MmioOr32 (GPIO6_BASE + GPIO_SETDATAOUT, BIT10); return EFI_SUCCESS; }
/** Sets the current local time and date information. @param Time A pointer to the current time. @retval EFI_SUCCESS The operation completed successfully. @retval EFI_INVALID_PARAMETER A time field is out of range. @retval EFI_DEVICE_ERROR The time could not be set due due to hardware error. **/ EFI_STATUS EFIAPI LibSetTime ( IN EFI_TIME *Time ) { EFI_STATUS Status; UINT8 Data; UINT8 MonthDayCount[12] = { 31, 29, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31 }; EFI_TPL OldTpl; // Input validation according both to UEFI spec and hardware constraints // UEFI spec says valid year range is 1900-9999 but TPS only supports 2000-2099 if ( (Time == NULL) || (Time->Year < 2000 || Time->Year > 2099) || (Time->Month < 1 || Time->Month > 12) || (Time->Day < 1 || Time->Day > MonthDayCount[Time->Month]) || (Time->Hour > 23) || (Time->Minute > 59) || (Time->Second > 59) || (Time->Nanosecond > 999999999) || ((Time->TimeZone < -1440 || Time->TimeZone > 1440) && Time->TimeZone != 2047) ) { return EFI_INVALID_PARAMETER; } OldTpl = gBS->RaiseTPL(TPL_NOTIFY); Data = Time->Year - 2000; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, YEARS_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Data = ((Time->Month / 10) << 4) | (Time->Month % 10); Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, MONTHS_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Data = ((Time->Day / 10) << 4) | (Time->Day % 10); Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, DAYS_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Data = ((Time->Hour / 10) << 4) | (Time->Hour % 10); Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, HOURS_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Data = ((Time->Minute / 10) << 4) | (Time->Minute % 10); Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, MINUTES_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Data = ((Time->Second / 10) << 4) | (Time->Second % 10); Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, SECONDS_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; TimeZone = Time->TimeZone; EXIT: gBS->RestoreTPL(OldTpl); return (Status == EFI_SUCCESS) ? Status : EFI_DEVICE_ERROR; }
BOOLEAN MMCIsCardPresent ( IN EFI_MMC_HOST_PROTOCOL *This ) { EFI_STATUS Status; UINT8 Data; // // Card detect is a GPIO0 on the TPS65950 // Status = gTPS65950->Read (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID2, GPIODATAIN1), 1, &Data); if (EFI_ERROR (Status)) { return FALSE; } return !(Data & CARD_DETECT_BIT); }
BOOLEAN MMCIsCardPresent ( IN EFI_MMC_HOST_PROTOCOL *This ) { EFI_STATUS Status; UINT8 Data; // // Card detect is a GPIO0 on the TWL6030 // Status = gTWL6030->Read (gTWL6030, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID1, MMCCTRL), 1, &Data); if (EFI_ERROR (Status)) { return FALSE; } return !(Data & CARD_DET_STS_MMC); }
/** This is the declaration of an EFI image entry point. This can be the entry point to an application written to this specification, an EFI boot service driver, or an EFI runtime driver. @param ImageHandle Handle that identifies the loaded image. @param SystemTable System Table for this image. @retval EFI_SUCCESS The operation completed successfully. **/ EFI_STATUS EFIAPI LibRtcInitialize ( IN EFI_HANDLE ImageHandle, IN EFI_SYSTEM_TABLE *SystemTable ) { EFI_STATUS Status; EFI_HANDLE Handle; UINT8 Data; EFI_TPL OldTpl; Status = gBS->LocateProtocol (&gEmbeddedExternalDeviceProtocolGuid, NULL, (VOID **)&gTPS65950); ASSERT_EFI_ERROR(Status); OldTpl = gBS->RaiseTPL(TPL_NOTIFY); Data = 1; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, RTC_CTRL_REG), 1, &Data); ASSERT_EFI_ERROR(Status); gBS->RestoreTPL(OldTpl); // Setup the setters and getters gRT->GetTime = LibGetTime; gRT->SetTime = LibSetTime; gRT->GetWakeupTime = LibGetWakeupTime; gRT->SetWakeupTime = LibSetWakeupTime; // Install the protocol Handle = NULL; Status = gBS->InstallMultipleProtocolInterfaces ( &Handle, &gEfiRealTimeClockArchProtocolGuid, NULL, NULL ); return Status; }
/** Returns the current time and date information, and the time-keeping capabilities of the hardware platform. @param Time A pointer to storage to receive a snapshot of the current time. @param Capabilities An optional pointer to a buffer to receive the real time clock device's capabilities. @retval EFI_SUCCESS The operation completed successfully. @retval EFI_INVALID_PARAMETER Time is NULL. @retval EFI_DEVICE_ERROR The time could not be retrieved due to hardware error. **/ EFI_STATUS EFIAPI LibGetTime ( OUT EFI_TIME *Time, OUT EFI_TIME_CAPABILITIES *Capabilities ) { EFI_STATUS Status; UINT8 Data; EFI_TPL OldTpl; if (Time == NULL) { return EFI_INVALID_PARAMETER; } OldTpl = gBS->RaiseTPL(TPL_NOTIFY); /* Get time and date */ ZeroMem(Time, sizeof(EFI_TIME)); // Latch values Status = gTPS65950->Read (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, RTC_CTRL_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Data |= BIT6; Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, RTC_CTRL_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; // Read registers Status = gTPS65950->Read (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, YEARS_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Time->Year = 2000 + ((Data >> 4) & 0xF) * 10 + (Data & 0xF); Status = gTPS65950->Read (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, MONTHS_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Time->Month = ((Data >> 4) & 0x1) * 10 + (Data & 0xF); Status = gTPS65950->Read (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, DAYS_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Time->Day = ((Data >> 4) & 0x3) * 10 + (Data & 0xF); Status = gTPS65950->Read (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, HOURS_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Time->Hour = ((Data >> 4) & 0x3) * 10 + (Data & 0xF); Status = gTPS65950->Read (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, MINUTES_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Time->Minute = ((Data >> 4) & 0x7) * 10 + (Data & 0xF); Status = gTPS65950->Read (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, SECONDS_REG), 1, &Data); if (Status != EFI_SUCCESS) goto EXIT; Time->Second = ((Data >> 4) & 0x7) * 10 + (Data & 0xF); Time->TimeZone = TimeZone; // TODO: check what to use here Time->Daylight = EFI_TIME_ADJUST_DAYLIGHT; // Set capabilities // TODO: Set real capabilities if (Capabilities != NULL) { Capabilities->Resolution = 1; Capabilities->Accuracy = 50000000; Capabilities->SetsToZero = FALSE; } EXIT: gBS->RestoreTPL(OldTpl); return (Status == EFI_SUCCESS) ? Status : EFI_DEVICE_ERROR; }