Skip to content

feat(overlays): fifteen functions adapted from the NTSC decomp - #69

Merged
Lynder063 merged 19 commits into
OpenRAC:mainfrom
cnobis:feat/ports-2
Oct 14, 2026
Merged

Lynder063 merged 19 commits into
OpenRAC:mainfrom
cnobis:feat/ports-2

Conversation

@cnobis

@cnobis cnobis commented Oct 14, 2026 •

Copy link
Copy Markdown
Contributor

Fifteen exact matches adapted from the NTSC decomp's matched C, one commit each. Each passed try_func.py (EXACT) and overlay_file_check.py (0 problems). The full build has no size mismatch, every function sits at its retail address, and the one known byte mismatch is unchanged. The report is regenerated in the last commit: 4389 of 5109.

Function Level What it does
func_L00_002629E0 shared does a segment cross a path
func_L00_0020D3A0 shared finds the ledge spot the hero can reach
func_L01_00303810 Novalis full-screen tiled noise draw callback
func_L01_002F0B48 Novalis spark burst around a moby
func_L06_002EAF90 Blarg moves a moby, pushes it out of walls, snaps it to its path
func_L06_0030D3E8 Blarg growing and fading sprite draw callback
func_L06_002F3D40 Blarg nearest box or mine within reach
func_L09_002F1198 Gaspar spawns a class 0x1A1 effect around a point
func_L09_0030BB28 Gaspar spawns a moby from its owner's spawn class
func_L11_00310058 Pokitaru tilting platform the hero tips over
func_L13_002EBD00 Gemlik the tractor beam of Qwark's ship (below)
func_L14_002D8500 Oltanis two glow quads for the plasmabot (class 211)
func_L14_00306BE0 Oltanis the Morph-o-Ray pickup (class 1354), which starts a cutscene
func_L14_002FD578 Oltanis class 908 (jet), five objects flying fixed paths
func_L18_002FABE0 Veldin 2 three nested glow quads

