443b22bdf17a6d2b4dbae6d8f6e261c4371b874b
AST(29): +AST_LIST_COMP, parser 解析 [for var in expr: body] sema: 创建子作用域注册循环变量, codegen: for 循环绑定+填充结果数组 已知限制: 仅支持 2 元素及以下数组 (大数组 alloca 对齐问题待修) Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
L Language
用 C17 实现的静态类型编译型编程语言
简介
L Language 是一门学习型编译语言,手写词法分析、递归下降 + Pratt 解析、语义分析和 LLVM IR 代码生成,最终生成原生可执行文件。语法博采众长(Rust/Swift/Elixir),拥有管道、字符串插值、命名参数等独有特性。
📖 语言参考手册 — 完整的语法、类型、示例教程
fn double(x: i64) -> i64 {
return x * 2;
}
fn main() -> i64 {
let name = "L";
print_str("Hello, \(name)!"); // 字符串插值
let result = 10 |> double() |> double(); // 管道
print_i64(result); // 40
return 0;
}
架构
源码(.l) → 词法分析(Token) → 语法分析(AST) → 语义分析(类型标注) → LLVM IR → 可执行文件
graph TB
subgraph 前端["编译器前端"]
Lexer[词法分析器<br/>手写状态机<br/>55+ 种 Token]
Parser[语法分析器<br/>递归下降 + Pratt<br/>25 种 AST 节点]
Sema[语义分析器<br/>作用域链 + 类型推断<br/>类型检查 + 错误收集]
end
subgraph 后端["编译器后端"]
Codegen[LLVM IR 生成<br/>AST → LLVM-C API<br/>内建 print 函数]
Link[链接器<br/>clang/lld<br/>生成 .exe]
end
subgraph 运行时["运行时支持"]
Builtins[内建函数<br/>print_i64 / print_f64<br/>print_bool → printf]
end
Source[源码 .l] --> Lexer
Lexer --> Parser
Parser --> Sema
Sema --> Codegen
Codegen --> Link
Link --> Exe[可执行文件 .exe]
Builtins -.-> Codegen
模块职责
| 模块 | 输入 | 输出 | 核心结构 |
|---|---|---|---|
lexer/ |
char* 源码 |
Token[] |
Token {kind, start, length, line, col} |
parser/ |
Token[] |
AstNode* |
25 种节点 (Program..MethodCall) |
ast/ |
— | 工厂函数 | AstNode {kind, type, as{union}} |
sema/ |
AstNode* |
类型标注 | Scope 作用域链 + Symbol 符号表 |
codegen/ |
AstNode* |
LLVMModuleRef |
CgCtx {module, builder, var_table} |
driver/ |
命令行参数 | exit code | 流水线串联 + 错误报告 |
功能 (v0.6)
类型系统
| 类型 | 语法 | 示例 |
|---|---|---|
| 32 位有符号整数 | i32 |
100 |
| 64 位有符号整数 | i64 |
42, -7 |
| 64 位无符号整数 | u64 |
999 |
| 64 位浮点数 | f64 |
3.14 |
| 布尔值 | bool |
true, false |
| 字符 | char |
'A' |
| 字符串 | str |
"hello" |
| 结构体 | struct |
Point { x: i64, y: i64 } |
| 枚举 | enum |
Color { Red, Green, Blue } |
| 数组 | T[N] |
i64[10] |
| 无返回值 | void |
函数默认 |
| 类型别名 | type |
type Meters = i64; |
let不可变 +var可变,类型推断i32→i64→f64自动加宽,char可隐式转为整数
控制流
if/else/else ifwhile循环for i in 0 to 10(去糖为 while)match expr { pat => { ... } _ => { ... } }(去糖为 if-else)guard x >= 0 else { return -1; }(去糖为 if-else)return
函数 & 方法
- 多参数、递归、struct 参数/返回值
- 返回类型校验
extend StructName { fn method(self: Type) -> Ret { ... } }instance.method(args)调用- 命名参数:
draw_rect(width: 10, height: 20)任意顺序传参 - 管道
|>:10 |> double() |> add(5)数据流从左到右 - 内建函数:
print_i64,print_f64,print_bool,print_str
运算符 & 语法糖
+ - * / % == != < > <= >= && || ! += -= *= /= |> str + str
- 字符串插值:
"Hello, \(name)!"→"Hello, " + name + "!"
内存管理
- str 拼接 malloc → 作用域退出自动 free (RAII)
- struct/array 栈上值类型
安装
依赖
- GCC 15.x (MinGW-w64)
- CMake ≥ 3.20
- LLVM 22.x(C API 库 + 头文件)
从源码构建
git clone git@lhy-git.liuhangyv.top:Serendipity/l-language.git
cd l-language
mkdir build && cd build
cmake .. -G "MinGW Makefiles" -DCMAKE_PREFIX_PATH="D:/settings/Language/LLVM"
mingw32-make -j4
生成 l_lang.exe。
安装包(Windows)
下载 L-Language-x.x.x-setup.exe,双击安装。包含编译器、LLVM 运行时和 8 个示例程序,无需额外安装 GCC 或 LLVM。
安装包构建:
cd scripts && build_installer.bat
需要 NSIS 3.x。
使用
# 编译并运行
./l_lang.exe example.l -o example.exe
./example.exe
# 查看生成的 LLVM IR
./l_lang.exe example.l --emit-ir
开发
# 构建
cd build && mingw32-make -j4
# 运行全部测试 (158 单元 + 29 集成)
./l_lang_lexer_test.exe # 词法分析 (41 tests)
./l_lang_test.exe # 语法分析 (15 tests)
./l_lang_sema_test.exe # 语义分析 (74 tests)
./l_lang_codegen_test.exe # 代码生成 (28 tests)
# 集成测试
for f in ../test/programs/*.l; do
./l_lang.exe "$f" -o out.exe && ./out.exe
done
技术栈
| 层 | 技术 |
|---|---|
| 实现语言 | C17 (GCC 15.x) |
| 构建系统 | CMake 3.20+ |
| IR 后端 | LLVM 22.1.7 C API |
| 链接器 | clang / lld |
| 内存管理 | Arena bump allocator |
| 测试框架 | 手写断言宏 (ASSERT / TEST_RUN / test_summary) |
项目结构
include/l_lang.h # 公共类型定义 (TypeKind, 向前声明)
src/
├── lexer/ # 词法分析器
│ ├── token.h/c # Token 类型 + 工具函数
│ └── lexer.h/c # 状态机 lex()
├── parser/
│ └── parser.h/c # Pratt 表达式 + 递归下降 parse()
├── ast/
│ └── ast.h/c # 14 种节点定义 + 创建函数
├── sema/
│ ├── symbol.h/c # 作用域链 (查/插)
│ └── sema.h/c # 类型推断 + 检查 sema_analyze()
├── codegen/
│ └── codegen.h/c # AST → LLVM IR codegen_module()
├── driver/
│ ├── main.c # 入口 + 命令行 + 流水线串联
│ └── error.h/c # 错误报告 (ErrorInfo / ErrorList)
└── util/
└── arena.h/c # Bump allocator (8MB)
test/
├── test_utils.h # 断言宏
├── test_lexer.c # 词法测试 (41 tests)
├── test_parser.c # 语法测试 (15 tests)
├── test_sema.c # 语义测试 (9 tests)
└── programs/ # 集成测试 (.l 源文件)
docs/
├── PRD.md # 产品需求文档
└── superpowers/plans/ # 实现计划
错误处理
| 阶段 | 策略 |
|---|---|
| 词法分析 | 首个非法字符即终止,报告 文件名:行:列: 错误信息 |
| 语法分析 | 首个语法错误即终止,报告期望 vs 实际 |
| 语义分析 | 收集所有类型错误后批量输出,红色 ANSI 高亮 |
| IR 生成 | LLVMVerifyModule 验证失败 → 输出 LLVM 诊断 |
| 链接 | system() 返回值检查,失败时打印 exit code |
贡献
欢迎提交 Issue 和 Pull Request。
本地开发环境
- GCC 14.x+ (MinGW-w64)
- CMake 3.20+
- LLVM 22.x(需要 C API 库和头文件)
代码规范
- C17 标准,
-Wall -Wextra -g零警告 - 注释用中文
- Arena 内存池贯穿全流水线,不在局部函数内 malloc
- 错误信息格式:
文件名:行:列: 描述 - 提交格式:
<类型>: <描述>(feat/fix/refactor/docs/test/chore)
版本号升级清单
版本号需在 3 个地方 手动修改:
| 文件 | 字段 | 说明 |
|---|---|---|
CMakeLists.txt |
VERSION 变量 |
CMake project() |
README.md |
badges | 文档徽章 |
CHANGELOG.md |
版本标题 | 变更日志 |
许可证
MIT License
作者
刘航宇 — 河南理工大学人工智能协会
Releases
2
L Language v0.8.0
Latest
Languages
C
93.3%
Lex
2.5%
NSIS
1.6%
Common Lisp
1.2%
CMake
1.1%
Other
0.2%