I've made this code a month ago, just never bothered to port it and post it. It's kinda untested so i don't know how much it will work.
Code:
# Hook (PAL ONLY) = 8009E0BC
# Address Ports (PAL ONLY)
.set UtilRandint, 0x800F2EE0
.set Racedata, 0x809BD728
.set sprintf, 0x80011A2C
# Exception Vector Values (DON'T PORT)
.set LastVariant, 0x800001B0
# Check if we are loading a track song by checking the file's first character
lbz r3, 0x15C(r1)
cmpwi r3, 'n'
beq+ isTrack
cmpwi r3, 'S'
beq+ isTrack
cmpwi r3, 'r'
bne end
# Backup LR
isTrack:
mflr r26
# Do bl trick
bl trick
# Track counts
.byte 0, 0, 0, 0 # Mario Circuit, Moo Moo Meadows, Mushroom Gorge, Grumble Volcano
.byte 0, 0, 0, 0 # Toad's Factory, Coconut Mall, DK Summit, Wario's Gold Mine
.byte 0, 0, 0, 0 # Luigi Circuit, Daisy Circuit, Moonview Highway, Maple Treeway
.byte 0, 0, 0, 0 # Bowser Castle, Rainbow Road, Dry Dry Ruins, Koopa Cape
.byte 0, 0, 0, 0 # GCN Peach Beach, GCN Mario Circuit, GCN Waluigi Stadium, GCN DK Mountain
.byte 0, 0, 0, 0 # DS Yoshi Falls, DS Desert Hills, DS Peach Gardens, DS Delfino Square
.byte 0, 0, 0, 0 # SNES Mario Circuit 3, SNES Ghost Valley 2, N64 Mario Raceway, N64 Sherbet Land
.byte 0, 0, 0, 0 # N64 Bowser's Castle, N64 DK's Jungle Parkway, GBA Bowser Castle 3, GBA Shy Guy Beach
.byte 0, 0, 0, 0, 0 # Delfino Pier, Block Plaza, Chain Chomp Wheel, Funky Stadium, Thwomp Desert
.byte 0, 0, 0, 0, 0 # GCN Cookie Land, DS Twilight House, SNES Battle Course 4, GBA Battle Course 3, N64 Skyscraper
.byte 0 # Galaxy Colosseum
.align 2
# Format string for final name
.string "/%d%s.brstm"
# String for final lap music
.string "_F"
# String for regular lap music
.string ""
.align 2
# Swap LR back
trick:
mflr r8
mtlr r26
# Load last character of filename before the extension
addi r7, r28, 0x150
lbzx r7, r7, r1
# Assume not fast
li r26, 0
# Check for an F either lower or uppercase
cmpwi r7, 'f'
beq isFast
cmpwi r7, 'F'
bne noFast
# Set r26 to 1 if so
isFast:
li r26, 1
# Check if we should randomize or pick the existing number
noFast:
cmpwi r26, 1
beq lastLap
# Get track slot
lis r7, Racedata@ha
lwz r7, Racedata@l(r7)
lwz r7, 0xB68(r7)
# Setup arguments
li r3, 0
lbzx r4, r7, r8
addi r4, r4, 1
# Call randint
lis r12, UtilRandint@h
ori r12, r12, UtilRandint@l
mtctr r12
bctrl
# Move result to r5 and store it in the EVA
mr r5, r3
lis r3, LastVariant@ha
stb r5, LastVariant@l(r3)
b numberPicked
# Otherwise get previous number stored there
lastLap:
lis r5, LastVariant@ha
lbz r5, LastVariant@l(r5)
# If result is 0, load original track
numberPicked:
cmpwi r5, 0
beq end
# Set the buffer to the beginning of the file extension
addi r3, r28, 0x14F
add r3, r3, r1
# Set format string
addi r4, r8, 0x2C
# Set empty string
addi r6, r8, 0x3B
cmpwi r26, 1
beq call
# Otherwise set fast lap string
subi r6, r6, 3
# Call sprintf
call:
lis r12, sprintf@h
ori r12, r12, sprintf@l
mtctr r12
bctrl
# Original instruction
end:
addi r26, r1, 0x150