技术文章 Phil Eaton - databases
本篇文章是“用 Go 从零写 SQL 数据库”系列的第一篇,目标是实现支持基本的 CREATE、INSERT、SELECT 命令和交互式 REPL 的最小数据库。作者从词法分析入手,设计 lexer 将输入转换为 token,依据 PostgreSQL 规则处理数字、字符串和标识符,并用 longestMatch 解决关键词前缀冲突;然后定义 AST 模型与递归下降解析器,分别解析三种语句。最后实现内存后端,用 map 存储表,以二进制表示 INT、字节串表示 TEXT,完成建表、插入和查询功能。文章给出完整代码与运行示例,并附测试,边界明确:仅支持单表基础操作,无持久化、事务和复杂表达式,适合初学者理解数据库与解析原理。
推荐收录,因为文章以可运行的 Go 代码完整展示了一个最小 SQL 数据库的词法分析、语法分析和内存执行流程,技术细节具体、步骤清晰,并配有测试样例与后续系列链接。适合想了解数据库内部机制、解析器实现或 Go 语言实践的中级读者,文中的 lexer/parser 组织方式和内存存储结构可直接迁移到其他小型解释器或教学项目。
技术文章 Phil Eaton - databases
本文是《Writing a SQL database from scratch in Go》系列第二篇,在首篇基础上为 gosql 增加二进制表达式与 WHERE 过滤。作者扩展 AST 加入 binaryExpression,采用 Pratt parsing 处理运算符优先级和括号;重构内存后端,让每个表达式针对表行求值。求值器支持标识符、数字/字符串/布尔字面量以及算术、比较、逻辑等运算符,并明确不进行隐式类型转换。SELECT 语句新增 WHERE 条件逐行过滤,投影列可通过表达式计算,文中给出 REPL 交互示例。该实现目前只支持单表、简单运算符,并依赖内存存储,是教学性质的 SQL 引擎骨架,尚未涉及索引、连接等真实数据库特性。
推荐收录,因为文章完整展示了在 Go 中实现 SQL 解析与求值的过程,包含 Pratt 解析器、AST 设计、表达式求值和内存表数据流,且代码与解释同步。适合对数据库内核、编译原理或解释器实现感兴趣的读者,可作为手写 SQL 引擎的参考起点。其可迁移价值在于解析器优先级处理和行上下文求值框架可复用于其他小型语言或查询引擎,但需注意示例省略了类型强制转换、优化和持久化等生产特性。
技术文章 Phil Eaton - databases
本文记录作者在 Go 实现的 SQL 数据库 gosql 中添加 LIMIT 和 OFFSET 支持的过程。作者首先更新词法分析器以识别两个新关键字,然后扩展 AST 结构并调整生成代码的辅助函数,使打印结果包含 LIMIT 和 OFFSET。接着,解析器在 SELECT 语句中识别这些子句并解析其后的表达式,同时将 LIMIT 和 OFFSET 作为 WHERE 表达式的边界分隔符。运行时内存后端会先计算 limit 和 offset 数值,然后在逐行过滤中跳过 offset 之前的行,并在超出 limit+offset 范围后停止。文章特别指出,LIMIT/OFFSET 仍需要扫描至少 offset 数量的行,不适合大数据集分页,应优先考虑基于索引的分页。该实现仅针对内存存储,未涉及其他后端或优化策略。
推荐收录,本文不是零散片段,而是完整展示了为 SQL 引擎添加 LIMIT/OFFSET 语法所需的词法、语法分析和运行时三个层次改动,并附有代码 diff 与运行验证。适合对数据库实现、编译前端或 Go 语言工程感兴趣的读者,其修改顺序和边界意识可迁移到类似扩展场景。风险是实现针对特定内存后端,未深入讨论一般化架构,但作为参考案例足够。
技术文章 知乎 - 严格鸽 2026/08/13
文章通过C++代码示例展示抽象并非零成本:直接使用 std::vector<int>& 参数时,由于LLVM IR带有nonnull、readonly、dereferenceable等属性,编译器能提取data指针并生成SIMD向量化代码;但将其封装为View类后,这些属性丢失,且&&短路求值使编译器不敢提前解引用,导致无法优化。作者通过调整&&顺序或显式添加size陷阱检查恢复了优化,说明问题在于抽象包装丢失编译期信息。文章还提到Rust存在类似现象,并已提交LLVM issue。结论指出编译器优化有边界,但通常仍优于手动优化,适用于关注性能与编译器的C++开发者。
推荐收录,因为它以具体代码和Godbolt汇编对比揭示了C++抽象导致的编译期信息丢失和向量化失败,并给出了可复现的解决方案。适合关注性能优化、编译器行为或C++抽象设计的读者,可迁移价值在于理解编译器元数据如何影响优化,以及如何通过调整代码顺序或添加断言恢复优化。
工程实践 Max Bernstein 2026/08/13
本文介绍了一种在编译器中间表示(IR)中实现 canonicalize 传递的方法,用于通过类型保护重写合并冗余的 GuardType 指令。作者首先描述了一个块局部的版本,该版本在每个基本块内重映射操作数,使后续的常量折叠能消除多余的检查。随后,作者基于支配树实现了全局版本,通过在支配树中沿支配者向下级联重写来扩大优化范围,并讨论了慢速但易于验证的实现策略。文章进一步扩展该传递,当块是条件分支的目标时,在 rewrite_map 中预先填入条件变量的真假常量,使分支体得以了解其条件值,从而简化 30k_ifelse 等基准中的分支链。作者还提到该传递可能需要常量驻留来保证幂等性,并说明了其依赖 SSA 最小化传递的效果。文章以具体代码和 PR 为证据,展示了编译器优化开发中的工程取舍与实证验证。
推荐收录,因为文章详细记录了一个现实编译器中的优化实现过程,既有算法伪代码,又有对支配树、SSA 形式、常量驻留等底层概念的透彻解释。编译器开发者或编程语言研究者可以从中学习如何设计传递以利用支配关系传播类型信息,以及如何在正确性和性能之间做工程取舍。文中所探讨的块局部与全局重写级联技术,以及条件分支信息播种方法,均具有较强的可迁移性。
技术文章 Niko Matsakis 2026/08/10
文章由 Rust 语言核心设计者 Niko Matsakis 撰写,介绍 Rust trait 系统中长期存在的循环 trait 实现问题。作者从动机出发,区分了“内部证明”与“外部证明”两种概念,并通过贴近真实 Rust 的例子说明循环 trait 如何影响语言的一致性与表达能力。作为系列博文的开篇,它旨在为后续深入的技术探索和可能的 RFC 设计铺路,重在建立问题背景和抽象模型,而不是给出实现方案。
收录推荐。作者是 Rust 语言设计的权威,对循环 trait 的解析具有长久参考价值,尤其适合语言设计者、编译器开发者以及希望理解 trait 系统深层次约束的 Rust 用户。文中提出的“内部/外部证明”视角为思考类型系统中的循环依赖提供了可迁移的思维框架,有助于理解类似语言特性的设计取舍。
技术文章 Daniel Lemire 2026/08/09
文章介绍了 Go 语言的 Profile-guided optimization (PGO) 原理与使用方法。作者解释了编译器在缺乏运行时信息时依赖启发式做优化决策,而 PGO 通过收集 CPU profile 让编译器了解热路径,从而更激进地内联热函数和去虚拟化接口调用。文中通过三个 JSON 文档的解析基准测试,展示了 PGO 可带来 2–4% 的吞吐量提升,但效果因训练数据与工作负载匹配程度而异,甚至可能出现略微性能回退。作者指出 Go 的 PGO 优化幅度有限但成本近乎为零,适合在发行版构建中默认启用。整体内容提供了可操作的实践指南和定量参考,但仅覆盖单个简单解析场景,未涉及更复杂的工作负载或 profile 采样策略。
本文以清晰的步骤和实际数据展示了 Go PGO 的用法与效果,避免了纯理论描述,为需要优化 Go 程序性能的开发者提供了可直接尝试的方法和预期参考。实验规模虽小,但结论谨慎,强调了 workload 匹配的重要性,可迁移到其他 Go 项目的构建流水线中。适合关注编译器优化、性能工程和 Go 工具链的读者。
技术文章 MaskRay 2026/08/09
文章深入解析LLVM分支概率信息(BranchProbabilityInfo)在没有PGO(Profile-Guided Optimization)资料时的静态估计机制。作者首先梳理了LLVM估算分支概率的多级回退流程,重点剖析了calcEstimatedHeuristics算法,该算法利用不可达、noreturn、cold等区块的种子权重,通过支配树和后支配树反向传播,并结合循环结构对出口边进行缩放,从而为多后继终结指令分配概率。文中给出了独立的C++实现,并详细讨论了权重标度、边分类、循环嵌套森林的作用,以及不可归约循环对概率计算的影响。此外,还指出了与LLVM源码bit-per-bit匹配所需注意的实现细节,如种子顺序和工作列表顺序。该方法展示了静态分析中如何仅凭控制流图和循环结构生成合理分支猜测,对理解编译器优化有重要参考价值。
本文为编译器开发者、程序分析研究人员或对底层代码优化感兴趣的人员提供了LLVM分支概率静态估计的深入技术剖析,不仅解释了算法原理、设计取舍和工程考量,还附带可复现代码和对比案例。其详细程度足以帮助读者迁移到其他编译系统或静态分析工具的开发中,适合作为长期技术参考资料收录。
科研思考 Stanford Hazy Research 2026/08/05
文章深入探讨了AI代理(agents)对传统软件抽象层的冲击。作者以自身经历对比:去年编写megakernel需要构建C++抽象层来管理复杂度,今年借助代理可直接从模糊提示生成目标优化代码,消解了对抽象层的依赖。由此提出CUDA DSL等抽象层正走向退休的观点,认为当智能执行器能填补意图中的缺口时,精密但脆弱的代码库可能不再是唯一的知识载体。同时指出抽象层不仅是认知卸载工具,也是共享接口和测试复用的基础,消除后会带来验证挑战。文章最终强调,虽然抽象可能过时,但领域知识、不变量和测试等核心思想将保留,知识传递的方式则从代码转向提示和神谕。全文适用于对AI辅助编程、编译器设计和软件演化感兴趣的读者,但结论基于作者深厚的领域经验,对初学者和不明确神谕的领域可能不直接适用。
收录理由:文章提出了一个前沿且深刻的工程哲学命题,将AI代理与编译器抽象、代码库价值等经典概念结合,提供了可迁移的思考框架。适合关注AI如何影响系统软件开发、编程语言设计和工程实践的读者,对重新评估抽象层和代码资产具有启发性。
工程实践 Fzakaria Blog 2026/08/01
文章介绍了一个在 Bazel 中从 357 字节的 hex0 种子自举构建的 C++ 工具链。作者受 stage0 和发行版自举过程启发,利用 LLM 协助完成了这一机械但步骤繁多的工程,最终工具链能够无补丁编译 Bazel Central Registry 中的 Abseil 和 GoogleTest,并通过 236 项测试。工具链包含审计报告,利用 Bazel aspect 验证构建图中每个动作仅执行工具链自产的程序,确保了极高的封闭性。当前方案仍需系统提供的 shell,但显著提升了 Bazel 构建的可重现性,适用于对构建可信性、可移植性有要求的 C/C++ 项目。
推荐收录,因为它将一个很有挑战性的自举工具链工程在 Bazel 体系中完整实现,并用实际测试和审计报告证明了可行性。这对于关注构建可重现性、供应链安全以及工具链定制的工程师具有直接的参考价值,文中的自举流程和封闭性验证方法可直接迁移至类似基础设施建设项目。
技术文章 LWN.net 2026/07/29
文章报道了 Alan Maguire 在 LSFMM+BPF 2026 峰会上关于在内核 BTF 调试信息中支持内联函数的提案。当前 BPF 程序通过 BTF 定位内核函数进行跟踪,但内联函数因无固定地址而无法被追踪。Maguire 建议扩展 BTF 格式以编码内联函数信息,如源代码位置和调用链,从而使跟踪工具能解析并附着探针。该方案需在 BTF 大小、复杂性和调试完整性之间权衡,并依赖编译器生成所需信息。这有助于提升 BPF 可观测性,但可能增加内核二进制体积,并需社区对格式变更达成共识。
推荐收录,因为它介绍了内核社区为解决 BPF 跟踪内联函数难题而提出的 BTF 扩展方案,涵盖了从问题、技术机制到潜在取舍的完整讨论。对从事内核调试、可观测性及 BPF 工具开发的读者,本文提供了关于跟踪信息格式设计及其工程权衡的一手参考,有助于理解内核调试基础设施的演进方向。
技术文章 LWN.net 2026/07/28
文章介绍了gccrs项目在2026年上半年以编译Linux内核为目标所取得的进展。通过针对内核crate进行测试,开发团队在属性处理、名称解析和资源管理等领域发现并修复了多个问题,显著提升了生成正确代码的能力。尽管目前编译器仅能处理简单的独立程序,但项目报告显示未来数月有望快速改善。文章基于项目周报和月报,呈现了编译器前端开发中遇到的具体技术挑战和解决过程。
推荐收录,因为它详细记录了将Rust前端集成到GCC中的工程实践,特别是针对Linux内核编译的具体适配工作和问题解决。这些内容对编译器开发者、Rust for Linux贡献者以及关注系统工具链进展的读者具有直接的参考价值,其中属性处理、名称解析等问题的解决思路可迁移至类似项目。
技术文章 Max Bernstein 2026/07/28
文章详细介绍了 Ruby 的 ZJIT 编译器中内联器(inliner)如何通过方法内联优化块(block)调用,从而提升性能。作者首先回顾了 Ruby 解释器中块的工作机制,随后解释 JIT 编译器如何通过类型特化来优化方法调用,并指出核心库方法(如 Array#each)因多态块调用导致优化困难。ZJIT 采用将 callee 的代码内联到 caller 中的方式,利用调用上下文将动态的 invokeblock 转换为直接的块调用和循环,消除了间接调用开销。文章展示了内联前后 HIR 的变化与微基准测试结果(如 cfunc_itself 达到 35 倍加速),并说明当前块内联尚未完全实现,内联阈值等参数仍在调优。适合对编译器设计、JIT 优化和 Ruby 运行时性能感兴趣的读者。
本文深入剖析了 ZJIT 内联器的设计动机、实现细节和实际收益,通过具体示例和基准数据展示了如何解决动态语言中块调用的优化难题。它对编译器开发者、语言虚拟机工程师和关注 Ruby 高性能优化的从业者具有直接的参考价值,其中基于调用上下文的代码重组思路也可迁移到其他 JIT 系统。
技术文章 Fzakaria Blog 2026/07/27
文章深入分析 x86-64 大代码模型(-mcmodel=large)在处理线程局部存储(TLS)时的根本性缺陷。作者通过构造超过 2 GiB 的 .bss 和 .text 示例,对比普通数据访问与 TLS 访问的编译器重定位类型,指出尽管大代码模型为普通数据生成了 64 位重定位,但 TLS 访问序列仍使用 32 位立即数(如 R_X86_64_TPOFF32),导致二进制文件超出 2 GiB 时链接失败。进一步剖析 GCC 与 LLVM 生成的指令序列,揭示问题并非编译器实现缺陷,而是 x86-64 psABI 从未定义大代码模型下的 TLS 访问模式,使得 64 位 TLS 偏移无法编码到指令中。文章提供了可复用的 Python 脚本用于生成巨型目标文件,验证了现象的通用性,并指出该限制对有大量线程局部变量的静态链接可执行文件尤为严重。
本文并非泛泛而谈,而是通过可复现的构造实验和汇编级分析,定位到 x86-64 ABI 规范的一项具体缺失,揭示了大型二进制工程中的一个隐蔽陷阱。其直接证据清晰、方法可迁移,适合从事工具链、系统软件或性能敏感大型应用开发的读者参考。文章还提供了生成测试用例的脚本,有助于读者在自己的环境中验证和延伸研究,具备长期的参考价值。
技术文章 Mitchell Hashimoto 2026/07/22
文章倡导所有开发者了解 SIMD(单指令多数据流)并破除其过于复杂的迷思。作者以 Zig 语言为例,展示了一套通用的五步模式来将标量循环向量化:广播常量、按向量宽度迭代、执行向量操作、归约向量结果、处理标量尾部。通过终端模拟器 Ghostty 中查找控制字符的真实案例,详细解释了每步的实现细节和寄存器位运算。文章还讨论了编译器自动向量化的局限性,强调手动编写 SIMD 可以在可预测的情况下获得显著性能提升,同时指出该方法主要适用于大量连续数据的处理场景,对于复杂算法则需更高技巧。整体内容清晰、可迁移,降低了 SIMD 的入门门槛。
本文以易懂的案例和通用模板系统讲解了 SIMD 的基本模式,适合希望提升循环密集型代码性能的软件开发者。其提出的五步法具有高度的可迁移性,能帮助读者跨语言理解向量化思维,避免过度依赖容易失效的编译器自动向量化。对于日常优化中处理扫描、比较、计数等任务的工程师,本文是一份低门槛、高回报的入门参考。
技术文章 MaskRay 2026/07/12
文章聚焦于编译器和程序分析中的不可约循环(irreducible loops)问题,首先回顾了支配树和自然循环在可约控制流图上的局限性,指出在优化后的机器码及反编译输出中常见的多入口循环无法被基于支配关系的方法识别。随后详细介绍了韦韬等人在SAS 2007提出的单趟DFS算法,该算法无需支配树或UNION-FIND,通过将遍历中遇到的每条边分为五种情况,并结合“头部链”合并机制,在一次深度优先搜索中同时完成循环识别与头部标记。文章提供了完整的C++实现,并借助不可约核心图和嵌套结构示例验证了算法输出Havlak最细化循环嵌套森林,同时展示了可约情况下与自然循环的一致性。该算法的时间复杂度为O(N+k*E),其中k为衡量非结构化程度的系数,在实际代码中接近线性。文章也指出了算法对DFS顺序的依赖以及不可约循环头的不唯一性。
推荐收录,本文不是简单的算法复述,而是从理论缺陷出发,逐步引出单趟DFS解决方案,并配有清晰图示、完整代码和可运行示例。它对编译器工程、程序分析和反编译领域的读者具有直接的参考意义,能够帮助他们理解如何处理非结构化控制流,并将这套轻量级循环识别方法迁移到自己的静态分析工具中。
技术文章 Random Oracle 2026/06/30
文章延续 QCC(Quining C Compiler)的话题,讨论如何把“单文件 C 程序变成 quine”的能力扩展到多程序循环。作者先构造一个基础链路:C 程序生成 Python 程序,Python 再打印出 C 源码,并说明关键前提是把任意字符串稳定转成可执行的目标语言程序,尤其要处理引号、换行和 Unicode 等转义问题。随后文章展示如何把链路继续扩展到 Rust,并指出理论上可继续叠加更多语言,但会受到行长与转义开销的限制。进一步地,作者把目标从“只会打印源码的程序”推广到保留原有业务功能的程序对,通过预处理宏或运行时文本切片从合并源码中裁出 A/B 两个版本,使它们既能执行原功能,也能按条件输出对方源码。文章最后总结这种构造可推广到多个程序,形成任意两两可达的完整图,但也坦承预处理方案会带来大量死代码,运行时裁剪会更干净。
推荐收录,因为文章给出了从单个 quine 到多程序 quine loop 的明确构造路径,包含字符串转目标语言程序、源码拼接、条件编译和可扩展性限制等直接证据。适合关注编程语言、自指程序、源到源转换和编译技术的读者,且其中关于宏裁剪与运行时裁剪的权衡具有可迁移价值。
技术文章 知乎 - 严格鸽 2026/06/20
文章围绕 C++ 中的内存别名与严格别名规则展开,用多个汇编对比例子说明编译器为何会基于类型系统做激进优化,以及这种优化为什么会让看似“合理”的强转代码在 UB 场景下产生反直觉结果。作者进一步比较了 Fortran、Java、Rust 在别名约束上的差异,并结合 `__restrict`、`char`/`uint8_t`、`vector` 内部布局等例子,说明别名问题如何直接影响性能优化、接口设计和工程实践。文章的结论是:别名分析能带来显著性能收益,但在 C++ 中必须严格遵守语言规则,否则优化会把“直觉正确”变成“语义错误”,因此高性能代码需要更谨慎的类型设计和显式约束。
推荐收录,因为它不是泛泛讲“别名会影响优化”,而是通过具体汇编和跨语言对比把编译器推理、UB 边界和性能收益讲清楚了。对写 C++、做底层性能优化或设计高性能数据结构的读者,这篇文章有很强的可迁移价值。
技术文章 Max Bernstein 2026/06/03
这篇文章系统梳理了动态语言 JIT 和多种编译器中的内联启发式,重点讨论“何时内联”比“如何内联”更难。作者从代码体积、编译时延迟、缓存压力、递归、调用深度、调用频率、调用上下文和 profile 传播等维度,比较了 Cinder、PyPy、V8、JavaScriptCore、SpiderMonkey、HotSpot、.NET、Dart、ART、HHVM 等实现差异,并补充了机器学习、部分内联和 AOT 信息辅助等研究方向。文章的结论是:内联本质上是一个全局收益与局部预算之间的权衡问题,启发式设计必须结合目标运行时、可观测性和分层编译策略。
推荐收录,因为它不是泛泛而谈“内联能提速”,而是把多个真实编译器/JIT 的决策规则、预算约束和调用上下文处理方式放在一起比较,长期参考价值很高。对做编译器、语言运行时或性能优化的读者来说,这篇文章能直接提供可迁移的启发式设计框架和调参视角。
技术文章 Max Bernstein 2026/06/01
这篇文章记录了作者如何用 Z3 验证一段 JIT 生成的分支less 汇编条件,目标是证明 `FIXNUM_MIN / -1` 这一溢出特殊情况的判定与原始 C 逻辑等价。文章不仅说明了 Ruby fixnum 在二进制补码下的边界行为,还展示了如何把等价性证明转成“寻找反例”的 SMT 问题,并通过故意改错常量来验证脚本确实能抓到反例。
推荐收录,因为它把一个很具体的编译/JIT 边界 bug,抽象成了可复用的形式化验证流程,适合做低层代码正确性检查的参考。对做编译器、JIT、运行时或底层位运算逻辑的读者来说,这种“用 Z3 证明等价性”的方法具有很强的迁移价值。
技术文章 Max Bernstein 2026/05/12
文章围绕编译器中的 static single information form(SSI)展开,重点讨论“partial SSI”这一更轻量的实现路径:不必完整实现复杂的 into-SSI / out-of-SSI 算法,而是可以在 SSA 构建阶段、或借助优化阶段已有的支配式重写机制,逐步插入和消除类型细化节点。作者用动态语言 JIT 的例子说明如何根据分支条件、guard 和对象形态推导更精确的类型信息,并进一步利用这些信息消除冗余操作、提升优化效果。
推荐收录,因为它不是泛泛介绍 SSA/SSI,而是把抽象的中间表示理论落到可实现的编译器工程路径上,清楚说明了如何以较低复杂度获得可用的类型细化能力。文章还讨论了适用边界、与完整 SSI 的差异以及 JIT/动态语言场景中的实现权衡,对编译器和运行时开发者都有长期参考价值。
技术文章 Eli Bendersky 2026/04/30
文章围绕“WebAssembly 是否算堆栈机”展开,作者认为这更多是术语争论:WASM 虽然主要通过栈完成运算,但同时提供了 locals,使其不像纯粹只能靠栈交换操作(如 dup、swap)的语言那样受限。作者用 Forth 中依赖大量 tuck/swap 的写法作对比,说明在复杂数据流下,WASM 通过命名局部变量能显著提升可读性。接着给出一个 add_to_byte 示例,比较折叠写法与线性写法,强调栈只是中间执行模型,程序员无需手工管理所有压栈出栈顺序。文章进一步通过 wasmtime 生成的 x86-64 代码说明,编译器会把重复读取同一 local 优化掉,最终代码与手写 C/汇编几乎一致。作者最后指出,WASM 对 locals 的不可别名性质让重复加载消除更容易成立,但这些结论仍依赖于没有对同一 local 的中途写入这一前提。
推荐收录,因为文章直接给出了 WASM 栈语义、locals 设计和编译后机器码的对应关系,并用真实反汇编证明了“多次读取 local 不会带来性能损失”。适合关注编程语言实现、虚拟机设计和编译优化的读者,具有较强的可迁移分析价值。
技术文章 Max Bernstein 2026/04/04
本文系统讲解了编译器中的 value numbering:先从 SSA 中“同形表达式是否可复用”的问题切入,说明它如何用于公共子表达式消除,并区分纯操作与带副作用操作。作者给出局部 value numbering 的实现思路:用哈希表为指令建立值号,遇到已存在的等价指令就用 union-find/Assign 形式替换,从而在单个基本块内消除重复计算。随后文章把问题推进到全局 value numbering,重点解释了为何必须借助支配关系而不是简单按块遍历,以及在分支、汇合和循环中 phi 节点为何需要特殊处理。文章还讨论了内存相关指令的失效与转发,例如 Load/Store forwarding、跨块的 kill set 管理,并对 Maxine、ART、V8、HotSpot 等实现做了对照。最后作者补充了统一哈希表、value partitioning、scoped hash map、JIT 场景中的强度削弱等相关方向,指出该方法对重复纯表达式很有效,但处理副作用和循环时需要额外的可用性与失效管理。
推荐收录:文章明确覆盖了 value numbering、SSA、dominators、phi 处理、内存失效与 load/store forwarding 等关键机制,并给出 Maxine 等真实实现片段作为直接证据。适合编译器、JIT 和程序优化读者参考,迁移价值在于可直接借鉴其“哈希表+支配关系+失效管理”的分析框架;主要边界是它对复杂内存建模与循环优化仍是概述性质。
工程实践 Max Bernstein 2026/03/27
文章围绕 Ruby JIT 实现 ZJIT 如何借助 Perfetto 做性能诊断展开,核心目标是把“侧退出栈计数”这类静态统计,升级为能看时间分布、调用栈和热点聚集位置的可视化追踪。作者先说明仅靠 --zjit-stats 只能知道退出原因数量,却难以定位它们发生在哪些 Ruby 方法中、集中在启动期还是稳态阶段,因此需要引入 trace。随后通过 Perfetto 的时间线和 SQL 接口,把 slice 与 args 表关联起来统计退出原因和顶层方法,直接找到了 ActiveRecord 相关的 shape/type guard miss 热点。实现部分展示了如何导出 trace、为何 JSON 格式会膨胀到 8GB,以及改用更紧凑的 FXT 二进制格式和采样后将体积降到约 100MB。文章也提到还可以继续追踪编译阶段、代码大小、失效、分配和 GC 等事件,但当前结论依赖采样与单次基准,适合做定位和直觉建立,不适合替代完整性能评测。
文章给出了从计数器到可视化 trace 的完整落地路径,并用真实 JIT 热点证明 Perfetto 能直接帮助定位 side-exit 归因。适合做编译器、运行时和性能排障的参考,尤其对需要把追踪数据转成可查询、可视化分析流程的工程场景有可迁移价值。
技术文章 Go Blog 2026/03/24
文章深入解释了 Go 1.26 中类型检查器的“类型构造”和循环检测改进。作者先用简单的别名、切片、指针示例说明类型构造是一个深度优先的过程:只有依赖类型都完成后,当前类型才能变成 complete。随后文章引入递归类型,说明当类型构造返回 incomplete 类型时,许多依赖底层类型的检查必须延后到全部类型完成之后。接着作者用数组长度依赖 `unsafe.Sizeof` 的例子展示了“incomplete value” 与 downstream/upstream 运算符的区分,说明一旦值表达式会迫使对不完整类型做解构,就必须立即报 cycle error。最后文章概述了新的实现方式:在各类上游表达式处统一检查 completeness,阻止不完整值继续传播,并借此修复了旧算法中一些边缘崩溃问题,提升了编译器稳定性。
文章直接给出 Go 1.26 类型检查器的内部机制、错误边界和实现策略,不是泛泛而谈语言特性,而是可复用的编译器设计案例。适合编译器、语言实现和静态分析读者参考,尤其有助于理解递归类型、延迟检查与循环错误检测的通用思路。
技术文章 Go Blog 2026/03/10
文章介绍 Go 1.26 新版 go fix 中的 source-level inliner:它把函数调用按源代码层面展开,并通过 //go:fix inline 指令,让库作者为旧 API、重命名接口和类型/常量迁移提供“自助式”现代化方案。文中以 ioutil.ReadFile 迁移到 os.ReadFile、oldmath 包重构为例,说明 go fix 与 gopls 如何自动提示并批量改写调用点。作者进一步剖析了实现难点:参数消除、求值副作用顺序、可能在编译期失败的常量表达式、名字遮蔽、未使用变量以及 defer 作用域。文章强调该工具追求的是“可证明不改变语义”的整洁改写,因此在批处理场景会比人类更保守,甚至拒绝某些需要函数字面量包裹的情况。
文中直接展示了 //go:fix inline 的迁移用法,并系统解释了源级内联器如何处理语义边界,是理解 Go 代码改写与编译器式重构工具的可靠材料。适合做语言工具、重构引擎或 API 迁移方案的参考,但也要注意它在副作用和 defer 等场景下会刻意保守。
技术文章 Go Blog 2026/02/27
文章系统介绍 Go 编译器在切片分配上的栈化优化演进:从原先 append 扩容时频繁产生 1、2、4… 的堆分配和 GC 压力,到 Go 1.25 对小尺寸 make([]T,0,n) 的推测性栈分配,再到 Go 1.26 对 append 扩容场景也能先用栈上小缓冲、必要时再转堆。作者解释了返回切片等逃逸场景下,编译器如何借助 runtime.move2heap 把最终结果搬到堆上,同时尽量保留中间阶段的栈分配收益。文章还点明这些优化依赖切片最终大小、是否逃逸以及 32 字节等边界条件,并给出关闭优化的调试开关。整体上它展示了 Go 通过编译器与运行时协同减少分配、降低 GC 负担的具体机制与适用边界。
推荐收录,因为文章直接给出了 Go 1.25/1.26 在切片分配上从堆到栈、再到自动回迁堆的实现路径,属于可长期参考的编译器优化案例。适合关注 Go 性能、编译器和运行时协同的读者,也能帮助工程师判断哪些写法会触发或错过这些优化。
技术文章 Max Bernstein 2026/02/25
文章延续 Toy Optimizer 系列,讲作者如何为一个玩具编译器优化器构建模糊测试器,目标不是找崩溃,而是检出优化引入的语义错误。作者随机生成由 load、store 和 escape 组成的小程序,再用解释器在“无别名”和“完全别名”两种参数环境下执行,比较优化前后 heap 与逃逸结果是否一致。文中展示了这种不变量如何迅速暴露故意注入的错误:一旦去掉别名写回的关键逻辑,测试会几乎立刻失败并给出具体差异。作者也说明了局限性,例如只覆盖两种极端别名情况,且该等价定义不适用于会删除分配的优化。整体上,这是一个关于编译器优化测试、属性测试和语义 oracle 设计的实用案例。
推荐收录,因为文章给出了可复用的编译器优化 fuzzing 方案:随机程序生成、语义解释器和基于别名场景的正确性判定,而且能用最小反例迅速暴露优化错误。适合编译器、语言实现和测试工程读者参考;但要注意它的 oracle 依赖当前优化模型,不能直接套到会改变分配语义的场景。
技术文章 Max Bernstein 2026/02/16
文章延续 Toy Optimizer 系列,围绕加载/存储转发中的别名分析展开,先指出仅按偏移量划分 alias class 太粗,会把不同类型对象上同一偏移的访问误判为冲突。作者借鉴 type-based alias analysis,用类型层次树的前序/后序区间表示各 heap region,将“是否可能别名”转化为区间重叠查询,并在缺少类型信息时退化到 Any。随后又补充了对象来源、分配点、常量对象和已知内建函数副作用等更强的别名线索,用于局部保留或部分失效缓存的 heap 信息。文章还讨论了未知调用、逃逸对象与保守失效的边界,强调这种做法在 JIT 和受控语言中能以较低成本提升优化精度,但在通用 C-like 场景下需要更强的分析配合。
推荐收录,因为文章给出了从偏移量别名到类型层次 TBAA 的具体改造路径,还展示了与对象来源、内建副作用和未知调用的联动处理。适合做编译器、JIT 和语言运行时优化的参考,尤其对需要在精度与分析成本之间取舍的读者很有迁移价值。
工程实践 Anthropic Engineering 2026/02/04
文章复盘了 Anthropic 研究员用 16 个并行 Claude 实例,从零实现一个 Rust 版 C 编译器的过程。核心不是“让模型写代码”本身,而是设计一个能长期自治的 harness:用无限循环驱动任务推进、通过 git 文件锁避免重复劳动,并让不同代理分工处理测试、文档、性能和代码去重。作者强调,真正决定成败的是高质量测试、可自动判错的日志、以及把问题拆成可并行的小任务;当 Linux 内核编译这种“单大任务”卡住时,又引入 GCC 作为在线 oracle 和抽样测试来恢复并行性。最终产物可编译 Linux 6.9 及多个大型项目,但仍存在 16 位 x86、汇编器/链接器、代码质量和性能不足等边界,说明当前自治编程仍远未“全能”。
有直接工程证据:并行代理、任务锁、测试 harness、GCC oracle 和 CI 共同构成了可复用的方法论。适合做 AI 编程代理、自动化测试与编译器工程的参考,但也明确暴露了自治开发在正确性、效率和边界处理上的风险。
技术文章 Max Bernstein 2026/01/22
文章讨论 ZJIT 在编译 Ruby 字节码时遇到的多入口控制流图设计难题。由于 Ruby 默认参数在调用时求值,编译器需要把默认参数逻辑放在被调函数内部,并同时支持解释器入口、JIT 入口和若干默认参数入口。作者展示了这种 HIR 设计如何让 SSA、RPO 遍历和 Cooper 风格支配树算法都变得别扭,因为图里不再存在唯一的起始块。文中系统比较了三种方案:保留特殊处理、合成超级入口块、或按入口复制整张 CFG,并说明复制方案虽然简单但会带来代码膨胀。最终更新里给出团队选择了 superblock/EBB 方案,接受了更复杂的 dominator 与 predecessor 处理,以换取更清晰的入口模型。文章的边界也很明确:结论主要适用于多入口 IR 设计,后续复杂分析仍需继续验证。
收录价值在于它不是泛泛谈“编译器设计”,而是拿真实的多入口函数 IR、支配树失配和三种可选方案做了具体权衡。适合编译器、语言运行时和 IR 设计读者参考,尤其是需要处理入口分裂、默认参数或多返回点的实现者。
技术文章 Max Bernstein 2025/12/30
文章系统梳理了 GDB 如何借助 JIT 接口恢复 JIT 代码的符号、函数名和行号信息,从而在断点、回溯和反汇编时避免大量“???”。作者先解释旧接口的工作流:JIT 在内存中生成一份包含 DWARF 的临时对象文件,再通过 __jit_debug_descriptor 和 __jit_debug_register_code 通知 GDB 读取。随后又介绍了新版自定义调试信息接口,说明 reader 需要实现的回调、匹配代码区间与帧信息的职责,以及目前各运行时的支持现状。文章还讨论了将 Linux perf map 复用到 GDB 的可行性、GDB JIT 链表导致的 O(n²) 问题,以及 GC/代码移动对符号稳定性的约束。整体来看,它不仅讲清了接口机制,也点出了工程实现中的性能与生命周期边界。
文中直接给出 GDB JIT 旧/新接口的调用链、reader 回调和典型坑位,是理解 JIT 调试基础设施的实用材料。适合做运行时、调试器或语言实现相关工作的读者参考,尤其能迁移到符号注册、代码生命周期管理和可观测性设计中。
工程实践 Stanford Hazy Research 2025/11/11
这篇文章深入分析了 AMD MI355X/CDNA4 GPU 上 AI kernel 的性能来源,并提出 HipKittens 作为面向 AMD 的编程原语集合。作者先从硬件结构入手,对比了 AMD 与 NVIDIA 在寄存器文件、SRAM、矩阵指令、chiplet/L2/LLC 组织以及编译器支持上的差异,说明许多在 NVIDIA 上有效的做法在 AMD 上会失效。文章重点解释了为什么 wave specialization 在 AMD 上表现不佳:没有寄存器重分配、AGPR/VGPR 约束更强、以及细粒度同步和内存指令行为更复杂。为此,作者提出 8-wave ping-pong 和 4-wave interleave 两种调度模式,并结合 chiplet-aware 的 grid 排布来提升缓存复用。实验表明,这些策略在 GEMM 和 attention 等工作负载上能达到接近或优于现有 AMD 基线的性能,但其方法强依赖 CDNA3/4 细节、HIPCC 行为和底层指令布局知识,移植到其他平台仍需重新验证。
收录依据很明确:文章不仅给出 AMD GPU 的硬件差异分析,还提供了寄存器调度、bank conflict、chiplet cache 复用和基准测试的完整证据链。适合做 GPU kernel、编译器和 AI 基础设施的长期参考,但读者需要接受其强 AMD/CDNA 绑定和大量底层实现细节。
工程实践 Stanford Hazy Research 2025/11/11
文章围绕 AMD GPU 上的高性能 AI kernel 设计,介绍了 HipKittens 这一套面向 HIP 的 C++ 嵌入式原语。作者先分析现有 AMD 软件栈的问题:AITER、PyTorch、Triton、TileLang 和 CK 在若干 attention/GEMM 场景下难以稳定逼近峰值,部分还受限于寄存器分配、bank conflict、chiplet swizzle 等硬件细节。随后提出核心判断:tile 抽象可以跨架构复用,但真正决定性能的内存访问、调度和后端实现必须按 AMD/ NVIDIA 分开定制。基于这一思路,HipKittens 用约 500 行代码实现 attention 前向、不到 100 行热循环实现 GEMM,并在多项基准上超过现有基线。文章同时指出 wave specialization 在 CDNA3/4 上并不总有效,说明可移植的高层接口并不等于可移植的底层优化。
文中直接给出可验证的性能结果:HipKittens 的 attention 和 GEMM kernel 在 AMD MI355X 上超过多种基线,且代码规模很小,说明其方法不只是概念展示。适合做 GPU kernel、AI 编译器和多硬件适配的参考,尤其能帮助读者理解“统一接口、分离后端实现”的可迁移设计。