|
4 | 4 | |---|---| |
5 | 5 | | 规范编号 | SPEC-007 | |
6 | 6 | | 标题 | 构建插件:配置、施工与校验的分工,运行时与规划期的义务 | |
7 | | -| 状态 | 草案 v0.1 | |
8 | | -| 版本 | 0.1 | |
| 7 | +| 状态 | 草案 v0.2 | |
| 8 | +| 版本 | 0.2 | |
9 | 9 | | 最后修改 | 2026-09-26 | |
10 | | -| 对应实现 | 逐条标注。标「已实现」的条款对应 mcpp >= 2026.9.26.1;标「未实现」的条款随 mcpp#702 落地 | |
| 10 | +| 对应实现 | 逐条标注。未注明版本的「已实现」条款对应 mcpp >= 2026.9.26.1;注明 mcpp#702 的条款对应 mcpp >= 2026.9.27.1 | |
11 | 11 | | 相关设计文档 | `.agents/docs/2026-09-26-compile-database-and-issue-699-design.md`(§5) | |
12 | 12 | | 相关 issue | mcpp#699、mcpp#701、mcpp#702、mcpp#703 | |
13 | 13 | | 使用文档 | [docs/30 - build.mcpp](../30-build-mcpp.md)、[docs/31 - 编写规则包](../31-authoring-a-rule-package.md) | |
|
57 | 57 | 环境变量。配置**禁止**依赖施工的结果,例如枚举一个安装前缀中由 action 产生的文件:规划 |
58 | 58 | (`mcpp emit build-database`)与第一次构建都发生在施工之前,依赖施工结果的配置在第一次与 |
59 | 59 | 第二次构建之间不同。(作者义务;构建程序的重新运行依据落在一个 `prepare` action 声明的目录内 |
60 | | - 时,引擎给出一条警告,**未实现**,mcpp#702) |
| 60 | + 时,引擎给出一条警告并点名两者,**已实现**,mcpp#702) |
61 | 61 | - **R1.4** 构建程序在规划与构建中**必须**行为相同。引擎不提供「正在规划」的信号,因为规划 |
62 | 62 | 所描述的计划与 `mcpp build --configure-only` 计算的计划相同(SPEC-005 R1.2)。(**已实现**) |
63 | 63 |
|
|
74 | 74 | | 宏 | `define` | `cfg` | 协议 1 | |
75 | 75 | | 链接库与库目录 | `link_lib`、`link_search` | `link-lib`、`link-search` | 协议 1 | |
76 | 76 | | 其他链接选项(含库的完整路径) | `link_flag` | `link-flag` | 协议 8 | |
77 | | - | 运行时搜索目录 | `runtime_search_dir` | `runtime-search-dir` | 协议 12,**未实现**(mcpp#702) | |
| 77 | + | 运行时搜索目录 | `runtime_search_dir` | `runtime-search-dir` | 协议 12(mcpp#702) | |
78 | 78 | | 放到程序旁的文件 | `deploy` | `deploy` | 协议 11 | |
79 | 79 | | 生成的源 | `generated`、`source` 与 `role = "source"` 的 action | `generated`、`source`、`action` | 协议 1 | |
80 | 80 | | 重新运行构建程序的依据 | `rerun_if_changed`、`rerun_if_changed_glob`、`rerun_if_env_changed` | 同名 | 协议 1、2 | |
|
87 | 87 | - **R2.3** 插件**必须**使用现行字段的指令,**禁止**依赖只为兼容而保留的字段 |
88 | 88 | (`[runtime] library_dirs`,docs/04 §2.11)。(作者义务) |
89 | 89 | - **R2.4** 链接选项的一个元素按 SPEC-004 §8 读成词,每个词原样到达链接器。插件**禁止**依赖 |
90 | | - 引擎内部的转义拼写(例如 `'$$ORIGIN'`)。(**未实现**,mcpp#703:当前 `ldflags` 与 |
| 90 | + 引擎内部的转义拼写(例如 `'$$ORIGIN'`)。(**已实现**,mcpp#703;此前 `ldflags` 与 |
91 | 91 | `link_flag` 中的 `$` 会被宿主 shell 展开) |
92 | 92 |
|
93 | 93 | ## 3. 施工:action |
|
96 | 96 | 自己发现的输入用 depfile 报告。(argv 与 depfile **已实现**;工具作为输入是作者义务) |
97 | 97 | - **R3.2** action **必须**在提交时命名它的输出文件,因为引擎在规划期确定源集合、指纹与模块 |
98 | 98 | 图。输出文件名在施工前无法得知的工作(安装一个前缀、解开一个 SDK)使用 `prepare` 角色。 |
99 | | - (输出命名 **已实现**;`prepare` **未实现**) |
| 99 | + (**已实现**;`prepare` 随 mcpp#702) |
100 | 100 | - **R3.3** 角色: |
101 | 101 |
|
102 | 102 | | `role` | 输出 | 顺序 | |
|
105 | 105 | | `object` | 加入链接集 | 链接边消费它 | |
106 | 106 | | `artifact` | 新文件,输入是链接产物 | 链接之后 | |
107 | 107 | | `check` | 引擎写的 stamp | 与编译并行;`blocking = true` 时声明包的编译边等待它 | |
108 | | - | `prepare` | 引擎写的 stamp;命令填充它用 `output_dir` 声明的目录,构建按目录引用其内容 | 声明包的每条编译边与链接边等待它 | |
109 | | - |
110 | | - `prepare`(**未实现**,mcpp#702)是施工,不是校验,任何只针对校验的策略都不作用于它。它的 |
111 | | - 产物由配置以目录为单位引用(`include_dir`、`link_search`、`runtime_search_dir`),或以 |
112 | | - `link_flag` 中的完整路径引用;这些名字在配置时确定,内容在施工时到达。一个 `prepare` action |
113 | | - **必须**用 `output_dir` 声明它填充的目录;命令成功而该目录不存在时,引擎不写 stamp,并以 |
114 | | - 指出该目录的消息使这条边失败。 |
| 108 | + | `prepare` | 引擎写的 stamp;命令填充它用 `output_dir` 声明的目录,构建按目录引用其内容 | 声明包的每条编译边与计划中的每条链接边(静态库归档除外)等待它 | |
| 109 | + |
| 110 | + `prepare`(**已实现**,mcpp#702)是施工,不是校验,任何只针对校验的策略都不作用于它;构建 |
| 111 | + 输出以 `PREPARE` 标注它。它的产物由配置以目录为单位引用(`include_dir`、`link_search`、 |
| 112 | + `runtime_search_dir`),或以 `link_flag` 中的完整路径引用;这些名字在配置时确定,内容在施工 |
| 113 | + 时到达。一个 `prepare` action **必须**用 `output_dir` 声明它填充的目录(缺少时引擎拒绝该 |
| 114 | + action);命令成功而该目录不存在,或除该 action 的 stamp 之外不含任何文件时,引擎不写 |
| 115 | + stamp,并以指出该目录的消息使这条边失败。链接边等待所有 `prepare`,因为每个包的链接全局 |
| 116 | + 指令并入整个计划共用的一份链接意图。 |
115 | 117 | - **R3.4** `check` 只用于校验,**禁止**用来表示施工。(作者义务) |
116 | 118 | - **R3.5** `check` 与 `prepare` 的命令成功后,引擎创建或更新它们的 stamp,使 stamp 新于该 |
117 | 119 | action 的每个输入;命令失败时不写 stamp。命令无需自己写 stamp。(创建自 2026.8.29.1 |
118 | | - **已实现**;更新**未实现**,mcpp#702:当前一个已存在的 stamp 不被更新,输入改变一次后该 |
| 120 | + **已实现**;更新 **已实现**,mcpp#702;此前一个已存在的 stamp 不被更新,输入改变一次后该 |
119 | 121 | action 在此后每次构建中都会重新运行) |
120 | | -- **R3.6** 角色**应当**以常量书写(`mcpp::roles::prepare` 等),使不认识该角色的旧引擎在编译 |
121 | | - 构建程序时拒绝它;引擎拒绝未知的角色字符串,并列出可用的角色。(**未实现**,mcpp#702: |
122 | | - 当前引擎把未知的角色字符串当作 `source`) |
| 122 | +- **R3.6** 角色**应当**以常量书写(`mcpp::roles::source`、`check`、`object`、`artifact`、 |
| 123 | + `prepare`),使不认识该角色的旧引擎在编译构建程序时拒绝它;引擎拒绝未知的角色字符串,并列出 |
| 124 | + 五个角色。(**已实现**,mcpp#702;此前引擎把未知的角色字符串当作 `source`) |
123 | 125 | - **R3.7** 构建期**不应**访问网络:下载属于安装期(载荷的安装、依赖的解析)。一个必须在构建期 |
124 | 126 | 下载的 action(例如由包管理器取得源码)**必须**在其说明中写明,并在离线构建中 |
125 | 127 | (`--offline` 或 `MCPP_OFFLINE=1`;前者在进程环境中设置后者,action 继承之)不访问网络: |
|
130 | 132 | - **R4.1** 一个目录中的共享库由施工产生(`prepare`)或文件名不定时,插件**必须**用 |
131 | 133 | `runtime_search_dir` 声明该目录。引擎把它用于 ELF 与 Mach-O 的运行路径(RUNPATH/rpath, |
132 | 134 | 从不作为 `-L`)、`mcpp run` 的加载路径、`mcpp pack` 的闭包搜索与运行时校验,并把依赖包的 |
133 | | - 声明传到消费方的可执行文件。(**未实现**,mcpp#702) |
| 135 | + 声明传到消费方的可执行文件。(**已实现**,mcpp#702) |
134 | 136 | - **R4.2** 一个在配置时已知的文件需要位于程序旁的某个相对位置时(Qt 的平台插件、Vulkan 的 |
135 | 137 | ICD 清单),插件用 `deploy`。(**已实现**,协议 11) |
136 | 138 | - **R4.3** Windows 的可执行文件没有运行路径。`mcpp run` 通过 `PATH` 使用运行时搜索目录, |
137 | 139 | `mcpp pack` 把闭包需要的 DLL 放到程序旁(**已实现**)。链接之后,引擎把程序直接或间接导入的、 |
138 | 140 | 位于其运行时搜索目录中的非系统 DLL 放到程序旁,使从构建目录直接启动的程序同样能找到它们; |
139 | | - 闭包的求解与 `mcpp pack` 相同。(**未实现**,mcpp#702) |
| 141 | + 闭包的求解与 `mcpp pack` 相同,DLL 在其目录中被替换后下一次构建再次放置。(**已实现**, |
| 142 | + mcpp#702) |
140 | 143 | - **R4.4** 插件**禁止**在 `link_flag` 中写运行路径(`-Wl,-rpath,...`),**必须**使用 R4.1。 |
141 | 144 | (作者义务) |
142 | 145 |
|
|
145 | 148 | - **R5.1** 规划运行构建程序,不运行任何 action(SPEC-005 R2.2)。插件遵守 R1.3 时,规划得出 |
146 | 149 | 的配置与构建相同。(**已实现**) |
147 | 150 | - **R5.2** 一个包的构建程序在规划中失败时,该包只按其清单描述,并得到一条错误诊断;成员的 |
148 | | - 其余部分照常描述。插件遵守 R1.2 时,环境不完整不会使构建程序失败。(**未实现**,mcpp#702) |
| 151 | + 其余部分照常描述。插件遵守 R1.2 时,环境不完整不会使构建程序失败。(**已实现**,mcpp#702) |
149 | 152 | - **R5.3** 插件所需的宿主工具在规划中构建失败时,规划继续,构建程序收到该工具将被发布的路径, |
150 | 153 | 并产生一条警告。插件**应当**在 action 中运行宿主工具,而不是在构建程序中运行,使规划不依赖 |
151 | | - 工具能否构建。(引擎部分 **未实现**,mcpp#702;「应当」为作者义务) |
| 154 | + 工具能否构建。(引擎部分 **已实现**,mcpp#702;「应当」为作者义务) |
152 | 155 |
|
153 | 156 | ## 6. 环境与载荷 |
154 | 157 |
|
|
179 | 182 | | 版本 | 日期 | 变更 | |
180 | 183 | |---|---|---| |
181 | 184 | | 0.1 | 2026-09-26 | 首版草案(mcpp#699、#701、#702、#703)。 | |
| 185 | +| 0.2 | 2026-09-26 | 随 mcpp 2026.9.27.1 落地:R1.3 的警告、R2.1 的 `runtime_search_dir`、R2.4、R3.3 的 `prepare`(目录须含文件;链接边等待所有 `prepare`)、R3.5、R3.6、R4.1、R4.3、R5.2、R5.3 标为已实现。 | |
0 commit comments