Skip to content

Commit efe4e46

Browse files
committed
AST WIP
1 parent 2f46d98 commit efe4e46

3 files changed

Lines changed: 63 additions & 38 deletions

File tree

src/ps_ast_debug.c

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616

1717
/** @brief Global flag to enable/disable AST debug output */
1818
bool ps_ast_debug = true;
19+
bool ps_ast_debug_prefix = false;
1920

2021
char *ps_ast_node_get_group_name(ps_ast_node_group group)
2122
{
@@ -99,7 +100,8 @@ void ps_ast_debug_line(const char *format, ...) // NOSONAR
99100
return;
100101
va_list args;
101102
va_start(args, format);
102-
// fprintf(stderr, "AST_DEBUG\t");
103+
if (ps_ast_debug_prefix)
104+
fprintf(stderr, "AST_DEBUG\t");
103105
vfprintf(stderr, format, args); // NOSONAR
104106
fprintf(stderr, "\n");
105107
va_end(args);

src/ps_ast_execute.c

Lines changed: 11 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -89,13 +89,13 @@ bool ps_ast_run_statement(ps_interpreter *interpreter, const ps_ast_node *statem
8989
case PS_AST_IF:
9090
return ps_ast_run_if(interpreter, (const ps_ast_if *)statement);
9191
case PS_AST_WHILE:
92-
return ps_ast_run_while(interpreter, (ps_ast_while *)statement);
92+
return ps_ast_run_while(interpreter, (const ps_ast_while *)statement);
9393
case PS_AST_REPEAT:
94-
return ps_ast_run_repeat(interpreter, (ps_ast_repeat *)statement);
94+
return ps_ast_run_repeat(interpreter, (const ps_ast_repeat *)statement);
9595
case PS_AST_FOR:
96-
return ps_ast_run_for(interpreter, (ps_ast_for *)statement);
96+
return ps_ast_run_for(interpreter, (const ps_ast_for *)statement);
9797
case PS_AST_PROCEDURE_CALL:
98-
return ps_ast_run_procedure_call(interpreter, (ps_ast_call *)statement);
98+
return ps_ast_run_procedure_call(interpreter, (const ps_ast_call *)statement);
9999
default:
100100
ps_ast_debug_line("Error: unexpected statement kind %d\n", statement->kind);
101101
return false;
@@ -278,23 +278,23 @@ bool ps_ast_eval_expression(ps_interpreter *interpreter, const ps_ast_node *expr
278278
assert(result != NULL);
279279
if (!ps_ast_node_check_group(expression, PS_AST_EXPRESSION))
280280
return false;
281-
ps_ast_debug_line("EXPRESSION @%p", (void *)expression);
281+
ps_ast_debug_line("EXPRESSION @%p", (const void *)expression);
282282
switch (expression->kind)
283283
{
284284
case PS_AST_RVALUE_CONST:
285-
ps_ast_value *rvalue = (ps_ast_value *)expression;
285+
ps_ast_value *rvalue = (const ps_ast_value *)expression;
286286
ps_ast_debug_line(" - Value: %s", ps_value_get_display_string(&rvalue->value, 0, 0));
287287
if (!ps_interpreter_copy_value(interpreter, &rvalue->value, &result->value))
288288
return false;
289289
break;
290290
case PS_AST_RVALUE_SIMPLE:
291-
ps_ast_variable_simple *variable_simple = (ps_ast_variable_simple *)expression;
291+
ps_ast_variable_simple *variable_simple = (const ps_ast_variable_simple *)expression;
292292
ps_ast_debug_line(" - Variable: %s", variable_simple->variable->name);
293293
if (!ps_interpreter_copy_value(interpreter, variable_simple->variable->value, &result->value))
294294
return false;
295295
break;
296296
case PS_AST_RVALUE_ARRAY:
297-
ps_ast_variable_array *variable_array = (ps_ast_variable_array *)expression;
297+
ps_ast_variable_array *variable_array = (const ps_ast_variable_array *)expression;
298298
ps_ast_debug_line(" - Array variable: %s[%d]", variable_array->variable->name, variable_array->n_indexes);
299299
ps_interpreter_set_message(interpreter, "TODO! Array access not implemented yet");
300300
interpreter->error = PS_ERROR_NOT_IMPLEMENTED;
@@ -305,7 +305,7 @@ bool ps_ast_eval_expression(ps_interpreter *interpreter, const ps_ast_node *expr
305305
.value.allocated = false,
306306
.value.type = &ps_system_none,
307307
.value.data = {0}};
308-
ps_ast_unary_operation *unary_operation = (ps_ast_unary_operation *)expression;
308+
const ps_ast_unary_operation *unary_operation = (const ps_ast_unary_operation *)expression;
309309
ps_ast_debug_line(" - Unary operation: %s", ps_operator_unary_get_name(unary_operation->operator));
310310
// first evaluate operand, then apply operator to it
311311
if (!ps_ast_eval_expression(interpreter, unary_operation->operand, &operand))
@@ -314,7 +314,7 @@ bool ps_ast_eval_expression(ps_interpreter *interpreter, const ps_ast_node *expr
314314
return false;
315315
break;
316316
case PS_AST_BINARY_OPERATION:
317-
ps_ast_binary_operation *binary_operation = (ps_ast_binary_operation *)expression;
317+
const ps_ast_binary_operation *binary_operation = (const ps_ast_binary_operation *)expression;
318318
ps_ast_debug_line(" - Binary operation: %s", ps_operator_binary_get_name(binary_operation->operator));
319319
// first evaluate operands, then apply operator to them
320320
ps_ast_value left = {.group = PS_AST_EXPRESSION,
@@ -332,12 +332,11 @@ bool ps_ast_eval_expression(ps_interpreter *interpreter, const ps_ast_node *expr
332332
return false;
333333
break;
334334
case PS_AST_FUNCTION_CALL:
335-
ps_ast_call *function_call = (ps_ast_call *)expression;
335+
const ps_ast_call *function_call = (const ps_ast_call *)expression;
336336
ps_ast_debug_line(" - Function call: %s", function_call->executable->name);
337337
ps_interpreter_set_message(interpreter, "TODO! Function calls not implemented yet");
338338
interpreter->error = PS_ERROR_NOT_IMPLEMENTED;
339339
return false;
340-
break;
341340
default:
342341
ps_interpreter_set_message(interpreter, "Unexpected expression kind %s (%d)\n",
343342
ps_ast_node_get_kind_name(expression->kind), expression->kind);

src/ps_ast_test.c

Lines changed: 49 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -84,6 +84,7 @@ bool ps_ast_test_delete_block_program(ps_ast_block *block_program)
8484
ps_ast_debug_line("Free the PROGRAM block node");
8585
block_program = (ps_ast_block *)ps_ast_free_block(block_program);
8686
ASSERT_RETURN_FALSE(block_program == NULL);
87+
return true;
8788
}
8889

8990
ps_interpreter *ps_ast_test_create_interpreter(ps_ast_block *block_program)
@@ -114,6 +115,7 @@ bool ps_ast_test_delete_interpreter(ps_interpreter *interpreter, ps_ast_block *b
114115
ps_ast_debug_line("Free interpreter");
115116
interpreter = ps_interpreter_free(interpreter);
116117
ASSERT_RETURN_FALSE(interpreter == NULL);
118+
return true;
117119
}
118120

119121
/**
@@ -157,9 +159,10 @@ bool ps_ast_test_minimal()
157159
* @brief Test Assignment Pascal program
158160
* L/C 123456789012345678901234567890123456789012345678901234567890
159161
* 1 Program Assignment;
160-
* 2 Var I: Integer;
162+
* 2 Var I, J: Integer;
161163
* 3 Begin
162-
* 4 I := 42 * 2;
164+
* 4 I := 21 * 2;
165+
* 4 J := I;
163166
* 5 End.
164167
*/
165168
bool ps_ast_test_assignment()
@@ -173,37 +176,50 @@ bool ps_ast_test_assignment()
173176
ps_interpreter *interpreter = ps_ast_test_create_interpreter(block_program);
174177
ASSERT_RETURN_FALSE(interpreter != NULL);
175178

176-
ps_ast_debug_line("Create a variable symbol I of type Integer and add it to the symbol tables");
177-
ps_value i_value = {.allocated = false, .type = &ps_system_integer, .data.i = 0};
178-
const ps_symbol *symbol_i = ps_symbol_alloc(PS_SYMBOL_KIND_VARIABLE, "I", &i_value);
179-
result = ps_interpreter_add_symbol(interpreter, (ps_symbol *)symbol_i);
179+
ps_ast_debug_line("Create variable symbols I ² J of type Integer and add them to the symbol tables");
180+
ps_value value_i = {.allocated = false, .type = &ps_system_integer, .data.i = 0};
181+
ps_symbol *symbol_i = ps_symbol_alloc(PS_SYMBOL_KIND_VARIABLE, "I", &value_i);
182+
result = ps_interpreter_add_symbol(interpreter, symbol_i);
183+
ASSERT_RETURN_FALSE(result);
184+
ps_value value_j = {.allocated = false, .type = &ps_system_integer, .data.i = 0};
185+
ps_symbol *symbol_j = ps_symbol_alloc(PS_SYMBOL_KIND_VARIABLE, "J", &value_j);
186+
result = ps_interpreter_add_symbol(interpreter, symbol_j);
180187
ASSERT_RETURN_FALSE(result);
181-
ps_symbol_table_error error = ps_symbol_table_add(block_program->symbols, (ps_symbol *)symbol_i);
188+
ps_symbol_table_error error = ps_symbol_table_add(block_program->symbols, symbol_i);
182189
ASSERT_RETURN_FALSE(error == PS_SYMBOL_TABLE_ERROR_NONE);
183-
block_program->n_vars = 1;
190+
error = ps_symbol_table_add(block_program->symbols, symbol_j);
191+
ASSERT_RETURN_FALSE(error == PS_SYMBOL_TABLE_ERROR_NONE);
192+
block_program->n_vars = 2;
184193

185-
ps_ast_debug_line("Create a statement list with one statement");
186-
// a PROCEDURE CALL to Writeln with one argument: a string value "Hello, World!"
187-
block_program->statement_list = ps_ast_create_statement_list(3, 5, 1);
194+
ps_ast_debug_line("Create a statement list with 2 statements");
195+
block_program->statement_list = ps_ast_create_statement_list(3, 5, 2);
188196
ASSERT_RETURN_FALSE(block_program->statement_list != NULL);
189197

190-
ps_ast_debug_line("Create the assignment statement I := 42 * 2;");
191-
ps_ast_variable_simple *variable_simple =
192-
ps_ast_create_variable_simple(3, 5, PS_AST_LVALUE_SIMPLE, (ps_symbol *)symbol_i);
193-
ASSERT_RETURN_FALSE(variable_simple != NULL);
194-
ps_value value_u_42 = {.allocated = false, .type = &ps_system_unsigned, .data.u = 42};
195-
ps_ast_value *rvalue_u_42 = ps_ast_create_rvalue_const(3, 10, value_u_42);
196-
ASSERT_RETURN_FALSE(rvalue_u_42 != NULL);
198+
ps_ast_debug_line("Create the assignment statement I := 21 * 2;");
199+
ps_ast_variable_simple *variable_i = ps_ast_create_variable_simple(3, 5, PS_AST_LVALUE_SIMPLE, symbol_i);
200+
ASSERT_RETURN_FALSE(variable_i != NULL);
201+
ps_value value_u_21 = {.allocated = false, .type = &ps_system_unsigned, .data.u = 21};
202+
ps_ast_value *rvalue_u_21 = ps_ast_create_rvalue_const(3, 10, value_u_21);
203+
ASSERT_RETURN_FALSE(rvalue_u_21 != NULL);
197204
ps_value value_u_2 = {.allocated = false, .type = &ps_system_unsigned, .data.u = 2};
198205
ps_ast_value *rvalue_u_2 = ps_ast_create_rvalue_const(3, 15, value_u_2);
199206
ASSERT_RETURN_FALSE(rvalue_u_2 != NULL);
200207
ps_ast_binary_operation *mul_operation =
201-
ps_ast_create_binary_operation(3, 13, PS_OP_MUL, (ps_ast_node *)rvalue_u_42, (ps_ast_node *)rvalue_u_2);
208+
ps_ast_create_binary_operation(3, 13, PS_OP_MUL, (ps_ast_node *)rvalue_u_21, (ps_ast_node *)rvalue_u_2);
202209
ASSERT_RETURN_FALSE(mul_operation != NULL);
203-
ps_ast_assignment *assignment =
204-
ps_ast_create_assignment(3, 5, (ps_ast_node *)variable_simple, (ps_ast_node *)mul_operation);
205-
ASSERT_RETURN_FALSE(assignment != NULL);
206-
block_program->statement_list->statements[0] = (ps_ast_node *)assignment;
210+
ps_ast_assignment *assignment_i =
211+
ps_ast_create_assignment(3, 5, (ps_ast_node *)variable_i, (ps_ast_node *)mul_operation);
212+
ASSERT_RETURN_FALSE(assignment_i != NULL);
213+
block_program->statement_list->statements[0] = (ps_ast_node *)assignment_i;
214+
215+
ps_ast_debug_line("Create the assignment statement J := I;");
216+
ps_ast_variable_simple *variable_j = ps_ast_create_variable_simple(4, 5, PS_AST_LVALUE_SIMPLE, symbol_j);
217+
ASSERT_RETURN_FALSE(variable_j != NULL);
218+
ps_ast_variable_simple *rvalue_i = ps_ast_create_variable_simple(4, 10, PS_AST_RVALUE_SIMPLE, symbol_i);
219+
ps_ast_assignment *assignment_j =
220+
ps_ast_create_assignment(4, 5, (ps_ast_node *)variable_j, (ps_ast_node *)rvalue_i);
221+
ASSERT_RETURN_FALSE(assignment_i != NULL);
222+
block_program->statement_list->statements[1] = (ps_ast_node *)assignment_j;
207223

208224
ps_ast_debug_line("Debug print the program");
209225
ps_ast_debug = true;
@@ -217,11 +233,19 @@ bool ps_ast_test_assignment()
217233
ps_ast_debug_line("Interpreter message: %s", interpreter->message);
218234
ASSERT_RETURN_FALSE(result);
219235

220-
ps_ast_debug_line("Check that variable I has the expected value 84");
236+
ps_ast_debug_line("Check that variable I has the expected value 42");
221237
ASSERT_RETURN_FALSE(symbol_i->value != NULL);
222238
ASSERT_RETURN_FALSE(symbol_i->value->type == &ps_system_integer);
223239
ps_ast_debug_line("Variable I value: %d", symbol_i->value->data.i);
224-
ASSERT_RETURN_FALSE(symbol_i->value->data.i == 84);
240+
ASSERT_RETURN_FALSE(symbol_i->value->data.i == 42);
241+
242+
ps_ast_debug_line("Check that variable J has the expected value 42");
243+
ASSERT_RETURN_FALSE(symbol_j->value != NULL);
244+
ASSERT_RETURN_FALSE(symbol_j->value->type == &ps_system_integer);
245+
ps_ast_debug_line("Variable J value: %d", symbol_i->value->data.i);
246+
ASSERT_RETURN_FALSE(symbol_j->value->data.i == 42);
247+
248+
ps_symbol_table_dump(stderr, NULL, block_program->symbols);
225249

226250
ps_ast_debug_line("Free symbol table for the program %s", block_program->name);
227251
ps_memory_free(PS_MEMORY_AST, block_program->symbols);

0 commit comments

Comments
 (0)