mirror of
https://github.com/DarkMatterCore/nxdumptool.git
synced 2024-11-26 20:22:17 +00:00
Match changes to the XCI page in Switchbrew.
This commit is contained in:
parent
86dbe3ffd8
commit
460bee888b
2 changed files with 30 additions and 30 deletions
|
@ -33,8 +33,8 @@ extern "C" {
|
||||||
|
|
||||||
#define GAMECARD_HEAD_MAGIC 0x48454144 /* "HEAD". */
|
#define GAMECARD_HEAD_MAGIC 0x48454144 /* "HEAD". */
|
||||||
|
|
||||||
#define GAMECARD_MEDIA_UNIT_SIZE 0x200
|
#define GAMECARD_PAGE_SIZE 0x200
|
||||||
#define GAMECARD_MEDIA_UNIT_OFFSET(x) ((u64)(x) * GAMECARD_MEDIA_UNIT_SIZE)
|
#define GAMECARD_PAGE_OFFSET(x) ((u64)(x) * GAMECARD_PAGE_SIZE)
|
||||||
|
|
||||||
#define GAMECARD_UPDATE_TID SYSTEM_UPDATE_TID
|
#define GAMECARD_UPDATE_TID SYSTEM_UPDATE_TID
|
||||||
|
|
||||||
|
@ -123,8 +123,8 @@ typedef enum {
|
||||||
typedef enum {
|
typedef enum {
|
||||||
GameCardFwVersion_ForDev = 0,
|
GameCardFwVersion_ForDev = 0,
|
||||||
GameCardFwVersion_ForProd = BIT(0),
|
GameCardFwVersion_ForProd = BIT(0),
|
||||||
GameCardFwVersion_ForProdSince400NUP = BIT(1), ///< cup_version >= 268435456 (4.0.0-0.0) in GameCardHeaderEncryptedArea.
|
GameCardFwVersion_ForProdSince400NUP = BIT(1), ///< upp_version >= 268435456 (4.0.0-0.0) in GameCardInfo.
|
||||||
GameCardFwVersion_ForProdSince1100NUP = BIT(2) ///< cup_version >= 738197504 (11.0.0-0.0) in GameCardHeaderEncryptedArea.
|
GameCardFwVersion_ForProdSince1100NUP = BIT(2) ///< upp_version >= 738197504 (11.0.0-0.0) in GameCardInfo.
|
||||||
} GameCardFwVersion;
|
} GameCardFwVersion;
|
||||||
|
|
||||||
typedef enum {
|
typedef enum {
|
||||||
|
@ -148,40 +148,40 @@ typedef struct {
|
||||||
u32 wait_2_time_read; ///< Always 0.
|
u32 wait_2_time_read; ///< Always 0.
|
||||||
u32 wait_1_time_write; ///< Always 0.
|
u32 wait_1_time_write; ///< Always 0.
|
||||||
u32 wait_2_time_write; ///< Always 0.
|
u32 wait_2_time_write; ///< Always 0.
|
||||||
VersionType2 fw_mode;
|
VersionType2 fw_mode; ///< Current SdkAddonVersion.
|
||||||
VersionType1 cup_version;
|
VersionType1 upp_version; ///< Bundled system update version.
|
||||||
u8 compatibility_type; ///< GameCardCompatibilityType.
|
u8 compatibility_type; ///< GameCardCompatibilityType.
|
||||||
u8 reserved_1[0x3];
|
u8 reserved_1[0x3];
|
||||||
u64 cup_hash;
|
u64 upp_hash; ///< SHA-256 checksum for the update partition.
|
||||||
u64 cup_id; ///< Must match GAMECARD_UPDATE_TID.
|
u64 upp_id; ///< Must match GAMECARD_UPDATE_TID.
|
||||||
u8 reserved_2[0x38];
|
u8 reserved_2[0x38];
|
||||||
} GameCardHeaderEncryptedArea;
|
} GameCardInfo;
|
||||||
|
|
||||||
NXDT_ASSERT(GameCardHeaderEncryptedArea, 0x70);
|
NXDT_ASSERT(GameCardInfo, 0x70);
|
||||||
|
|
||||||
/// Placed after the `GameCardKeyArea` section.
|
/// Placed after the `GameCardKeyArea` section.
|
||||||
typedef struct {
|
typedef struct {
|
||||||
u8 signature[0x100]; ///< RSA-2048-PSS with SHA-256 signature over the rest of the header.
|
u8 signature[0x100]; ///< RSA-2048-PSS with SHA-256 signature over the rest of the header.
|
||||||
u32 magic; ///< "HEAD".
|
u32 magic; ///< "HEAD".
|
||||||
u32 secure_area_start_address; ///< Expressed in GAMECARD_MEDIA_UNIT_SIZE blocks.
|
u32 rom_area_start_page_address; ///< Expressed in GAMECARD_PAGE_SIZE units.
|
||||||
u32 backup_area_start_address; ///< Always 0xFFFFFFFF.
|
u32 backup_area_start_page_address; ///< Always 0xFFFFFFFF.
|
||||||
GameCardKeyIndex key_index;
|
GameCardKeyIndex key_index;
|
||||||
u8 rom_size; ///< GameCardRomSize.
|
u8 rom_size; ///< GameCardRomSize.
|
||||||
u8 header_version; ///< Always 0.
|
u8 header_version; ///< Always 0.
|
||||||
u8 flags; ///< GameCardFlags.
|
u8 flags; ///< GameCardFlags.
|
||||||
u64 package_id;
|
u64 package_id; ///< Used for challenge–response authentication.
|
||||||
u32 valid_data_end_address; ///< Expressed in GAMECARD_MEDIA_UNIT_SIZE blocks.
|
u32 valid_data_end_address; ///< Expressed in GAMECARD_PAGE_SIZE units.
|
||||||
u8 reserved[0x4];
|
u8 reserved[0x4];
|
||||||
u8 iv[0x10];
|
u8 iv[0x10];
|
||||||
u64 partition_fs_header_address; ///< Root HFS0 header offset.
|
u64 partition_fs_header_address; ///< Root Hash File System header offset.
|
||||||
u64 partition_fs_header_size; ///< Root HFS0 header size.
|
u64 partition_fs_header_size; ///< Root Hash File System header size.
|
||||||
u8 partition_fs_header_hash[SHA256_HASH_SIZE];
|
u8 partition_fs_header_hash[SHA256_HASH_SIZE];
|
||||||
u8 initial_data_hash[SHA256_HASH_SIZE];
|
u8 initial_data_hash[SHA256_HASH_SIZE];
|
||||||
u32 sel_sec; ///< GameCardSelSec.
|
u32 sel_sec; ///< GameCardSelSec.
|
||||||
u32 sel_t1_key; ///< Always 2.
|
u32 sel_t1_key; ///< Always 2.
|
||||||
u32 sel_key; ///> Always 0.
|
u32 sel_key; ///> Always 0.
|
||||||
u32 normal_area_end_address; ///< Expressed in GAMECARD_MEDIA_UNIT_SIZE blocks.
|
u32 lim_area; ///< Expressed in GAMECARD_PAGE_SIZE units.
|
||||||
GameCardHeaderEncryptedArea encrypted_area;
|
GameCardInfo card_info;
|
||||||
} GameCardHeader;
|
} GameCardHeader;
|
||||||
|
|
||||||
NXDT_ASSERT(GameCardHeader, 0x200);
|
NXDT_ASSERT(GameCardHeader, 0x200);
|
||||||
|
|
|
@ -30,7 +30,7 @@
|
||||||
#define GAMECARD_ACCESS_WAIT_TIME 3 /* Seconds. */
|
#define GAMECARD_ACCESS_WAIT_TIME 3 /* Seconds. */
|
||||||
|
|
||||||
#define GAMECARD_UNUSED_AREA_BLOCK_SIZE 0x24
|
#define GAMECARD_UNUSED_AREA_BLOCK_SIZE 0x24
|
||||||
#define GAMECARD_UNUSED_AREA_SIZE(x) (((x) / GAMECARD_MEDIA_UNIT_SIZE) * GAMECARD_UNUSED_AREA_BLOCK_SIZE)
|
#define GAMECARD_UNUSED_AREA_SIZE(x) (((x) / GAMECARD_PAGE_SIZE) * GAMECARD_UNUSED_AREA_BLOCK_SIZE)
|
||||||
|
|
||||||
#define GAMECARD_STORAGE_AREA_NAME(x) ((x) == GameCardStorageArea_Normal ? "normal" : ((x) == GameCardStorageArea_Secure ? "secure" : "none"))
|
#define GAMECARD_STORAGE_AREA_NAME(x) ((x) == GameCardStorageArea_Normal ? "normal" : ((x) == GameCardStorageArea_Secure ? "secure" : "none"))
|
||||||
|
|
||||||
|
@ -322,7 +322,7 @@ bool gamecardGetTrimmedSize(u64 *out)
|
||||||
{
|
{
|
||||||
mutexLock(&g_gameCardMutex);
|
mutexLock(&g_gameCardMutex);
|
||||||
bool ret = (g_gameCardInserted && g_gameCardInfoLoaded && out);
|
bool ret = (g_gameCardInserted && g_gameCardInfoLoaded && out);
|
||||||
if (ret) *out = (sizeof(GameCardHeader) + GAMECARD_MEDIA_UNIT_OFFSET(g_gameCardHeader.valid_data_end_address));
|
if (ret) *out = (sizeof(GameCardHeader) + GAMECARD_PAGE_OFFSET(g_gameCardHeader.valid_data_end_address));
|
||||||
mutexUnlock(&g_gameCardMutex);
|
mutexUnlock(&g_gameCardMutex);
|
||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
@ -840,9 +840,9 @@ static bool gamecardReadStorageArea(void *out, u64 read_size, u64 offset, bool l
|
||||||
/* Calculate appropiate storage area offset and retrieve the right storage area pointer. */
|
/* Calculate appropiate storage area offset and retrieve the right storage area pointer. */
|
||||||
u64 base_offset = (area == GameCardStorageArea_Normal ? offset : (offset - g_gameCardStorageNormalAreaSize));
|
u64 base_offset = (area == GameCardStorageArea_Normal ? offset : (offset - g_gameCardStorageNormalAreaSize));
|
||||||
|
|
||||||
if (!(base_offset % GAMECARD_MEDIA_UNIT_SIZE) && !(read_size % GAMECARD_MEDIA_UNIT_SIZE))
|
if (!(base_offset % GAMECARD_PAGE_SIZE) && !(read_size % GAMECARD_PAGE_SIZE))
|
||||||
{
|
{
|
||||||
/* Optimization for reads that are already aligned to a GAMECARD_MEDIA_UNIT_SIZE boundary. */
|
/* Optimization for reads that are already aligned to a GAMECARD_PAGE_SIZE boundary. */
|
||||||
rc = fsStorageRead(&g_gameCardStorage, base_offset, out_u8, read_size);
|
rc = fsStorageRead(&g_gameCardStorage, base_offset, out_u8, read_size);
|
||||||
if (R_FAILED(rc))
|
if (R_FAILED(rc))
|
||||||
{
|
{
|
||||||
|
@ -853,8 +853,8 @@ static bool gamecardReadStorageArea(void *out, u64 read_size, u64 offset, bool l
|
||||||
success = true;
|
success = true;
|
||||||
} else {
|
} else {
|
||||||
/* Fix offset and/or size to avoid unaligned reads. */
|
/* Fix offset and/or size to avoid unaligned reads. */
|
||||||
u64 block_start_offset = ALIGN_DOWN(base_offset, GAMECARD_MEDIA_UNIT_SIZE);
|
u64 block_start_offset = ALIGN_DOWN(base_offset, GAMECARD_PAGE_SIZE);
|
||||||
u64 block_end_offset = ALIGN_UP(base_offset + read_size, GAMECARD_MEDIA_UNIT_SIZE);
|
u64 block_end_offset = ALIGN_UP(base_offset + read_size, GAMECARD_PAGE_SIZE);
|
||||||
u64 block_size = (block_end_offset - block_start_offset);
|
u64 block_size = (block_end_offset - block_start_offset);
|
||||||
|
|
||||||
u64 data_start_offset = (base_offset - block_start_offset);
|
u64 data_start_offset = (base_offset - block_start_offset);
|
||||||
|
@ -976,8 +976,8 @@ static HashFileSystemContext *gamecardInitializeHashFileSystemContext(const char
|
||||||
|
|
||||||
bool success = false, dump_fs_header = false;
|
bool success = false, dump_fs_header = false;
|
||||||
|
|
||||||
if ((name && !*name) || offset < (GAMECARD_CERTIFICATE_OFFSET + sizeof(FsGameCardCertificate)) || !IS_ALIGNED(offset, GAMECARD_MEDIA_UNIT_SIZE) || \
|
if ((name && !*name) || offset < (GAMECARD_CERTIFICATE_OFFSET + sizeof(FsGameCardCertificate)) || !IS_ALIGNED(offset, GAMECARD_PAGE_SIZE) || \
|
||||||
(size && (!IS_ALIGNED(size, GAMECARD_MEDIA_UNIT_SIZE) || (offset + size) > g_gameCardStorageTotalSize)))
|
(size && (!IS_ALIGNED(size, GAMECARD_PAGE_SIZE) || (offset + size) > g_gameCardStorageTotalSize)))
|
||||||
{
|
{
|
||||||
LOG_MSG("Invalid parameters!");
|
LOG_MSG("Invalid parameters!");
|
||||||
goto end;
|
goto end;
|
||||||
|
@ -1039,7 +1039,7 @@ static HashFileSystemContext *gamecardInitializeHashFileSystemContext(const char
|
||||||
|
|
||||||
/* Calculate full Hash FS header size. */
|
/* Calculate full Hash FS header size. */
|
||||||
fs_ctx->header_size = (sizeof(HashFileSystemHeader) + (fs_header.entry_count * sizeof(HashFileSystemEntry)) + fs_header.name_table_size);
|
fs_ctx->header_size = (sizeof(HashFileSystemHeader) + (fs_header.entry_count * sizeof(HashFileSystemEntry)) + fs_header.name_table_size);
|
||||||
fs_ctx->header_size = ALIGN_UP(fs_ctx->header_size, GAMECARD_MEDIA_UNIT_SIZE);
|
fs_ctx->header_size = ALIGN_UP(fs_ctx->header_size, GAMECARD_PAGE_SIZE);
|
||||||
|
|
||||||
/* Allocate memory for the full Hash FS header. */
|
/* Allocate memory for the full Hash FS header. */
|
||||||
fs_ctx->header = calloc(fs_ctx->header_size, sizeof(u8));
|
fs_ctx->header = calloc(fs_ctx->header_size, sizeof(u8));
|
||||||
|
|
Loading…
Reference in a new issue