fusee-cpp: Implement mbist workaround

This commit is contained in:
Michael Scire 2021-08-21 15:49:36 -07:00
parent 635aeb09b9
commit bc3bcb02ce
10 changed files with 226 additions and 1 deletions

View File

@ -29,6 +29,21 @@ namespace ams::clkrst {
void EnableI2c1Clock();
void EnableI2c5Clock();
void EnableHost1xClock();
void EnableTsecClock();
void EnableSorSafeClock();
void EnableSor0Clock();
void EnableSor1Clock();
void EnableKfuseClock();
void DisableI2c1Clock();
void DisableHost1xClock();
void DisableTsecClock();
void DisableSorSafeClock();
void DisableSor0Clock();
void DisableSor1Clock();
void DisableKfuseClock();
}

View File

@ -100,6 +100,8 @@ namespace ams::fuse {
DramId GetDramId();
bool GetSecureBootKey(void *dst);
void GetEcid(br::BootEcid *out);
HardwareType GetHardwareType();
HardwareState GetHardwareState();

View File

@ -18,6 +18,8 @@
namespace ams::tsec {
bool RunTsecFirmware(const void *fw, size_t fw_size);
void Lock();
}

View File

@ -62,11 +62,21 @@ namespace ams::clkrst {
.reset_offset = CLK_RST_CONTROLLER_RST_DEVICES_##_REG_, \
.clk_enb_offset = CLK_RST_CONTROLLER_CLK_OUT_ENB_##_REG_, \
.clk_src_offset = CLK_RST_CONTROLLER_CLK_SOURCE_##_NAME_, \
.index = CLK_RST_CONTROLLER_CLK_ENB_##_NAME_##_INDEX, \
.index = CLK_RST_CONTROLLER_CLK_ENB_##_NAME_##_INDEX, \
.clk_src = CLK_RST_CONTROLLER_CLK_SOURCE_##_NAME_##_##_NAME_##_CLK_SRC_##_CLK_, \
.clk_div = _DIV_, \
}
#define DEFINE_CLOCK_PARAMETERS_WITHOUT_CLKDIV(_VARNAME_, _REG_, _NAME_) \
constexpr inline const ClockParameters _VARNAME_ = { \
.reset_offset = CLK_RST_CONTROLLER_RST_DEVICES_##_REG_, \
.clk_enb_offset = CLK_RST_CONTROLLER_CLK_OUT_ENB_##_REG_, \
.clk_src_offset = 0, \
.index = CLK_RST_CONTROLLER_CLK_ENB_##_NAME_##_INDEX, \
.clk_src = 0, \
.clk_div = 0, \
}
DEFINE_CLOCK_PARAMETERS(UartAClock, L, UARTA, PLLP_OUT0, 0);
DEFINE_CLOCK_PARAMETERS(UartBClock, L, UARTB, PLLP_OUT0, 0);
DEFINE_CLOCK_PARAMETERS(UartCClock, H, UARTC, PLLP_OUT0, 0);
@ -74,6 +84,14 @@ namespace ams::clkrst {
DEFINE_CLOCK_PARAMETERS(I2c5Clock, H, I2C5, CLK_M, 0);
DEFINE_CLOCK_PARAMETERS(ActmonClock, V, ACTMON, CLK_M, 0);
DEFINE_CLOCK_PARAMETERS(Host1xClock, L, HOST1X, PLLP_OUT0, 3);
DEFINE_CLOCK_PARAMETERS(TsecClock, U, TSEC, PLLP_OUT0, 2);
DEFINE_CLOCK_PARAMETERS(Sor1Clock, X, SOR1, PLLP_OUT0, 2);
DEFINE_CLOCK_PARAMETERS_WITHOUT_CLKDIV(SorSafeClock, Y, SOR_SAFE);
DEFINE_CLOCK_PARAMETERS_WITHOUT_CLKDIV(Sor0Clock, X, SOR0);
DEFINE_CLOCK_PARAMETERS_WITHOUT_CLKDIV(KfuseClock, H, KFUSE);
}
void SetRegisterAddress(uintptr_t address) {
@ -108,8 +126,56 @@ namespace ams::clkrst {
EnableClock(I2c5Clock);
}
void EnableHost1xClock() {
EnableClock(Host1xClock);
}
void EnableTsecClock() {
EnableClock(TsecClock);
}
void EnableSorSafeClock() {
EnableClock(SorSafeClock);
}
void EnableSor0Clock() {
EnableClock(Sor0Clock);
}
void EnableSor1Clock() {
EnableClock(Sor1Clock);
}
void EnableKfuseClock() {
EnableClock(KfuseClock);
}
void DisableI2c1Clock() {
DisableClock(I2c1Clock);
}
void DisableHost1xClock() {
DisableClock(Host1xClock);
}
void DisableTsecClock() {
DisableClock(TsecClock);
}
void DisableSorSafeClock() {
DisableClock(SorSafeClock);
}
void DisableSor0Clock() {
DisableClock(Sor0Clock);
}
void DisableSor1Clock() {
DisableClock(Sor1Clock);
}
void DisableKfuseClock() {
DisableClock(KfuseClock);
}
}

View File

@ -432,6 +432,19 @@ namespace ams::fuse {
return reg::HasValue(GetChipRegistersCommon().FUSE_SECURITY_MODE, FUSE_REG_BITS_ENUM(SECURITY_MODE_SECURITY_MODE, ENABLED));
}
bool GetSecureBootKey(void *dst) {
/* Get the sbk from fuse data. */
bool valid = false;
for (size_t i = 0; i < 4; ++i) {
const u32 key_word = GetChipRegistersCommon().FUSE_PRIVATE_KEY[i];
static_cast<u32 *>(dst)[i] = key_word;
valid |= key_word != 0xFFFFFFFF;
}
return valid;
}
void ConfigureFuseBypass() {
/* Make the fuse registers visible. */
clkrst::SetFuseVisibility(true);

View File

@ -19,8 +19,41 @@ namespace ams::tsec {
namespace {
enum TsecResult {
TsecResult_Success = 0xB0B0B0B0,
TsecResult_Failure = 0xD0D0D0D0,
};
bool RunFirmwareImpl(const void *fw, size_t fw_size) {
/* Enable relevant clocks. */
clkrst::EnableHost1xClock();
clkrst::EnableTsecClock();
clkrst::EnableSorSafeClock();
clkrst::EnableSor0Clock();
clkrst::EnableSor1Clock();
clkrst::EnableKfuseClock();
/* Disable clocks once we're done. */
ON_SCOPE_EXIT {
clkrst::DisableHost1xClock();
clkrst::DisableTsecClock();
clkrst::DisableSorSafeClock();
clkrst::DisableSor0Clock();
clkrst::DisableSor1Clock();
clkrst::DisableKfuseClock();
};
/* TODO */
AMS_UNUSED(fw, fw_size);
return true;
}
}
bool RunTsecFirmware(const void *fw, size_t fw_size) {
/* TODO */
AMS_UNUSED(fw, fw_size);
return RunFirmwareImpl(fw, fw_size);
}
void Lock() {

View File

@ -29,6 +29,7 @@
#include <vapours/tegra/tegra_evp.hpp>
#include <vapours/tegra/tegra_flow_ctlr.hpp>
#include <vapours/tegra/tegra_i2c.hpp>
#include <vapours/tegra/tegra_i2s.hpp>
#include <vapours/tegra/tegra_ictlr.hpp>
#include <vapours/tegra/tegra_mc.hpp>
#include <vapours/tegra/tegra_mipi_cal.hpp>

View File

@ -62,6 +62,11 @@ DEFINE_CLK_RST_REG(MISC_CLK_ENB_CFG_ALL_VISIBLE, 28, 1);
DEFINE_CLK_RST_REG_BIT_ENUM(OSC_CTRL_XOE, 0, DISABLE, ENABLE);
DEFINE_CLK_RST_REG(OSC_CTRL_XOFS, 4, 6);
DEFINE_CLK_RST_REG_BIT_ENUM(PLLD_BASE_CSI_CLK_SRC, 23, BRICK, PLL_D);
DEFINE_CLK_RST_REG_BIT_ENUM(PLLD_BASE_PLLD_REF_DIS, 29, REF_ENABLE, REF_DISABLE);
DEFINE_CLK_RST_REG_BIT_ENUM(PLLD_BASE_PLLD_ENABLE, 30, DISABLE, ENABLE);
DEFINE_CLK_RST_REG_BIT_ENUM(PLLD_BASE_PLLD_BYPASS, 31, DISABLE, ENABLE);
DEFINE_CLK_RST_REG_BIT_ENUM(PLLX_BASE_PLLX_ENABLE, 30, DISABLE, ENABLE);
DEFINE_CLK_RST_REG(SUPER_CCLK_DIVIDER_SUPER_CDIV_DIVISOR, 0, 8);
@ -111,37 +116,48 @@ DEFINE_CLK_RST_REG_BIT_ENUM(PLLC4_BASE_PLLC4_ENABLE, 30, DISABLE, ENABLE);
#define CLK_RST_CONTROLLER_CLK_SOURCE_I2C1 (0x124)
#define CLK_RST_CONTROLLER_CLK_SOURCE_I2C5 (0x128)
#define CLK_RST_CONTROLLER_CLK_SOURCE_DISP1 (0x138)
#define CLK_RST_CONTROLLER_CLK_SOURCE_VI (0x148)
#define CLK_RST_CONTROLLER_CLK_SOURCE_SDMMC1 (0x150)
#define CLK_RST_CONTROLLER_CLK_SOURCE_SDMMC2 (0x154)
#define CLK_RST_CONTROLLER_CLK_SOURCE_SDMMC4 (0x164)
#define CLK_RST_CONTROLLER_CLK_SOURCE_UARTA (0x178)
#define CLK_RST_CONTROLLER_CLK_SOURCE_UARTB (0x17C)
#define CLK_RST_CONTROLLER_CLK_SOURCE_HOST1X (0x180)
#define CLK_RST_CONTROLLER_CLK_SOURCE_I2C2 (0x198)
#define CLK_RST_CONTROLLER_CLK_SOURCE_UARTC (0x1A0)
#define CLK_RST_CONTROLLER_CLK_SOURCE_I2C3 (0x1B8)
#define CLK_RST_CONTROLLER_CLK_SOURCE_SDMMC3 (0x1BC)
#define CLK_RST_CONTROLLER_CLK_SOURCE_CSITE (0x1D4)
#define CLK_RST_CONTROLLER_CLK_SOURCE_TSEC (0x1F4)
#define CLK_RST_CONTROLLER_CLK_SOURCE_MSELECT (0x3B4)
#define CLK_RST_CONTROLLER_CLK_SOURCE_I2C4 (0x3C4)
#define CLK_RST_CONTROLLER_CLK_SOURCE_ACTMON (0x3E8)
#define CLK_RST_CONTROLLER_CLK_SOURCE_SOR1 (0x410)
#define CLK_RST_CONTROLLER_CLK_SOURCE_DSIA_LP (0x620)
#define CLK_RST_CONTROLLER_CLK_SOURCE_DVFS_REF (0x62C)
#define CLK_RST_CONTROLLER_CLK_SOURCE_DVFS_SOC (0x630)
#define CLK_RST_CONTROLLER_CLK_SOURCE_I2C6 (0x65C)
#define CLK_RST_CONTROLLER_CLK_SOURCE_UART_FST_MIPI_CAL (0x66C)
#define CLK_RST_CONTROLLER_CLK_SOURCE_SDMMC_LEGACY_TM (0x694)
#define CLK_RST_CONTROLLER_CLK_SOURCE_NVENC (0x6A4)
/* RST_DEV_*_SET */
#define CLK_RST_CONTROLLER_RST_DEV_L_SET (0x300)
#define CLK_RST_CONTROLLER_RST_DEV_H_SET (0x308)
#define CLK_RST_CONTROLLER_RST_DEV_U_SET (0x310)
#define CLK_RST_CONTROLLER_RST_DEV_V_SET (0x430)
#define CLK_RST_CONTROLLER_RST_DEV_W_SET (0x438)
#define CLK_RST_CONTROLLER_RST_DEV_X_SET (0x290)
#define CLK_RST_CONTROLLER_RST_DEV_Y_SET (0x2A8)
/* RST_DEV_*_CLR */
#define CLK_RST_CONTROLLER_RST_DEV_L_CLR (0x304)
#define CLK_RST_CONTROLLER_RST_DEV_H_CLR (0x30C)
#define CLK_RST_CONTROLLER_RST_DEV_U_CLR (0x314)
#define CLK_RST_CONTROLLER_RST_DEV_V_CLR (0x434)
#define CLK_RST_CONTROLLER_RST_DEV_W_CLR (0x43C)
#define CLK_RST_CONTROLLER_RST_DEV_X_CLR (0x294)
#define CLK_RST_CONTROLLER_RST_DEV_Y_CLR (0x2AC)
/* CLK_ENB_*_SET */
#define CLK_RST_CONTROLLER_CLK_ENB_L_SET (0x320)
@ -193,6 +209,13 @@ DEFINE_CLK_RST_REG_BIT_ENUM(PLLC4_BASE_PLLC4_ENABLE, 30, DISABLE, ENABLE);
#define CLK_RST_CONTROLLER_CLK_ENB_ACTMON_INDEX (0x17)
#define CLK_RST_CONTROLLER_CLK_ENB_HOST1X_INDEX (0x1C)
#define CLK_RST_CONTROLLER_CLK_ENB_TSEC_INDEX (0x13)
#define CLK_RST_CONTROLLER_CLK_ENB_SOR0_INDEX (0x16)
#define CLK_RST_CONTROLLER_CLK_ENB_SOR1_INDEX (0x17)
#define CLK_RST_CONTROLLER_CLK_ENB_SOR_SAFE_INDEX (0x1E)
#define CLK_RST_CONTROLLER_CLK_ENB_KFUSE_INDEX (0x08)
/* RST_CPUG_CMPLX_* */
#define CLK_RST_CONTROLLER_RST_CPUG_CMPLX_SET (0x450)
#define CLK_RST_CONTROLLER_RST_CPUG_CMPLX_CLR (0x454)
@ -235,6 +258,19 @@ DEFINE_CLK_RST_REG_THREE_BIT_ENUM(CLK_SOURCE_UARTA_UARTA_CLK_SRC, 29, PLLP_OUT0,
DEFINE_CLK_RST_REG_THREE_BIT_ENUM(CLK_SOURCE_UARTB_UARTB_CLK_SRC, 29, PLLP_OUT0, PLLC2_OUT0, PLLC_OUT0, PLLC4_OUT0, RESERVED4, PLLC4_OUT1, CLK_M, PLLC4_OUT2);
DEFINE_CLK_RST_REG_THREE_BIT_ENUM(CLK_SOURCE_UARTC_UARTC_CLK_SRC, 29, PLLP_OUT0, PLLC2_OUT0, PLLC_OUT0, PLLC4_OUT0, RESERVED4, PLLC4_OUT1, CLK_M, PLLC4_OUT2);
DEFINE_CLK_RST_REG_THREE_BIT_ENUM(CLK_SOURCE_VI_VI_CLK_SRC, 29, RESERVED0, PLLC2_OUT0, PLLC_OUT, PLLC3_OUT0, PLLP_OUT0, CLK_M, PLLA1_OUT0, PLLC4_OUT0);
DEFINE_CLK_RST_REG_THREE_BIT_ENUM(CLK_SOURCE_HOST1X_HOST1X_CLK_SRC, 29, PLLC4_OUT1, PLLC2_OUT0, PLLC_OUT0, PLLC4_OUT2, PLLP_OUT0, CLK_M, PLLA_OUT0, PLLC4_OUT0);
DEFINE_CLK_RST_REG_THREE_BIT_ENUM(CLK_SOURCE_NVENC_NVENC_CLK_SRC, 29, RESERVED0, PLLC2_OUT0, PLLC_OUT0, PLLC3_OUT0, PLLP_OUT0, RESERVED5, PLLA1_OUT0, CLK_M);
DEFINE_CLK_RST_REG_THREE_BIT_ENUM(CLK_SOURCE_TSEC_TSEC_CLK_SRC, 29, PLLP_OUT0, PLLC2_OUT0, PLLC_OUT0, PLLC3_OUT0, RESERVED4, PLLA1_OUT0, CLK_M, PLLC4_OUT0);
DEFINE_CLK_RST_REG_BIT_ENUM(CLK_SOURCE_SOR1_SOR1_CLK_SEL0, 14, MUX, SOR1_BRICK_OUTPUT);
DEFINE_CLK_RST_REG_BIT_ENUM(CLK_SOURCE_SOR1_SOR1_CLK_SEL1, 15, SAFE_CLOCK, SOR1_CLOCK_SWITCH);
DEFINE_CLK_RST_REG_THREE_BIT_ENUM(CLK_SOURCE_SOR1_SOR1_CLK_SRC, 29, PLLP_OUT0, RESERVED1, PLLD_OUT0, RESERVED3, RESERVED4, PLLD2_OUT0, CLK_M, RESERVED7);
DEFINE_CLK_RST_REG_THREE_BIT_ENUM(CLK_SOURCE_MSELECT_MSELECT_CLK_SRC, 29, PLLP_OUT0, PLLC2_OUT0, PLLC_OUT0, PLLC4_OUT2, PLLC4_OUT1, CLK_S, CLK_M, PLLC4_OUT0);
DEFINE_CLK_RST_REG(CLK_SOURCE_MSELECT_MSELECT_CLK_DIVISOR, 0, 8);
@ -302,6 +338,7 @@ DEFINE_CLK_RST_REG_BIT_ENUM(RST_CPUG_CMPLX_CLR_CLR_NONCPURESET, 29, DISABLE, ENA
HANDLER(U, CRAM2, 2, 24) \
HANDLER(V, CPUG, 3, 0) \
HANDLER(V, MSELECT, 3, 3) \
HANDLER(V, APB2APE, 3, 11) \
HANDLER(V, SPDIF_DOUBLER, 3, 22) \
HANDLER(V, ACTMON, 3, 23) \
HANDLER(V, TZRAM, 3, 30) \
@ -322,10 +359,12 @@ DEFINE_CLK_RST_REG_BIT_ENUM(RST_CPUG_CMPLX_CLR_CLR_NONCPURESET, 29, DISABLE, ENA
HANDLER(X, MC_BBC, 5, 10) \
HANDLER(X, EMC_DLL, 5, 14) \
HANDLER(X, UART_FST_MIPI_CAL, 5, 17) \
HANDLER(X, VIC, 5, 18) \
HANDLER(X, GPU, 5, 24) \
HANDLER(X, DBGAPB, 5, 25) \
HANDLER(X, PLLG_REF, 5, 29) \
HANDLER(Y, LEGACY_TM, 6, 1) \
HANDLER(Y, APE, 6, 6) \
HANDLER(Y, MC_CCPA, 6, 8) \
HANDLER(Y, MC_CDPA, 6, 9) \
HANDLER(Y, PLLP_OUT_CPU, 6, 31)

View File

@ -0,0 +1,52 @@
/*
* Copyright (c) 2018-2020 Atmosphère-NX
*
* This program is free software; you can redistribute it and/or modify it
* under the terms and conditions of the GNU General Public License,
* version 2, as published by the Free Software Foundation.
*
* This program is distributed in the hope it will be useful, but WITHOUT
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
* more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#pragma once
#include <vapours/common.hpp>
#include <vapours/assert.hpp>
#include <vapours/literals.hpp>
#include <vapours/util.hpp>
#include <vapours/results.hpp>
#include <vapours/reg.hpp>
#define I2S_REG(x) (0x702d1000 + x)
#define I2S0_I2S_CG (0x088)
#define I2S0_I2S_CTRL (0x0A0)
#define I2S1_I2S_CG (0x188)
#define I2S1_I2S_CTRL (0x1A0)
#define I2S2_I2S_CG (0x288)
#define I2S2_I2S_CTRL (0x2A0)
#define I2S3_I2S_CG (0x388)
#define I2S3_I2S_CTRL (0x3A0)
#define I2S4_I2S_CG (0x488)
#define I2S4_I2S_CTRL (0x4A0)
#define I2S_REG_BITS_MASK(NAME) REG_NAMED_BITS_MASK (I2S, NAME)
#define I2S_REG_BITS_VALUE(NAME, VALUE) REG_NAMED_BITS_VALUE (I2S, NAME, VALUE)
#define I2S_REG_BITS_ENUM(NAME, ENUM) REG_NAMED_BITS_ENUM (I2S, NAME, ENUM)
#define I2S_REG_BITS_ENUM_SEL(NAME, __COND__, TRUE_ENUM, FALSE_ENUM) REG_NAMED_BITS_ENUM_SEL(I2S, NAME, __COND__, TRUE_ENUM, FALSE_ENUM)
#define DEFINE_I2S_REG(NAME, __OFFSET__, __WIDTH__) REG_DEFINE_NAMED_REG (I2S, NAME, __OFFSET__, __WIDTH__)
#define DEFINE_I2S_REG_BIT_ENUM(NAME, __OFFSET__, ZERO, ONE) REG_DEFINE_NAMED_BIT_ENUM (I2S, NAME, __OFFSET__, ZERO, ONE)
#define DEFINE_I2S_REG_TWO_BIT_ENUM(NAME, __OFFSET__, ZERO, ONE, TWO, THREE) REG_DEFINE_NAMED_TWO_BIT_ENUM (I2S, NAME, __OFFSET__, ZERO, ONE, TWO, THREE)
#define DEFINE_I2S_REG_THREE_BIT_ENUM(NAME, __OFFSET__, ZERO, ONE, TWO, THREE, FOUR, FIVE, SIX, SEVEN) REG_DEFINE_NAMED_THREE_BIT_ENUM(I2S, NAME, __OFFSET__, ZERO, ONE, TWO, THREE, FOUR, FIVE, SIX, SEVEN)
#define DEFINE_I2S_REG_FOUR_BIT_ENUM(NAME, __OFFSET__, ZERO, ONE, TWO, THREE, FOUR, FIVE, SIX, SEVEN, EIGHT, NINE, TEN, ELEVEN, TWELVE, THIRTEEN, FOURTEEN, FIFTEEN) REG_DEFINE_NAMED_FOUR_BIT_ENUM (I2S, NAME, __OFFSET__, ZERO, ONE, TWO, THREE, FOUR, FIVE, SIX, SEVEN, EIGHT, NINE, TEN, ELEVEN, TWELVE, THIRTEEN, FOURTEEN, FIFTEEN)
DEFINE_I2S_REG_BIT_ENUM(I2S_CG_SLCG_ENABLE, 0, FALSE, TRUE);
DEFINE_I2S_REG_BIT_ENUM(I2S_CTRL_MASTER, 10, DISABLE, ENABLE);

View File

@ -58,6 +58,7 @@
#define APBDEV_PMC_AUTO_WAKE2_LVL_MASK (0x170)
#define APBDEV_PMC_OSC_EDPD_OVER (0x1A4)
#define APBDEV_PMC_CLK_OUT_CNTRL (0x1A8)
#define APBDEV_PMC_RST_STATUS (0x1B4)
#define APBDEV_PMC_IO_DPD_REQ (0x1B8)
#define APBDEV_PMC_IO_DPD_STATUS (0x1BC)
#define APBDEV_PMC_IO_DPD2_REQ (0x1C0)
@ -65,6 +66,7 @@
#define APBDEV_PMC_SEL_DPD_TIM (0x1C8)
#define APBDEV_PMC_SCRATCH45 (0x234)
#define APBDEV_PMC_SCRATCH46 (0x238)
#define APBDEV_PMC_SCRATCH49 (0x244)
#define APBDEV_PMC_TSC_MULT (0x2B4)
#define APBDEV_PMC_STICKY_BITS (0x2C0)
#define APBDEV_PMC_WEAK_BIAS (0x2C8)