fix issues

This commit is contained in:
Yanis42
2024-01-31 17:51:38 +01:00
parent 7ff9daeffd
commit eef0f9b2f3
31 changed files with 110 additions and 1500 deletions

1
.gitignore vendored
View File

@@ -28,6 +28,7 @@ docs/doxygen/
*.dump
out.txt
*.ram
common-key.bin
# Tool artifacts
tools/mipspro7.2_compiler/

View File

View File

@@ -1 +0,0 @@
5831385a7f216370cdbea55616b12fed oot-gc-eu-mq-dbg-compressed.z64

View File

@@ -1 +0,0 @@
f0b7f35375f9cc8ca1b2d59d78e35405 oot-gc-eu-mq-dbg.z64

View File

View File

@@ -1 +0,0 @@
1618403427e4344a57833043db5ce3c3 oot-gc-eu-mq-compressed.z64

View File

@@ -1 +0,0 @@
1a438f4235f8038856971c14a798122a oot-gc-eu-mq.z64

View File

View File

@@ -10,6 +10,7 @@ from pathlib import Path
EXTRACTED_ASSETS_NAMEFILE = ".extracted-assets.json"
VERSION = ""
def SignalHandler(sig, frame):
@@ -28,7 +29,7 @@ def ExtractFile(xmlPath, outputPath, outputSourcePath):
Path(outputPath).mkdir(parents=True, exist_ok=True)
Path(outputSourcePath).mkdir(parents=True, exist_ok=True)
execStr = f"{zapdPath} e -eh -i {xmlPath} -b baseroms/gc-eu-mq-dbg/segments -o {outputPath} -osf {outputSourcePath} -gsf 1 -rconf {configPath} {ZAPDArgs}"
execStr = f"{zapdPath} e -eh -i {xmlPath} -b baseroms/{VERSION}/segments -o {outputPath} -osf {outputSourcePath} -gsf 1 -rconf {configPath} {ZAPDArgs}"
if "overlays" in xmlPath:
execStr += " --static"
@@ -100,8 +101,12 @@ def main():
parser.add_argument("-j", "--jobs", help="Number of cpu cores to extract with.")
parser.add_argument("-u", "--unaccounted", help="Enables ZAPD unaccounted detector warning system.", action="store_true")
parser.add_argument("-Z", help="Pass the argument on to ZAPD, e.g. `-ZWunaccounted` to warn about unaccounted blocks in XMLs. Each argument should be passed separately, *without* the leading dash.", metavar="ZAPD_ARG", action="append")
parser.add_argument("-v", "--version", help="OoT Version", choices=["gc-eu-mq-dbg", "hacker-mq"])
args = parser.parse_args()
global VERSION
VERSION = args.version
global ZAPDArgs
ZAPDArgs = processZAPDArgs(args.Z) if args.Z else ""
@@ -141,7 +146,7 @@ def main():
if extract_text_path is not None or extract_staff_text_path is not None:
print("Extracting text")
from tools import msgdis
msgdis.extract_all_text(extract_text_path, extract_staff_text_path)
msgdis.extract_all_text(extract_text_path, extract_staff_text_path, VERSION)
xmlFiles = []
for currentPath, _, files in os.walk(os.path.join("assets", "xml")):

View File

@@ -1,6 +1,7 @@
#!/usr/bin/python3
import struct
import argparse
from multiprocessing import Pool, cpu_count
from pathlib import Path
@@ -1581,6 +1582,20 @@ def ExtractFunc(i):
#####################################################################
def main():
description = "Extract data from baserom."
parser = argparse.ArgumentParser(description=description)
parser.add_argument("version", help="Version of the game to extract.", choices=["gc-eu-mq-dbg", "hacker-mq"])
args = parser.parse_args()
version = args.version
global ROM_FILE_PATH
global SEGMENTS_PATH
if version == "hacker-mq":
ROM_FILE_PATH = Path(f'baseroms/{version}/baserom-decompressed.z64')
SEGMENTS_PATH = Path(f'baseroms/{version}/segments/')
SEGMENTS_PATH.mkdir(parents=True, exist_ok=True)
# read baserom data

View File

