banach-space/llvm-tutor: Out-of-Tree LLVM Passes You Can Actually Build
A collection of out-of-tree LLVM passes for teaching and learning
At a glance
- What is it?
- llvm-tutor is a collection of self-contained LLVM 23 passes built against a binary LLVM install, aimed at developers writing their first out-of-tree pass. Its value is the build and test scaffolding around each example, not the passes themselves.
- Who is it for?
- Adopt llvm-tutor if you are writing your first out-of-tree LLVM pass and want a CMake and LIT skeleton you can copy, and if you already have LLVM 23 installed, since the repository is pinned to that release. Do not adopt it if you need a maintained library of production passes, if you are on an older LLVM and cannot upgrade, or if you want to build LLVM from source as part of the workflow, because the README describes the binary-install path as the point of the project.
- Can I use it commercially?
- Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
- Is it still maintained?
- Yes. The repository last received commits 10 days ago.
- What is it written in?
- Mainly C++, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on September 29, 2026, and from our analysis. They are not legal advice.
Editorial analysis
The gap llvm-tutor fills between LLVM's API docs and a working pass
LLVM's pass infrastructure is documented, but the documentation does not hand you a buildable project. The distance between reading about a PassBuilder callback and producing a shared object that opt will load is where most first attempts stall: CMake plumbing, the LLVMConfig.cmake lookup, the plugin registration macro, the difference between a static and a dynamic plugin. llvm-tutor is a set of small passes designed to close exactly that distance. Each one is self-contained, and the repository layout reflects that: a top-level CMakeLists.txt, per-pass directories such as HelloWorld, plus include, lib, inputs, test and utils. The intended reader is a novice or aspiring LLVM developer, and the README says so directly, describing the project as a tutorial that targets that audience. The passes are the vehicle; the scaffolding is the product. If you already write out-of-tree passes comfortably, there is little here for you beyond a reading exercise in idiom.
How the passes plug into opt: dynamic plugins and the new pass manager
The mechanism is the modern one. A pass is compiled into a shared library (libHelloWorld.so on Linux, libHelloWorld.dylib on macOS) and loaded at runtime by opt through -load-pass-plugin, then selected by name with -passes=hello-world. Nothing is linked into opt itself, which is what out-of-tree means here. The HelloWorld example is an analysis-style pass: for every function defined in the input module it prints the function name and its argument count, and it does not modify the module. That is why the README's invocation includes -disable-output, which stops opt from writing an output bitcode file that would be identical to the input. The repository also carries a Dockerfile per distribution (Dockerfile_archlinux, Dockerfile_fedora, Dockerfile_ubuntu, Dockerfile_ubuntu_apt), so the environment can be reproduced rather than described. The README's table of contents also promises conceptual material on analysis versus transformation passes, dynamic versus static plugins, and optimisation passes inside LLVM, which is the context a reader needs before the individual examples make sense.
Building HelloWorld against a binary LLVM 23 install
The README's build path assumes LLVM 23 is already installed and points CMake at it. Set LLVM_DIR to the installation directory, configure the HelloWorld subdirectory out of source, and build. The variable CMake actually consumes is LT_LLVM_INSTALL_DIR, which is used to locate LLVMConfig.cmake.
export LLVM_DIR=<installation/dir/of/llvm/23>
mkdir build
cd build
cmake -DLT_LLVM_INSTALL_DIR=$LLVM_DIR <source/dir/llvm/tutor>/HelloWorld/
makeYou need an input module before you can run anything. The repository ships inputs/input_for_hello.c, and clang-23 turns it into LLVM IR.
$LLVM_DIR/bin/clang -O1 -S -emit-llvm <source/dir/llvm/tutor>/inputs/input_for_hello.c -o input_for_hello.llThen load the plugin and select the pass. The README gives the expected output, which is the useful part: it tells you what success looks like before you have any intuition for the tooling.
$LLVM_DIR/bin/opt -load-pass-plugin ./libHelloWorld.{so|dylib} -passes=hello-world -disable-output input_for_hello.llExpect four lines of function names with argument counts, for foo, bar, fez and main. If you see nothing, the plugin did not load, not that the pass is broken. To build the whole collection rather than one example, point CMake at the repository root instead of the HelloWorld subdirectory, keeping the same LT_LLVM_INSTALL_DIR setting.
The LLVM 23 pin is the constraint that decides whether this fits
The README is unambiguous: the examples are based on LLVM 23, and the install instructions cover llvm-23, llvm-23-dev, llvm-23-tools and clang-23 on Ubuntu, or llvm@23 on macOS via Homebrew. Requirements are a C++17 compiler and CMake 3.20 or higher. The project is out-of-tree in the build sense, but not version-agnostic. LLVM's pass API has changed across releases, and a tutorial pinned to one release will not compile against an older one without edits. If your toolchain is on an earlier LLVM and you cannot move, the examples stop being copy-paste and become a porting exercise, which is a different and harder task than the one the project is trying to teach. The README does describe building LLVM 23 from sources with a release/23.x checkout, but it also states that building from sources can be slow and tricky to debug and is not necessary. Take that at face value: the project's whole premise is that you install a binary LLVM and build only the passes. The README does not document rollback of a pass plugin or a supported downgrade path, so treat the LLVM 23 requirement as a hard boundary rather than a suggestion.
LIT and FileCheck are where the examples become checkable
The repository includes test/ and the README lists lit (llvm-lit) and FileCheck as additional requirements, noting that installing LLVM 23 satisfies them. This matters more than it sounds. A pass that prints to stderr is easy to get subtly wrong, and FileCheck turns the expected output into an assertion rather than a comment. The README also states that all examples are complemented with LIT tests and reference input files. For someone learning the pass API, the test file is often the clearest statement of intent: it shows the input, the invocation and the exact strings the pass must produce. The CI set-up is visible too, with workflows for Apple Silicon and x86 Ubuntu. The README does not document how to add a new pass to the test harness step by step, so you are reading the existing examples and generalising, which is a reasonable expectation for this audience but worth knowing before you start.
Not a pass library, and not a substitute for LLVM's own documentation
The clearest limitation is scope. These are reference examples, not a package you depend on. There are no releases in the repository, so consumption is by cloning or vendoring, and the value is in reading and adapting rather than linking. The passes are deliberately small: HelloWorld counts arguments and prints names. If you need a working transformation pass for a real optimisation pipeline, you will be writing it yourself, and llvm-tutor will have shown you the registration and build shape but not the analysis. The second limitation is the documentation boundary. The README is a tutorial, and it does not claim to be a complete reference for the pass manager or the IR. Where a design question goes beyond the examples, the README is silent, and the LLVM project's own documentation is the place to look. The table of contents also lists the optimisation-pass section twice, a small editorial slip that suggests the document has grown by accretion rather than revision. None of this undermines the examples; it does mean you should not treat the README as exhaustive.
Kaleidoscope teaches a language, llvm-tutor teaches the plugin boundary
The obvious alternative is the LLVM Kaleidoscope tutorial, which is the canonical way people learn LLVM and the phrase most often searched alongside this project. The two solve different problems. Kaleidoscope walks through building a small language end to end: lexer, parser, AST, code generation, and eventually optimisation passes wired into a driver you compile yourself. llvm-tutor starts later in that story. It assumes you have IR and a binary LLVM installation, and it focuses on the out-of-tree plugin boundary: how a pass becomes a shared library, how opt loads and selects it, and how a test asserts its output. If you want to understand how LLVM represents programs, Kaleidoscope is the better starting point. If you already have IR and want to write a pass that runs under opt without rebuilding LLVM, llvm-tutor is the shorter path. Some readers will want both, in that order. The repository also points to clang-tutor for the equivalent treatment of Clang, which is the natural next step once the LLVM pass model is familiar.
Licence and the cost of tracking LLVM releases
The repository is MIT licensed, which permits reuse and modification with the usual attribution requirement. For a tutorial whose main use is copying build files and pass skeletons into your own project, that is permissive enough that licence is unlikely to be the deciding factor; keep the copyright notice if you copy substantial portions. The real ongoing cost is version tracking. The README states the project is updated with every LLVM release, and the last push was on 2026-09-20, so the examples currently target LLVM 23. That cadence is a benefit only if you follow it. If your organisation pins an older LLVM for stability, every llvm-tutor update moves away from you, and the examples you copied will drift from the version you build against. Budget for the fact that a tutorial pinned to a moving upstream release requires periodic re-reading, not just a one-time clone. The README does not describe a compatibility matrix across LLVM versions, so there is no published statement about which older releases the examples still compile against.
Editorial conclusion
Adopt llvm-tutor if you are writing your first out-of-tree LLVM pass and want a CMake and LIT skeleton you can copy, and if you already have LLVM 23 installed, since the repository is pinned to that release. Do not adopt it if you need a maintained library of production passes, if you are on an older LLVM and cannot upgrade, or if you want to build LLVM from source as part of the workflow, because the README describes the binary-install path as the point of the project. Before committing, verify that the LLVMConfig.cmake under your LLVM 23 installation resolves through LT_LLVM_INSTALL_DIR and that llvm-lit is on your path, because the LIT tests are the only executable specification of what each pass is supposed to print.
Frequently asked questions
What is banach-space/llvm-tutor?
It is a collection of self-contained out-of-tree LLVM passes intended as a tutorial for novice and aspiring LLVM developers. The README describes it as a tutorial built around reference examples, with CMake build scripts, LIT tests, CI set-up and documentation, and notes that it is based on LLVM 23.
How do I install and build banach-space/llvm-tutor?
Install LLVM 23 first, either from apt.llvm.org on Ubuntu or with brew install llvm@23 on macOS. Then configure with CMake, passing LT_LLVM_INSTALL_DIR set to the LLVM 23 installation directory, and run make in the build directory. The README's HelloWorld example builds just that subdirectory.
Which LLVM version does banach-space/llvm-tutor require?
LLVM 23. The README also requires a C++17 compiler and CMake 3.20 or higher, and lists clang-23 and opt as the tools needed to run the passes.
Does banach-space/llvm-tutor include tests?
Yes. The repository has a test directory, and the README states that all examples are complemented with LIT tests and reference input files. Running them requires lit (llvm-lit) and FileCheck, which the README notes are satisfied by installing LLVM 23.
Official sources
Add this badge to your README
If you maintain this project, the badge below links readers to this analysis and shows its maintenance status from the daily GitHub snapshot. Paste the markdown into your README; add ?metric=license or ?metric=stars to the image URL for a different field.
[](https://hysenlabs.com/projects/banach-space-llvm-tutor)