Files
mtgodot-poc/.agents/skills/metin2-40250-parity-audit/references/project-map.md
T
shenleiandClaude Opus 5.5 cd9e5b259d android: build.sh installs and syncs the game files when a phone is attached
After building the APK, android/build.sh now picks the attached device (ANDROID_SERIAL for several),
installs the APK (reinstalling on a signature mismatch), syncs the zh client into files/Client and, with
--launch, wakes the phone and starts the app. Without a device it only builds.

push-client.sh is now incremental (android/sync_client.py): the device keeps files/Client/.mt_sync
(size, mtime, path of what the last sync wrote), so later syncs send only new and changed files as one
tar streamed through `adb shell -T run-as` (no copy in /data/local/tmp) and delete the ones gone
locally. Only game resources are synced; settings and logs the app writes there are kept. --locale zh
rebuilds build/zh-locale/Client first when its inputs changed. android/adb_env.sh picks adb and falls
back to server port 5038 when :5037 cannot bind.

Verified against a fake adb device: first sync (1.4 GB, byte-identical), no-op resync, changed files,
deletions, locale switch, --full, the install/launch path and the no-device path.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-09-30 16:36:21 +09:00

5.0 KiB

Project map

Reference client (40250)

  • Root: MT_40250_SOURCE, else reference_root in audit/manifest.json — on this machine ../40250/Server Client TMP4/ClientVS22/source relative to the repo (quote it: the path has spaces).
  • Active sources: the ClCompile/ClInclude items in ../vs_files/*/*.vcxproj; files not listed there are not product code.
  • Many UserInterface/ files contain CP949 bytes in comments: use grep -a / grep -arn, or plain grep silently reports no match.
  • Python UI and game scripts: ../../Client/Eternexus/root/*.py relative to the reference root (90 files; identical to the shipped Client/pack/root.epk), window layouts in ../../Client/Eternexus/uiscript/uiscript/, locale data in ../../Client/Eternexus/locale_*/. assets/root in this repo is a different (m2dev) version with material differences (e.g. uitarget.py button table); never use it as the 40250 reference.
  • Server source (for protocol questions only, not client behavior): ../40250/Server Client TMP4/Server/metin2.
Library Lines Content
UserInterface 64.7k network stream + phases, CPythonPlayer, CInstanceBase, managers, Python modules
EterLib 48.7k device/render state, camera, input/IME, net stream, resources, collision primitives
GameLib 30.7k CActorInstance (motion, battle, attach, events), flying objects, map/terrain, race data
EterBase 6.3k utilities, timer, CRC, file
EffectLib 6.1k effect/particle instances
EterGrnLib 5.9k Granny models, motion, LOD
EterPack 3.4k pack format
MilesLib 2.3k audio
EterLocale 1.1k codepages, locale strings
PRTerrainLib 1.0k terrain texture/height data

Current client

  • src/port/<Lib>/<File>.{h,cpp} — mirror of each 40250 logic/python unit (see SKILL.md "Code layout").

  • src/platform/ — implementations of the mirrored 40250 platform classes (D3D8 recorder, Granny, Miles, SpeedTree stand-in, window/input, ScriptLib boot).

  • src/host/ — SDL3 + Vulkan host (main.cpp entry, live_client.cpp loop, vulkan_window.h renderer split across vulkan_window.cpp/vk_*.cpp/sdl_window.cpp/ui_batches.cpp); src/gr2/ — Granny reader; src/codepage/ — code pages.

  • third_party/ — vendored cpython 2.7.18, cryptopp, freetype, minilzo.

  • tests/port/ — port tests and the fake login server; tests/gr2/ — Granny reader tests.

  • android/ — SDLActivity shell, android/build.sh, android/push-client.sh.

  • scripts/ — gates and build helpers; tools/ — standalone dev tools (Granny oracle, perf, server).

  • The GDScript runtime and extension/src/net below are gone (2026-09-23 … 09-29); the table records where logic came from.

  • The files in the table below are migration sources: when a unit is ported, its logic moves out of them into the mirror file.

Legacy counterparts (migration sources)

40250 Current
CPythonNetworkStream* phases, CAccountConnector extension/src/net/classic/classic_session.cpp, classic_stream.cpp, classic_parser.cpp
packet structs / CMainPacketHeaderMap extension/src/net/classic/wire_classic.h
EterLib/NetStream.cpp sequence + cipher extension/src/net/classic/sequence_table.h, classic_cipher.cpp
CPythonCharacterManager, CInstanceBase state from packets extension/src/net/entity_store.cpp, project/net_world.gd
CPythonPlayer input/move (PythonPlayerInput*.cpp), main CInstanceBase movement project/player_controller.gd
PythonPlayerEventHandler.cpp (OnMove/OnMoving/OnWaiting/OnStop -> SendCharacterStatePacket) project/net_play.gd
CPythonPlayer skill use project/player_skill.gd
CFlyingObject* project/fly_object.gd
EterLib/Camera.cpp + PythonApplicationCamera project/game_camera.gd
ui*.py windows project/ui/*_ui.gd (ported from the wrong assets/root; replaced by the python layer)

Removed non-counterparts

The 106 project/*_system.gd files that only their own test_*_parity.gd loaded were deleted on 2026-09-22 (commit a989b8f1). Do not recreate them; port the real 40250 code path instead.

Existing evidence (historical)

  • docs/CLIENT-GAP.md, docs/CLIENT-PARITY-AUDIT-AND-FIX-GUIDE.md, docs/archive/CLIENT-40250-PORT.md, docs/PARITY-GAP.md: background only; trust the port-map, not their status text.
  • tools/granny-oracle/run-diff-suite.sh: Granny numerical comparison suite.

Verification commands

cmake -S . -B build/native -DCMAKE_BUILD_TYPE=Release -DMT_BUILD_NATIVE_RENDER=ON -DCMAKE_PREFIX_PATH=/opt/homebrew
cmake --build build/native -j8 && ctest --test-dir build/native --output-on-failure -j4
./scripts/port_gate.sh macos android                        # build/port-gate
./android/build.sh Release                                  # build/android + APK; installs + syncs zh assets when a phone is attached

All build trees live under build/ (gitignored). Always finish with git diff --check.