Prepare repository for public release
- README: attract-mode stills + demo GIF as the hero row, status/warning callouts, metrics table, "Contents" index, doc-index table; simplified the two-agent workflow diagram (LR -> TD, fewer edges) for GitHub web - Table-of-contents indexes added to internals.md, porting-notes.md, agentic-development.md, AUDIO-PLAN.md - CI: add Windows/MSYS2 build job, minimal token (contents: read), persist-credentials: false, concurrency group; run on main + master. validate job regenerates the US ROM-asset symbol file only and configures ntsc-final (PAL/JP need a region ROM; no ROM is used in CI) - .github: SECURITY.md, issue forms + chooser config, PR template, labels.yml, dependabot (Actions, monthly) - Do not track the proprietary SGI IRIX IDO toolchain or SGIImageViewer.exe; document in SetupGuide.md / building.md how to obtain IDO for N64 ROM builds (the PC port does not need it) - Stop tracking two committed *.pyc files; drop stale screenshots and a redundant .gitignore line; misc doc cross-reference fixes Claude-Session: https://claude.ai/code/session_01GULf6knbsqfsnW39tMr9WT
No files matched your search
@@ -1,6 +1,8 @@
|
||||
* text=auto eol=lf
|
||||
*.png binary
|
||||
*.jpg binary
|
||||
*.gif binary
|
||||
*.mp4 binary
|
||||
*.z64 binary
|
||||
*.exe binary
|
||||
*.bin binary
|
||||
@@ -0,0 +1,71 @@
|
||||
name: Bug report (build or run)
|
||||
description: A build failure, crash, hang, or rendering/audio/input defect in the PC port
|
||||
labels: ["bug"]
|
||||
body:
|
||||
- type: markdown
|
||||
attributes:
|
||||
value: |
|
||||
Thanks for filing a report. First, please check:
|
||||
|
||||
- The port is **Phase 2 of 4** — rendering is incomplete and many
|
||||
cosmetic defects are already tracked in
|
||||
[`docs/dev/GRAPHICS-BACKLOG.md`](https://github.com/jkdansereau/goldeneye-pc-port/blob/main/docs/dev/GRAPHICS-BACKLOG.md).
|
||||
Search open issues and that file before filing.
|
||||
- Only the **Windows / MSYS2 MINGW64** build is tested. Linux and
|
||||
macOS are best-effort — build breaks there are expected.
|
||||
- Do **not** attach a ROM, extracted assets, or any game data.
|
||||
- type: input
|
||||
id: commit
|
||||
attributes:
|
||||
label: Commit
|
||||
description: Output of `git rev-parse --short HEAD`
|
||||
placeholder: 311fd012
|
||||
validations:
|
||||
required: true
|
||||
- type: dropdown
|
||||
id: region
|
||||
attributes:
|
||||
label: Region / ROMID
|
||||
options: [ntsc-final, pal-final, jpn-final]
|
||||
validations:
|
||||
required: true
|
||||
- type: input
|
||||
id: os
|
||||
attributes:
|
||||
label: OS / environment
|
||||
description: e.g. "Windows 10, MSYS2 MINGW64" or "Ubuntu 22.04, native gcc"
|
||||
validations:
|
||||
required: true
|
||||
- type: dropdown
|
||||
id: stage
|
||||
attributes:
|
||||
label: Which stage fails?
|
||||
options:
|
||||
- Asset extraction
|
||||
- CMake configure
|
||||
- Compile / link
|
||||
- Runtime — crash or hang
|
||||
- Runtime — wrong rendering / audio / input
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: what
|
||||
attributes:
|
||||
label: What happened vs. what you expected
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: repro
|
||||
attributes:
|
||||
label: Steps to reproduce
|
||||
description: Exact commands, flags (e.g. `-level_09`), and what you did in-game.
|
||||
validations:
|
||||
required: true
|
||||
- type: textarea
|
||||
id: logs
|
||||
attributes:
|
||||
label: Logs
|
||||
description: |
|
||||
Paste the terminal error, and `ge007.crash.log` if the port crashed.
|
||||
For a rendering defect, attach a screenshot.
|
||||
render: text
|
||||
@@ -0,0 +1,14 @@
|
||||
blank_issues_enabled: true
|
||||
contact_links:
|
||||
- name: Build & setup guide
|
||||
url: https://github.com/jkdansereau/goldeneye-pc-port/blob/main/docs/building.md
|
||||
about: Read this first for build/extraction problems — most are covered here.
|
||||
- name: Known rendering defects
|
||||
url: https://github.com/jkdansereau/goldeneye-pc-port/blob/main/docs/dev/GRAPHICS-BACKLOG.md
|
||||
about: Cosmetic / rendering issues already known and tracked. Check before filing.
|
||||
- name: Security vulnerability
|
||||
url: https://github.com/jkdansereau/goldeneye-pc-port/security/advisories/new
|
||||
about: Report memory-safety / build-pipeline vulnerabilities privately, not as a public issue.
|
||||
- name: Rights-holder concern
|
||||
url: https://github.com/jkdansereau/goldeneye-pc-port/blob/main/NOTICE
|
||||
about: If you represent a rights holder, see NOTICE and open an issue titled accordingly.
|
||||
@@ -0,0 +1,41 @@
|
||||
# Security Policy
|
||||
|
||||
This project is a non-commercial, fan-made research port. It has no server
|
||||
component and ships no binaries. The realistic security surface is:
|
||||
|
||||
- the PC port executable parsing your own ROM and asset files at load time
|
||||
(a malformed ROM/asset could in principle crash it or worse), and
|
||||
- the build/extraction scripts and CI workflow.
|
||||
|
||||
## Reporting a vulnerability
|
||||
|
||||
Please **do not** open a public issue for a security problem.
|
||||
|
||||
Use GitHub's private vulnerability reporting:
|
||||
**Security → Report a vulnerability** on this repository
|
||||
(<https://github.com/jkdansereau/goldeneye-pc-port/security/advisories/new>).
|
||||
|
||||
If that is unavailable, email the maintainer at the address on their GitHub
|
||||
profile with `SECURITY` in the subject.
|
||||
|
||||
Please include:
|
||||
|
||||
- affected version / commit hash (from `git rev-parse HEAD`),
|
||||
- OS and how you built (region, `IDO_RECOMP`, MSYS2 vs WSL, …),
|
||||
- a minimal reproduction, and
|
||||
- the crash log (`ge007.crash.log`) or a stack trace if you have one.
|
||||
|
||||
## Scope
|
||||
|
||||
In scope: memory-safety bugs in the `port/` layer and PC-port tooling,
|
||||
issues in the CI workflow or build scripts, and dependency problems we can
|
||||
act on.
|
||||
|
||||
Out of scope: bugs inherited unchanged from the upstream
|
||||
[GoldenEye 007 decompilation](https://github.com/n64decomp/007) that are not
|
||||
made worse by the port (report those upstream), missing-asset or wrong-ROM
|
||||
errors, and anything requiring a ROM or assets we do not distribute.
|
||||
|
||||
## Supported versions
|
||||
|
||||
Only the tip of the default branch is supported. There are no releases yet.
|
||||
@@ -0,0 +1,8 @@
|
||||
version: 2
|
||||
updates:
|
||||
# Keep the GitHub Actions used by .github/workflows/ up to date. Opens a PR
|
||||
# when a new version of an action is released; review and merge like any other.
|
||||
- package-ecosystem: github-actions
|
||||
directory: /
|
||||
schedule:
|
||||
interval: monthly
|
||||
@@ -0,0 +1,58 @@
|
||||
# Source of truth for this repo's issue/PR labels.
|
||||
# GitHub does not read this file automatically. Apply it with the gh commands
|
||||
# in the comment block at the bottom, or wire up a label-sync action later.
|
||||
#
|
||||
# `bug` and `documentation` are GitHub defaults and are kept as-is.
|
||||
|
||||
- name: bug
|
||||
color: d73a4a
|
||||
description: Something is broken
|
||||
|
||||
- name: rendering
|
||||
color: 5319e7
|
||||
description: Graphics / fast3d / RSP output defect (see docs/dev/GRAPHICS-BACKLOG.md)
|
||||
|
||||
- name: audio
|
||||
color: 1d76db
|
||||
description: Sound / music / libaudio (Phase 3)
|
||||
|
||||
- name: input
|
||||
color: 0e8a16
|
||||
description: Keyboard / mouse / controller
|
||||
|
||||
- name: build
|
||||
color: fbca04
|
||||
description: CMake / MSYS2 / toolchain / CI
|
||||
|
||||
- name: asset-extraction
|
||||
color: c2e0c6
|
||||
description: ROM asset extraction pipeline (scripts/, tools/extractor)
|
||||
|
||||
- name: upstream
|
||||
color: bfd4f2
|
||||
description: Originates in the n64decomp/007 decompilation, not the port — may belong upstream
|
||||
|
||||
- name: abi-64bit
|
||||
color: fef2c0
|
||||
description: 32-to-64-bit pointer-width / struct-layout issue (the #ifdef PORT exception)
|
||||
|
||||
- name: needs-repro
|
||||
color: e99695
|
||||
description: Cannot reproduce yet; waiting on more detail
|
||||
|
||||
- name: wontfix
|
||||
color: ffffff
|
||||
description: Out of scope or working as intended
|
||||
|
||||
# Apply with the GitHub CLI (run once, after the repo exists):
|
||||
#
|
||||
# gh label create rendering -c 5319e7 -d "Graphics / fast3d / RSP output defect"
|
||||
# gh label create audio -c 1d76db -d "Sound / music / libaudio (Phase 3)"
|
||||
# gh label create input -c 0e8a16 -d "Keyboard / mouse / controller"
|
||||
# gh label create build -c fbca04 -d "CMake / MSYS2 / toolchain / CI"
|
||||
# gh label create asset-extraction -c c2e0c6 -d "ROM asset extraction pipeline"
|
||||
# gh label create upstream -c bfd4f2 -d "Originates in the decompilation, not the port"
|
||||
# gh label create abi-64bit -c fef2c0 -d "32-to-64-bit pointer-width / struct-layout issue"
|
||||
# gh label create needs-repro -c e99695 -d "Cannot reproduce yet; waiting on more detail"
|
||||
#
|
||||
# `bug` and `wontfix` already exist as GitHub defaults.
|
||||
@@ -0,0 +1,37 @@
|
||||
<!--
|
||||
Read CONTRIBUTING.md first. This is a faithfulness-focused port; the ground
|
||||
rules there are non-negotiable.
|
||||
-->
|
||||
|
||||
## What this changes
|
||||
|
||||
<!-- One or two sentences. Link the issue it closes: "Closes #123". -->
|
||||
|
||||
## Why
|
||||
|
||||
<!-- The reasoning, not just the diff. What was wrong / missing? -->
|
||||
|
||||
## Scope check
|
||||
|
||||
- [ ] No changes under `src/` or `include/` — **or** the only changes are the
|
||||
narrow `#ifdef PORT` ABI exception (CONTRIBUTING.md rule 2), and each is
|
||||
documented in `docs/porting-notes.md` / `docs/dev/findings.md`.
|
||||
- [ ] `Makefile`, `tools/`, `rsp/`, `ld/` untouched (N64 build).
|
||||
- [ ] If `CMakeLists.txt` `REGION_DEFS` changed, it still matches the N64
|
||||
`Makefile` per-region macro set exactly.
|
||||
|
||||
## Verification
|
||||
|
||||
<!-- What you actually ran. Delete lines that don't apply. -->
|
||||
|
||||
- [ ] `./build-pc.sh ntsc-final` — clean configure + link
|
||||
- [ ] Crash-free run of at least one level (`-level_09`)
|
||||
- [ ] Single-frame `GE_PCDUMP` diff against the committed golden — no
|
||||
unexpected change
|
||||
- [ ] pal-final / jpn-final also configured
|
||||
|
||||
Platform tested: <!-- e.g. Windows 10 / MSYS2 MINGW64 -->
|
||||
|
||||
## Notes for the reviewer
|
||||
|
||||
<!-- Anything uncertain, follow-ups, or areas that need a closer look. -->
|
||||
@@ -2,26 +2,43 @@ name: CI
|
||||
|
||||
on:
|
||||
push:
|
||||
branches: [ master ]
|
||||
branches: [ main, master ]
|
||||
paths-ignore: [ '**.md', 'docs/**', 'LICENSE', 'NOTICE' ]
|
||||
pull_request:
|
||||
paths-ignore: [ '**.md', 'docs/**', 'LICENSE', 'NOTICE' ]
|
||||
workflow_dispatch:
|
||||
|
||||
# The full port build needs assets extracted from a copyrighted ROM, which CI
|
||||
# does not have. This job validates everything that does NOT depend on those
|
||||
# assets: the PC-port tooling, the generated ROM-asset symbol files, and a
|
||||
# CMake configure of all three regions (which checks REGION_DEFS, the source
|
||||
# list, and that SDL2 / zlib / OpenGL are discoverable).
|
||||
# Minimal token: CI only reads the repo and uploads build artifacts, neither of
|
||||
# which needs write access. Fork PRs run untrusted build scripts on the runner,
|
||||
# so keep the granted scope as small as possible and never expose secrets here.
|
||||
permissions:
|
||||
contents: read
|
||||
|
||||
concurrency:
|
||||
group: ci-${{ github.ref }}
|
||||
cancel-in-progress: true
|
||||
|
||||
# Two jobs:
|
||||
#
|
||||
# This is a configure-only smoke test. It does NOT compile or run the port, and
|
||||
# it running on ubuntu is NOT a statement that the port builds or works on
|
||||
# Linux — it has only ever been built and tested on Windows (MSYS2).
|
||||
# validate — ubuntu, configure-only. Byte-compiles the tooling,
|
||||
# regenerates the US ROM-asset symbol file, and CMake-
|
||||
# configures ntsc-final (REGION_DEFS, the source list, and
|
||||
# that SDL2 / zlib / OpenGL are discoverable). No ROM is used.
|
||||
# Does NOT compile; running on ubuntu is NOT a claim the port
|
||||
# works on Linux.
|
||||
#
|
||||
# windows-build — windows/MSYS2, the real supported platform. Compiles and
|
||||
# links the full executable. Neither the ROM nor extracted
|
||||
# assets are needed to BUILD (they are runtime-only), so CI
|
||||
# builds but never runs the port.
|
||||
|
||||
jobs:
|
||||
validate:
|
||||
runs-on: ubuntu-22.04
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
with:
|
||||
persist-credentials: false
|
||||
|
||||
- name: Install dependencies
|
||||
run: |
|
||||
@@ -31,17 +48,61 @@ jobs:
|
||||
- name: Byte-compile Python tooling
|
||||
run: python3 -m compileall -q scripts tools_pc
|
||||
|
||||
- name: Regenerate ROM-asset symbol files
|
||||
# US only. gen_romassets.py resolves every symbol for the US region from
|
||||
# the committed CSVs with no ROM present; PAL/JP each need a handful of
|
||||
# region-specific prop/font offsets that only come from that region's ROM
|
||||
# (see docs/building.md — PAL/JP builders generate romassets_e/j.s
|
||||
# locally). No ROM is used or required here.
|
||||
- name: Regenerate ROM-asset symbol file (US)
|
||||
run: |
|
||||
python3 scripts/gen_romassets.py u
|
||||
python3 scripts/gen_romassets.py e
|
||||
python3 scripts/gen_romassets.py j
|
||||
git diff --stat -- port/src/romassets_u.s
|
||||
|
||||
- name: CMake configure (all regions)
|
||||
run: |
|
||||
for r in ntsc-final pal-final jpn-final; do
|
||||
echo "::group::configure $r"
|
||||
cmake -S . -B "build-$r" -DROMID="$r"
|
||||
echo "::endgroup::"
|
||||
done
|
||||
- name: CMake configure (ntsc-final)
|
||||
run: cmake -S . -B build-ntsc -DROMID=ntsc-final
|
||||
|
||||
# Real Windows (MSYS2 MINGW64) build — the only platform the port is
|
||||
# developed and tested on. This compiles and LINKS the full executable.
|
||||
#
|
||||
# No ROM and no extracted assets are needed to build: the compiled asset set
|
||||
# is a handful of committed pure-data .c files plus the generated
|
||||
# address-constant romassets_<region>.s. The ROM (.z64) and the ROM-derived
|
||||
# blobs are runtime-only dependencies — CI cannot run the game, only build it.
|
||||
windows-build:
|
||||
runs-on: windows-latest
|
||||
defaults:
|
||||
run:
|
||||
shell: msys2 {0}
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
with:
|
||||
persist-credentials: false
|
||||
|
||||
- uses: msys2/setup-msys2@v2
|
||||
with:
|
||||
msystem: MINGW64
|
||||
update: true
|
||||
install: >-
|
||||
mingw-w64-x86_64-toolchain
|
||||
mingw-w64-x86_64-cmake
|
||||
mingw-w64-x86_64-SDL2
|
||||
mingw-w64-x86_64-zlib
|
||||
mingw-w64-x86_64-python
|
||||
|
||||
- name: Regenerate ROM-asset symbol file (US)
|
||||
run: python scripts/gen_romassets.py u
|
||||
|
||||
- name: Build (ntsc-final)
|
||||
run: ./build-pc.sh ntsc-final
|
||||
|
||||
- name: Upload executable
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: ge007-ntsc-final
|
||||
path: build-pc/ge007*
|
||||
if-no-files-found: error
|
||||
retention-days: 14
|
||||
|
||||
# CI builds the executable but does not run it — running the port needs a
|
||||
# ROM, which CI does not provide. Runtime checks (the -level_09 soak, a
|
||||
# golden-frame diff) would run on a self-hosted runner instead. Not planned.
|
||||
@@ -76,6 +76,12 @@ ge007.ini
|
||||
!build/test.c
|
||||
!notes/StyleGuide.md
|
||||
#tools
|
||||
# Original SGI IRIX 5.3 IDO toolchain (proprietary SGI binaries) and the SGI
|
||||
# image viewer are NOT distributed with this repo. They are only needed to
|
||||
# build the N64 ROM or to regenerate tools/ido5.3_recomp; the PC port does not
|
||||
# use them. See docs/SetupGuide.md "Recompile IDO" for how to obtain them.
|
||||
tools/irix/
|
||||
tools/SGIImageViewer.exe
|
||||
tools/extractor/*.o
|
||||
tools/extractor/extractor
|
||||
tools/aaa_rip/main.o
|
||||
@@ -117,7 +123,6 @@ assets/obseg/em/data/under.seg
|
||||
|
||||
scripts/local/
|
||||
scripts/make/local/
|
||||
scripts/__pycache__/generate_prop_model_c.cpython-310.pyc
|
||||
|
||||
# PC port debug/session artifacts
|
||||
_run.log
|
||||
|
||||
@@ -4,8 +4,8 @@
|
||||
|
||||
- `n64decomp/007`: WIP decompilation of GoldenEye 007 (N64), byte-matches US/EU/JP ROMs.
|
||||
- Active work: **PC port** modelled on the Perfect Dark PC port (same Rare "Indy" engine family).
|
||||
- **Reference docs:** `docs/internals.md` — architecture, GE-specific RSP deltas, phased plan (§1–§10). `docs/dev/findings.md` — the `Dxx` finding log (§F + §H, indexed at the top of §F); read the entry you need, don't linear-read. `docs/porting-notes.md` — the recurring N64→PC bug classes, one screen.
|
||||
- **Current status:** the README "Status" section. Current task + environment: `docs/HANDOFF.md` (a rolling local working file).
|
||||
- **Reference docs:** `docs/internals.md` — architecture, GE-specific RSP deltas, phased plan (§1–§10). `docs/dev/findings.md` — the `Dxx` finding log (§F + §H, indexed at the top of §F); read the entry you need, don't linear-read. `docs/porting-notes.md` — the recurring N64→PC bug classes (dense; skim the headers, read what's relevant).
|
||||
- **Current status:** the README "Status" section, and `docs/dev/LEVEL-STATUS.md` for the per-level sweep. Current task + environment: `docs/HANDOFF.md` (a rolling local working file — may be absent in a fresh clone; fall back to the README "Status" section).
|
||||
- **Dispatching subagents?** `docs/dev-process.md` — task budgets/deadlines, file partitioning, pre-flight, the standard brief template. Every investigation subagent reads `docs/porting-notes.md` first and appends to it.
|
||||
|
||||
## Non-negotiables
|
||||
@@ -55,7 +55,7 @@ Run `/linkcheck` for this sweep. Record new findings in `docs/dev/findings.md`
|
||||
start) is functional; file-backed EEPROM saves work. Cosmetic defects are
|
||||
parked in `docs/dev/GRAPHICS-BACKLOG.md`.
|
||||
- **Phase 3 (audio + input):** input layer done (`port/src/input.c`); polish
|
||||
bugs open (D118*, D169). Audio not started — libaudio → SDL, copy-and-adapt
|
||||
from the PD port's `mixer.c`.
|
||||
bugs open (D118* mouse-look residuals; interactive feel-checks owed). Audio
|
||||
not started — libaudio → SDL, copy-and-adapt from the PD port's `mixer.c`.
|
||||
- **Phase 4 (saves + polish):** file-backed EEPROM done; widescreen, config,
|
||||
rebinding UI outstanding.
|
||||
@@ -12,15 +12,16 @@ Context is scarce. Load by tier; do not blind-read whole files.
|
||||
|
||||
- **Tier 0 — always (auto-loaded):** `CLAUDE.md`, `AGENTS.md`. Nothing
|
||||
else auto-loads.
|
||||
- **Tier 1 — every session start, read fully (both are short):**
|
||||
- **Tier 1 — every session start:**
|
||||
`docs/HANDOFF.md` (current state + next task + environment — a rolling
|
||||
local working file; may be absent in a fresh clone, in which case read
|
||||
the README "Status" section instead),
|
||||
`docs/porting-notes.md` (recurring bug classes).
|
||||
the README "Status" section instead) — read fully;
|
||||
`docs/porting-notes.md` (recurring bug classes) — skim the section
|
||||
headers, read the classes relevant to the task.
|
||||
- **Tier 2 — on demand only, do NOT read start-to-finish:**
|
||||
- `docs/internals.md` — architecture / RSP deltas / phased plan (§1–§10
|
||||
of the old research doc). Read the section you need.
|
||||
- `docs/dev/findings.md` — the `Dxx` finding log (§11 + §F + §H).
|
||||
- `docs/internals.md` — architecture / RSP deltas / phased plan (§1–§10).
|
||||
Read the section you need.
|
||||
- `docs/dev/findings.md` — the `Dxx` finding log (§F + §H).
|
||||
**Jump to a specific `Dxx` via the index at the top of §F.** Never
|
||||
linear-read.
|
||||
- `docs/dev/HANDOFF-ARCHIVE.md` — prior-session narrative (M-2…). Only
|
||||
@@ -33,8 +34,9 @@ Context is scarce. Load by tier; do not blind-read whole files.
|
||||
Having a concrete "next step" from the handoff is NOT license to skip this.
|
||||
|
||||
1. Read the Tier 1 docs: `docs/HANDOFF.md` (immediate task, standing
|
||||
procedure, environment gotchas) and `docs/porting-notes.md`
|
||||
(recurring bug classes — you will re-derive catalogued bugs if you don't).
|
||||
procedure, environment gotchas — or the README "Status" section if it is
|
||||
absent) and `docs/porting-notes.md` (recurring bug classes — you will
|
||||
re-derive catalogued bugs if you don't).
|
||||
2. Skim the README "Status" section for where the project stands.
|
||||
3. If you may dispatch a subagent this session, read `docs/dev-process.md`
|
||||
NOW — not at dispatch time.
|
||||
|
||||
@@ -11,7 +11,7 @@ keep the port faithful to the original game.
|
||||
belong to the N64 build and are never touched for PC work. If PC code seems
|
||||
to need a behavioural change in the game, the fix belongs in `port/`.
|
||||
|
||||
2. **Narrow ABI exception.** The 32->64-bit transition forces a small class of
|
||||
2. **Narrow ABI exception.** The 32→64-bit transition forces a small class of
|
||||
mechanical, semantics-preserving edits to ROM-serialized structs (storing an
|
||||
embedded 32-bit pointer as `u32` and casting at the use site). These are
|
||||
allowed, must be guarded with `#ifdef PORT`, must change no behaviour, and
|
||||
@@ -35,6 +35,6 @@ keep the port faithful to the original game.
|
||||
## Where to look
|
||||
|
||||
- `docs/internals.md` — how the port is structured.
|
||||
- `docs/porting-notes.md` — the recurring bug classes; check here before
|
||||
debugging a crash, you are likely looking at a known pattern.
|
||||
- `docs/porting-notes.md` — the recurring bug classes. Check here before
|
||||
debugging a crash; you are likely looking at a known pattern.
|
||||
- `docs/dev/` — the full finding log and per-level status.
|
||||
@@ -1,5 +1,10 @@
|
||||
# GoldenEye 007 — PC port
|
||||
|
||||
-orange)
|
||||

|
||||

|
||||

|
||||
|
||||
A work-in-progress native port of **GoldenEye 007** (Rare, 1997) to modern
|
||||
desktop platforms, built on top of the
|
||||
[GoldenEye decompilation](https://github.com/n64decomp/007).
|
||||
@@ -11,26 +16,33 @@ sources are compiled for the host; the N64's Reality Signal Processor is
|
||||
emulated in software; every other hardware surface (video, audio, input,
|
||||
timers, save storage) is shimmed in a dedicated `port/` layer.
|
||||
|
||||
> [!IMPORTANT]
|
||||
> **You must supply your own GoldenEye 007 ROM.** This repository contains no
|
||||
> Nintendo code or assets, and no ROM. Nothing here is distributable as a
|
||||
> playable game — see [Requirements](#requirements) and [Legal](#legal).
|
||||
|
||||
<p align="center">
|
||||
<img src="docs/img/archives-1.png" width="49%" alt="Archives level rendering in the port">
|
||||
<img src="docs/img/bunker1-1.png" width="49%" alt="Bunker 1 rendering in the port">
|
||||
<br>
|
||||
<img src="docs/img/archives-2.png" width="32%" alt="Guards in the Archives level">
|
||||
<img src="docs/img/bunker1-2.png" width="32%" alt="Bunker 1 with HUD">
|
||||
<img src="docs/img/bunker1-3.png" width="32%" alt="Bunker 1 storage room">
|
||||
<br><em>In-engine captures — Archives and Bunker 1 running in the port.</em>
|
||||
<img src="docs/img/attract-bunker1.png" width="32%" alt="Bunker 1 intro camera">
|
||||
<img src="docs/media/goldeneye-demo.gif" width="32%" alt="~15 s of the port running: mission dossier, Facility, Silo, Jungle, Archives">
|
||||
<img src="docs/img/attract-dam.png" width="32%" alt="Dam intro camera">
|
||||
<br><em>In-engine, running in the port — Bunker 1 and Dam attract views, and a
|
||||
~15 s clip (no audio yet, Phase 3): mission dossier → Facility → Silo →
|
||||
Jungle → Archives.</em>
|
||||
</p>
|
||||
|
||||
> **Not playable yet.** This is a work-in-progress research port. The intro and
|
||||
> menus render and all 21 solo levels load, but it is **not** a complete or
|
||||
> reliably playable game: there is **no audio**, the front-end 3D models and
|
||||
> some text are broken, input has known rough edges, and you should expect
|
||||
> crashes and glitches once you are past the level intro. Treat it as a
|
||||
> technical demo of the porting work, not a way to play GoldenEye.
|
||||
## Contents
|
||||
|
||||
- [Background](#background)
|
||||
- [Status](#status)
|
||||
- [Requirements](#requirements)
|
||||
- [Building](#building) · [Windows (MSYS2)](#windows-msys2) · [Linux](#linux)
|
||||
- [Running](#running) · [Default controls](#default-controls)
|
||||
- [How it works](#how-it-works)
|
||||
- [Project layout](#project-layout)
|
||||
- [Documentation](#documentation)
|
||||
- [Credits](#credits)
|
||||
- [Legal](#legal)
|
||||
- [License](#license)
|
||||
|
||||
## Background
|
||||
|
||||
@@ -55,33 +67,42 @@ It used two agents:
|
||||
The two **handed work back and forth** through shared written artifacts:
|
||||
|
||||
```mermaid
|
||||
flowchart LR
|
||||
H["human<br/>direction · integration<br/>build + playtest"]
|
||||
flowchart TD
|
||||
H["human<br/>direction · integration · playtest"]
|
||||
C["Claude<br/>(Claude Code)"]
|
||||
Q["Qwen 3.8<br/>(pi, local RTX 5090)"]
|
||||
D[("shared artifacts<br/>finding log · bug-class notes · handoff doc")]
|
||||
D[("shared artifacts<br/>findings · notes · handoff doc")]
|
||||
H -->|"scoped task + budget"| C
|
||||
H -->|"scoped task + budget"| Q
|
||||
C <-->|read / append| D
|
||||
Q <-->|read / append| D
|
||||
C -.->|"hit usage limit ->"| Q
|
||||
Q -.->|"needs deeper reasoning ->"| C
|
||||
C -->|"patch + write-up"| H
|
||||
Q -->|"patch + write-up"| H
|
||||
C -->|"patch + write-up"| D
|
||||
Q -->|"patch + write-up"| D
|
||||
C <-.->|handoff| Q
|
||||
D --> H
|
||||
```
|
||||
|
||||
The handoff document was originally a session-to-session note; it became the
|
||||
**interface between the two models** — when Claude hit a usage limit
|
||||
mid-problem, the local model picked the task up from that state and continued.
|
||||
|
||||
**By the numbers:** ~2 weeks, one person part-time · 217 commits · 160
|
||||
root-caused bugs logged · ~30 handoff sessions · `#ifdef PORT` ABI edits in 63
|
||||
game-source files · ~17k lines of port layer + ~6k lines of Python asset
|
||||
tooling. By day 4 the full ~230-unit codebase compiled and linked; by day 8
|
||||
the intro rendered; by **day 13 all 21 solo missions ran crash-free**; by
|
||||
day 14 the front end was playable end to end. Estimated effort split
|
||||
(milestone-weighted): **~60% Claude / ~40% local model** — the local model
|
||||
built the entire foundation (build, boot, RSP wiring, converters).
|
||||
**By the numbers:**
|
||||
|
||||
| Metric | Value |
|
||||
|---|---|
|
||||
| Timeline | ~2 weeks, one person part-time |
|
||||
| Commits | ~223 |
|
||||
| Root-caused bugs logged | 162 (`D1`–`D169`; some later merged or withdrawn) |
|
||||
| Handoff sessions | ~33 |
|
||||
| ABI edits to game code | 63 files, all `#ifdef PORT` |
|
||||
| Port layer / tooling | ~17k lines C/C++ · ~6k lines Python |
|
||||
| Effort split (milestone-weighted) | ~60% Claude · ~40% local model |
|
||||
|
||||
The local model built the entire foundation — build, boot chain, RSP wiring,
|
||||
asset converters — then both agents ran the debugging phase together:
|
||||
|
||||
- **Day 4** — the full ~230-unit codebase compiles and links
|
||||
- **Day 8** — the whole intro renders
|
||||
- **Day 13** — all 21 solo missions run crash-free
|
||||
- **Day 14** — front end playable end to end
|
||||
|
||||
Full write-up, timeline chart, and an honest "what worked / what didn't":
|
||||
[`docs/dev/agentic-development.md`](docs/dev/agentic-development.md). The
|
||||
@@ -89,13 +110,21 @@ workflow itself: [`docs/dev-process.md`](docs/dev-process.md).
|
||||
|
||||
## Status
|
||||
|
||||
> [!WARNING]
|
||||
> **Not playable yet.** This is a work-in-progress research port. The intro and
|
||||
> menus render and all 21 solo levels load, but it is **not** a complete or
|
||||
> reliably playable game: there is **no audio**, the front-end 3D models and
|
||||
> some text are broken, input has known rough edges, and you should expect
|
||||
> crashes and glitches once you are past the level intro. Treat it as a
|
||||
> technical demo of the porting work, not a way to play GoldenEye.
|
||||
|
||||
**Phase 2 of 4 (rendering).** The port boots, renders, and is playable through
|
||||
the front end into the early game. It is not finished and it is not stable.
|
||||
|
||||
**Working**
|
||||
|
||||
- Boot -> Rare/Nintendo logos -> gun-barrel -> cast intro, fully rendered.
|
||||
- Front end: main menu -> mission select -> difficulty -> briefing -> mission start.
|
||||
- Boot → Rare/Nintendo logos → gun-barrel → cast intro, fully rendered.
|
||||
- Front end: main menu → mission select → difficulty → briefing → mission start.
|
||||
- **All 21 solo missions load, render, and survive an unattended play window
|
||||
without crashing** (see [`docs/dev/LEVEL-STATUS.md`](docs/dev/LEVEL-STATUS.md)).
|
||||
- Software RSP (fast3d): textured world geometry, skeletal characters, HUD,
|
||||
@@ -107,8 +136,9 @@ the front end into the early game. It is not finished and it is not stable.
|
||||
**Not yet working**
|
||||
|
||||
- **Audio** — not implemented (Phase 3). The game runs silent.
|
||||
- Front-end 3D models (spinning Nintendo logo, gun-barrel Bond, cast) are
|
||||
mispositioned or absent.
|
||||
- Some front-end 3D models — the spinning Nintendo logo, and the MISSION
|
||||
COMPLETE / mode-select models — are mispositioned or absent. (The
|
||||
gun-barrel Bond intro renders correctly.)
|
||||
- Assorted cosmetic defects (some text layout, a few incomplete asset
|
||||
conversions) are tracked in
|
||||
[`docs/dev/GRAPHICS-BACKLOG.md`](docs/dev/GRAPHICS-BACKLOG.md) and parked
|
||||
@@ -173,7 +203,8 @@ cd goldeneye-pc-port
|
||||
./build-pc.sh ntsc-final
|
||||
```
|
||||
|
||||
The executable is written to `build-pc/ge007.x86_64` (Windows: `.exe`).
|
||||
The executable is written to `build-pc/ge007.x86_64` (on Windows,
|
||||
`build-pc/ge007.x86_64.exe`).
|
||||
|
||||
## Running
|
||||
|
||||
@@ -188,13 +219,13 @@ Configuration is written to `ge007.ini` on first run.
|
||||
### Default controls
|
||||
|
||||
| Action | Keyboard / mouse | Controller |
|
||||
|-------------------|-------------------------|-----------------------|
|
||||
|---------------------|--------------------------|---------------|
|
||||
| Move / strafe | `W` `A` `S` `D` / arrows | Left stick |
|
||||
| Aim / look | Mouse | Right stick |
|
||||
| Fire (Z) | Left mouse / `LCtrl` | Right trigger |
|
||||
| Aim mode (R) | Right mouse / `LShift` | Left trigger |
|
||||
| Use / accept (A) | `Space` / `E` | A / X |
|
||||
| Reload / cancel (B)| `R` / `F` | B / Y / RB |
|
||||
| Use / accept (A) | `Space` / `E` / `X` | A / X |
|
||||
| Reload / cancel (B) | `R` / `F` | B / Y / RB |
|
||||
| L trigger | `Q` | LB |
|
||||
| Start | `Enter` / `Tab` | Start |
|
||||
|
||||
@@ -217,7 +248,7 @@ touch N64 hardware is redirected into `port/`:
|
||||
- **`port/src/{video,audio,input,fs,romdata,config}.c`** — the SDL2 / OpenGL /
|
||||
filesystem backends.
|
||||
|
||||
The 32->64-bit transition forces a small, catalogued class of mechanical
|
||||
The 32→64-bit transition forces a small, catalogued class of mechanical
|
||||
ABI-only edits to ROM-serialized structs (pointer-width reconciliation); these
|
||||
change no behaviour and are documented individually.
|
||||
|
||||
@@ -244,21 +275,15 @@ docs/ see below
|
||||
|
||||
## Documentation
|
||||
|
||||
- [`docs/building.md`](docs/building.md) — full build + asset-extraction guide.
|
||||
- [`docs/internals.md`](docs/internals.md) — architecture, the RSP-emulation
|
||||
approach, GE-vs-PD engine differences, the phased plan.
|
||||
- [`docs/porting-notes.md`](docs/porting-notes.md) — the recurring N64->PC bug
|
||||
classes hit during the port, with fixes.
|
||||
- [`docs/dev/agentic-development.md`](docs/dev/agentic-development.md) — the
|
||||
research angle: the two-agent setup, timeline, handoff workflow, and a
|
||||
candid assessment of what did and didn't work.
|
||||
- [`docs/dev-process.md`](docs/dev-process.md) — the investigation workflow in
|
||||
detail (budgets, file partitioning, the finding-log discipline).
|
||||
- [`docs/dev/`](docs/dev/) — the raw engineering record: the full finding log,
|
||||
per-level status, graphics backlog, playtest matrices.
|
||||
- [`docs/SetupGuide.md`](docs/SetupGuide.md),
|
||||
[`docs/StructureGuide.md`](docs/StructureGuide.md),
|
||||
[`docs/StyleGuide.md`](docs/StyleGuide.md) — inherited from the decompilation.
|
||||
| Doc | What's in it |
|
||||
|---|---|
|
||||
| [`docs/building.md`](docs/building.md) | Full build + asset-extraction guide. |
|
||||
| [`docs/internals.md`](docs/internals.md) | Architecture, the RSP-emulation approach, GE-vs-PD engine differences, the phased plan. |
|
||||
| [`docs/porting-notes.md`](docs/porting-notes.md) | The recurring N64→PC bug classes hit during the port, with fixes. |
|
||||
| [`docs/dev/agentic-development.md`](docs/dev/agentic-development.md) | The research angle: the two-agent setup, timeline, handoff workflow, and an assessment of what did and didn't work. |
|
||||
| [`docs/dev-process.md`](docs/dev-process.md) | The investigation workflow in detail — budgets, file partitioning, the finding-log discipline. |
|
||||
| [`docs/dev/`](docs/dev/) | The raw engineering record: the full finding log, per-level status, graphics backlog, playtest matrices. |
|
||||
| [`docs/SetupGuide.md`](docs/SetupGuide.md), [`docs/StructureGuide.md`](docs/StructureGuide.md), [`docs/StyleGuide.md`](docs/StyleGuide.md) | Inherited from the decompilation. |
|
||||
|
||||
## Credits
|
||||
|
||||
@@ -267,7 +292,7 @@ This port is a thin layer on a large amount of other people's work.
|
||||
**Prior work it is built on**
|
||||
|
||||
- The [GoldenEye 007 decompilation](https://github.com/n64decomp/007) — years of
|
||||
effort by kholdfuzion, Larry Ficken, and the project's contributors; plus
|
||||
effort by Larry Ficken ("kholdfuzion") and the project's contributors; plus
|
||||
zoinkity's GoldenEye documentation, which the decomp started from. This port
|
||||
is a fork of that repository.
|
||||
- The [Perfect Dark PC port](https://github.com/fgsfdsfgs/perfect_dark)
|
||||
@@ -298,8 +323,11 @@ This port is a thin layer on a large amount of other people's work.
|
||||
|
||||
**Tools and models used to develop the port**
|
||||
|
||||
- [Qwen 3.8](https://github.com/QwenLM/Qwen) (Alibaba Qwen team);
|
||||
[Unsloth](https://unsloth.ai) (the GGUF quantisation and Unsloth Desktop).
|
||||
- Qwen 3.8 (Alibaba Qwen team), run locally as the
|
||||
[`unsloth/Qwen3.8-27B-GGUF`](https://huggingface.co/unsloth/Qwen3.8-27B-GGUF)
|
||||
`UD-Q4_K_XL` quant;
|
||||
[Unsloth](https://unsloth.ai) (the GGUF quantisation and Unsloth Desktop,
|
||||
used as the local model server).
|
||||
- [pi](https://pi.dev/) — the local coding-agent harness.
|
||||
- [Claude / Claude Code](https://claude.com/claude-code) (Anthropic).
|
||||
|
||||
|
||||
@@ -5,14 +5,14 @@
|
||||
# Usage:
|
||||
# ./build-pc.sh [ntsc-final|pal-final|jpn-final]
|
||||
#
|
||||
# Dependencies (see docs/internals.md):
|
||||
# Dependencies (see docs/building.md):
|
||||
# - CMake >= 3.16
|
||||
# - SDL2 dev
|
||||
# - zlib dev
|
||||
# - OpenGL dev (opengl32 on Windows, GL on Linux, OpenGL.framework on macOS)
|
||||
#
|
||||
# Example (Linux):
|
||||
# sudo apt install cmake libsdl2-dev zlib1g-dev libgl4-mesa-dev
|
||||
# sudo apt install cmake libsdl2-dev zlib1g-dev libgl1-mesa-dev
|
||||
# Example (macOS):
|
||||
# brew install cmake sdl2 zlib
|
||||
# Example (Windows/MSYS2):
|
||||
|
||||
@@ -88,9 +88,23 @@ This project can compile the ROM's C code in one of two ways, controlled by the
|
||||
[qemu-irix](https://github.com/n64decomp/qemu-irix/releases) user-mode emulator instead. Slower, but useful as a
|
||||
lower-risk reference if you ever suspect the recompiled toolchain is misbehaving.
|
||||
|
||||
> **The IRIX IDO binaries are not distributed with this repository.** They are
|
||||
> proprietary SGI software and only ever ran on IRIX/MIPS. Neither `tools/irix/`
|
||||
> nor `tools/SGIImageViewer.exe` is committed here; the **PC port does not need
|
||||
> them at all** (asset extraction uses `tools/extractor`, and the port itself
|
||||
> builds with CMake + your host compiler). You only need the IDO toolchain to
|
||||
> build the actual **N64 ROM** or to regenerate `tools/ido5.3_recomp`. To get it:
|
||||
> obtain the IDO 5.3 tree from an IRIX 5.3 installation, from
|
||||
> [`decompals/ido-static-recomp`](https://github.com/decompals/ido-static-recomp)
|
||||
> (which documents where its input binaries come from), or from the N64
|
||||
> decompilation community, and place it at `tools/irix/root/` (with `cc` etc.
|
||||
> under `tools/irix/root/usr/bin/`). `tools/SGIImageViewer.exe` is an optional
|
||||
> convenience only.
|
||||
|
||||
The recompiled toolchain isn't checked into git — it's generated locally the first time it's needed, from the
|
||||
original IDO binaries in `tools/irix/root`. A plain `make` from the repo root builds it automatically if it's
|
||||
missing (wired up via `tools/Makefile`), so most people never need to run this step by hand. To build it explicitly
|
||||
original IDO binaries in `tools/irix/root` (see the note above on obtaining those). A plain `make` from the repo
|
||||
root builds it automatically if it's missing (wired up via `tools/Makefile`), so most people never need to run
|
||||
this step by hand. To build it explicitly
|
||||
(e.g. to watch its own build output, or force a rebuild after changing it):
|
||||
|
||||
```bash
|
||||
|
||||
@@ -35,10 +35,13 @@ versions and hashes.
|
||||
### Asset extraction (decompilation toolchain)
|
||||
|
||||
The extraction scripts need `binutils-mips-linux-gnu` (or an equivalent MIPS
|
||||
binutils), `make`, `git`, `python3`, and `qemu-irix` for the IRIX IDO
|
||||
compiler. On Windows this is easiest under WSL or a Linux VM. Full details and
|
||||
alternatives (Docker, the recompiled IDO toolchain) are in
|
||||
[`SetupGuide.md`](SetupGuide.md).
|
||||
binutils), `make`, `git`, and `python3`. They build a small host-compiled
|
||||
`tools/extractor` and slice blobs straight out of the ROM — **no IDO / IRIX
|
||||
toolchain is involved in extraction or in the PC build.** (The IDO toolchain is
|
||||
only needed to build the N64 ROM itself, and its proprietary SGI binaries are
|
||||
not distributed here — see [`SetupGuide.md`](SetupGuide.md) "Recompile IDO".)
|
||||
On Windows this is easiest under WSL or a Linux VM. Full details and
|
||||
alternatives (Docker) are in [`SetupGuide.md`](SetupGuide.md).
|
||||
|
||||
---
|
||||
|
||||
|
||||
@@ -40,14 +40,14 @@ more room.
|
||||
|
||||
Lewis's agents recorded generalisable IDO quirks in a learnings file; later
|
||||
agents read it and did better. Our equivalent is
|
||||
[`porting-notes.md`](porting-notes.md) — the recurring N64->PC bug classes,
|
||||
one screen, each entry an index into the full [`dev/findings.md`](dev/findings.md)
|
||||
[`porting-notes.md`](porting-notes.md) — the recurring N64→PC bug classes,
|
||||
each entry a terse index into the full [`dev/findings.md`](dev/findings.md)
|
||||
log. Every investigation brief links it, and every investigation ends by
|
||||
appending any new generalisable quirk.
|
||||
|
||||
The classes it currently tracks:
|
||||
|
||||
- pointer-width struct growth (32->64) in ROM-serialized or pun-allocated
|
||||
- pointer-width struct growth (32→64) in ROM-serialized or pun-allocated
|
||||
structs — the dominant class;
|
||||
- 16-byte host `Gfx`/`Vtx` vs 8-byte N64 — reservation and copy sizing;
|
||||
- big-endian rodata read on a little-endian host: `f32` word-pairs, header
|
||||
|
||||
@@ -7,6 +7,24 @@ for closing **D77** (no audible music/sound on PC). Companion docs: `docs/HANDOF
|
||||
|
||||
---
|
||||
|
||||
## Contents
|
||||
|
||||
1. [Goal and scope](#1-goal-and-scope)
|
||||
2. [Current state](#2-current-state-verified-by-reading-not-assumption)
|
||||
3. [The GE pipeline in one paragraph](#3-the-ge-pipeline-in-one-paragraph)
|
||||
4. [How the PD port does it](#4-how-the-pd-port-does-it-ground-truth-comparison)
|
||||
5. [Architecture options](#5-architecture-options-evaluate-all-recommendation-marked) — options A/B/C + sub-decisions A1–A3
|
||||
6. [DMEM layout](#6-dmem-layout-ido-from-srclibultraaudiosynthinternalsh5771)
|
||||
7. [Shims and ABI fixes required](#7-shims-and-abi-fixes-required) — incl. [7.1 `K0_TO_PHYS` bug](#71-bug-found-k0_to_phys-is-unshimmed-and-corrupts-pointers-on-pc)
|
||||
8. [Phase 0 — recon](#8-phase-0--recon-do-first-informs-everything)
|
||||
9. [Open questions](#9-open-questions-decide-before-phase-1)
|
||||
10. [Phases and milestones](#10-phases-and-milestones)
|
||||
11. [Verification ritual (audio-specific)](#11-verification-ritual-audio-specific-on-top-of-the-standard-one-in-agentsmd)
|
||||
12. [Risks / unknowns](#12-risks--unknowns)
|
||||
13. [Key references](#13-key-references)
|
||||
|
||||
---
|
||||
|
||||
## 1. Goal and scope
|
||||
|
||||
Make GoldenEye's audio audible on the PC port with 1:1 fidelity to the N64 pipeline:
|
||||
|
||||
@@ -16,6 +16,9 @@ once the game is playable start-to-finish without crashes.
|
||||
| ~~**D116 (HUD)**~~ | ~~proportional-font strings + ammo counter mirrored~~ | **CLOSED — NOT A BUG (M-33, §F D168).** Same capture-orientation artifact as D114. |
|
||||
| **D148** | Level-end cinematics don't play. Dam: hitting the exit trigger should show Bond rappelling down the dam (the bungee jump); instead it cuts straight to the mission-complete report. | Scripted cutscene / cinematic-camera + Bond rappel anim. Found M-27 during the first full Dam→Facility playthrough. Progression is unaffected — the report and next briefing load fine. **M-31 (§F D160):** static-traced the Dam end ailists (`ai_24`→`ai_17`, `camera_switch`→`CutsceneRecord` type-46 lookup). Diagnostic `GE_D160=1` shipped (`c95713f5`) — user runs Dam to the exit with it set; the trace pins whether the cutscene AI runs, and whether the propDef-index walk (D122/D132 family) hands `camera_switch` a bogus cutscene record. Leading hypothesis: propDef `sizepropdef` stride desync (medium confidence), not D75 anim-model. |
|
||||
| **D149** | Front-end MISSION COMPLETE / mode-select 3D models (dossier, wallets) render as garbled full-screen geometry or not at all — one of the compiled sub-DLs (seg5+0x9ee4) is malformed, D146 now skips it instead of aborting. | D75 family. §F D146. |
|
||||
| **D170** | Named-NPC "flee" scripted behaviour looks wrong on PC: on Silo, Ourumov breaks into a full run the instant he alerts ("Ourumov: Kill him!") rather than the N64 walk/retreat; developer reports Trevelyan behaves the same way on Cradle. | **Observed, not investigated** (M-34, from a Silo playtest capture; user bug report — no fix wanted yet). Could be a genuine ailist / `chrTick` divergence, OR the D155/D156 wall-clock `deltaFrames` locomotion-anim speed-up (a catch-up spike playing the walk cycle at 2–3×). **Verify first:** capture the same beat against N64 reference footage before assuming it diverges — Ourumov may be scripted to flee. If it's real, suspect the frametiming clamp (§F D155/D156) or the Cradle-family AI path (§F D123). |
|
||||
| **D171** | Silo missile-shaft: a large translucent grey triangle sweeps across the lower frame while panning down the shaft (~3 s of the capture). Looks like a stray poly / near-plane clip fan, same family as D106 (portal near-plane min>max). | **Observed, not investigated** (M-34, Silo capture). Cosmetic, intermittent, tied to camera angle in the open vertical shaft. |
|
||||
| **D172** | Bullet-impact / blood particle spray renders magenta or cyan instead of dark red (visible on guards hit at close range on Silo). | **Observed, not investigated** (M-34, Silo capture). A channel-order / CC-mode error in the particle-sprite path (magenta = R+B, cyan = G+B) — not the D64/D120 blood-decal family (those are crash/hang + missing decals, not colour). Likely a texture-format or env-colour decode in `blood_animation.c` / the fast3d sprite path. |
|
||||
|
||||
## Resolved (for reference)
|
||||
|
||||
|
||||
@@ -1,8 +1,9 @@
|
||||
# HANDOFF ARCHIVE — session-by-session narrative
|
||||
|
||||
> **Reference only.** Current state, next task, and environment live in
|
||||
> `docs/HANDOFF.md`; per-finding detail in `docs/internals.md` §F/§H
|
||||
> (indexed at the top of §F). This file is the frozen accumulation of
|
||||
> **Reference only.** Current state lives in the [README](../../README.md)
|
||||
> "Status" section and `docs/dev/LEVEL-STATUS.md`; per-finding detail is in
|
||||
> [`findings.md`](findings.md) §F/§H (indexed at the top of §F). This file
|
||||
> is the frozen accumulation of
|
||||
> prior sessions' handoff briefs (through session M-11), kept so the
|
||||
> reasoning behind a fix is recoverable. Everything below is as-written
|
||||
> at the time and may be superseded.
|
||||
|
||||
@@ -1,4 +1,19 @@
|
||||
# Agentic development: goal, method, timeline, assessment
|
||||
# Agentic development: a two-agent experiment
|
||||
|
||||
*A GoldenEye 007 N64→desktop port, taken from "builds a ROM" to "playable front
|
||||
end" in about two weeks — driven mostly by two coding agents, a local
|
||||
open-weight model and a hosted frontier model, handing work back and forth
|
||||
through shared written notes under one person's direction. This is the goal,
|
||||
the method, the timeline, and an honest read on what did and didn't work.*
|
||||
|
||||
## Contents
|
||||
|
||||
- [Why this project exists](#why-this-project-exists)
|
||||
- [The setup](#the-setup)
|
||||
- [Timeline](#timeline)
|
||||
- [By the numbers](#by-the-numbers) — [Commit velocity](#commit-velocity) · [Who did what](#who-did-what)
|
||||
- [The handoff workflow](#the-handoff-workflow)
|
||||
- [Assessment](#assessment)
|
||||
|
||||
## Why this project exists
|
||||
|
||||
@@ -26,10 +41,10 @@ and forth** through shared written artifacts, directed by one human.
|
||||
|
||||
| | |
|
||||
|---|---|
|
||||
| Local agent | `unsloth/Qwen3.8-27B-GGUF:UD-Q4_K_XL` on a single **NVIDIA RTX 5090**, driven mainly through the **[pi](https://pi.dev/)** coding agent. Unsloth Desktop (a newer local agentic-coding harness) was also trialed but not used significantly. |
|
||||
| Local agent | `unsloth/Qwen3.8-27B-GGUF:UD-Q4_K_XL` on a single **NVIDIA RTX 5090**, driven mainly through the **[pi](https://pi.dev/)** coding agent. Unsloth Desktop (Unsloth's local model runtime, which can drive agents such as Claude Code) was also trialed but not used significantly. |
|
||||
| Hosted agent | **Claude**, via **Claude Code**, on a Claude Pro subscription — mostly **Sonnet 5**, with **Opus 5** used as an escalation tier for the hardest problems and whenever there was subscription budget to spend on it |
|
||||
| Human | one person: direction, work partitioning, integration, and every build / playtest / frame-capture the agents could not run |
|
||||
| Base | fork of the [GoldenEye 007 decompilation](https://github.com/n64decomp/007) (years of prior work by Larry Ficken / "KholdFuzion" and contributors) |
|
||||
| Base | fork of the [GoldenEye 007 decompilation](https://github.com/n64decomp/007) (years of prior work by Larry Ficken ("kholdfuzion") and contributors) |
|
||||
| Reused | the [Perfect Dark PC port](https://github.com/fgsfdsfgs/perfect_dark)'s `fast3d` software RSP — same Rare engine family |
|
||||
|
||||
The port is the GoldenEye-specific porting work **on top of** those two
|
||||
@@ -56,13 +71,13 @@ gantt
|
||||
OS shims, threads, fast3d integration :2026-08-21, 2d
|
||||
First rendered frames :m4, 2026-08-22, 1d
|
||||
Offline asset-conversion pipeline :2026-08-22, 2d
|
||||
Entire intro renders (logos->cast) :m5, 2026-08-24, 1d
|
||||
Entire intro renders (logos to cast) :m5, 2026-08-24, 1d
|
||||
section Both agents - handoff workflow
|
||||
Claude joins :milestone, 2026-08-27, 0d
|
||||
Stage load; Bunker 1 renders + firefight :2026-08-27, 2d
|
||||
21 solo levels: load + render + no-crash :m6, 2026-08-29, 1d
|
||||
21 solo levels load + render + no-crash :m6, 2026-08-29, 1d
|
||||
SDL input layer (kbd/mouse/gamepad) :2026-08-29, 1d
|
||||
Front-end flow menu->briefing->start :m7, 2026-08-30, 1d
|
||||
Front-end flow (menu to briefing to start) :m7, 2026-08-30, 1d
|
||||
File-backed EEPROM saves :2026-08-31, 1d
|
||||
```
|
||||
|
||||
@@ -75,26 +90,22 @@ gantt
|
||||
- **Day 11** (27 Aug): second agent joins.
|
||||
- **Day 13** (29 Aug): **all 21 solo missions load, render, and survive an
|
||||
unattended play window without crashing.**
|
||||
- **Day 14** (30–31 Aug): front end playable end to end (menu -> mission
|
||||
select -> difficulty -> briefing -> start); file-backed saves.
|
||||
- **Day 14** (30–31 Aug): front end playable end to end (menu → mission
|
||||
select → difficulty → briefing → start); file-backed saves.
|
||||
|
||||
So roughly **two weeks**, one person part-time, to take a decompilation from
|
||||
"builds an N64 ROM" to "boots on desktop, renders every solo level, playable
|
||||
through the front end into the early game" — with audio and a set of cosmetic
|
||||
issues still outstanding.
|
||||
|
||||
We are not aware of a prior Nintendo 64 native PC port developed primarily
|
||||
through coding agents, or of one reaching this state on this timeline. That is
|
||||
a statement about how little precedent there is, not a claim of a record.
|
||||
|
||||
## By the numbers
|
||||
|
||||
| | |
|
||||
|---|---|
|
||||
| Calendar time | 16 days (16 Aug – 1 Sep 2026), one person part-time |
|
||||
| Commits on the port | 217 |
|
||||
| Root-caused bugs logged | 160 (`D1`–`D167` in [`findings.md`](findings.md)) |
|
||||
| Handoff sessions | ~30 (`M-2` … `M-32`) |
|
||||
| Commits on the port | ~223 |
|
||||
| Root-caused bugs logged | 162 (`D1`–`D169` in [`findings.md`](findings.md); some later merged or withdrawn) |
|
||||
| Handoff sessions | ~33 (`M-2` … `M-33`) |
|
||||
| Game-source files given `#ifdef PORT` ABI edits | 63 files, 241 blocks |
|
||||
| New port-layer / tooling files | 128 |
|
||||
| Port layer | ~17,000 lines C/C++ (`port/`) |
|
||||
@@ -108,20 +119,24 @@ xychart-beta
|
||||
title "Commits per day"
|
||||
x-axis ["8/16", "8/17", "8/20", "8/21", "8/22", "8/23", "8/24", "8/27", "8/28", "8/29", "8/30", "8/31", "9/1"]
|
||||
y-axis "commits" 0 --> 60
|
||||
bar [1, 2, 2, 6, 9, 2, 4, 7, 57, 39, 39, 46, 3]
|
||||
bar [1, 2, 2, 6, 9, 2, 4, 7, 57, 39, 39, 46, 9]
|
||||
```
|
||||
|
||||
The 8/25–8/26 gap is between phases; the jump on 8/28 is the second agent
|
||||
joining, plus the parallel multi-agent "bursts" used near the end.
|
||||
Days with no commits are omitted. The 8/25–8/26 gap is between phases; the
|
||||
step up from 8/28 onward is the collaborative phase in full swing, including
|
||||
the parallel multi-agent "bursts" used near the end.
|
||||
|
||||
### Who did what
|
||||
|
||||
```mermaid
|
||||
pie showData title "Commits by phase"
|
||||
"Phase A - local model, solo (16-24 Aug)" : 26
|
||||
"Phase B - collaborative (27 Aug-1 Sep)" : 191
|
||||
pie showData title "Commits by agent (raw count)"
|
||||
"Claude" : 161
|
||||
"Local model (Qwen 3.8 / pi)" : 62
|
||||
```
|
||||
|
||||
(Phase A — the first 26 commits, to 24 Aug — was entirely the local model,
|
||||
solo; from 27 Aug on the two agents worked in parallel.)
|
||||
|
||||
| Milestone / workstream | Primary agent | Weight |
|
||||
|---|---|---|
|
||||
| PC build system, region macros, full compile + link of ~230 units | local model | large |
|
||||
@@ -130,7 +145,7 @@ pie showData title "Commits by phase"
|
||||
| Offline asset-conversion architecture + first converters (`tools_pc/`) | local model | large |
|
||||
| Intro rendering (logos → gun-barrel → cast) | local model | medium |
|
||||
| Stage load unblocked (`D69`–`D87`) | Claude | medium |
|
||||
| 21-level crash sweep — ~12 crash classes root-caused (`D88`–`D167`) | Claude | large |
|
||||
| 21-level crash sweep — ~12 crash classes root-caused (`D88`–`D169`) | Claude | large |
|
||||
| SDL input layer (keyboard / mouse / gamepad, mouse-look) | Claude | medium |
|
||||
| Front-end flow (menu → briefing → start), EEPROM saves | Claude | medium |
|
||||
| Parallel struct-layout / converter static audits | local model | medium |
|
||||
@@ -138,14 +153,15 @@ pie showData title "Commits by phase"
|
||||
| The hardest structural bugs (matrix handedness, format specs) | Claude | — |
|
||||
| Every build, playtest, frame capture, integration, and direction | human | — |
|
||||
|
||||
**Estimated effort split.** By raw commit count it is ~28% local model /
|
||||
~72% Claude (Phase A entirely local, ~15–20% of Phase B local). Weighting by
|
||||
milestone difficulty rather than commit count — the foundation the local model
|
||||
built is a heavier third of the project than its commit count suggests — the
|
||||
developer's estimate is roughly:
|
||||
**Estimated effort split.** The raw commit count above (~28% local / ~72%
|
||||
Claude) undercounts the local model: Phase A landed the build system and boot
|
||||
chain in relatively few, large commits, and the local model kept contributing
|
||||
~15–20% of Phase B in parallel. Weighting by milestone difficulty rather than
|
||||
raw commits — the foundation is a heavier third of the project than its commit
|
||||
share suggests — the developer's estimate is roughly:
|
||||
|
||||
```mermaid
|
||||
pie showData title "Estimated agent effort (milestone-weighted)"
|
||||
pie showData title "Agent effort, milestone-weighted"
|
||||
"Claude" : 60
|
||||
"Local model (Qwen 3.8 / pi)" : 40
|
||||
```
|
||||
@@ -163,8 +179,8 @@ This is the part worth paying attention to.
|
||||
|
||||
```mermaid
|
||||
flowchart LR
|
||||
H[Human: direction, integration,<br/>build + playtest verification]
|
||||
C[Claude / Claude Code<br/>frontier, hosted]
|
||||
H["Human: direction, integration,<br/>build + playtest verification"]
|
||||
C["Claude / Claude Code<br/>frontier, hosted"]
|
||||
Q["Qwen 3.8 via pi<br/>open-weight, local RTX 5090"]
|
||||
D[(Shared artifacts:<br/>HANDOFF.md · findings.md · porting-notes.md)]
|
||||
|
||||
@@ -172,10 +188,10 @@ flowchart LR
|
||||
H -->|scopes task, budget, files| Q
|
||||
C <-->|reads / appends| D
|
||||
Q <-->|reads / appends| D
|
||||
C -.->|usage limit reached ->| Q
|
||||
Q -.->|hard structural bug ->| C
|
||||
C -->|patch + writeup| H
|
||||
Q -->|patch + writeup| H
|
||||
C -.->|usage limit reached| Q
|
||||
Q -.->|hard structural bug| C
|
||||
C -->|patch + write-up| H
|
||||
Q -->|patch + write-up| H
|
||||
```
|
||||
|
||||
Both agents worked against the **same three written artifacts**, which is what
|
||||
@@ -187,12 +203,12 @@ let them substitute for each other:
|
||||
usage limit mid-problem, the local model picked the task up from the
|
||||
HANDOFF state and continued; when the local model hit a bug that needed
|
||||
deeper structural reasoning, it wrote up where it was and Claude took over.
|
||||
2. **`findings.md`** — the chronological finding log. 160 numbered entries,
|
||||
2. **`findings.md`** — the chronological finding log. 162 numbered entries,
|
||||
each a root cause with `file:line` evidence and the fix. New agents (either
|
||||
model) are pointed at the relevant entries before they start.
|
||||
3. **`porting-notes.md`** — the append-only "recurring bug classes" file. The
|
||||
single highest-leverage artifact: it stopped both models from
|
||||
re-deriving the same class of N64->PC bug over and over.
|
||||
re-deriving the same class of N64→PC bug over and over.
|
||||
|
||||
Around these, the working rules (full detail in
|
||||
[`../dev-process.md`](../dev-process.md)):
|
||||
@@ -200,7 +216,7 @@ Around these, the working rules (full detail in
|
||||
- **file-partitioned tasks** — each agent's task scoped to a disjoint set of
|
||||
files so patches never collided;
|
||||
- **visible budgets** — every investigation task carried an explicit
|
||||
"N build->run cycles" limit and a defined fallback (revert probes, write up
|
||||
"N build→run cycles" limit and a defined fallback (revert probes, write up
|
||||
with a confidence rating);
|
||||
- **the human owns verification** — building, running the game, capturing a
|
||||
frame, and judging it against N64 reference footage was never delegated.
|
||||
|
||||
|
Before Width: | Height: | Size: 453 KiB |
|
Before Width: | Height: | Size: 380 KiB |
|
Before Width: | Height: | Size: 160 KiB |
|
Before Width: | Height: | Size: 318 KiB |
|
Before Width: | Height: | Size: 269 KiB |
|
Before Width: | Height: | Size: 268 KiB |
@@ -17,6 +17,27 @@ platforms.
|
||||
|
||||
---
|
||||
|
||||
## Contents
|
||||
|
||||
1. [Executive summary](#1-executive-summary)
|
||||
2. [What the PD port actually does (the reference architecture)](#2-what-the-pd-port-actually-does-the-reference-architecture)
|
||||
— [2.1 Emulate the RSP, bypass the RDP](#21-the-key-architectural-insight-emulate-the-rsp-bypass-the-rdp)
|
||||
· [2.2 How the RSP is invoked](#22-how-the-rsp-is-invoked)
|
||||
· [2.3 Build system](#23-build-system)
|
||||
· [2.4 PD-port copy-candidate audit](#24-pd-port-copy-candidate-audit-session-2026-08-22)
|
||||
3. [GoldenEye decomp: what we're porting](#3-goldeneye-decomp-what-were-porting)
|
||||
— [3.1 Entry / main loop](#31-entry--main-loop)
|
||||
· [3.2 The two libultra trees](#32-the-two-libultra-trees-srclibultra-and-srclibultrare)
|
||||
4. [N64 hardware surfaces that must be shimmed](#4-n64-hardware-surfaces-that-must-be-shimmed)
|
||||
5. [GE-specific graphics differences vs PD (the RSP work)](#5-ge-specific-graphics-differences-vs-pd-the-rsp-work)
|
||||
6. [Audio](#6-audio)
|
||||
7. [Input & saves](#7-input--saves)
|
||||
8. [Recommended plan](#8-recommended-plan) — phases 0–4
|
||||
9. [Open questions / risks](#9-open-questions--risks)
|
||||
10. [References](#10-references)
|
||||
|
||||
---
|
||||
|
||||
## 1. Executive summary
|
||||
|
||||
* **Feasibility: HIGH.** GoldenEye and Perfect Dark share the same Rare
|
||||
|
||||
|
After Width: | Height: | Size: 6.1 MiB |
@@ -1,13 +1,29 @@
|
||||
# Porting notes — recurring N64→PC bug classes
|
||||
|
||||
A one-screen field guide to the bug classes that keep recurring when running
|
||||
big-endian 32-bit N64 game code, unmodified, on a little-endian 64-bit host.
|
||||
Each entry cites a `Dxx` label; the full evidence and fix for that instance
|
||||
live in [`dev/findings.md`](dev/findings.md) under the same label.
|
||||
A field guide to the bug classes that keep recurring when running big-endian
|
||||
32-bit N64 game code, unmodified, on a little-endian 64-bit host. Terse by
|
||||
design — each entry compresses a full investigation to a symptom, a fix, and a
|
||||
grep heuristic for finding siblings. Each entry cites a `Dxx` label; the full
|
||||
evidence and fix for that instance live in [`dev/findings.md`](dev/findings.md)
|
||||
under the same label. Skim the section headers; read the classes relevant to
|
||||
the task at hand.
|
||||
|
||||
If you are debugging a crash in this port, read this first — the odds are
|
||||
good that you are looking at one of these.
|
||||
|
||||
## Contents
|
||||
|
||||
- [A. Pointer-width struct growth (32→64) — the dominant class](#a-pointer-width-struct-growth-3264--the-dominant-class)
|
||||
- [B. 16-byte PC `Gfx` / `Vtx` vs 8-byte N64](#b-16-byte-pc-gfx--vtx-vs-8-byte-n64)
|
||||
- [C. Big-endian rodata / ROM data read on little-endian PC](#c-big-endian-rodata--rom-data-read-on-little-endian-pc)
|
||||
- [C2. Port-layer / SDL shims](#c2-port-layer--sdl-shims)
|
||||
- [D. N64 hardware idioms fast3d does not emulate](#d-n64-hardware-idioms-fast3d-does-not-emulate)
|
||||
- [D2. The HUD/model "X-mirror" — RESOLVED](#d2-the-hudmodel-x-mirror-d114d116--resolved-it-was-an-upside-down-capture)
|
||||
- [D3. GCC/mingw makes an all-non-negative `enum` UNSIGNED](#d3-gccmingw-makes-an-all-non-negative-enum-unsigned)
|
||||
- [D4. N64 "interrupts off" must be a real lock on PC](#d4-n64-interrupts-off-is-not-free-on-pc--it-must-be-a-real-lock)
|
||||
- [D5. Loop bounds that assume linker adjacency of two globals](#d5-loop-bounds-that-assume-linker-adjacency-of-two-file-scope-globals)
|
||||
- [E. Process / method notes](#e-process--method-notes)
|
||||
|
||||
## A. Pointer-width struct growth (32→64) — the dominant class
|
||||
|
||||
A decomp struct with pointer fields, or one pun-allocated into a fixed
|
||||
|
||||