Fast-Stack and Fast-Jump
40 % faster BASIC for you
by BILL BODENSTEIN
Atari 8-bit BASIC is dependable, versatile and friendly- but it's not fast.
Consider this example of how Atari BASIC trades speed for safety: You press [BREAK] to stop a program, change a few lines and then resume the edited program with a CONT or GOTO statement. With most other programming languages, this could lead to disaster because of the way those languages use their runtime stack.
Immediately before execution of a GOSUB (subroutine call), the runtime stack stores information needed to return from that subroutine. When Atari BASIC encounters a RETURN statement, it can tell which line to return to by pulling the line number of the previous GOSUB statement from the top of the runtime stack. The same process is used to find the line number of the FOR referenced by a NEXT statement.
But after Atari BASIC knows the line number, it still must search through the entire BASIC program, starting from the first line, until it finds the selected line. Unlike most other languages, Atari BASIC doesn't just jump to an address removed from the stack. Rather, it locates the proper return address safely-but slowly.
However, Fast-Stack gives you a way to trade some safety for speed. This one-line machine language program is activated by a USR call. Fast-Stack copies BASIC ROM to BASIC RAM, then modifies BASIC so that the runtime stack uses the return line memory address, instead of the return line number
Fast-Stack should increase your BASIC program speed 10% to as much as 40%, depending on the program size and how far down in the program you placed the most frequently used GOSUBs and FOR/NEXT loops.
To prevent jumping to the wrong address after editing lines, the modified BASIC in RAM will only be active while the program is RUNning. ROM-based BASIC is turned on again at the READY prompt.
However, because stopping the program will not clear the runtime stack, re-entering the program from the subroutine level could cause Error 15-GOSUB or FOR line deleted. That's because BASIC ROM treats the address of the line taken from the stack as the line number itself. Therefore, use Fast-Stack only with your finished BASIC programs. If you need to edit a program containing Fast-Stack, return to the edited program with a RUN command instead of GOTO or CONT.
You may need to change the number of iterations in any DELAY loop your BASIC programs. Better yet, use the internal real-time clock (memory locations 18-20) so that delays will always be the same with either XL or XE systems.
The Fast-Stack version of BASIC RAM will remain active in a BASIC program loaded and RUN from a RUN "D:filename" or RUN "C:" statement embedded in another BASIC program. If you want the second program to RUN at normal speed, add POKE 54017,25 3 to its first line to turn on ROM-based BASIC. POKE 54017,25 5 turns on your modified BASIC again. Be sure to type a CLR statement before using either of these POKEs.
Fast-Jump also modifies Atari BASIC in RAM, but this routine speeds up the routine that searches for a matching line number.
Let's say that in a 500-line program, line 400 contains the statement GOTO 402. Upon encountering this GOTO, unmodified BASIC will automatically start at your program's first line and search-for a fairly long time-until it finds line 402.
Fast-Jump's line-searcher routine does things in a speedier way. It compares the current line with the line being referenced. If the referenced line follows or is the current line, BASIC begins searching from the current line, not at the start of the program. In our previous example, BASIC, modified by Fast-Jump, will begin searching at line 400-and discover line 402 very quickly
HOW IT WORKS
Whenever unmodified BASIC encounters a GOTO or GOSUB, it converts the number, variable, or expression that follows the statement into a two-byte integer. BASIC then starts at the first line of the program and compares this two-byte number with the two-byte line number that precedes each tokenized BASIC line. When a match is found, the address of that line is returned in STMCUR, the current BASIC statement pointer (locations 138 and 139), and execution begins from this new line. If no match is found, an ERROR 12 (Line Not Found) is generated.
In a 10-to-30-line program, execution time can be reduced 10% with each GOTO, GOSUB or READ if the line being referenced (or containing DATA) immediately follows or is the line containing that statement. In programs over 500 lines, some line-referencing statements RUN more than 80% faster.
To achieve the greatest speed improvements, try putting the subroutines immediately below the lines that call them. With Fast-Jump, you needn't cram them all at the start of your program for faster execution. Instead, in those first lines, place only the subroutines called throughout the program.
It's good Fast-Jump practice not to backwards-reference your subroutines. Instead of these lines:
1000 IF Z*X>l0 THEN 2000
1010 X=X+1:IF X<10 THEN 1000
try this one:
1000 ON Z * X>10 GOTO 2000:X = X + l:IF X<10 THEN 1000
If (Z*X) is not greater than 10, execution is tranferred to the next statement-not the next line, as with IF-THEN conditions. (A FOR/NEXT loop may also work, using the speed benefits of Fast-Stack.)
One problem with Fast-Jump is that it occupies the area of Atari BASIC code that handles the NEW command, so NEW does nothing. To erase the BASIC program, change any NEW statement in your program to POKE 202,1:END. In direct mode NEW works fine, because Fast-Stack reenables BASIC ROM when exiting the program.
TYPING THEM IN
Type in Listing 1, FASTPROG.BAS, check it with TYPO II and SAVE it to disk or cassette. When RUN, FASTPROG.BAS creates a file called FASTPROG.LST which contains both the Fast-Jump and Fast-Stack routines.
Listing 2 and Listing 3 are the MAC/65 source code for Fast-Stack and Fast-Jump, respectively. You do not need to type them in order to use the program. Antic Disk Owners will find all three listings on the monthly disk.
To merge these two routines with your BASIC program, simply ENTER the FASTPROG.LST file from disk or cassette. NOTE: the routines occupy lines 0 and 1, so be sure your own BASIC program leaves these lines free.
Though Fast-Stack and Fast-Jump work independently, you'll need both USR calls, because the machine language routine in line 0 is also responsible for copying BASIC into memory.
Bill Bodenstein is a computer science senior at the University of Cincinnati. Readers rated his Multi-Autorun the most popular program in our March, 1987 issue.