Load Savebanner Text from BMG [ArcticLuma113]
#1
Usage:

Place a binary BMG at the location /Boot/saveX.bmg on the disc, where X is one of C, E, F, G, I, J, K, N, S, or W corresponding to SYSCONF language settings. This BMG cannot be bigger than 0x400 bytes. If it is not present, this code will fall back to a default BMG embedded inside StaticR.rel.

This BMG should define messages 0x18697 though 0x1869a.

This code uses addresses 0x80003200 through 0x80003600. Make sure no other codes are using those addresses, or modify the source to use a different address as the buffer for the loaded BMG.

(Note: NTSC-K and PAL codes are currently untested, beyond making sure the game doesn't crash with this code enabled.)

NTSC-U:
C264C718 00000002
80C4005C 38000001
60000000 00000000
C264C750 00000031
7CC03378 9421FFA0
BFA10008 7FA802A6
93A10060 7C7D1B78
7CFE3B78 7D1F4378
90810014 48000015
2F426F6F 742F7361
76653F2E 626D6700
7C6802A6 38800043
2C000007 41820074
38840002 2C000001
41820068 38840001
2C000003 4182005C
38840001 2C000002
41820050 38840002
2C000005 41820044
38840001 2C000000
41820038 38840001
2C000009 4182002C
38840003 2C000006
41820020 38840005
2C000004 41820014
38840004 2C000008
41820008 38800045
9883000A 38810020
90810018 3CC08015
60C6E21C 7CC803A6
4E800021 2C030000
4182007C 80810018
80A40034 2C050400
4080004C 7C832378
3C808000 60843200
9081001C 38C00000
38E00002 3D008015
6108E794 7D0803A6
4E800021 2C030000
4180001C 8081001C
3C604D45 60635347
80A40000 7C051800
41820008 80810014
80610018 3CA08015
60A5E4C8 7CA803A6
4E800021 8081001C
48000008 80810014
7FE8FB78 7FC7F378
7FA3EB78 BBA10008
80C10060 7CC803A6
38210060 3CC0805D
60C6831C 7CC903A6
4E800420 00000000

PAL:
C2637A28 00000002
80C4005C 38000001
60000000 00000000
C2637A88 00000031
7CC03378 9421FFA0
BFA10008 7FA802A6
93A10060 7C7D1B78
7CFE3B78 7D1F4378
90810014 48000015
2F426F6F 742F7361
76653F2E 626D6700
7C6802A6 38800043
2C000007 41820074
38840002 2C000001
41820068 38840001
2C000003 4182005C
38840001 2C000002
41820050 38840002
2C000005 41820044
38840001 2C000000
41820038 38840001
2C000009 4182002C
38840003 2C000006
41820020 38840005
2C000004 41820014
38840004 2C000008
41820008 38800045
9883000A 38810020
90810018 3CC08015
60C6E2BC 7CC803A6
4E800021 2C030000
4182007C 80810018
80A40034 2C050400
4080004C 7C832378
3C808000 60843200
9081001C 38C00000
38E00002 3D008015
6108E834 7D0803A6
4E800021 2C030000
4180001C 8081001C
3C604D45 60635347
80A40000 7C051800
41820008 80810014
80610018 3CA08015
60A5E568 7CA803A6
4E800021 8081001C
48000008 80810014
7FE8FB78 7FC7F378
7FA3EB78 BBA10008
80C10060 7CC803A6
38210060 3CC0805F
60C68C00 7CC903A6
4E800420 00000000

NTSC-J:
C2637174 00000031
38000000 9421FFA0
BFA10008 7FA802A6
93A10060 7C7D1B78
7CFE3B78 7D1F4378
90810014 48000015
2F426F6F 742F7361
76653F2E 626D6700
7C6802A6 38800043
2C000007 41820074
38840002 2C000001
41820068 38840001
2C000003 4182005C
38840001 2C000002
41820050 38840002
2C000005 41820044
38840001 2C000000
41820038 38840001
2C000009 4182002C
38840003 2C000006
41820020 38840005
2C000004 41820014
38840004 2C000008
41820008 38800045
9883000A 38810020
90810018 3CC08015
60C6E1DC 7CC803A6
4E800021 2C030000
4182007C 80810018
80A40034 2C050400
4080004C 7C832378
3C808000 60843200
9081001C 38C00000
38E00002 3D008015
6108E754 7D0803A6
4E800021 2C030000
4180001C 8081001C
3C604D45 60635347
80A40000 7C051800
41820008 80810014
80610018 3CA08015
60A5E488 7CA803A6
4E800021 8081001C
48000008 80810014
7FE8FB78 7FC7F378
7FA3EB78 BBA10008
80C10060 7CC803A6
38210060 3CC0805F
60C684DC 7CC903A6
4E800420 00000000

NTSC-K:
C2625E20 00000031
38000009 9421FFA0
BFA10008 7FA802A6
93A10060 7C7D1B78
7CFE3B78 7D1F4378
90810014 48000015
2F426F6F 742F7361
76653F2E 626D6700
7C6802A6 38800043
2C000007 41820074
38840002 2C000001
41820068 38840001
2C000003 4182005C
38840001 2C000002
41820050 38840002
2C000005 41820044
38840001 2C000000
41820038 38840001
2C000009 4182002C
38840003 2C000006
41820020 38840005
2C000004 41820014
38840004 2C000008
41820008 38800045
9883000A 38810020
90810018 3CC08015
60C6E334 7CC803A6
4E800021 2C030000
4182007C 80810018
80A40034 2C050400
4080004C 7C832378
3C808000 60843200
9081001C 38C00000
38E00002 3D008015
6108E8AC 7D0803A6
4E800021 2C030000
4180001C 8081001C
3C604D45 60635347
80A40000 7C051800
41820008 80810014
80610018 3CA08015
60A5E5E0 7CA803A6
4E800021 8081001C
48000008 80810014
7FE8FB78 7FC7F378
7FA3EB78 BBA10008
80C10060 7CC803A6
38210060 3CC0805E
60C67020 7CC903A6
4E800420 00000000

Source:
Code:
# First part.
# Inject at:
#   0x8064c718 USA
#   0x80637a28 PAL
# Not used in NTSC-J or NTSC-K (afaik)

lwz r6, 92(r4) # Replaces lwz r0, 92(r4)
li r0, 1 # Force a later cmpwi/beq check to hook into our Part 2 payload

Code:
# Second part.
# Inject at:
#   0x8064c750 (USA)
#   0x80637a88 (PAL)
#   0x80637174 (JAP)
#   0x80625e20 (KOR)

.if region == 'e'
.set DVDOpen, 0x8015e21c # USA
.set DVDRead, 0x8015e794 # USA
.set DVDClose, 0x8015e4c8 # USA
.set ParseBMG, 0x805d831c # USA
.elseif region == 'p'
.set DVDOpen, 0x8015e2bc # PAL
.set DVDRead, 0x8015e834 # PAL
.set DVDClose, 0x8015e568 # PAL
.set ParseBMG, 0x805f8c00 # PAL
.elseif region == 'j'
.set DVDOpen, 0x8015e1dc # JAP
.set DVDRead, 0x8015e754 # JAP
.set DVDClose, 0x8015e488 # JAP
.set ParseBMG, 0x805f84dc # JAP
.elseif region == 'k'
.set DVDOpen, 0x8015e334 # KOR
.set DVDRead, 0x8015e8ac # KOR
.set DVDClose, 0x8015e5e0 # KOR
.set ParseBMG, 0x805e7020 # KOR
.else
.err
.endif
.set BMGBuf, 0x80003200

# in: r6 - Sysconf language (PAL/NTSC-U only), r4 - original BMG address
# out: r4 - BMG address

# r0 isn't set or checked in Japanese or Korean games, so set them now.
# TODO: Load up Sysconf ourselves in this case
.if region == 'j'
li r0, 0
.elseif region == 'k'
li r0, 9
.else # America and Europe
mr r0, r6 # Part 1 above sets r6
.endif

# Set up stack buffer:
# 0x8 - stack frame
# 0x18 - 3 registers and 3 extra pointers
# 0x40 - DVDFileInfo struct
stwu sp, -0x60(sp)
stmw r29, 8(sp)
mflr r29 # TODO: are these two instructions really necessary? (Likely needed as a place for ParseBMG to come back to once it's done)
stw r29, 0x60(sp)
# back up registers needed for DVDOpen/DVDRead arguments
mr r29, r3
mr r30, r7
mr r31, r8
# back up pointer to original BMG
stw r4, 0x14(sp)
# get address of the file name
bl file
.asciz "/Boot/save?.bmg"
.balign 4
file:
mflr r3
# check sysconf language
li r4, 0x43
cmpwi r0, 7 # C
beq _after
addi r4, r4, 2
cmpwi r0, 1 # E
beq _after
addi r4, r4, 1
cmpwi r0, 3 # F
beq _after
addi r4, r4, 1
cmpwi r0, 2 # G
beq _after
addi r4, r4, 2
cmpwi r0, 5 # I
beq _after
addi r4, r4, 1
cmpwi r0, 0 # J
beq _after
addi r4, r4, 1
cmpwi r0, 9 # K
beq _after
addi r4, r4, 3
cmpwi r0, 6 # N
beq _after
addi r4, r4, 5
cmpwi r0, 4 # S
beq _after
addi r4, r4, 4
cmpwi r0, 8 # W
beq _after
li r4, 0x45
_after:
stb r4, 10(r3)
addi r4, sp, 0x20
stw r4, 0x18(sp)
# Call DVDOpen
# r3: File name r4: DVDFileInfo*
lis r6, DVDOpen@h
ori r6, r6, DVDOpen@l
mtlr r6
blrl
cmpwi r3, 0
beq _fail2 # TODO: better way?
# Check    if the file size is >= 0x400
lwz r4, 0x18(sp)
lwz r5, 52(r4)
cmpwi r5, 0x400
bge _fail # too big
# Call DVDRead
# r3: DVDFileInfo* r4: dest buffer r5: size r6: offset r7: unknown, assumed constant 2
mr r3, r4
lis r4, BMGBuf@h
ori r4, r4, BMGBuf@l
stw r4, 0x1c(sp)
li r6, 0
li r7, 2
lis r8, DVDRead@h
ori r8, r8, DVDRead@l
mtlr r8
blrl
cmpwi r3, 0
blt _fail # TODO: better way?
lwz r4, 0x1c(sp)
# Check if we really got a BMG file
lis r3, 0x4d45
ori r3, r3, 0x5347
lwz r5, 0(r4)
cmpw r5, r3
beq _success
_fail:
lwz r4, 0x14(sp)
_success:
# close the file
# r3: DVDFileInfo*
lwz r3, 0x18(sp)
lis r5, DVDClose@h
ori r5, r5, DVDClose@l
mtlr r5
blrl
lwz r4, 0x1c(sp)
b _cleanup
_fail2:
lwz r4, 0x14(sp)
_cleanup:
# Reset changed registers (other than r5 and r6, they're set later anyways)
mr r8, r31
mr r7, r30
mr r3, r29
lmw r29, 8(sp)
# TODO: are these two instructions necessary also?
# Better safe than sorry I guess. The BMG parser needs to know where to return to.
# Also at this point, r6 is safe to use as it's written to by said parser.
lwz r6, 0x60(sp)
mtlr r6
addi sp, sp, 0x60
# Default instruction is a branch, so we jump directly to the BMG parser
lis r6, ParseBMG@h
ori r6, r6, ParseBMG@l
mtctr r6
bctr
Reply
#2
Nice code! and welcome to MarioKartWii.com
Reply


Forum Jump:


Users browsing this thread: 1 Guest(s)