Specimen Report · C

rrrlz

phiat/rrrlz

Compare LLVM optimization levels (O0–O3) across pathfinding algorithms, with interactive SDL2 step-through animation

Stars
★ 1
Forks
⑂ 0
Language
C
Size
92 kB
Last Push
2mo ago
Forged
3mo ago
llvmoptimizationpathfindingsdl2visualization
# rrrlz — LLVM Optimization Comparison Lab A collection of C programs built through the LLVM toolchain at multiple optimization levels to study how different passes transform code. ## Programs | Directory | Algorithm | Description | |---|---|---| | `hello/` | Hello World | Minimal baseline — shows optimization pipeline with trivial code | | `dijkstra/` | Dijkstra's Algorithm | Shortest path on a 20x20 grid, uniform expansion | | `astar/` | A* Search | Heuristic-guided shortest path on the same grid | | `bellman_ford/` | Bellman-Ford | Edge-relaxation shortest path, no heap, negative weight support | | `floyd_warshall/` | Floyd-Warshall | All-pairs shortest paths, O(V^3) triple-nested loop | | `ida_star/` | IDA* | Memory-efficient A* via iterative deepening with f-cost threshold | | `visualizer/` | SDL2 Visualizer | Step-through animation of 14 pathfinding algorithms | ## How It Works Each program goes through a 4-stage LLVM pipeline: ``` source.c → clean IR (.ll) → optimized IR → assembly (.s) → binary clang -O1 opt -O{level} llc clang (no opts applied) ``` This is run at 5 optimization levels: **O1, O2, O3, Os, Oz** The key insight: by generating clean (unoptimized) IR first and then running `opt` separately, you can see exactly what each optimization level changes in the IR — independent of clang's frontend decisions. ## Quick Start ```bash # Build everything just all bash build_all.sh # Build one target just dijkstra just visualizer # Run ./dijkstra/dijkstra_opt_O2 ./astar/astar_opt_O2 # Visualizer (requires libsdl2-dev, WSLg or X11) just run ./visualizer/visualizer ``` ## Comparing Optimizations ```bash # Compare IR between optimization levels diff dijkstra/dijkstra_opt_O1.ll dijkstra/dijkstra_opt_O3.ll diff astar/astar_opt_O1.ll astar/astar_opt_Os.ll # Compare assembly diff -u dijkstra/dijkstra_opt_O1.s dijkstra/dijkstra_opt_O3.s # Side-by-side vimdiff astar/astar_opt_O2.ll astar/astar_opt_O3.ll ``` ## What to Look For ### O1 → O2 - Small helper functions get inlined (`get_index`, `is_valid`, `heuristic`) - Basic loop optimizations (LICM, dead store elimination) ### O2 → O3 - Loop unrolling in heap operations - More aggressive inlining thresholds - Vectorization opportunities (if any) ### Os / Oz (size optimization) - Functions stay outlined (less inlining) - No loop unrolling - Smaller instruction sequences preferred over faster ones - Oz is more aggressive than Os about size ## Optimization-Visible Code Patterns The pathfinding implementations deliberately include patterns that produce different IR at different levels: 1. **Small helper functions** — inlining threshold differences 2. **Nested loops** — unrolling and vectorization 3. **Array indexing** — strength reduction 4. **Multi-condition branches** — branch prediction, dead branch elimination 5. **Arithmetic** (heuristic) — constant propagation, algebraic simplification ## Project Structure ``` rrrlz/ ├── README.md # This file ├── justfile # Build recipes (just all, just run, etc.) ├── build_all.sh # Build script for all targets ├── hello/ │ └── hello.c # Minimal baseline program ├── dijkstra/ │ ├── ALGO.md │ └── dijkstra.c # Dijkstra's shortest path ├── astar/ │ ├── ALGO.md │ └── astar.c # A* search with Manhattan heuristic ├── bellman_ford/ │ ├── ALGO.md │ └── bellman_ford.c # Bellman-Ford edge relaxation ├── floyd_warshall/ │ ├── ALGO.md │ └── floyd_warshall.c # Floyd-Warshall all-pairs shortest paths ├── ida_star/ │ ├── ALGO.md │ └── ida_star.c # IDA* iterative deepening A* └── visualizer/ └── visualizer.c # SDL2 step-through animation ``` ## Requirements - `clang` (C compiler + IR generation) - `opt` (LLVM optimizer) - `llc` (LLVM static compiler — IR to assembly) - `libsdl2-dev` (for visualizer only) - `just` (task runner, optional — `cargo install just` or via mise) All part of the LLVM/Clang toolchain (`apt install clang llvm libsdl2-dev`).
↗ GitHub