news 2026/10/14 16:50:59

Verible 开发者指南:源码导航、编译数据库与提交前自动化检查全流程

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
Verible 开发者指南:源码导航、编译数据库与提交前自动化检查全流程
  • 开发工具
  • Lint
  • 静态分析
  • 硬件开发

【免费下载链接】verible

Verible is a suite of SystemVerilog developer tools, including a parser, style-linter, formatter and language server

项目地址:https://gitcode.com/gh_mirrors/ve/verible
点击查看免费下载

Verible 是 Chips Alliance 维护的 SystemVerilog 开发者工具集(解析器、风格检查器、格式化工具与语言服务器),其 doc/development.md 是面向贡献者与二次开发者的开发资源文档,汇总了源码搜索导航、clangd 编译数据库构建、clang-tidy 缓存检查与before-submit.sh提交前检查流水线等核心开发辅助手段。本文以该文档为主线,结合仓库中.github/bin/下的实际脚本实现与 MODULE.bazel、shell.nix 等构建配置,完整讲解在 Verible 中建立高效的本地开发工作流的每一步,读完后你可以独立搭建导航环境、理解代码组织约定,并在提交 PR 前复现 CI 的全部本地检查。

一、搜索与导航 Verible 源码

doc/development.md 的开篇建议:熟悉这个代码库需要时间,善用搜索索引。文档给出了三条导航路径:

  1. 在线搜索镜像:项目维护了一个按代码搜索索引过的源码镜像(cs.opensource.google 上的 verible 镜像),适合全局关键字检索与历史浏览;
  2. 自建 Kythe 索引:如果需要离线跨引用导航(查找引用、跳转定义),可以按照 doc/indexing.md 的说明,用 Kythe 的 C++ 提取器对 Bazel 构建目标做编译抽取、生成 GraphStore 并启动 Web UI。仓库根目录还提供了 kythe-browse.sh,它针对SystemVerilog 源码(而非 C++ 源码)执行同样的流程:先构建//verible/verilog/tools/kythe:all,再用verible-verilog-kythe-extractor抽取 Kythe facts,经entrystream、write_entries、write_tables后由http_server在localhost:8080提供浏览(端口可用环境变量BROWSE_PORT覆盖)。
  3. 编辑器导航(推荐日常使用):让编辑器使用clangd语言服务器,并先生成它所需的编译数据库:
.github/bin/make-compilation-db.sh

编译数据库是如何生成的

阅读 make-compilation-db.sh 可以看清这条命令背后的完整流程:

  • 构建所需的 Bazel 与 bant 工具链可通过环境变量BAZEL和get-bant-path.sh定位,bant 作为开发依赖声明在 MODULE.bazel 中(bazel_dep(name = "bant", version = "0.3.6", dev_dependency = True));
  • 脚本会先对 MODULE.bazel 声明的外部依赖逐个执行bazel fetch(abseil-cpp、nlohmann_json、protobuf、re2、rules_flex、zlib、googletest),确保外部源码全部落地;
  • 接着用 bant 列出并构建所有genrule与cc_proto_library目标(list-targets -g "genrule|cc_proto_library" -m -c3 ...),使生成文件在依赖分析中可见;
  • 由于 bant 尚不能区分逐文件的编译参数,脚本选择不生成compile_commands.json,而是用bant compile-flags -o compile_flags.txt生成更简单的统一编译参数文件,这对各类工具都更易消化;
  • 最后补一个已知缺口:bant 尚看不到 toolchain 内部的 flex 依赖,脚本会扫描bazel-out/../../../external/*flex*/src/FlexLexer.h并把对应-I目录追加进compile_flags.txt。

因此该脚本的产物是项目根目录下的compile_flags.txt,供 clangd 及后文的 clang-tidy 缓存脚本共同消费。

二、保持代码整洁的自动化工具

带缓存的 clang-tidy 检查

文档指出:有了编译数据库后,可以运行 clang-tidy 检查器:

.github/bin/run-clang-tidy-cached.cc

并特别提醒:首次运行会花较长时间,但结果会被缓存。

