Sunday, August 18, 2013

New Translator – INPUT Statements (Tagged)

The implementation of INPUT statement translation went fairly quickly using the new translation routines.  Only a couple of days were required using the new command centric translator routines, compared to well over a month using the old token centric translator routines.  This should be an indicator how the implementation should go for the rest of the BASIC commands.

The INPUT statements implementation in the new translator is now complete and version v0.4.4 has been tagged.  All tests still pass with the old translator routines.  All translator tests pass with the new translator routines with the exception of the REM statements (test #15) as this has not been implemented yet.  Some slight cleanup was done with the latest commit along with updating the files for v0.4.4.  Implementation of REM statements and operators can now commence in the new translator.

[commit 00815b4bac]

New INPUT Translation

The new INPUT translate routine required several local variables besides a status variable, including an index into the RPN output list of the InputBegin or InputBeginStr code where to insert the input parse codes (see below), a done flag, and an input token.  This routine will be used for both the INPUT and INPUT PROMPT commands.

For the INPUT command a new token is created for the InputBegin code.  For the INPUT PROMPT command, the get expression routine is called to get a string expression.  The done stack top item is dropped and the terminating token is checked.  If the terminating token is a comma, the 'Question' sub-code is set in the token, else if the token is not a semicolon, the "expecting operator, semicolon or comma" error is returned.  The token is set to the InputBeginStr code.

The index to where the input begin token will be inserted into the RPN output list is obtained by the current count of the number of items in the list.  The token is appended to the output and a loop is entered to get each of the input variables.

The get operand routine is called to get any type of variable reference.  The next token is obtained.  If the token is a comma, the done flag is set to false and the input token is set to the token (to be reused for the input assign token).  If the token is a semicolon, the 'Keep' sub-code is set in the command token, the done flag is set to true, the input token is set to the token (for reuse), and the next token is obtained.  For all other tokens, the done flag is set to true, and the input token is set to a new token.

The input token is set to the InputAssign code and the process final operand routine is called to process the reference on top of the done stack and set the input token code to the appropriate input assign code for the data type of the reference.  A new token is created with the second associated code of the input assign code, which will be the coordinating input parse code.  The input parse token is then inserted into the output list at the begin index.  The input parse token for each subsequent reference will be inserted in front of the last input parse token, and therefore all the input parse tokens will be in the desired reverse order (making execution easier).  The loop continues while the done flag is not set.

Upon exit from the loop, if the status is set to an error, the error is returned.  Otherwise, the command token is appended to the output and if terminating token is not an end-of-statement, the "expecting comma, semicolon or end-of-statement" error is returned.  (Note the reversal of the "comma" and "semicolon" words in the error message used for the PRINT statement, which makes more sense for the INPUT statement.)  Finally the done status is returned.  See the commit log for the other minor changes required to implement the INPUT translate routine.

[commit 8b079faf61]