You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
No game data is included. You need your own copy of the Xbox disc,
extracted (default.xbe, NFSUNDER/, ...).
✨ Features
🏁 Native code: the whole game runs as recompiled C, built with
xboxrecomp
🎮 Two renderers: Vulkan (NVK on Switch) and OpenGL, with render scaling
up to 4x
📺 Widescreen 16:9 by default, using the game's own wide mode
🪞 Car reflections (Vulkan), switchable in the game's
Options → Video → Car Reflections; Off also skips the six reflection
passes the game draws every race frame
🔍 Resolution Scale in Options → Video (Vulkan): 1x, 1.5x
(default), 2x, 2.5x, applied at once
🖼️ Cleaner picture (Vulkan): mipmaps with trilinear and anisotropic
filtering, mipmapped car reflections, FXAA, square pixels in 16:9 races
(1280x720 at 1.5x); Anti-Aliasing, Anisotropic (Off-16x) and
Square Pixels in Options → Video
🎬 Full-screen movies decoded with FFmpeg (VP6)
🔊 Audio through an emulated Xbox APU, with 5.1 downmixed to stereo
👥 Two-player split screen, with Joy-Con pairs or one sideways Joy-Con
per player
📳 Rumble on Switch HD rumble and SDL controllers, strength set in
Options → Gameplay → Vibration (Off, 10%-100%)
🔤 Switch wording in the menus (Start → +, no Xbox Live or hard-disk
names)
💾 Saves stay next to the game in game/UDATA; the Options → Audio
volumes (the Xbox game never saved them) are kept in nfsu2x_options.txt
🕹️ Playing on Switch
Copy the NRO to sdmc:/switch/nfsu2x/ (nfsu2x-vulkan.nro for the Vulkan
build).
Copy the extracted disc (not the ISO) to sdmc:/switch/nfsu2x/game/.
Start it with title takeover: hold R while launching any game.
Applet mode leaves too little memory.
sdmc:/switch/nfsu2x/
├── nfsu2x-vulkan.nro
├── nfsu2x_env.txt optional settings, KEY=VALUE per line
├── nfsu2x_options.txt written by the in-game options the port adds and
│ the Audio volumes
└── game/
├── default.xbe
└── ...
Buttons map by label (Switch A = Xbox A). Settings go in nfsu2x_env.txt
(see Configuration) and the log is written to the
same folder.
the toolkit (MIT), vendored with this port's changes: NV2A renderers (Vulkan, OpenGL), SDL audio, Switch platform layer, translator fixes
tools/regen.sh
XBE → lifted C (gen/, never committed)
switch/build.sh
Switch NRO build + SD-card staging
⚙️ Configuration
On Linux these are ordinary environment variables. On the Switch they go in
sdmc:/switch/nfsu2x/nfsu2x_env.txt, one KEY=VALUE per line (# starts a
comment). Anything left out runs at its default, which is the fastest normal
configuration. Most of the list is for debugging, so the sections below are folded.
Toolkit to build or regenerate with (default: the vendored xboxrecomp/).
NFSU2_XBE
default.xbe to lift (tools/regen.sh).
NFSU2_GEN_DIR
Directory for the lifted C (default /root/nfsu2x/gen).
LIFT_ONLY=1
regen.sh: skip disasm / function id / ABI analysis and only re-lift (enough after translator or recomp_manual.c changes; seed changes need the full run).
RECOMP_LEAF_LOCALS=0
Translator: keep MMX leaf-function registers in globals instead of C locals.
RECOMP_REG_LOCALS=0
Translator: keep eax..edi/esp in globals instead of C locals.
RECOMP_X87_LOCALS=0
Translator: keep the x87 stack top in its global instead of a local.
NFSU2_GAME_SRC
switch/build.sh: extracted disc to stage (default /root/nfsu2x/game).
switch/build.sh: build directory (default /root/nfsu2x/build-switch, -vk with VULKAN=1).
JOBS
switch/build.sh: parallel compile jobs (6 fits -O2 in RAM).
VULKAN=1
switch/build.sh: build the Vulkan renderer (nfsu2x-vulkan.nro).
NVK_SDK, GLSLANG_DIR
switch/build.sh with VULKAN=1: mesa-switch NVK install and Switch glslang.
FFMPEG_DIR
switch/build.sh: LGPL VP6-only FFmpeg for the movies (tools/build_ffmpeg_vp6.sh).
Game and host
Variable
Meaning
NFSU2_GAME_DIR
Extracted disc (Linux; default ./game). The Switch always uses sdmc:/switch/nfsu2x/game/.
NFSU2_GL=0
Use the executor's CPU renderer instead of the GPU renderer.
NFSU2_APU=0
With RECOMP_AC97_READY=plain: no emulated APU (no sound).
NFSU2_SIM_STEPS
Longest game-time step per frame, in 1/60 s (default 6 = 100 ms; 3 = the original 50 ms cap, which slows races below 20 fps).
NFSU2_NATIVE_VP6
Movie decoder: 1 = FFmpeg (default when built with it), 0 = the lifted decoder, 2 = both and compare.
NFSU2_MOVIE_FLASH=1
Keep the opening trailer's white flash frames (shown black by default).
NFSU2_SWITCH_TEXT
Switch wording in the menus (Start → +, no Xbox Live/hard-disk names): 1 on (Switch default), 0 off.
NFSU2_EXIT_TRACE=1
Print the guest state at exit.
RECOMP_WIDESCREEN=0
Tell the game the TV is 4:3 (default 16:9).
RECOMP_CMDLINE
Command line handed to the title (e.g. +map intro).
HOME, XDG_DATA_HOME
Linux: fallback save directory ($XDG_DATA_HOME/xboxrecomp, else ~/.local/share/xboxrecomp) when none is configured. NFSU2's own saves go to <game>/UDATA.
Switch (Horizon)
Variable
Meaning
NFSU2_NO_LOG=1 / NFSU2_LOG=0
No log file, no [perf] reports, no profiler.
NFSU2_LOG_SYNC=1
Write every log line to the card at once (slow; for hangs).
NFSU2_LOADER=0
No loading screen (logo + bar) before the first frame.
RECOMP_NX_PROFILE
Sampling profiler into prof.bin: 1 = busy threads, 2 = every thread above 2%.
RECOMP_NX_SHM=1
Guest RAM from shared memory instead of code memory.
RECOMP_NX_AUDIO_PRIO=0
Leave the APU and SDL audio threads at priority 59 (default: above the game threads).
RECOMP_NX_GUEST_RT=1
Run the time-critical guest thread (EA mixer) at a real-time host priority.
RECOMP_NX_JOYCON=single
One sideways Joy-Con per player.
RECOMP_NX_JOYCON_ROTATE=0
Don't rotate the sideways Joy-Con stick.
RECOMP_GUEST_ONE_CORE
1 = pin guest threads to one core, 2 = guest threads only (interrupts float).
Scheduling and kernel
Variable
Meaning
RECOMP_GIL=0
No guest lock (guest threads run in parallel; races the title's streaming).
RECOMP_GIL_EAGER=1
Hand the guest lock over by guest priority (main thread and time-critical threads pre-empt).
RECOMP_KERNEL_FAST=0
Release the guest lock in every kernel call, even the cheap time queries and IRQL changes.
RECOMP_FRAME_LAG=1
Wait on the previous frame's fence instead of the current one (game and GPU work overlap).
RECOMP_VBLANK
Vblank interrupt for D3D (default 1).
RECOMP_WORKERS=inline
Run the title's worker routines inline instead of on threads.
RECOMP_ASYNC_IO=1
Asynchronous NtReadFile.
RECOMP_CS_MODE=single
Every guest critical section behind one recursive lock.
RECOMP_NATIVE=0
Use the lifted culling functions instead of the native C versions.
RECOMP_NATIVE_CHECK=1
Run both and report any difference.
RECOMP_QUIET
1 = no periodic kernel/GPU summaries (Switch default), 0 = show them.
RECOMP_NO_LOG=1
No xbox_kernel.log.
XBOX_LOG_LEVEL
Kernel log level (0 errors … trace).
RECOMP_KERNEL_LOG_BUDGET
Kernel calls logged before the log goes quiet.
Graphics (GL and Vulkan renderers)
Variable
Meaning
RECOMP_PB_EXEC
Execute the NV2A pushbuffer (default 1; the title draws through it).
RECOMP_GL_SCALE
Render resolution multiple, 0.5..4 (fractions allowed). Vulkan: only until Options → Video → Resolution Scale is changed (default there 1.5x).
RECOMP_GL_THREAD=1
GL renderer: GL calls on their own thread.
RECOMP_GL_DIRECT=0
Convert every vertex to float4 instead of uploading it as stored.
RECOMP_GL_DXT=0
Decode DXT textures on the CPU instead of uploading them compressed.
RECOMP_GL_SHARED_Z=0
One depth buffer per colour surface (old behaviour; lights show through walls).
RECOMP_GL_TEX_MB
Texture cache budget in MB (least recently used go first).
Need for Speed and Underground are trademarks of Electronic Arts. This is
an unofficial fan project, not affiliated with or endorsed by EA or Microsoft.
About
Need For Speed Underground 2 Xbox Original port for Nintendo Switch