Step 05 · The mlir-translate / lli pipeline
mlir-translate is MLIR's bridge to external IRs. Its
--mlir-to-llvmir mode walks an MLIR module that's already in the
llvm dialect and produces textual LLVM IR. From there lli or
llc take over.
MiniLang source
│ Lexer → Parser → Resolver → TypeChecker → IR builder
▼
MiniLang TAC IR
│ mlir_emit::emit
▼
MLIR (`llvm` dialect)
│ mlir-translate --mlir-to-llvmir
▼
LLVM IR (text)
│ lli (or llc -filetype=obj + ld)
▼
Process exit code + stdout
Implementing the pipeline in C++
runShell (in mlir_emit.cpp) forks /bin/sh -c "mlir-translate ... | lli"
with pipes attached. Robust enough for tests; production tooling would
likely link MLIR's own translation library instead.
Catching errors
If mlir-translate rejects our IR (wrong type, missing op), the pipe
breaks and lli exits non-zero. We capture stderr from the child
into PipelineResult::error so test failures point at the offending
stage.
Inspecting intermediate stages
echo 'print 42;' | ./build/mlmlir | tee /tmp/m.mlir
/opt/homebrew/opt/llvm/bin/mlir-opt /tmp/m.mlir --canonicalize # pretty + sanity-check
/opt/homebrew/opt/llvm/bin/mlir-translate /tmp/m.mlir --mlir-to-llvmir
/opt/homebrew/opt/llvm/bin/mlir-translate /tmp/m.mlir --mlir-to-llvmir \
| /opt/homebrew/opt/llvm/bin/llc -O2 -filetype=obj -o /tmp/m.o