From 5b3d389627603071e5eb70f2cc6f15917d540cf6 Mon Sep 17 00:00:00 2001 From: jimzrt Date: Sat, 26 Oct 2019 12:25:49 +0200 Subject: [PATCH] merge lockpick_rcm and hekate changes --- Makefile | 2 +- source/hos/pkg2.c | 1 - source/incognito/incognito.c | 8 ++++- source/libs/fatfs/diskio.c | 15 ++++----- source/libs/fatfs/ffconf.h | 2 +- source/power/max17050.c | 5 --- source/soc/clock.c | 2 ++ source/soc/fuse.h | 19 ++++++++++++ source/soc/kfuse.c | 57 +++++++++++++++++++++++++++++++++++ source/soc/kfuse.h | 42 ++++++++++++++++++++++++++ source/storage/sdmmc_driver.c | 18 +++++------ 11 files changed, 146 insertions(+), 25 deletions(-) create mode 100644 source/soc/kfuse.c create mode 100644 source/soc/kfuse.h diff --git a/Makefile b/Makefile index 4cd6f54..dc3c88c 100644 --- a/Makefile +++ b/Makefile @@ -29,7 +29,7 @@ OBJS = $(patsubst $(SOURCEDIR)/%.S, $(BUILDDIR)/$(TARGET)/%.o, \ CUSTOMDEFINES := -DIPL_LOAD_ADDR=$(IPL_LOAD_ADDR) CUSTOMDEFINES += -DLP_VER_MJ=$(LPVERSION_MAJOR) -DLP_VER_MN=$(LPVERSION_MINOR) -DLP_VER_BF=$(LPVERSION_BUGFX) -ARCH := -march=armv4t -mtune=arm7tdmi -mthumb-interwork +ARCH := -march=armv4t -mtune=arm7tdmi -mthumb -mthumb-interwork CFLAGS = $(ARCH) -O2 -nostdlib -ffunction-sections -fdata-sections -fomit-frame-pointer -std=gnu11 -Wall $(CUSTOMDEFINES) LDFLAGS = $(ARCH) -nostartfiles -lgcc -Wl,--nmagic,--gc-sections -Xlinker --defsym=IPL_LOAD_ADDR=$(IPL_LOAD_ADDR) diff --git a/source/hos/pkg2.c b/source/hos/pkg2.c index e745cbc..301fd4e 100644 --- a/source/hos/pkg2.c +++ b/source/hos/pkg2.c @@ -139,7 +139,6 @@ int pkg2_decompress_kip(pkg2_kip1_info_t* ki, u32 sectsToDecomp) memcpy(newKip, &hdr, sizeof(hdr)); newKipSize = dstDataPtr-(unsigned char*)(newKip); - free(ki->kip1); ki->kip1 = newKip; ki->size = newKipSize; diff --git a/source/incognito/incognito.c b/source/incognito/incognito.c index ad17d3e..922f712 100644 --- a/source/incognito/incognito.c +++ b/source/incognito/incognito.c @@ -109,7 +109,11 @@ bool dump_keys() tsec_ctxt_t tsec_ctxt; - emummc_storage_init_mmc(&storage, &sdmmc); + if (!emummc_storage_init_mmc(&storage, &sdmmc)) + { + EPRINTF("Unable to init MMC."); + return false; + } // Read package1. u8 *pkg1 = (u8 *)malloc(0x40000); @@ -119,6 +123,7 @@ bool dump_keys() if (!pkg1_id) { EPRINTF("Unknown pkg1 version."); + free(pkg1); return false; } @@ -135,6 +140,7 @@ bool dump_keys() if (!found_tsec_fw) { EPRINTF("Failed to locate TSEC firmware."); + free(pkg1); return false; } diff --git a/source/libs/fatfs/diskio.c b/source/libs/fatfs/diskio.c index e820c6a..75a1c1e 100644 --- a/source/libs/fatfs/diskio.c +++ b/source/libs/fatfs/diskio.c @@ -107,7 +107,7 @@ static inline int _emmc_xts(u32 ks1, u32 ks2, u32 enc, u8 *tweak, bool regen_twe pdst += 0x10; } - se_aes_crypt_ecb(ks2, 0, dst, secsize, src, secsize); + se_aes_crypt_ecb(ks2, enc, dst, secsize, src, secsize); pdst = (u8 *)dst; @@ -150,12 +150,11 @@ DRESULT disk_read ( __attribute__ ((aligned (16))) static u8 tweak[0x10]; __attribute__ ((aligned (16))) static u64 prev_cluster = -1; __attribute__ ((aligned (16))) static u32 prev_sector = 0; - u32 tweak_exp = 0; - bool regen_tweak = true, cache_sector = false; + bool needs_cache_sector = false; if (secindex == 0 || clear_sector_cache) { - free(sector_cache); - sector_cache = (sector_cache_t *)malloc(sizeof(sector_cache_t) * MAX_SEC_CACHE_ENTRIES); + if (!sector_cache) + sector_cache = (sector_cache_t *)malloc(sizeof(sector_cache_t) * MAX_SEC_CACHE_ENTRIES); clear_sector_cache = false; secindex = 0; } @@ -176,12 +175,14 @@ DRESULT disk_read ( if (s == secindex && s < MAX_SEC_CACHE_ENTRIES) { sector_cache[s].sector = sector; sector_cache[s].visit_count++; - cache_sector = true; + needs_cache_sector = true; secindex++; } } if (nx_emmc_part_read(&storage, system_part, sector, count, buff)) { + u32 tweak_exp = 0; + bool regen_tweak = true; if (prev_cluster != sector / 0x20) { // sector in different cluster than last read prev_cluster = sector / 0x20; tweak_exp = sector % 0x20; @@ -194,7 +195,7 @@ DRESULT disk_read ( // fatfs will never pull more than a cluster _emmc_xts(9, 8, 0, tweak, regen_tweak, tweak_exp, prev_cluster, buff, buff, count * 0x200); - if (cache_sector) { + if (needs_cache_sector) { memcpy(sector_cache[s].cached_sector, buff, 0x200); memcpy(sector_cache[s].tweak, tweak, 0x10); } diff --git a/source/libs/fatfs/ffconf.h b/source/libs/fatfs/ffconf.h index 221c909..dc9577e 100644 --- a/source/libs/fatfs/ffconf.h +++ b/source/libs/fatfs/ffconf.h @@ -97,7 +97,7 @@ */ -#define FF_USE_LFN 1 +#define FF_USE_LFN 3 #define FF_MAX_LFN 255 /* The FF_USE_LFN switches the support for LFN (long file name). / diff --git a/source/power/max17050.c b/source/power/max17050.c index aca452e..227f76b 100644 --- a/source/power/max17050.c +++ b/source/power/max17050.c @@ -43,9 +43,6 @@ #define MAX17050_VMAX_TOLERANCE 50 /* 50 mV */ -#pragma GCC push_options -#pragma GCC optimize ("Os") - int max17050_get_property(enum MAX17050_reg reg, int *value) { u16 data; @@ -267,5 +264,3 @@ int max17050_fix_configuration() return 0; } - -#pragma GCC pop_options \ No newline at end of file diff --git a/source/soc/clock.c b/source/soc/clock.c index 73e5fb3..0726748 100644 --- a/source/soc/clock.c +++ b/source/soc/clock.c @@ -15,6 +15,7 @@ */ #include "../soc/clock.h" +#include "../soc/kfuse.h" #include "../soc/t210.h" #include "../utils/util.h" #include "../storage/sdmmc.h" @@ -188,6 +189,7 @@ void clock_enable_kfuse() usleep(10); CLOCK(CLK_RST_CONTROLLER_RST_DEVICES_H) &= 0xFFFFFEFF; usleep(20); + kfuse_wait_ready(); } void clock_disable_kfuse() diff --git a/source/soc/fuse.h b/source/soc/fuse.h index 191f18a..0748936 100644 --- a/source/soc/fuse.h +++ b/source/soc/fuse.h @@ -37,12 +37,31 @@ #define FUSE_WRITE_ACCESS_SW 0x30 #define FUSE_PWR_GOOD_SW 0x34 #define FUSE_SKU_INFO 0x110 +#define FUSE_CPU_SPEEDO_0_CALIB 0x114 +#define FUSE_CPU_IDDQ_CALIB 0x118 +#define FUSE_OPT_FT_REV 0x128 +#define FUSE_CPU_SPEEDO_1_CALIB 0x12C +#define FUSE_CPU_SPEEDO_2_CALIB 0x130 +#define FUSE_SOC_SPEEDO_0_CALIB 0x134 +#define FUSE_SOC_SPEEDO_1_CALIB 0x138 +#define FUSE_SOC_SPEEDO_2_CALIB 0x13C +#define FUSE_SOC_IDDQ_CALIB 0x140 +#define FUSE_OPT_CP_REV 0x190 #define FUSE_FIRST_BOOTROM_PATCH_SIZE 0x19c #define FUSE_PRIVATE_KEY0 0x1A4 #define FUSE_PRIVATE_KEY1 0x1A8 #define FUSE_PRIVATE_KEY2 0x1AC #define FUSE_PRIVATE_KEY3 0x1B0 +#define FUSE_PRIVATE_KEY4 0x1B4 #define FUSE_RESERVED_SW 0x1C0 +#define FUSE_OPT_VENDOR_CODE 0x200 +#define FUSE_OPT_FAB_CODE 0x204 +#define FUSE_OPT_LOT_CODE_0 0x208 +#define FUSE_OPT_LOT_CODE_1 0x20C +#define FUSE_OPT_WAFER_ID 0x210 +#define FUSE_OPT_X_COORDINATE 0x214 +#define FUSE_OPT_Y_COORDINATE 0x218 +#define FUSE_GPU_IDDQ_CALIB 0x228 /*! Fuse commands. */ #define FUSE_READ 0x1 diff --git a/source/soc/kfuse.c b/source/soc/kfuse.c new file mode 100644 index 0000000..52f188f --- /dev/null +++ b/source/soc/kfuse.c @@ -0,0 +1,57 @@ +/* + * Copyright (c) 2018 naehrwert + * + * 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 . + */ + +#include "../soc/kfuse.h" +#include "../soc/clock.h" +#include "../soc/t210.h" +#include "../utils/util.h" + +int kfuse_read(u32 *buf) +{ + int res = 0; + + clock_enable_kfuse(); + + while (!(KFUSE(KFUSE_STATE) & KFUSE_STATE_DONE)) + ; + + if (!(KFUSE(KFUSE_STATE) & KFUSE_STATE_CRCPASS)) + goto out; + + KFUSE(KFUSE_KEYADDR) = KFUSE_KEYADDR_AUTOINC; + for (int i = 0; i < KFUSE_NUM_WORDS; i++) + buf[i] = KFUSE(KFUSE_KEYS); + + res = 1; + +out:; + clock_disable_kfuse(); + return res; +} + +int kfuse_wait_ready() +{ + // Wait for KFUSE to finish init and verification of data. + while (!(KFUSE(KFUSE_STATE) & KFUSE_STATE_DONE)) + { + usleep(500); + } + + if (!(KFUSE(KFUSE_STATE) & KFUSE_STATE_CRCPASS)) + return 0; + + return 1; +} diff --git a/source/soc/kfuse.h b/source/soc/kfuse.h new file mode 100644 index 0000000..3824eb8 --- /dev/null +++ b/source/soc/kfuse.h @@ -0,0 +1,42 @@ +/* + * Copyright (c) 2018 naehrwert + * + * 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 . + */ + +#ifndef _KFUSE_H_ +#define _KFUSE_H_ + +#include "../utils/types.h" + +#define KFUSE_STATE_SOFTRESET (1 << 31) +#define KFUSE_STATE_STOP (1 << 25) +#define KFUSE_STATE_RESTART (1 << 24) +#define KFUSE_STATE_CRCPASS (1 << 17) +#define KFUSE_STATE_DONE (1 << 16) +#define KFUSE_STATE_ERRBLOCK_MASK 0x3F00 +#define KFUSE_STATE_ERRBLOCK_SHIFT 8 +#define KFUSE_STATE_CURBLOCK_MASK 0x3F + +#define KFUSE_KEYADDR_AUTOINC (1<<16) + +#define KFUSE_STATE 0x80 +#define KFUSE_KEYADDR 0x88 +#define KFUSE_KEYS 0x8C + +#define KFUSE_NUM_WORDS 144 + +int kfuse_read(u32 *buf); +int kfuse_wait_ready(); + +#endif diff --git a/source/storage/sdmmc_driver.c b/source/storage/sdmmc_driver.c index 9330eac..0c0c2ff 100644 --- a/source/storage/sdmmc_driver.c +++ b/source/storage/sdmmc_driver.c @@ -77,7 +77,7 @@ static int _sdmmc_set_voltage(sdmmc_t *sdmmc, u32 power) { pwr |= TEGRA_MMC_PWRCTL_SD_BUS_POWER; sdmmc->regs->pwrcon = pwr; - } + } return 1; } @@ -385,7 +385,7 @@ int sdmmc_get_rsp(sdmmc_t *sdmmc, u32 *rsp, u32 size, u32 type) static void _sdmmc_reset(sdmmc_t *sdmmc) { - sdmmc->regs->swrst |= + sdmmc->regs->swrst |= TEGRA_MMC_SWRST_SW_RESET_FOR_CMD_LINE | TEGRA_MMC_SWRST_SW_RESET_FOR_DAT_LINE; _sdmmc_get_clkcon(sdmmc); u32 timeout = get_tmr_ms() + 2000; @@ -456,7 +456,7 @@ static int _sdmmc_setup_read_small_block(sdmmc_t *sdmmc) static int _sdmmc_parse_cmdbuf(sdmmc_t *sdmmc, sdmmc_cmd_t *cmd, bool is_data_present) { u16 cmdflags = 0; - + switch (cmd->rsp_type) { case SDMMC_RSP_TYPE_0: @@ -722,7 +722,7 @@ static int _sdmmc_check_mask_interrupt(sdmmc_t *sdmmc, u16 *pout, u16 mask) sdmmc->regs->norintsts = norintsts & mask; return SDMMC_MASKINT_MASKED; } - + return SDMMC_MASKINT_NOERROR; } @@ -767,7 +767,7 @@ static int _sdmmc_stop_transmission_inner(sdmmc_t *sdmmc, u32 *rsp) if (!res) return 0; - + _sdmmc_cache_rsp(sdmmc, rsp, 4, SDMMC_RSP_TYPE_1); return _sdmmc_wait_prnsts_type1(sdmmc); @@ -901,7 +901,7 @@ static int _sdmmc_execute_cmd_inner(sdmmc_t *sdmmc, sdmmc_cmd_t *cmd, sdmmc_req_ _sdmmc_parse_cmdbuf(sdmmc, cmd, is_data_present); int res = _sdmmc_wait_request(sdmmc); - DPRINTF("rsp(%d): %08X, %08X, %08X, %08X\n", res, + DPRINTF("rsp(%d): %08X, %08X, %08X, %08X\n", res, sdmmc->regs->rspreg0, sdmmc->regs->rspreg1, sdmmc->regs->rspreg2, sdmmc->regs->rspreg3); if (res) { @@ -943,7 +943,7 @@ static int _sdmmc_config_sdmmc1() gpio_output_enable(GPIO_PORT_Z, GPIO_PIN_1, GPIO_OUTPUT_DISABLE); usleep(100); - // Check if SD card is inserted. + // Check if SD card is inserted. if(!!gpio_read(GPIO_PORT_Z, GPIO_PIN_1)) return 0; @@ -1055,7 +1055,7 @@ void sdmmc_end(sdmmc_t *sdmmc) if (!sdmmc->clock_stopped) { _sdmmc_sd_clock_disable(sdmmc); - // Disable SDMMC power. + // Disable SDMMC power. _sdmmc_set_voltage(sdmmc, SDMMC_POWER_OFF); // Disable SD card power. @@ -1134,7 +1134,7 @@ int sdmmc_enable_low_voltage(sdmmc_t *sdmmc) _sdmmc_set_voltage(sdmmc, SDMMC_POWER_1_8); _sdmmc_get_clkcon(sdmmc); msleep(5); - + if (sdmmc->regs->hostctl2 & SDHCI_CTRL_VDD_180) { sdmmc->regs->clkcon |= TEGRA_MMC_CLKCON_SD_CLOCK_ENABLE;