Add Endor source reader before lexing with provenance and URI provider
Verify databases and deploy Aster VM / verify-and-deploy (push) Successful in 6m53s

This commit is contained in:
2026-10-19 03:23:38 +08:00
parent 4bf889e5b7
commit 483d9d1717
27 changed files with 667 additions and 37 deletions
+6 -3
View File
@@ -1,6 +1,6 @@
# 源码词法与 PEG 语法前端
frontend 包提供手写 Rust lexer 和 rust-peg 生成的 token parser。当前入口为 lex、parse、parse_expression,CLI 提供 parse 文件命令;结果是 AST,还没有 AST 到字节码的编译器、类型检查、名称解析或源码执行。Core 不依赖 frontend 或 peg,仍保持零外部依赖。
frontend 包提供 [Endor 阅读器](reader.md)、手写 Rust lexer 和 rust-peg 生成的 token parser。宿主通过 SourceUnit 调用带来源的词法/语法入口,原有 lex、parse、parse_expression 保留;CLI 提供 parse 文件/stdin 命令;结果是 AST,还没有 AST 到字节码的编译器、类型检查、名称解析或源码执行。Core 不依赖 frontend 或 peg,仍保持零外部依赖。
首版以 Endorphin-Language 设计稿的基础词法、表达式与函数章节为起点,语法可以继续修改;设计稿中的未完成部分不作为阻塞前端实现的前置条件,也不被整体视作已经实现的语言能力。这里维护当前解析契约;源码位置见 [frontend](../../crates/frontend/README.md)。
@@ -14,6 +14,9 @@ grammar.peg 保留 rust-peg 0.8 的 peg::parser! 外层声明,因此是直接
| API | 输入与结果 |
| --- | --- |
| lex_source(&SourceUnit) | 对阅读器输出分词,错误携带来源、修订及行列 |
| parse_source(&SourceUnit) | 对阅读器输出解析基础函数 Program,错误携带来源信息 |
| parse_source_expression(&SourceUnit) | 对阅读器输出解析一个完整表达式,错误携带来源信息 |
| lex(&str) | 产生 Vec<Token>;每个 token 只有种类和原始源码的字节范围,不复制文本 |
| parse(&str) | 解析一个或多个完整函数定义,返回 Program;空输入和未消费的尾部内容报错 |
| parse_expression(&str) | 解析一个完整表达式,不能忽略尾部 token |
@@ -24,7 +27,7 @@ AST 的名称、数字原文和解码后的字符串均由 AST 自己持有,
## 词法规则
- 输入是有效 UTF-8 的 &str。CLI 使用严格的 read_to_string 读文件;其他编码由宿主先显式解码,不修改全局 locale。
- lexer 输入是有效 UTF-8 的 &str。阅读器将字符串、流、文件或宿主 URI provider 的结果转换为不可变 SourceUnit;CLI 通过阅读器严格解码字节。其他编码由宿主先显式解码,不修改全局 locale。
- 名称首字符为下划线或 Rust char::is_alphabetic,后续为下划线或 char::is_alphanumeric。这是当前明确采用的分类,不承诺 XID/NFKC 规则;没有自动规范化。中文、日文可用于名称,emoji 可以用于字符串。
- 名称统一产生 Name token。function、let、return 只在相应语法位置按拼写识别,不预先固定全局保留字表;class、agent 等也仍可作为名称。
- 数字为 ASCII 十进制数字,可带两边都有数字的小数部分;原文保留,不转换为 f64。负号单独分词;科学计数法、数字后缀、下划线分隔、前导正号、.5 和 1. 形式不在当前表达式语法中。
@@ -59,6 +62,6 @@ use、namespace、class、agent、完整类型语法、条件/循环、比较
词法和语法错误分别标记为 Lexical/Syntax。语法错误将 PEG 的 token 下标转换成原始源码 Span,保留期望项目列表;EOF 错误使用 source.len() 处的空区间。Diagnostic::location 返回一基行列,列按 Unicode 标量计数,CRLF 只算一次换行,不按字节列或字形簇计数。
`cli parse <file>` 成功时输出 Rust Debug 格式的 AST,失败时在 stderr 输出文件/行/列和诊断并返回非零退出码。AST Debug 文本不是稳定的序列化协议。命令不执行源码、不初始化 VM、不连接数据库;具体运行与本地禁测约定见 [运行](../operations/README.md) 和 [验证](../operations/validation.md)。
`cli parse <file>` 与 `cli parse -` 成功时输出 Rust Debug 格式的 AST,失败时在 stderr 输出来源/行/列和诊断并返回非零退出码;`-` 表示从 stdin 读到 EOF,不是 REPL。阅读与来源包装规则见 [阅读器](reader.md)。AST Debug 文本不是稳定的序列化协议。命令不执行源码、不初始化 VM、不连接数据库;具体运行与本地禁测约定见 [运行](../operations/README.md) 和 [验证](../operations/validation.md)。
后续编译器应将 AST 经名称/闭包分析转换为现有字节码,不另设 AST 求值器;解析成功不表示表达式已有运行语义。VM 虽已支持 MakeFunction,但从源码创建函数仍需要编译器接入。解析器也不是不可信代码沙箱,当前没有通用输入大小或解析递归深度限额。