Corrections: two rows above first used the NTSC decomp's names, which do not match the objects:

  • func_L14_002FD578 is not a mine cart. It updates class 908 (jet in the editor's class list), placed five times high above Oltanis, each flying a fixed path. Its code also handles a hit (mask 0x800000): the object stops and restarts at its path's start after a timer, and the third such hit in level 14 plays a voice line once.
  • func_L14_002D8500 draws two glow quads for the plasmabot (class 211), not for a racer.

func_L14_00306BE0 is the update of the Morph-o-Ray pickup (class 1354). The commit messages keep the old wording.

Adapting them took more than renaming symbols:

  • Level data sits 0x80 to 0xD0 above its US address, varying by level.
  • A load through $at or through its own destination register means MACRO_ADDR, and a $gp load means SDATA.
  • Two Oltanis dialogue ids are 5 higher in PAL (0x53DB and 0x53E5 for the US 0x53D6 and 0x53E0).
  • Where a file already declares a callee with other parameter types, the function calls it through a second name, or takes the file's types and converts them inside.
  • Moby fields the NTSC decomp names appear under their unkXX names from include/moby.h.

func_L13_002EBD00 is the tractor beam that Qwark's ship fires at Ratchet's ship in the Gemlik boss fight: the cone of white rings from the cannon under the ship. Its caller is the update of class 388 (qwarks_starfighter_part), which aims at the hero and draws the beam only while the ship faces him within 60 degrees. The function draws one ring-textured quad per unit from attachment point 0x13 toward the target, the rings flow along the beam over 20 frames, and the last 10 units fade out. The rings all have the same size. The cone shape in game is perspective, since the beam points at the player.

The cleanup commit drops the near misses and functional C of these fifteen, with their functional.tsv rows, and regenerates nonmatching/README.md with nonmatching.py's index(). That also brings three stale rows on main up to date.

Left out on purpose:

  • func_L12_00304038 matches too, but its C needs a two-dimensional variable-length array. hostgen takes only one-dimensional ones, and the port uses the functional C only while a function is still assembly here. Landing it now would turn the Hoven effect back into a stub in the port, so it waits for hostgen.
  • func_L14_002E1570 is 33 bytes off, from scheduling around a float constant.
  • func_L15_002C62A8 matches in the NTSC decomp only through volatile reads that order the code, which this project does not allow.

Credited in THIRD_PARTY_NOTICES.md and in each function's source comment.

Generated with Claude Code

cnobis and others added 18 commits October 14, 2026 19:08
Moves a moby along its facing by the given scale and pushes it back out
of walls, then optionally snaps it to its path. Adapted from Lombyte's
FUN_L06_002e9b60. The wall check is called through a second name with
Lombyte's argument order, which sets up the call as retail does.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The draw callback of the fading sprite effect that func_L06_0030D2A0
registers: projects the moby to the screen and draws one textured quad
that grows and fades with its timer. Adapted from Lombyte's
FUN_L06_0030bfa8. Its declaration now takes the moby.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Tests whether the segment from start to end crosses the path with the
given index, in the plane of the segment's direction. Adapted from
Lombyte's FUN_L00_00261968, with the file's own vector type and second
names for the callees, whose prototypes the file declares later with its
own types.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Spawns a class 0x1A1 moby at a random angle and radius around an origin,
moving along a direction, sized and slowed by how far the angle is from
that direction. Adapted from Lombyte's FUN_L09_002efe48, with the
parameters in this file's declared order and the moby fields under their
names in include/moby.h.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
A draw callback that covers the screen with 32-pixel tiles of a random
part of effect texture 30, faded in by the moby's timer. Adapted from
Lombyte's FUN_L01_00302438, with the screen size read through
D_0013E15A + 0x4A6 as other files here do.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Finds the first of the level's ledge spots whose sphere holds a point and
whose owner reports a hit within reach of the hero, the reach depending on
the hero's control mode, and returns the spot's owner, kind and hit.
Adapted from Lombyte's FUN_L00_0020cd08. The parameters keep the types
the file declares and take their real types inside.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Spawns one moby from the owner's spawn class at a position, sets it up
from its class header, splits the owner's unkB4 count with it and returns
it. When no moby is free it reports the owner's save id instead. Adapted
from Lombyte's FUN_L09_0030a778, with the moby fields Lombyte names under
their unkXX names in include/moby.h.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The tilting platform on Pokitaru: its rot.y springs back through a damped
spin, the hero standing on it tilts it toward his side, and a tilt past
the level's limit knocks him into the falling state. Adapted from
Lombyte's FUN_L11_0030eb90. Level 11's constants sit 0x90 above their US
addresses.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The draw callback of an Oltanis racer: two glow quads at its lamp
(pvars 0xE0) and its tail (pvars 0x200), each turned toward a fixed
point of the level. Adapted from Lombyte's FUN_L14_002d71f0. Its
declaration now takes the moby.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The update of a spinning pickup on Oltanis: it removes itself when its
mission slot is unset, otherwise floats and turns in place, and when the
hero touches it starts a cutscene, then saves, queues its dialogue and a
help message and removes itself. Adapted from Lombyte's
FUN_L14_00305758. PAL shows dialogue 0x53E5 where the US build shows
0x53E0.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The update of the Oltanis mine cart: a hit stops it, bursts it, and on
the third one in level 14 plays a voice line once; then it either starts
on its path, runs it, or waits out its timer and restarts at the path's
first point. Adapted from Lombyte's FUN_L14_002fc0f0. PAL plays
dialogue 0x53DB where the US build plays 0x53D6.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Bursts sparks around a moby: for each of the level's burst count, a
random start near the moby and a random velocity along the given
direction, then a level-defined number of sparks with random sizes,
colours, lifetimes and fades. Adapted from Lombyte's FUN_L01_002ef770.
Level 1's constants sit 0x90 above their US addresses.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Picks the nearest box or mine (classes 0x3B1, 0x400, 0x515, 0x516)
within 12 units and at the moby's height, from its target group or else
the level's moby list, skipping ones already used, and marks the search
done. Adapted from Lombyte's FUN_L06_002f2910, with its moby and vars
types cut down to the fields this function reads.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Draws three nested glow quads around a point on Veldin's second visit,
facing a fixed position, after resetting the point's rotation on the
frame its timer comes due. Adapted from Lombyte's FUN_L18_002f9780.
Level 18's data sits 0x80 to 0x90 above its US addresses.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Draws a Gemlik beam from a point of the moby to the target in its pvars
as a chain of textured quads one step apart, scrolling with the frame
counter and fading over its last ten units. Adapted from Lombyte's
FUN_L13_002ea8c8, with a plain field for the quad's reserved word.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…unctions

The fifteen functions of this branch are exact now: their near misses and
functional files go, with their rows in functional.tsv.

nonmatching/README.md is regenerated with tools/nonmatching.py's index().
It also catches up with main on three rows: func_L09_00306DD8's staged
file is gone, and func_L05_00317B68 and func_L00_001F8750 moved to
functional/ and game/.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Regenerated with gen_progress_report.py --no-build after build_sn.sh, and
--check says it is current. The fifteen functions of this branch are new.
Main's totals said 4372 while its units already summed to 4374, so the
total moves by 17.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@decomp-dev

decomp-dev Bot commented Oct 14, 2026 •

Copy link
Copy Markdown

Report for SCES_509.16 (e1ee2ee - 73f79d7)

📈 Matched code: 82.67% (+0.28%, +10440 bytes)

✅ 18 new matches
Unit Item Bytes Before After
Level 13: Gemlik Base func_L13_002EBD00 +824 0.00% 100.00%
Level 18: Veldin (return) func_L18_002FABE0 +792 0.00% 100.00%
Shared level code func_L06_002F3D40 +788 0.00% 100.00%
Level 14: Oltanis func_L14_002D8500 +668 0.00% 100.00%
Level 11: Pokitaru func_L11_00310058 +624 0.00% 100.00%
Shared level code func_L09_0030BB28 +620 0.00% 100.00%
Shared level code func_L00_0020D3A0 +588 0.00% 100.00%
Shared level code func_L01_00303810 +524 0.00% 100.00%
Shared level code func_L00_002629E0 +476 0.00% 100.00%
Shared level code func_L06_002EAF90 +428 0.00% 100.00%
Shared level code func_L03_002E9AF8 +276 100.00% 100.00%
Shared level code func_L06_0030D3E8 +172 63.77% 100.00%
Shared level code func_L15_002E5770 +148 100.00% 100.00%
Level 14: Oltanis func_L14_002FD578 +44 94.18% 100.00%
Level 09: Gaspar func_L09_002F1198 +18 96.40% 100.00%
Level 14: Oltanis func_L14_00306BE0 +9 98.91% 100.00%
Shared level code func_L01_002F0B48 +5 99.37% 100.00%
Shared level code func_L02_002DB810 -20 100.00% 100.00%
🥀 4 broken matches
Unit Item Bytes Before After
Shared level code func_L11_0030A8C8 -756 100.00% 0.00%
Shared level code func_L08_00211A38 -748 100.00% 0.00%
Shared level code func_L00_0029AFB8 -544 100.00% 0.00%
Shared level code func_L03_002E99F0 -36 100.00% 0.00%
📉 1 regression in an unmatched item
Unit Item Bytes Before After
Shared level code func_L00_001F8750 -110 94.83% 0.00%

The C as adapted used volatile to steer the compiler, which says nothing
about what the original source did. Each matches as plain C:

- func_L18_002FABE0: the four floats at D_L18_001625E0 are one vector,
  written in turn and passed by address, so they are an array.
- func_L09_0030BB28: the three stores to the returned object go in the
  order 0x94, 0x68, 0x6C, and m needs no forced reload.
- func_L01_00303810: coordinate needs no volatile at all.

overlay_file_check: 3 files, 0 problems.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@Lynder063
Lynder063 merged commit 3e53c2d into OpenRAC:main Oct 14, 2026
1 check passed
Lynder063 added a commit that referenced this pull request Oct 14, 2026
feat(overlays): 50 pure-C ports, plus #69, #70 and #71 merged
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants