From d11579d041a5721ccedcc219f445d16a692b5837 Mon Sep 17 00:00:00 2001 From: Eugen Wissner Date: Wed, 8 Apr 2026 22:07:00 +0200 Subject: [PATCH] Use add_ptr instruction for array access expressions --- boot/stage21/cl.elna | 86 ++++++++++++++++++-------------------------- 1 file changed, 35 insertions(+), 51 deletions(-) diff --git a/boot/stage21/cl.elna b/boot/stage21/cl.elna index 4114947..5c0a009 100644 --- a/boot/stage21/cl.elna +++ b/boot/stage21/cl.elna @@ -990,18 +990,18 @@ proc elna_rtl_add_ptr(instructions: ^ElnaList, tac_instruction: ^ElnaTacInstruct var result: ^ElnaRtlInstruction; rtl_operand: ElnaRtlOperand; + intermediate: ElnaRtlOperand; begin + elna_rtl_generate_pseudo(@intermediate, variable_map); + result := elna_rtl_instruction_create(ElnaRtlOperator.li); - elna_rtl_instruction_set_operand(result, 1, ElnaRtlKind.pseudo, - tac_instruction^.operands[4].value, tac_instruction^.operands[4].length, 0); + elna_rtl_instruction_set_operand(result, 1, intermediate.kind, intermediate.value, intermediate.length, 0); elna_rtl_instruction_set_operand(result, 2, ElnaRtlKind.immediate, tac_instruction^.operands[3].value, 0, 0); elna_list_append(instructions, result); result := elna_rtl_instruction_create(ElnaRtlOperator.mul); - elna_rtl_instruction_set_operand(result, 1, ElnaRtlKind.pseudo, - tac_instruction^.operands[4].value, tac_instruction^.operands[4].length, 0); - elna_rtl_instruction_set_operand(result, 2, ElnaRtlKind.pseudo, - tac_instruction^.operands[4].value, tac_instruction^.operands[4].length, 0); + elna_rtl_instruction_set_operand(result, 1, intermediate.kind, intermediate.value, intermediate.length, 0); + elna_rtl_instruction_set_operand(result, 2, intermediate.kind, intermediate.value, intermediate.length, 0); elna_rtl_operand_value(instructions, @tac_instruction^.operands[2], variable_map, @rtl_operand); elna_rtl_instruction_set_operand(result, 3, rtl_operand.kind, rtl_operand.value, rtl_operand.length, 0); elna_list_append(instructions, result); @@ -1011,9 +1011,7 @@ begin tac_instruction^.operands[4].value, tac_instruction^.operands[4].length, 0); elna_rtl_operand_value(instructions, @tac_instruction^.operands[1], variable_map, @rtl_operand); elna_rtl_instruction_set_operand(result, 2, rtl_operand.kind, rtl_operand.value, rtl_operand.length, 0); - elna_rtl_instruction_set_operand(result, 3, ElnaRtlKind.pseudo, - tac_instruction^.operands[4].value, tac_instruction^.operands[4].length, 0); - + elna_rtl_instruction_set_operand(result, 3, intermediate.kind, intermediate.value, intermediate.length, 0); elna_list_append(instructions, result) end; @@ -1243,31 +1241,29 @@ var target_operand: ElnaRtlOperand; pseudo_symbol: ^ElnaRtlInfo; begin - if tac_instruction^.operands[2].kind = ElnaTacKind.variable then - elna_rtl_operand_value(instructions, @tac_instruction^.operands[1], variable_map, @source_operand); - pseudo_symbol := elna_symbol_table_lookup(variable_map, - tac_instruction^.operands[2].value, tac_instruction^.operands[2].length); + elna_rtl_operand_value(instructions, @tac_instruction^.operands[1], variable_map, @source_operand); + pseudo_symbol := elna_symbol_table_lookup(variable_map, + tac_instruction^.operands[2].value, tac_instruction^.operands[2].length); - if pseudo_symbol = nil then - elna_rtl_generate_pseudo(@target_operand, variable_map); - instruction := elna_rtl_instruction_create(ElnaRtlOperator.la); + if pseudo_symbol = nil then + elna_rtl_generate_pseudo(@target_operand, variable_map); + instruction := elna_rtl_instruction_create(ElnaRtlOperator.la); - elna_rtl_instruction_set_operand(instruction, 1, target_operand.kind, target_operand.value, target_operand.length, 0); - elna_rtl_instruction_set_operand(instruction, 2, ElnaRtlKind.symbol, + elna_rtl_instruction_set_operand(instruction, 1, target_operand.kind, target_operand.value, target_operand.length, 0); + elna_rtl_instruction_set_operand(instruction, 2, ElnaRtlKind.symbol, + tac_instruction^.operands[2].value, tac_instruction^.operands[2].length, 0); + elna_list_append(instructions, instruction); + + instruction := elna_rtl_instruction_create(ElnaRtlOperator.sw); + elna_rtl_instruction_set_operand(instruction, 1, source_operand.kind, source_operand.value, source_operand.length, 0); + elna_rtl_instruction_set_operand(instruction, 2, target_operand.kind, target_operand.value, target_operand.length, 0); + elna_list_append(instructions, instruction) + else + instruction := elna_rtl_instruction_create(ElnaRtlOperator.mv); + elna_rtl_instruction_set_operand(instruction, 1, ElnaRtlKind.pseudo, tac_instruction^.operands[2].value, tac_instruction^.operands[2].length, 0); - elna_list_append(instructions, instruction); - - instruction := elna_rtl_instruction_create(ElnaRtlOperator.sw); - elna_rtl_instruction_set_operand(instruction, 1, source_operand.kind, source_operand.value, source_operand.length, 0); - elna_rtl_instruction_set_operand(instruction, 2, target_operand.kind, target_operand.value, target_operand.length, 0); - elna_list_append(instructions, instruction) - else - instruction := elna_rtl_instruction_create(ElnaRtlOperator.mv); - elna_rtl_instruction_set_operand(instruction, 1, ElnaRtlKind.pseudo, - tac_instruction^.operands[2].value, tac_instruction^.operands[2].length, 0); - elna_rtl_instruction_set_operand(instruction, 2, source_operand.kind, source_operand.value, source_operand.length, 0); - elna_list_append(instructions, instruction); - end + elna_rtl_instruction_set_operand(instruction, 2, source_operand.kind, source_operand.value, source_operand.length, 0); + elna_list_append(instructions, instruction); end end; @@ -2290,10 +2286,7 @@ var instruction: ^ElnaTacInstruction; begin if operand_result^.kind = ElnaTacOperandType.dereferenced_pointer then - instruction := elna_tac_instruction_create(ElnaTacOperator.copy); - elna_tac_instruction_set_operand(instruction, 1, from^.kind, from^.value, from^.length); - elna_tac_instruction_set_operand(instruction, 2, to^.kind, to^.value, to^.length); - elna_list_append(instructions, instruction) + memmove(to, from, #size(ElnaTacOperand)) elsif operand_result^.kind = ElnaTacOperandType.sub_object then instruction := elna_tac_instruction_create(ElnaTacOperator.get_address); elna_tac_instruction_set_operand(instruction, 1, from^.kind, from^.value, from^.length); @@ -2844,9 +2837,7 @@ var instruction: ^ElnaTacInstruction; operand_result: ElnaTacOperandResult; inter_operand: ElnaTacOperand; - index_type: Word; - index_value: Word; - index_length: Word; + index_operand: ElnaTacOperand; aggregate_type: ^ElnaTypeArray; designator_base: ^ElnaTreeExpression; element_type: ^ElnaType; @@ -2856,31 +2847,24 @@ begin element_type := aggregate_type^.base; elna_tac_binary_expression(instructions, array_access_expression^.index, symbol_table, @inter_operand); - elna_tac_make_variable(@index_type, @index_value, @index_length, symbol_table); + elna_tac_make_variable(@index_operand.kind, @index_operand.value, @index_operand.length, symbol_table); instruction := elna_tac_instruction_create(ElnaTacOperator.subtract); - elna_tac_instruction_set_operand(instruction, 1, index_type, index_value, index_length); + elna_tac_instruction_set_operand(instruction, 1, index_operand.kind, index_operand.value, index_operand.length); elna_tac_instruction_set_operand(instruction, 2, inter_operand.kind, inter_operand.value, inter_operand.length); elna_tac_instruction_set_operand(instruction, 3, ElnaTacKind.constant, 1, 0); elna_list_append(instructions, instruction); - instruction := elna_tac_instruction_create(ElnaTacOperator.multiply); - elna_tac_instruction_set_operand(instruction, 1, index_type, index_value, index_length); - elna_tac_instruction_set_operand(instruction, 2, index_type, index_value, index_length); - elna_tac_instruction_set_operand(instruction, 3, ElnaTacKind.constant, element_type^.size, 0); - elna_list_append(instructions, instruction); - elna_tac_designator(instructions, array_access_expression^.array, symbol_table, @operand_result, @inter_operand); elna_tac_make_variable(@operand^.kind, @operand^.value, @operand^.length, symbol_table); - elna_tac_copy_address(instructions, @operand_result, @inter_operand, operand); - instruction := elna_tac_instruction_create(ElnaTacOperator.add); + instruction := elna_tac_instruction_create(ElnaTacOperator.add_ptr); elna_tac_instruction_set_operand(instruction, 1, operand^.kind, operand^.value, operand^.length); - elna_tac_instruction_set_operand(instruction, 2, operand^.kind, operand^.value, operand^.length); - elna_tac_instruction_set_operand(instruction, 3, index_type, index_value, index_length); - + elna_tac_instruction_set_operand(instruction, 2, index_operand.kind, index_operand.value, index_operand.length); + elna_tac_instruction_set_operand(instruction, 3, ElnaTacKind.constant, element_type^.size, 0); + elna_tac_instruction_set_operand(instruction, 4, operand^.kind, operand^.value, operand^.length); elna_list_append(instructions, instruction) end;