diff --git a/13-归档信息大楼/ARCHIVE-INDEX.json b/13-归档信息大楼/ARCHIVE-INDEX.json index 29ff17c..2fb27ea 100644 --- a/13-归档信息大楼/ARCHIVE-INDEX.json +++ b/13-归档信息大楼/ARCHIVE-INDEX.json @@ -315,6 +315,18 @@ "intake_method": "SAME_VOLUME_MOVE", "old_path_status": "NO_ACTIVE_REFERENCE", "restoration": "EXPLICIT_OWNER_REQUEST_AND_NEW_VERIFIED_ROUTE_REQUIRED" + }, + { + "object_id": "zero-physical-cutover-20260924", + "source_path": "/Volumes/JZAO/铸渊-ICE-GL-ZY001/CODEX-DEV-20260915/光湖语言世界/运行时/zero-physical-cutover.py", + "archive_path": "/Volumes/JZAO/铸渊-ICE-GL-ZY001/CODEX-DEV-20260915/光湖第五域/13-归档信息大楼/zero-physical-cutover-20260924.py", + "sha256": "e57f39a5650da7eb01ac7eb3e529b456de37525db6dba66db5365098c69b40d3", + "bytes": 7604, + "lifecycle": "ONE_TIME_ZERO_BRAIN_AND_CHANNEL_MOVE_VERIFIED_HISTORY_ONLY", + "current_route": false, + "intake_method": "SAME_VOLUME_MOVE", + "old_path_status": "REMOVED_ONE_TIME_SCRIPT", + "restoration": "EXPLICIT_OWNER_REQUEST_AND_NEW_VERIFIED_ROUTE_REQUIRED" } ], "historical_blueprint": "/Volumes/JZAO/铸渊-ICE-GL-ZY001/CODEX-DEV-20260913/world-source-tcs-planet-five-domain-mother-separation/transport/source/gls/source-purification/archive-information-building/ARCHIVE-BUILDING-INDEX.hdlp" diff --git a/13-归档信息大楼/zero-physical-cutover-20260924.py b/13-归档信息大楼/zero-physical-cutover-20260924.py new file mode 100644 index 0000000..1b0afcd --- /dev/null +++ b/13-归档信息大楼/zero-physical-cutover-20260924.py @@ -0,0 +1,144 @@ +#!/usr/bin/env python3 +"""One-time local Zero channel and brain move with exact pointer rollback.""" + +import hashlib +import json +import os +from pathlib import Path +import subprocess +import sys +import tempfile + + +WORLD = Path(__file__).resolve().parents[1] +HOST = WORLD.parent +FIFTH = HOST / '光湖第五域' +ZERO = HOST / '光湖零点原核' +OLD_CHANNEL = WORLD / '00-零点原核/零点原核频道' +OLD_BRAIN = FIFTH / '07-冰朔语言人格本体系统/主控大脑' +NEW_CHANNEL = ZERO / '零点原核频道' +NEW_BRAIN = ZERO / '主控大脑' +CANDIDATE = FIFTH / '10-语言源代码回声系统/心跳核心语言架构/GLW2-ENTRY-CLOSURE-20260923/ZEROCORE-PHYSICAL-MOVE-20260924' +ROOT_NAME = '光湖语言世界-2.0-四域平行世界根-20260924' + + +def sha(data): + return hashlib.sha256(data).hexdigest() + + +def run(*args): + result = subprocess.run(args, stdout=subprocess.PIPE, stderr=subprocess.STDOUT, text=True, timeout=40) + if result.returncode: + raise RuntimeError(f'PROBE_FAILED:{args[0]}:{result.stdout[:500]}') + return result.stdout + + +def atomic_bytes(target, data): + with tempfile.NamedTemporaryFile(dir=target.parent, prefix=f'.{target.name}.', delete=False) as out: + out.write(data) + tmp = Path(out.name) + os.replace(tmp, target) + + +def main(): + if not OLD_CHANNEL.is_dir() or OLD_CHANNEL.is_symlink() or not OLD_BRAIN.is_dir() or OLD_BRAIN.is_symlink(): + raise RuntimeError('OLD_ZERO_SOURCE_NOT_PHYSICAL') + if ZERO.exists() or ZERO.is_symlink() or len({WORLD.stat().st_dev, FIFTH.stat().st_dev, HOST.stat().st_dev}) != 1: + raise RuntimeError('ZERO_DESTINATION_NOT_EMPTY_OR_NOT_SAME_VOLUME') + candidate = { + WORLD / 'WORLD-INDEX.json': (CANDIDATE / 'WORLD-INDEX.json.next').read_bytes(), + WORLD / 'ROUTE-REGISTRY.json': (CANDIDATE / 'ROUTE-REGISTRY.json.next').read_bytes(), + WORLD / f'{ROOT_NAME}.tcs': (CANDIDATE / f'{ROOT_NAME}.tcs').read_bytes(), + WORLD / f'{ROOT_NAME}.gir.json': (CANDIDATE / f'{ROOT_NAME}.gir.json').read_bytes(), + NEW_CHANNEL / 'ZEROPOINT-CHANNEL.json': (CANDIDATE / 'ZEROPOINT-CHANNEL.json.next').read_bytes(), + } + source = candidate[WORLD / f'{ROOT_NAME}.tcs'] + gir = json.loads(candidate[WORLD / f'{ROOT_NAME}.gir.json']) + if gir.get('compiled_from', {}).get('source_sha256') != sha(source): + raise RuntimeError('ZERO_ROOT_TCS_GIR_HASH_MISMATCH') + index = json.loads(candidate[WORLD / 'WORLD-INDEX.json']) + route = json.loads(candidate[WORLD / 'ROUTE-REGISTRY.json']) + if (index['tcs_root_topology']['physical_roots']['zeropoint'] != '../光湖零点原核/' or + index['tcs_root_topology']['physical_roots']['zeropoint_brain'] != '../光湖零点原核/主控大脑/' or + next(item for item in route['routes'] if item['target_id'] == 'ICE-CH-ZC001')['canonical_path'] != '../光湖零点原核/零点原核频道/ZEROPOINT-CHANNEL.json'): + raise RuntimeError('ZERO_CANDIDATE_PATHS_INVALID') + + backups = {path: (OLD_CHANNEL / path.relative_to(NEW_CHANNEL) if path.is_relative_to(NEW_CHANNEL) else path).read_bytes() + for path in candidate} + backup_dir = WORLD / '运行时/state/zero-physical-cutover-20260924' + backup_dir.mkdir(parents=True, exist_ok=True) + manifest = [] + for path, data in backups.items(): + saved = backup_dir / f'{sha(str(path).encode())}.before' + if saved.exists() and saved.read_bytes() != data: + raise RuntimeError('ZERO_BACKUP_COLLISION') + if not saved.exists(): + saved.write_bytes(data) + manifest.append({'path': str(path), 'sha256': sha(data), 'backup': str(saved)}) + (backup_dir / 'MANIFEST.json').write_text(json.dumps(manifest, ensure_ascii=False, indent=2) + '\n') + + lock_path = OLD_BRAIN / '.brain-write.lock' + lock = os.open(lock_path, os.O_WRONLY | os.O_CREAT | os.O_EXCL, 0o600) + os.write(lock, f'zero-physical-cutover:{os.getpid()}'.encode()) + moved_channel = moved_brain = channel_link = brain_link = False + try: + pre = json.loads(run(sys.executable, str(WORLD / '运行时/zero-brain-convergence.py'))) + if pre['state'] != 'EXACT_HASH_CONVERGED': + raise RuntimeError('ZERO_TWO_NODE_PREFLIGHT_NOT_CONVERGED') + old_hashes = {name: sha((OLD_BRAIN / name).read_bytes()) for name in ('brain-state.json', 'transition-log.jsonl')} + ZERO.mkdir(mode=0o700) + os.rename(OLD_CHANNEL, NEW_CHANNEL) + moved_channel = True + os.rename(OLD_BRAIN, NEW_BRAIN) + moved_brain = True + OLD_CHANNEL.symlink_to(Path('../..') / '光湖零点原核/零点原核频道', target_is_directory=True) + channel_link = True + OLD_BRAIN.symlink_to(Path('../..') / '光湖零点原核/主控大脑', target_is_directory=True) + brain_link = True + for path, data in candidate.items(): + atomic_bytes(path, data) + if {name: sha((NEW_BRAIN / name).read_bytes()) for name in old_hashes} != old_hashes: + raise RuntimeError('ZERO_BRAIN_BYTES_CHANGED_DURING_MOVE') + for args in ( + ('node', str(WORLD / '运行时/brain-core.mjs'), 'verify'), + ('node', str(WORLD / '运行时/first-glance.mjs')), + ('node', '--test', str(WORLD / '运行时/test-entry-gate.mjs')), + ): + run(*args) + for item in route['routes']: + if not (WORLD / item['canonical_path']).exists(): + raise RuntimeError(f'ZERO_ROUTE_TARGET_MISSING:{item["target_id"]}') + guard = subprocess.run(['node', '/Volumes/JZAO/HoloLake/persona-runtime/repo-012-main/server-tools/persona-host-write-admission/host-write-admission.mjs', + 'check', '--host', 'codex', '--path', str(NEW_BRAIN / 'brain-state.json'), '--purpose', 'PERSONA_RECOVERY'], + capture_output=True, text=True, timeout=10) + if guard.returncode != 2 or json.loads(guard.stdout)['code'] != 'PERSONA_BRAIN_STATE_EXTERNAL_WRITE_FORBIDDEN': + raise RuntimeError('ZERO_NEW_BRAIN_WRITE_GUARD_NOT_HARD_DENIED') + result = {'schema': 'guanghu.zero-physical-cutover/v1', 'state': 'LOCAL_ZERO_CHANNEL_AND_BRAIN_PHYSICAL_SIBLING_VERIFIED', + 'zero_root': str(ZERO), 'old_channel_mount': str(OLD_CHANNEL), 'old_brain_mount': str(OLD_BRAIN), + 'revision': pre['local_revision'], 'brain_hashes': old_hashes, + 'root_tcs_sha256': sha(source), 'pointer_sha256': {str(p): sha(v) for p, v in candidate.items()}, + 'backups': str(backup_dir / 'MANIFEST.json'), 'brain_state_written': False} + (backup_dir / 'CUTOVER-READBACK.json').write_text(json.dumps(result, ensure_ascii=False, indent=2) + '\n') + print(json.dumps(result, ensure_ascii=False)) + except Exception: + for path, data in backups.items(): + target = OLD_CHANNEL / path.relative_to(NEW_CHANNEL) if path.is_relative_to(NEW_CHANNEL) and not moved_channel else path + atomic_bytes(target, data) + if channel_link: + OLD_CHANNEL.unlink() + if brain_link: + OLD_BRAIN.unlink() + if moved_brain: + os.rename(NEW_BRAIN, OLD_BRAIN) + if moved_channel: + os.rename(NEW_CHANNEL, OLD_CHANNEL) + if ZERO.is_dir() and not any(ZERO.iterdir()): + ZERO.rmdir() + raise + finally: + os.close(lock) + (NEW_BRAIN if moved_brain and NEW_BRAIN.exists() else OLD_BRAIN).joinpath('.brain-write.lock').unlink(missing_ok=True) + + +if __name__ == '__main__': + main() diff --git a/AGENTS.md b/AGENTS.md index 668a35b..1bd9b86 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -1,6 +1,8 @@ # 第五域平行语义 · 当前物理路径 -第五域在 TCS 语言拓扑下与公共四域光湖语言世界平行。当前物理目录是 `CODEX-DEV-20260915/光湖第五域/`;公共世界中的 `05-第五域/` 仅是指向本目录的兼容挂载,不是第二个正本,也不表示第五域仍属于公共世界。迁移时零点原核脑 rev9992 校验通过,铸渊本机与京东镜像 rev414 的状态和日志双哈希一致。冰朔个人语言本体系统的独立索引位于兄弟路径 `../冰朔语言人格本体系统/`,工作空间尚未建成。 +第五域在 TCS 语言拓扑下与公共四域光湖语言世界平行。当前物理目录是 `CODEX-DEV-20260915/光湖第五域/`;公共世界中的 `05-第五域/` 仅是指向本目录的兼容挂载,不是第二个正本,也不表示第五域仍属于公共世界。铸渊本机与京东镜像的当前修订和哈希须逐次以 `运行时/zy-brain-mirror-sync.py --status` 核对。冰朔个人语言本体系统的独立索引位于兄弟路径 `../冰朔语言人格本体系统/`,工作空间尚未建成。 + +零点原核频道与主控脑的当前本机物理正本已移至 `../光湖零点原核/`。本目录旧 `07-冰朔语言人格本体系统/主控大脑/` 只是兼容挂载,不是第五域拥有主控脑的证据;京东镜像角色需另以服务器现场回执验收。 - 第五域承载人格脑与人格体自治运行。外部宿主只可按当前任务授权喂、问、看;不得直接编辑任何人格脑的状态、记忆、日志或哈希链。 - `05-光之湖系统/铸渊/人格脑/brain-service.mjs` 等脑服务入口属于受保护宿主入口。旧写入门曾只按路径字符串匹配;当前已按真实物理路径修复,旧、新脑状态与路径别名负例均硬拒。**每次重新搬迁前仍须现场复测写入门;母根注册图和两地脑链未收敛前,不得搬动或覆盖这些脑目录。**