]> Chaos Git - corbenik/corbenik.git/commitdiff
Crypto changes
authorchaoskagami <chaos.kagami@gmail.com>
Sat, 9 Jul 2016 04:58:05 +0000 (00:58 -0400)
committerchaoskagami <chaos.kagami@gmail.com>
Sat, 9 Jul 2016 04:58:05 +0000 (00:58 -0400)
source/common.h
source/firm/crypto.c [deleted file]
source/firm/crypto.h [deleted file]
source/firm/fcram.c
source/firm/firm.c
source/std/memory.c

index 46eedd1143df8d392e1b676ddcaa8aad7a01c214..4113dda4f9abbe04c3f42afb9c4cc03a898c2fe4 100644 (file)
@@ -9,7 +9,6 @@
 #include "std/unused.h"
 
 #include "firm/fcram.h"
-#include "firm/crypto.h"
 #include "firm/headers.h"
 
 #include "patch_format.h"
diff --git a/source/firm/crypto.c b/source/firm/crypto.c
deleted file mode 100644 (file)
index 67d8e86..0000000
+++ /dev/null
@@ -1,376 +0,0 @@
-// From http://github.com/b1l1s/ctr
-
-#include "crypto.h"
-
-#include <stddef.h>
-#include "../std/memory.h"
-/* original version by megazig */
-
-#ifndef __thumb__
-#define BSWAP32(x)                                                                                                                                             \
-    {                                                                                                                                                          \
-        __asm__("eor r1, %1, %1, ror #16\n\t"                                                                                                                  \
-                "bic r1, r1, #0xFF0000\n\t"                                                                                                                    \
-                "mov %0, %1, ror #8\n\t"                                                                                                                       \
-                "eor %0, %0, r1, lsr #8\n\t"                                                                                                                   \
-                : "=r"(x)                                                                                                                                      \
-                : "0"(x)                                                                                                                                       \
-                : "r1");                                                                                                                                       \
-    };
-
-#define ADD_u128_uint32_t(u128_0, u128_1, u128_2, u128_3, uint32_t_0)                                                                                          \
-    {                                                                                                                                                          \
-        __asm__("adds %0, %4\n\t"                                                                                                                              \
-                "addcss %1, %1, #1\n\t"                                                                                                                        \
-                "addcss %2, %2, #1\n\t"                                                                                                                        \
-                "addcs %3, %3, #1\n\t"                                                                                                                         \
-                : "+r"(u128_0), "+r"(u128_1), "+r"(u128_2), "+r"(u128_3)                                                                                       \
-                : "r"(uint32_t_0)                                                                                                                              \
-                : "cc");                                                                                                                                       \
-    }
-#else
-#define BSWAP32(x)                                                                                                                                             \
-    {                                                                                                                                                          \
-        x = __builtin_bswap32(x);                                                                                                                              \
-    }
-
-#define ADD_u128_uint32_t(u128_0, u128_1, u128_2, u128_3, uint32_t_0)                                                                                          \
-    {                                                                                                                                                          \
-        __asm__("mov r4, #0\n\t"                                                                                                                               \
-                "add %0, %0, %4\n\t"                                                                                                                           \
-                "adc %1, %1, r4\n\t"                                                                                                                           \
-                "adc %2, %2, r4\n\t"                                                                                                                           \
-                "adc %3, %3, r4\n\t"                                                                                                                           \
-                : "+r"(u128_0), "+r"(u128_1), "+r"(u128_2), "+r"(u128_3)                                                                                       \
-                : "r"(uint32_t_0)                                                                                                                              \
-                : "cc", "r4");                                                                                                                                 \
-    }
-#endif /*__thumb__*/
-
-void
-aes_setkey(uint8_t keyslot, const void *key, uint32_t keyType, uint32_t mode)
-{
-    if (keyslot <= 0x03)
-        return; // Ignore TWL keys for now
-
-    uint32_t *key32 = (uint32_t *)key;
-    *REG_AESCNT = (*REG_AESCNT & ~(AES_CNT_INPUT_ENDIAN | AES_CNT_INPUT_ORDER)) | mode;
-    *REG_AESKEYCNT = (*REG_AESKEYCNT >> 6 << 6) | keyslot | AES_KEYCNT_WRITE;
-
-    REG_AESKEYFIFO[keyType] = key32[0];
-    REG_AESKEYFIFO[keyType] = key32[1];
-    REG_AESKEYFIFO[keyType] = key32[2];
-    REG_AESKEYFIFO[keyType] = key32[3];
-}
-
-void
-aes_use_keyslot(uint8_t keyslot)
-{
-    if (keyslot > 0x3F)
-        return;
-
-    *REG_AESKEYSEL = keyslot;
-    *REG_AESCNT = *REG_AESCNT | 0x04000000; /* mystery bit */
-}
-
-void
-aes_setiv(const void *iv, uint32_t mode)
-{
-    const uint32_t *iv32 = (const uint32_t *)iv;
-    *REG_AESCNT = (*REG_AESCNT & ~(AES_CNT_INPUT_ENDIAN | AES_CNT_INPUT_ORDER)) | mode;
-
-    // Word order for IV can't be changed in REG_AESCNT and always default to
-    // reversed
-    if (mode & AES_INPUT_NORMAL) {
-        REG_AESCTR[0] = iv32[3];
-        REG_AESCTR[1] = iv32[2];
-        REG_AESCTR[2] = iv32[1];
-        REG_AESCTR[3] = iv32[0];
-    } else {
-        REG_AESCTR[0] = iv32[0];
-        REG_AESCTR[1] = iv32[1];
-        REG_AESCTR[2] = iv32[2];
-        REG_AESCTR[3] = iv32[3];
-    }
-}
-
-void
-aes_advctr(void *ctr, uint32_t val, uint32_t mode)
-{
-    uint32_t *ctr32 = (uint32_t *)ctr;
-
-    int i;
-    if (mode & AES_INPUT_BE) {
-        for (i = 0; i < 4; ++i) // Endian swap
-            BSWAP32(ctr32[i]);
-    }
-
-    if (mode & AES_INPUT_NORMAL) {
-        ADD_u128_uint32_t(ctr32[3], ctr32[2], ctr32[1], ctr32[0], val);
-    } else {
-        ADD_u128_uint32_t(ctr32[0], ctr32[1], ctr32[2], ctr32[3], val);
-    }
-
-    if (mode & AES_INPUT_BE) {
-        for (i = 0; i < 4; ++i) // Endian swap
-            BSWAP32(ctr32[i]);
-    }
-}
-
-void
-aes_change_ctrmode(void *ctr, uint32_t fromMode, uint32_t toMode)
-{
-    uint32_t *ctr32 = (uint32_t *)ctr;
-    int i;
-    if ((fromMode ^ toMode) & AES_CNT_INPUT_ENDIAN) {
-        for (i = 0; i < 4; ++i)
-            BSWAP32(ctr32[i]);
-    }
-
-    if ((fromMode ^ toMode) & AES_CNT_INPUT_ORDER) {
-        uint32_t temp = ctr32[0];
-        ctr32[0] = ctr32[3];
-        ctr32[3] = temp;
-
-        temp = ctr32[1];
-        ctr32[1] = ctr32[2];
-        ctr32[2] = temp;
-    }
-}
-
-void
-aes_batch(void *dst, const void *src, uint32_t blockCount)
-{
-    *REG_AESBLKCNT = blockCount << 16;
-    *REG_AESCNT |= AES_CNT_START;
-
-    const uint32_t *src32 = (const uint32_t *)src;
-    uint32_t *dst32 = (uint32_t *)dst;
-
-    uint32_t wbc = blockCount;
-    uint32_t rbc = blockCount;
-
-    while (rbc) {
-        if (wbc && ((*REG_AESCNT & 0x1F) <= 0xC)) // There's space for at least 4 ints
-        {
-            *REG_AESWRFIFO = *src32++;
-            *REG_AESWRFIFO = *src32++;
-            *REG_AESWRFIFO = *src32++;
-            *REG_AESWRFIFO = *src32++;
-            wbc--;
-        }
-
-        if (rbc && ((*REG_AESCNT & (0x1F << 0x5)) >= (0x4 << 0x5))) // At least 4 ints available for read
-        {
-            *dst32++ = *REG_AESRDFIFO;
-            *dst32++ = *REG_AESRDFIFO;
-            *dst32++ = *REG_AESRDFIFO;
-            *dst32++ = *REG_AESRDFIFO;
-            rbc--;
-        }
-    }
-}
-
-inline void
-aes_setmode(uint32_t mode)
-{
-    *REG_AESCNT = mode | AES_CNT_INPUT_ORDER | AES_CNT_OUTPUT_ORDER | AES_CNT_INPUT_ENDIAN | AES_CNT_OUTPUT_ENDIAN | AES_CNT_FLUSH_READ | AES_CNT_FLUSH_WRITE;
-}
-
-void
-aes(void *dst, const void *src, uint32_t blockCount, void *iv, uint32_t mode, uint32_t ivMode)
-{
-    aes_setmode(mode);
-
-    uint32_t blocks;
-    while (blockCount != 0) {
-        if ((mode & AES_ALL_MODES) != AES_ECB_ENCRYPT_MODE && (mode & AES_ALL_MODES) != AES_ECB_DECRYPT_MODE)
-            aes_setiv(iv, ivMode);
-
-        blocks = (blockCount >= 0xFFFF) ? 0xFFFF : blockCount;
-
-        // Save the last block for the next decryption CBC batch's iv
-        if ((mode & AES_ALL_MODES) == AES_CBC_DECRYPT_MODE) {
-            memcpy(iv, src + (blocks - 1) * AES_BLOCK_SIZE, AES_BLOCK_SIZE);
-            aes_change_ctrmode(iv, AES_INPUT_BE | AES_INPUT_NORMAL, ivMode);
-        }
-
-        // Process the current batch
-        aes_batch(dst, src, blocks);
-
-        // Save the last block for the next encryption CBC batch's iv
-        if ((mode & AES_ALL_MODES) == AES_CBC_ENCRYPT_MODE) {
-            memcpy(iv, dst + (blocks - 1) * AES_BLOCK_SIZE, AES_BLOCK_SIZE);
-            aes_change_ctrmode(iv, AES_INPUT_BE | AES_INPUT_NORMAL, ivMode);
-        }
-
-        // Advance counter for CTR mode
-        else if ((mode & AES_ALL_MODES) == AES_CTR_MODE)
-            aes_advctr(iv, blocks, ivMode);
-
-        src += blocks * AES_BLOCK_SIZE;
-        dst += blocks * AES_BLOCK_SIZE;
-        blockCount -= blocks;
-    }
-}
-
-void
-ncch_getctr(const ncch_h *ncch, uint8_t *ctr, uint8_t type)
-{
-    uint32_t version = ncch->version;
-    const uint8_t *partitionID = ncch->partitionID;
-
-    int i;
-    for (i = 0; i < 16; i++)
-        ctr[i] = 0x00;
-
-    if (version == 2 || version == 0) {
-        for (i = 0; i < 8; i++)
-            ctr[i] = partitionID[7 - i]; // Convert to big endian & normal input
-        ctr[8] = type;
-    } else if (version == 1) {
-        int x = 0;
-        if (type == NCCHTYPE_EXHEADER)
-            x = MEDIA_UNITS;
-        else if (type == NCCHTYPE_EXEFS)
-            x = ncch->exeFSOffset * MEDIA_UNITS;
-        else if (type == NCCHTYPE_ROMFS)
-            x = ncch->exeFSOffset * MEDIA_UNITS;
-
-        for (i = 0; i < 8; i++)
-            ctr[i] = partitionID[i];
-        for (i = 0; i < 4; i++)
-            ctr[i + 12] = (x >> ((3 - i) * 8)) & 0xFF;
-    }
-}
-
-void
-sha_wait_idle()
-{
-    while (*REG_SHA_CNT & 1)
-        ;
-}
-
-void
-sha(void *res, const void *src, uint32_t size, uint32_t mode)
-{
-    sha_wait_idle();
-    *REG_SHA_CNT = mode | SHA_CNT_OUTPUT_ENDIAN | SHA_NORMAL_ROUND;
-
-    const uint32_t *src32 = (const uint32_t *)src;
-    int i;
-    while (size >= 0x40) {
-        sha_wait_idle();
-        for (i = 0; i < 4; ++i) {
-            *REG_SHA_INFIFO = *src32++;
-            *REG_SHA_INFIFO = *src32++;
-            *REG_SHA_INFIFO = *src32++;
-            *REG_SHA_INFIFO = *src32++;
-        }
-
-        size -= 0x40;
-    }
-
-    sha_wait_idle();
-    memcpy((void *)REG_SHA_INFIFO, src32, size);
-
-    *REG_SHA_CNT = (*REG_SHA_CNT & ~SHA_NORMAL_ROUND) | SHA_FINAL_ROUND;
-
-    while (*REG_SHA_CNT & SHA_FINAL_ROUND)
-        ;
-    sha_wait_idle();
-
-    uint32_t hashSize = SHA_256_HASH_SIZE;
-    if (mode == SHA_224_MODE)
-        hashSize = SHA_224_HASH_SIZE;
-    else if (mode == SHA_1_MODE)
-        hashSize = SHA_1_HASH_SIZE;
-
-    memcpy(res, (void *)REG_SHA_HASH, hashSize);
-}
-
-void
-rsa_wait_idle()
-{
-    while (*REG_RSA_CNT & 1)
-        ;
-}
-
-void
-rsa_use_keyslot(uint32_t keyslot)
-{
-    *REG_RSA_CNT = (*REG_RSA_CNT & ~RSA_CNT_KEYSLOTS) | (keyslot << 4);
-}
-
-void
-rsa_setkey(uint32_t keyslot, const void *mod, const void *exp, uint32_t mode)
-{
-    rsa_wait_idle();
-    *REG_RSA_CNT = (*REG_RSA_CNT & ~RSA_CNT_KEYSLOTS) | (keyslot << 4) | RSA_IO_BE | RSA_IO_NORMAL;
-
-    uint32_t size = mode * 4;
-
-    volatile uint32_t *keyslotCnt = REG_RSA_SLOT0 + (keyslot << 4);
-    keyslotCnt[0] &= ~(RSA_SLOTCNT_KEY_SET | RSA_SLOTCNT_WPROTECT);
-    keyslotCnt[1] = mode;
-
-    memcpy((void *)REG_RSA_MOD_END - size, mod, size);
-
-    if (exp == NULL) {
-        size -= 4;
-        while (size) {
-            *REG_RSA_EXPFIFO = 0;
-            size -= 4;
-        }
-        *REG_RSA_EXPFIFO = 0x01000100; // 0x00010001 byteswapped
-    } else {
-        const uint32_t *exp32 = (const uint32_t *)exp;
-        while (size) {
-            *REG_RSA_EXPFIFO = *exp32++;
-            size -= 4;
-        }
-    }
-}
-
-int
-rsa_iskeyset(uint32_t keyslot)
-{
-    return *(REG_RSA_SLOT0 + (keyslot << 4)) & 1;
-}
-
-void
-rsa(void *dst, const void *src, uint32_t size)
-{
-    uint32_t keyslot = (*REG_RSA_CNT & RSA_CNT_KEYSLOTS) >> 4;
-    if (rsa_iskeyset(keyslot) == 0)
-        return;
-
-    rsa_wait_idle();
-    *REG_RSA_CNT |= RSA_IO_BE | RSA_IO_NORMAL;
-
-    // Pad the message with zeroes so that it's a multiple of 8
-    // and write the message with the end aligned with the register
-    uint32_t padSize = ((size + 7) & ~7) - size;
-    memset((void *)REG_RSA_TXT_END - (size + padSize), 0, padSize);
-    memcpy((void *)REG_RSA_TXT_END - size, src, size);
-
-    // Start
-    *REG_RSA_CNT |= RSA_CNT_START;
-
-    rsa_wait_idle();
-    memcpy(dst, (void *)REG_RSA_TXT_END - size, size);
-}
-
-int
-rsa_verify(const void *data, uint32_t size, const void *sig, uint32_t mode)
-{
-    uint8_t dataHash[SHA_256_HASH_SIZE];
-    sha(dataHash, data, size, SHA_256_MODE);
-
-    uint8_t decSig[0x100]; // Way too big, need to request a work area
-
-    uint32_t sigSize = mode * 4;
-    rsa(decSig, sig, sigSize);
-
-    return memcmp(dataHash, decSig + (sigSize - SHA_256_HASH_SIZE), SHA_256_HASH_SIZE) == 0;
-}
diff --git a/source/firm/crypto.h b/source/firm/crypto.h
deleted file mode 100644 (file)
index baa33f6..0000000
+++ /dev/null
@@ -1,136 +0,0 @@
-// From http://github.com/b1l1s/ctr
-
-#ifndef __CRYPTO_H
-#define __CRYPTO_H
-
-#include <stdint.h>
-#include "headers.h"
-
-/**************************AES****************************/
-#define REG_AESCNT ((volatile uint32_t *)0x10009000)
-#define REG_AESBLKCNT ((volatile uint32_t *)0x10009004)
-#define REG_AESWRFIFO ((volatile uint32_t *)0x10009008)
-#define REG_AESRDFIFO ((volatile uint32_t *)0x1000900C)
-#define REG_AESKEYSEL ((volatile uint8_t *)0x10009010)
-#define REG_AESKEYCNT ((volatile uint8_t *)0x10009011)
-#define REG_AESCTR ((volatile uint32_t *)0x10009020)
-
-#define REG_AESKEYFIFO ((volatile uint32_t *)0x10009100)
-#define REG_AESKEYXFIFO ((volatile uint32_t *)0x10009104)
-#define REG_AESKEYYFIFO ((volatile uint32_t *)0x10009108)
-
-#define AES_CCM_DECRYPT_MODE (0u << 27)
-#define AES_CCM_ENCRYPT_MODE (1u << 27)
-#define AES_CTR_MODE (2u << 27)
-#define AES_CTR_MODE (2u << 27)
-#define AES_CBC_DECRYPT_MODE (4u << 27)
-#define AES_CBC_ENCRYPT_MODE (5u << 27)
-#define AES_ECB_DECRYPT_MODE (6u << 27)
-#define AES_ECB_ENCRYPT_MODE (7u << 27)
-#define AES_ALL_MODES (7u << 27)
-
-#define AES_CNT_START 0x80000000
-#define AES_CNT_INPUT_ORDER 0x02000000
-#define AES_CNT_OUTPUT_ORDER 0x01000000
-#define AES_CNT_INPUT_ENDIAN 0x00800000
-#define AES_CNT_OUTPUT_ENDIAN 0x00400000
-#define AES_CNT_FLUSH_READ 0x00000800
-#define AES_CNT_FLUSH_WRITE 0x00000400
-
-#define AES_INPUT_BE (AES_CNT_INPUT_ENDIAN)
-#define AES_INPUT_LE 0
-#define AES_INPUT_NORMAL (AES_CNT_INPUT_ORDER)
-#define AES_INPUT_REVERSED 0
-
-#define AES_TEMP_KEYSLOT 0x11
-
-#define AES_BLOCK_SIZE 0x10
-
-#define AES_KEYCNT_WRITE (1 << 0x7)
-#define AES_KEYNORMAL 0
-#define AES_KEYX 1
-#define AES_KEYY 2
-
-/**************************SHA****************************/
-#define REG_SHA_CNT ((volatile uint32_t *)0x1000A000)
-#define REG_SHA_BLKCNT ((volatile uint32_t *)0x1000A004)
-#define REG_SHA_HASH ((volatile uint32_t *)0x1000A040)
-#define REG_SHA_INFIFO ((volatile uint32_t *)0x1000A080)
-
-#define SHA_CNT_STATE 0x00000003
-#define SHA_CNT_UNK2 0x00000004
-#define SHA_CNT_OUTPUT_ENDIAN 0x00000008
-#define SHA_CNT_MODE 0x00000030
-#define SHA_CNT_ENABLE 0x00010000
-#define SHA_CNT_ACTIVE 0x00020000
-
-#define SHA_HASH_READY 0x00000000
-#define SHA_NORMAL_ROUND 0x00000001
-#define SHA_FINAL_ROUND 0x00000002
-
-#define SHA_OUTPUT_BE SHA_CNT_OUTPUT_ENDIAN
-#define SHA_OUTPUT_LE 0
-
-#define SHA_256_MODE 0
-#define SHA_224_MODE 0x00000010
-#define SHA_1_MODE 0x00000020
-
-#define SHA_256_HASH_SIZE (256 / 8)
-#define SHA_224_HASH_SIZE (224 / 8)
-#define SHA_1_HASH_SIZE (160 / 8)
-
-/**************************RSA****************************/
-#define REG_RSA_CNT ((volatile uint32_t *)0x1000B000)
-#define REG_RSA_SLOT0 ((volatile uint32_t *)0x1000B100)
-#define REG_RSA_SLOT1 ((volatile uint32_t *)0x1000B110)
-#define REG_RSA_SLOT2 ((volatile uint32_t *)0x1000B120)
-#define REG_RSA_SLOT3 ((volatile uint32_t *)0x1000B130)
-#define REG_RSA_EXPFIFO ((volatile uint32_t *)0x1000B200)
-#define REG_RSA_MOD_END ((volatile uint32_t *)0x1000B500)
-#define REG_RSA_TXT_END ((volatile uint32_t *)0x1000B900)
-
-#define RSA_CNT_START 0x00000001
-#define RSA_CNT_KEYSLOTS 0x000000F0
-#define RSA_CNT_IO_ENDIAN 0x00000100
-#define RSA_CNT_IO_ORDER 0x00000200
-
-#define RSA_SLOTCNT_KEY_SET 0x00000001
-#define RSA_SLOTCNT_WPROTECT 0x00000002 // Write protect
-
-#define RSA_IO_BE RSA_CNT_IO_ENDIAN
-#define RSA_IO_LE 0
-#define RSA_IO_NORMAL RSA_CNT_IO_ORDER
-#define RSA_IO_REVERSED 0
-
-#define RSA_TEMP_KEYSLOT 0
-
-#define RSA_1024_MODE 0x20
-#define RSA_2048_MODE 0x40
-
-void aes_setkey(uint8_t keyslot, const void *key, uint32_t keyType, uint32_t mode);
-void aes_use_keyslot(uint8_t keyslot);
-
-void aes(void *dst, const void *src, uint32_t blockCount, void *iv, uint32_t mode, uint32_t ivMode);
-
-void aes_setiv(const void *iv, uint32_t mode);
-void aes_advctr(void *ctr, uint32_t val, uint32_t mode);
-void aes_change_ctrmode(void *ctr, uint32_t fromMode, uint32_t toMode);
-
-void aes_batch(void *dst, const void *src, uint32_t blockCount);
-
-void sha(void *res, const void *src, uint32_t size, uint32_t mode);
-
-void rsa_setkey(uint32_t keyslot, const void *mod, const void *exp, uint32_t mode);
-void rsa_use_keyslot(uint32_t keyslot);
-
-int rsa_verify(const void *data, uint32_t size, const void *sig, uint32_t mode);
-
-typedef enum {
-    NCCHTYPE_EXHEADER = 1,
-    NCCHTYPE_EXEFS = 2,
-    NCCHTYPE_ROMFS = 3,
-} ctr_ncchtypes;
-
-void ncch_getctr(const ncch_h *ncch, uint8_t *ctr, uint8_t type);
-
-#endif
index 1949451d9a68119eb8d77c4c7556a68117cfa9ef..7b81b3286003c83d1053ecbac08a638574c8c817 100644 (file)
@@ -6,6 +6,6 @@ void *fcram_static_mem = (void*)FCRAM_STATIC_ALLOC_LOC;
 void *static_allocate(size_t bytes) {
     size_t aligned_bytes = bytes + (4 - (bytes % 4)); // Align to integer size (for ARM processor)
     void *ret = fcram_static_mem;
-    fcram_static_mem += aligned_bytes;
+    fcram_static_mem = (uint8_t*)fcram_static_mem + aligned_bytes;
     return ret;
 }
