mirror of
https://github.com/Atmosphere-NX/Atmosphere
synced 2024-12-22 20:31:14 +00:00
exosphere: Add support for enabling debugmode via BCT.ini
This commit is contained in:
parent
49ad66e478
commit
72a2c10896
8 changed files with 80 additions and 18 deletions
|
@ -28,8 +28,9 @@
|
||||||
#include "exocfg.h"
|
#include "exocfg.h"
|
||||||
|
|
||||||
static bool g_battery_profile = false;
|
static bool g_battery_profile = false;
|
||||||
|
static bool g_debugmode_override_user = false, g_debugmode_override_priv = false;
|
||||||
|
|
||||||
uint32_t configitem_set(ConfigItem item, uint64_t value) {
|
uint32_t configitem_set(bool privileged, ConfigItem item, uint64_t value) {
|
||||||
if (item != CONFIGITEM_BATTERYPROFILE) {
|
if (item != CONFIGITEM_BATTERYPROFILE) {
|
||||||
return 2;
|
return 2;
|
||||||
}
|
}
|
||||||
|
@ -40,7 +41,7 @@ uint32_t configitem_set(ConfigItem item, uint64_t value) {
|
||||||
|
|
||||||
bool configitem_is_recovery_boot(void) {
|
bool configitem_is_recovery_boot(void) {
|
||||||
uint64_t is_recovery_boot;
|
uint64_t is_recovery_boot;
|
||||||
if (configitem_get(CONFIGITEM_ISRECOVERYBOOT, &is_recovery_boot) != 0) {
|
if (configitem_get(true, CONFIGITEM_ISRECOVERYBOOT, &is_recovery_boot) != 0) {
|
||||||
generic_panic();
|
generic_panic();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -49,7 +50,7 @@ bool configitem_is_recovery_boot(void) {
|
||||||
|
|
||||||
bool configitem_is_retail(void) {
|
bool configitem_is_retail(void) {
|
||||||
uint64_t is_retail;
|
uint64_t is_retail;
|
||||||
if (configitem_get(CONFIGITEM_ISRETAIL, &is_retail) != 0) {
|
if (configitem_get(true, CONFIGITEM_ISRETAIL, &is_retail) != 0) {
|
||||||
generic_panic();
|
generic_panic();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -62,13 +63,18 @@ bool configitem_should_profile_battery(void) {
|
||||||
|
|
||||||
uint64_t configitem_get_hardware_type(void) {
|
uint64_t configitem_get_hardware_type(void) {
|
||||||
uint64_t hardware_type;
|
uint64_t hardware_type;
|
||||||
if (configitem_get(CONFIGITEM_HARDWARETYPE, &hardware_type) != 0) {
|
if (configitem_get(true, CONFIGITEM_HARDWARETYPE, &hardware_type) != 0) {
|
||||||
generic_panic();
|
generic_panic();
|
||||||
}
|
}
|
||||||
return hardware_type;
|
return hardware_type;
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t configitem_get(ConfigItem item, uint64_t *p_outvalue) {
|
void configitem_set_debugmode_override(bool user, bool priv) {
|
||||||
|
g_debugmode_override_user = user;
|
||||||
|
g_debugmode_override_priv = priv;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint32_t configitem_get(bool privileged, ConfigItem item, uint64_t *p_outvalue) {
|
||||||
uint32_t result = 0;
|
uint32_t result = 0;
|
||||||
switch (item) {
|
switch (item) {
|
||||||
case CONFIGITEM_DISABLEPROGRAMVERIFICATION:
|
case CONFIGITEM_DISABLEPROGRAMVERIFICATION:
|
||||||
|
@ -109,7 +115,11 @@ uint32_t configitem_get(ConfigItem item, uint64_t *p_outvalue) {
|
||||||
*p_outvalue = bootconfig_get_memory_arrangement();
|
*p_outvalue = bootconfig_get_memory_arrangement();
|
||||||
break;
|
break;
|
||||||
case CONFIGITEM_ISDEBUGMODE:
|
case CONFIGITEM_ISDEBUGMODE:
|
||||||
*p_outvalue = (int)(bootconfig_is_debug_mode());
|
if ((privileged && g_debugmode_override_priv) || (!privileged && g_debugmode_override_user)) {
|
||||||
|
*p_outvalue = 1;
|
||||||
|
} else {
|
||||||
|
*p_outvalue = (int)(bootconfig_is_debug_mode());
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case CONFIGITEM_KERNELMEMORYCONFIGURATION:
|
case CONFIGITEM_KERNELMEMORYCONFIGURATION:
|
||||||
*p_outvalue = bootconfig_get_kernel_memory_configuration();
|
*p_outvalue = bootconfig_get_kernel_memory_configuration();
|
||||||
|
|
|
@ -43,13 +43,15 @@ typedef enum {
|
||||||
CONFIGITEM_EXOSPHERE_VERSION = 65000
|
CONFIGITEM_EXOSPHERE_VERSION = 65000
|
||||||
} ConfigItem;
|
} ConfigItem;
|
||||||
|
|
||||||
uint32_t configitem_set(ConfigItem item, uint64_t value);
|
uint32_t configitem_set(bool privileged, ConfigItem item, uint64_t value);
|
||||||
uint32_t configitem_get(ConfigItem item, uint64_t *p_outvalue);
|
uint32_t configitem_get(bool privileged, ConfigItem item, uint64_t *p_outvalue);
|
||||||
|
|
||||||
bool configitem_is_recovery_boot(void);
|
bool configitem_is_recovery_boot(void);
|
||||||
bool configitem_is_retail(void);
|
bool configitem_is_retail(void);
|
||||||
bool configitem_should_profile_battery(void);
|
bool configitem_should_profile_battery(void);
|
||||||
|
|
||||||
|
void configitem_set_debugmode_override(bool user, bool priv);
|
||||||
|
|
||||||
uint64_t configitem_get_hardware_type(void);
|
uint64_t configitem_get_hardware_type(void);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -67,3 +67,19 @@ unsigned int exosphere_should_perform_620_keygen(void) {
|
||||||
|
|
||||||
return g_exosphere_cfg.target_firmware >= EXOSPHERE_TARGET_FIRMWARE_620 && EXOSPHERE_CHECK_FLAG(EXOSPHERE_FLAG_PERFORM_620_KEYGEN);
|
return g_exosphere_cfg.target_firmware >= EXOSPHERE_TARGET_FIRMWARE_620 && EXOSPHERE_CHECK_FLAG(EXOSPHERE_FLAG_PERFORM_620_KEYGEN);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unsigned int exosphere_should_override_debugmode_priv(void) {
|
||||||
|
if (!g_has_loaded_config) {
|
||||||
|
generic_panic();
|
||||||
|
}
|
||||||
|
|
||||||
|
return EXOSPHERE_CHECK_FLAG(EXOSPHERE_FLAG_IS_DEBUGMODE_PRIV);
|
||||||
|
}
|
||||||
|
|
||||||
|
unsigned int exosphere_should_override_debugmode_user(void) {
|
||||||
|
if (!g_has_loaded_config) {
|
||||||
|
generic_panic();
|
||||||
|
}
|
||||||
|
|
||||||
|
return EXOSPHERE_CHECK_FLAG(EXOSPHERE_FLAG_IS_DEBUGMODE_USER);
|
||||||
|
}
|
||||||
|
|
|
@ -50,6 +50,8 @@
|
||||||
|
|
||||||
#define EXOSPHERE_FLAGS_DEFAULT 0x00000000
|
#define EXOSPHERE_FLAGS_DEFAULT 0x00000000
|
||||||
#define EXOSPHERE_FLAG_PERFORM_620_KEYGEN (1 << 0u)
|
#define EXOSPHERE_FLAG_PERFORM_620_KEYGEN (1 << 0u)
|
||||||
|
#define EXOSPHERE_FLAG_IS_DEBUGMODE_PRIV (1 << 1u)
|
||||||
|
#define EXOSPHERE_FLAG_IS_DEBUGMODE_USER (1 << 2u)
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
unsigned int magic;
|
unsigned int magic;
|
||||||
|
@ -60,6 +62,8 @@ typedef struct {
|
||||||
unsigned int exosphere_load_config(void);
|
unsigned int exosphere_load_config(void);
|
||||||
unsigned int exosphere_get_target_firmware(void);
|
unsigned int exosphere_get_target_firmware(void);
|
||||||
unsigned int exosphere_should_perform_620_keygen(void);
|
unsigned int exosphere_should_perform_620_keygen(void);
|
||||||
|
unsigned int exosphere_should_override_debugmode_priv(void);
|
||||||
|
unsigned int exosphere_should_override_debugmode_user(void);
|
||||||
|
|
||||||
static inline unsigned int exosphere_get_target_firmware_for_init(void) {
|
static inline unsigned int exosphere_get_target_firmware_for_init(void) {
|
||||||
const unsigned int magic = MAILBOX_EXOSPHERE_CONFIG_PHYS.magic;
|
const unsigned int magic = MAILBOX_EXOSPHERE_CONFIG_PHYS.magic;
|
||||||
|
|
|
@ -509,6 +509,7 @@ uintptr_t get_pk2ldr_stack_address(void) {
|
||||||
void load_package2(coldboot_crt0_reloc_list_t *reloc_list) {
|
void load_package2(coldboot_crt0_reloc_list_t *reloc_list) {
|
||||||
/* Load Exosphere-specific config. */
|
/* Load Exosphere-specific config. */
|
||||||
exosphere_load_config();
|
exosphere_load_config();
|
||||||
|
configitem_set_debugmode_override(exosphere_should_override_debugmode_user() != 0, exosphere_should_override_debugmode_priv() != 0);
|
||||||
|
|
||||||
/* Setup the Security Engine. */
|
/* Setup the Security Engine. */
|
||||||
setup_se();
|
setup_se();
|
||||||
|
|
|
@ -44,8 +44,8 @@
|
||||||
#define DEBUG_PANIC_ON_FAILURE 0
|
#define DEBUG_PANIC_ON_FAILURE 0
|
||||||
|
|
||||||
/* User SMC prototypes */
|
/* User SMC prototypes */
|
||||||
uint32_t smc_set_config(smc_args_t *args);
|
uint32_t smc_set_config_user(smc_args_t *args);
|
||||||
uint32_t smc_get_config(smc_args_t *args);
|
uint32_t smc_get_config_user(smc_args_t *args);
|
||||||
uint32_t smc_check_status(smc_args_t *args);
|
uint32_t smc_check_status(smc_args_t *args);
|
||||||
uint32_t smc_get_result(smc_args_t *args);
|
uint32_t smc_get_result(smc_args_t *args);
|
||||||
uint32_t smc_exp_mod(smc_args_t *args);
|
uint32_t smc_exp_mod(smc_args_t *args);
|
||||||
|
@ -71,7 +71,7 @@ uint32_t smc_decrypt_or_import_rsa_key(smc_args_t *args);
|
||||||
uint32_t smc_cpu_suspend(smc_args_t *args);
|
uint32_t smc_cpu_suspend(smc_args_t *args);
|
||||||
uint32_t smc_cpu_off(smc_args_t *args);
|
uint32_t smc_cpu_off(smc_args_t *args);
|
||||||
uint32_t smc_cpu_on(smc_args_t *args);
|
uint32_t smc_cpu_on(smc_args_t *args);
|
||||||
/* uint32_t smc_get_config(smc_args_t *args); */
|
uint32_t smc_get_config_priv(smc_args_t *args);
|
||||||
uint32_t smc_get_random_bytes_for_priv(smc_args_t *args);
|
uint32_t smc_get_random_bytes_for_priv(smc_args_t *args);
|
||||||
uint32_t smc_panic(smc_args_t *args);
|
uint32_t smc_panic(smc_args_t *args);
|
||||||
uint32_t smc_configure_carveout(smc_args_t *args);
|
uint32_t smc_configure_carveout(smc_args_t *args);
|
||||||
|
@ -89,8 +89,8 @@ typedef struct {
|
||||||
|
|
||||||
static smc_table_entry_t g_smc_user_table[SMC_USER_HANDLERS] = {
|
static smc_table_entry_t g_smc_user_table[SMC_USER_HANDLERS] = {
|
||||||
{0, NULL},
|
{0, NULL},
|
||||||
{0xC3000401, smc_set_config},
|
{0xC3000401, smc_set_config_user},
|
||||||
{0xC3000002, smc_get_config},
|
{0xC3000002, smc_get_config_user},
|
||||||
{0xC3000003, smc_check_status},
|
{0xC3000003, smc_check_status},
|
||||||
{0xC3000404, smc_get_result},
|
{0xC3000404, smc_get_result},
|
||||||
{0xC3000E05, smc_exp_mod},
|
{0xC3000E05, smc_exp_mod},
|
||||||
|
@ -114,7 +114,7 @@ static smc_table_entry_t g_smc_priv_table[SMC_PRIV_HANDLERS] = {
|
||||||
{0xC4000001, smc_cpu_suspend},
|
{0xC4000001, smc_cpu_suspend},
|
||||||
{0x84000002, smc_cpu_off},
|
{0x84000002, smc_cpu_off},
|
||||||
{0xC4000003, smc_cpu_on},
|
{0xC4000003, smc_cpu_on},
|
||||||
{0xC3000004, smc_get_config}, /* NOTE: Same function as for USER */
|
{0xC3000004, smc_get_config_priv},
|
||||||
{0xC3000005, smc_get_random_bytes_for_priv},
|
{0xC3000005, smc_get_random_bytes_for_priv},
|
||||||
{0xC3000006, smc_panic},
|
{0xC3000006, smc_panic},
|
||||||
{0xC3000007, smc_configure_carveout},
|
{0xC3000007, smc_configure_carveout},
|
||||||
|
@ -329,15 +329,15 @@ uint32_t smc_wrapper_async(smc_args_t *args, uint32_t (*handler)(smc_args_t *),
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t smc_set_config(smc_args_t *args) {
|
uint32_t smc_set_config_user(smc_args_t *args) {
|
||||||
/* Actual value presumed in X3 on hardware. */
|
/* Actual value presumed in X3 on hardware. */
|
||||||
return configitem_set((ConfigItem)args->X[1], args->X[3]);
|
return configitem_set(false, (ConfigItem)args->X[1], args->X[3]);
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t smc_get_config(smc_args_t *args) {
|
uint32_t smc_get_config_user(smc_args_t *args) {
|
||||||
uint64_t out_item = 0;
|
uint64_t out_item = 0;
|
||||||
uint32_t result;
|
uint32_t result;
|
||||||
result = configitem_get((ConfigItem)args->X[1], &out_item);
|
result = configitem_get(false, (ConfigItem)args->X[1], &out_item);
|
||||||
args->X[1] = out_item;
|
args->X[1] = out_item;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -534,6 +534,14 @@ uint32_t smc_cpu_suspend(smc_args_t *args) {
|
||||||
return smc_wrapper_sync(args, cpu_suspend_wrapper);
|
return smc_wrapper_sync(args, cpu_suspend_wrapper);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint32_t smc_get_config_priv(smc_args_t *args) {
|
||||||
|
uint64_t out_item = 0;
|
||||||
|
uint32_t result;
|
||||||
|
result = configitem_get(true, (ConfigItem)args->X[1], &out_item);
|
||||||
|
args->X[1] = out_item;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
uint32_t smc_get_random_bytes_for_priv(smc_args_t *args) {
|
uint32_t smc_get_random_bytes_for_priv(smc_args_t *args) {
|
||||||
/* This is an interesting SMC. */
|
/* This is an interesting SMC. */
|
||||||
/* The kernel must NEVER be unable to get random bytes, if it needs them */
|
/* The kernel must NEVER be unable to get random bytes, if it needs them */
|
||||||
|
|
|
@ -37,6 +37,8 @@
|
||||||
|
|
||||||
#define EXOSPHERE_FLAGS_DEFAULT 0x00000000
|
#define EXOSPHERE_FLAGS_DEFAULT 0x00000000
|
||||||
#define EXOSPHERE_FLAG_PERFORM_620_KEYGEN (1 << 0u)
|
#define EXOSPHERE_FLAG_PERFORM_620_KEYGEN (1 << 0u)
|
||||||
|
#define EXOSPHERE_FLAG_IS_DEBUGMODE_PRIV (1 << 1u)
|
||||||
|
#define EXOSPHERE_FLAG_IS_DEBUGMODE_USER (1 << 2u)
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
unsigned int magic;
|
unsigned int magic;
|
||||||
|
@ -47,5 +49,7 @@ typedef struct {
|
||||||
#define MAILBOX_EXOSPHERE_CONFIGURATION ((volatile exosphere_config_t *)(0x40002E40))
|
#define MAILBOX_EXOSPHERE_CONFIGURATION ((volatile exosphere_config_t *)(0x40002E40))
|
||||||
|
|
||||||
#define EXOSPHERE_TARGETFW_KEY "target_firmware"
|
#define EXOSPHERE_TARGETFW_KEY "target_firmware"
|
||||||
|
#define EXOSPHERE_DEBUGMODE_PRIV_KEY "debug_mode"
|
||||||
|
#define EXOSPHERE_DEBUGMODE_USER_KEY "debug_mode_user"
|
||||||
|
|
||||||
#endif
|
#endif
|
|
@ -53,9 +53,26 @@
|
||||||
|
|
||||||
static int exosphere_ini_handler(void *user, const char *section, const char *name, const char *value) {
|
static int exosphere_ini_handler(void *user, const char *section, const char *name, const char *value) {
|
||||||
exosphere_config_t *exo_cfg = (exosphere_config_t *)user;
|
exosphere_config_t *exo_cfg = (exosphere_config_t *)user;
|
||||||
|
int tmp = 0;
|
||||||
if (strcmp(section, "exosphere") == 0) {
|
if (strcmp(section, "exosphere") == 0) {
|
||||||
if (strcmp(name, EXOSPHERE_TARGETFW_KEY) == 0) {
|
if (strcmp(name, EXOSPHERE_TARGETFW_KEY) == 0) {
|
||||||
sscanf(value, "%d", &exo_cfg->target_firmware);
|
sscanf(value, "%d", &exo_cfg->target_firmware);
|
||||||
|
}
|
||||||
|
if (strcmp(name, EXOSPHERE_DEBUGMODE_PRIV_KEY) == 0) {
|
||||||
|
sscanf(value, "%d", &tmp);
|
||||||
|
if (tmp) {
|
||||||
|
exo_cfg->flags |= EXOSPHERE_FLAG_IS_DEBUGMODE_PRIV;
|
||||||
|
} else {
|
||||||
|
exo_cfg->flags &= ~(EXOSPHERE_FLAG_IS_DEBUGMODE_PRIV);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (strcmp(name, EXOSPHERE_DEBUGMODE_USER_KEY) == 0) {
|
||||||
|
sscanf(value, "%d", &tmp);
|
||||||
|
if (tmp) {
|
||||||
|
exo_cfg->flags |= EXOSPHERE_FLAG_IS_DEBUGMODE_USER;
|
||||||
|
} else {
|
||||||
|
exo_cfg->flags &= ~(EXOSPHERE_FLAG_IS_DEBUGMODE_USER);
|
||||||
|
}
|
||||||
} else {
|
} else {
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue