{"record":{"id":"cdcba348e9ba6314","repo":"BoundaryML/baml","slug":"virtual-local-local-without-definition","errorCode":null,"errorMessage":"virtual local {local} without definition","messagePattern":"virtual local (.+?) without definition","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"critical","filePath":"baml_language/crates/baml_compiler2_emit/src/emit.rs","lineNumber":3371,"sourceCode":"\n    fn pull_constant(&mut self, constant: &Constant<'ctx>) -> Result<(), Self::Error> {\n        self.emit_constant(constant);\n        Ok(())\n    }\n\n    fn pull_local(&mut self, local: Local) -> Result<LocalPullAction<'ctx>, Self::Error> {\n        let classification = self.analysis.classifications[&local];\n\n        let action = match classification {\n            LocalClassification::Virtual => {\n                // Attribute inlined virtual loads to their defining statement.\n                self.set_debug_span(self.def_span_for_local(local), false);\n                // Inline the definition rvalue at use site.\n                let rvalue = self.analysis.def_use[&local]\n                    .def\n                    .as_ref()\n                    .map(|def| def.rvalue.clone())\n                    .unwrap_or_else(|| panic!(\"virtual local {local} without definition\"));\n                // MakeClosure must be handled specially: its captures need to load\n                // cell pointers (LoadVar) not cell values (LoadDeref). We intercept\n                // here so that `emit_rvalue_pull` (which sets loading_for_closure_capture)\n                // is called rather than the generic `walk_rvalue_pull` inlining path.\n                // MakeBoundMethod / MakeVirtualBoundMethod / VirtualFieldAccess must\n                // also be handled specially: none is handled by `walk_rvalue_pull`\n                // (which panics on them), so route through `emit_rvalue_pull`.\n                // BinaryOp must be routed through `emit_rvalue_pull` so that the\n                // type-aware specialization in `try_specialize_binary_op` can fire\n                // (e.g. emitting `CmpBigintOp` instead of the generic `CmpOp`).\n                // Class aggregates may use emitter-only spread helpers, so they\n                // also need to flow through `emit_rvalue_pull` when inlined.\n                if matches!(\n                    rvalue,\n                    Rvalue::MakeClosure { .. }\n                        | Rvalue::MakeBoundMethod { .. }\n                        | Rvalue::MakeVirtualBoundMethod { .. }\n                        | Rvalue::MakeVirtualFunction { .. }","sourceCodeStart":3353,"sourceCodeEnd":3389,"githubUrl":"https://github.com/BoundaryML/baml/blob/bd85ce9dee1463ff04d27efd20531013a4ff46c1/baml_language/crates/baml_compiler2_emit/src/emit.rs#L3353-L3389","documentation":"Panic while inlining a virtual (def-use optimized) local at its use site: the analysis recorded the local as having a use, but def_use[&local].def is None, so there is no rvalue to inline. A virtual local exists precisely to have its single definition inlined; a use without a definition breaks that invariant.","triggerScenarios":"Emitting a use of a virtual local whose def-use entry has no recorded definition rvalue — e.g. the definition was dropped by a pass but the use remained, or the local was misclassified as virtual.","commonSituations":"Compiler development around the def-use/virtual-local optimization; users see a compiler crash rather than a source-level error.","solutions":["Ensure every virtual local has its definition rvalue recorded in def_use before emission of its uses.","Re-materialize locals as normal stack locals when their definition cannot be inlined.","Verify the pass that promotes locals to virtual ones checks for a present definition.","Report the triggering BAML source as a compiler bug."],"exampleFix":null,"handlingStrategy":"validation","validationCode":"// only treat locals as virtual when a definition exists\nfn can_be_virtual(local: &Local, def_use: &DefUse) -> bool {\n    def_use.uses(local) == 1 && def_use.def(local).is_some()\n}","typeGuard":null,"tryCatchPattern":"// compiler panic — guard the compile entry point\nmatch baml_compile(source) {\n    Err(e) => log_internal_bug(e),\n    Ok(b) => use_bytecode(b),\n}","preventionTips":["Promote a local to virtual only if its definition rvalue is recorded","Fall back to a stack local when inlining is impossible","Test the def-use optimization against edge-case control flow","Keep optimization passes and emitter invariants covered by tests"],"tags":["compiler","lir","panic","optimization"],"backgroundTag":"internal-invariant-violation","analyzedSha":"bd85ce9dee1463ff04d27efd20531013a4ff46c1","analyzedAt":"2026-09-12T03:38:25.718Z","contentChangedAt":"2026-09-12T03:38:25.718Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}