Myth of the Three Realms: Enhanced Complete Edition (Quanzhou)

✅ 可玩

三界神话完整加强版「泉州师院」

sjshwzjqb

🔑 fluffos / Mud@2026 更新 92afcb3 2026-09-01 源码 下载 ZIP

▶ 开始游玩 · Play Now

"三界神话"系列第五个、也是最后一个档案(另见 099 `sjsh`/宝鸡站、100 `sjshv150`/紫藤分站、101 `sjshv2578bb`/测试二区、102 `sjshwzb`/泉州师院完整版),与 `sjshwzb` 共享同一份泉州地图、宗门配置(含独有的少林、峨嵋、昆仑支线)以及阿修罗界、魔界、天空界等神话场景,核心系统档案 99% 以上逐字节相同,是同一世界观的加强版而非另一款独立游戏。出生地〖南城客栈〗人物齐全:留言板、送礼物的☆小宁宁☆、热心店小二,以及暗示存在邮件系统的邮差"千里眼"(`d/ourhome/npc/bigeye.lpc`);死亡→复活循环完整可玩,在朱雀大街击杀敌人后会被送入〖阴阳界〗,由判官崔珏引导完成生死簿对话,再复活落地南城客栈。

English

The fifth and final build in the "Myth of the Three Realms" series (see also sjsh, sjshv150, sjshv2578bb, and sjshwzb) — an enhanced edition sharing sjshwzb's Quanzhou map, sect roster (including the exclusive Shaolin/Emei/Kunlun additions and the Asura/Demon-Realm/Sky-Realm mythology zones), and core system files almost exactly (99%+ of shared-path files are byte-identical). The starting Southern-City Inn is fully populated: a message board, a gift-giving NPC (☆小宁宁☆), an innkeeper, and a postman ("Farsighted Eye," d/ourhome/npc/bigeye.lpc) hinting at a mail system. Killing a mob on Vermilion Bird Street sends the player through death to Judge Cui Jue in the Yin-Yang Realm before respawning at the inn. The main operational difference from sjshwzb is that its wizlist started empty rather than pre-seeded.

README

内容亮点

本次修复的关键 bug

1. 损坏的 convertd.lpc 字节:和 sjsh/sjshv150/sjshwzb 完全相同的损坏模式,同样的非 UTF8 杂散字节紧贴闭合引号("Illegal character 0xce/0xb2/0xee/0x96/0xa3",第 258 行附近)。用同样的 字节级 Python 脚本修复了 45 处。 2. 经典 §8.1 check_legal_name()i%2 奇偶假设:和 sjshwzb 完全相同的 bug 和修法——adm/daemons/logind.lpc 改成 逐字符检查(is_chinese(name[i..i]),去掉奇偶门槛),长度限制 从字节数 2-12 改成字符数 1-6。adm/simul_efun/chinese.lpcis_chinese() 本身已经正确,不用改。 emoted.lpc/message.lpc/channeld.lpc 逐一检查过,均不存在 已知 bug。 3. §10.7 深度功能测试(2026-08-08)新发现并修复的 bug,详见 NOTES.md 的完整记录:logind.lpc 遗留调试 printf(§7.34)、 file.lpclog_file()assure_file() 防护(§7.11)、 峨嵋〖华严顶〗房间引用大写 .C 文件在运行时 case-mismatch 崩溃 (§8.15,EMEI_B.C/YINGKE.C 已重命名为小写)、以及移植 §8.15 修复时新发现的 carry_object() 存在性检查对无扩展名路径假阴性 (新增 AGENTS.md §7.99)——起始房间南城客栈的邮差"千里眼" NPC 原本会因为这个假阴性在每一次新角色注册时 100% 崩溃,已连带 修复并回填到 sjshwzb。§7.97(LISTNODES 死亡死循环)、§8.13 (WIZ 密码二次登录死锁)等其余家族已知 bug 类别均已逐条核实, 本档案不适用。

管理员账号 / Admin account

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

注册流程提示

sjshwzb 完全相同:选择内码(GB/BIG5)→ 是否中小学生(回答 no)→ 输入 new → 英文 ID → 中文名字 → 管理密码 + 确认 → 普通密码 (必须与管理密码不同)+ 确认 → email(需要 [email protected] 格式)→ 个人主页/ICQ(可留空)→ 性别 → 是否接受赠礼 → 天赋点分配。

本地运行

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

游戏端口:40173

NOTES · 移植与修复记录

WASM 修复摘要(迁移自 meta.json 的 group_note)

