Compiles a single `stmt` into the `ctx`.
(
ctx: &mut Context,
symtable: &mut LocalSymtable<'_>,
stmt: Statement,
)
| 758 | |
| 759 | /// Compiles a single `stmt` into the `ctx`. |
| 760 | fn compile_stmt( |
| 761 | ctx: &mut Context, |
| 762 | symtable: &mut LocalSymtable<'_>, |
| 763 | stmt: Statement, |
| 764 | ) -> Result<()> { |
| 765 | let start_pc = ctx.codegen.next_pc(); |
| 766 | let mut mark_start = true; |
| 767 | match stmt { |
| 768 | Statement::ArrayAssignment(span) => { |
| 769 | let key_pos = span.vref_pos; |
| 770 | |
| 771 | let (arr_reg, info) = match symtable.get_local_or_global(&span.vref) { |
| 772 | Ok((reg, SymbolPrototype::Array(info))) => (reg, info), |
| 773 | |
| 774 | Ok((_, SymbolPrototype::Scalar(_))) | Err(syms::Error::UndefinedSymbol(..)) => { |
| 775 | return Err(Error::NotAnArray(key_pos, span.vref)); |
| 776 | } |
| 777 | |
| 778 | Err(e) => return Err(Error::from_syms(e, key_pos)), |
| 779 | }; |
| 780 | |
| 781 | if span.subscripts.len() != info.ndims { |
| 782 | return Err(Error::WrongNumberOfSubscripts( |
| 783 | key_pos, |
| 784 | info.ndims, |
| 785 | span.subscripts.len(), |
| 786 | )); |
| 787 | } |
| 788 | |
| 789 | let mut symtable = symtable.frozen(); |
| 790 | let mut outer_scope = symtable.temp_scope(); |
| 791 | |
| 792 | let val_reg = outer_scope.alloc().map_err(|e| Error::from_syms(e, key_pos))?; |
| 793 | compile_expr_as_type( |
| 794 | &mut ctx.codegen, |
| 795 | &mut symtable, |
| 796 | val_reg, |
| 797 | span.expr, |
| 798 | info.subtype, |
| 799 | )?; |
| 800 | |
| 801 | let first_sub_reg = compile_integer_exprs( |
| 802 | &mut ctx.codegen, |
| 803 | &mut symtable, |
| 804 | &mut outer_scope, |
| 805 | key_pos, |
| 806 | span.subscripts.into_iter(), |
| 807 | )?; |
| 808 | ctx.codegen.emit(bytecode::make_store_array(arr_reg, val_reg, first_sub_reg), key_pos); |
| 809 | } |
| 810 | |
| 811 | Statement::Assignment(span) => { |
| 812 | compile_assignment(&mut ctx.codegen, symtable, span)?; |
| 813 | } |
| 814 | |
| 815 | Statement::Call(span) => { |
| 816 | let key = SymbolKey::from(&span.vref.name); |
| 817 | let key_pos = span.vref_pos; |
no test coverage detected