Step
) to check for
breakpoints or single step mode.
Since the contents of the various
variables of the program can potentially have to be sent to the
user, this procedure Step
must have access to both
their names and values, and must know about their types,
including for local variables within procedures. Therefore, a
symbol table
must be maintained, that will hold a shadow copy of all variables
and parameters used in the program.
For instance, given the following sample program (line numbers have been added to make it easier to locate the original code in the modified version):
01 program Demo; 02 const NbDays = 7; 03 type WeekDays=(Su,Mo,Tu,We,Th,Fr,Sa); 04 Element=record 05 Name: string; 06 Next: ^Element; 07 end; 08 var Num : real 09 S : string; 10 Day : WeekDays; 11 WorkDays : set of WeekDays; 12 Matrix : array['a'..'z',1..10] of integer; 13 Chain : ^Element; 14 begin 15 Num := 3.1415; 16 S := 'Hi there'; 17 Day := Tu; 18 WorkDays := [Mo..Fr]; 19 Matrix['d',3] := 67; 20 new(Chain); 21 Chain.Name := 'Brown'; 22 Chain.Next := nil; 23 end.A declaration will be added after line 11:
11 WorkDays : set of WeekDays; www_WorkDays: WeekDays;to allow the insertion of a loop to scan the values in
WorkDays
whenever this variable is changed.
Similarly, two declarations will be added after line 12:
12 Matrix : array['a'..'z',1..10] of integer; www_Matrix_1: 'a'..'z'; www_Matrix_2: 1..10;to allow the insertion of two embedded loops to scan the values in
Matrix
whenever this variable is changed.
Then, the executable part of the program will look like:
14 begin - code added here to create symbol table entries for objects declared in this block Step; 15 Num := 3.1415; - code added here to (re)define value of 'Num' in symbol table Step; 16 S := 'Hi there'; - code added here to (re)define value of 'S' in symbol table Step; 17 Day := Tu; - code added here to (re)define value of 'Day' in symbol table Step; 18 WorkDays := [Mo..Fr]; - code added here to (re)define value of 'WorkDays' in symbol table (this will be done by checking whether each possible value in WeekDays is present in WorkDays or not) Step; 19 Matrix['d',3] := 67; - code added here to (re)define value of index "3" of substructure "'d'" in structure Matrix. Step; 20 new(Chain); - code added here to indicate that 'Chain' points to a new structure - code added here to create a new entry for 'Chain^' in symbol table - code added here to create a new entry for each component of the 'Chain^' structure. Step; 21 Chain^.Name := 'Brown'; - code added here to (re)define value of '.Name' component of dynamic structure 'Chain^' Step; 22 Chain^.Next := nil; - code added here to (re)define value of '.Next' component of dynamic structure 'Chain^' Step; - before exiting the block, remove all local objects from symbol table 23 end;For the technical reader, full detail of the final code produced for the example above is available, as well as a list of the procedures used in the final code.
All this can seem quite complicated, but it can easily be automated. A tool is currently being developed to parse Pascal code and to add all these calls automatically to the original code. Of course, all these lines that are added to the original code will not be displayed to the user.
For applications written in some interpreted language,
for which the interpreter gives the programmer direct access
to the interpreter's symbol table, the modifications of the
original code would be much simpler than in the scheme we just
described, since only calls to the Step
procedure
need to be added to the code.
Site Hosting: Bronco