[ctrtool] Fixed issue #7

This commit is contained in:
jakcron
2015-11-20 03:13:31 +08:00
parent 7e04a8249e
commit 127d1161e5
29 changed files with 241 additions and 253 deletions
+20 -21
View File
@@ -20,12 +20,12 @@ void cia_set_file(cia_context* ctx, FILE* file)
ctx->file = file;
}
void cia_set_offset(cia_context* ctx, u32 offset)
void cia_set_offset(cia_context* ctx, u64 offset)
{
ctx->offset = offset;
}
void cia_set_size(cia_context* ctx, u32 size)
void cia_set_size(cia_context* ctx, u64 size)
{
ctx->size = size;
}
@@ -39,8 +39,8 @@ void cia_set_usersettings(cia_context* ctx, settings* usersettings)
void cia_save(cia_context* ctx, u32 type, u32 flags)
{
u32 offset;
u32 size;
u64 offset;
u64 size;
u16 contentflags;
u8 docrypto;
filepath* path = 0;
@@ -133,14 +133,13 @@ void cia_save(cia_context* ctx, u32 type, u32 flags)
cia_save_blob(ctx, path->pathname, offset, size, 0);
}
void cia_save_blob(cia_context *ctx, char *out_path, u32 offset, u32 size, int do_cbc)
void cia_save_blob(cia_context *ctx, char *out_path, u64 offset, u64 size, int do_cbc)
{
FILE *fout = 0;
u8 buffer[16*1024];
fseek(ctx->file, ctx->offset + offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset + offset, SEEK_SET);
fout = fopen(out_path, "wb");
if (fout == NULL)
{
@@ -180,7 +179,7 @@ clean:
void cia_process(cia_context* ctx, u32 actions)
{
fseek(ctx->file, 0, SEEK_SET);
fseeko64(ctx->file, 0, SEEK_SET);
if (fread(&ctx->header, 1, sizeof(ctr_ciaheader), ctx->file) != sizeof(ctr_ciaheader))
{
@@ -192,14 +191,14 @@ void cia_process(cia_context* ctx, u32 actions)
ctx->sizecert = getle32(ctx->header.certsize);
ctx->sizetik = getle32(ctx->header.ticketsize);
ctx->sizetmd = getle32(ctx->header.tmdsize);
ctx->sizecontent = (u32)getle64(ctx->header.contentsize);
ctx->sizecontent = getle64(ctx->header.contentsize);
ctx->sizemeta = getle32(ctx->header.metasize);
ctx->offsetcerts = align(ctx->sizeheader, 64);
ctx->offsettik = align(ctx->offsetcerts + ctx->sizecert, 64);
ctx->offsettmd = align(ctx->offsettik + ctx->sizetik, 64);
ctx->offsetcontent = align(ctx->offsettmd + ctx->sizetmd, 64);
ctx->offsetmeta = align(ctx->offsetcontent + ctx->sizecontent, 64);
ctx->offsetmeta = align64(ctx->offsetcontent + ctx->sizecontent, 64);
if (actions & InfoFlag)
cia_print(ctx);
@@ -260,7 +259,7 @@ void cia_verify_contents(cia_context *ctx, u32 actions)
body = tmd_get_body(&ctx->tmd);
chunk = (ctr_tmd_contentchunk*)(body->contentinfo + (sizeof(ctr_tmd_contentinfo) * TMD_MAX_CONTENTS));
fseek(ctx->file, ctx->offset + ctx->offsetcontent, SEEK_SET);
fseeko64(ctx->file, ctx->offset + ctx->offsetcontent, SEEK_SET);
for(i = 0; i < getbe16(body->contentcount); i++)
{
content_size = getbe64(chunk->size) & 0xffffffff;
@@ -298,14 +297,14 @@ void cia_print(cia_context* ctx)
fprintf(stdout, "Header size 0x%08x\n", getle32(header->headersize));
fprintf(stdout, "Type %04x\n", getle16(header->type));
fprintf(stdout, "Version %04x\n", getle16(header->version));
fprintf(stdout, "Certificates offset: 0x%08x\n", ctx->offsetcerts);
fprintf(stdout, "Certificates size: 0x%04x\n", ctx->sizecert);
fprintf(stdout, "Ticket offset: 0x%08x\n", ctx->offsettik);
fprintf(stdout, "Ticket size 0x%04x\n", ctx->sizetik);
fprintf(stdout, "TMD offset: 0x%08x\n", ctx->offsettmd);
fprintf(stdout, "TMD size: 0x%04x\n", ctx->sizetmd);
fprintf(stdout, "Meta offset: 0x%04x\n", ctx->offsetmeta);
fprintf(stdout, "Meta size: 0x%04x\n", ctx->sizemeta);
fprintf(stdout, "Content offset: 0x%08x\n", ctx->offsetcontent);
fprintf(stdout, "Content size: 0x%016"PRIx64"\n", getle64(header->contentsize));
fprintf(stdout, "Certificates offset: 0x%"PRIx64"\n", ctx->offsetcerts);
fprintf(stdout, "Certificates size: 0x%x\n", ctx->sizecert);
fprintf(stdout, "Ticket offset: 0x%"PRIx64"n", ctx->offsettik);
fprintf(stdout, "Ticket size 0x%x\n", ctx->sizetik);
fprintf(stdout, "TMD offset: 0x%"PRIx64"\n", ctx->offsettmd);
fprintf(stdout, "TMD size: 0x%x\n", ctx->sizetmd);
fprintf(stdout, "Meta offset: 0x%"PRIx64"\n", ctx->offsetmeta);
fprintf(stdout, "Meta size: 0x%x\n", ctx->sizemeta);
fprintf(stdout, "Content offset: 0x%"PRIx64"\n", ctx->offsetcontent);
fprintf(stdout, "Content size: 0x%"PRIx64"\n", ctx->sizecontent);
}
+11 -11
View File
@@ -33,8 +33,8 @@ typedef struct
typedef struct
{
FILE* file;
u32 offset;
u32 size;
u64 offset;
u64 size;
u8 titlekey[16];
u8 iv[16];
ctr_ciaheader header;
@@ -48,25 +48,25 @@ typedef struct
u32 sizecert;
u32 sizetik;
u32 sizetmd;
u32 sizecontent;
u64 sizecontent;
u32 sizemeta;
u32 offsetcerts;
u32 offsettik;
u32 offsettmd;
u32 offsetcontent;
u32 offsetmeta;
u64 offsetcerts;
u64 offsettik;
u64 offsettmd;
u64 offsetcontent;
u64 offsetmeta;
} cia_context;
void cia_init(cia_context* ctx);
void cia_set_file(cia_context* ctx, FILE* file);
void cia_set_offset(cia_context* ctx, u32 offset);
void cia_set_size(cia_context* ctx, u32 size);
void cia_set_offset(cia_context* ctx, u64 offset);
void cia_set_size(cia_context* ctx, u64 size);
void cia_set_usersettings(cia_context* ctx, settings* usersettings);
void cia_print(cia_context* ctx);
void cia_save(cia_context* ctx, u32 type, u32 flags);
void cia_process(cia_context* ctx, u32 actions);
void cia_save_blob(cia_context *ctx, char *out_path, u32 offset, u32 size, int do_cbc);
void cia_save_blob(cia_context *ctx, char *out_path, u64 offset, u64 size, int do_cbc);
void cia_verify_contents(cia_context *ctx, u32 actions);
#endif // _CIA_H_
+14 -23
View File
@@ -13,33 +13,24 @@ void ctr_set_iv( ctr_aes_context* ctx,
}
void ctr_add_counter( ctr_aes_context* ctx,
u32 carry )
u32 block_num )
{
u32 counter[4];
u32 sum;
int i;
u32 i, j;
for (i = 0; i < block_num; i++) {
for (j = 0x10; j > 0; j--) {
// increment u8 by 1
ctx->ctr[j - 1]++;
for(i=0; i<4; i++)
counter[i] = (ctx->ctr[i*4+0]<<24) | (ctx->ctr[i*4+1]<<16) | (ctx->ctr[i*4+2]<<8) | (ctx->ctr[i*4+3]<<0);
// if it didn't overflow to 0, then we can exit now
if (ctx->ctr[j - 1])
break;
for(i=3; i>=0; i--)
{
sum = counter[i] + carry;
// if we reach here, the next u8 needs to be incremented
if (sum < counter[i])
carry = 1;
else
carry = 0;
counter[i] = sum;
}
for(i=0; i<4; i++)
{
ctx->ctr[i*4+0] = counter[i]>>24;
ctx->ctr[i*4+1] = counter[i]>>16;
ctx->ctr[i*4+2] = counter[i]>>8;
ctx->ctr[i*4+3] = counter[i]>>0;
// Loop to beginning back if needed
if (j == 1)
j = 0x10;
}
}
}
+1 -1
View File
@@ -56,7 +56,7 @@ void ctr_set_iv( ctr_aes_context* ctx,
u8 iv[16] );
void ctr_add_counter( ctr_aes_context* ctx,
u32 carry );
u32 block_num );
void ctr_set_counter( ctr_aes_context* ctx,
u8 ctr[16] );
+7 -7
View File
@@ -37,12 +37,12 @@ void cwav_set_file(cwav_context* ctx, FILE* file)
ctx->file = file;
}
void cwav_set_offset(cwav_context* ctx, u32 offset)
void cwav_set_offset(cwav_context* ctx, u64 offset)
{
ctx->offset = offset;
}
void cwav_set_size(cwav_context* ctx, u32 size)
void cwav_set_size(cwav_context* ctx, u64 size)
{
ctx->size = size;
}
@@ -57,12 +57,12 @@ void cwav_process(cwav_context* ctx, u32 actions)
u32 i;
u32 infoheaderoffset;
fseek(ctx->file, ctx->offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset, SEEK_SET);
fread(&ctx->header, 1, sizeof(cwav_header), ctx->file);
infoheaderoffset = getle32(ctx->header.infoblockref.offset);
fseek(ctx->file, ctx->offset + infoheaderoffset, SEEK_SET);
fseeko64(ctx->file, ctx->offset + infoheaderoffset, SEEK_SET);
fread(&ctx->infoheader, 1, sizeof(cwav_infoheader), ctx->file);
ctx->channelcount = getle32(ctx->infoheader.channelcount);
@@ -79,7 +79,7 @@ void cwav_process(cwav_context* ctx, u32 actions)
{
u32 channeloffset = infoheaderoffset + 0x1C + getle32(ctx->channel[i].inforef.offset);
fseek(ctx->file, ctx->offset + channeloffset, SEEK_SET);
fseeko64(ctx->file, ctx->offset + channeloffset, SEEK_SET);
fread(&ctx->channel[i].info, sizeof(cwav_channelinfo), 1, ctx->file);
if (ctx->infoheader.encoding == CWAV_ENCODING_DSPADPCM)
@@ -88,7 +88,7 @@ void cwav_process(cwav_context* ctx, u32 actions)
{
u32 codecoffset = channeloffset + getle32(ctx->channel[i].info.codecref.offset);
fseek(ctx->file, ctx->offset + codecoffset, SEEK_SET);
fseeko64(ctx->file, ctx->offset + codecoffset, SEEK_SET);
fread(&ctx->channel[i].infodspadpcm, sizeof(cwav_dspadpcminfo), 1, ctx->file);
}
}
@@ -98,7 +98,7 @@ void cwav_process(cwav_context* ctx, u32 actions)
{
u32 codecoffset = channeloffset + getle32(ctx->channel[i].info.codecref.offset);
fseek(ctx->file, ctx->offset + codecoffset, SEEK_SET);
fseeko64(ctx->file, ctx->offset + codecoffset, SEEK_SET);
fread(&ctx->channel[i].infoimaadpcm, sizeof(cwav_imaadpcminfo), 1, ctx->file);
}
}
+4 -4
View File
@@ -165,8 +165,8 @@ typedef struct
{
FILE* file;
settings* usersettings;
u32 offset;
u32 size;
u64 offset;
u64 size;
u32 channelcount;
cwav_header header;
cwav_infoheader infoheader;
@@ -175,8 +175,8 @@ typedef struct
void cwav_init(cwav_context* ctx);
void cwav_set_file(cwav_context* ctx, FILE* file);
void cwav_set_offset(cwav_context* ctx, u32 offset);
void cwav_set_size(cwav_context* ctx, u32 size);
void cwav_set_offset(cwav_context* ctx, u64 offset);
void cwav_set_size(cwav_context* ctx, u64 size);
void cwav_set_usersettings(cwav_context* ctx, settings* usersettings);
void cwav_process(cwav_context* ctx, u32 actions);
void cwav_dspadpcm_init(cwav_dspadpcmstate* state);
+5 -7
View File
@@ -18,12 +18,12 @@ void exefs_set_file(exefs_context* ctx, FILE* file)
ctx->file = file;
}
void exefs_set_offset(exefs_context* ctx, u32 offset)
void exefs_set_offset(exefs_context* ctx, u64 offset)
{
ctx->offset = offset;
}
void exefs_set_size(exefs_context* ctx, u32 size)
void exefs_set_size(exefs_context* ctx, u64 size)
{
ctx->size = size;
}
@@ -122,10 +122,8 @@ void exefs_save(exefs_context* ctx, u32 index, u32 flags)
fprintf(stderr, "Error, failed to create file %s\n", outfname);
goto clean;
}
fseek(ctx->file, ctx->offset + offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset + offset, SEEK_SET);
ctr_init_counter(&ctx->aes, ctx->key, ctx->counter);
ctr_add_counter(&ctx->aes, offset / 0x10);
@@ -209,7 +207,7 @@ clean:
void exefs_read_header(exefs_context* ctx, u32 flags)
{
fseek(ctx->file, ctx->offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset, SEEK_SET);
fread(&ctx->header, 1, sizeof(exefs_header), ctx->file);
ctr_init_counter(&ctx->aes, ctx->key, ctx->counter);
@@ -270,7 +268,7 @@ int exefs_verify(exefs_context* ctx, u32 index, u32 flags)
if (size == 0)
return 0;
fseek(ctx->file, ctx->offset + offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset + offset, SEEK_SET);
ctr_init_counter(&ctx->aes, ctx->key, ctx->counter);
ctr_add_counter(&ctx->aes, offset / 0x10);
+4 -4
View File
@@ -30,8 +30,8 @@ typedef struct
u8 partitionid[8];
u8 counter[16];
u8 key[16];
u32 offset;
u32 size;
u64 offset;
u64 size;
exefs_header header;
ctr_aes_context aes;
ctr_sha256_context sha;
@@ -42,8 +42,8 @@ typedef struct
void exefs_init(exefs_context* ctx);
void exefs_set_file(exefs_context* ctx, FILE* file);
void exefs_set_offset(exefs_context* ctx, u32 offset);
void exefs_set_size(exefs_context* ctx, u32 size);
void exefs_set_offset(exefs_context* ctx, u64 offset);
void exefs_set_size(exefs_context* ctx, u64 size);
void exefs_set_usersettings(exefs_context* ctx, settings* usersettings);
void exefs_set_partitionid(exefs_context* ctx, u8 partitionid[8]);
void exefs_set_counter(exefs_context* ctx, u8 counter[16]);
+3 -3
View File
@@ -17,12 +17,12 @@ void exheader_set_file(exheader_context* ctx, FILE* file)
ctx->file = file;
}
void exheader_set_offset(exheader_context* ctx, u32 offset)
void exheader_set_offset(exheader_context* ctx, u64 offset)
{
ctx->offset = offset;
}
void exheader_set_size(exheader_context* ctx, u32 size)
void exheader_set_size(exheader_context* ctx, u64 size)
{
ctx->size = size;
}
@@ -88,7 +88,7 @@ void exheader_read(exheader_context* ctx, u32 actions)
{
if (ctx->haveread == 0)
{
fseek(ctx->file, ctx->offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset, SEEK_SET);
fread(&ctx->header, 1, sizeof(exheader_header), ctx->file);
ctr_init_counter(&ctx->aes, ctx->key, ctx->counter);
+4 -4
View File
@@ -154,8 +154,8 @@ typedef struct
u8 hash[32];
u8 counter[16];
u8 key[16];
u32 offset;
u32 size;
u64 offset;
u64 size;
exheader_header header;
exheader_arm11systemlocalcaps_deserialised system_local_caps;
@@ -181,8 +181,8 @@ typedef struct
void exheader_init(exheader_context* ctx);
void exheader_set_file(exheader_context* ctx, FILE* file);
void exheader_set_offset(exheader_context* ctx, u32 offset);
void exheader_set_size(exheader_context* ctx, u32 size);
void exheader_set_offset(exheader_context* ctx, u64 offset);
void exheader_set_size(exheader_context* ctx, u64 size);
void exheader_set_partitionid(exheader_context* ctx, u8 partitionid[8]);
void exheader_set_counter(exheader_context* ctx, u8 counter[16]);
void exheader_set_programid(exheader_context* ctx, u8 programid[8]);
+4 -4
View File
@@ -16,7 +16,7 @@ void firm_set_file(firm_context* ctx, FILE* file)
ctx->file = file;
}
void firm_set_offset(firm_context* ctx, u32 offset)
void firm_set_offset(firm_context* ctx, u64 offset)
{
ctx->offset = offset;
}
@@ -66,7 +66,7 @@ void firm_save(firm_context* ctx, u32 index, u32 flags)
fseek(ctx->file, ctx->offset + offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset + offset, SEEK_SET);
fprintf(stdout, "Saving section %d to %s...\n", index, outpath.pathname);
while(size)
@@ -100,7 +100,7 @@ void firm_process(firm_context* ctx, u32 actions)
{
u32 i;
fseek(ctx->file, ctx->offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset, SEEK_SET);
fread(&ctx->header, 1, sizeof(firm_header), ctx->file);
if (getle32(ctx->header.magic) != MAGIC_FIRM)
@@ -154,7 +154,7 @@ int firm_verify(firm_context* ctx, u32 flags)
if (size == 0)
return 0;
fseek(ctx->file, ctx->offset + offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset + offset, SEEK_SET);
ctr_sha_256_init(&ctx->sha);
+2 -2
View File
@@ -35,7 +35,7 @@ typedef struct
{
FILE* file;
settings* usersettings;
u32 offset;
u64 offset;
u32 size;
firm_header header;
ctr_sha256_context sha;
@@ -45,7 +45,7 @@ typedef struct
void firm_init(firm_context* ctx);
void firm_set_file(firm_context* ctx, FILE* file);
void firm_set_offset(firm_context* ctx, u32 offset);
void firm_set_offset(firm_context* ctx, u64 offset);
void firm_set_size(firm_context* ctx, u32 size);
void firm_set_usersettings(firm_context* ctx, settings* usersettings);
void firm_process(firm_context* ctx, u32 actions);
+19 -22
View File
@@ -17,12 +17,12 @@ void ivfc_set_usersettings(ivfc_context* ctx, settings* usersettings)
ctx->usersettings = usersettings;
}
void ivfc_set_offset(ivfc_context* ctx, u32 offset)
void ivfc_set_offset(ivfc_context* ctx, u64 offset)
{
ctx->offset = offset;
}
void ivfc_set_size(ivfc_context* ctx, u32 size)
void ivfc_set_size(ivfc_context* ctx, u64 size)
{
ctx->size = size;
}
@@ -35,9 +35,7 @@ void ivfc_set_file(ivfc_context* ctx, FILE* file)
void ivfc_process(ivfc_context* ctx, u32 actions)
{
fseek(ctx->file, ctx->offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset, SEEK_SET);
fread(&ctx->header, 1, sizeof(ivfc_header), ctx->file);
if (getle32(ctx->header.magic) != MAGIC_IVFC)
@@ -55,22 +53,22 @@ void ivfc_process(ivfc_context* ctx, u32 actions)
ctx->level[2].hashblocksize = 1 << getle32(ctx->romfsheader.level3.blocksize);
ctx->level[1].hashblocksize = 1 << getle32(ctx->romfsheader.level2.blocksize);
ctx->level[0].hashblocksize = 1 << getle32(ctx->romfsheader.level1.blocksize);
ctx->level[0].hashoffset = 0x60;
ctx->bodyoffset = align64(ctx->level[0].hashoffset + getle32(ctx->romfsheader.masterhashsize), ctx->level[2].hashblocksize);
ctx->bodyoffset = align64(IVFC_HEADER_SIZE + getle32(ctx->romfsheader.masterhashsize), ctx->level[2].hashblocksize);
ctx->bodysize = getle64(ctx->romfsheader.level3.hashdatasize);
ctx->level[2].dataoffset = ctx->bodyoffset;
ctx->level[2].datasize = align64(ctx->bodysize, ctx->level[2].hashblocksize);
ctx->level[1].hashoffset = align64(ctx->bodyoffset + ctx->bodysize, ctx->level[2].hashblocksize);
ctx->level[2].hashoffset = ctx->level[1].hashoffset + getle64(ctx->romfsheader.level2.logicaloffset) - getle64(ctx->romfsheader.level1.logicaloffset);
ctx->level[0].dataoffset = ctx->level[2].dataoffset + ctx->level[2].datasize;
ctx->level[0].datasize = align64(getle64(ctx->romfsheader.level1.hashdatasize), ctx->level[0].hashblocksize);
ctx->level[1].dataoffset = ctx->level[2].hashoffset;
ctx->level[1].dataoffset = ctx->level[0].dataoffset + ctx->level[0].datasize;
ctx->level[1].datasize = align64(getle64(ctx->romfsheader.level2.hashdatasize), ctx->level[1].hashblocksize);
ctx->level[0].dataoffset = ctx->level[1].hashoffset;
ctx->level[0].datasize = align64(getle64(ctx->romfsheader.level1.hashdatasize), ctx->level[0].hashblocksize);
ctx->level[0].hashoffset = IVFC_HEADER_SIZE;
ctx->level[1].hashoffset = ctx->level[0].dataoffset;
ctx->level[2].hashoffset = ctx->level[1].dataoffset;
}
if (actions & VerifyFlag)
@@ -98,7 +96,7 @@ void ivfc_verify(ivfc_context* ctx, u32 flags)
ivfc_level* level = ctx->level + i;
blockcount = level->datasize / level->hashblocksize;
if (blockcount * level->hashblocksize != level->datasize)
if (level->datasize % level->hashblocksize != 0)
{
fprintf(stderr, "Error, IVFC block size mismatch\n");
return;
@@ -110,7 +108,6 @@ void ivfc_verify(ivfc_context* ctx, u32 flags)
{
u8 calchash[32];
u8 testhash[32];
ivfc_hash(ctx, level->dataoffset + level->hashblocksize * j, level->hashblocksize, calchash);
ivfc_read(ctx, level->hashoffset + 0x20 * j, 0x20, testhash);
@@ -121,15 +118,15 @@ void ivfc_verify(ivfc_context* ctx, u32 flags)
}
}
void ivfc_read(ivfc_context* ctx, u32 offset, u32 size, u8* buffer)
void ivfc_read(ivfc_context* ctx, u64 offset, u64 size, u8* buffer)
{
if ( (offset > ctx->size) || (offset+size > ctx->size) )
{
fprintf(stderr, "Error, IVFC offset out of range (offset=0x%08x, size=0x%08x)\n", offset, size);
fprintf(stderr, "Error, IVFC offset out of range (offset=0x%08"PRIx64", size=0x%08"PRIx64")\n", offset, size);
return;
}
fseek(ctx->file, ctx->offset + offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset + offset, SEEK_SET);
if (size != fread(buffer, 1, size, ctx->file))
{
fprintf(stderr, "Error, IVFC could not read file\n");
@@ -137,7 +134,7 @@ void ivfc_read(ivfc_context* ctx, u32 offset, u32 size, u8* buffer)
}
}
void ivfc_hash(ivfc_context* ctx, u32 offset, u32 size, u8* hash)
void ivfc_hash(ivfc_context* ctx, u64 offset, u64 size, u8* hash)
{
if (size > IVFC_MAX_BUFFERSIZE)
{
@@ -157,7 +154,7 @@ void ivfc_print(ivfc_context* ctx)
fprintf(stdout, "\nIVFC:\n");
fprintf(stdout, "Header: %c%c%c%c\n", header->magic[0], header->magic[1], header->magic[2], header->magic[3]);
fprintf(stdout, "Header: %.4s\n", header->magic);
fprintf(stdout, "Id: %08x\n", getle32(header->id));
for(i=0; i<ctx->levelcount; i++)
@@ -169,9 +166,9 @@ void ivfc_print(ivfc_context* ctx)
fprintf(stdout, "Level %d: \n", i);
else
fprintf(stdout, "Level %d (%s): \n", i, level->hashcheck == Good? "GOOD" : "FAIL");
fprintf(stdout, " Data offset: 0x%016"PRIx64"\n", ctx->offset + level->dataoffset);
fprintf(stdout, " Data size: 0x%016"PRIx64"\n", level->datasize);
fprintf(stdout, " Hash offset: 0x%016"PRIx64"\n", ctx->offset + level->hashoffset);
fprintf(stdout, " Data offset: 0x%08"PRIx64"\n", ctx->offset + level->dataoffset);
fprintf(stdout, " Data size: 0x%08"PRIx64"\n", level->datasize);
fprintf(stdout, " Hash offset: 0x%08"PRIx64"\n", ctx->offset + level->hashoffset);
fprintf(stdout, " Hash block size: 0x%08x\n", level->hashblocksize);
}
}
+7 -6
View File
@@ -4,6 +4,7 @@
#include "types.h"
#include "settings.h"
#define IVFC_HEADER_SIZE 0x60
#define IVFC_MAX_LEVEL 4
#define IVFC_MAX_BUFFERSIZE 0x4000
@@ -43,8 +44,8 @@ typedef struct
typedef struct
{
FILE* file;
u32 offset;
u32 size;
u64 offset;
u64 size;
settings* usersettings;
ivfc_header header;
@@ -59,14 +60,14 @@ typedef struct
void ivfc_init(ivfc_context* ctx);
void ivfc_process(ivfc_context* ctx, u32 actions);
void ivfc_set_offset(ivfc_context* ctx, u32 offset);
void ivfc_set_size(ivfc_context* ctx, u32 size);
void ivfc_set_offset(ivfc_context* ctx, u64 offset);
void ivfc_set_size(ivfc_context* ctx, u64 size);
void ivfc_set_file(ivfc_context* ctx, FILE* file);
void ivfc_set_usersettings(ivfc_context* ctx, settings* usersettings);
void ivfc_verify(ivfc_context* ctx, u32 flags);
void ivfc_print(ivfc_context* ctx);
void ivfc_read(ivfc_context* ctx, u32 offset, u32 size, u8* buffer);
void ivfc_hash(ivfc_context* ctx, u32 offset, u32 size, u8* hash);
void ivfc_read(ivfc_context* ctx, u64 offset, u64 size, u8* buffer);
void ivfc_hash(ivfc_context* ctx, u64 offset, u64 size, u8* hash);
#endif // __IVFC_H__
+1 -1
View File
@@ -40,7 +40,7 @@ void lzss_process(lzss_context* ctx, u32 actions)
FILE* fout = 0;
fseek(ctx->file, ctx->offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset, SEEK_SET);
if (actions & ExtractFlag)
+4 -10
View File
@@ -31,7 +31,7 @@ typedef struct
int actions;
u32 filetype;
FILE* infile;
u32 infilesize;
u64 infilesize;
settings usersettings;
} toolcontext;
@@ -259,6 +259,7 @@ int main(int argc, char* argv[])
if (ctx.actions & ShowKeysFlag)
keyset_dump(&ctx.usersettings.keys);
ctx.infilesize = _fsize(infname);
ctx.infile = fopen(infname, "rb");
if (ctx.infile == 0)
@@ -267,16 +268,9 @@ int main(int argc, char* argv[])
return -1;
}
fseek(ctx.infile, 0, SEEK_END);
ctx.infilesize = ftell(ctx.infile);
fseek(ctx.infile, 0, SEEK_SET);
if (ctx.filetype == FILETYPE_UNKNOWN)
{
fseek(ctx.infile, 0x100, SEEK_SET);
fseeko64(ctx.infile, 0x100, SEEK_SET);
fread(&magic, 1, 4, ctx.infile);
switch(getle32(magic))
@@ -296,7 +290,7 @@ int main(int argc, char* argv[])
if (ctx.filetype == FILETYPE_UNKNOWN)
{
fseek(ctx.infile, 0, SEEK_SET);
fseeko64(ctx.infile, 0, SEEK_SET);
fread(magic, 1, 4, ctx.infile);
switch(getle32(magic))
+49 -56
View File
@@ -30,12 +30,12 @@ void ncch_set_usersettings(ncch_context* ctx, settings* usersettings)
ctx->usersettings = usersettings;
}
void ncch_set_offset(ncch_context* ctx, u32 offset)
void ncch_set_offset(ncch_context* ctx, u64 offset)
{
ctx->offset = offset;
}
void ncch_set_size(ncch_context* ctx, u32 size)
void ncch_set_size(ncch_context* ctx, u64 size)
{
ctx->size = size;
}
@@ -51,7 +51,7 @@ void ncch_get_counter(ncch_context* ctx, u8 counter[16], u8 type)
u32 mediaunitsize = ncch_get_mediaunit_size(ctx);
u8* partitionid = ctx->header.partitionid;
u32 i;
u32 x = 0;
u64 x = 0;
memset(counter, 0, 16);
@@ -81,8 +81,8 @@ void ncch_get_counter(ncch_context* ctx, u8 counter[16], u8 type)
int ncch_extract_prepare(ncch_context* ctx, u32 type, u32 flags)
{
u32 offset = 0;
u32 size = 0;
u64 offset = 0;
u64 size = 0;
u8 counter[16];
@@ -126,7 +126,7 @@ int ncch_extract_prepare(ncch_context* ctx, u32 type, u32 flags)
ctx->extractsize = size;
ctx->extractflags = flags;
fseek(ctx->file, offset, SEEK_SET);
fseeko64(ctx->file, offset, SEEK_SET);
ncch_get_counter(ctx, counter, type);
ctr_init_counter(&ctx->aes, ctx->key, counter);
@@ -138,25 +138,25 @@ clean:
int ncch_extract_buffer(ncch_context* ctx, u8* buffer, u32 buffersize, u32* outsize, u8 nocrypto)
{
u32 max = buffersize;
u32 read_len = buffersize;
if (max > ctx->extractsize)
max = ctx->extractsize;
if (read_len > ctx->extractsize)
read_len = ctx->extractsize;
*outsize = max;
*outsize = read_len;
if (ctx->extractsize)
{
if (max != fread(buffer, 1, max, ctx->file))
if (read_len != fread(buffer, 1, read_len, ctx->file))
{
fprintf(stdout, "Error reading input file\n");
goto clean;
}
if (ctx->encrypted && !nocrypto)
ctr_crypt_counter(&ctx->aes, buffer, buffer, max);
ctr_crypt_counter(&ctx->aes, buffer, buffer, read_len);
ctx->extractsize -= max;
ctx->extractsize -= read_len;
}
return 1;
@@ -203,15 +203,15 @@ void ncch_save(ncch_context* ctx, u32 type, u32 flags)
while(1)
{
u32 max;
u32 read_len;
if (0 == ncch_extract_buffer(ctx, buffer, sizeof(buffer), &max, type == NCCHTYPE_LOGO))
if (0 == ncch_extract_buffer(ctx, buffer, sizeof(buffer), &read_len, type == NCCHTYPE_LOGO))
goto clean;
if (max == 0)
if (read_len == 0)
break;
if (max != fwrite(buffer, 1, max, fout))
if (read_len != fwrite(buffer, 1, read_len, fout))
{
fprintf(stdout, "Error writing output file\n");
goto clean;
@@ -307,7 +307,7 @@ void ncch_process(ncch_context* ctx, u32 actions)
int result = 1;
fseek(ctx->file, ctx->offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset, SEEK_SET);
fread(&ctx->header, 1, 0x200, ctx->file);
if (getle32(ctx->header.magic) != MAGIC_NCCH)
@@ -385,53 +385,47 @@ int ncch_signature_verify(ncch_context* ctx, rsakey2048* key)
}
u32 ncch_get_exefs_offset(ncch_context* ctx)
u64 ncch_get_exefs_offset(ncch_context* ctx)
{
u32 mediaunitsize = ncch_get_mediaunit_size(ctx);
return ctx->offset + getle32(ctx->header.exefsoffset) * mediaunitsize;
return ctx->offset + getle32(ctx->header.exefsoffset) * ncch_get_mediaunit_size(ctx);
}
u32 ncch_get_exefs_size(ncch_context* ctx)
u64 ncch_get_exefs_size(ncch_context* ctx)
{
u32 mediaunitsize = ncch_get_mediaunit_size(ctx);
return getle32(ctx->header.exefssize) * mediaunitsize;
return getle32(ctx->header.exefssize) * ncch_get_mediaunit_size(ctx);
}
u32 ncch_get_romfs_offset(ncch_context* ctx)
u64 ncch_get_romfs_offset(ncch_context* ctx)
{
u32 mediaunitsize = ncch_get_mediaunit_size(ctx);
return ctx->offset + getle32(ctx->header.romfsoffset) * mediaunitsize;
return ctx->offset + getle32(ctx->header.romfsoffset) * ncch_get_mediaunit_size(ctx);
}
u32 ncch_get_romfs_size(ncch_context* ctx)
u64 ncch_get_romfs_size(ncch_context* ctx)
{
u32 mediaunitsize = ncch_get_mediaunit_size(ctx);
return getle32(ctx->header.romfssize) * mediaunitsize;
return getle32(ctx->header.romfssize) * ncch_get_mediaunit_size(ctx);
}
u32 ncch_get_exheader_offset(ncch_context* ctx)
u64 ncch_get_exheader_offset(ncch_context* ctx)
{
return ctx->offset + 0x200;
}
u32 ncch_get_exheader_size(ncch_context* ctx)
u64 ncch_get_exheader_size(ncch_context* ctx)
{
return getle32(ctx->header.extendedheadersize);
}
u32 ncch_get_logo_offset(ncch_context* ctx)
u64 ncch_get_logo_offset(ncch_context* ctx)
{
u32 mediaunitsize = ncch_get_mediaunit_size(ctx);
return ctx->offset + getle32(ctx->header.logooffset) * mediaunitsize;
return ctx->offset + getle32(ctx->header.logooffset) * ncch_get_mediaunit_size(ctx);
}
u32 ncch_get_logo_size(ncch_context* ctx)
u64 ncch_get_logo_size(ncch_context* ctx)
{
u32 mediaunitsize = ncch_get_mediaunit_size(ctx);
return getle32(ctx->header.logosize) * mediaunitsize;
return getle32(ctx->header.logosize) * ncch_get_mediaunit_size(ctx);
}
u32 ncch_get_mediaunit_size(ncch_context* ctx)
u64 ncch_get_mediaunit_size(ncch_context* ctx)
{
unsigned int mediaunitsize = settings_get_mediaunit_size(ctx->usersettings);
@@ -473,7 +467,7 @@ void ncch_determine_key(ncch_context* ctx, u32 actions)
// Firstly, check if the NCCH is already decrypted, by reading the programid in the exheader
// Otherwise, use determination rules
fseek(ctx->file, ncch_get_exheader_offset(ctx), SEEK_SET);
fseeko64(ctx->file, ncch_get_exheader_offset(ctx), SEEK_SET);
memset(&exheader, 0, sizeof(exheader));
fread(&exheader, 1, sizeof(exheader), ctx->file);
@@ -560,9 +554,8 @@ static const char* contentplatformtostring(unsigned char platform)
void ncch_print(ncch_context* ctx)
{
ctr_ncchheader *header = &ctx->header;
u32 offset = ctx->offset;
u32 mediaunitsize = ncch_get_mediaunit_size(ctx);
u64 offset = ctx->offset;
u64 mediaunitsize = ncch_get_mediaunit_size(ctx);
fprintf(stdout, "\nNCCH:\n");
@@ -573,10 +566,10 @@ void ncch_print(ncch_context* ctx)
memdump(stdout, "Signature (GOOD): ", header->signature, 0x100);
else
memdump(stdout, "Signature (FAIL): ", header->signature, 0x100);
fprintf(stdout, "Content size: 0x%08x\n", getle32(header->contentsize)*mediaunitsize);
fprintf(stdout, "Content size: 0x%08"PRIx64"\n", getle32(header->contentsize)*mediaunitsize);
fprintf(stdout, "Partition id: %016"PRIx64"\n", getle64(header->partitionid));
fprintf(stdout, "Maker code: %.2s\n", header->makercode);
fprintf(stdout, "Version: %04x\n", getle16(header->version));
fprintf(stdout, "Version: %d\n", getle16(header->version));
fprintf(stdout, "Title seed check: %08x\n", getle32(header->seedcheck));
fprintf(stdout, "Program id: %016"PRIx64"\n", getle64(header->programid));
if(ctx->logohashcheck == Unchecked)
@@ -594,7 +587,7 @@ void ncch_print(ncch_context* ctx)
else
memdump(stdout, "Exheader hash (FAIL): ", header->extendedheaderhash, 0x20);
fprintf(stdout, "Flags: %016"PRIx64"\n", getle64(header->flags));
fprintf(stdout, " > Mediaunit size: 0x%x\n", mediaunitsize);
fprintf(stdout, " > Mediaunit size: 0x%x\n", (u32)mediaunitsize);
if (header->flags[7] & 4)
fprintf(stdout, " > Crypto key: None\n");
else if (header->flags[7] & 1)
@@ -608,16 +601,16 @@ void ncch_print(ncch_context* ctx)
fprintf(stdout, " > No RomFS mount\n");
fprintf(stdout, "Plain region offset: 0x%08x\n", getle32(header->plainregionsize)? offset+getle32(header->plainregionoffset)*mediaunitsize : 0);
fprintf(stdout, "Plain region size: 0x%08x\n", getle32(header->plainregionsize)*mediaunitsize);
fprintf(stdout, "Logo offset: 0x%08x\n", getle32(header->logosize)? offset+getle32(header->logooffset)*mediaunitsize : 0);
fprintf(stdout, "Logo size: 0x%08x\n", getle32(header->logosize)*mediaunitsize);
fprintf(stdout, "ExeFS offset: 0x%08x\n", getle32(header->exefssize)? offset+getle32(header->exefsoffset)*mediaunitsize : 0);
fprintf(stdout, "ExeFS size: 0x%08x\n", getle32(header->exefssize)*mediaunitsize);
fprintf(stdout, "ExeFS hash region size: 0x%08x\n", getle32(header->exefshashregionsize)*mediaunitsize);
fprintf(stdout, "RomFS offset: 0x%08x\n", getle32(header->romfssize)? offset+getle32(header->romfsoffset)*mediaunitsize : 0);
fprintf(stdout, "RomFS size: 0x%08x\n", getle32(header->romfssize)*mediaunitsize);
fprintf(stdout, "RomFS hash region size: 0x%08x\n", getle32(header->romfshashregionsize)*mediaunitsize);
fprintf(stdout, "Plain region offset: 0x%08"PRIx64"\n", getle32(header->plainregionsize)? offset+getle32(header->plainregionoffset)*mediaunitsize : 0);
fprintf(stdout, "Plain region size: 0x%08"PRIx64"\n", getle32(header->plainregionsize)*mediaunitsize);
fprintf(stdout, "Logo offset: 0x%08"PRIx64"\n", getle32(header->logosize)? offset+getle32(header->logooffset)*mediaunitsize : 0);
fprintf(stdout, "Logo size: 0x%08"PRIx64"\n", getle32(header->logosize)*mediaunitsize);
fprintf(stdout, "ExeFS offset: 0x%08"PRIx64"\n", getle32(header->exefssize)? offset+getle32(header->exefsoffset)*mediaunitsize : 0);
fprintf(stdout, "ExeFS size: 0x%08"PRIx64"\n", getle32(header->exefssize)*mediaunitsize);
fprintf(stdout, "ExeFS hash region size: 0x%08"PRIx64"\n", getle32(header->exefshashregionsize)*mediaunitsize);
fprintf(stdout, "RomFS offset: 0x%08"PRIx64"\n", getle32(header->romfssize)? offset+getle32(header->romfsoffset)*mediaunitsize : 0);
fprintf(stdout, "RomFS size: 0x%08"PRIx64"\n", getle32(header->romfssize)*mediaunitsize);
fprintf(stdout, "RomFS hash region size: 0x%08"PRIx64"\n", getle32(header->romfshashregionsize)*mediaunitsize);
if (ctx->exefshashcheck == Unchecked)
memdump(stdout, "ExeFS Hash: ", header->exefssuperblockhash, 0x20);
else if (ctx->exefshashcheck == Good)
+14 -14
View File
@@ -57,8 +57,8 @@ typedef struct
FILE* file;
u8 key[16];
u32 encrypted;
u32 offset;
u32 size;
u64 offset;
u64 size;
settings* usersettings;
ctr_ncchheader header;
ctr_aes_context aes;
@@ -69,31 +69,31 @@ typedef struct
int exheaderhashcheck;
int logohashcheck;
int headersigcheck;
u32 extractsize;
u64 extractsize;
u32 extractflags;
} ncch_context;
void ncch_init(ncch_context* ctx);
void ncch_process(ncch_context* ctx, u32 actions);
void ncch_set_offset(ncch_context* ctx, u32 offset);
void ncch_set_size(ncch_context* ctx, u32 size);
void ncch_set_offset(ncch_context* ctx, u64 offset);
void ncch_set_size(ncch_context* ctx, u64 size);
void ncch_set_file(ncch_context* ctx, FILE* file);
void ncch_set_usersettings(ncch_context* ctx, settings* usersettings);
u32 ncch_get_exefs_offset(ncch_context* ctx);
u32 ncch_get_exefs_size(ncch_context* ctx);
u32 ncch_get_romfs_offset(ncch_context* ctx);
u32 ncch_get_romfs_size(ncch_context* ctx);
u32 ncch_get_exheader_offset(ncch_context* ctx);
u32 ncch_get_exheader_size(ncch_context* ctx);
u32 ncch_get_logo_offset(ncch_context* ctx);
u32 ncch_get_logo_size(ncch_context* ctx);
u64 ncch_get_exefs_offset(ncch_context* ctx);
u64 ncch_get_exefs_size(ncch_context* ctx);
u64 ncch_get_romfs_offset(ncch_context* ctx);
u64 ncch_get_romfs_size(ncch_context* ctx);
u64 ncch_get_exheader_offset(ncch_context* ctx);
u64 ncch_get_exheader_size(ncch_context* ctx);
u64 ncch_get_logo_offset(ncch_context* ctx);
u64 ncch_get_logo_size(ncch_context* ctx);
void ncch_print(ncch_context* ctx);
int ncch_signature_verify(ncch_context* ctx, rsakey2048* key);
void ncch_verify(ncch_context* ctx, u32 flags);
void ncch_save(ncch_context* ctx, u32 type, u32 flags);
int ncch_extract_prepare(ncch_context* ctx, u32 type, u32 flags);
int ncch_extract_buffer(ncch_context* ctx, u8* buffer, u32 buffersize, u32* outsize, u8 nocrypto);
u32 ncch_get_mediaunit_size(ncch_context* ctx);
u64 ncch_get_mediaunit_size(ncch_context* ctx);
void ncch_get_counter(ncch_context* ctx, u8 counter[16], u8 type);
void ncch_determine_key(ncch_context* ctx, u32 actions);
#endif // _NCCH_H_
+4 -4
View File
@@ -13,7 +13,7 @@ void ncsd_init(ncsd_context* ctx)
memset(ctx, 0, sizeof(ncsd_context));
}
void ncsd_set_offset(ncsd_context* ctx, u32 offset)
void ncsd_set_offset(ncsd_context* ctx, u64 offset)
{
ctx->offset = offset;
}
@@ -23,7 +23,7 @@ void ncsd_set_file(ncsd_context* ctx, FILE* file)
ctx->file = file;
}
void ncsd_set_size(ncsd_context* ctx, u32 size)
void ncsd_set_size(ncsd_context* ctx, u64 size)
{
ctx->size = size;
}
@@ -48,7 +48,7 @@ int ncsd_signature_verify(const void* blob, rsakey2048* key)
return ctr_rsa_verify_hash(sig, hash, key);
}
unsigned int ncsd_get_mediaunit_size(ncsd_context* ctx)
u64 ncsd_get_mediaunit_size(ncsd_context* ctx)
{
unsigned int mediaunitsize = settings_get_mediaunit_size(ctx->usersettings);
@@ -60,7 +60,7 @@ unsigned int ncsd_get_mediaunit_size(ncsd_context* ctx)
void ncsd_process(ncsd_context* ctx, u32 actions)
{
fseek(ctx->file, ctx->offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset, SEEK_SET);
fread(&ctx->header, 1, 0x200, ctx->file);
if (getle32(ctx->header.magic) != MAGIC_NCSD)
+5 -5
View File
@@ -33,8 +33,8 @@ typedef struct
typedef struct
{
FILE* file;
u32 offset;
u32 size;
u64 offset;
u64 size;
u32 ncch_index;
ctr_ncsdheader header;
settings* usersettings;
@@ -44,14 +44,14 @@ typedef struct
void ncsd_init(ncsd_context* ctx);
void ncsd_set_offset(ncsd_context* ctx, u32 offset);
void ncsd_set_size(ncsd_context* ctx, u32 size);
void ncsd_set_offset(ncsd_context* ctx, u64 offset);
void ncsd_set_size(ncsd_context* ctx, u64 size);
void ncsd_set_ncch_index(ncsd_context* ctx, u32 ncch_index);
void ncsd_set_file(ncsd_context* ctx, FILE* file);
void ncsd_set_usersettings(ncsd_context* ctx, settings* usersettings);
int ncsd_signature_verify(const void* blob, rsakey2048* key);
void ncsd_process(ncsd_context* ctx, u32 actions);
void ncsd_print(ncsd_context* ctx);
unsigned int ncsd_get_mediaunit_size(ncsd_context* ctx);
u64 ncsd_get_mediaunit_size(ncsd_context* ctx);
#endif // _NCSD_H_
+9 -14
View File
@@ -18,12 +18,12 @@ void romfs_set_file(romfs_context* ctx, FILE* file)
ctx->file = file;
}
void romfs_set_offset(romfs_context* ctx, u32 offset)
void romfs_set_offset(romfs_context* ctx, u64 offset)
{
ctx->offset = offset;
}
void romfs_set_size(romfs_context* ctx, u32 size)
void romfs_set_size(romfs_context* ctx, u64 size)
{
ctx->size = size;
}
@@ -49,7 +49,7 @@ void romfs_process(romfs_context* ctx, u32 actions)
ivfc_set_usersettings(&ctx->ivfc, ctx->usersettings);
ivfc_process(&ctx->ivfc, actions);
fseek(ctx->file, ctx->offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset, SEEK_SET);
fread(&ctx->header, 1, sizeof(romfs_header), ctx->file);
if (getle32(ctx->header.magic) != MAGIC_IVFC)
@@ -60,7 +60,7 @@ void romfs_process(romfs_context* ctx, u32 actions)
ctx->infoblockoffset = ctx->offset + 0x1000;
fseek(ctx->file, ctx->infoblockoffset, SEEK_SET);
fseeko64(ctx->file, ctx->infoblockoffset, SEEK_SET);
fread(&ctx->infoheader, 1, sizeof(romfs_infoheader), ctx->file);
if (getle32(ctx->infoheader.headersize) != sizeof(romfs_infoheader))
@@ -83,13 +83,13 @@ void romfs_process(romfs_context* ctx, u32 actions)
if (ctx->dirblock)
{
fseek(ctx->file, dirblockoffset, SEEK_SET);
fseeko64(ctx->file, dirblockoffset, SEEK_SET);
fread(ctx->dirblock, 1, dirblocksize, ctx->file);
}
if (ctx->fileblock)
{
fseek(ctx->file, fileblockoffset, SEEK_SET);
fseeko64(ctx->file, fileblockoffset, SEEK_SET);
fread(ctx->fileblock, 1, fileblocksize, ctx->file);
}
@@ -295,13 +295,8 @@ void romfs_extract_datafile(romfs_context* ctx, u64 offset, u64 size, filepath*
goto clean;
offset += ctx->datablockoffset;
if ( (offset >> 32) )
{
fprintf(stderr, "Error, support for 64-bit offset not yet implemented.\n");
goto clean;
}
fseek(ctx->file, offset, SEEK_SET);
fseeko64(ctx->file, offset, SEEK_SET);
outfile = fopen(path->pathname, "wb");
if (outfile == 0)
{
@@ -344,9 +339,9 @@ void romfs_print(romfs_context* ctx)
fprintf(stdout, "Header size: 0x%08X\n", getle32(ctx->infoheader.headersize));
for(i=0; i<4; i++)
{
fprintf(stdout, "Section %d offset: 0x%08X\n", i, ctx->offset + 0x1000 + getle32(ctx->infoheader.section[i].offset));
fprintf(stdout, "Section %d offset: 0x%08"PRIX64"\n", i, ctx->offset + 0x1000 + getle32(ctx->infoheader.section[i].offset));
fprintf(stdout, "Section %d size: 0x%08X\n", i, getle32(ctx->infoheader.section[i].size));
}
fprintf(stdout, "Data offset: 0x%08X\n", ctx->offset + 0x1000 + getle32(ctx->infoheader.dataoffset));
fprintf(stdout, "Data offset: 0x%08"PRIX64"\n", ctx->offset + 0x1000 + getle32(ctx->infoheader.dataoffset));
}
+4 -4
View File
@@ -56,8 +56,8 @@ typedef struct
{
FILE* file;
settings* usersettings;
u32 offset;
u32 size;
u64 offset;
u64 size;
romfs_header header;
romfs_infoheader infoheader;
u8* dirblock;
@@ -73,8 +73,8 @@ typedef struct
void romfs_init(romfs_context* ctx);
void romfs_set_file(romfs_context* ctx, FILE* file);
void romfs_set_offset(romfs_context* ctx, u32 offset);
void romfs_set_size(romfs_context* ctx, u32 size);
void romfs_set_offset(romfs_context* ctx, u64 offset);
void romfs_set_size(romfs_context* ctx, u64 size);
void romfs_set_usersettings(romfs_context* ctx, settings* usersettings);
void romfs_test(romfs_context* ctx);
int romfs_dirblock_read(romfs_context* ctx, u32 diroffset, u32 dirsize, void* buffer);
+2 -2
View File
@@ -16,7 +16,7 @@ void tik_set_file(tik_context* ctx, FILE* file)
ctx->file = file;
}
void tik_set_offset(tik_context* ctx, u32 offset)
void tik_set_offset(tik_context* ctx, u64 offset)
{
ctx->offset = offset;
}
@@ -76,7 +76,7 @@ void tik_process(tik_context* ctx, u32 actions)
goto clean;
}
fseek(ctx->file, ctx->offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset, SEEK_SET);
fread((u8*)&ctx->tik, 1, sizeof(eticket), ctx->file);
tik_decrypt_titlekey(ctx, ctx->titlekey);
+2 -2
View File
@@ -41,7 +41,7 @@ typedef struct
typedef struct
{
FILE* file;
u32 offset;
u64 offset;
u32 size;
u8 titlekey[16];
eticket tik;
@@ -51,7 +51,7 @@ typedef struct
void tik_init(tik_context* ctx);
void tik_set_file(tik_context* ctx, FILE* file);
void tik_set_offset(tik_context* ctx, u32 offset);
void tik_set_offset(tik_context* ctx, u64 offset);
void tik_set_size(tik_context* ctx, u32 size);
void tik_set_usersettings(tik_context* ctx, settings* usersettings);
void tik_get_decrypted_titlekey(tik_context* ctx, u8 decryptedkey[0x10]);
+2 -2
View File
@@ -17,7 +17,7 @@ void tmd_set_file(tmd_context* ctx, FILE* file)
ctx->file = file;
}
void tmd_set_offset(tmd_context* ctx, u32 offset)
void tmd_set_offset(tmd_context* ctx, u64 offset)
{
ctx->offset = offset;
}
@@ -39,7 +39,7 @@ void tmd_process(tmd_context* ctx, u32 actions)
if (ctx->buffer)
{
fseek(ctx->file, ctx->offset, SEEK_SET);
fseeko64(ctx->file, ctx->offset, SEEK_SET);
fread(ctx->buffer, 1, ctx->size, ctx->file);
if (actions & InfoFlag)
+2 -2
View File
@@ -74,7 +74,7 @@ typedef struct
typedef struct
{
FILE* file;
u32 offset;
u64 offset;
u32 size;
u8* buffer;
u8 content_hash_stat[64];
@@ -89,7 +89,7 @@ extern "C" {
void tmd_init(tmd_context* ctx);
void tmd_set_file(tmd_context* ctx, FILE* file);
void tmd_set_offset(tmd_context* ctx, u32 offset);
void tmd_set_offset(tmd_context* ctx, u64 offset);
void tmd_set_size(tmd_context* ctx, u32 size);
void tmd_set_usersettings(tmd_context* ctx, settings* usersettings);
void tmd_print(tmd_context* ctx);
+9 -8
View File
@@ -2,16 +2,17 @@
#define __TYPES_H__
#include <stdint.h>
#include <inttypes.h>
typedef unsigned char u8;
typedef unsigned short u16;
typedef unsigned int u32;
typedef unsigned long long u64;
typedef uint8_t u8;
typedef uint16_t u16;
typedef uint32_t u32;
typedef uint64_t u64;
typedef signed char s8;
typedef signed short s16;
typedef signed int s32;
typedef signed long long s64;
typedef int8_t s8;
typedef int16_t s16;
typedef int32_t s32;
typedef int64_t s64;
enum flags
{
+23 -10
View File
@@ -1,13 +1,13 @@
#include <stdio.h>
#include <string.h>
#include <sys/stat.h>
#include <sys/types.h>
#include "utils.h"
#ifdef _WIN32
#include <direct.h>
#else
#include <sys/stat.h>
#include <sys/types.h>
#include <wchar.h>
#endif
@@ -20,7 +20,7 @@ u32 align(u32 offset, u32 alignment)
u64 align64(u64 offset, u32 alignment)
{
u64 mask = ~(alignment-1);
u64 mask = ~(u64)(alignment-1);
return (offset + (alignment-1)) & mask;
}
@@ -91,19 +91,15 @@ void putle32(u8* p, u32 n)
void readkeyfile(u8* key, const char* keyfname)
{
u32 keysize = _fsize(keyfname);
FILE* f = fopen(keyfname, "rb");
u32 keysize = 0;
if (0 == f)
{
fprintf(stdout, "Error opening key file\n");
goto clean;
}
fseek(f, 0, SEEK_END);
keysize = ftell(f);
fseek(f, 0, SEEK_SET);
if (keysize != 16)
{
fprintf(stdout, "Error key size mismatch, got %d, expected %d\n", keysize, 16);
@@ -190,3 +186,20 @@ int makedir(const char* dir)
return mkdir(dir, 0777);
#endif
}
u64 _fsize(const char *filename)
{
#ifdef _WIN32
struct _stat64 st;
if (_stat64(filename, &st) != 0)
return 0;
else
return st.st_size;
#else
struct stat st;
if (stat(filename, &st) != 0)
return 0;
else
return st.st_size;
#endif
}
+6
View File
@@ -35,6 +35,12 @@ int key_load(char *name, u8 *out_buf);
int makedir(const char* dir);
u64 _fsize(const char *filename);
#ifndef _WIN32
extern int fseeko64 (FILE *__stream, __off64_t __off, int __whence);
#endif
#ifdef __cplusplus
}
#endif