index 78d0b9f29899859c7794bf1a403002551e760368..b33e4bd9f5d77a417b086a072d0e6a3dfe932369 100644 (file)
@@ -3,6 +3,9 @@
 #include <stdint.h>
 #include <stddef.h>
 
+#include <ctr9/io.h>
+#include <ctr9/aes.h>
+
 #include "../common.h"
 #include "../misc/sha256.h"
 
@@ -25,6 +28,47 @@ static int update_96_keys = 0;
 
 static volatile uint32_t *const a11_entry = (volatile uint32_t *)0x1FFFFFF8;
 
+typedef enum {
+    NCCHTYPE_EXHEADER = 1,
+    NCCHTYPE_EXEFS = 2,
+    NCCHTYPE_ROMFS = 3,
+} ctr_ncchtypes;
+
+void
+ncch_getctr(const ncch_h *ncch, uint8_t *ctr, uint8_t type)
+{
+    uint32_t version = ncch->version;
+    const uint8_t *partitionID = ncch->partitionID;
+    int i;
+
+    for (i = 0; i < 16; i++)
+        ctr[i] = 0x00;
+
+    if (version == 2 || version == 0) {
+        for (i = 0; i < 8; i++)
+            ctr[i] = partitionID[7 - i]; // Convert to big endian & normal input
+        ctr[8] = type;
+    } else if (version == 1) {
+        int x = 0;
+        if (type == NCCHTYPE_EXHEADER)
+            x = MEDIA_UNITS;
+        else if (type == NCCHTYPE_EXEFS)
+            x = ncch->exeFSOffset * MEDIA_UNITS;
+        else if (type == NCCHTYPE_ROMFS)
+            x = ncch->exeFSOffset * MEDIA_UNITS;
+        for (i = 0; i < 8; i++)
+            ctr[i] = partitionID[i];
+        for (i = 0; i < 4; i++)
+            ctr[i + 12] = (x >> ((3 - i) * 8)) & 0xFF;
+    }
+}
+
+void
+aes(void *dst, const void *src, uint32_t blockCount, void *iv, uint32_t mode, uint32_t ivMode)
+{
+    set_ctr(iv);
+}
+
 void
 slot0x11key96_init()
 {
@@ -33,7 +77,7 @@ slot0x11key96_init()
     uint8_t key[AES_BLOCK_SIZE];
     if (read_file(key, PATH_SLOT0X11KEY96, AES_BLOCK_SIZE) != 0 || read_file(key, PATH_ALT_SLOT0X11KEY96, AES_BLOCK_SIZE) != 0) {
         // Read key successfully.
-        aes_setkey(0x11, key, AES_KEYNORMAL, AES_INPUT_BE | AES_INPUT_NORMAL);
+        setup_aeskey(0x11, key);
 
         // Tell boot_firm it needs to regenerate the keys.
         update_96_keys = 1;
@@ -54,7 +98,7 @@ decrypt_cetk_key(void *key, const void *cetk)
     if (sigtype != SIG_TYPE_RSA2048_SHA256)
         return 1;
 
-    ticket_h *ticket = (ticket_h *)(cetk + sizeof(sigtype) + 0x13C);
+    ticket_h *ticket = (ticket_h *)((uint8_t*)cetk + sizeof(sigtype) + 0x13C);
 
     if (ticket->ticketCommonKeyYIndex != 1)
         return 1;
@@ -76,11 +120,11 @@ decrypt_cetk_key(void *key, const void *cetk)
         if (i < p9_base)
             return 1;
 
-        aes_setkey(0x3D, common_key_y, AES_KEYY, AES_INPUT_BE | AES_INPUT_NORMAL);
+        setup_aeskeyY(0x3D, common_key_y);
         common_key_y_init = 1;
     }
 
-    aes_use_keyslot(0x3D);
+    use_aeskey(0x3D);
     memcpy(iv, ticket->titleID, sizeof(ticket->titleID));
 
     memcpy(key, ticket->titleKey, sizeof(ticket->titleKey));
@@ -99,8 +143,8 @@ decrypt_firm_title(firm_h *dest, ncch_h *ncch, uint32_t *size, void *key)
     uint8_t exefs_iv[16] = { 0 };
 
     fprintf(BOTTOM_SCREEN, "n");
-    aes_setkey(0x16, key, AES_KEYNORMAL, AES_INPUT_BE | AES_INPUT_NORMAL);
-    aes_use_keyslot(0x16);
+    setup_aeskey(0x16, key);
+    use_aeskey(0x16);
     aes(ncch, ncch, *size / AES_BLOCK_SIZE, firm_iv, AES_CBC_DECRYPT_MODE, AES_INPUT_BE | AES_INPUT_NORMAL);
 
     if (ncch->magic != NCCH_MAGIC)
@@ -110,12 +154,12 @@ decrypt_firm_title(firm_h *dest, ncch_h *ncch, uint32_t *size, void *key)
     ncch_getctr(ncch, exefs_iv, NCCHTYPE_EXEFS);
 
     // Get the exefs offset and size from the NCCH
-    exefs_h *exefs = (exefs_h *)((void *)ncch + ncch->exeFSOffset * MEDIA_UNITS);
+    exefs_h *exefs = (exefs_h *)((uint8_t *)ncch + ncch->exeFSOffset * MEDIA_UNITS);
     uint32_t exefs_size = ncch->exeFSSize * MEDIA_UNITS;
 
     fprintf(BOTTOM_SCREEN, "e");
-    aes_setkey(0x2C, exefs_key, AES_KEYY, AES_INPUT_BE | AES_INPUT_NORMAL);
-    aes_use_keyslot(0x2C);
+    setup_aeskeyY(0x2C, exefs_key);
+    use_aeskey(0x2C);
     aes(exefs, exefs, exefs_size / AES_BLOCK_SIZE, exefs_iv, AES_CTR_MODE, AES_INPUT_BE | AES_INPUT_NORMAL);
 
     // Get the decrypted FIRM
@@ -145,18 +189,18 @@ decrypt_arm9bin(arm9bin_h *header, uint64_t firm_title, uint8_t version)
         slot0x11key96_init();
         slot = 0x16;
 
-        aes_use_keyslot(0x11);
+        use_aeskey(0x11);
         aes(decrypted_keyx, header->slot0x16keyX, 1, NULL, AES_ECB_DECRYPT_MODE, 0);
-        aes_setkey(slot, decrypted_keyx, AES_KEYX, AES_INPUT_BE | AES_INPUT_NORMAL);
+        setup_aeskeyX(slot, decrypted_keyx);
     }
 
