Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include <stdio.h>
- #include <string.h>
- #include "sha256.h"
- int crypto_fix(char* cxi_path, char* seed_path){
- FILE * cxi = fopen(cxi_path, "r+b");
- if (cxi == NULL){
- printf("CXI COULD NOT BE OPENED\n");
- return -1;
- }
- fseek(cxi, 0, SEEK_END);
- int cxi_size = ftell(cxi); //get cxi filesize
- fseek(cxi, 0, SEEK_SET);
- if (cxi_size < 0x200){ //if it's too small to be a cxi, return -2
- printf("INVALID CXI\n");
- return -2;
- }
- unsigned char ncch[5] = { '\0' };
- fseek(cxi, 0x100, SEEK_SET);
- fread(&ncch, 4, 1, cxi);
- if (strcmp(ncch, "NCCH") != 0){ //if not NCCH, return -2
- printf("INVALID CXI\n");
- return -2;
- }
- unsigned char seed_flag = 0;
- fseek(cxi, 0x18F, SEEK_SET);
- fread(&seed_flag, 1, 1, cxi);
- if (!(seed_flag & 0x20)){ //if seed crypto is not enabled
- printf("SEED CRYPTO NOT DETECTED\n");
- return -3;
- }
- FILE * seeddb = fopen(seed_path, "rb");
- if (seeddb == NULL){
- printf("SEEDDB COULD NOT BE OPENED\n");
- return -4;
- }
- fseek(seeddb, 0, SEEK_END);
- int seeddb_size = ftell(seeddb); //get seeddb filesize
- fseek(seeddb, 0, SEEK_SET);
- unsigned int seedcount = 0;
- if (seeddb_size < 0x10) fread(&seedcount, 4, 1, seeddb);
- if (0x10 + (seedcount * 0x20) != seeddb_size){ //if the seeddb is too small, return -5
- printf("INVALID SEEDDB\n");
- return -5;
- }
- unsigned int unique_id = 0;
- fseek(cxi, 0x109, SEEK_SET);
- fread(&unique_id, 3, 1, cxi); //retrieve the unique id from the cxi
- printf("UNIQUE ID: 0x%X\n", unique_id);
- unsigned char cxi_keyY[0x10] = { 0 };
- fseek(cxi, 0, SEEK_SET);
- fread(&cxi_keyY, 0x10, 1, cxi); //read keyy from the cxi
- printf("KEYY: ");
- for (int i = 0; i < 0x10; i++){
- if (cxi_keyY[i] < 0x10){
- printf("0");
- printf("%X", cxi_keyY[i]);
- } else {
- printf("%X", cxi_keyY[i]);
- }
- }
- printf("\n");
- unsigned int uid_check = 0;
- unsigned char seed[0x10] = { 0 };
- for (int i = 0; i < seedcount; i++){ //search the seeddb for the unique id
- fseek(seeddb, 0x11+(i*0x20), SEEK_SET);
- fread(&uid_check, 3, 1, seeddb);
- if (uid_check == unique_id){
- fseek(seeddb, 0x18+(i*0x20), SEEK_SET);
- fread(&seed, 0x10, 1, seeddb);
- break;
- } else if (i == seedcount-1){ //if seed could not be located, return -6
- printf("SEED NOT FOUND");
- return -6;
- }
- }
- printf("SEED: ");
- for (int i = 0; i < 0x10; i++){
- if (seed[i] < 0x10){
- printf("0");
- printf("%X", seed[i]);
- } else {
- printf("%X", seed[i]);
- }
- }
- printf("\n");
- unsigned char keyY_gen[0x20] = { 0 }; //create array including data to be hashed
- memcpy(keyY_gen, cxi_keyY, 0x10);
- memcpy(keyY_gen+0x10, seed, 0x10);
- unsigned char keyy[0x20] = { 0 }; //create an sha256 over the new keyy data
- sha256_context keyy_ctx;
- sha256_starts(&keyy_ctx);
- sha256_update(&keyy_ctx, keyY_gen, 0x20);
- sha256_finish(&keyy_ctx, keyy);
- printf("NEW KEYY: ");
- for (int i = 0; i < 0x10; i++){
- if (keyy[i] < 0x10){
- printf("0");
- printf("%X", keyy[i]);
- } else {
- printf("%X", keyy[i]);
- }
- }
- printf("\n");
- fseek(cxi, 0, SEEK_SET);
- fwrite(&keyy, 0x10, 1, cxi); //write the new keyy to the cxi
- seed_flag = seed_flag & 0x0F;
- fseek(cxi, 0x18F, SEEK_SET);
- fwrite(&seed_flag, 1, 1, cxi);
- fclose(cxi);
- fclose(seeddb);
- printf("DONE!\n");
- return 0;
- }
- int main(int argc, char *argv[]){
- if (argc < 3 || argc > 4){ //if invalid number of arguments, prompt user with arg' layout
- printf("Crypto-Fixer <CXI PATH> <SEEDDB PATH> (OPTIONAL OUTPUT)\n");
- return 1;
- } else if (argc == 3){
- return crypto_fix(argv[1], argv[2]);
- } else if (argc == 4){
- FILE * input = fopen(argv[1], "rb");
- if (input == NULL){
- printf("INPUT COULD NOT BE OPENED\n");
- return 2;
- }
- fseek(input, 0, SEEK_END);
- int size = ftell(input);
- fseek(input, 0, SEEK_SET);
- if (size < 0x200){
- printf("INVALID CXI\n");
- return -2;
- }
- unsigned char ncch[5] = { '\0' };
- fseek(input, 0x100, SEEK_SET);
- fread(&ncch, 4, 1, input);
- if (strcmp(ncch, "NCCH") != 0){
- printf("INVALID CXI\n");
- return -2;
- }
- FILE * output = fopen(argv[3], "wb");
- printf("Copying input CXI to output file...\n");
- unsigned char buf[0x100000];
- for (int i = 0; i < size; i+=0x100000){
- if (i + 0x100000 > size){
- fread(&buf, size - i, 1, input);
- fwrite(&buf, size - i, 1, output);
- } else {
- fread(&buf, 0x100000, 1, input);
- fwrite(&buf, 0x100000, 1, output);
- }
- }
- fclose(input);
- fclose(output);
- return crypto_fix(argv[3], argv[2]);
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment