Lab 01 — PTX/SASS Dissection
Phase: 03 — GPU Compilers | Difficulty: ⭐⭐⭐☆☆ | Time: 3–4 hours
Tools: CUDA toolkit (nvcc, cuobjdump) — or godbolt.org with zero install
Concept primer:
../WARMUP.mdCh. 3–8.
Run
nvcc -ptx -o saxpy.ptx kernels.cu # PTX for annotation
nvcc -cubin -arch=sm_80 -o kernels.cubin kernels.cu
cuobjdump --dump-sass kernels.cubin > kernels.sass # SASS for the hunt
nvcc -Xptxas=-v -c kernels.cu # registers/smem/spills
No toolkit? godbolt.org → language CUDA C++ → compiler
"NVCC (latest)" → flags -O3 -arch=sm_80; the right pane shows PTX, and "Add new
→ Device" shows SASS. Everything below except the fatbin step works there.
0. The mission
Four tiny kernels (kernels.cu), four investigations:
saxpy— annotate every PTX line. Template insaxpy-annotation-template.md; answer key insaxpy-annotated.md. Do not peek early.guarded— a smallifbody: find where the branch disappeared in SASS (if-conversion →@%p-predicated stores /SEL).unrolled—#pragma unroll 8loop: count the replicated bodies in SASS; note the register count change in-Xptxas=-v.spiller— a kernel with a large per-thread array. Compile normally, then with-maxrregcount=16: find theLDL/STLlocal-memory spills that appear, and the "bytes spill stores/loads" line in ptxas output.
Then the fatbin dissection:
nvcc -gencode arch=compute_80,code=sm_80 \
-gencode arch=compute_90,code=sm_90 \
-gencode arch=compute_90,code=compute_90 -c kernels.cu -o fat.o
cuobjdump --list-elf fat.o # two ELFs (sm_80, sm_90)...
cuobjdump --dump-ptx fat.o | head # ...plus embedded PTX (compute_90)
Map each artifact to the load-time decision tree (WARMUP Ch. 7) and write, in two sentences, what happens on (a) an A100, (b) an H100, (c) whatever ships next.
1. The annotation rubric (what "done" means for saxpy)
Your annotation must identify: the .param ABI and ld.param prologue; the
cvta.to.global state-space conversion and why it exists; the
mad.lo.s32 index formula and which special registers feed it; the
setp+@%p bra tail guard; the mul.wide.s32 byte-offset computation; the
fma.rn.f32 contraction (and what -fmad=false would do to it). Six items —
the same six the WARMUP Ch. 5 tour narrates.
2. Findings sheet (fill in)
| Kernel | Flag setup | What I found (instruction + line) | Mechanism (one sentence) |
|---|---|---|---|
| guarded | -O3 | ||
| unrolled | -O3 | ||
| spiller | default | ||
| spiller | -maxrregcount=16 | ||
| fat.o | 3 gencodes |
3. Extensions
- Cross-compiler: same saxpy through
clang -x cuda --cuda-device-only -S(LLVM NVPTX) — diff the PTX against nvcc's. What's identical (the ABI), what differs (instruction selection, virtual register naming)? - Cross-vendor: on Godbolt, compile the HIP version with
hipccfor gfx90a and skim the GCN ISA — note there's no PTX-like layer (WARMUP Ch. 9's asymmetry, seen with your own eyes). - Tensor Core spotting: compile a 16×16
wmmaexample and findHMMAin SASS — the instruction the whole AI economy runs on.
4. What this lab proves about you
The compiler stack is no longer folklore: you've read the contract layer (PTX), the truth layer (SASS), and the deployment layer (fatbin) with your own eyes, and you can connect each to a production decision (numerical policy, occupancy tuning, build matrix).