Skip to content

Commit 2372082

Browse files
committed
array value access & assignment OK?
1 parent be50871 commit 2372082

9 files changed

Lines changed: 182 additions & 80 deletions

examples/030-array.pas

Lines changed: 0 additions & 24 deletions
This file was deleted.

examples/030-array0.pas

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
(*
2+
This file is part of the PascalScript Pascal interpreter.
3+
SPDX-FileCopyrightText: 2026 Christophe 'CHiPs' Petit <chips44@gmail.com>
4+
SPDX-License-Identifier: LGPL-3.0-or-later
5+
*)
6+
Program Arrays;
7+
8+
Type
9+
// NumberArray = Array[1..10] Of Integer;
10+
NumberArray = Array['A'..'F'] Of Integer;
11+
12+
Var
13+
Numbers: NumberArray;
14+
// I: Integer;
15+
I: Char;
16+
N: Integer;
17+
18+
Begin
19+
// For I := 1 To 10 Do
20+
N := 10;
21+
For I := 'A' To 'F' Do
22+
Begin
23+
Numbers[I] := N;
24+
N := N + 1;
25+
End;
26+
// For I := 1 To 10 Do
27+
For I := 'A' To 'F' Do
28+
WriteLn(I:2, ' * ', I:2, ' = ', Numbers[I]:3);
29+
End.

examples/031-array1.pas

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
(*
2+
This file is part of the PascalScript Pascal interpreter.
3+
SPDX-FileCopyrightText: 2026 Christophe 'CHiPs' Petit <chips44@gmail.com>
4+
SPDX-License-Identifier: LGPL-3.0-or-later
5+
*)
6+
Program Arrays;
7+
8+
Type
9+
NumberArray = Array['A'..'F'] Of Integer;
10+
11+
Var
12+
Numbers: NumberArray;
13+
C: Char;
14+
N: Integer;
15+
16+
Begin
17+
Numbers['C'] := 42;
18+
N := 10;
19+
For C := 'A' To 'F' Do
20+
Begin
21+
Numbers[C] := N;
22+
N := N + 1;
23+
End;
24+
For C := 'A' To 'F' Do
25+
WriteLn(C:2, ' = ', Numbers[C]:3);
26+
End.

examples/032-array2.pas

Lines changed: 73 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,73 @@
1+
(*
2+
This file is part of the PascalScript Pascal interpreter.
3+
SPDX-FileCopyrightText: 2026 Christophe 'CHiPs' Petit <chips44@gmail.com>
4+
SPDX-License-Identifier: LGPL-3.0-or-later
5+
*)
6+
Program Arrays;
7+
8+
Type
9+
TIndex1 = 1..10;
10+
NumberArray = Array[1..10] Of Integer;
11+
StringArray = Array[1..10] Of String;
12+
13+
{ Same as Free Pascal SysUtils }
14+
Function IntToStr(N: Integer): String;
15+
Var S: String;
16+
Digit: Integer;
17+
Begin
18+
{ Convert an Integer to a string }
19+
{ This is a simplified version of the SysUtils.IntToStr function }
20+
{ It does not handle all edge cases, but is sufficient for this example }
21+
If N = 0 Then
22+
S := '0'
23+
Else
24+
Begin
25+
S := '';
26+
If N < 0 Then
27+
Begin
28+
N := -N;
29+
S := '-';
30+
End;
31+
While N > 0 Do
32+
Begin
33+
Digit := N Mod 10;
34+
S := Chr(Ord('0') + Digit) + S;
35+
N := N Div 10;
36+
End;
37+
End;
38+
IntToStr := S;
39+
End;
40+
41+
function Pad(N: Integer, w: Integer): String;
42+
Var S: String;
43+
Begin
44+
S := IntToStr(N);
45+
while Length(S) < w do
46+
Begin
47+
S := '0' + S;
48+
End;
49+
Pad := S;
50+
End;
51+
52+
Var
53+
Numbers: NumberArray;
54+
Strings: StringArray;
55+
I, N: Integer;
56+
S: String;
57+
58+
Begin
59+
N := 1;
60+
For I := 1 To 10 Do
61+
Begin
62+
Numbers[I] := N;
63+
Strings[I] := {'#' + Pad(I, 2) + ' ' + }IntToStr(N);
64+
N := N * 2;
65+
End;
66+
WriteLn('# | Number | String ');
67+
WriteLn('---|--------|--------');
68+
For I := 1 To 10 Do
69+
Begin
70+
S := Strings[I];
71+
WriteLn(I:2, ' | ', Numbers[I]:6, ' | ', S);
72+
End;
73+
End.

