Lower global static array and record access
This commit is contained in:
@@ -7,8 +7,9 @@ program;
|
||||
|
||||
(* Stage 18 compiler. *)
|
||||
|
||||
(* - Record fields can be aggregates themselves *)
|
||||
(* - Record fields can be aggregates themselves. *)
|
||||
(* - Static arrays. *)
|
||||
(* - Global variables can have any valid type. *)
|
||||
|
||||
type
|
||||
(**
|
||||
@@ -2799,10 +2800,21 @@ begin
|
||||
field_offset := field_offset + field_type^.size;
|
||||
goto elna_tac_field_access_expression_field
|
||||
end;
|
||||
if is_address then
|
||||
last_instruction := _elna_tac_instruction_create(ElnaTacOperator.copy);
|
||||
_elna_tac_instruction_set_operand(last_instruction, 1, ElnaTacOperand.pseudo, "$unary", 6);
|
||||
_elna_tac_instruction_set_operand(last_instruction, 2, operand_type^, operand_value^, operand_length^)
|
||||
else
|
||||
last_instruction := _elna_tac_instruction_create(ElnaTacOperator.get_address);
|
||||
_elna_tac_instruction_set_operand(last_instruction, 1, ElnaTacOperand.pseudo, "$unary", 6);
|
||||
_elna_tac_instruction_set_operand(last_instruction, 2, operand_type^, operand_value^, operand_length^)
|
||||
end;
|
||||
first_instruction := elna_instruction_list_concatenate(first_instruction, last_instruction);
|
||||
|
||||
last_instruction := _elna_tac_instruction_create(ElnaTacOperator.add);
|
||||
_elna_tac_instruction_set_operand(last_instruction, 1, ElnaTacOperand.pseudo, "$unary", 6);
|
||||
_elna_tac_instruction_set_operand(last_instruction, 2, ElnaTacOperand.immediate, field_offset, 0);
|
||||
_elna_tac_instruction_set_operand(last_instruction, 3, operand_type^, operand_value^, operand_length^);
|
||||
_elna_tac_instruction_set_operand(last_instruction, 3, ElnaTacOperand.pseudo, "$unary", 6);
|
||||
|
||||
operand_type^ := ElnaTacOperand.pseudo;
|
||||
operand_value^ := "$unary";
|
||||
@@ -2845,14 +2857,27 @@ begin
|
||||
index_instructions := elna_instruction_list_concatenate(index_instructions, add_instruction);
|
||||
|
||||
array_instructions := elna_tac_designator(array_access_expression^.array, symbol_table, @is_address, operand_type, operand_value, operand_length);
|
||||
elna_instruction_list_concatenate(offset_instruction, array_instructions);
|
||||
if is_address then
|
||||
array_instructions := _elna_tac_instruction_create(ElnaTacOperator.copy);
|
||||
_elna_tac_instruction_set_operand(array_instructions, 1, ElnaTacOperand.pseudo, "$unary", 6);
|
||||
_elna_tac_instruction_set_operand(array_instructions, 2, operand_type^, operand_value^, operand_length^)
|
||||
else
|
||||
array_instructions := _elna_tac_instruction_create(ElnaTacOperator.get_address);
|
||||
_elna_tac_instruction_set_operand(array_instructions, 1, ElnaTacOperand.pseudo, "$unary", 6);
|
||||
_elna_tac_instruction_set_operand(array_instructions, 2, operand_type^, operand_value^, operand_length^)
|
||||
end;
|
||||
elna_instruction_list_concatenate(offset_instruction, array_instructions);
|
||||
|
||||
operand_type^ := ElnaTacOperand.pseudo;
|
||||
operand_value^ := "$unary";
|
||||
operand_length^ := 6;
|
||||
|
||||
add_instruction := _elna_tac_instruction_create(ElnaTacOperator.add);
|
||||
_elna_tac_instruction_set_operand(add_instruction, 1, operand_type^, operand_value^, operand_length^);
|
||||
_elna_tac_instruction_set_operand(add_instruction, 2, operand_type^, operand_value^, operand_length^);
|
||||
_elna_tac_instruction_set_operand(add_instruction, 3, ElnaTacOperand.pseudo, "$lhs", 4);
|
||||
|
||||
elna_instruction_list_concatenate(offset_instruction, array_instructions);
|
||||
|
||||
return elna_instruction_list_concatenate(index_instructions, add_instruction)
|
||||
end;
|
||||
|
||||
@@ -4171,29 +4196,21 @@ proc elna_tac_variable_declaration(parser_tree: ^ElnaTreeVariableDeclaration);
|
||||
var
|
||||
name: Word;
|
||||
name_length: Word;
|
||||
variable_type: ^ElnaTreeNamedTypeExpression;
|
||||
variable_type: ^ElnaType;
|
||||
result: ^ElnaInstructionDeclaration;
|
||||
variable_info: ^ElnaSymbolTemporaryInfo;
|
||||
begin
|
||||
result := malloc(#size(ElnaInstructionDeclaration));
|
||||
|
||||
result^.next := nil;
|
||||
|
||||
name := parser_tree^.name;
|
||||
name_length := parser_tree^.length;
|
||||
variable_type := parser_tree^._type;
|
||||
variable_info := _symbol_table_lookup(@symbol_table_global, name, name_length);
|
||||
variable_type := variable_info^.variable_type;
|
||||
|
||||
result^.next := nil;
|
||||
result^.name := name;
|
||||
result^.length := name_length;
|
||||
result^.body := variable_type^.size;
|
||||
|
||||
name := variable_type^.name;
|
||||
name_length := variable_type^.length;
|
||||
|
||||
if string_compare("Array", 5, name, name_length) then
|
||||
(* Else we assume this is a zeroed 4096 bytes big array. *)
|
||||
result^.body := 4096
|
||||
else
|
||||
result^.body := 4
|
||||
end;
|
||||
return result
|
||||
end;
|
||||
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user