[makerom] Simplified CIA version logic.

This commit is contained in:
jakcron
2015-10-22 01:45:08 +08:00
parent d7d45411ba
commit 4c965b8c92
4 changed files with 41 additions and 29 deletions
+4 -22
View File
@@ -170,6 +170,7 @@ int GetSettingsFromUsrset(cia_settings *ciaset, user_settings *usrset)
ciaset->cert.caCrlVersion = 0; ciaset->cert.caCrlVersion = 0;
ciaset->cert.signerCrlVersion = 0; ciaset->cert.signerCrlVersion = 0;
ciaset->common.useCxiRemasterVersion = !usrset->cia.useFullTitleVer;
for(int i = 0; i < 3; i++){ for(int i = 0; i < 3; i++){
ciaset->common.titleVersion[i] = usrset->cia.titleVersion[i]; ciaset->common.titleVersion[i] = usrset->cia.titleVersion[i];
} }
@@ -239,6 +240,7 @@ int GetSettingsFromNcch0(cia_settings *ciaset, u32 ncch0_offset)
int result = VerifyNcch(ncch0, ciaset->keys, false, ciaset->verbose == false); int result = VerifyNcch(ncch0, ciaset->keys, false, ciaset->verbose == false);
if(result == UNABLE_TO_LOAD_NCCH_KEY){ if(result == UNABLE_TO_LOAD_NCCH_KEY){
ciaset->content.keyFound = false; ciaset->content.keyFound = false;
ciaset->common.useCxiRemasterVersion = false;
if(!ciaset->content.IsCfa){ if(!ciaset->content.IsCfa){
fprintf(stderr,"[CIA WARNING] CXI AES Key could not be loaded\n"); fprintf(stderr,"[CIA WARNING] CXI AES Key could not be loaded\n");
fprintf(stderr," Meta Region, SaveDataSize, Remaster Version cannot be obtained\n"); fprintf(stderr," Meta Region, SaveDataSize, Remaster Version cannot be obtained\n");
@@ -306,35 +308,15 @@ int GetTmdDataFromNcch(cia_settings *ciaset, u8 *ncch, ncch_info *ncch_ctx, u8 *
ciaset->tmd.savedataSize = 0; ciaset->tmd.savedataSize = 0;
// Process title version // Process title version
// If this is a CFA, the -major must be set, since CFAs don't have an exheader // If this is a CXI, and we have to pull version major from exheader...
if(ciaset->content.IsCfa){ if(!ciaset->content.IsCfa && ciaset->common.useCxiRemasterVersion){
if(ciaset->common.titleVersion[VER_MAJOR] == MAX_U16){ // '-major' wasn't set
fprintf(stderr,"[CIA ERROR] Invalid major version. Use \"-major\" option.\n");
result = CIA_BAD_VERSION;
goto cleanup;
}
}
// Otherwise this is a CXI, if it can be decrypted, -major cannot be set and must be read from exheader
else if(ciaset->content.keyFound){
if(ciaset->common.titleVersion[VER_MAJOR] != MAX_U16){ // '-major' was set
fprintf(stderr,"[CIA ERROR] Option \"-major\" cannot be applied for cxi.\n");
result = CIA_BAD_VERSION;
goto cleanup;
}
// Setting remaster ver // Setting remaster ver
ciaset->common.titleVersion[VER_MAJOR] = GetRemasterVersion_frm_exhdr(exhdr); ciaset->common.titleVersion[VER_MAJOR] = GetRemasterVersion_frm_exhdr(exhdr);
} }
// CXI which cannot be decrypted
else{
if(ciaset->common.titleVersion[VER_MAJOR] == MAX_U16) // '-major' wasn't set
ciaset->common.titleVersion[VER_MAJOR] = 0;
}
// Calculate u16 title version // Calculate u16 title version
ciaset->tmd.version = ciaset->tik.version = SetupVersion(ciaset->common.titleVersion[VER_MAJOR],ciaset->common.titleVersion[VER_MINOR],ciaset->common.titleVersion[VER_MICRO]); ciaset->tmd.version = ciaset->tik.version = SetupVersion(ciaset->common.titleVersion[VER_MAJOR],ciaset->common.titleVersion[VER_MINOR],ciaset->common.titleVersion[VER_MICRO]);
cleanup:
free(exhdr); free(exhdr);
return result; return result;
} }
+2 -2
View File
@@ -7,7 +7,6 @@ typedef enum
CIA_NO_NCCH0 = -1, CIA_NO_NCCH0 = -1,
CIA_INVALID_NCCH0 = -2, CIA_INVALID_NCCH0 = -2,
CIA_CONFILCTING_CONTENT_IDS = -3, CIA_CONFILCTING_CONTENT_IDS = -3,
CIA_BAD_VERSION = -4,
} cia_errors; } cia_errors;
typedef struct typedef struct
@@ -23,8 +22,9 @@ typedef struct
bool verbose; bool verbose;
struct{ struct{
bool useCxiRemasterVersion;
u64 titleId; u64 titleId;
u16 titleVersion[4]; u16 titleVersion[3];
u8 titleKey[16]; u8 titleKey[16];
} common; } common;
+33 -5
View File
@@ -118,7 +118,7 @@ void SetDefaults(user_settings *set)
set->cia.deviceId = 0; set->cia.deviceId = 0;
set->cia.eshopAccId = 0; set->cia.eshopAccId = 0;
set->cia.useDataTitleVer = false; set->cia.useDataTitleVer = false;
set->cia.titleVersion[VER_MAJOR] = MAX_U16; // invalid so changes can be detected set->cia.useFullTitleVer = false;
set->cia.randomTitleKey = false; set->cia.randomTitleKey = false;
set->common.keys.aes.currentCommonKey = MAX_U8 + 1; // invalid so changes can be detected set->common.keys.aes.currentCommonKey = MAX_U8 + 1; // invalid so changes can be detected
for (int i = 0; i < CIA_MAX_CONTENT; i++) for (int i = 0; i < CIA_MAX_CONTENT; i++)
@@ -450,13 +450,29 @@ int SetArgument(int argc, int i, char *argv[], user_settings *set)
} }
// Cia Options // Cia Options
else if (strcmp(argv[i], "-ver") == 0) {
if (ParamNum != 1) {
PrintArgReqParam(argv[i], 1);
return USR_ARG_REQ_PARAM;
}
set->cia.useFullTitleVer = true;
u32 ver = strtoul(argv[i + 1], NULL, 0);
if (ver > VER_MAX) {
fprintf(stderr, "[SETTING ERROR] Version: '%d' is too large, max: '%d'\n", ver, VER_MAX);
return USR_BAD_ARG;
}
set->cia.titleVersion[VER_MAJOR] = (ver >> 10) & VER_MAJOR_MAX;
set->cia.titleVersion[VER_MINOR] = (ver >> 4) & VER_MINOR_MAX;
set->cia.titleVersion[VER_MICRO] = ver & VER_MICRO_MAX;
return 2;
}
else if (strcmp(argv[i], "-major") == 0) { else if (strcmp(argv[i], "-major") == 0) {
if (ParamNum != 1) { if (ParamNum != 1) {
PrintArgReqParam(argv[i], 1); PrintArgReqParam(argv[i], 1);
return USR_ARG_REQ_PARAM; return USR_ARG_REQ_PARAM;
} }
set->cia.useNormTitleVer = true; set->cia.useNormTitleVer = true;
u32 ver = strtoul(argv[i + 1], NULL, 10); u32 ver = strtoul(argv[i + 1], NULL, 0);
if (ver > VER_MAJOR_MAX) { if (ver > VER_MAJOR_MAX) {
fprintf(stderr, "[SETTING ERROR] Major version: '%d' is too large, max: '%d'\n", ver, VER_MAJOR_MAX); fprintf(stderr, "[SETTING ERROR] Major version: '%d' is too large, max: '%d'\n", ver, VER_MAJOR_MAX);
return USR_BAD_ARG; return USR_BAD_ARG;
@@ -470,7 +486,7 @@ int SetArgument(int argc, int i, char *argv[], user_settings *set)
return USR_ARG_REQ_PARAM; return USR_ARG_REQ_PARAM;
} }
set->cia.useNormTitleVer = true; set->cia.useNormTitleVer = true;
u32 ver = strtoul(argv[i + 1], NULL, 10); u32 ver = strtoul(argv[i + 1], NULL, 0);
if (ver > VER_MINOR_MAX) { if (ver > VER_MINOR_MAX) {
fprintf(stderr, "[SETTING ERROR] Minor version: '%d' is too large, max: '%d'\n", ver, VER_MINOR_MAX); fprintf(stderr, "[SETTING ERROR] Minor version: '%d' is too large, max: '%d'\n", ver, VER_MINOR_MAX);
return USR_BAD_ARG; return USR_BAD_ARG;
@@ -483,7 +499,7 @@ int SetArgument(int argc, int i, char *argv[], user_settings *set)
PrintArgReqParam(argv[i], 1); PrintArgReqParam(argv[i], 1);
return USR_ARG_REQ_PARAM; return USR_ARG_REQ_PARAM;
} }
u32 ver = strtoul(argv[i + 1], NULL, 10); u32 ver = strtoul(argv[i + 1], NULL, 0);
if (ver > VER_MICRO_MAX) { if (ver > VER_MICRO_MAX) {
fprintf(stderr, "[SETTING ERROR] Micro version: '%d' is too large, max: '%d'\n", ver, VER_MICRO_MAX); fprintf(stderr, "[SETTING ERROR] Micro version: '%d' is too large, max: '%d'\n", ver, VER_MICRO_MAX);
return USR_BAD_ARG; return USR_BAD_ARG;
@@ -497,7 +513,7 @@ int SetArgument(int argc, int i, char *argv[], user_settings *set)
return USR_ARG_REQ_PARAM; return USR_ARG_REQ_PARAM;
} }
set->cia.useDataTitleVer = true; set->cia.useDataTitleVer = true;
u32 ver = strtoul(argv[i + 1], NULL, 10); u32 ver = strtoul(argv[i + 1], NULL, 0);
if (ver > VER_DVER_MAX) { if (ver > VER_DVER_MAX) {
fprintf(stderr, "[SETTING ERROR] Data version: '%d' is too large, max: '%d'\n", ver, VER_DVER_MAX); fprintf(stderr, "[SETTING ERROR] Data version: '%d' is too large, max: '%d'\n", ver, VER_DVER_MAX);
return USR_BAD_ARG; return USR_BAD_ARG;
@@ -732,6 +748,16 @@ int CheckArgumentCombination(user_settings *set)
return USR_BAD_ARG; return USR_BAD_ARG;
} }
if (set->cia.useDataTitleVer && set->cia.useFullTitleVer) {
fprintf(stderr, "[SETTING ERROR] Arguments \"-dver\" and \"-ver\" cannot be used together\n");
return USR_BAD_ARG;
}
if (set->cia.useNormTitleVer && set->cia.useFullTitleVer) {
fprintf(stderr, "[SETTING ERROR] Arguments \"-ver\" and \"-major\"/\"-minor\" cannot be used together\n");
return USR_BAD_ARG;
}
if (set->ncch.elfPath && set->ncch.codePath) { if (set->ncch.elfPath && set->ncch.codePath) {
fprintf(stderr, "[SETTING ERROR] Arguments \"-elf\" and \"-code\" cannot be used together\n"); fprintf(stderr, "[SETTING ERROR] Arguments \"-elf\" and \"-code\" cannot be used together\n");
return USR_BAD_ARG; return USR_BAD_ARG;
@@ -878,6 +904,7 @@ void DisplayHelp(char *app_name)
printf(" -romfs <file> RomFS binary\n"); printf(" -romfs <file> RomFS binary\n");
printf("CIA/CCI OPTIONS:\n"); printf("CIA/CCI OPTIONS:\n");
printf(" -content <file>:<index> Specify content files\n"); printf(" -content <file>:<index> Specify content files\n");
printf(" -ver <version> Title Version\n");
} }
void DisplayExtendedHelp(char *app_name) void DisplayExtendedHelp(char *app_name)
@@ -923,6 +950,7 @@ void DisplayExtendedHelp(char *app_name)
printf("CIA OPTIONS:\n"); printf("CIA OPTIONS:\n");
printf(" -content <file>:<index>:<id> Specify content files\n"); printf(" -content <file>:<index>:<id> Specify content files\n");
printf(" -ver <version> Title Version\n"); printf(" -ver <version> Title Version\n");
printf(" -major <version> Major version\n");
printf(" -minor <version> Minor version\n"); printf(" -minor <version> Minor version\n");
printf(" -micro <version> Micro version\n"); printf(" -micro <version> Micro version\n");
printf(" -dver <version> Data-title version\n"); printf(" -dver <version> Data-title version\n");
+2
View File
@@ -15,6 +15,7 @@ typedef enum
typedef enum typedef enum
{ {
VER_MAX = 65535,
VER_MAJOR_MAX = 63, VER_MAJOR_MAX = 63,
VER_MINOR_MAX = 63, VER_MINOR_MAX = 63,
VER_MICRO_MAX = 15, VER_MICRO_MAX = 15,
@@ -291,6 +292,7 @@ typedef struct
bool useNormTitleVer; bool useNormTitleVer;
bool useDataTitleVer; bool useDataTitleVer;
bool useFullTitleVer;
u16 titleVersion[3]; u16 titleVersion[3];
u32 deviceId; u32 deviceId;