Skip to main content

luaur_ast/methods/
parser_push_local.rs

1use crate::records::ast_local::AstLocal;
2use crate::records::binding::Binding;
3use crate::records::parser::Parser;
4
5impl Parser {
6    #[allow(non_snake_case)]
7    pub fn push_local(&mut self, binding: &Binding) -> *mut AstLocal {
8        let name = binding.name;
9
10        // C++: `AstLocal*& local = local_map[name.name];` — operator[] inserts a
11        // null slot when absent, and the prior value becomes the new local's
12        // shadow before the slot is reassigned to the freshly allocated local.
13        let shadow = *self.local_map.get_or_insert(name.name);
14
15        let function_depth = self.function_stack.len() - 1;
16        let loop_depth = self.function_stack.last().unwrap().loop_depth as usize;
17
18        let new_local = AstLocal {
19            name: name.name,
20            location: name.location,
21            shadow,
22            function_depth,
23            loop_depth,
24            is_const: binding.is_const,
25            is_exported: false,
26            annotation: binding.annotation,
27        };
28
29        // Safety: self.allocator is a raw pointer to the arena Allocator.
30        let local = unsafe { (*self.allocator).alloc(new_local) };
31
32        *self.local_map.get_or_insert(name.name) = local;
33        self.local_stack.push(local);
34
35        local
36    }
37}