src/pascalscript.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@
2020
#include "ps_symbol_table.h"
2121
#include "ps_version.h"
2222

23-
#define DEBUGGER_SOURCE "examples/030-array.pas"
23+
#define DEBUGGER_SOURCE "examples/031-array1.pas"
2424
// #define DEBUGGER_SOURCE "examples/005-first.pas"
2525

2626
// Runtime options

src/ps_array.c

Lines changed: 5 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ ps_type_definition *ps_array_get_type_def(const ps_symbol *symbol)
5252
ps_symbol_debug(stderr, "PS_ARRAY_GET_TYPE_DEF, => array : ", symbol);
5353
if (symbol == NULL || symbol->value == NULL || symbol->value->type == NULL)
5454
return NULL;
55-
ps_symbol *symbol2;
55+
const ps_symbol *symbol2;
5656
if (symbol->kind == PS_SYMBOL_KIND_TYPE_DEFINITION)
5757
{
5858
symbol2 = symbol;
@@ -83,17 +83,14 @@ ps_symbol *ps_array_get_subrange(const ps_symbol *array_type)
8383
{
8484
if (ps_array_debug)
8585
ps_symbol_debug(stderr, "ps_array_get_subrange, array_type: ", array_type);
86-
// WORKS(?) => array->value->type->value->data.t->def.a.subrange
87-
ps_symbol_debug(stderr, "GET_SUBRANGE\tARRAY\t\t", array_type);
88-
ps_value_debug(stderr, "GET_SUBRANGE\tVALUE\t\t", array_type->value);
89-
ps_symbol_debug(stderr, "GET_SUBRANGE\tTYPE\t\t", array_type->value->type);
90-
ps_value_debug(stderr, "GET_SUBRANGE\tTYPE\t\t", array_type->value->type->value);
9186
const ps_type_definition *type_def = ps_array_get_type_def(array_type);
92-
ps_type_definition_debug(stderr, "GET_SUBRANGE\tTYPE_DEF\t", type_def);
87+
if (ps_array_debug)
88+
ps_type_definition_debug(stderr, "GET_SUBRANGE\tTYPE_DEF\t", type_def);
9389
if (type_def == NULL)
9490
return NULL;
9591
ps_symbol *subrange = type_def->def.a.subrange;
96-
ps_symbol_debug(stderr, "GET_SUBRANGE\tSUBRANGE\t", subrange);
92+
if (ps_array_debug)
93+
ps_symbol_debug(stderr, "GET_SUBRANGE\tSUBRANGE\t", subrange);
9794
return subrange;
9895
}
9996

@@ -141,13 +138,9 @@ ps_error ps_array_set_value(ps_symbol *array_var, const ps_value *index, const p
141138
array_var->value->data.a->values == NULL)
142139
return PS_ERROR_INVALID_PARAMETERS;
143140
const ps_symbol *subrange = ps_array_get_subrange(array_var->value->type);
144-
ps_symbol_debug(stderr, "SET_VALUE ", subrange);
145-
ps_type_definition_debug(stderr, "SET_VALUE ", subrange->value->data.t);
146141
// Get offset from index
147-
fprintf(stderr, "11111 OFFSET\n");
148142
ps_array_debug = true;
149143
ps_unsigned offset = ps_type_definition_get_subrange_offset(subrange->value->data.t, index);
150-
fprintf(stderr, "22222 offset=%u, count=%u\n", offset, array_var->value->data.a->count);
151144
if (offset >= array_var->value->data.a->count)
152145
return PS_ERROR_INVALID_SUBRANGE;
153146
ps_array_debug = false;

src/ps_type_definition.c

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -175,7 +175,7 @@ ps_unsigned ps_type_definition_get_subrange_count(const ps_type_definition *subr
175175

176176
ps_unsigned ps_type_definition_get_subrange_offset(const ps_type_definition *subrange, const ps_value *index)
177177
{
178-
bool debug = true;
178+
bool debug = false;
179179
ps_unsigned offset = PS_UNSIGNED_MAX;
180180
if (subrange->type == PS_TYPE_SUBRANGE)
181181
{
@@ -192,7 +192,7 @@ ps_unsigned ps_type_definition_get_subrange_offset(const ps_type_definition *sub
192192
{
193193
case PS_TYPE_CHAR:
194194
// 'C' from 'A'..'Z' => Ord('C') - Ord('A') => 2
195-
if (ps_value_get_type(index) == PS_TYPE_CHAR && index->data.c >= subrange->def.g.c.min &&
195+
if (ps_value_get_base(index) == PS_TYPE_CHAR && index->data.c >= subrange->def.g.c.min &&
196196
index->data.c <= subrange->def.g.c.max)
197197
offset = index->data.c - subrange->def.g.c.min;
198198
break;
@@ -220,7 +220,7 @@ ps_unsigned ps_type_definition_get_subrange_offset(const ps_type_definition *sub
220220
case PS_TYPE_INTEGER:
221221
// 3 from -4..4 => 3 - -4 => 7
222222
// 0..8
223-
if (ps_value_get_type(index) == PS_TYPE_INTEGER && index->data.i >= subrange->def.g.i.min &&
223+
if (ps_value_get_base(index) == PS_TYPE_INTEGER && index->data.i >= subrange->def.g.i.min &&
224224
index->data.i <= subrange->def.g.i.max)
225225
offset = index->data.i - subrange->def.g.i.min;
226226
break;

src/ps_visit_expression.c

Lines changed: 11 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -276,37 +276,33 @@ bool ps_visit_term(ps_interpreter *interpreter, ps_interpreter_mode mode, ps_val
276276
bool ps_visit_factor_identifier_array(ps_interpreter *interpreter, ps_interpreter_mode mode, const ps_symbol *symbol,
277277
ps_value *result)
278278
{
279-
// interpreter->debug = DEBUG_VERBOSE;
280279
VISIT_BEGIN("FACTOR", "ARRAY");
281280

282-
ps_type_definition *type_def = ps_array_get_type_def(symbol->value->type);
281+
const ps_type_definition *type_def = ps_array_get_type_def(symbol->value->type);
283282
if (type_def == NULL)
284283
RETURN_ERROR(PS_ERROR_TYPE_MISMATCH)
285284
READ_NEXT_TOKEN
286285
if (lexer->current_token.type == PS_TOKEN_LEFT_BRACKET)
287286
{
288-
ps_value index = {.type = type_def->def.a.item_type, .allocated = false, .data.v = NULL};
289-
// clang-format off
290-
ps_symbol_debug (stderr, "ARRAY ", symbol);
291-
ps_value_debug (stderr, "INDEX ", &index);
292-
ps_symbol_debug (stderr, "ITEM_TYPE ", type_def->def.a.item_type);
293-
ps_symbol_debug (stderr, "SUBRANGE1 ", type_def->def.a.subrange);
294-
ps_type_definition_debug(stderr, "SUBRANGE2 ", type_def->def.a.subrange->value->data.t);
295-
// clang-format on
287+
ps_value index = {.type = &ps_system_none/*type_def->def.a.item_type*/, .allocated = false, .data.v = NULL};
296288
READ_NEXT_TOKEN
297289
if (!ps_visit_expression(interpreter, mode, &index))
298290
{
299291
ps_interpreter_set_message(interpreter, "Index is invalid");
300292
TRACE_ERROR("INDEX")
301293
}
302294
EXPECT_TOKEN(PS_TOKEN_RIGHT_BRACKET)
303-
ps_error error = ps_array_get_value(symbol, &index, result, interpreter->range_check);
304-
if (error != PS_ERROR_NONE)
295+
if (mode == MODE_EXEC)
305296
{
306-
ps_interpreter_set_message(interpreter, "Can't get array value for index %s",
307-
ps_value_get_debug_string(&index));
308-
RETURN_ERROR(error)
297+
ps_error error = ps_array_get_value(symbol, &index, result, interpreter->range_check);
298+
if (error != PS_ERROR_NONE)
299+
{
300+
ps_interpreter_set_message(interpreter, "Can't get array value for index %s",
301+
ps_value_get_debug_string(&index));
302+
RETURN_ERROR(error)
303+
}
309304
}
305+
READ_NEXT_TOKEN
310306
}
311307

312308
VISIT_END("OK")
@@ -342,7 +338,6 @@ bool ps_visit_factor_identifier(ps_interpreter *interpreter, ps_interpreter_mode
342338
symbol->name, ps_symbol_get_kind_name(symbol->kind),
343339
ps_type_definition_get_name(symbol->value->type->value->data.t));
344340
}
345-
// fprintf(stderr, "ARRAY? %s\n", ps_value_is_array(symbol->value) ? "YES" : "NO");
346341
if (ps_value_is_array(symbol->value))
347342
{
348343
if (!ps_visit_factor_identifier_array(interpreter, mode, symbol, result))

src/ps_visit_statement.c

Lines changed: 34 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,38 @@ bool ps_visit_compound_statement(ps_interpreter *interpreter, ps_interpreter_mod
8686
// VISIT_END("OK");
8787
// }
8888

89+
bool ps_visit_assignment_array(ps_interpreter *interpreter, ps_interpreter_mode mode, ps_symbol *variable)
90+
{
91+
VISIT_BEGIN("ASSIGNMENT", "ARRAY")
92+
93+
ps_value result = {.type = &ps_system_none, .data.v = NULL};
94+
ps_value index = {.type = &ps_system_none, .data.v = NULL};
95+
96+
EXPECT_TOKEN(PS_TOKEN_LEFT_BRACKET)
97+
READ_NEXT_TOKEN
98+
index.type = variable->value->type->value->data.t->def.a.subrange;
99+
if (!ps_visit_expression(interpreter, mode, &index))
100+
TRACE_ERROR("INDEX")
101+
EXPECT_TOKEN(PS_TOKEN_RIGHT_BRACKET)
102+
READ_NEXT_TOKEN
103+
EXPECT_TOKEN(PS_TOKEN_ASSIGN)
104+
READ_NEXT_TOKEN
105+
result.type = variable->value->type->value->data.t->def.a.item_type;
106+
if (!ps_visit_expression(interpreter, mode, &result))
107+
TRACE_ERROR("EXPRESSION1")
108+
if (mode == MODE_EXEC)
109+
{
110+
ps_error error = ps_array_set_value(variable, &index, &result, interpreter->range_check);
111+
if (error != PS_ERROR_NONE)
112+
{
113+
interpreter->error = error;
114+
TRACE_ERROR("ARRAY_ASSIGN")
115+
}
116+
}
117+
118+
VISIT_END("OK")
119+
}
120+
89121
/**
90122
* Visit assignment:
91123
* IDENTIFIER := EXPRESSION
@@ -98,11 +130,9 @@ bool ps_visit_compound_statement(ps_interpreter *interpreter, ps_interpreter_mod
98130
*/
99131
bool ps_visit_assignment(ps_interpreter *interpreter, ps_interpreter_mode mode, ps_symbol *variable)
100132
{
101-
// interpreter->debug = DEBUG_TRACE;
102133
VISIT_BEGIN("ASSIGNMENT", "")
103134

104135
ps_value result = {.type = &ps_system_none, .data.v = NULL};
105-
ps_value index = {.type = &ps_system_none, .data.v = NULL};
106136

107137
if (variable->kind == PS_SYMBOL_KIND_CONSTANT)
108138
{
@@ -122,28 +152,8 @@ bool ps_visit_assignment(ps_interpreter *interpreter, ps_interpreter_mode mode,
122152
if (ps_value_get_type(variable->value) == PS_TYPE_ARRAY)
123153
{
124154
// => array[index] := expression
125-
EXPECT_TOKEN(PS_TOKEN_LEFT_BRACKET)
126-
READ_NEXT_TOKEN
127-
index.type = variable->value->type->value->data.t->def.a.subrange;
128-
if (!ps_visit_expression(interpreter, mode, &index))
129-
TRACE_ERROR("INDEX")
130-
EXPECT_TOKEN(PS_TOKEN_RIGHT_BRACKET)
131-
READ_NEXT_TOKEN
132-
EXPECT_TOKEN(PS_TOKEN_ASSIGN)
133-
READ_NEXT_TOKEN
134-
result.type = variable->value->type->value->data.t->def.a.item_type;
135-
if (!ps_visit_expression(interpreter, mode, &result))
136-
TRACE_ERROR("EXPRESSION1")
137-
ps_value_debug(stderr, "*** RESULT ", &result);
138-
ps_value_debug(stderr, "*** INDEX ", &index);
139-
ps_error error = ps_array_set_value(variable, &index, &result, interpreter->range_check);
140-
if (error != PS_ERROR_NONE)
141-
{
142-
interpreter->error = error;
143-
TRACE_ERROR("ARRAY_ASSIGN")
144-
}
145-
fprintf(stderr, "\n\n*** HERE! ***\n\n");
146-
ps_array_debug_values(stderr, variable);
155+
if (!ps_visit_assignment_array(interpreter, mode, variable))
156+
TRACE_ERROR("ARRAY")
147157
}
148158
else
149159
{

0 commit comments

Comments
 (0)