@@ -30,7 +30,7 @@ APPLY_OPTS = "--format --style=file"
# Compiler options used with Clang-Tidy
# Normal warnings are disabled with -Wno-everything to focus only on tidying
INCLUDES = "-Iinclude -Isrc -Ibuild/gc-eu-mq-dbg -I."
INCLUDES = "-Iinclude -Isrc -Ibuild/gc-eu-mq-dbg -Ibuild/hacker-mq -I."
DEFINES = "-D_LANGUAGE_C -DNON_MATCHING"
COMPILER_OPTS = f"-fno-builtin -std=gnu90 -m32 -Wno-everything {INCLUDES} {DEFINES}"

View File

@@ -9,7 +9,7 @@ import mapfile_parser
def symInfoMain():
parser = argparse.ArgumentParser(description="Display various information about a symbol or address.")
parser.add_argument("symname", help="symbol name or VROM/VRAM address to lookup")
parser.add_argument("-v", "--oot-version", help="Which version should be processed", default="gc-eu-mq-dbg")
parser.add_argument("-v", "--oot-version", help="Which version should be processed", default="hacker-mq")
parser.add_argument("-e", "--expected", dest="use_expected", action="store_true", help="use the map file in expected/build/ instead of build/")
args = parser.parse_args()

View File

@@ -1,5 +1,5 @@
CFLAGS := -Wall -Wextra -pedantic -std=c99 -g -O2
PROGRAMS := elf2rom makeromfs mkdmadata mkldscript reloc_prereq vtxdis yaz0
PROGRAMS := elf2rom makeromfs mkdmadata mkldscript reloc_prereq
ifeq ($(shell command -v clang >/dev/null 2>&1; echo $$?),0)
CC := clang
@@ -20,11 +20,20 @@ endif
all: $(PROGRAMS)
$(MAKE) -C ZAPD
$(MAKE) -C fado
ifeq ($(wildcard ./gzinject/Makefile),)
cd ./gzinject && ./configure
endif
$(MAKE) -C gzinject
$(MAKE) -C z64compress
clean:
$(RM) $(PROGRAMS) $(addsuffix .exe,$(PROGRAMS))
$(MAKE) -C ZAPD clean
$(MAKE) -C fado clean
ifneq ($(wildcard ./gzinject/Makefile),)
$(MAKE) -C gzinject clean
endif
$(MAKE) -C z64compress clean
distclean: clean
@@ -35,8 +44,6 @@ makeromfs_SOURCES := makeromfs.c n64chksum.c util.c
mkdmadata_SOURCES := mkdmadata.c spec.c util.c
mkldscript_SOURCES := mkldscript.c spec.c util.c
reloc_prereq_SOURCES := reloc_prereq.c spec.c util.c
vtxdis_SOURCES := vtxdis.c
yaz0_SOURCES := yaz0tool.c yaz0.c util.c
define COMPILE =

View File

