Rik Karlsson, Oaktori, VA
I hate BASIC program line listings! Especially the way I write program lines: long, complex and without a memory-grabbing space in sight. They are just plain hard to read. That is, until now. Oh, yes, I still write the same way, but now I'm LLISTing using PAGELIST/CMD and it makes all the difference.
The Nov/Dec 1980 80-U.S. Journal featured an article on LLIST/CMD, a 'filter' for hardcopy BASIC line listings that gives the user a way to limit the length of any one printed line and also provides subsequent line indentations. This right-justified LLIST is good, but it was obvious that more needed to be done to satisfy me. So, I grabbed my modified-for-disk Editor-Assembler, Z-80 programming book, wish list of expected results, and went to work.
First, I decided to use LLIST/CMD as the basis for my new program. Okay, what was at the top of my need list? Pagination.
Pagination is the automatic halting of a hardcopy printout at the bottom of a page of material. This is important for a couple of reasons. One, paginated line listings are easier to store as a flat file than continuous roll ones. Second, if you are like me, you run off periodic 'proofs' of work in progress to check all of that good logic. I know, some of you folks sit down and flowchart, program in BASIC away from the keyboard, and don't have to see what you've done at the machine. But, I'm one who loves ideas more than all that workup work—go with the flow at the keyboard, I say, and see what happens! That's what interpreted BASIC'S all about, right?
Periodic proofs of line listings use up valuable roll paper. I've found a source of 'used' paper (one side clear) for this purpose, and since it isn't in rolls, I'm stuck if I don't have pagination. If you aren't into recycling, here's one area where the savings can come in a hurry. Anyway, PAGELIST/CMD paginates or not, as you select.
After programming pagination into PAGELIST/ CMD, it was time to 'open up' the listings for readability. The answer to this need is called linefeed-on-colon. Even the longest, most complex BASIC lines have colons to separate statements. Here is where money can be made in readability.
Let's look at the anatomy of the assembly language program and see what's going on here (Listing 1).
Since PAGELIST/CMD is meant to be used under BASIC, I added a step in the initialization sequence of the former LLIST/CMD. Now, the PAGELIST/CMD execution module is automatically protected in high RAM by resetting the DOS top of
64 Basic Computing memory pointer at 4049H. Lines 810 and 820 do this.
Lines 830-890 prompt the user for a maximum line length. The default value is 64 characters. An <ENTER>, instead of a number, in response to this query, is an acceptance of the default value and advances the program to a prompt for number of indentation spaces desired.
Lines 900-990 ask for and get the space response. Note that lines 950-970 insure that line length exceeds spaces requested. These two requests and queries are almost the same as programmed in LLIST/ CMD.
Lines 1000-1060 are new code, and request a yes or no response to whether pagination is desired. If it is, the indicator byte at TMODE' is set to one. An <ENTER> or 'N' answer advances the program to the next request, leaving pagination off.
Lines 1070-1140 ask for a yes or no response to activating the colon-on-linefeed option. A 'Y' causes the colon comparison code to be completed in the execution module.
Line 1150 is the end of initialization and jumps the program to DOS READY.
The INPUT routine, lines 1160-1320, is all new code as compared to LLIST/CMD. First, it uses the Level 2 input routine at address 0040H to wait for, and get, a user response. An RST 16 is executed to analyze the input. If a number is found, the carry flag is set and a RE Turn is executed. Notice in the code after CALL INPUT (in the initialization area), how the carry flag is used to direct traffic.
If no decimal number is present, a check for an <ENTER> is made. If found, the Z flag is set and a RETurn is executed. The Z flag also is set for an 'N' response. Notice again, how the Z flag directs program flow in the initialization module.
If neither number, <ENTER> nor 'N' is found to be input, a 'Y' is looked for. No 'Y', no RETurn—an Input Error!' message is displayed.
The messages in PAGELIST/ CMD are printed by a CALL to 4467H. This is a generalized DOS print-to-screen routine which recognizes a 03H or 0DH stop byte. I added a few touches to the request messages for clarity. Lines 1360-
PAGELIST/CMD is really two separate programs, if you will. The initialization module beginning at label 'START' is actually a program that configures the execution module according to the user's wishes. Once used, the initialization module becomes irrelevant to PAGELIST operation. Notice that it is ORGed low in memory and really could be almost anywhere. The execution module starting at label 'LLIST', however, is the workhorse routine of PAGELIST.
PAGELIST's execution module is a 'filter'. Its job is to sit between the printer and the ROM LLIST/ LPRINT code and insure that hardcopy printing is carried out according to the user's desires. Inserting PAGELIST into the line of events is accomplished by lines 750-780 of the initialization module.
Okay, now that our gatekeeper to the printer is on the job, how does he do what we have asked him to do?
First, the C register contains the byte enroute to the printer. Lines 1520-1590 compare that byte with three codes of interest; carriage return, top of form and quote mark. The first two cause execution to be routed to a few bytes of code that reset the line character counter back to zero, then prints the code. Remember, we've specified a maximum line length acceptable, so that every time a linefeed is executed, the character counter must be reset to a starting value.
The recognition of a quote mark causes a swapping of bytes at FF50H. This is Mister Toggle. He gets the present value of the comparison byte at location 'CKQTE+1' (address FF4AH), and reverses it. If it is a zero, he makes it a one, a one becomes a zero. Why? Because that byte controls the linefeed on colon function later on, as we will see. If none of the three comparisons are found to be true, the character counter is incremented by one and another comparison is attempted.
The byte at 'CLCPR' plus one, is initialized to the ASCII code for a colon upon user selection of the linefeed-on-colon option. If no colon is detected, execution falls through to check for maximum line length. If the line is at that length, a carriage return is effected. If not, the byte is printed normally, and we're back to line 1520.
If a colon is detected, a jump is made to 'CKQTE'. Okay, if Mister Toggle is a one, execution is routed back upstream for normal handling. Why? Because a one will appear only if just one quote mark has been encountered, meaning that a colon has been detected within a quoted string. Since the only colons of interest are between BASIC program statements, no action is taken. If Mister Toggle is a zero, an even number of quotes (or none at all) has been detected, and the colon
Listing 1 — PAGELIST Assembly Language Program vjtiiuU 00110 00120 00130 00140 00150 00160 00170 00180 00190 00200 00210 00220 00230 00240 00250 00260 00270 00280 00290 00300 00302 00304
BY RIK KARLSSON 3103 FOX MILL ROAD OAKTON,VIRGINIA 22124
THIS IS A GREATLY MODIFIED VERSION OF LLIST/CMD WHICH APPEARED IN 80-U.S. MAGAZINE OF NOV/DEC 1980. THIS PROGRAM ONLY RUNS UNDER A DISK OPERATING SYSTEM.
THE KEY DIFFERENCES BETWEEN THIS PROGRAM AND LLIST/CMD INCLUDE THE PAGINATION OPTION, LINEFEED ON COLON OPTION, AND THE USE OF SOME DOS ROUTINES TO PRINT THE MESSAGES. THE INPUT ROUTINE CALLS LEVEL-II ROM AS WELL. WHEN INITIALIZING, <ENTER> ALWAYS ADVANCES THE USER TO THE NEXT INPUT PARAMETER THUS FORCING A REVIEW AND ACCEPTANCE OF EACH ONE.
SUBROUTINES TO HANDLE THE PAGINATION OPTION ARE ADDED AS 'PGREQ','MODE' AND 'HOLD.' LINEFEED ON COLON IS ACTIVATED BY 'COLON' AND RECOGNIZED AT 'CLCPR.' THE BYTE AT 'CKQTE'+1 IS TOGGLED SO THAT NO LINEFEED WILL OCCUR ON A COLON ENCLOSED IN QUOTES.
is acted upon.
Now, execution falls through to carriage return, reset character counter, and check-page-length-in-lines subroutines. Line 1840, 'CALL MODE', executes a subroutine that increments the counter for number of lines printed, then checks for end of page. If 57 lines is detected, a message is displayed, and a wait for <ENTER> loop begun. <ENTER> causes execution to continue by entering spaces at the head of the next line and, finally, the next character being printed. Whew!
And, it happens that way for each character printed, folks. "But, what if I want to change the parameters? Do I have to go back to DOS and start all over again?" No, Virginia, there is a Santa Claus in two forms, PAGE LIST/B AS, a companion program, or direct command input of parameters. The direct command input mode is fully covered in the lead in (Listing 1, lines 430-690) documentation to the assembly language program listing. In most cases, only the line counter reset is actually needed in practice. To reset the line counter to zero following completion of a full program line listing, 'POKE &HFF94,0.' For those few times when a more extensive reconfiguration is required, the PAGELIST/BAS BASIC program is more thorough, capable and automatic.
Here is what the PAGELIST/BAS program is all about.
Recall that PAGELIST/CMD was composed of two separate programs, an initialization/configuration module and an execution module. The execution module is the only part of the composite left operative in memory after initialization.
PAGELIST/BAS (Listing 2) is RUN under BASIC and is a BASIC language configuration module for the PAGELIST machine code execution module. When RUN, it first checks to see that the execution module is indeed active. This is accomplished by examining the lineprinter device control block (DCB). If the DCB printer driver address points to the start address of the execution module, we're in business. If not, the fact is reported, and the BASIC program is terminated. To use PAGELIST in this case, you will have to start over 66 Basic Computing
00320 ;ALSO ADDED IS AN AUTOMATIC MEMORY PROTECT FEATURE 00330 ;AT INITIALIZATION WHICH SETS THE DOS MEMORY SIZE 00340 ; POINTER AT 4049H TO THE START OF THE EXECUTION MODULE
Was this article helpful?