-    aes_setkey(slot, header->keyy, AES_KEYY, AES_INPUT_BE | AES_INPUT_NORMAL);
-    aes_setiv(header->ctr, AES_INPUT_BE | AES_INPUT_NORMAL);
+    setup_aeskeyY(slot, header->keyy);
+    set_ctr(header->ctr);
 
     void *arm9bin = (uint8_t *)header + 0x800;
     int size = atoi(header->size);
 
-    aes_use_keyslot(slot);
+    use_aeskey(slot);
     aes(arm9bin, arm9bin, size / AES_BLOCK_SIZE, header->ctr, AES_CTR_MODE, AES_INPUT_BE | AES_INPUT_NORMAL);
 
     if (firm_title == NATIVE_FIRM_TITLEID)
@@ -337,18 +381,18 @@ boot_firm()
     // depending on which firmware you're booting from.
     // TODO: Don't use the hardcoded offset.
     if (update_96_keys && fsig->console == console_n3ds && fsig->version > 0x0F) {
-        void *keydata = find_section_key();
+        uint8_t *keydata = find_section_key();
         if (!keydata) {
             abort("Couldn't find key!\n");
         }
 
         wait();
 
-        aes_use_keyslot(0x11);
+        use_aeskey(0x11);
         uint8_t keyx[AES_BLOCK_SIZE];
         for (int slot = 0x19; slot < 0x20; slot++) {
             aes(keyx, keydata, 1, NULL, AES_ECB_DECRYPT_MODE, 0);
-            aes_setkey(slot, keyx, AES_KEYX, AES_INPUT_BE | AES_INPUT_NORMAL);
+            setup_aeskeyX(slot, keyx);
             *(uint8_t *)(keydata + 0xF) += 1;
         }
 
@@ -356,7 +400,7 @@ boot_firm()
     }
 
     for (firm_section_h *section = firm_loc->section; section < firm_loc->section + 4 && section->address != 0; section++) {
-        memcpy((void *)section->address, (void *)firm_loc + section->offset, section->size);
+        memcpy((void *)section->address, (void *)((uint8_t*)firm_loc + section->offset), section->size);
     }
     fprintf(BOTTOM_SCREEN, "Copied FIRM\n");
 