@@ -1,177 +0,0 @@
#!/usr/bin/env python3
import argparse
import os
import sys
from collections import OrderedDict
gAddressWidth = 18 # if your ld >= 2.40 change this to 10
script_dir = os.path.dirname(os.path.realpath(__file__))
root_dir = script_dir + "/../"
asm_dir = root_dir + "asm/non_matchings/overlays/actors"
build_dir = root_dir + "build/gc-eu-mq-dbg/"
def read_rom():
with open("baseroms/gc-eu-mq-dbg/baserom-decompressed.z64", "rb") as f:
return f.read()
def find_dir(query):
for root, dirs, files in os.walk(asm_dir):
for d in dirs:
if d == query:
return os.path.join(root, d)
return None
def get_all_s_files():
ret = set()
for root, dirs, files in os.walk(asm_dir):
for f in files:
if f.endswith(".s"):
ret.add(f[:-2])
return ret
def get_symbol_bytes(offsets, func):
if func not in offsets or "start" not in offsets[func] or "end" not in offsets[func]:
return None
start = offsets[func]["start"]
end = offsets[func]["end"]
return list(rom_bytes[start:end])
def parse_map(fname):
ram_offset = None
cur_file = "<no file>"
syms = {}
prev_sym = None
prev_line = ""
with open(fname) as f:
for line in f:
if "load address" in line:
if "noload" in line or "noload" in prev_line:
ram_offset = None
continue
ram = int(line[16 : 16 + gAddressWidth], 0)
rom = int(line[16 + gAddressWidth + 25 : 16 + gAddressWidth + 25 + gAddressWidth], 0)
ram_offset = ram - rom
continue
prev_line = line
if (
ram_offset is None
or "=" in line
or "*fill*" in line
or " 0x" not in line
):
continue
ram = int(line[16 : 16 + gAddressWidth], 0)
rom = ram - ram_offset
fn = line.split()[-1]
if "0x" in fn:
ram_offset = None
elif "/" in fn:
cur_file = fn
else:
syms[fn] = (rom, cur_file, prev_sym, ram)
prev_sym = fn
return syms
def get_map_offsets(syms):
offsets = {}
for sym in syms:
prev_sym = syms[sym][2]
if sym not in offsets:
offsets[sym] = {}
if prev_sym not in offsets:
offsets[prev_sym] = {}
offsets[sym]["start"] = syms[sym][0]
offsets[prev_sym]["end"] = syms[sym][0]
return offsets
def diff_syms(qb, tb):
if len(tb) < 8:
return 0
if len(qb) > len(tb):
larger = qb
smaller = tb
else:
larger = tb
smaller = qb
len_ratio = len(smaller) / len(larger)
n_bytes = len(smaller)
matches = 0
for i in range(0, n_bytes, 4):
if smaller[i] == larger[i]:
matches += 4
return (matches / n_bytes) * len_ratio
def get_matches(query):
query_bytes = get_symbol_bytes(map_offsets, query)
if query_bytes is None:
sys.exit("Symbol '" + query + "' not found")
ret = {}
for symbol in map_offsets:
if symbol is not None and query != symbol:
target_bytes = get_symbol_bytes(map_offsets, symbol)
if target_bytes is not None:
score = diff_syms(query_bytes, target_bytes)
if score >= args.threshold:
ret[symbol] = score
return OrderedDict(sorted(ret.items(), key=lambda kv: kv[1], reverse=True))
def do_query(query):
matches = get_matches(query)
num_matches = len(matches)
if num_matches == 0:
print(query + " - found no matches")
return
i = 0
more_str = ":"
if args.num_out < num_matches:
more_str = " (showing only " + str(args.num_out) + "):"
print(query + " - found " + str(num_matches) + " matches total" + more_str)
for match in matches:
if i == args.num_out:
break
match_str = "{:.2f} - {}".format(matches[match], match)
if match not in s_files:
match_str += " (decompiled)"
print(match_str)
i += 1
print()
parser = argparse.ArgumentParser(description="Tools to assist with decomp")
parser.add_argument("query", help="function or file")
parser.add_argument("--threshold", help="score threshold between 0 and 1 (higher is more restrictive)", type=float, default=0.95, required=False)
parser.add_argument("--num-out", help="number of functions to display", type=int, default=10, required=False)
args = parser.parse_args()
rom_bytes = read_rom()
map_syms = parse_map(build_dir + "z64.map")
map_offsets = get_map_offsets(map_syms)
s_files = get_all_s_files()
query_dir = find_dir(args.query)
if query_dir is not None:
files = os.listdir(query_dir)
for f_name in files:
do_query(f_name[:-2])
else:
do_query(args.query)

View File

