mirror of
https://github.com/SciresM/hactool
synced 2024-11-21 19:53:01 +00:00
Add support for key derivation.
Passing in --sbk=, --tseckey= with -t keygen and an input BOOT0 BIS partition will now derive all keys derivable iwth the sources in the loaded keyset, and print them to output.
This commit is contained in:
parent
41e6695e6e
commit
2159f4396f
8 changed files with 623 additions and 5 deletions
13
aes.c
13
aes.c
|
@ -48,6 +48,19 @@ void aes_setiv(aes_ctx_t *ctx, const void *iv, size_t l) {
|
|||
}
|
||||
}
|
||||
|
||||
/* Calculate CMAC. */
|
||||
void aes_calculate_cmac(void *dst, void *src, size_t size, const void *key) {
|
||||
mbedtls_cipher_context_t m_ctx;
|
||||
mbedtls_cipher_init(&m_ctx);
|
||||
if (mbedtls_cipher_setup(&m_ctx, mbedtls_cipher_info_from_type(MBEDTLS_CIPHER_AES_128_ECB))
|
||||
|| mbedtls_cipher_cmac_starts(&m_ctx, key, 0x80)
|
||||
|| mbedtls_cipher_cmac_update(&m_ctx, src, size)
|
||||
|| mbedtls_cipher_cmac_finish(&m_ctx, dst)) {
|
||||
FATAL_ERROR("Failed to calculate CMAC!");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* Encrypt with context. */
|
||||
void aes_encrypt(aes_ctx_t *ctx, void *dst, const void *src, size_t l) {
|
||||
size_t out_len = 0;
|
||||
|
|
3
aes.h
3
aes.h
|
@ -2,6 +2,7 @@
|
|||
#define HACTOOL_AES_H
|
||||
|
||||
#include "mbedtls/cipher.h"
|
||||
#include "mbedtls/cmac.h"
|
||||
|
||||
/* Enumerations. */
|
||||
typedef enum {
|
||||
|
@ -30,6 +31,8 @@ void aes_setiv(aes_ctx_t *ctx, const void *iv, size_t l);
|
|||
void aes_encrypt(aes_ctx_t *ctx, void *dst, const void *src, size_t l);
|
||||
void aes_decrypt(aes_ctx_t *ctx, void *dst, const void *src, size_t l);
|
||||
|
||||
void aes_calculate_cmac(void *dst, void *src, size_t size, const void *key);
|
||||
|
||||
void aes_xts_encrypt(aes_ctx_t *ctx, void *dst, const void *src, size_t l, size_t sector, size_t sector_size);
|
||||
void aes_xts_decrypt(aes_ctx_t *ctx, void *dst, const void *src, size_t l, size_t sector, size_t sector_size);
|
||||
|
||||
|
|
50
extkeys.c
50
extkeys.c
|
@ -209,6 +209,9 @@ void extkeys_initialize_keyset(nca_keyset_t *keyset, FILE *f) {
|
|||
} else if (strcmp(key, "header_key") == 0) {
|
||||
parse_hex_key(keyset->header_key, value, sizeof(keyset->header_key));
|
||||
matched_key = 1;
|
||||
} else if (strcmp(key, "encrypted_header_key") == 0) {
|
||||
parse_hex_key(keyset->encrypted_header_key, value, sizeof(keyset->encrypted_header_key));
|
||||
matched_key = 1;
|
||||
} else if (strcmp(key, "package2_key_source") == 0) {
|
||||
parse_hex_key(keyset->package2_key_source, value, sizeof(keyset->package2_key_source));
|
||||
matched_key = 1;
|
||||
|
@ -221,10 +224,57 @@ void extkeys_initialize_keyset(nca_keyset_t *keyset, FILE *f) {
|
|||
} else if (strcmp(key, "sd_card_save_key_source") == 0) {
|
||||
parse_hex_key(keyset->sd_card_key_sources[0], value, sizeof(keyset->sd_card_key_sources[0]));
|
||||
matched_key = 1;
|
||||
} else if (strcmp(key, "master_key_source") == 0) {
|
||||
parse_hex_key(keyset->master_key_source, value, sizeof(keyset->master_key_source));
|
||||
matched_key = 1;
|
||||
} else if (strcmp(key, "keyblob_mac_key_source") == 0) {
|
||||
parse_hex_key(keyset->keyblob_mac_key_source, value, sizeof(keyset->keyblob_mac_key_source));
|
||||
matched_key = 1;
|
||||
} else if (strcmp(key, "secure_boot_key") == 0) {
|
||||
parse_hex_key(keyset->secure_boot_key, value, sizeof(keyset->secure_boot_key));
|
||||
matched_key = 1;
|
||||
} else if (strcmp(key, "tsec_key") == 0) {
|
||||
parse_hex_key(keyset->tsec_key, value, sizeof(keyset->tsec_key));
|
||||
matched_key = 1;
|
||||
} else {
|
||||
char test_name[0x100];
|
||||
memset(test_name, 0, sizeof(100));
|
||||
for (unsigned int i = 0; i < 0x20 && !matched_key; i++) {
|
||||
snprintf(test_name, sizeof(test_name), "keyblob_key_source_%02"PRIx32, i);
|
||||
if (strcmp(key, test_name) == 0) {
|
||||
parse_hex_key(keyset->keyblob_key_sources[i], value, sizeof(keyset->keyblob_key_sources[i]));
|
||||
matched_key = 1;
|
||||
break;
|
||||
}
|
||||
|
||||
snprintf(test_name, sizeof(test_name), "keyblob_key_%02"PRIx32, i);
|
||||
if (strcmp(key, test_name) == 0) {
|
||||
parse_hex_key(keyset->keyblob_keys[i], value, sizeof(keyset->keyblob_keys[i]));
|
||||
matched_key = 1;
|
||||
break;
|
||||
}
|
||||
|
||||
snprintf(test_name, sizeof(test_name), "keyblob_mac_key_%02"PRIx32, i);
|
||||
if (strcmp(key, test_name) == 0) {
|
||||
parse_hex_key(keyset->keyblob_mac_keys[i], value, sizeof(keyset->keyblob_mac_keys[i]));
|
||||
matched_key = 1;
|
||||
break;
|
||||
}
|
||||
|
||||
snprintf(test_name, sizeof(test_name), "encrypted_keyblob_%02"PRIx32, i);
|
||||
if (strcmp(key, test_name) == 0) {
|
||||
parse_hex_key(keyset->encrypted_keyblobs[i], value, sizeof(keyset->encrypted_keyblobs[i]));
|
||||
matched_key = 1;
|
||||
break;
|
||||
}
|
||||
|
||||
snprintf(test_name, sizeof(test_name), "keyblob_%02"PRIx32, i);
|
||||
if (strcmp(key, test_name) == 0) {
|
||||
parse_hex_key(keyset->keyblobs[i], value, sizeof(keyset->keyblobs[i]));
|
||||
matched_key = 1;
|
||||
break;
|
||||
}
|
||||
|
||||
snprintf(test_name, sizeof(test_name), "master_key_%02"PRIx32, i);
|
||||
if (strcmp(key, test_name) == 0) {
|
||||
parse_hex_key(keyset->master_keys[i], value, sizeof(keyset->master_keys[i]));
|
||||
|
|
44
main.c
44
main.c
|
@ -31,7 +31,7 @@ static void usage(void) {
|
|||
" -y, --verify Verify hashes and signatures.\n"
|
||||
" -d, --dev Decrypt with development keys instead of retail.\n"
|
||||
" -k, --keyset Load keys from an external file.\n"
|
||||
" -t, --intype=type Specify input file type [nca, xci, pfs0, romfs, hfs0, npdm, pk11, pk21, ini1, kip1]\n"
|
||||
" -t, --intype=type Specify input file type [nca, xci, pfs0, romfs, hfs0, npdm, pk11, pk21, ini1, kip1, keygen]\n"
|
||||
" --titlekey=key Set title key for Rights ID crypto titles.\n"
|
||||
" --contentkey=key Set raw key for NCA body decryption.\n"
|
||||
"NCA options:\n"
|
||||
|
@ -86,6 +86,9 @@ static void usage(void) {
|
|||
"NAX0 options:\n"
|
||||
" --sdseed=seed Set console unique seed for SD card NAX0 encryption.\n"
|
||||
" --sdpath=path Set relative path for NAX0 key derivation (ex: /registered/000000FF/cafebabecafebabecafebabecafebabe.nca).\n"
|
||||
"Key Derivation options:\n"
|
||||
" --sbk=key Set console unique Secure Boot Key for key derivation.\n"
|
||||
" --tseckey=key Set console unique TSEC Key for key derivation.\n"
|
||||
"\n", __TIME__, __DATE__, prog_name);
|
||||
exit(EXIT_FAILURE);
|
||||
}
|
||||
|
@ -158,6 +161,8 @@ int main(int argc, char **argv) {
|
|||
{"onlyupdated", 0, NULL, 31},
|
||||
{"sdseed", 1, NULL, 32},
|
||||
{"sdpath", 1, NULL, 33},
|
||||
{"sbk", 1, NULL, 34},
|
||||
{"tseckey", 1, NULL, 35},
|
||||
{NULL, 0, NULL, 0},
|
||||
};
|
||||
|
||||
|
@ -209,6 +214,8 @@ int main(int argc, char **argv) {
|
|||
nca_ctx.tool_ctx->file_type = FILETYPE_KIP1;
|
||||
} else if (!strcmp(optarg, "nax0") || !strcmp(optarg, "nax")) {
|
||||
nca_ctx.tool_ctx->file_type = FILETYPE_NAX0;
|
||||
} else if (!strcmp(optarg, "keygen") || !strcmp(optarg, "keys") || !strcmp(optarg, "boot0") || !strcmp(optarg, "boot")) {
|
||||
nca_ctx.tool_ctx->file_type = FILETYPE_BOOT0;
|
||||
}
|
||||
break;
|
||||
case 0: filepath_set(&nca_ctx.tool_ctx->settings.section_paths[0], optarg); break;
|
||||
|
@ -340,6 +347,12 @@ int main(int argc, char **argv) {
|
|||
case 33:
|
||||
filepath_set(&tool_ctx.settings.nax0_sd_path, optarg);
|
||||
break;
|
||||
case 34:
|
||||
parse_hex_key(nca_ctx.tool_ctx->settings.keygen_sbk, optarg, 16);
|
||||
break;
|
||||
case 35:
|
||||
parse_hex_key(nca_ctx.tool_ctx->settings.keygen_tsec, optarg, 16);
|
||||
break;
|
||||
default:
|
||||
usage();
|
||||
return EXIT_FAILURE;
|
||||
|
@ -589,12 +602,39 @@ int main(int argc, char **argv) {
|
|||
xci_process(&xci_ctx);
|
||||
break;
|
||||
}
|
||||
case FILETYPE_BOOT0: {
|
||||
nca_keyset_t new_keyset;
|
||||
memcpy(&new_keyset, &tool_ctx.settings.keyset, sizeof(new_keyset));
|
||||
for (unsigned int i = 0; i < 0x10; i++) {
|
||||
if (tool_ctx.settings.keygen_sbk[i] != 0) {
|
||||
memcpy(new_keyset.secure_boot_key, tool_ctx.settings.keygen_sbk, 0x10);
|
||||
}
|
||||
}
|
||||
for (unsigned int i = 0; i < 0x10; i++) {
|
||||
if (tool_ctx.settings.keygen_tsec[i] != 0) {
|
||||
memcpy(new_keyset.tsec_key, tool_ctx.settings.keygen_tsec, 0x10);
|
||||
}
|
||||
}
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
fseek(tool_ctx.file, 0x180000 + 0x200 * i, SEEK_SET);
|
||||
if (fread(&new_keyset.encrypted_keyblobs[i], sizeof(new_keyset.encrypted_keyblobs[i]), 1, tool_ctx.file) != 1) {
|
||||
fprintf(stderr, "Error: Failed to read encrypted_keyblob_%02x from boot0!\n", i);
|
||||
return EXIT_FAILURE;
|
||||
}
|
||||
}
|
||||
printf("Deriving keys...\n");
|
||||
pki_derive_keys(&new_keyset);
|
||||
printf("--\n");
|
||||
printf("All derivable keys (using loaded sources):\n\n");
|
||||
pki_print_keys(&new_keyset);
|
||||
break;
|
||||
}
|
||||
default: {
|
||||
fprintf(stderr, "Unknown File Type!\n\n");
|
||||
usage();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (tool_ctx.file != NULL) {
|
||||
fclose(tool_ctx.file);
|
||||
}
|
||||
|
|
|
@ -1783,7 +1783,7 @@
|
|||
* Requires: MBEDTLS_AES_C or MBEDTLS_DES_C
|
||||
*
|
||||
*/
|
||||
//#define MBEDTLS_CMAC_C
|
||||
#define MBEDTLS_CMAC_C
|
||||
|
||||
/**
|
||||
* \def MBEDTLS_CTR_DRBG_C
|
||||
|
|
497
pki.c
497
pki.c
|
@ -4,6 +4,180 @@
|
|||
#include "pki.h"
|
||||
|
||||
const nca_keyset_t nca_keys_retail = {
|
||||
ZEROES_KEY, /* Secure Boot Key (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* TSEC Key (CONSOLE UNIQUE) */
|
||||
{
|
||||
ZEROES_KEY, /* Keyblob Key 00 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 01 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 02 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 03 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 04 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 05 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 06 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 07 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 08 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 09 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 10 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 11 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 12 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 13 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 14 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 15 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 16 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 17 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 18 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 19 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 20 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 21 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 22 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 23 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 24 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 25 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 26 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 27 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 28 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 29 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 30 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY /* Keyblob Key 31 (CONSOLE UNIQUE) */
|
||||
},
|
||||
{
|
||||
ZEROES_KEY, /* Keyblob Mac Key 00 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 01 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 02 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 03 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 04 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 05 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 06 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 07 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 08 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 09 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 10 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 11 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 12 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 13 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 14 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 15 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 16 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 17 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 18 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 19 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 20 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 21 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 22 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 23 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 24 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 25 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 26 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 27 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 28 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 29 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 30 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY /* Keyblob Mac Key 31 (CONSOLE UNIQUE) */
|
||||
},
|
||||
{
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 00 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 01 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 02 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 03 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 04 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 05 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 06 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 07 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 08 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 09 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 10 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 11 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 12 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 13 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 14 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 15 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 16 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 17 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 18 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 19 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 20 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 21 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 22 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 23 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 24 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 25 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 26 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 27 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 28 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 29 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 30 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB /* Encrypted Keyblob 31 (CONSOLE UNIQUE) */
|
||||
},
|
||||
{
|
||||
ZEROES_KEYBLOB, /* Keyblob 00 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 01 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 02 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 03 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 04 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 05 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 06 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 07 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 08 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 09 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 10 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 11 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 12 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 13 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 14 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 15 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 16 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 17 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 18 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 19 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 20 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 21 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 22 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 23 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 24 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 25 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 26 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 27 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 28 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 29 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 30 */
|
||||
ZEROES_KEYBLOB /* Keyblob 31 */
|
||||
},
|
||||
{
|
||||
ZEROES_KEY, /* Keyblob Key Source 00 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 01 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 02 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 03 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 04 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 05 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 06 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 07 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 08 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 09 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 10 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 11 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 12 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 13 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 14 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 15 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 16 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 17 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 18 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 19 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 20 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 21 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 22 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 23 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 24 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 25 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 26 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 27 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 28 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 29 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 30 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY /* Keyblob Key Source 31 (CONSOLE UNIQUE) */
|
||||
},
|
||||
ZEROES_KEY, /* Keyblob Mac Key Source */
|
||||
ZEROES_KEY, /* Master Key Source */
|
||||
{
|
||||
ZEROES_KEY, /* Master Key 00 */
|
||||
ZEROES_KEY, /* Master Key 01 */
|
||||
|
@ -250,6 +424,180 @@ const nca_keyset_t nca_keys_retail = {
|
|||
};
|
||||
|
||||
const nca_keyset_t nca_keys_dev = {
|
||||
ZEROES_KEY, /* Secure Boot Key (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* TSEC Key (CONSOLE UNIQUE) */
|
||||
{
|
||||
ZEROES_KEY, /* Keyblob Key 00 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 01 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 02 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 03 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 04 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 05 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 06 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 07 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 08 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 09 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 10 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 11 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 12 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 13 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 14 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 15 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 16 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 17 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 18 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 19 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 20 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 21 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 22 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 23 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 24 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 25 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 26 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 27 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 28 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 29 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key 30 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY /* Keyblob Key 31 (CONSOLE UNIQUE) */
|
||||
},
|
||||
{
|
||||
ZEROES_KEY, /* Keyblob Mac Key 00 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 01 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 02 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 03 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 04 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 05 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 06 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 07 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 08 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 09 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 10 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 11 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 12 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 13 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 14 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 15 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 16 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 17 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 18 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 19 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 20 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 21 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 22 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 23 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 24 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 25 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 26 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 27 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 28 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 29 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Mac Key 30 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY /* Keyblob Mac Key 31 (CONSOLE UNIQUE) */
|
||||
},
|
||||
{
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 00 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 01 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 02 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 03 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 04 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 05 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 06 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 07 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 08 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 09 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 10 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 11 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 12 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 13 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 14 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 15 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 16 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 17 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 18 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 19 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 20 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 21 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 22 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 23 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 24 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 25 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 26 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 27 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 28 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 29 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB, /* Encrypted Keyblob 30 (CONSOLE UNIQUE) */
|
||||
ZEROES_ENC_KEYBLOB /* Encrypted Keyblob 31 (CONSOLE UNIQUE) */
|
||||
},
|
||||
{
|
||||
ZEROES_KEYBLOB, /* Keyblob 00 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 01 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 02 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 03 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 04 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 05 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 06 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 07 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 08 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 09 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 10 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 11 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 12 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 13 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 14 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 15 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 16 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 17 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 18 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 19 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 20 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 21 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 22 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 23 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 24 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 25 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 26 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 27 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 28 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 29 */
|
||||
ZEROES_KEYBLOB, /* Keyblob 30 */
|
||||
ZEROES_KEYBLOB /* Keyblob 31 */
|
||||
},
|
||||
{
|
||||
ZEROES_KEY, /* Keyblob Key Source 00 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 01 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 02 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 03 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 04 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 05 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 06 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 07 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 08 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 09 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 10 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 11 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 12 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 13 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 14 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 15 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 16 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 17 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 18 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 19 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 20 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 21 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 22 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 23 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 24 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 25 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 26 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 27 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 28 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 29 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY, /* Keyblob Key Source 30 (CONSOLE UNIQUE) */
|
||||
ZEROES_KEY /* Keyblob Key Source 31 (CONSOLE UNIQUE) */
|
||||
},
|
||||
ZEROES_KEY, /* Keyblob Mac Key Source */
|
||||
ZEROES_KEY, /* Master Key Source */
|
||||
{
|
||||
ZEROES_KEY, /* Master Key 00 */
|
||||
ZEROES_KEY, /* Master Key 01 */
|
||||
|
@ -518,8 +866,72 @@ void generate_kek(unsigned char *dst, const unsigned char *src, const unsigned c
|
|||
|
||||
void pki_derive_keys(nca_keyset_t *keyset) {
|
||||
unsigned char zeroes[0x100];
|
||||
unsigned char cmac[0x10];
|
||||
memset(zeroes, 0, 0x100);
|
||||
memset(cmac, 0, 0x10);
|
||||
/* Derive keys as necessary. */
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
/* Start by deriving keyblob keys. */
|
||||
if (memcmp(&keyset->secure_boot_key, zeroes, 0x10) == 0) {
|
||||
continue;
|
||||
}
|
||||
if (memcmp(&keyset->tsec_key, zeroes, 0x10) == 0) {
|
||||
continue;
|
||||
}
|
||||
if (memcmp(&keyset->keyblob_key_sources[i], zeroes, 0x10) == 0) {
|
||||
continue;
|
||||
}
|
||||
aes_ctx_t *sbk_ctx = new_aes_ctx(keyset->secure_boot_key, 0x10, AES_MODE_ECB);
|
||||
aes_ctx_t *tsec_ctx = new_aes_ctx(keyset->tsec_key, 0x10, AES_MODE_ECB);
|
||||
aes_decrypt(tsec_ctx, &keyset->keyblob_keys[i], &keyset->keyblob_key_sources[i], 0x10);
|
||||
aes_decrypt(sbk_ctx, &keyset->keyblob_keys[i], &keyset->keyblob_keys[i], 0x10);
|
||||
free_aes_ctx(tsec_ctx);
|
||||
free_aes_ctx(sbk_ctx);
|
||||
if (memcmp(keyset->keyblob_mac_key_source, zeroes, 0x10) == 0) {
|
||||
continue;
|
||||
}
|
||||
aes_ctx_t *mac_gen_ctx = new_aes_ctx(&keyset->keyblob_keys[i], 0x10, AES_MODE_ECB);
|
||||
aes_decrypt(sbk_ctx, &keyset->keyblob_mac_keys[i], keyset->keyblob_mac_key_source, 0x10);
|
||||
free_aes_ctx(mac_gen_ctx);
|
||||
}
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
/* Then we decrypt keyblobs. */
|
||||
if (memcmp(&keyset->keyblob_keys[i], zeroes, 0x10) == 0) {
|
||||
continue;
|
||||
}
|
||||
if (memcmp(&keyset->keyblob_mac_keys[i], zeroes, 0x10) == 0) {
|
||||
continue;
|
||||
}
|
||||
if (memcmp(&keyset->encrypted_keyblobs[i], zeroes, 0xB0) == 0) {
|
||||
continue;
|
||||
}
|
||||
aes_calculate_cmac(cmac, &keyset->encrypted_keyblobs[i][0x10], 0xA0, keyset->keyblob_mac_keys[i]);
|
||||
if (memcmp(cmac, &keyset->encrypted_keyblobs[i][0], 0x10) != 0) {
|
||||
fprintf(stderr, "[ WARN ] Keyblob MAC %02x is invalid. Are SBK/TSEC key correct?\n", i);
|
||||
continue;
|
||||
}
|
||||
aes_ctx_t *keyblob_ctx = new_aes_ctx(&keyset->keyblob_keys[i], 0x10, AES_MODE_CTR);
|
||||
aes_setiv(keyblob_ctx, &keyset->encrypted_keyblobs[i][0x10], 0x10);
|
||||
aes_decrypt(keyblob_ctx, &keyset->keyblobs[i], &keyset->encrypted_keyblobs[i][0x20], sizeof(keyset->keyblobs[i]));
|
||||
free_aes_ctx(keyblob_ctx);
|
||||
/* Package1 key is at the end of the keyblob. */
|
||||
memcpy(&keyset->package1_keys[i], &keyset->keyblobs[i][0x80], 0x10);
|
||||
}
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
/* Then we derive master keys. */
|
||||
if (memcmp(keyset->master_key_source, zeroes, 0x10) == 0) {
|
||||
continue;
|
||||
}
|
||||
/* We only need the first key in the blob. */
|
||||
if (memcmp(keyset->keyblobs[i], zeroes, 0x10) == 0) {
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Derive Master Keys. */
|
||||
aes_ctx_t *master_gen_ctx = new_aes_ctx(&keyset->keyblobs[i], 0x10, AES_MODE_ECB);
|
||||
aes_decrypt(master_gen_ctx, &keyset->master_keys[i], keyset->master_key_source, 0x10);
|
||||
free_aes_ctx(master_gen_ctx);
|
||||
}
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
if (memcmp(&keyset->master_keys[i], zeroes, 0x10) == 0) {
|
||||
continue;
|
||||
|
@ -577,6 +989,91 @@ void pki_derive_keys(nca_keyset_t *keyset) {
|
|||
|
||||
}
|
||||
|
||||
void pki_print_keys(nca_keyset_t *keyset) {
|
||||
unsigned char zeroes[0x100] = {0};
|
||||
#define PRINT_KEY_WITH_NAME(ky, kn) do { if (memcmp(ky, zeroes, sizeof(ky)) != 0) { printf("%-32s= ", #kn); for (unsigned int k_i = 0; k_i < sizeof(ky); k_i++) { printf("%02X", ky[k_i]); } printf("\n"); } } while (0)
|
||||
#define PRINT_KEY_WITH_NAME_IDX(ky, kn, idx) do { if (memcmp(ky, zeroes, sizeof(ky)) != 0) { char KEY_NAME[32]; snprintf(KEY_NAME, sizeof(KEY_NAME), "%s_%02"PRIx32, #kn, idx); printf("%-32s= ", KEY_NAME); for (unsigned int k_i = 0; k_i < sizeof(ky); k_i++) { printf("%02X", ky[k_i]); } printf("\n"); } } while (0)
|
||||
|
||||
PRINT_KEY_WITH_NAME(keyset->secure_boot_key, secure_boot_key);
|
||||
PRINT_KEY_WITH_NAME(keyset->tsec_key, tsec_key);
|
||||
printf("\n");
|
||||
PRINT_KEY_WITH_NAME(keyset->keyblob_mac_key_source, keyblob_mac_key_source);
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->keyblob_key_sources[i], keyblob_key_source, i);
|
||||
}
|
||||
printf("\n");
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->keyblob_keys[i], keyblob_key, i);
|
||||
}
|
||||
printf("\n");
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->keyblob_mac_keys[i], keyblob_mac_key, i);
|
||||
}
|
||||
printf("\n");
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->encrypted_keyblobs[i], encrypted_keyblob, i);
|
||||
}
|
||||
printf("\n");
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->keyblobs[i], keyblob, i);
|
||||
}
|
||||
printf("\n");
|
||||
PRINT_KEY_WITH_NAME(keyset->master_key_source, master_key_source);
|
||||
printf("\n");
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->master_keys[i], master_key, i);
|
||||
}
|
||||
printf("\n");
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->package1_keys[i], package1_key, i);
|
||||
}
|
||||
printf("\n");
|
||||
PRINT_KEY_WITH_NAME(keyset->package2_key_source, package2_key_source);
|
||||
printf("\n");
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->package2_keys[i], package2_key, i);
|
||||
}
|
||||
printf("\n");
|
||||
PRINT_KEY_WITH_NAME(keyset->aes_kek_generation_source, aes_kek_generation_source);
|
||||
PRINT_KEY_WITH_NAME(keyset->aes_key_generation_source, aes_kek_generation_source);
|
||||
PRINT_KEY_WITH_NAME(keyset->titlekek_source, titlekek_source);
|
||||
printf("\n");
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->titlekeks[i], titlekek, i);
|
||||
}
|
||||
printf("\n");
|
||||
PRINT_KEY_WITH_NAME(keyset->key_area_key_application_source, key_area_key_application_source);
|
||||
PRINT_KEY_WITH_NAME(keyset->key_area_key_ocean_source, key_area_key_ocean_source);
|
||||
PRINT_KEY_WITH_NAME(keyset->key_area_key_system_source, key_area_key_system_source);
|
||||
PRINT_KEY_WITH_NAME(keyset->sd_card_kek_source, sd_card_kek_source);
|
||||
PRINT_KEY_WITH_NAME(keyset->sd_card_key_sources[0], sd_card_save_key_source);
|
||||
PRINT_KEY_WITH_NAME(keyset->sd_card_key_sources[1], sd_card_nca_key_source);
|
||||
printf("\n");
|
||||
PRINT_KEY_WITH_NAME(keyset->encrypted_header_key, encrypted_header_key);
|
||||
PRINT_KEY_WITH_NAME(keyset->header_key, header_key);
|
||||
printf("\n");
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->key_area_keys[i][0], key_area_key_application, i);
|
||||
}
|
||||
printf("\n");
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->key_area_keys[i][1], key_area_key_ocean, i);
|
||||
}
|
||||
printf("\n");
|
||||
for (unsigned int i = 0; i < 0x20; i++) {
|
||||
PRINT_KEY_WITH_NAME_IDX(keyset->key_area_keys[i][2], key_area_key_system, i);
|
||||
}
|
||||
printf("\n");
|
||||
|
||||
/*
|
||||
unsigned char titlekeks[0x20][0x10];
|
||||
unsigned char key_area_keys[0x20][3][0x10];
|
||||
*/
|
||||
|
||||
#undef PRINT_KEY_WITH_NAME
|
||||
#undef PRINT_KEY
|
||||
}
|
||||
|
||||
void pki_initialize_keyset(nca_keyset_t *keyset, keyset_variant_t variant) {
|
||||
switch (variant) {
|
||||
case KEYSET_DEV:
|
||||
|
|
3
pki.h
3
pki.h
|
@ -6,9 +6,12 @@
|
|||
|
||||
#define ZEROES_KEY {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}
|
||||
#define ZEROES_XTS_KEY {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}
|
||||
#define ZEROES_KEYBLOB {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}
|
||||
#define ZEROES_ENC_KEYBLOB {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}
|
||||
#define ZEROES_KAEKS {ZEROES_KEY, ZEROES_KEY, ZEROES_KEY}
|
||||
|
||||
void pki_derive_keys(nca_keyset_t *keyset);
|
||||
void pki_print_keys(nca_keyset_t *keyset);
|
||||
void pki_initialize_keyset(nca_keyset_t *keyset, keyset_variant_t variant);
|
||||
|
||||
#endif
|
16
settings.h
16
settings.h
|
@ -16,6 +16,15 @@ typedef enum {
|
|||
} hactool_basefile_t;
|
||||
|
||||
typedef struct {
|
||||
unsigned char secure_boot_key[0x10]; /* Secure boot key for use in key derivation. NOTE: CONSOLE UNIQUE. */
|
||||
unsigned char tsec_key[0x10]; /* TSEC key for use in key derivation. NOTE: CONSOLE UNIQUE. */
|
||||
unsigned char keyblob_keys[0x20][0x10]; /* Actual keys used to decrypt keyblobs. NOTE: CONSOLE UNIQUE.*/
|
||||
unsigned char keyblob_mac_keys[0x20][0x10]; /* Keys used to validate keyblobs. NOTE: CONSOLE UNIQUE. */
|
||||
unsigned char encrypted_keyblobs[0x20][0xB0]; /* Actual encrypted keyblobs (EKS). NOTE: CONSOLE UNIQUE. */
|
||||
unsigned char keyblobs[0x20][0xB0]; /* Actual decrypted keyblobs (EKS). */
|
||||
unsigned char keyblob_key_sources[0x20][0x10]; /* Seeds for keyblob keys. */
|
||||
unsigned char keyblob_mac_key_source[0x10]; /* Seed for keyblob MAC key derivation. */
|
||||
unsigned char master_key_source[0x10]; /* Seed for master key derivation. */
|
||||
unsigned char master_keys[0x20][0x10]; /* Firmware master keys. */
|
||||
unsigned char package1_keys[0x20][0x10]; /* Package1 keys. */
|
||||
unsigned char package2_keys[0x20][0x10]; /* Package2 keys. */
|
||||
|
@ -28,7 +37,7 @@ typedef struct {
|
|||
unsigned char titlekek_source[0x10]; /* Seed for titlekeks. */
|
||||
unsigned char header_kek_source[0x10]; /* Seed for header kek. */
|
||||
unsigned char sd_card_kek_source[0x10]; /* Seed for SD card kek. */
|
||||
unsigned char sd_card_key_sources[2][0x20]; /* Seed for SD card encryption keys. */
|
||||
unsigned char sd_card_key_sources[2][0x20]; /* Seed for SD card encryption keys. */
|
||||
unsigned char encrypted_header_key[0x20]; /* Actual encrypted header key. */
|
||||
unsigned char header_key[0x20]; /* NCA header key. */
|
||||
unsigned char titlekeks[0x20][0x10]; /* Title key encryption keys. */
|
||||
|
@ -53,6 +62,8 @@ typedef struct {
|
|||
unsigned char contentkey[0x10];
|
||||
int has_sdseed;
|
||||
unsigned char sdseed[0x10];
|
||||
unsigned char keygen_sbk[0x10];
|
||||
unsigned char keygen_tsec[0x10];
|
||||
filepath_t section_paths[4];
|
||||
filepath_t section_dir_paths[4];
|
||||
override_filepath_t exefs_path;
|
||||
|
@ -87,7 +98,8 @@ enum hactool_file_type
|
|||
FILETYPE_PACKAGE2,
|
||||
FILETYPE_INI1,
|
||||
FILETYPE_KIP1,
|
||||
FILETYPE_NAX0
|
||||
FILETYPE_NAX0,
|
||||
FILETYPE_BOOT0
|
||||
};
|
||||
|
||||
#define ACTION_INFO (1<<0)
|
||||
|
|
Loading…
Reference in a new issue