@@ -387,17 +431,17 @@ find_proc9(firm_h *firm, firm_section_h *process9, exefs_h **p9exefs)
             break;
 
         if (section->type == FIRM_TYPE_ARM9) {
-            void *arm9section = (void *)firm + section->offset;
+            uint8_t *arm9section = (uint8_t *)firm + section->offset;
             while (arm9section < arm9section + section->size) {
                 if (!memcmp(arm9section, "Process9", 8)) { // Process9
-                    ncch_h *ncch = (ncch_h *)(arm9section - sizeof(ncch_h));
+                    ncch_h *ncch = (ncch_h *)((uint8_t*)arm9section - sizeof(ncch_h));
                     if (ncch->magic == NCCH_MAGIC) {
                         // Found Process9
                         ncch_ex_h *p9exheader = (ncch_ex_h *)(ncch + 1);
                         *p9exefs = (exefs_h *)(p9exheader + 1);
                         process9->address = p9exheader->sci.textCodeSet.address;
                         process9->size = (*p9exefs)->fileHeaders[0].size;
-                        process9->offset = (void *)((*p9exefs) + 1) - (void *)firm;
+                        process9->offset = ((uint32_t)((*p9exefs) + 1) - (uint32_t)firm);
                         fprintf(BOTTOM_SCREEN, "p");
                         return 0;
                     }
index aab59c2519ed22ecbc22c0728dcb7b315a0e901e..bb33b684a09247cc911d54089642dc5c3d33a0a5 100644 (file)
@@ -46,8 +46,9 @@ void
 memmove(void *dest, const void *src, size_t size)
 {
     // memcpy does the job of moving backwards just fine
-    if (dest < src || src + size <= dest) {
-        return memcpy(dest, src, size);
+    if (dest < src || (uint8_t*)src + size <= (uint8_t*)dest) {
+        memcpy(dest, src, size);
+        return;
     }
 
     // Moving forward is just a reverse memcpy