Return of the King (nt7 / Mire 7)

✅ 可玩

王者归来

nt7

🔑 fluffos / Mud@2026wiz 更新 1309d15 2026-10-22 源码 下载 ZIP 上游 fluffos/nt7

▶ 开始游玩 · Play Now

底层标注"NTLIB V7",属于本项目"泥潭/NT/nitan/Lonely"系列引擎家族的又一独立分支——与 nitan170911(仙剑奇侠传)、nitan6(笑傲江湖)、hhsj(洪荒世界)等库同宗同源,但核心档案(master.lpc、logind.lpc、securityd.lpc 等)均已各自独立演化,属于不同的具体游戏。开局同样是盘古开天地的创世场景:在"生命之谷"选择角色性格(`choose 1`-`4`),然后在忘忧池"洗"天赋(`washto <膂力> <悟性> <根骨> <身法>`,13-30 之间、总和不超过 80),随即自动"投胎"进入古村的世界之树;门派、帮派威望、军功、结婚生子等系统与同家族的 hhsj/nitan6 类似,并提供 5555(GBK)、6666(UTF-8)、8888(网页版 WebSocket)三个不同字符集/协议的端口。源码来自 GitHub 上一个已经完成 UTF-8 转码、并已适配现代 FluffOS v2019 驱动的社群维护分支(`github.com/fluffos/nt7`)。

English

A member of the NT/nitan/Lonely engine family (see nitan170911, nitan6, hhsj, xfbhh, nt1, nt6). Core daemons (master.lpc, logind.lpc, securityd.lpc, chinesed.lpc) share the family's overall shape but have diverged substantially in content from every sibling checked (hundreds to thousands of differing lines even after whitespace normalization) -- a real independent branch, not a duplicate. New characters undergo the same Pangu creation-myth 'birth ceremony' as hhsj/nt6 (choose a personality, wash attributes in the Valley of Life, land in the Ancient Village).

README

本馆只保留说明和启动脚本。 work/ 是 fluffos/nt7 子模块(泥潭根就是仓库根,pin 04a1a75e,leftover 689)。LPC 已在那个仓库改成 .lpc + §9;修复请提交到那个仓库,不要在本馆再改一份。管理员试玩种子在 overlay/。

内容亮点

内容与角色创建流程详见上方简介。

在线试玩

(本库尚未纳入 WASM 站点批量打包流程;本地驱动运行方式见下方。)

管理员账号 / Admin account

警告:对外公开架设前请务必修改这两个密码。

本地运行

cd libs/nt7
~/src/fluffos/build-debug/src/driver config.fluffos

游戏端口:40211。

NOTES · 移植与修复记录

git clone https://github.com/fluffos/nt7 → nt7

Source: fluffos/nt7 submodule at 04a1a75e (leftover 689: .lpc + §9 formatted on that repo; mudlib root is the repo root; filename-extension slices widened for .lpc). In-game name 王者归来 / NTLIB V7. Slug nt7, number 163, port 40211.

leftover 689: work/ is the fluffos/nt7 submodule

hosting is fluffos-upstream. work/ is now the fluffos/nt7 gitlink (pin 04a1a75e8f137138a1da21aae7c204572d872339), not a second formatted fork. config.fluffos mudlib directory still points at work/ (this repo's root *is* the mudlib). patches/ stays empty — the rename, §9 format, .lpc slices, and static→nosave keywords live on that fluffos-org repo. log_file("static/...") path literals were not rewritten (convert_lib's \bstatic\b also hits those; they stay "static/"). The catalog-only dead #ifndef __SENSIBLE_MODIFIERS__ shim in include/globals.h was not landed upstream. help/ntbook encoding sidecar stayed upstream-as-shipped. Three pre-existing lexerrors were left untouched: quest/skybook/update.lpc, inherit/condition/damo.lpc, d/dragon/outlet.lpc. PRs #3/#4/#5 were already on 53dce3a1 before this rename. Catalog-only overlay: data/login|user for fluffos / Mud@2026wiz (regular) + Mud@2026 (admin/recovery), including fluffos.package.o. Native 巫师休息室 (/d/wizard/ wizard_room) look/score/quit on fluffos / Mud@2026wiz (浮云, (boss)). score said 还没有出生呐 — by design (wizard skips the birth ceremony). Driver debug.log and work/log/ log_error were this boot (2026-09-12 08:17); unused-local compile warnings only. error_handler was not written (no caught runtime error). Zip pack: 29918 .lpc, overlay seed, no .git/ store. Full choose/washto/古村 registration was already verified at onboard.