从 run-clang-tidy-cached.cc 的实现看,这是一个自包含的 C++17 程序——文件开头的#if 0段让它可以直接当 shell 脚本执行,首次运行时用c++ -std=c++17就地编译自己再运行。其缓存与增量机制值得拆解:

  • 内容寻址缓存:每个源文件的 clang-tidy 输出按hash(文件内容)命名存入~/.cache/clang-tidy/下的项目缓存目录(Verible 的缓存前缀配置为verible_,见 run-clang-tidy-cached.cc#L121-L130 中的kConfig)。文件内容不变则直接复用缓存;
  • 头文件变更联动:若开启了revisit_if_any_include_changes(默认开启),源文件的指纹会与其#include头文件的内容哈希异或——foo.cc本身没改,但bar.h改了,foo.cc仍会被重新检查,从而发现“依赖头文件行为”的隐患;
  • 构建环境变更重查:toplevel_build_file配置为MODULE.bazel,当MODULE.bazel或编译数据库的时间戳比某条已缓存的告警更新时,会重新审视该文件(依赖变化可能改变 tidy 结论);
  • 项目定制:Verible 的kConfig排除了.git/、.github/、vscode/目录以及tree-operations_test、symbol-table_test这两个处理非常慢的测试文件,并标记is_bazel_project = true,使报告中的路径能规范化回项目根目录;
  • 并行与配置:CLANG_TIDY_JOBS控制并行任务数(默认取硬件并发度);环境变量CLANG_TIDY、CLANG_TIDY_CONFIG、CACHE_DIR可分别覆盖 tidy 二进制、配置文件与缓存目录。tidy 的配置本身来自仓库根目录的 .clang-tidy;
  • 输出:明细报告与按 check 汇总的计数报告分别写入缓存目录的verible_clang-tidy.out与verible_clang-tidy.summary符号链接,无告警时直接打印 “No clang-tidy complaints.”。

文件头部注释中还给出了典型的高级用法示例——只跑某个检查并自动修复:

run-clang-tidy-cached.cc --checks="-*,modernize-use-override" --fix

脚本运行前提是项目根目录存在compile_commands.json或compile_flags.txt(即先跑过 make-compilation-db.sh),否则它会在 run-clang-tidy-cached.cc#L595-L604 处直接报错退出。

提交前一站式检查:before-submit.sh

文档建议:在创建 Pull Request 之前运行下面这个脚本,看看有没有遗漏(CI 也能兜底,但本地先跑一遍体验更好):

.github/bin/before-submit.sh

并说明它内部也会跑 clang-tidy,因此首次运行同样较慢。通读 before-submit.sh 可以看到它实际串联了7 个阶段,且支持--skip-clang-tidy、--skip-cpp-std两个开关跳过耗时步骤:

  1. 构建 bant(通过get-bant-path.sh),它是后续编译数据库与构建清理的基础;
  2. 刷新编译数据库:直接调用 make-compilation-db.sh,这一步同时保证外部依赖全部拉取,为构建清理做好准备(before-submit.sh#L41-L49);
  3. 运行 build cleaner:bant dwyu,清理无用依赖与代码结构问题;
  4. 全量测试:bazel test -c opt --test_summary=terse ...;
  5. 多语言标准回归:分别用-std=c++20与-std=c++23重跑全部测试,保证代码不只在新标准下能编译(before-submit.sh#L58-L65);
  6. clang-tidy(带缓存),然后
  7. 格式化 + 潜在问题检查:依次调用 run-format.sh 与 check-potential-problems.sh。

两个子脚本各自也值得展开:

run-format.sh:对仓库内所有*.h/*.cc(排除third_party/、external_libs/、.github/)执行clang-format -i。格式基准是 CONTRIBUTING.md 声明的 Google C++ 风格,仓库的 .clang-format 在 Google 基础上做了唯一一处定制——指针/引用一律右对齐(PointerAlignment: Right)。若装有buildifier,还会顺手格式化 MODULE.bazel 与所有BUILD、*.bzl文件。

check-potential-problems.sh是一组“防止误引入坏习惯”的静态 grep 检查,规则包括(见 check-potential-problems.sh#L22-L114):

  • 统一使用std::string_view,禁止absl::string_view及其 BUILD 依赖;
  • status_macros.h只能在.cc编译单元中使用,不得出现在头文件里(避免污染全局命名空间);
  • verible/common下禁止出现verilog::命名空间——这是保证 common 层语言无关的关键约束;
  • #include必须写完全限定路径(如#include "verible/common/..."),不允许#include "foo.h"这类相对写法;
  • C++ 文件命名用连字符分隔、下划线仅用于_test后缀(例如foo-bar_test.cc),测试文件必须以_test结尾;
  • MODULE.bazel 中禁止引入rules_python(会破坏平台无关的静态构建策略);
  • 禁止使用std::regex(慢且依赖异常),改用 RE2;
  • 禁止使用.bazelversion,要求仓库兼容当前所有活跃的 Bazel 版本。

风格与测试的配套约定

结合 CONTRIBUTING.md,本地开发还应注意:提交前对改动文件执行clang-format --style=file -i <files>;每项改动应附带防回归的测试(以单元测试为主),项目也欢迎纯测试用例的贡献。检查覆盖率可运行:

MODE=coverage .github/bin/build-and-test.sh .github/bin/generate-coverage-html.sh

报告位于coverage-html/index.html。

三、阅读代码的经验提示

doc/development.md 的 “Tips” 部分给出了两条长期有效的建议,文档中保留了原文表述:

  • 读测试代码:大多数.h和.cc文件都配有_test.cc单元测试,而且测试“永远不会过时”——因为 CI 保证它们始终通过。从测试读起,是理解一个模块行为最可靠的入口;
  • 找示例:挖掘 git 历史,沿着 blame/annotation 看特定代码行何时被修改;寻找相关的已关闭 issue,以及解决它们的提交。

四、代码组织:每个目录的 README 是入口

文档 “Code Organization” 一节指出:源码树的每个目录都带有一个简短的 README.md 描述其内容,并给出三大顶层划分:

  • verible/common:所有语言无关的库与工具。按 verible/common/README.md 的目录摘要,包含util(通用算法与数据结构)、strings(纯字符串操作)、lexer(产生 token 流的词法器接口与适配器)、parser(从 token 构建语法树的解析器接口与适配器)、text(源码结构表示:token、行、树等)、analysis(文本结构上的分析与查询设施)、formatting(可复用的格式化操作);
  • verible/verilog:SystemVerilog 相关的库与工具。按 verible/verilog/README.md,可独立安装的工具都组织在tools/下(syntax、lint、formatter、ls、diff、project、obfuscator、preprocessor、kythe 等),其余目录都是支撑库;
  • external_libs:部分外部库依赖。按 external_libs/README.md 的说明,首选方式是通过 Bazel 工作区声明外部依赖(当前即 MODULE.bazel),只有在工作流无法良好支持时才在此目录存放库的拷贝。

需要注意,第四部分中的“common 语言无关”约定不是纸面承诺,而是由 check-potential-problems.sh 在提交前检查中强制执行的——这体现了 Verible 用脚本固化架构约束的工程习惯。

五、深入子主题的文档地图

doc/development.md 本身是一个“枢纽文档”,它把四个子主题导向更深入的专项指南,这里按仓库现状逐一说明:

  • Verilog 前端:doc/parser_design.md 描述了词法/解析器设计——Flex 生成词法器但与 Bison 生成的解析器完全解耦(yyparse()并不直接调用yylex()),中间经过 contextualizer(消歧 token 的多重解释,简化 LR 语法)与 filter(把 token 流过滤成视图,如隐藏注释以便解析)两个环节;解析器用 LALR(1) 生成,其语法非常规地显式处理预处理构造、指令与宏,从而能对“有限但实用”的未预处理代码子集工作,并构建捕获所有非注释 token 的具体语法树(CST)。对应源码位于 verible/verilog/parser(verilog.lex与verilog.y);
  • 分析器(Lint 规则):doc/style_lint.md 是风格检查器的开发者指南,说明三类分析基类——LineLintRule(逐行)、TokenStreamLintRule(逐 token)、SyntaxTreeLintRule(语法树,绝大多数 SystemVerilog 规则属于此类)——以及树分析工具与规则实现方法,规则实现集中在 verible/verilog/analysis/checkers;
  • 格式化工具:doc/formatter.md 讲解 formatter 的工作原理与调试方法(注意:development.md 原文此处链接拼写为foramtter.md,仓库中实际文件为formatter.md);
  • 转换(Transformers):development.md 中该小节当前为空占位,暂无深入文档;
  • Kythe 索引:doc/indexing.md 覆盖从下载 Kythe 工具集、构建 Web 前端,到用--experimental_action_listener=:extract_cxx抽取编译事实、生成 GraphStore 与 serving tables 的完整流程,文中也提醒:如果只是想本地改代码,不必索引,直接调用.github/bin/make-compilation-db.sh生成编译数据库即可。

六、适用前提:本地构建环境

上述工作流默认在能完成构建的环境中运行,按 README.md 的开发者章节与仓库配置,适用前提包括:

  • 需要 Bazel 构建系统与 C++20 兼容编译器;Nix 用户可以直接在仓库内nix-shell,shell.nix 提供了 bazel_8、clang-tidy/clang-format 工具链(并通过CLANG_TIDY、CLANG_FORMAT环境变量注入版本),以及 lcov、buildifier、flex/bison 等开发辅助;
  • 常规构建命令为bazel build -c opt //...;若 flex/bison 生成工具遇到编译问题,可加--//bazel:use_local_flex_bison使用本地工具链;
  • 需要静态链接产物时可用bazel build -c opt --config=create_static_linked_executables //...(改用 bfd 链接器)。

小结

Verible 的 doc/development.md 用一页文档搭建起了贡献者的工作流骨架:在线索引 + clangd 编译数据库负责看懂代码,带缓存的 clang-tidy 与before-submit.sh负责守住质量(测试、多标准回归、格式化、架构约束检查一应俱全),目录 README 与四份专项文档(parser_design.md、style_lint.md、formatter.md、indexing.md) 则负责深入各子系统。配合 CONTRIBUTING.md 的沟通、代码评审与测试要求,这份开发资源文档与.github/bin/下的脚本共同构成了在本地完整复现 CI 检查的开发闭环。

  • 开发工具
  • Lint
  • 静态分析
  • 硬件开发

【免费下载链接】verible

Verible is a suite of SystemVerilog developer tools, including a parser, style-linter, formatter and language server

项目地址:https://gitcode.com/gh_mirrors/ve/verible
点击查看免费下载

相关推荐

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/10/14 16:50:46

MATLAB SOM Toolbox:解锁自组织映射的完整分析与可视化工作流

简介&#xff1a;基于MATLAB的Kohonen自组织映射&#xff08;SOM&#xff09;软件包&#xff0c;面向机器学习研究者、数据工程师以及希望探索高维数据内在规律的初学者&#xff0c;用于无监督降维、可视化和模式发现&#xff0c;通过二维或三维网格映射将复杂数据结构转化为清…

作者头像 李华
网站建设 2026/10/14 16:50:12

文件系统原理与架构:从存储介质到系统调用的完整图解

1. 存储介质回顾&#xff1a;数据最终落在哪里做后端或者系统方向的人&#xff0c;迟早会遇到文件系统。刚开始接触时往往一头雾水&#xff1a;明明有磁盘&#xff0c;为什么要再搞一层文件系统&#xff1f;更别说后续冒出来的块设备、页缓存、inode这些概念&#xff0c;每个词…

作者头像 李华
网站建设 2026/10/14 16:49:48

STM32F407心电监测系统:从电极到QRS检测的完整嵌入式信号链实现

简介&#xff1a;本资源是一款基于STM32F103C8T6的便携式多参数生理监测系统完整工程&#xff0c;面向嵌入式初学者、电子设计竞赛学生及医疗电子方向实践者&#xff0c;解决家庭场景下心率、血氧饱和度与心电图&#xff08;ECG&#xff09;三合一实时采集与可视化需求。压缩包…

作者头像 李华
网站建设 2026/10/14 16:49:33

AI 生成系统的全功能验证报告:汽修厂案例的八个测试项

B 站的读者知道我做实测系列:快餐连锁、母婴店都测过。第三测,汽修厂——同行覃老板的店,十一年,六个举升机工位,一间配件仓。 选汽修厂不是随手挑的。前两测之后,评论区吵翻了:有人说餐饮简单,有人说母婴店单据少,生成系统赢在业务轻。 这回特意挑了个「重」的——汽修的单据密…

作者头像 李华