三界神话「泉州师院」完整加强版,sjsh 家族集群的第五个也是最后一个。和 sjshwzb 同一血统——逐字节相同的 bug 组合:master.lpc 的 log_error()/standard_trace() 里没有 CHANNEL_D 呼叫(§7.60 不适用),securityd.lpc 的 valid_read() 从不覆盖驱动的 user 参数(§7.59 不适用),没有 sited.lpc(没有回环闸门)。WASM 修复:(1)熟悉的 convertd.lpc 字节级损坏(45 行,和 sjsh/sjshv150/sjshwzb 完全相同的 0xce/0xb2/0xee/0x96/0xa3 非法字符签名,第 258 行附近,同样的"杂散非 UTF8 字节转义闭合引号"模式)——用标准的字节级 Python 脚本修复。(2)adm/daemons/logind.lpc 里 §8.1 类的 check_legal_name() i%2 奇偶门槛,和 sjshwzb 完全相同的 bug 和修法:改成逐字符呼叫 is_chinese(name[i..i]),不设奇偶门槛,长度界限从字节数(2-12)改成字符数(1-6)。adm/simul_efun/chinese.lpc 的 is_chinese() 本来就是正确的码点区间检查——不用修。emoted.lpc/message.lpc/channeld.lpc:直接检查过,已知的 bug 都不存在也不需要修。管理员账号播种:fluffos (admin) 加入 adm/etc/wizlist(这份快照的 wizlist 档案是空的/只有空白字符,不像 sjshwzb 那份已经有两个其它巫师——是全新写入的)。注册流程在一次连续的 WASM 客户端会话里完整验证过,和 sjshwzb 完全相同的流程(GB/BIG5 选择→非学生关卡→"new"→英文 id→中文名字→管理密码+普通密码,必须不同→电子邮件,需要 [email protected] 格式→可选的个人主页/ICQ→性别→拒绝赠礼→属性分配),全程没有意外错误。管理员权限已直接通过登录横幅"您的系统权限目前是:(admin)"确认。LPC 格式化工具对全部 11569 个档案运行(写入 11286 个,72 个因为杂乱的历史代码报错,211 个未改动);还原了和 sjshwzb 相同的 2 个档案(panshi_dan.lpc、npc/mm.lpc),确认是转档之前就存在(作者一方,早于本轮)的缺引号损坏被格式化工具进一步重新加了空格。没有 :: 父类呼叫拆分命中。逐一比对了同一个 case 密集的档案(d/calvin/esman.lpc,内容和 sjshwzb 那份逐字节相同)——干净,没有语句被吞掉。通过去空白差异比对了全部 4 个 map.lpc 档案——所有差异都只是大括号排版风格(K&R 合并),内容零变化。格式化后用同样的完整注册流程重新验证过——干净,管理员权限依然是 (admin)。

§7.86 跨库扫描修复(留言板 post 崩溃)

深度功能测试(§10.7,2026-08-08)

三界神话系列的第五个、也是最后一个档案。用原生驱动(build-debug/src/driver,端口 40173)通过 scripts/tmux_mud.sh 走完整轮,对照同家族已深挖的 sjsh(宝鸡站)/sjshv150(紫藤分站)/sjshv2578bb(测试二区)/sjshwzb(泉州师院完整版)NOTES.md 逐条核对候选 bug——README 已注明本档案和 sjshwzb 同源、核心文件(master.lpc/securityd.lpc/logind.lpc)与已知 bug 集合逐字节一致,但仍按项目惯例逐条独立验证,不直接照搬结论。

家族总结(5/5 成员全部深挖完毕,2026-08-08)

sjshwzjqb 是三界神话「三界」系列 5 个档案家族(sjsh/sjshv150/sjshv2578bb/sjshwzb/sjshwzjqb)里最后一个完成 §10.7 深度功能测试的成员。基于本档案自己的发现和其余 4 份手足档案各自 NOTES.md 记载的结果,按 bug 类别汇总复现频率(分母固定为 5):

| Bug 类别 | 命中家族成员数 | 备注 | |---|---|---| | §7.34(logind.lpc 遗留 debug printf) | 5/5 | 全员命中,逐一确认并删除,是本家族最普遍的问题 | | §7.11(log_file 缺 assure_file 防护) | 4/5 | sjsh/sjshv150/sjshwzb/sjshwzjqb 命中;sjshv2578bb 通过 MONITOR_D->log_file() 转发已自带防护 | | §7.86(board inherit+多余 replace_program()) | 5/5 | 全员命中(跨库扫描批量修复),另有 sjshwzb/sjshwzjqb 各自独立发现的一处大写 .C 扩展名漏网实例(§8.15 附带) | | §7.97(LISTNODES 缺续行反斜杠死循环) | 1/5 | 仅 sjsh 命中,其余 4 份档案该头文件各自独立维护、内容不同源 | | §8.13(WIZ 密码二次登录死锁) | 1/5 | 仅 sjshv150 命中;sjshv2578bb 通过 #ifdef NO_CHECK_WIZPWD 已自行规避;sjshwzb/sjshwzjqb 走双密码架构、压根没有这个登录闸门 | | §8.15(大写 .C runtime case-mismatch 崩溃) | 2/5 | 仅 sjshwzb/sjshwzjqb(同一血统分支)命中,sjsh/sjshv150/sjshv2578bb 无此内容 | | §7.99(file_size() 存在性检查对无扩展名路径假阴性,本轮新增条目) | 2/5 | sjshwzjqb 现场发现并修复,回填修复到同血统的 sjshwzb | | §8.9/§7.88/§7.12/§8.3a/§8.3b/§7.90/§7.5/§7.98 | 0/5 | 全员均不适用(各自独立验证,非假设性排除) |