earlier snapshot note (superseded)

Onboard convert was from 53dce3a1. Leftover 689 landed the catalog LPC delta on fluffos/nt7 and pinned that SHA.

WASM-safe GBK port branch (2026-09-15)

Corpus set_encoding sweep: adm/kernel/master.lpc connect() called set_encoding("GBK") when port == 5555. Catalog config uses 40211, so museum WASM never hit it; still hardened upstream (fluffos/nt7 201c00b5) with catch() → utf-8 fallback in case a multi-port / 5555 listener is used under an ICU-slim build.

Status: native + WASM playable, full registration verified both ways

Lineage vs. the existing NT/nitan/Lonely family (AGENTS.md §2.1/§11)

Genuinely distinct branch, not a duplicate of any existing lib. Spot-checked core files (adm/kernel/master.lpc, adm/daemons/ logind.lpc, adm/daemons/securityd.lpc, adm/daemons/named.lpc, adm/daemons/chinesed.lpc) against nitan170911, nitan6, nt1, nt6, nt6nitan6win, xfbhh, and hhsj: every file differs substantially (hundreds to ~900 diff lines even under whitespace- insensitive diff -bw, out of files 150–1,850 lines long) — this is NOT the "byte-identical modulo reformatting" shape that predicts a wholesale fix-port (contrast: nt7's feature/dbase.lpc byte content vs. hhsj's post-reformat copy WAS identical modulo indentation style, confirming shared engine ancestry, but the higher-level daemon files have each evolved independently since the fork). Directory layout (adm/, clone/, cmds/, d/, data/, feature/, inherit/, kungfu/, quest/, u/, template/ …) and world content (d/ dongtian/, family/sect system, data/business bsave format) closely mirror hhsj's, and securityd.lpc's own file header credits "Doing Lu for ULTRA HELL" (the same "Doing"/hell lineage credit chain documented elsewhere in AGENTS.md §11) — strong evidence of a shared distant ancestor, not a recent fork of any single already-onboarded lib.

The single biggest payoff of checking lineage first: the family's signature architecture bug (AGENTS.md §7.15, "the nitan set/query/ dbase architecture bug") is ALREADY FIXED upstream here, and does not need porting. §7.15 describes the NT/nitan/Lonely lineage's classic trap: bare set()/query()/delete()/addn() simul_efun calls resolving this_object() to the SIMUL_EFUN OBJECT (wrong) rather than the caller, requiring a two-part fix (real local set/query in feature/dbase.lpc + a previous_object()-based simul_efun fallback). nt7's feature/dbase.lpc has NO local set/query/delete functions at all (same shape as the historically-BROKEN state on nitan170911/nitan6/hhsj/xfbhh/nt6/nt6nitan6win/nt1 before this project's own fixes) — but nt7's simul_efun shim (adm/kernel/simul_efun/ntefun.lpc, guarded #ifndef __PACKAGE_DBASE__, which is always true on this driver) correctly uses previous_object() (the CALLER) rather than this_object() (the simul_efun itself) to resolve the redirect target:

varargs mixed query(string prop, object ob) {
    if (!objectp(ob)) ob = previous_object();
    return ob->query_db(prop);
}

