Why it is called Stable
The name is a claim about serialization, not about the opset never changing shape day to day. StableHLOThe portable, versioned tensor IR that JAX and PyTorch both lower into; chapter 03 reads it line by line.taught in /l/stablehlo → modules serialize to a versioned bytecode format, and that format comes with an explicit compatibility guarantee: a module you save today keeps deserializing correctly for a documented window, and a module using slightly newer features still loads on documented older readers. That guarantee is the entire reason a mastery site can spend a chapter on the format at all, since dumps you capture now stay readable as your compiler version moves on.
The published policy sets that window at roughly five years backward and two years forward. A module serialized on one compiler version keeps deserializing correctly on readers up to about five years newer, and a module built with slightly ahead-of-its-time features still loads on readers up to about two years older. Those are not casual round numbers; they are the specific commitment the format makes, and it is what turns StableHLOThe portable, versioned tensor IR that JAX and PyTorch both lower into; chapter 03 reads it line by line.taught in /l/stablehlo → from an internal compiler detail into something you can depend on for anything you plan to keep around.
That commitment is what lets a saved model outlive the framework version that produced it. A checkpoint exported with one JAX release, serialized as StableHLOThe portable, versioned tensor IR that JAX and PyTorch both lower into; chapter 03 reads it line by line.taught in /l/stablehlo →, can be loaded and compiled by a different toolchain years later without a re-export, because the format itself carries the compatibility guarantee rather than leaving it to whichever framework happens to read the file. That is a deliberate trade against the alternative, where every framework upgrade risks breaking every artifact you saved with the previous one.
None of this is abstract once you start reading real dumps end to end. The type notation from the first section, the region structure from the second, and the custom_callHLO’s escape hatch for work outside the op set; a pallas_call rides through the compiler as one, carrying its Mosaic payload.taught in /l/stablehlo → boundary from the third all show up together in a single StableHLOThe portable, versioned tensor IR that JAX and PyTorch both lower into; chapter 03 reads it line by line.taught in /l/stablehlo → module the moment you lower any nontrivial JAX program, and the versioning story here is what keeps that same module readable next year.
Exercises
jax.lax.while_loop yourself with a two-element carry and find the carry tuple threading through stablehlo.while in the dump. Compare its shape against the scan program in this guide. custom_call. Name the call target and say what payload rides inside it. Check yourself
01 What exactly is stable about StableHLO?
The serialized form. Modules serialize to a versioned bytecode with an explicit compatibility guarantee, roughly five years backward and two years forward, not a promise that the opset never changes.
02 Why does that guarantee matter to someone who just trains models?
A checkpoint exported as StableHLO under one JAX release can be deserialized and compiled by a toolchain years later without a re-export. The saved artifact outlives the framework version that produced it.
Readings
- StableHLO compatibility ↗ the exact windows this lesson summarizes
- StableHLO bytecode ↗ the format the guarantee is made about