@@ -35,11 +35,13 @@ def decompress(data: bytes, is_zlib_compressed: bool) -> bytes:
FILE_TABLE_OFFSET = {
"gc-eu-mq": 0x07170,
"gc-eu-mq-dbg": 0x12F70,
"hacker-mq": 0x12F70,
}
VERSIONS_MD5S = {
"gc-eu-mq": "1a438f4235f8038856971c14a798122a",
"gc-eu-mq-dbg": "f0b7f35375f9cc8ca1b2d59d78e35405",
"hacker-mq": "f0b7f35375f9cc8ca1b2d59d78e35405",
}
@@ -153,7 +155,7 @@ def byte_swap(file_content: bytearray) -> bytearray:
def per_version_fixes(file_content: bytearray, version: str) -> bytearray:
if version == "gc-eu-mq-dbg":
if version in {"gc-eu-mq-dbg", "hacker-mq"}:
# Strip the overdump
print("Stripping overdump...")
file_content = file_content[0:0x3600000]
@@ -256,7 +258,7 @@ def main():
f"Error: Expected a hash of {correct_str_hash} but got {str_hash}. The baserom has probably been tampered, find a new one"
)
if version == "gc-eu-mq-dbg":
if version in {"gc-eu-mq-dbg", "hacker-mq"}:
if str_hash == "32fe2770c0f9b1a9cd2a4d449348c1cb":
print(
"The provided baserom is a rom which has been edited with ZeldaEdit and is not suitable for use with decomp. Find a new one."

View File

@@ -1,256 +0,0 @@
#!/usr/bin/env python3
import struct, sys
item_ids = {
0x00 : "ITEM_DEKU_STICK",
0x01 : "ITEM_DEKU_NUT",
0x02 : "ITEM_BOMB",
0x03 : "ITEM_BOW",
0x04 : "ITEM_ARROW_FIRE",
0x05 : "ITEM_DINS_FIRE",
0x06 : "ITEM_SLINGSHOT",
0x07 : "ITEM_OCARINA_FAIRY",
0x08 : "ITEM_OCARINA_OF_TIME",
0x09 : "ITEM_BOMBCHU",
0x0A : "ITEM_HOOKSHOT",
0x0B : "ITEM_LONGSHOT",
0x0C : "ITEM_ARROW_ICE",
0x0D : "ITEM_FARORES_WIND",
0x0E : "ITEM_BOOMERANG",
0x0F : "ITEM_LENS_OF_TRUTH",
0x10 : "ITEM_MAGIC_BEAN",
0x11 : "ITEM_HAMMER",
0x12 : "ITEM_ARROW_LIGHT",
0x13 : "ITEM_NAYRUS_LOVE",
0x14 : "ITEM_BOTTLE_EMPTY",
0x15 : "ITEM_BOTTLE_POTION_RED",
0x16 : "ITEM_BOTTLE_POTION_GREEN",
0x17 : "ITEM_BOTTLE_POTION_BLUE",
0x18 : "ITEM_BOTTLE_FAIRY",
0x19 : "ITEM_BOTTLE_FISH",
0x1A : "ITEM_BOTTLE_MILK_FULL",
0x1B : "ITEM_BOTTLE_RUTOS_LETTER",
0x1C : "ITEM_BOTTLE_BLUE_FIRE",
0x1D : "ITEM_BOTTLE_BUG",
0x1E : "ITEM_BOTTLE_BIG_POE",
0x1F : "ITEM_BOTTLE_MILK_HALF",
0x20 : "ITEM_BOTTLE_POE",
0x21 : "ITEM_WEIRD_EGG",
0x22 : "ITEM_CHICKEN",
0x23 : "ITEM_ZELDAS_LETTER",
0x24 : "ITEM_MASK_KEATON",
0x25 : "ITEM_MASK_SKULL",
0x26 : "ITEM_MASK_SPOOKY",
0x27 : "ITEM_MASK_BUNNY_HOOD",
0x28 : "ITEM_MASK_GORON",
0x29 : "ITEM_MASK_ZORA",
0x2A : "ITEM_MASK_GERUDO",
0x2B : "ITEM_MASK_TRUTH",
0x2C : "ITEM_SOLD_OUT",
0x2D : "ITEM_POCKET_EGG",
0x2E : "ITEM_POCKET_CUCCO",
0x2F : "ITEM_COJIRO",
0x30 : "ITEM_ODD_MUSHROOM",
0x31 : "ITEM_ODD_POTION",
0x32 : "ITEM_POACHERS_SAW",
0x33 : "ITEM_BROKEN_GORONS_SWORD",
0x34 : "ITEM_PRESCRIPTION",
0x35 : "ITEM_EYEBALL_FROG",
0x36 : "ITEM_EYE_DROPS",
0x37 : "ITEM_CLAIM_CHECK",
0x38 : "ITEM_BOW_FIRE",
0x39 : "ITEM_BOW_ICE",
0x3A : "ITEM_BOW_LIGHT",
0x3B : "ITEM_SWORD_KOKIRI",
0x3C : "ITEM_SWORD_MASTER",
0x3D : "ITEM_SWORD_BIGGORON",
0x3E : "ITEM_SHIELD_DEKU",
0x3F : "ITEM_SHIELD_HYLIAN",
0x40 : "ITEM_SHIELD_MIRROR",
0x41 : "ITEM_TUNIC_KOKIRI",
0x42 : "ITEM_TUNIC_GORON",
0x43 : "ITEM_TUNIC_ZORA",
0x44 : "ITEM_BOOTS_KOKIRI",
0x45 : "ITEM_BOOTS_IRON",
0x46 : "ITEM_BOOTS_HOVER",
0x47 : "ITEM_BULLET_BAG_30",
0x48 : "ITEM_BULLET_BAG_40",
0x49 : "ITEM_BULLET_BAG_50",
0x4A : "ITEM_QUIVER_30",
0x4B : "ITEM_QUIVER_40",
0x4C : "ITEM_QUIVER_50",
0x4D : "ITEM_BOMB_BAG_20",
0x4E : "ITEM_BOMB_BAG_30",
0x4F : "ITEM_BOMB_BAG_40",
0x50 : "ITEM_STRENGTH_GORONS_BRACELET",
0x51 : "ITEM_STRENGTH_SILVER_GAUNTLETS",
0x52 : "ITEM_STRENGTH_GOLD_GAUNTLETS",
0x53 : "ITEM_SCALE_SILVER",
0x54 : "ITEM_SCALE_GOLDEN",
0x55 : "ITEM_GIANTS_KNIFE",
0x56 : "ITEM_ADULTS_WALLET",
0x57 : "ITEM_GIANTS_WALLET",
0x58 : "ITEM_DEKU_SEEDS",
0x59 : "ITEM_FISHING_POLE",
0x5A : "ITEM_SONG_MINUET",
0x5B : "ITEM_SONG_BOLERO",
0x5C : "ITEM_SONG_SERENADE",
0x5D : "ITEM_SONG_REQUIEM",
0x5E : "ITEM_SONG_NOCTURNE",
0x5F : "ITEM_SONG_PRELUDE",
0x60 : "ITEM_SONG_LULLABY",
0x61 : "ITEM_SONG_EPONA",
0x62 : "ITEM_SONG_SARIA",
0x63 : "ITEM_SONG_SUN",
0x64 : "ITEM_SONG_TIME",
0x65 : "ITEM_SONG_STORMS",
0x66 : "ITEM_MEDALLION_FOREST",
0x67 : "ITEM_MEDALLION_FIRE",
0x68 : "ITEM_MEDALLION_WATER",
0x69 : "ITEM_MEDALLION_SPIRIT",
0x6A : "ITEM_MEDALLION_SHADOW",
0x6B : "ITEM_MEDALLION_LIGHT",
0x6C : "ITEM_KOKIRI_EMERALD",
0x6D : "ITEM_GORON_RUBY",
0x6E : "ITEM_ZORA_SAPPHIRE",
0x6F : "ITEM_STONE_OF_AGONY",
0x70 : "ITEM_GERUDOS_CARD",
0x71 : "ITEM_SKULL_TOKEN",
0x72 : "ITEM_HEART_CONTAINER",
0x73 : "ITEM_HEART_PIECE",
0x74 : "ITEM_DUNGEON_BOSS_KEY",
0x75 : "ITEM_DUNGEON_COMPASS",
0x76 : "ITEM_DUNGEON_MAP",
0x77 : "ITEM_SMALL_KEY",
0x78 : "ITEM_MAGIC_JAR_SMALL",
0x79 : "ITEM_MAGIC_JAR_BIG",
0x7A : "ITEM_HEART_PIECE_2",
0x7B : "ITEM_INVALID_1",
0x7C : "ITEM_INVALID_2",
0x7D : "ITEM_INVALID_3",
0x7E : "ITEM_INVALID_4",
0x7F : "ITEM_INVALID_5",
0x80 : "ITEM_INVALID_6",
0x81 : "ITEM_INVALID_7",
0x82 : "ITEM_MILK",
0x83 : "ITEM_RECOVERY_HEART",
0x84 : "ITEM_RUPEE_GREEN",
0x85 : "ITEM_RUPEE_BLUE",
0x86 : "ITEM_RUPEE_RED",
0x87 : "ITEM_RUPEE_PURPLE",
0x88 : "ITEM_RUPEE_GOLD",
0x89 : "ITEM_INVALID_8",
0x8A : "ITEM_DEKU_STICKS_5",
0x8B : "ITEM_DEKU_STICKS_10",
0x8C : "ITEM_DEKU_NUTS_5",
0x8D : "ITEM_DEKU_NUTS_10",
0x8E : "ITEM_BOMBS_5",
0x8F : "ITEM_BOMBS_10",
0x90 : "ITEM_BOMBS_20",
0x91 : "ITEM_BOMBS_30",
0x92 : "ITEM_ARROWS_5",
0x93 : "ITEM_ARROWS_10",
0x94 : "ITEM_ARROWS_30",
0x95 : "ITEM_DEKU_SEEDS_30",
0x96 : "ITEM_BOMBCHUS_5",
0x97 : "ITEM_BOMBCHUS_20",
0x98 : "ITEM_DEKU_STICK_UPGRADE_20",
0x99 : "ITEM_DEKU_STICK_UPGRADE_30",
0x9A : "ITEM_DEKU_NUT_UPGRADE_30",
0x9B : "ITEM_DEKU_NUT_UPGRADE_40",
0xFC : "ITEM_SWORD_CS",
0xFE : "ITEM_NONE_FE",
0xFF : "ITEM_NONE",
}
def disas_elfmsgs(start):
baserom = None
with open("baseroms/gc-eu-mq-dbg/baserom-decompressed.z64", "rb") as infile:
baserom = bytearray(infile.read())
branches = []
pos = start
while (True):
print(f"/* {pos - start:04X} {((pos - start) // 4):3} */ ", end="")
b0, b1, b2, b3 = struct.unpack(">BBBB", baserom[pos:pos+4])
elf_message_types = {
0x00: "CHECK",
0x20: "UNK_1",
0x40: "UNK_2",
0x60: "SKIP",
0xE0: "END",
}
cont = True
branch_to = None
# Get Type
elf_message_type = b0 & 0xE0
ARG_0 = elf_message_types[elf_message_type]
if elf_message_type in [0, 0x20, 0x40, 0xE0]:
if elf_message_type == 0xE0:
cont = False
ARG_1 = f"0x{(b2 & 0xFF):04X}"
elif elf_message_type == 0x60:
branch_to = 4 * (b2 & 0xFF)
ARG_1 = (b2 & 0xFF)
else:
assert False , "Encountered unknown type"
ARG_2 = f"{bool(b0 & 1)}".lower()
# Get condition
condition_type = b0 & 0x1E
if condition_type == 0:
if elf_message_type == 0xE0 and b1 == 0 and not (b0 & 1):
print(f"QUEST_HINT_END({ARG_1}),")
else:
print(f"QUEST_HINT_FLAG({ARG_0}, {ARG_1}, {ARG_2}, 0x{b1:02X}), /* eventChkInf[{(b1 >> 4) & 0xF}] & 0x{1 << (b1 & 0xF):X} */")
assert b3 == 0
elif condition_type == 2:
print(f"QUEST_HINT_DUNGEON_ITEM({ARG_0}, {ARG_1}, {ARG_2}, {item_ids[b1]}),")
assert b3 == 0
elif condition_type == 4:
print(f"QUEST_HINT_ITEM({ARG_0}, {ARG_1}, {ARG_2}, {item_ids[b1]}, {item_ids[b3]}),")
elif condition_type == 6:
condition_other_type = b1 & 0xF0
if condition_other_type == 0:
print(f"QUEST_HINT_STRENGTH_UPG({ARG_0}, {ARG_1}, {ARG_2}, {b1 & 0xF}),")
assert b3 == 0
elif condition_other_type == 0x10:
print(f"QUEST_HINT_BOOTS({ARG_0}, {ARG_1}, {ARG_2}, {item_ids[b3]}),")
assert (b1 & 0xF) == 0
elif condition_other_type == 0x20:
print(f"QUEST_HINT_SONG({ARG_0}, {ARG_1}, {ARG_2}, {item_ids[b3]}),")
assert (b1 & 0xF) == 0
elif condition_other_type == 0x30:
print(f"QUEST_HINT_MEDALLION({ARG_0}, {ARG_1}, {ARG_2}, {item_ids[b3]}),")
assert (b1 & 0xF) == 0
elif condition_other_type == 0x40:
print(f"QUEST_HINT_MAGIC({ARG_0}, {ARG_1}, {ARG_2}),")
assert (b1 & 0xF) == 0
assert b3 == 0
else:
assert False , "Encountered unknown condition (other) type"
else:
assert False , "Encountered unknown condition type"
# Control flow
if branch_to is not None:
branches.append(branch_to)
pos += 4
if not cont:
print("")
if not cont and all([dst < pos - start for dst in branches]):
break
disas_elfmsgs(int(sys.argv[1],16))

View File

@@ -1,12 +0,0 @@
; DO NOT EDIT (unless you know what you are doing)
;
; This subdirectory is a git "subrepo", and this file is maintained by the
; git-subrepo command. See https://github.com/ingydotnet/git-subrepo#readme
;
[subrepo]
remote = https://github.com/krimtonz/gzinject.git
branch = master
commit = ee44efce5d842e5d4488ee47c16da8b673da5086
parent = 53941daac4bb1482a9125f3595642df1bafb5f6d
method = merge
cmdver = 0.4.5

0
tools/gzinject/configure vendored Normal file → Executable file
View File

0
tools/gzinject/install-sh Normal file → Executable file
View File

View File

@@ -6,6 +6,8 @@
import re, struct
from os import path
VERSION = ""
# ===================================================
# Util
# ===================================================
@@ -280,9 +282,10 @@ def read_tables():
global combined_message_entry_table
global staff_message_entry_table
global VERSION
baserom = None
with open("baseroms/gc-eu-mq-dbg/baserom-decompressed.z64","rb") as infile:
with open(f"baseroms/{VERSION}/baserom-decompressed.z64","rb") as infile:
baserom = infile.read()
nes_message_entry_table = as_message_table_entry(baserom[nes_message_entry_table_addr:ger_message_entry_table_addr])
@@ -313,6 +316,7 @@ def fixup_message(message):
###
def dump_all_text():
global VERSION
# text id, ypos, type, nes, ger, fra
messages = []
for i,entry in enumerate(combined_message_entry_table,0):
@@ -326,7 +330,7 @@ def dump_all_text():
nes_offset = segmented_to_physical(entry[3])
nes_length = next_entry[3] - entry[3]
nes_text = ""
with open("baseroms/gc-eu-mq-dbg/segments/nes_message_data_static","rb") as infile:
with open(f"baseroms/{VERSION}/segments/nes_message_data_static","rb") as infile:
infile.seek(nes_offset)
nes_text = fixup_message(decode(infile.read(nes_length), entry[1]).replace("\x00","",-1))
@@ -337,13 +341,13 @@ def dump_all_text():
next_entry = combined_message_entry_table[i+2]
ger_offset = segmented_to_physical(entry[4])
ger_length = next_entry[4] - entry[4]
with open("baseroms/gc-eu-mq-dbg/segments/ger_message_data_static","rb") as infile:
with open(f"baseroms/{VERSION}/segments/ger_message_data_static","rb") as infile:
infile.seek(ger_offset)
ger_text = fixup_message(decode(infile.read(ger_length), entry[1]).replace("\x00","",-1))
fra_offset = segmented_to_physical(entry[5])
fra_length = next_entry[5] - entry[5]
with open("baseroms/gc-eu-mq-dbg/segments/fra_message_data_static","rb") as infile:
with open(f"baseroms/{VERSION}/segments/fra_message_data_static","rb") as infile:
infile.seek(fra_offset)
fra_text = fixup_message(decode(infile.read(fra_length), entry[1]).replace("\x00","",-1))
@@ -352,7 +356,8 @@ def dump_all_text():
return messages
def dump_staff_text():
staff_message_data_static_size = path.getsize("baseroms/gc-eu-mq-dbg/segments/staff_message_data_static")
global VERSION
staff_message_data_static_size = path.getsize(f"baseroms/{VERSION}/segments/staff_message_data_static")
# text id, ypos, type, staff
messages = []
for i,entry in enumerate(staff_message_entry_table,0):
@@ -361,14 +366,18 @@ def dump_staff_text():
staff_offset = segmented_to_physical(entry[3])
# hacky way to ensure the staff message entry table is read all the way to the end
staff_length = (staff_message_data_static_size if entry[0] == 0x052F else segmented_to_physical(next_entry[3])) - segmented_to_physical(entry[3])
with open("baseroms/gc-eu-mq-dbg/segments/staff_message_data_static","rb") as infile:
with open(f"baseroms/{VERSION}/segments/staff_message_data_static","rb") as infile:
infile.seek(staff_offset)
messages.append((entry[0], entry[1], entry[2], fixup_message(decode(infile.read(staff_length), entry[1]).replace("\x00","",-1))))
else:
messages.append((entry[0], entry[1], entry[2], "///END///"))
return messages
def extract_all_text(text_out, staff_text_out):
def extract_all_text(text_out, staff_text_out, version: str):
global VERSION
if len(VERSION) == 0:
VERSION = version
if text_out is not None or staff_text_out is not None:
read_tables()

Some files were not shown because too many files have changed in this diff Show More