结论:这个家族最稳定、跨全部 5 个快照复现的问题是 §7.34(遗留调试输出)和 §7.86(留言板崩溃),说明这两处很可能是某个更早的共同祖先档案里就已经存在的缺陷,被逐代快照原样复制。§7.97/§8.13/§8.15 则是各快照独立分叉演化后产生的差异——同一代码库的不同存档时间点,会因为管理员各自的修补历史不同而携带不同的遗留 bug 子集,"血统相同"不能替代逐份验证。§7.99 是本轮唯一一个纯技术性的新发现:不是这份档案原始代码的 bug,而是本项目自己在移植 §8.15 修复时引入的一个新的假阴性风险,提醒未来任何"加一层 file_size() 存在性检查"式的防御性修复都要连带检查同一辅助函数的其它调用方。

§7.100 扫描修复(ROOM 基类多余 replace_program()

#define ROOM "/std/room":删除 644 处多余的、独立成行的 replace_program(ROOM);(保留 inherit ROOM;),636 处脚本自动 删除;另有 4 份房间建造工具副本手动修正——obj/roommaker.lpcu/calvin/obj/roommaker.lpc 是标准的"两套模板"简单变体; u/qkl/roommaker.lpcu/koker/obj/teshu/roommaker.lpc 是手足 sjshwzb 同批也命中的"3 处出现"room_code/str 变体,三处均手动 删除。work/data/room/*.lpc(4 个文件,与 sjshwzb 同名同构)确 认无此调用,无需处理。修复后全库仅剩 26 处历史遗留的 //-注释掉实例,均确认无害、未改动。已用 build-debug 驱动干净 启动验证(0 个新增编译错误,端口 40173 正常监听,debug.log 无新 增 "cannot replace"/"cannot bind" 行);未做完整 §10.7 深度游玩 测试。

§7.30 uninitialized-mapping accessor sweep (2026-08-20)

Corpus-wide mechanical sweep of the feature/skill.lpc shared-lineage bug (confirmed independently on xiakexing2017/jqxz2015/haiyang2 via round-four testing): 3 accessor(s) in this file returned a raw never-initialized mapping instance variable (defaults to int 0, not ([]), until first assigned), crashing any unguarded keys()/sizeof()/indexing caller for a fresh/untrained character. Fixed at the accessor level (mapp(x) ? x : ([])) per the documented remedy. Verified via lpcc --batch static compile check only (not a live boot) as part of a large mechanical sweep; not individually functionally re-tested live on this lib.

深度功能测试第二轮(2026-08-23):死亡计数器、buy、拜师、大写目录死链、邮件系统

用既有的 fluffos 账号(§10.7 深挖账号)通过原生驱动(端口 40173)+ scripts/tmux_mud.sh 逐条核实 2026-08-08 那轮记录的「未覆盖」四项。 本档案和刚测完的同源手足 sjshwzb 逐字节同源的核心文件集合完全一致 (combatd.lpc/weapon.h/std/room.lpc/d/nanhai/*),所以本轮直接 对照 sjshwzb 那轮的发现逐项复核,而不是从头盲测——多数命中的是同一 血统里独立分叉演化出的同一个 bug。

修复文件清单(本轮):d/lingtai/obj/shengmao.lpc(缺引号,真实 崩溃修复)、include/weapon.h(补 HALBERD/F_HALBERD 宏,移植自 sjshwzb)、std/room.lpcmake_inventory()/reset() 空指针防护, 移植自 sjshwzb)。工具调用数约 90 次,在预算范围内。

AGENTS.md §7.19 sweep (2026-09-01): enable_player() reentrancy from init()

Same corpus-wide bug class as mhxy/wuhanzhan (AGENTS.md §7.19): this lib's feature/command.lpc enable_player() wrapper (around the raw enable_commands() efun) is reachable from an NPC's init() via a redundant create()-then-init()-calls-setup() (or reset_me() calling setup()) chain -- confirmed live via a static scan of every init() body in this lib: 50 NPC/item files call setup() directly or via reset_me() from init(), after create() already called setup() once (which already made the object living()). Calling enable_commands() a second time on an already-living() object makes the driver re-invoke that object's own init() as a side effect, which re-enters this same chain while the original call is still on the stack -- genuine reentrancy, crashing with "Too deep recursion" (most likely to surface on an NPC's first-ever preload/compile).

feature/damage.lpc's revive() and cmds/std/sleep.lpc's wakeup1()/wakeup2() call enable_player() again while the object is still living(). This confirms a bare if (living(this_object())) return; guard would be the WRONG fix (it would silently break that legitimate re-enable) -- used the same true reentrancy-flag fix as mhxy instead: a nosave private int in_enable_player_now; set for the duration of the wrapper's body, guarding only genuine same-call-stack reentrancy while leaving every legitimate re-enable (revive/wakeup/disguise) unaffected. feature/command.lpc's enable_player() had a single fall-through exit (no early returns), so one guard-at-top + one clear-at-bottom pair was sufficient. Verified via a single-file lpcc --batch compile check (PASS) -- not individually live-boot-tested.