From bc1fac4b9ea14669375043a0c737b6215dd1cc29 Mon Sep 17 00:00:00 2001 From: Fazana <52551480+FazanaJ@users.noreply.github.com> Date: Mon, 23 Aug 2021 12:10:03 +0100 Subject: [PATCH] Farcall tweaks You can now safely store code in global banks without the game murdering it. Also fixed some `memory.c` warnings --- include/segment_symbols.h | 1 + levels/scripts.c | 2 +- sm64.ld | 10 +++++++++- src/engine/level_script.c | 14 ++++++++++++-- src/game/farcall_helpers.h | 1 + src/game/memory.c | 8 ++++---- 6 files changed, 28 insertions(+), 8 deletions(-) diff --git a/include/segment_symbols.h b/include/segment_symbols.h index 22ae7246..93da9cfa 100644 --- a/include/segment_symbols.h +++ b/include/segment_symbols.h @@ -45,6 +45,7 @@ DECLARE_ACTOR_SEGMENT(group17) DECLARE_SEGMENT(entry) DECLARE_SEGMENT(engine) DECLARE_SEGMENT(behavior) +DECLARE_NOLOAD(behavior) DECLARE_SEGMENT(scripts) DECLARE_SEGMENT(goddard) DECLARE_SEGMENT(framebuffers) diff --git a/levels/scripts.c b/levels/scripts.c index d0f64006..48c7c2e1 100644 --- a/levels/scripts.c +++ b/levels/scripts.c @@ -63,7 +63,7 @@ const LevelScript level_main_scripts_entry[] = { LOAD_YAY0(/*seg*/ 0x03, _common1_yay0SegmentRomStart, _common1_yay0SegmentRomEnd), LOAD_RAW_WITH_CODE( /*seg*/ 0x17, _group0_geoSegmentRomStart, _group0_geoSegmentRomEnd, _group0_geoSegmentBssStart, _group0_geoSegmentBssEnd), LOAD_RAW_WITH_CODE( /*seg*/ 0x16, _common1_geoSegmentRomStart, _common1_geoSegmentRomEnd, _common1_geoSegmentBssStart, _common1_geoSegmentBssEnd), - LOAD_RAW( /*seg*/ 0x13, _behaviorSegmentRomStart, _behaviorSegmentRomEnd), + LOAD_RAW_WITH_CODE( /*seg*/ 0x13, _behaviorSegmentRomStart, _behaviorSegmentRomEnd, _behaviorSegmentBssStart, _behaviorSegmentBssEnd), ALLOC_LEVEL_POOL(), LOAD_MODEL_FROM_GEO(MODEL_MARIO, mario_geo), LOAD_MODEL_FROM_GEO(MODEL_SMOKE, smoke_geo), diff --git a/sm64.ld b/sm64.ld index a36692d3..2b843e6a 100755 --- a/sm64.ld +++ b/sm64.ld @@ -314,9 +314,17 @@ SECTIONS /* use segmented addressing for behaviors */ BEGIN_SEG(behavior, 0x13000000) { - KEEP(BUILD_DIR/data/behavior_data.o(.data)); + KEEP(BUILD_DIR/data/behavior_data.o(.data*)); + KEEP(BUILD_DIR/data/behavior_data.o(.rodata*)); + KEEP(BUILD_DIR/data/behavior_data.o(.text)); } END_SEG(behavior) + BEGIN_NOLOAD(behavior) + { + KEEP(BUILD_DIR/data/behavior_data.o(.bss*)); + } + END_NOLOAD(behavior) + /* 0x8016F000 21D7D0-255EC0 [386F0] */ BEGIN_SEG(goddard, RAM_END - GODDARD_SIZE) diff --git a/src/engine/level_script.c b/src/engine/level_script.c index ec2d4693..ad327cdb 100644 --- a/src/engine/level_script.c +++ b/src/engine/level_script.c @@ -315,13 +315,23 @@ static void level_cmd_init_level(void) { extern s32 gTlbEntries; +//This clears all the temporary bank TLB maps. group0, common1 and behavourdata are always loaded, +//and they're also loaded first, so that means we just leave the first 3 indexes mapped. +void unmap_tlbs(void) +{ + while (gTlbEntries > 3) + { + osUnmapTLB(gTlbEntries); + gTlbEntries--; + } +} + static void level_cmd_clear_level(void) { clear_objects(); clear_area_graph_nodes(); clear_areas(); main_pool_pop_state(); - gTlbEntries = 0; - osUnmapTLBAll(); + unmap_tlbs(); sCurrentCmd = CMD_NEXT; } diff --git a/src/game/farcall_helpers.h b/src/game/farcall_helpers.h index 4e06b02d..99a9cc0f 100644 --- a/src/game/farcall_helpers.h +++ b/src/game/farcall_helpers.h @@ -20,6 +20,7 @@ #include "level_update.h" #include "mario.h" #include "save_file.h" +#include "game_init.h" #define o gCurrentObject diff --git a/src/game/memory.c b/src/game/memory.c index 838ac185..16d13ec5 100644 --- a/src/game/memory.c +++ b/src/game/memory.c @@ -28,7 +28,7 @@ #define ALIGN4(val) (((val) + 0x3) & ~0x3) #define ALIGN8(val) (((val) + 0x7) & ~0x7) #define ALIGN16(val) (((val) + 0xF) & ~0xF) -#define ALIGN(val, alignment) (((val) + ((alignment) - 1)) & ~((alignment) - 1)) +//#define ALIGN(val, alignment) (((val) + ((alignment) - 1)) & ~((alignment) - 1)) struct MainPoolState { u32 freeSpace; @@ -286,7 +286,7 @@ void dma_read(u8 *dest, u8 *srcStart, u8 *srcEnd) { * Perform a DMA read from ROM, allocating space in the memory pool to write to. * Return the destination address. */ -static void *dynamic_dma_read(u8 *srcStart, u8 *srcEnd, u32 side, u32 alignment, u32 bssLength) { +void *dynamic_dma_read(u8 *srcStart, u8 *srcEnd, u32 side, u32 alignment, u32 bssLength) { void *dest; u32 size = ALIGN16(srcEnd - srcStart); u32 offset = 0; @@ -652,12 +652,12 @@ void *alloc_display_list(u32 size) { static struct DmaTable *load_dma_table_address(u8 *srcAddr) { struct DmaTable *table = dynamic_dma_read(srcAddr, srcAddr + sizeof(u32), - MEMORY_POOL_LEFT, NULL, NULL); + MEMORY_POOL_LEFT, 0, 0); u32 size = table->count * sizeof(struct OffsetSizePair) + sizeof(struct DmaTable) - sizeof(struct OffsetSizePair); main_pool_free(table); - table = dynamic_dma_read(srcAddr, srcAddr + size, MEMORY_POOL_LEFT, NULL, NULL); + table = dynamic_dma_read(srcAddr, srcAddr + size, MEMORY_POOL_LEFT, 0, 0); table->srcAddr = srcAddr; return table; }