From 9b9f784c26e7adff34224bb0a574323c0aa6a5a7 Mon Sep 17 00:00:00 2001 From: Aurora Date: Sun, 20 Mar 2016 01:00:45 +0100 Subject: [PATCH] Fixed intermittent splash from CakeBrah, made splash last slightly longer, added shutdown on error, slimmed down FatFs, added error on missing emuNAND, changed folder to "aurei", changed the dat name to "AuReiNand.dat", propered the built-in screen init of the chainloader, remade the look of the 3dsx (First luma-powered CFW!) --- Makefile | 32 +++++----- icon.png | Bin 6231 -> 3140 bytes loader/source/fatfs/sdmmc/common.h | 1 + loader/source/i2c.c | 75 ++++------------------ loader/source/i2c.h | 19 +----- loader/source/main.c | 20 +++--- loader/source/screeninit.c | 16 +++-- loader/source/types.h | 1 - reboot/rebootCode.s | 2 +- source/draw.c | 16 ++--- source/emunand.c | 5 ++ source/fatfs/ffconf.h | 2 +- source/firm.c | 25 ++++---- source/i2c.c | 98 +++++++++++++++++++++++++++++ source/i2c.h | 18 ++++++ source/loader.c | 4 +- source/main.c | 5 ++ source/memory.c | 6 ++ source/memory.h | 1 + source/start.s | 15 +++-- 20 files changed, 215 insertions(+), 146 deletions(-) create mode 100644 source/i2c.c create mode 100644 source/i2c.h diff --git a/Makefile b/Makefile index 28005b6..0e22ac2 100644 --- a/Makefile +++ b/Makefile @@ -12,7 +12,7 @@ ifneq ($(PYTHON_VER_MAJOR), 3) PYTHON3 := py -3 endif -name := ReiNand +name := AuReiNand dir_source := source dir_data := data @@ -26,7 +26,7 @@ dir_loader := loader ASFLAGS := -mlittle-endian -mcpu=arm946e-s -march=armv5te CFLAGS := -Wall -Wextra -MMD -MP -marm $(ASFLAGS) -fno-builtin -fshort-wchar -std=c11 -Wno-main -O2 -ffast-math -FLAGS := name=$(name).dat dir_out=$(abspath $(dir_out)) ICON=$(abspath icon.png) --no-print-directory +FLAGS := name=$(name).dat dir_out=$(abspath $(dir_out)) ICON=$(abspath icon.png) APP_DESCRIPTION="Noob-friendly 3DS CFW." APP_AUTHOR="Reisyukaku/Aurora Wright" --no-print-directory objects_cfw = $(patsubst $(dir_source)/%.s, $(dir_build)/%.o, \ $(patsubst $(dir_source)/%.c, $(dir_build)/%.o, \ @@ -43,29 +43,29 @@ launcher: $(dir_out)/$(name).dat a9lh: $(dir_out)/arm9loaderhax.bin .PHONY: emunand -emunand: $(dir_out)/rei/emunand/emunand.bin +emunand: $(dir_out)/aurei/emunand/emunand.bin .PHONY: reboot -reboot: $(dir_out)/rei/reboot/reboot.bin +reboot: $(dir_out)/aurei/reboot/reboot.bin .PHONY: ninjhax ninjhax: $(dir_out)/3ds/$(name) .PHONY: loader -loader: $(dir_out)/rei/loader.bin +loader: $(dir_out)/aurei/loader.bin .PHONY: clean clean: @$(MAKE) $(FLAGS) -C $(dir_mset) clean @$(MAKE) $(FLAGS) -C $(dir_ninjhax) clean @rm -rf $(dir_out) $(dir_build) - @cd $(dir_loader) && make clean + @$(MAKE) -C $(dir_loader) clean -$(dir_out)/$(name).dat: $(dir_build)/main.bin $(dir_out)/rei +$(dir_out)/$(name).dat: $(dir_build)/main.bin $(dir_out)/aurei @$(MAKE) $(FLAGS) -C $(dir_mset) launcher dd if=$(dir_build)/main.bin of=$@ bs=512 seek=144 -$(dir_out)/arm9loaderhax.bin: $(dir_build)/main.bin $(dir_out)/rei +$(dir_out)/arm9loaderhax.bin: $(dir_build)/main.bin $(dir_out)/aurei @cp -av $(dir_build)/main.bin $@ $(dir_out)/3ds/$(name): @@ -74,21 +74,21 @@ $(dir_out)/3ds/$(name): @mv $(dir_out)/$(name).3dsx $@ @mv $(dir_out)/$(name).smdh $@ -$(dir_out)/rei: - @mkdir -p "$(dir_out)/rei" +$(dir_out)/aurei: + @mkdir -p "$(dir_out)/aurei" -$(dir_out)/rei/emunand/emunand.bin: $(dir_emu)/emuCode.s +$(dir_out)/aurei/emunand/emunand.bin: $(dir_emu)/emuCode.s @armips $< - @mkdir -p "$(dir_out)/rei/emunand" + @mkdir -p "$(dir_out)/aurei/emunand" @mv emunand.bin $@ -$(dir_out)/rei/reboot/reboot.bin: $(dir_reboot)/rebootCode.s +$(dir_out)/aurei/reboot/reboot.bin: $(dir_reboot)/rebootCode.s @armips $< - @mkdir -p "$(dir_out)/rei/reboot" + @mkdir -p "$(dir_out)/aurei/reboot" @mv reboot.bin $@ -$(dir_out)/rei/loader.bin: $(dir_out)/rei $(dir_loader)/Makefile - @cd $(dir_loader) && make +$(dir_out)/aurei/loader.bin: $(dir_out)/aurei $(dir_loader)/Makefile + @$(MAKE) -C $(dir_loader) @mv $(dir_loader)/loader.bin $@ $(dir_build)/main.bin: $(dir_build)/main.elf diff --git a/icon.png b/icon.png index f4768065ac8017717f24c6b44913f0caff3e9e31..df686f8f0b4136346418dfbf5958c335a0cf09e5 100644 GIT binary patch literal 3140 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 #include "../../types.h" \ No newline at end of file diff --git a/loader/source/i2c.c b/loader/source/i2c.c index f0beefd..6f03579 100644 --- a/loader/source/i2c.c +++ b/loader/source/i2c.c @@ -10,11 +10,11 @@ static const struct { u8 bus_id, reg_addr; } dev_data[] = { {2, 0xA4}, {2, 0x9A}, {2, 0xA0}, }; -inline u8 i2cGetDeviceBusId(u8 device_id) { +static inline u8 i2cGetDeviceBusId(u8 device_id) { return dev_data[device_id].bus_id; } -inline u8 i2cGetDeviceRegAddr(u8 device_id) { +static inline u8 i2cGetDeviceRegAddr(u8 device_id) { return dev_data[device_id].reg_addr; } @@ -26,7 +26,7 @@ static vu8* reg_data_addrs[] = { (vu8*)(I2C3_REG_OFF + I2C_REG_DATA), }; -inline vu8* i2cGetDataReg(u8 bus_id) { +static inline vu8* i2cGetDataReg(u8 bus_id) { return reg_data_addrs[bus_id]; } @@ -38,22 +38,22 @@ static vu8* reg_cnt_addrs[] = { (vu8*)(I2C3_REG_OFF + I2C_REG_CNT), }; -inline vu8* i2cGetCntReg(u8 bus_id) { +static inline vu8* i2cGetCntReg(u8 bus_id) { return reg_cnt_addrs[bus_id]; } //----------------------------------------------------------------------------- -inline void i2cWaitBusy(u8 bus_id) { +static inline void i2cWaitBusy(u8 bus_id) { while (*i2cGetCntReg(bus_id) & 0x80); } -inline bool i2cGetResult(u8 bus_id) { +static inline u32 i2cGetResult(u8 bus_id) { i2cWaitBusy(bus_id); return (*i2cGetCntReg(bus_id) >> 4) & 1; } -void i2cStop(u8 bus_id, u8 arg0) { +static void i2cStop(u8 bus_id, u8 arg0) { *i2cGetCntReg(bus_id) = (arg0 << 5) | 0xC0; i2cWaitBusy(bus_id); *i2cGetCntReg(bus_id) = 0xC5; @@ -61,14 +61,14 @@ void i2cStop(u8 bus_id, u8 arg0) { //----------------------------------------------------------------------------- -bool i2cSelectDevice(u8 bus_id, u8 dev_reg) { +static u32 i2cSelectDevice(u8 bus_id, u8 dev_reg) { i2cWaitBusy(bus_id); *i2cGetDataReg(bus_id) = dev_reg; *i2cGetCntReg(bus_id) = 0xC2; return i2cGetResult(bus_id); } -bool i2cSelectRegister(u8 bus_id, u8 reg) { +static u32 i2cSelectRegister(u8 bus_id, u8 reg) { i2cWaitBusy(bus_id); *i2cGetDataReg(bus_id) = reg; *i2cGetCntReg(bus_id) = 0xC0; @@ -77,58 +77,7 @@ bool i2cSelectRegister(u8 bus_id, u8 reg) { //----------------------------------------------------------------------------- -u8 i2cReadRegister(u8 dev_id, u8 reg) { - u8 bus_id = i2cGetDeviceBusId(dev_id); - u8 dev_addr = i2cGetDeviceRegAddr(dev_id); - - for (size_t i = 0; i < 8; i++) { - if (i2cSelectDevice(bus_id, dev_addr) && i2cSelectRegister(bus_id, reg)) { - if (i2cSelectDevice(bus_id, dev_addr | 1)) { - i2cWaitBusy(bus_id); - i2cStop(bus_id, 1); - i2cWaitBusy(bus_id); - return *i2cGetDataReg(bus_id); - } - } - *i2cGetCntReg(bus_id) = 0xC5; - i2cWaitBusy(bus_id); - } - return 0xff; -} - -bool i2cReadRegisterBuffer(unsigned int dev_id, int reg, u8* buffer, size_t buf_size) { - u8 bus_id = i2cGetDeviceBusId(dev_id); - u8 dev_addr = i2cGetDeviceRegAddr(dev_id); - - size_t j = 0; - while (!i2cSelectDevice(bus_id, dev_addr) - || !i2cSelectRegister(bus_id, reg) - || !i2cSelectDevice(bus_id, dev_addr | 1)) - { - i2cWaitBusy(bus_id); - *i2cGetCntReg(bus_id) = 0xC5; - i2cWaitBusy(bus_id); - if (++j >= 8) - return false; - } - - if (buf_size != 1) { - for (size_t i = 0; i < buf_size - 1; i++) { - i2cWaitBusy(bus_id); - *i2cGetCntReg(bus_id) = 0xF0; - i2cWaitBusy(bus_id); - buffer[i] = *i2cGetDataReg(bus_id); - } - } - - i2cWaitBusy(bus_id); - *i2cGetCntReg(bus_id) = 0xE1; - i2cWaitBusy(bus_id); - *buffer = *i2cGetDataReg(bus_id); - return true; -} - -bool i2cWriteRegister(u8 dev_id, u8 reg, u8 data) { +u32 i2cWriteRegister(u8 dev_id, u8 reg, u8 data) { u8 bus_id = i2cGetDeviceBusId(dev_id); u8 dev_addr = i2cGetDeviceRegAddr(dev_id); @@ -139,11 +88,11 @@ bool i2cWriteRegister(u8 dev_id, u8 reg, u8 data) { *i2cGetCntReg(bus_id) = 0xC1; i2cStop(bus_id, 0); if (i2cGetResult(bus_id)) - return true; + return 1; } *i2cGetCntReg(bus_id) = 0xC5; i2cWaitBusy(bus_id); } - return false; + return 0; } diff --git a/loader/source/i2c.h b/loader/source/i2c.h index 7377c28..00658ea 100644 --- a/loader/source/i2c.h +++ b/loader/source/i2c.h @@ -15,21 +15,4 @@ #define I2C_DEV_GYRO 10 #define I2C_DEV_IR 13 -u8 i2cGetDeviceBusId(u8 device_id); -u8 i2cGetDeviceRegAddr(u8 device_id); - -vu8* i2cGetDataReg(u8 bus_id); -vu8* i2cGetCntReg(u8 bus_id); - -void i2cWaitBusy(u8 bus_id); -bool i2cGetResult(u8 bus_id); -u8 i2cGetData(u8 bus_id); -void i2cStop(u8 bus_id, u8 arg0); - -bool i2cSelectDevice(u8 bus_id, u8 dev_reg); -bool i2cSelectRegister(u8 bus_id, u8 reg); - -u8 i2cReadRegister(u8 dev_id, u8 reg); -bool i2cWriteRegister(u8 dev_id, u8 reg, u8 data); - -bool i2cReadRegisterBuffer(unsigned int dev_id, int reg, u8* buffer, size_t buf_size); +u32 i2cWriteRegister(u8 dev_id, u8 reg, u8 data); \ No newline at end of file diff --git a/loader/source/main.c b/loader/source/main.c index 7cc0d43..8900b15 100644 --- a/loader/source/main.c +++ b/loader/source/main.c @@ -26,16 +26,16 @@ void main(void){ //Get pressed buttons u16 pressed = HID_PAD; - if(((pressed & BUTTON_B) && loadPayload("/rei/payloads/b.bin")) || - ((pressed & BUTTON_X) && loadPayload("/rei/payloads/x.bin")) || - ((pressed & BUTTON_Y) && loadPayload("/rei/payloads/y.bin")) || - ((pressed & BUTTON_SELECT) && loadPayload("/rei/payloads/select.bin")) || - ((pressed & BUTTON_START) && loadPayload("/rei/payloads/start.bin")) || - ((pressed & BUTTON_RIGHT) && loadPayload("/rei/payloads/right.bin")) || - ((pressed & BUTTON_LEFT) && loadPayload("/rei/payloads/left.bin")) || - ((pressed & BUTTON_UP) && loadPayload("/rei/payloads/up.bin")) || - ((pressed & BUTTON_DOWN) && loadPayload("/rei/payloads/down.bin")) || - loadPayload("/rei/payloads/default.bin")){ + if(((pressed & BUTTON_B) && loadPayload("/aurei/payloads/b.bin")) || + ((pressed & BUTTON_X) && loadPayload("/aurei/payloads/x.bin")) || + ((pressed & BUTTON_Y) && loadPayload("/aurei/payloads/y.bin")) || + ((pressed & BUTTON_SELECT) && loadPayload("/aurei/payloads/select.bin")) || + ((pressed & BUTTON_START) && loadPayload("/aurei/payloads/start.bin")) || + ((pressed & BUTTON_RIGHT) && loadPayload("/aurei/payloads/right.bin")) || + ((pressed & BUTTON_LEFT) && loadPayload("/aurei/payloads/left.bin")) || + ((pressed & BUTTON_UP) && loadPayload("/aurei/payloads/up.bin")) || + ((pressed & BUTTON_DOWN) && loadPayload("/aurei/payloads/down.bin")) || + loadPayload("/aurei/payloads/default.bin")){ //Determine if screen was already inited if(*(vu8 *)0x10141200 == 0x1) initLCD(); ((void (*)())PAYLOAD_ADDRESS)(); diff --git a/loader/source/screeninit.c b/loader/source/screeninit.c index 0bb02c8..349218f 100644 --- a/loader/source/screeninit.c +++ b/loader/source/screeninit.c @@ -2,9 +2,10 @@ #include "i2c.h" void initLCD(void){ - vu32 *const arm11 = (u32 *)0x1FFFFFF8; + vu32 *const arm11 = (vu32 *)0x1FFFFFF8; void __attribute__((naked)) ARM11(void){ + __asm(".word 0xF10C01C0"); *(vu32 *)0x10141200 = 0x1007F; *(vu32 *)0x10202014 = 0x00000001; *(vu32 *)0x1020200C &= 0xFFFEFFFE; @@ -91,6 +92,11 @@ void initLCD(void){ *(vu32 *)0x10400568 = 0x18346500; *(vu32 *)0x1040056c = 0x18346500; + //Set CakeBrah framebuffers + *((vu32 *)0x23FFFE00) = 0x18300000; + *((vu32 *)0x23FFFE04) = 0x18300000; + *((vu32 *)0x23FFFE08) = 0x18346500; + //Clear ARM11 entry offset *arm11 = 0; @@ -100,14 +106,6 @@ void initLCD(void){ ((void (*)())*arm11)(); } - //Set CakeBrah framebuffers - *(vu32 *)0x23FFFE00 = 0x18300000; - *(vu32 *)0x23FFFE04 = 0x18300000; - *(vu32 *)0x23FFFE08 = 0x18346500; - *arm11 = (u32)ARM11; - - //This delay is needed for some reason - for(vu32 i = 0; i < 0x2000; ++i); while(*arm11); } \ No newline at end of file diff --git a/loader/source/types.h b/loader/source/types.h index be2a914..56d82bb 100644 --- a/loader/source/types.h +++ b/loader/source/types.h @@ -6,7 +6,6 @@ #pragma once -#include #include #include diff --git a/reboot/rebootCode.s b/reboot/rebootCode.s index 06409e7..9054edb 100644 --- a/reboot/rebootCode.s +++ b/reboot/rebootCode.s @@ -99,7 +99,7 @@ Memcpy: BX LR FileName: - .dcw "sdmc:/rei/patched_firmware_sys.bin" + .dcw "sdmc:/aurei/patched_firmware_sys.bin" .word 0x0 .pool diff --git a/source/draw.c b/source/draw.c index e3acdc0..26e851d 100644 --- a/source/draw.c +++ b/source/draw.c @@ -32,17 +32,17 @@ void __attribute__((naked)) shutdownLCD(void){ ((void (*)())*arm11)(); } -static void clearScreen(void){ - memset(fb->top_left, 0, 0x46500); - memset(fb->top_right, 0, 0x46500); - memset(fb->bottom, 0, 0x38400); +static void clearScreens(void){ + memset32(fb->top_left, 0, 0x46500); + memset32(fb->top_right, 0, 0x46500); + memset32(fb->bottom, 0, 0x38400); } void loadSplash(void){ - clearScreen(); + clearScreens(); //Don't delay boot if no splash image is on the SD - if(fileRead(fb->top_left, "/rei/splash.bin", 0x46500) + - fileRead(fb->bottom, "/rei/splashbottom.bin", 0x38400)){ - u64 i = 0xFFFFFF; while(--i) __asm("mov r0, r0"); //Less Ghetto sleep func + if(fileRead(fb->top_left, "/aurei/splash.bin", 0x46500) + + fileRead(fb->bottom, "/aurei/splashbottom.bin", 0x38400)){ + u64 i = 0x1300000; while(--i) __asm("mov r0, r0"); //Less Ghetto sleep func } } \ No newline at end of file diff --git a/source/emunand.c b/source/emunand.c index f380172..53485bc 100644 --- a/source/emunand.c +++ b/source/emunand.c @@ -22,6 +22,11 @@ void getEmunandSect(u32 *off, u32 *head, u32 emuNAND){ } //Fallback to the first emuNAND if there's no second one else if(emuNAND == 2) getEmunandSect(off, head, 1); + //Check if a RedNAND is present + else if(sdmmc_sdcard_readsectors(1, 1, temp) == 0){ + if(*(u32 *)(temp + 0x100) != NCSD_MAGIC) + *head = 0; + } } } diff --git a/source/fatfs/ffconf.h b/source/fatfs/ffconf.h index 4b863c6..e664a06 100644 --- a/source/fatfs/ffconf.h +++ b/source/fatfs/ffconf.h @@ -23,7 +23,7 @@ / and optional writing functions as well. */ -#define _FS_MINIMIZE 0 +#define _FS_MINIMIZE 3 /* This option defines minimization level to remove some basic API functions. / / 0: All basic functions are enabled. diff --git a/source/firm.c b/source/firm.c index 65a9bfd..9f9bec3 100755 --- a/source/firm.c +++ b/source/firm.c @@ -32,7 +32,7 @@ void setupCFW(void){ //Retrieve the last booted FIRM u8 previousFirm = CFG_BOOTENV; u32 overrideConfig = 0; - const char lastConfigPath[] = "rei/lastbootcfg"; + const char lastConfigPath[] = "aurei/lastbootcfg"; //Detect the console being used if(PDN_MPCORE_CFG == 1) console = 0; @@ -41,10 +41,10 @@ void setupCFW(void){ pressed = HID_PAD; //Determine if A9LH is installed - if(a9lhBoot || fileExists("/rei/installeda9lh")){ + if(a9lhBoot || fileExists("/aurei/installeda9lh")){ a9lhSetup = 1; //Check flag for > 9.2 SysNAND - if(fileExists("/rei/updatedsysnand")) updatedSys = 1; + if(fileExists("/aurei/updatedsysnand")) updatedSys = 1; } //If booting with A9LH and it's a MCU reboot, try to force boot options @@ -92,14 +92,14 @@ void setupCFW(void){ } } - if(mode) firmPathPatched = emuNAND ? (emuNAND == 1 ? "/rei/patched_firmware_emu.bin" : - "/rei/patched_firmware_em2.bin") : - "/rei/patched_firmware_sys.bin"; + if(mode) firmPathPatched = emuNAND ? (emuNAND == 1 ? "/aurei/patched_firmware_emu.bin" : + "/aurei/patched_firmware_em2.bin") : + "/aurei/patched_firmware_sys.bin"; //Skip decrypting and patching FIRM - if(fileExists("/rei/usepatchedfw")){ + if(fileExists("/aurei/usepatchedfw")){ //Only needed with this flag - if(!mode) firmPathPatched = "/rei/patched_firmware90.bin"; + if(!mode) firmPathPatched = "/aurei/patched_firmware90.bin"; if(fileExists(firmPathPatched)) usePatchedFirm = 1; } } @@ -118,7 +118,7 @@ u32 loadFirm(void){ //Load FIRM from SD else{ const char *path = usePatchedFirm ? firmPathPatched : - (mode ? "/rei/firmware.bin" : "/rei/firmware90.bin"); + (mode ? "/aurei/firmware.bin" : "/aurei/firmware90.bin"); firmSize = fileSize(path); if(!firmSize) return 0; fileRead((u8 *)firmLocation, path, firmSize); @@ -147,7 +147,7 @@ static u32 loadEmu(void){ emuCodeOffset; //Read emunand code from SD - const char path[] = "/rei/emunand/emunand.bin"; + const char path[] = "/aurei/emunand/emunand.bin"; u32 size = fileSize(path); if(!size) return 0; if(!console || !mode) nandRedir[5] = 0xA4; @@ -168,6 +168,9 @@ static u32 loadEmu(void){ *pos_offset = emuOffset; *pos_header = emuHeader; + //No emuNAND detected + if(!*pos_header) return 0; + //Patch emuNAND code in memory for O3DS and 9.0 N3DS if(!console || !mode){ void *pos_instr = memsearch((void *)emuCodeOffset, "\xA6\x01\x08\x30", size, 4); @@ -219,7 +222,7 @@ u32 patchFirm(void){ fOpenOffset; //Read reboot code from SD - const char path[] = "/rei/reboot/reboot.bin"; + const char path[] = "/aurei/reboot/reboot.bin"; u32 size = fileSize(path); if(!size) return 0; getReboot(firmLocation, firmSize, &rebootOffset); diff --git a/source/i2c.c b/source/i2c.c new file mode 100644 index 0000000..6f03579 --- /dev/null +++ b/source/i2c.c @@ -0,0 +1,98 @@ +#include "i2c.h" + +//----------------------------------------------------------------------------- + +static const struct { u8 bus_id, reg_addr; } dev_data[] = { + {0, 0x4A}, {0, 0x7A}, {0, 0x78}, + {1, 0x4A}, {1, 0x78}, {1, 0x2C}, + {1, 0x2E}, {1, 0x40}, {1, 0x44}, + {2, 0xD6}, {2, 0xD0}, {2, 0xD2}, + {2, 0xA4}, {2, 0x9A}, {2, 0xA0}, +}; + +static inline u8 i2cGetDeviceBusId(u8 device_id) { + return dev_data[device_id].bus_id; +} + +static inline u8 i2cGetDeviceRegAddr(u8 device_id) { + return dev_data[device_id].reg_addr; +} + +//----------------------------------------------------------------------------- + +static vu8* reg_data_addrs[] = { + (vu8*)(I2C1_REG_OFF + I2C_REG_DATA), + (vu8*)(I2C2_REG_OFF + I2C_REG_DATA), + (vu8*)(I2C3_REG_OFF + I2C_REG_DATA), +}; + +static inline vu8* i2cGetDataReg(u8 bus_id) { + return reg_data_addrs[bus_id]; +} + +//----------------------------------------------------------------------------- + +static vu8* reg_cnt_addrs[] = { + (vu8*)(I2C1_REG_OFF + I2C_REG_CNT), + (vu8*)(I2C2_REG_OFF + I2C_REG_CNT), + (vu8*)(I2C3_REG_OFF + I2C_REG_CNT), +}; + +static inline vu8* i2cGetCntReg(u8 bus_id) { + return reg_cnt_addrs[bus_id]; +} + +//----------------------------------------------------------------------------- + +static inline void i2cWaitBusy(u8 bus_id) { + while (*i2cGetCntReg(bus_id) & 0x80); +} + +static inline u32 i2cGetResult(u8 bus_id) { + i2cWaitBusy(bus_id); + return (*i2cGetCntReg(bus_id) >> 4) & 1; +} + +static void i2cStop(u8 bus_id, u8 arg0) { + *i2cGetCntReg(bus_id) = (arg0 << 5) | 0xC0; + i2cWaitBusy(bus_id); + *i2cGetCntReg(bus_id) = 0xC5; +} + +//----------------------------------------------------------------------------- + +static u32 i2cSelectDevice(u8 bus_id, u8 dev_reg) { + i2cWaitBusy(bus_id); + *i2cGetDataReg(bus_id) = dev_reg; + *i2cGetCntReg(bus_id) = 0xC2; + return i2cGetResult(bus_id); +} + +static u32 i2cSelectRegister(u8 bus_id, u8 reg) { + i2cWaitBusy(bus_id); + *i2cGetDataReg(bus_id) = reg; + *i2cGetCntReg(bus_id) = 0xC0; + return i2cGetResult(bus_id); +} + +//----------------------------------------------------------------------------- + +u32 i2cWriteRegister(u8 dev_id, u8 reg, u8 data) { + u8 bus_id = i2cGetDeviceBusId(dev_id); + u8 dev_addr = i2cGetDeviceRegAddr(dev_id); + + for (int i = 0; i < 8; i++) { + if (i2cSelectDevice(bus_id, dev_addr) && i2cSelectRegister(bus_id, reg)) { + i2cWaitBusy(bus_id); + *i2cGetDataReg(bus_id) = data; + *i2cGetCntReg(bus_id) = 0xC1; + i2cStop(bus_id, 0); + if (i2cGetResult(bus_id)) + return 1; + } + *i2cGetCntReg(bus_id) = 0xC5; + i2cWaitBusy(bus_id); + } + + return 0; +} diff --git a/source/i2c.h b/source/i2c.h new file mode 100644 index 0000000..00658ea --- /dev/null +++ b/source/i2c.h @@ -0,0 +1,18 @@ +#pragma once + +#include "types.h" + +#define I2C1_REG_OFF 0x10161000 +#define I2C2_REG_OFF 0x10144000 +#define I2C3_REG_OFF 0x10148000 + +#define I2C_REG_DATA 0 +#define I2C_REG_CNT 1 +#define I2C_REG_CNTEX 2 +#define I2C_REG_SCL 4 + +#define I2C_DEV_MCU 3 +#define I2C_DEV_GYRO 10 +#define I2C_DEV_IR 13 + +u32 i2cWriteRegister(u8 dev_id, u8 reg, u8 data); \ No newline at end of file diff --git a/source/loader.c b/source/loader.c index d3dae58..e31a10f 100644 --- a/source/loader.c +++ b/source/loader.c @@ -8,7 +8,7 @@ #define PAYLOAD_ADDRESS 0x24F00000 void loadPayload(void){ - if(fileExists("rei/payloads/default.bin") && - fileRead((u8 *)PAYLOAD_ADDRESS, "rei/loader.bin", 0)) + if(fileExists("aurei/payloads/default.bin") && + fileRead((u8 *)PAYLOAD_ADDRESS, "aurei/loader.bin", 0)) ((void (*)())PAYLOAD_ADDRESS)(); } \ No newline at end of file diff --git a/source/main.c b/source/main.c index c826738..e071a50 100644 --- a/source/main.c +++ b/source/main.c @@ -8,6 +8,7 @@ #include "fs.h" #include "firm.h" +#include "i2c.h" void main(void){ mountSD(); @@ -18,4 +19,8 @@ void startCFW(void){ if(!loadFirm()) return; if(!patchFirm()) return; launchFirm(); +} + +void shutdown(void){ + i2cWriteRegister(I2C_DEV_MCU, 0x20, 1); } \ No newline at end of file diff --git a/source/memory.c b/source/memory.c index a66f88d..c53840a 100644 --- a/source/memory.c +++ b/source/memory.c @@ -19,6 +19,12 @@ void memset(void *dest, int filler, u32 size){ destc[i] = (u8)filler; } +void memset32(void *dest, u32 filler, u32 size){ + u32 *dest32 = (u32 *)dest; + for (u32 i = 0; i < size / 4; i++) + dest32[i] = filler; +} + int memcmp(const void *buf1, const void *buf2, u32 size){ const u8 *buf1c = (const u8 *)buf1; const u8 *buf2c = (const u8 *)buf2; diff --git a/source/memory.h b/source/memory.h index c3d3767..8d9c7a8 100644 --- a/source/memory.h +++ b/source/memory.h @@ -10,5 +10,6 @@ void memcpy(void *dest, const void *src, u32 size); void memset(void *dest, int filler, u32 size); +void memset32(void *dest, u32 filler, u32 size); int memcmp(const void *buf1, const void *buf2, u32 size); void *memsearch(void *start_pos, const void *search, u32 size, u32 size_search); \ No newline at end of file diff --git a/source/start.s b/source/start.s index faff078..1ef54f0 100644 --- a/source/start.s +++ b/source/start.s @@ -10,7 +10,7 @@ _start: mcr p15, 0, r0, c5, c0, 2 @ write data access mcr p15, 0, r0, c5, c0, 3 @ write instruction access - @ Set MPU permissions + @ Set MPU permissions and cache settings ldr r0, =0xFFFF001D @ ffff0000 32k ldr r1, =0x01FF801D @ 01ff8000 32k ldr r2, =0x08000027 @ 08000000 1M @@ -27,6 +27,11 @@ _start: mcr p15, 0, r5, c6, c5, 0 mcr p15, 0, r6, c6, c6, 0 mcr p15, 0, r7, c6, c7, 0 + mov r4, #0x25 + mov r0, #0x5 + mcr p15, 0, r4, c2, c0, 0 @ data cacheable + mcr p15, 0, r4, c2, c0, 1 @ instruction cacheable + mcr p15, 0, r0, c3, c0, 0 @ data bufferable @ Enable caches mrc p15, 0, r0, c1, c0, 0 @ read control register @@ -48,13 +53,11 @@ _start: bl main - @ Set cache settings - mov r0, #0x25 - mcr p15, 0, r0, c3, c0, 0 @ Write bufferable 0, 2, 5 - mcr p15, 0, r0, c2, c0, 0 @ Data cacheable 0, 2, 5 - mcr p15, 0, r0, c2, c0, 1 @ Inst cacheable 0, 2, 5 + mcr p15, 0, r4, c3, c0, 0 @ data bufferable bl startCFW + bl shutdown + .die: b .die