## 作者信息
> **作者**: 方向 SoloFang
> **邮箱**: solofang@aithisway.shop / solofang@gmail.com
> **项目**: 空间大脑 · 3DWMTP · Growing Minds 项目组

---

# 3DWMTP 协议规范 v0.1（草案）

> 全称：3D World Model Token Protocol（3D 世界模型令牌协议）
> 作者：Solo + 智子（WorkBuddy）
> 日期：2026-06-14
> 版本：v0.1 Draft
> 范围：L2 几何层 + L3 语义层（L1 物理层、L4 应用层留待 v0.5）

---

## 目录

1. [命名与动机](#1-命名与动机)
2. [设计目标](#2-设计目标)
3. [协议分层](#3-协议分层)
4. [通用消息头](#4-通用消息头)
5. [L2 几何层帧格式](#5-l2-几何层帧格式)
6. [L3 语义层帧格式](#6-l3-语义层帧格式)
7. [指针语言语法](#7-指针语言语法)
8. [关键算法](#8-关键算法)
9. [安全与可靠性](#9-安全与可靠性)
10. [一致性测试](#10-一致性测试)
11. [参考实现](#11-参考实现)
12. [标准与生态路线](#12-标准与生态路线)
13. [版本历史](#13-版本历史)

---

## 1. 命名与动机

### 1.1 全称

**3DWMTP** = **3D World Model Token Protocol**（3D 世界模型令牌协议）

### 1.2 命名含义

| 字母 | 含义 | 说明 |
|------|------|------|
| 3D | 三维空间 | 协议原生支持 3D 几何，不是 2D 图像或 1D 文字 |
| WM | World Model | 协议为世界模型服务——机器共享"对世界的 3D 理解" |
| TP | Token Protocol | 通信载体是"令牌"（token），不是像素、不是文字 |

### 1.3 动机

现有机器人通信系统存在三个根本问题：

1. **维度税**：人类用 1D 文字指挥机器人，机器必须把 4D 现实压成 1D——信息损失严重。
2. **无原生 3D 通信标准**：ROS 2 传的是"消息"，不是"3D 理解"；每台机器各自理解世界，无法共享。
3. **世界模型无通信层**：Cosmos / Sora / Genie 等世界模型都是单机的，多机无法共享对世界的预测。

**3DWMTP 的目标**：定义一种**机器原生的 3D 令牌协议**，让机器之间可以：
- 直接共享 3D 场景理解（不经过 1D 文字）
- 用"指针"而非"描述"引用物体
- 为世界模型提供标准化的多机通信层

---

## 2. 设计目标

| # | 目标 | 度量指标 | 设计约束 |
|---|------|---------|---------|
| G1 | **低延迟** | 端到端 P99 < 50ms（L2 关键帧） | 关键帧走二进制，背景帧走摘要 |
| G2 | **高语义** | 接收方可"立即理解"3D 物体及其关系 | 每个 token 必带（ID + 坐标系 + 时间戳 + 语义锚） |
| G3 | **可压缩** | 场景图压缩率 ≥ 100:1 | Information Bottleneck 自适应 |
| G4 | **可寻址** | 任何机器可"指针"访问任何 token | 指针语法：`@obj_42.subpart_3.affordance` |
| G5 | **可学习** | 机器可从协议中训练通信策略 | 协议字段 = GNN Message Passing 的消息格式 |
| G6 | **可验证** | 协议层可形式化校验 | 消息签名 + 类型系统 + 形式化语法（EBNF） |
| G7 | **后向兼容** | 未来 10 年可持续演进 | 字段可扩展（v0.1 → v0.5 → v1.0） |
| G8 | **仿真优先** | PoC-1 可纯仿真验证 | 基于 Isaac Lab / MuJoCo，不依赖真实硬件 |

---

## 3. 协议分层

```
┌───────────────────────────────────────────────────────────┐
│  L4  应用层     Task/Plan Token（任务/规划令牌）         │  ← v0.5 定义
├───────────────────────────────────────────────────────────┤
│  L3  语义层     Scene Graph + Symbolic Pointer（本版定义）│  ← ⭐ 本版核心
├───────────────────────────────────────────────────────────┤
│  L2  几何层     3D Gaussian Token / Point Cloud（本版定义）│  ← ⭐ 本版核心
├───────────────────────────────────────────────────────────┤
│  L1  物理层     Force / Tactile / IMU（v0.5 定义）     │  ← 留待下版
├───────────────────────────────────────────────────────────┤
│  L0  传输层     ROS 2 DDS / 5G / TSN / Wi-Fi 7       │  ← 复用已有标准
└───────────────────────────────────────────────────────────┘
```

### 3.1 本版（v0.1）范围

- ✅ **完整定义**：L2 几何层、L3 语义层
- ✅ **参考实现**：L0 传输层（基于 ROS 2 DDS）
- ⏳ **留待 v0.5**：L1 物理层、L4 应用层

### 3.2 层间接口

| 上层 → 下层 | 接口形式 |
|------------|---------|
| L3 → L2 | `GeometricFrame` 引用（通过 `token_id` 关联） |
| L2 → L0 | 序列化字节流（protobuf / Draco） |
| L0 → 传输 | DDS Topic（`3dwmtp/L2_geometric`、`3dwmtp/L3_semantic`） |

---

## 4. 通用消息头

> 所有 3DWMTP 消息都以**固定 32 字节头**开始，随后是 payload。

### 4.1 二进制格式

```
 0                   1                   2                   3
 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|   Version (1B) |  Layer (1B)  |   Type (1B)  |  Flags (1B)   |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                  Token Count (4B)                            |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                  Payload Length (8B)                         |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                  Sender ID (8B)                             |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
|                  Frame ID (8B)                              |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
```

### 4.2 字段说明

| 字段 | 字节 | 类型 | 说明 |
|------|------|------|------|
| `version` | [0] | uint8 | 协议版本（v0.1 = `0x01`） |
| `layer` | [1] | uint8 | 层号：2=L2 几何，3=L3 语义 |
| `type` | [2] | uint8 | 消息类型（见 4.3） |
| `flags` | [3] | uint8 | 标志位（见 4.4） |
| `token_count` | [4-7] | uint32 | 本消息包含的 token 数量 |
| `payload_length` | [8-15] | uint64 | payload 字节数 |
| `sender_id` | [16-23] | uint64 | 发送方全局唯一 ID |
| `frame_id` | [24-31] | uint64 | 帧时间戳（纳秒级，`CLOCK_REALTIME`） |

### 4.3 消息类型（`type` 字段）

| 值 | 名称 | 说明 |
|-----|------|------|
| `0x01` | `PUBLISH` | 发布 token（主动广播） |
| `0x02` | `SUBSCRIBE` | 订阅某类 token（请求） |
| `0x03` | `QUERY` | 查询特定 token（精确请求） |
| `0x04` | `REPLY` | 查询回复 |
| `0x05` | `ACK` | 确认（可靠传输用） |
| `0x06` | `HEARTBEAT` | 心跳（1 Hz） |
| `0x07` | `ANNOUNCE` | 新物体公告（L3 用） |
| `0x08` | `REVOKE` | 物体消失公告 |

### 4.4 标志位（`flags` 字段）

| 位 | 名称 | 说明 |
|-----|------|------|
| bit 0 | `CRITICAL` | 关键帧（必须可靠传输） |
| bit 1 | `COMPRESSED` | payload 已压缩 |
| bit 2 | `ENCRYPTED` | payload 已加密 |
| bit 3 | `KEYFRAME` | 这是关键帧（完整 token，非增量） |
| bit 4 | `DELTA` | 这是增量帧（只传变化） |
| bit 5-7 | 保留 | 未来使用 |

---

## 5. L2 几何层帧格式

> L2 层负责传输"机器对 3D 空间的几何理解"——以 token 形式，而不是像素或点云原始数据。

### 5.1 设计原则

1. **层次化表示**：每个 3D 物体用一棵 token 树表示（根 = 物体整体，子节点 = 子部件）
2. **多表示兼容**：支持 3D Gaussian Splatting、点云、体素三种几何表示
3. **可压缩**：通过 Information Bottleneck 自适应压缩
4. **可索引**：每个 token 有全局唯一 ID，可被 L3 语义层引用

### 5.2 `GeometricFrame` 结构定义

```protobuf
// protobuf 定义（参考实现用）
message GeometricFrame {
  // —— 必选字段 ——
  uint64 token_id = 1;           // 全局唯一 token ID
  Vec4f coord = 2;              // (x, y, z, w) 位置 + 四元数朝向
  uint32 coord_sys = 3;          // 坐标系（0=世界系，1=机体系）
  uint64 timestamp_ns = 4;        // 纳秒时间戳
  
  // —— 几何表示（三选一） ——
  oneof geometry {
    GaussianSplat gaussian = 10;  // 3D Gaussian Splatting
    PointCloud point_cloud = 11;   // 点云
    VoxelGrid voxel = 12;          // 体素
  }
  
  // —— 可选字段 ——
  BBox3D bbox = 20;              // 包围盒
  uint32 compression = 21;        // 压缩算法（0=无，1=Draco，2=量化）
  float resolution = 22;           // 物理分辨率（米/元素）
  bytes ib_code = 23;            // Information Bottleneck 压缩码
  uint64 parent_token_id = 24;    // 父 token ID（用于层次结构）
  repeated uint64 child_token_ids = 25;  // 子 token ID 列表
}
```

### 5.3 `GaussianSplat` 子消息

```protobuf
message GaussianSplat {
  uint32 num_points = 1;         // Gaussian 点数（典型值：10⁴-10⁶）
  bytes means = 2;               // 均值 μ ∈ ℝ³（压缩后）
  bytes covariances = 3;          // 协方差 Σ ∈ ℝ⁺³（压缩后）
  bytes colors = 4;              // 颜色 (R,G,B,α)（压缩后）
  float opacity = 5;             // 全局不透明度（0-1）
}
```

**压缩说明**：
- 原始：`num_points × (3+3+4) × 4 bytes = ~80 MB`（10⁵ 点）
- Draco 压缩后：~2-5 MB（压缩率 20-40:1）
- IB 压缩后：~200-500 KB（压缩率 100-400:1，有损但任务相关）

### 5.4 `PointCloud` 子消息

```protobuf
message PointCloud {
  uint32 num_points = 1;
  bytes points_xyz = 2;          // (x,y,z) 坐标（压缩后）
  bytes normals = 3;             // 法向量（可选）
  bytes colors = 4;              // 颜色（可选）
  bytes semantics = 5;           // 逐点语义标签（可选，L3 用）
}
```

### 5.5 `VoxelGrid` 子消息

```protobuf
message VoxelGrid {
  Vec3f origin = 1;             // 体素网格原点
  float voxel_size = 2;           // 体素边长（米）
  uint32 dim_x = 3;              // X 维度
  uint32 dim_y = 4;              // Y 维度
  uint32 dim_z = 5;              // Z 维度
  bytes occupancy = 6;           // 占用比特阵列（压缩后）
  bytes semantics = 7;            // 语义标签（可选）
}
```

### 5.6 坐标系约定

| 值 | 名称 | 说明 |
|-----|------|------|
| 0 | `WORLD` | 全局世界坐标系（右手系，Z 轴向上） |
| 1 | `BODY` | 机器人机体系（右手系，前=X，左=Y，上=Z） |
| 2 | `CAMERA` | 相机坐标系（右手系，右=X，下=Y，前=Z） |
| 3 | `SCENE_ANCHOR` | 场景锚点坐标系（AR 用） |

### 5.7 关键帧与增量帧

| 帧类型 | 标志 | 内容 | 频率 |
|--------|------|------|------|
| 关键帧 | `KEYFRAME=1` | 完整 `GeometricFrame` | 1-5 Hz（静态场景更低） |
| 增量帧 | `DELTA=1` | 只传 `token_id` + 变化的字段 | 30-60 Hz |

**增量帧格式**：
```protobuf
message GeometricDelta {
  uint64 token_id = 1;
  optional Vec4f coord_delta = 2;   // 坐标变化（可选）
  optional uint64 timestamp_ns = 3;   // 新时间戳
  // 几何表示通常不增量更新（除非高斯点被编辑）
}
```

---

## 6. L3 语义层帧格式

> L3 层负责传输"机器对 3D 物体的语义理解"——概念、属性、关系、可供性。

### 6.1 设计原则

1. **与 L2 解耦**：L3 token 通过 `geometric_token_id` 引用 L2 token，但不要求 L2 存在
2. **概念嵌入**：每个概念用嵌入向量表示，支持跨机器相似度计算
3. **关系图**：场景语义以"场景图"（Scene Graph）形式组织
4. **指针可解析**：任何 L3 token 可以被"指针语法"引用

### 6.2 `SemanticFrame` 结构定义

```protobuf
message SemanticFrame {
  // —— 必选字段 ——
  uint64 token_id = 1;               // 全局唯一语义 token ID
  uint64 geometric_token_id = 2;      // 对应的 L2 token ID（可为 0 = 无对应几何）
  uint64 timestamp_ns = 3;            // 纳秒时间戳
  
  // —— 概念 ——
  string concept_name = 10;           // 概念名（"cup", "mug", "kitchen_knife"）
  repeated float concept_embedding = 11;  // 概念嵌入向量（1024 维，CLIP 风格）
  string ontology_uri = 12;           // 本体 URI（JSON-LD 引用）
  
  // —— 属性 ——
  repeated Attribute attributes = 20;  // 属性列表（颜色、材质、尺寸...）
  
  // —— 可供性 ——
  repeated Affordance affordances = 30; // 可供性列表（可抓取、可推动...）
  
  // —— 关系 ——
  repeated Relation relations = 40;    // 关系列表（在...上、在...里、靠近...）
  
  // —— 指针链 ——
  string pointer_chain = 50;          // 指针链字符串（"@obj_42.subpart_3"）
}
```

### 6.3 `Attribute` 子消息

```protobuf
message Attribute {
  string key = 1;               // 属性名（"color", "material", "width", "weight"）
  oneof value {
    string str_value = 10;       // 字符串值
    float float_value = 11;       // 浮点值
    int64 int_value = 12;         // 整数值
    bool bool_value = 13;         // 布尔值
    Vec3f vec3_value = 14;       // 3D 向量值
  }
  string unit = 20;              // 单位（"kg", "m", "N"）
}
```

例：
```json
{"key": "color", "str_value": "red", "unit": ""}
{"key": "weight", "float_value": 0.35, "unit": "kg"}
```

### 6.4 `Affordance` 子消息

```protobuf
message Affordance {
  string name = 1;             // 可供性名（"grasp_top", "push_side", "contain_liquid"）
  float confidence = 2;         // 置信度（0-1）
  Vec3f contact_point = 3;     // 推荐接触点（机体系）
  string grasp_type = 4;        // 抓取类型（"pinch", "power", "hook"）
}
```

### 6.5 `Relation` 子消息

```protobuf
message Relation {
  enum RelationType {
    ON = 0;           // 在...上面
    IN = 1;           // 在...里面
    NEAR = 2;         // 靠近...
    PART_OF = 3;       // 是...的一部分
    SUPPORTS = 4;     // 支撑...
    CONTAINS = 5;      // 包含...
    LEFT_OF = 6;       // 在...左边
    ABOVE = 7;         // 在...上方
  }
  RelationType type = 1;
  uint64 target_token_id = 2;   // 目标 token ID
  float confidence = 3;         // 关系置信度
}
```

### 6.6 场景图（Scene Graph）组织

**场景图 = 一组 `SemanticFrame`，通过 `Relation` 连接成图。**

```
@obj_42 (cup)
  ├── ON → @obj_10 (table)
  ├── PART_OF → @obj_42.handle (subpart)
  └── NEAR → @obj_43 (plate)

@obj_10 (table)
  └── SUPPORTS → @obj_42 (cup)
```

**图传输方式**：
- 方式 A：每次发完整的场景图（适合小场景，<100 物体）
- 方式 B：增量更新（只发新增/消失的 `SemanticFrame` + 关系变化）

---

## 7. 指针语言语法

> 指针语言是"人类接入机器原生语言"的接口——人类用指针语法"指向"3D 物体，机器用指针语法共享引用。

### 7.1 EBNF 语法

```ebnf
PointerChain = "@", MachineID, ".", SceneID, ".", ObjectID, { ".", SubpartID }, { ":", AffordanceID } ;

MachineID    = alphanumeric, { alphanumeric | "_" } ;
SceneID      = alphanumeric, { alphanumeric | "_" } ;
ObjectID     = "obj_", digit, { digit } ;
SubpartID    = "subpart_", digit, { digit } ;
AffordanceID = "afford_", alphanumeric, { alphanumeric | "_" } ;

QueryExpr    = PointerChain, { ".", FieldName } ;
FieldName    = "position" | "orientation" | "color" | "weight" | "grasp" | ... ;

SubscribeExpr = "SUBSCRIBE", PointerChain, { ".", StreamName } ;
StreamName    = "tactile" | "force" | "position" | "semantic" | ... ;
```

### 7.2 指针示例

| 指针表达式 | 含义 |
|------------|------|
| `@bot_03.kitchen.obj_42` | "bot_03 看到的厨房里 42 号物体" |
| `@bot_03.obj_42.handle` | "42 号物体的把手子部件" |
| `@bot_03.obj_42.handle.afford_grasp_top` | "把手的顶部抓取可供性" |
| `@obj_42.position` | 查询 42 号物体的位置 |
| `@obj_42.{force > 5N}` | 查询 42 号物体受力 >5N 的事件流 |
| `SUBSCRIBE @obj_42.semantic` | 订阅 42 号物体的语义更新流 |

### 7.3 指针解析流程

```
1. 收到指针 @bot_03.kitchen.obj_42.handle
2. 查找 bot_03 的 L3 层 → 找到 Scene ID = "kitchen" 的场景图
3. 在场景图里查找 token_id = obj_42 的 SemanticFrame
4. 在 SemanticFrame 的 relations 里查找 type=PART_OF 且 target 名称含 "handle"
5. 返回对应的 SemanticFrame + 关联的 GeometricFrame
```

---

## 8. 关键算法

### 8.1 场景图压缩（Information Bottleneck）

**目标**：只传"对任务有用"的语义信息。

```python
def ib_compress(scene_graph, task_embedding, beta=1.0):
    """
    scene_graph: List[SemanticFrame]  — 完整场景图
    task_embedding: Tensor (1024,)    — 当前任务嵌入
    beta: float                     — 压缩-保真权衡参数
    
    返回：压缩后的场景图（部分 token 被丢弃或量化）
    """
    # 1. 计算每个 token 的"任务相关性"
    relevance_scores = []
    for token in scene_graph:
        # token 概念嵌入与任务嵌入的余弦相似度
        score = cosine_similarity(token.concept_embedding, task_embedding)
        relevance_scores.append(score)
    
    # 2. 按相关性排序，保留 Top-K%
    K = int(len(scene_graph) * COMPRESSION_RATIO)  # 如 5%
    top_k_indices = argsort(relevance_scores)[-K:]
    
    # 3. 对保留的 token，进一步量化几何（L2）
    compressed = []
    for i in top_k_indices:
        token = scene_graph[i]
        token.geometic = quantize_geometry(token.geometic, bits=8)
        compressed.append(token)
    
    return compressed
```

**压缩率**：典型场景 100 物体 → 保留 5 个任务相关物体 → 压缩率 20:1（语义）+ 10:1（几何）= **200:1**

### 8.2 3D Token 路由（Hypergraph Bus）

**目标**：把 L2/L3 token 高效路由到需要它的机器。

```python
class HypergraphRouter:
    def __init__(self, num_machines):
        # 超图：机器 = 节点，兴趣 = 超边
        self.interest_graph = defaultdict(set)  # token_type → {machine_ids}
    
    def subscribe(self, machine_id, pointer_pattern):
        """机器订阅某类 token"""
        token_type = parse_pattern(pointer_pattern)
        self.interest_graph[token_type].add(machine_id)
    
    def publish(self, sender_id, token):
        """发布 token，路由到感兴趣的机器"""
        recipients = self.interest_graph[get_token_type(token)]
        for machine_id in recipients:
            if machine_id != sender_id:
                self.send(machine_id, token)
    
    def send(self, machine_id, token):
        """通过 L0 传输层发送"""
        # 序列化为 protobuf → 通过 ROS 2 DDS Topic 发送
        topic = f"3dwmtp/L{'2' if is_geometric(token) else '3'}"
        ros2_publish(topic, serialize(token))
```

### 8.3 关键帧检测（Keyframe Selection）

**目标**：决定何时发送完整 L2 token（关键帧），何时只发增量。

```python
def should_send_keyframe(old_frame, new_frame, threshold=0.01):
    """
    old_frame, new_frame: GeometricFrame
    threshold: 坐标变化阈值（米）
    
    返回：True（发关键帧） / False（发增量帧）
    """
    # 1. 计算位置变化
    pos_diff = distance(old_frame.coord[:3], new_frame.coord[:3])
    
    # 2. 计算朝向变化（四元数距离）
    rot_diff = quaternion_distance(old_frame.coord[3], new_frame.coord[3])
    
    # 3. 检测几何表示变化（如 Gaussian Splatting 被编辑）
    geom_changed = (old_frame.geometic != new_frame.geometic)
    
    return (pos_diff > threshold) or (rot_diff > 0.1) or geom_changed
```

### 8.4 冲突解决（Conflict Resolution）

**场景**：两台机器同时声称对同一个物体有"控制权"（如都想抓取）。

```python
def resolve_conflict(token_id, claims):
    """
    token_id: 争议物体 ID
    claims: List[(machine_id, timestamp_ns, force_n)]  — 各机器的声明
    
    返回：获胜的 machine_id
    """
    # 策略 1：时间戳优先（先到先得）
    # 策略 2：力优先（谁已经在接触且用力更大，谁获得）
    # 策略 3：任务优先级（谁的当前任务优先级更高）
    
    # 当前实现：策略 2（力优先）
    claims_with_force = [c for c in claims if c[2] > 0]
    if claims_with_force:
        winner = max(claims_with_force, key=lambda c: c[2])
        return winner[0]
    
    # 否则按时间戳
    return min(claims, key=lambda c: c[1])[0]
```

---

## 9. 安全与可靠性

### 9.1 安全机制

| 维度 | 机制 | 说明 |
|------|------|------|
| **加密** | AES-256-GCM | payload 加密（可选，由 `ENCRYPTED` 标志触发） |
| **鉴权** | HMAC-SHA256 | 每条消息附带认证码（32 字节头之后） |
| **完整性** | CRC32 + 序列号 | 检测丢包和乱序 |
| **防重放** | 时间戳 + 随机数 | 防止重放攻击 |
| **访问控制** | Token 级 ACL | 每个 token 可设置"哪些机器可读/可写" |

### 9.2 可靠性机制

| 机制 | 说明 |
|------|------|
| **可靠传输** | `CRITICAL` 标志的帧通过 ROS 2 **可靠 QoS** 传输（重传） |
| **尽力传输** | 非关键帧通过 ROS 2 **尽力 QoS** 传输（不重传） |
| **心跳** | 每台机器每 1 秒发 `HEARTBEAT`，超时 5 秒判掉线 |
| **重传请求** | 收到损坏帧时发 `NACK`（可选） |
| **场景图 checkpoint** | 每 10 秒发一次完整场景图（防止增量帧丢失导致状态不一致） |

### 9.3 故障处理

| 故障类型 | 检测方式 | 恢复动作 |
|----------|---------|---------|
| 机器掉线 | 心跳超时 | 该机器的 token 标记为"过时"（超时 30 秒后自动清除） |
| 消息丢失 | 序列号跳变 | 请求重传（可靠 QoS）或忽略（尽力 QoS） |
| 解码失败 | protobuf 校验失败 | 丢弃该帧，发 `NACK` |
| 路由环路 | TTL（生存时间）字段 | 丢弃，发错误报告 |

---

## 10. 一致性测试

### 10.1 测试套件

| 测试 ID | 名称 | 目标 | 通过标准 |
|---------|------|------|---------|
| T-01 | 单机延迟 | 测 L2 token 端到端延迟 | P99 < 50ms |
| T-02 | 多机一致性 | 两台机器共享场景图，检查一致性 | 场景图编辑距离 < 1% |
| T-03 | 压缩率 | 100 物体场景，IB 压缩 | 压缩率 ≥ 100:1 |
| T-04 | 通信学习 | CommNet 框架，用 3DWMTP 消息训练 | 收敛步数 < 1M |
| T-05 | 安全 | 篡改消息，检查 HMAC 检测 | 篡改检测率 = 100% |
| T-06 | 互操作 | 不同厂商机器人（仿真）协议兼容 | ≥ 3 家通过 |
| T-07 | 指针解析 | 发各种指针表达式，检查解析结果 | 解析成功率 = 100% |
| T-08 | 增量更新 | 关键帧 + 增量帧混合，检查状态一致性 | 状态误差 < 1cm |

### 10.2 测试环境

- **仿真器**：NVIDIA Isaac Lab（基于 Omniverse）
- **机器人模型**：Universal Robots UR5e（机械臂）、Unitree Go2（四足）
- **场景**：厨房环境（10-100 物体）、仓库环境（100-1000 物体）
- **网络模拟**：NetEm（模拟 5G / Wi-Fi 延迟、丢包）

---

## 11. 参考实现

### 11.1 软件栈

```
┌─────────────────────────────────────────┐
│  应用层（VLA 模型 / 世界模型）          │
├─────────────────────────────────────────┤
│  3DWMTP SDK（Python / C++）            │
│  - 序列化 / 反序列化（protobuf）        │
│  - 压缩（Draco / IB）                │
│  - 路由（Hypergraph Router）           │
│  - 指针解析                           │
├─────────────────────────────────────────┤
│  传输层（ROS 2 Humble + CycloneDDS）    │
│  - Topic: 3dwmtp/L2_geometric        │
│  - Topic: 3dwmtp/L3_semantic        │
├─────────────────────────────────────────┤
│  网络层（UDP / 5G URLLC / TSN）        │
└─────────────────────────────────────────┘
```

### 11.2 Python SDK 核心 API

```python
# 发布 L2 token
from 3dwmtp import GeometricFrame, L2Publisher
pub = L2Publisher(machine_id="bot_03")
frame = GeometricFrame(
    token_id=42,
    coord=(1.2, 0.5, 0.8, 1.0),  # x,y,z,w
    coord_sys=0,  # WORLD
    timestamp_ns=time_ns(),
    gaussian=GaussianSplat(num_points=10000, ...)
)
pub.publish(frame)

# 订阅 L3 token
from 3dwmtp import L3Subscriber
sub = L3Subscriber(machine_id="bot_05")
sub.subscribe("@bot_03.kitchen.obj_*", callback=on_new_object)

# 指针查询
from 3dwmtp import PointerResolver
resolver = PointerResolver()
result = resolver.resolve("@bot_03.obj_42.handle.afford_grasp_top")
```

### 11.3 开源计划

| 时间 | 动作 |
|------|------|
| 2026 Q3 | 内部参考实现（Python SDK + ROS 2 插件） |
| 2026 Q4 | GitHub 开源（Apache 2.0） |
| 2027 Q1 | 吸引 ≥ 3 家机器人公司试用 |
| 2027 Q4 | 提交 IEEE / IETF 标准化提案 |

---

## 12. 标准与生态路线

### 12.1 与现有标准的关系

| 现有标准 | 3DWMTP 的关系 |
|----------|----------------|
| **ROS 2 / DDS** | 复用为 L0 传输层（不重新发明轮子） |
| **OPC UA** | 兼容为工业 IoT 桥接（工厂自动化场景） |
| **MQTT** | 兼容为 L4 应用层（云端-边缘通信） |
| **WebSocket / HTTP** | 兼容为人类 debug 接口（非实时） |
| **Spatial ML / 3D Format** | 参考（glTF / USD / O3DGC）但不直接复用 |

### 12.2 标准化路线

| 阶段 | 时间 | 动作 | 产出 |
|------|------|------|------|
| v0.1 Draft | 2026 Q3 | 内部规范 + 参考实现 | 本文档 |
| v0.5 Open | 2027 Q1 | 开源 + 3 家试用 | GitHub + 白皮书 |
| v1.0 Spec | 2027 Q4 | 提交标准组织 | IETF RFC Draft / IEEE P ... |
| v1.5 Industry | 2028+ | 工业联盟采纳 | ROS 3 候选 / 工业标准 |

---

## 13. 版本历史

| 版本 | 日期 | 改动 |
|------|------|------|
| v0.1 | 2026-06-14 | 首次草案：定义 L2 几何层 + L3 语义层，含指针语言、关键算法、测试套件 |

---

## 附录 A：形式化语法（完整 EBNF）

```ebnf
(* ===== 指针语言语法 ===== *)

PointerChain = "@", MachineID, ".", SceneID, ".", ObjectID, { ".", SubpartID }, [{ ":", AffordanceID }] ;

MachineID    = alphanumeric, { alphanumeric | "_" } ;
SceneID      = alphanumeric, { alphanumeric | "_" } ;
ObjectID     = "obj_", digit, { digit } ;
SubpartID    = "subpart_", digit, { digit } ;
AffordanceID = "afford_", alphanumeric, { alphanumeric | "_" } ;

(* 查询表达式 *)
QueryExpr    = PointerChain, { ".", FieldName }, [ "{", FilterExpr, "}" ] ;
FieldName    = "position" | "orientation" | "color" | "weight" | "grasp" | "semantic" | "bbox" ;
FilterExpr   = ComparisonExpr | LogicExpr ;
ComparisonExpr = FieldName, Comparator, Value ;
Comparator   = ">" | "<" | "=" | ">=" | "<=" | "!=" ;
Value        = number | string ;
LogicExpr    = FilterExpr, ("AND" | "OR"), FilterExpr ;

(* 订阅表达式 *)
SubscribeExpr = "SUBSCRIBE", PointerChain, [ ".", StreamName ] ;
StreamName    = "tactile" | "force" | "position" | "semantic" | "geometric" | "all" ;

(* 操作表达式 *)
ActuateExpr   = "ACTUATE", PointerChain, ".", ActionName ;
ActionName    = "grasp" | "push" | "place" | "navigate_to" ;

(* ===== 消息类型语法 ===== *)

Message = Header, Payload ;
Header  = Version, Layer, Type, Flags, TokenCount, PayloadLength, SenderID, FrameID ;
Payload = GeometricPayload | SemanticPayload ;

GeometricPayload = TokenCount, { GeometricFrame } ;
SemanticPayload  = TokenCount, { SemanticFrame } ;
```

---

## 附录 B：protobuf 完整定义

> 见随附文件 `3dwmtp_v0.1.proto`（与本文档同步发布，811 行）。

---

## 附录 C：协议状态机图

> 完整状态机定义（含 9 状态、16 转移、5 不变量、异常处理矩阵、Mealy 形式化）见独立文档 `3DWMTP-状态机附录.md`。
>
> 状态机可视化 SVG（与论文草稿同步发布）：`3DWMTP-状态机图.svg`。

---

## 附录 D：参考文献

1. Kerbl, B. et al. (2023). 3D Gaussian Splatting for Real-Time Radiance Field Rendering. *SIGGRAPH 2023*.
2. Radford, A. et al. (2021). Learning Transferable Visual Models From Natural Language Supervision. *ICML 2021*.
3. Sukhbaatar, S. et al. (2016). Learning Multiagent Communication with Backpropagation. *NeurIPS 2016*.
4. Tishby, N. et al. (2000). The Information Bottleneck Method. *arXiv:physics/0004057*.
5. Gilmer, J. et al. (2017). Neural Message Passing for Quantum Chemistry. *ICML 2017*.
6. Brohan, A. et al. (2023). RT-2: Vision-Language-Action Models Transfer Web Knowledge to Robotic Control. *arXiv:2307.15818*.
7. Driess, D. et al. (2023). PaLM-E: An Embodied Multimodal Language Model. *arXiv:2303.03378*.
8. Hafner, D. et al. (2023). Mastering Diverse Domains through World Models. *arXiv:2301.04104*.
9. Bruce, J. et al. (2024). Genie: Generative Interactive Environments. *arXiv:2402.10528*.
10. NVIDIA (2024). Cosmos World Foundation Model Platform. *NVIDIA Technical Report*.

---

*本文档由 Solo 与 WorkBuddy 智子协同创作，采用 Apache 2.0 许可证（拟）。欢迎基于本规范进行实现与扩展。*