This is architecturally correct and was verified live (registration, washto, score all read/write player properties correctly). Since every bare call anywhere in the whole tree routes through this ONE correctly-implemented simul_efun (there being no local override anywhere to create the split-resolution shape §7.78 describes), the downstream §7.78 (mixin-file bare-call mis-resolution) and §7.79 (addn/addn_temp misdirection) bug classes don't apply here either — addn's shim uses the same previous_object() pattern. check_legal_name also already uses a real Unicode pcre_match(str, "^\\p{Han}+$") check (§8.1's "byte-range Chinese-detection" bug class does NOT apply — the GBK-byte-oriented is_chinese2() variant still exists in the same file but is unreachable dead code, confirmed via corpus-wide grep, left alone). Net effect: this branch appears to have either independently fixed, or never actually shipped, the exact bug class that was this project's single biggest recurring finding across the rest of this lineage — a useful confirmation that the bug is a fork-time regression in SOME branches, not baked into the shared upstream design itself as §7.15's own text once concluded.

Bugs found + fixed (programming/driver-compat only, per AGENTS.md §6)

1. §7.80-shaped bug, confirmed present, fixed: adm/daemons/ eventd.lpc's create() builds its event-file list with map_array(event_name, (: $1[0..<3] :)) to strip the .lpc extension — same off-by-one as the corpus-wide §7.80 sweep (str[0..<n] keeps len-n+1 chars on this driver, so stripping a 4-char suffix needs [0..<5], not [0..<3]). This lib wasn't part of that sweep (never onboarded before), so it still had the bug. Fixed [0..<3] → [0..<5]. Filed upstream, bundled with the 29 sibling sites found in round two below, as PR #3. 2. §4.3 string-literal collision, self-inflicted by the mechanical static→nosave conversion, fixed: 150 files/282 call sites had log_file("static/...", ...)-style path literals rewritten to "nosave/... by convert_lib.sh's blind \bstatic\b sed (the original source, confirmed via raw/, has zero "nosave/ strings anywhere — this is 100% conversion-tool fallout, not an upstream bug). Reverted every "nosave/ → "static/ across the whole tree. Not upstream-worthy (audited for the fluffos-org-PR queue, 2026-08-31): this is self-inflicted by this collection's own static→nosave conversion pass, not present in the upstream source at all — no PR filed. 3. #ifndef __SENSIBLE_MODIFIERS__ shim in include/globals.h, confirmed DEAD (not a live bug on this driver), removed for cleanliness anyway: the classic AGENTS.md §4.3 "#define protected static" shim was present (#define protected nosave), but this driver's LPC preprocessor already defines __SENSIBLE_MODIFIERS__ unconditionally (confirmed via the driver's own predefines dump), so the #ifndef branch was always compiled out — protected was already the real keyword, not aliased. Removed the dead shim block rather than leave a misleading comment; verified via a clean recompile (no new warnings/errors), and confirms feature/ command.lpc's protected nomask int command_hook(...) (§8.3a) was never actually broken here either — no fix needed for that one. Not upstream-worthy (audited for the fluffos-org-PR queue, 2026-08-31): a dead-code cleanup with no functional-bug signature, not a genuine bug fix — no PR filed. 4. New WASM-only bug, found + fixed, root-caused via bisection: the very FIRST connection under the WASM build always failed logon() silently (driver log: new_conn_handler: logon() on object clone/user/login#0 has failed, the user is disconnected., with ZERO LPC-level error/trace anywhere — safe_apply() just returns null) — reproducibly, at the exact same point, regardless of what was typed. Bisected with temporary write() markers spliced into logon(): everything up through chinese_number(max_usr) printed fine; the very next call, TIME_D->replace_ctime(time1), never even entered the target function body. Root cause: TIME_D (adm/daemons/timed.lpc) is listed in adm/etc/preload and DOES compile clean during boot preload (no warnings/errors at all), but is NOT actually resident (find_object(TIME_D) returns 0) by the time of the very first connection — and a bare call_other() (TIME_D->replace_ctime(...)) to a not-yet-loaded object, which transparently triggers an implicit load_object() and works fine under the NATIVE driver, silently fails the whole logon() call under the WASM build instead (confirmed empirically: an EXPLICIT catch(load_object(TIME_D)) immediately before the call fixes it completely, and every following line — including replace_ctime()'s own body — then executes normally). This looks like a genuine WASM-specific driver-level gap (implicit load-on-call_other not reliable there), not a mudlib logic bug, but per AGENTS.md §1.3's "mudlib-side guards are encouraged" policy, fixed at the mudlib level: if (!find_object(TIME_D)) catch(load_object(TIME_D)); immediately before the TIME_D->replace_ctime(time1) call in logind.lpc's logon(). Did NOT attempt to preemptively guard every other daemon call in this ~30k-file mega-lib against the same theoretical class — this was the one call site actually exercised and confirmed broken on the critical first-connection path; note for a future WASM pass on this lib (or a sibling) if another first-connection daemon call turns up the same symptom. Filed upstream, bundled with fix #5 below, as PR #5. 5. Unrelated hardening applied alongside #4: logind.lpc's logon() also had an UNCONDITIONAL DATABASE_D->db_count_user() call (real MySQL db_connect()) feeding a purely cosmetic "N registered players" banner line — every other DATABASE_D-> call in the same file is already correctly gated behind #ifdef DB_SAVE (disabled in this checkout's include/unixconf.h/winconf.h), so this one call was inconsistent with the file's own convention. Fixed to match: #ifdef DB_SAVE ... #else reg_usr = 0; #endif. Confirmed via bisection this was NOT the actual cause of bug #4 (removing it alone didn't fix the WASM hang) — kept anyway since it's a genuine, independent correctness/consistency fix (and doubly so under WASM, where PACKAGE_DB isn't compiled in at all, per the WASM build's own CMakePresets.json). Filed upstream bundled with fix #4, see PR #5.

Interactive verification

Native (~/src/fluffos/build-debug/src/driver config.fluffos, scripts/mudclient.py): full flow scripted end-to-end multiple times — id → confirm → surname/given-name (real Chinese, e.g. 秦风/秦峰/秦枫) → admin password → confirm → play password → confirm → gender → notice board → lands in /d/register/regroom ("泥潭注册室") → reg <email> completes the stub email-registration step (mail-sending is commented out upstream; registered flag just gets set) → moves to /d/register/entry ("生命之谷", meets 盘古/Pangu by name) → choose 1-4 → washto <str> <int> <con> <dex> (13–30 each, ≤80 total) auto- completes the "投胎" (reincarnation) step and moves the character straight into /d/city.../世界之树 in the Ancient Village (no separate born <city> command needed once washto succeeds — confirmed the game's own flow, not a bug: do_washto() calls the equivalent of do_born() internally). look/score both produce correct, fully-rendered output (character sheet shows the exact str/int/con/dex values from washto, correct gender/personality/age, zero mojibake). quit triggers the same "new account must stay online 30 minutes or it's deleted" policy already documented as intentional design on hhsj — confirmed by completing it with y: clean "账号...档案被 删除" message, save file actually removed, zero debug.log errors throughout any of the runs.

WASM (scripts/wasm_client.js against ~/src/fluffos/build-wasm/src): same full flow, same script, same result — registration through choose/washto/world-entry/score/quit all produce identical correct output to the native run, after fix #4 above. Before that fix, EVERY WASM connection attempt failed at the exact same point (silently, right after the "已经执行了N秒" uptime banner) regardless of what was typed — this was the actual §1.3/§1.4 WASM playability blocker for this lib, not an IP/socket/pcre-package issue like the family's other usual WASM traps.

Not fixed (deliberately, out of scope)

Admin account seeding (AGENTS.md §1.5)

adm/etc/wizlist already shipped fluffos (boss) (seeded upstream by this project's own author in the pre-existing 254262ec commit, before this pass even started). No save file existed for it yet, so registered it for real through the normal flow (this lib's registration requires BOTH an admin/recovery password and a distinct regular login password — sending the same value for both is rejected): id fluffos, name 浮云 (surname 浮, given name 云 — picking the same character twice for both, e.g. "浮浮", trips a same-surname-name re-confirmation branch in get_name() that isn't a bug, just needs the joined full name typed back; used two different characters instead), admin password Mud@2026, regular login password Mud@2026wiz (matching this project's own established convention for this specific repo, from the 254262ec commit message). Since fluffos already resolves to (boss) via wizlist, enter_world()'s own startroom logic correctly routes it straight to WIZARD_ROOM (/d/wizard/wizard_room) instead of through the normal player birth-ceremony rooms — confirmed correct behavior, not a bug (wizard accounts are expected to skip reg/ choose/washto). Verified live: reconnect with the regular password succeeds, update /adm/daemons/timed reports "成功!". score reports "还没有出生呐" (not yet "born") for this account, since the normal birth-ceremony rooms that set the born property are never visited by a wizard-status login — did not chase this further (out of scope, likely by design for a staff-only account that isn't meant to use score).

Deep functional test (round two, 2026-08-27)

Full §10.7 playthrough (never previously done on this lib) against a freshly-rebuilt ~/src/fluffos/build-debug/src/driver, native only. Also checked all of AGENTS.md's standing cross-cutting bug-pattern list (§7.121, §8.3a, §7.112, §7.118, §7.122–§7.136, §7.139, §7.141– §7.148) via systematic grep — see per-pattern notes below. No sibling NT/nitan-lineage bug classes applied here beyond what's already documented above (§7.15 architecture bug already fixed upstream, per the earlier onboarding writeup).

Housekeeping note, not an nt7 bug: found an unrelated stray driver process (PID bound to port 40211, cwd in a completely different lib sanguozhi, reparented to init) squatting on this lib's assigned port before boot could even start — killed by exact PID before proceeding. Unrelated to nt7's own code; flagged here only so a future session knows this can happen on a shared host.

Bug found and fixed #1 — §7.80-shaped filename-slice bug, 29 more call sites in the kungfu/skill tree

explode(__FILE__, "/")[<1][0..<3] (and the dirs[<1][0..<3] variant) appears in 27 individual kungfu/skill/**/*.lpc files plus the two shared mixins inherit/meskill/skill_model_{weapon,unarmed}.lpc and the shared header kungfu/skill/force.h — the exact same str[0..<n] off-by-one this project already fixed in this very lib's adm/daemons/ eventd.lpc (.lpc is 4 characters, [0..<3] only strips 2, so "guiyuan-tunafa.lpc" yields "guiyuan-tunafa.l" instead of "guiyuan-tunafa"). This project's original onboarding pass only grepped for eventd.lpc's own exact line shape and never turned up this second, much larger family of call sites in the same lib. Two confirmed-live consequences:

The remaining ~20 kungfu/skill call sites compute the same corrupted id but only pass it to SCBORN_D->valid_learn()/valid_perform() — a prerequisite-checking daemon whose file (adm/daemons/scbornd.lpc) does not exist anywhere in this archive at all (confirmed via corpus-wide grep for scbornd/SCBORN_D). Every such call unconditionally fails regardless of the id's correctness, so fixing the slice has no observable behavior change at those specific call sites — flagging this as a separate, out-of-scope missing-content gap (inventing what a whole prerequisite daemon should do would be a content/design decision, not a programming fix) rather than chasing it further. Fixed the slice arithmetic at all 29 sites anyway ([0..<3] → [0..<5]), since it's the same unambiguous mechanical bug independent of what currently consumes the result. Filed upstream, bundled with the eventd.lpc instance above, as PR #3.

One additional match, adm/daemons/skillsd.lpc's real valid_perform( object me, string file) (the actively-used SKILLS_D, as opposed to the unreferenced dev-sandbox copy at u/lonely/skillsd.lpc), had already had its own [0..<3] slice commented out and replaced with a bare dirs[<1] (no stripping at all) by a prior author — checked this against its real caller (inherit/skill/skill.lpc's perform_action(), which passes an already-extension-less path via perform_action_file()) and confirmed the no-slice form is actually CORRECT for that call site's real argument shape (the one other caller that would pass a .lpc-suffixed path is fully commented out, dead code). Left untouched.

