Saturday, December 6, 2014

Pre-Table – Unary Operator Detection

The expression information structure within the table entry contained a unary code member, which was used to determine if a code was or could be a unary operator.  This member contained the code of the unary operator or a null code.  Only four codes contained a non-null code, which included the two negate codes (double and integer), the NOT operator, and the main subtract code.  The subtract code contained the first negate code, but the others contained their own code.

This was not efficient use of the member as it was only used for four codes especially considering there was another way to determine a unary operator, namely checking if token type is Operator and the number of operands is one.

This required a change in how the negate and subtract operators are associated with each other.  Originally these codes were not associated as the unary code member was used to get from the subtract code to the negate code.  Without the unary code member, an association was needed.  It did not make sense and was problematic to associate the negate code to the subtract code, which already had a number of associated codes.

Therefore the subtract code was associated with the negate code as a secondary associated code (the negate code already has the integer negate code associated to it).  Making it the second associated code makes sense as the subtract has two operands.  This change required some changes with how the translator handles unary operators.

When getting an operand, the translator get expression routine checked if the current token was a unary operator, and if it was, changed it to a unary operator.  Now it just checks if the current token is not a unary operator before calling the get operand routine.  When getting an operator, if the operator was a unary operator, an error was thrown immediately.  This was changed to check if the unary operator has a secondary associated code (a binary operator), it if it does, the token is changed to the secondary associated code, otherwise an error is thrown as before.

The table initialization that sets the expected data type member was changed to look through the primary associated codes only for unary operator instead of the secondary associated codes.  There was an is unary operator function definition in the table class definition that was not used and didn't have a function, so it was removed.  The unary code argument was removed from all of the expression info constructor calls.

[branch table commit b472f6a36d]

Pre-Table – Sub-String Assignments

In researching the requirements for the new table design, specifically how to implement associated codes (which will be renamed alternate codes), there was an issue with the associated codes for sub-string assignments (LEFT$, MID$ and RIGHT$).

The sub-string assignment codes are the first associated code for the sub-string codes.  The sub-string assignment-keep codes are the first associated code of the sub-string assignment codes.  For recreation, the original sub-string code was the second associated code for each of these assignment codes.  This was necessary since the sub-string code contained the actual number of arguments as the sub-string assignment codes contain only two arguments (one for the value and one for the reference being assigned).

This circular association back to the original sub-string code was going to be a problem with the new table design and so the sub-string code associated were removed.  The first change made to the sub-string assignment table entries was to put back the original sub-string keyword name.  Since the debug name is the combination of the primary and secondary names, the secondary names were changed to remove redundancy, for example, the debug name for AssignLeft changes to LEFT$(Assign.  The affected expected test outputs were updated accordingly.

The assign string recreate function was modified to use the keyword name to look up the original sub-string code instead of using the second associated code for the sub-string assignment codes.  This caused a problem with the MID3 codes as the MID2 code was found, which contained the wrong number of arguments.  This was resolved by adding the Multiple table flag to the MID3 codes.  When this flag is set, the sub-string code found is incremented to the next code.  This change caused a problem during table initialization checking, which was modified to only check Multiple flagged entries if the Reference flag is not also set.

The assign string recreate function was also using the fact that the second associated index was set zero to detect an assignment-keep code (which are used in string list assignment statements).  The string built so far needs to be put back onto the recreation stack.  With the above changes, the assignment-keep codes no longer have associated codes.  This was resolved by adding a new Keep table flag to identify the assignment-keep codes.

[branch table commit f0c7ebdacd]

Pre-Table – Maximum Checks

There were two constants defined in the table source file, one for the maximum number of operands and one for the maximum number of associated codes.  During table initialization, while it is iterating over all of the table entries, it looks for the largest operand count and associated code count for any entry.  If these largest values are larger than the maximum, then a table initialization error occurs (the application then aborts).

I was not able to determine why these constants and checks were put in.  There is nothing that necessarily limits the number of operands or associated codes.  These maximum constants were only used for these checks.  Therefore, these constants and checks were removed.

[branch table commit 489c59904c]