Verified live: bai wu bo (拜师) then learn wu bo unarmed 1 correctly raised a fresh character's unarmed skill (skills showed 基本拳脚 (unarmed) - 不堪一击 6/14 after one learn call) — this exercises the general skill-learning path, not the specific 9 force-skill files, since reaching those requires much deeper progression; the force.h self-exclusion fix was verified by direct code-level tracing (confirmed the corrected id now matches what member_array() checks against) rather than a live multi-level force skill grind, given time budget — documented here as verified-by-code- reading rather than fully live-verified for that specific consequence.

Bug found and fixed #2 — a missing-content-factory null check silently truncates the crontab scheduler on every single boot

100%-reproducible on every fresh boot (not a random-roll fluke): adm/daemons/timed.lpc's init_crontab() reads adm/etc/crontab (140 lines) and does find_object(table[1]) || load_object(table[1]) on every referenced object to verify it resolves — one of the very first entries (line 120) references /u/redl/cangku (a wizard's personal treasure room, target of 6 华山论剑/牛人三部曲 tournament-scheduling crontab lines). Loading it for the first time runs its create(), which does EQUIPMENT_D->create_dynamic("", 60, 600)->move(this_ object()) in a loop — an unguarded §7.147-shaped chain. Worse, create_dynamic() ITSELF (adm/daemons/equipmentd.lpc:1368) has no null check either: ob = TEMPLATE_D->create_object(filename, obj_type, temp_status); can return 0 (whenever the randomly-rolled obj_type/ level combination doesn't resolve to a real shipped template file), and the very next statements unconditionally do set(..., ob) and ob->set_color(color) — a bare call_other() on int(0), which throws uncaught: *Bad argument 1 to EFUN call_other() Expected: object, string, array, Got: int(0) (debug.log, reproduced on every single boot in this session, both before and after the fix was verified absent).

Severity beyond the immediate crash: the error is only caught by an OUTER catch() several frames further up the call stack (logind. lpc's pre-existing catch(load_object(TIME_D)), from this lib's own bug #4 above) — which means the entire unwind aborts init_crontab()'s for-loop at that exact point, silently discarding EVERY crontab entry after line 120 (the 华山论剑 sect-tournament scheduler, the 牛人三部曲 PK-event scheduler, and anything else later in the 140-line file) on every single boot, not merely failing to spawn one random equipment drop in one wizard's personal room.

Fix: added if (!objectp(ob)) return 0; immediately after the TEMPLATE_D->create_object() call in equipmentd.lpc's create_dynamic(), restoring the function's own already-documented "returns 0 on failure" contract (mirrors the identical early-return guard already present at the top of the same function for ilvl < 1). Also fixed the caller-side chain in cangku.lpc: stored the return in the already-available ob local and guarded the ->move() call with if (objectp(ob)). Verified live: debug.log goes from this error firing deterministically on every single fresh boot (both via a first connection reaching logind.lpc's TIME_D lazy-load path, and via a direct wizard update /u/redl/cangku.lpc/update /adm/daemons/ equipmentd.lpc) to zero occurrences across multiple clean reboots post-fix. Filed upstream as PR #4. Added as a new confirmed instance of AGENTS.md §7.147, with a new note about the extra severity when an unguarded factory chain is reached from inside a bootstrap/scheduler loop rather than ordinary gameplay.

Standing cross-cutting patterns checked, confirmed clean

Interactive verification (this pass)

Registered a fresh Chinese-named test character (qinfengnt, 秦风, admin pw fluffos, play pw Mud2026play) via a raw Python socket bridge script, one continuous session:

RSS stayed under 130MB throughout (well below this lineage's documented §7.110 OOM risk threshold) — no mass-restore operation was exercised this session, so that risk wasn't specifically stress-tested here.

Local run

cd libs/nt7
~/src/fluffos/build-debug/src/driver config.fluffos

Port: 40211.

深度功能测试(§10.7,2026-10-11):“无副作用表达式”警告复查(上游 PR)

深度功能测试(§10.7,2026-10-13):编译警告清零(上游 fluffos/nt7#9)

work/ 是 fluffos/nt7 子模块,此前的警告整理只扫 vendored 库,本库一直没扫到(29920 个对象中 29228 个可编译,可编译文件警告 4896 条,201 个文件本来就编译不过)。做法同 sanguozhi/xkx100utf8:在 scripts/submodule_patch_scratch.py build nt7 建的副本里先用 lpc_twin_port.py adopt nt6 nt7 --pre ad9512a1885~1(TWIN_DST_TREE 指向副本)照搬 nt6 已修好、代码相同的 847 个文件,再跑 lpc_warnings.py --fix、toolkit_fix.sh 的各个按诊断修复的脚本和 lpc_diamonds.py --fix-redundant,剩下的手修。结果:可编译 29480 个,可编译文件的警告 4896 -> 0,编译不过的仍是 201 个。改动的对象加上包含改过头文件的对象共 7948 个,旧树和新树各在新进程里载入一次:7880 -> 7881 通过,无回退;打过补丁的树开机到输入英文名字的提示。修复合并到上游(PR #9,合并提交 a615a6fb),本库钉到该提交(rebase_upstreams.py)。

孪生搬运的坑:include/dbase.h 被判成 twin(文件本身和 nt6 修前一字不差),搬来了 nt6 补的 set/query/... 原型。nt6 的 feature/dbase.lpc 自己定义这些函数,nt7 的 dbase 只有 set_db/query_db,query() 等是 simul_efun(adm/kernel/simul_efun/ntefun.lpc,按 previous_object() 转到 query_db),nt6 那个“混入件读到 simul_efun 共享 dbase”的严重问题在本库并不存在。原型一加,继承 F_DBASE 的物件里 query() 成了没有定义的本地函数,Undefined function called: query,全库只剩 3736 个对象能载入。撤回 dbase.h,再去掉 adopt 给 banker/control/guarder/liquid 加的 #include <dbase.h>(KB 08 §10.13)。

修掉的真 bug:

- #12 pangen-cuojiefu 练功扣内力写成 receive_damage("neili", -52),F_DAMAGE 报“伤害值为负值”,一练就错;改为 add("neili", -52)。 - #13 receive_damage("jingli"/"neili"/"force", N):本库 F_DAMAGE 只收 jing/qi,练 liuxing-bu、qianzhu-feixing 等和若干绝招都报“伤害种类错误”,改为 add(type, -N);SCBORN_D(转世,/adm/daemons/scbornd)从没进过树,而每个绝招都调 SCBORN_D->valid_perform()、force.h 调 valid_learn(),补一个答“未转世”的替身;qufannao-zhi 继承 F_DAMAGE 后 query 原型盖住了 sefun,改为直接 ob->query();无门派玩家的 family 映射加判断。 - #14 filter_player() 也要求 environment(ob):注册中途放弃的空身体不在任何房间,有两个时下次登录 find_player() 报 “The player(<id>) has existed in the world.”;kungfu/condition/baitan.lpc 调的命令在 /cmds/usr/baitan.lpc,不在 /cmds/std/。 - #15 18 处拼错/改名前的技能名(busi-shenglong、cuhixiao-jifa、jiemie-zhua、choushui-zhang、xiawuxiang、lenyue-shengong、yaowang-mishu、meiren-shanzhao、五种毒药的 five_poison、hengshan-jianfa、xuanyuan-arror,KB 06 §7.249)query_skill() 恒为 0,门槛永远不过或公式里那一项白算;8 个从英文名技能抄来的 query_action() 还读原技能等级(canhe-zhi 读 canhe-finger、murong-jianfa 读 murong-sword、xuedao-daofa 读 xue-dao 等),只学了本技能的人按 0 级取招;6 处无门派判断(一灯门下 du/yu、xxnpc、kunlun-strike、唐门 kedian/wenzi);qiantian-yiyang/jujing 用了 sj 才有的 MIN 宏,从没编译过,补本地定义。HEAD 对改后 30 个对象载入对比,回退 0,jujing 新载入。

log/ subdirectories nobody created: the logging write_file() / log_file() raises (2026-10-22, KB 06 §7.358)

The code of this lib writes logs into 13 subdirectories of log/: log/gift (clone/gift/pill/pill.lpc), log/job (kungfu/class/quanzhen/beidou.h), log/mission (d/city/task2/renzhi.lpc) .... Neither the archive, a git clone nor the site pack has them (no local boot wrote into them, so gen_keep_dirs.py never recorded them), and write_file() raises *Wrong permissions for opening file /log/dlog/money for append. "No such file or directory" for a missing directory: the function that logs stops on that line and what came after it (the reward, the flag, the next step) never runs. In the eval probe this lib's log_file() wrote nothing (the probe object has no write access and the sefun does not make the directory itself), so what a real caller gets was not measured. log/gift, log/job, log/mission, log/money, log/nosave, log/preload, log/quest, log/riddle, log/skybook, log/static/guilei, log/super, log/test, log/user are now in scripts/wasm_keep_dirs.txt (scripts/lpc_keep_log_dirs.py; the site and the pristine tree create the empty directories from it). Proof (scripts/lpcc_eval.py, an eval object under /adm/daemons or similar writes /log/zzdirprobe/..., fresh processes): the measured table in KB 06 §7.358.