!pr1
WildCAT for DOS 3.3....................................Erv Edge

WildCAT is a series of patches to DOS 3.3 which modify the CATALOG command.  The new features include:

   * A catalog by "wildcard" FILENAME facility.
   * A catalog by FILETYPE facility.
   * An alternate, short-form: either DIR or CAT.
   * Catalog free space patch.
   * Ctrl-Q catalog abort.
   * TYPE a random or sequential text file.

Lee Reynold's FILEDUMP command has been re-packaged and re-presented as TYPE (see Call-A.P.P.L.E.  6/82 p47).  More on this later.  WildCAT, along with TYPE, is an attempt to teach new tricks to an old dog, as it were.

The normal DOS CATALOG command allows slot, drive, and volume parameters.  I have added a filename parameter, but process it a little differently than the way file names are usually processed.  To display the catalog entries for all files whose names contain a particular string, type any of the following:

   CATALOG ^string [,Dn] [,Sn] [,Vn]
   DIR ^string [,Dn] [,Sn] [,Vn]
   CAT ^string [,Dn] [,Sn] [,Vn]

where "^string" begins with the "^" or caret symbol (shifted N on the ][+ or shifted 6 on the //e or //c); the string should contain no blanks, although it may "end" with them; the string would normally end with a carriage return or with a comma if a drive or slot number is specified.  Only those files that contain the "string" somewhere in the filename will be listed.  (Of course you already know that the D, S, and V parameters are shown in brackets above because they are optional; you do not type the brackets.)

For example, "CATALOG ^TEST" would list each file with 'TEST' as part of the filename; while "DIR ^PAY." would list those with 'PAY.' somewhere in the filename; and "CAT^.OBJ,D2" would list filenames on drive 2 that contain the partial string '.OBJ'.  "CAT" and "DIR" are simply synonyms for "CATALOG".

I have also arranged things so you can list the catalog entries of a specified file-type.  You simply type the file type code in the CATALOG command:

   CATALOG t [,Dn] [,Sn] [,Vn]
   DIR t [,Dn] [,Sn] [,Vn]
   CAT t [,Dn] [,Sn] [,Vn]

where "t" is any of the unadorned, single-letter filetypes: A B I R S T.  Only that type of file (if present) will be listed.

For example, "CATALOG T" would list all the text files; "DIR A,D2" would list all of the Applesoft files on drive 2; "CAT B,S5,D1" would list all the binary files on slot 5, drive 1.  Yes, "DIRT" works just fine.
!np
I added the TYPE command, which allows you to display the contents of text files.  Both CATALOG and TYPE will optionally:

   1.  Print "hidden" control characters as inverse:
      POKE 234,0 to print as inverse (default)
      POKE 234,255 to function as-is

   2.  Lower case letters may be shifted to upper case:
      POKE -18700,255 no shift (default)
      POKE -18700,223 to shift lower to upper case.

You can slow down TYPE's output via SPEED=xx or POKE 241,xx; or pause by pressing any key; then Ctrl-Q to abort.  Also, TYPE pauses and waits for a keypress when it encounters a hex 00 imbedded in the file or at end of file; press Ctrl-Q to quit.  You may TYPE random text files by holding down REPT-SPACE to get past the hex 00's at the end of each logical record.

The listing that follows is intended for information only:  it is not BRUNable.  My intention is that you prepare the EXEC shown below to actually install the patches.  Any word processor that produces a straight, sequential text file may be used to prepare the EXEC.  Of course you can also use the S-C Macro Assembler for this purpose.  Then, type EXEC WILDCAT to apply the patches to DOS 3.3 in memory.  After checking it out and running any other tests you like, put in a new diskette, enter a HELLO program, and type INIT HELLO to "permanently" install WildCAT in the DOS on tracks 0, 1, and 2.

When I wrote WildCAT, I had two main goals in mind:  it should be a (mostly in-place) code replacement, and it should be compatible with the known means of using (abusing?) the existing CATALOG code at $AD98-AE69.

One major design consideration was a mechanism for entering the ^string/type parameter.  This required merely changing the "keyword parameter table" so CATALOG could have a "filename".

Next, a distinction had to be made between a "wildcard" and a "filetype" parameter.  It made sense to 'delimit' the wildcard string; then the single-character filetype would be just that: a single character, entered without a delimiter.  But this "phony" name mechanism has it's own problems:

First, "What's in a Name?" (DOS Manual p.  16): a filename has to start with a letter...which automatically eliminates most special characters (eg, equal, pound, slash, colon, etc) as the delimiter.  The command parsing routine doesn't really know what it's working on at the time.  All it knows is: if a name may be present, it must be valid.  The validity test is only that the first character be equal to or greater that $C0 or an @-sign.  The @-sign could have been used, but it's a problem on some 80-column boards; the ^ or caret works nicely (and besides, it looks good).

Second, now that we have a name (however, phony) and since the CATALOG command lives in the File Manager (FM) portion of DOS, there will be a buffer allocated for it.  Unfortunately, the Command Interpreter (CI) DOCAT routine, which calls the FM, already "knows" that there will not really be a name, so it does not include housekeeping code to deallocate a buffer.  So merrily allocating files without closing them...after the third time: NO BUFFERS AVAILABLE.  And naively adding CLOSE (even if there were room for it), would have one very undesirable side effect if a "regular" catalog were requested: CATALOG-CLOSE without FNAME will close all open files.  WildCAT instead plays a little shell game with DOS: The new DOCAT routine saves the first character of FNAME and substitutes a zero.  Thereafter, neither the File Manager nor the rest of DOS ever knows that a name has been entered, so FM never actually allocates a buffer.

Third, what really should happen if a phony name is not entered?  A regular catalog, of course, but how would this be indicated to WildCAT?  Well, the shell game has a sting.  Early on when the CI PARSE routine discovers that a filename is a valid parameter, it first clears FNAME to all blanks, expecting to fill it in with whatever comes in next.  If a comma or carriage return comes in next, then FNAME still contains the blank; and that's what WildCAT saves off (under the shell) before it substitutes the zero.

Thus, the "sting" is that the CI "tricks" itself into telling WildCAT what to do in the absence of a ^string/type specifier: WildCAT takes a blank to indicate "do a regular" catalog; just as positively as a "^" indicates "do a wildcard" catalog, and a single character indicates "do a filetype" catalog.

The blank indicator also helps satisfy the second goal above and solves the problem of compatibilty with the "known means" of using/abusing the existing CATALOG code.  WildCAT simply has to put a blank under the shell at each of the points where the code could most reasonably be entered without going thru the Command Interpreter's new  DOCAT routine.  That's exactly what all the JSR's to the routine AllowENTry are doing.

Satisfying that second goal takes up a lot of space, however; and has somewhat undermined the first constraint: WildCAT certainly isn't "in-place" in one place! And I apologize for this rather bizarre, serpentine code; I do hope that now you understand why some things were done the way they were.

Although considerable effort was spent to maintain compatibilty with the existing DOS commands, there were some compromises:

1.  While the DOS manual (page 22) states: "To specify drive 1, you use the notation D1 separated from the file name by a comma", you can in fact leave out the comma between CATALOG and D1.  With WildCAT that comma is now required; otherwise, it would take the "D" as a filetype and try to find it ... which of course it wouldn't and there would be no files reported.  This would also be a problem for Applesoft programs that do something like: PRINT D$"CATALOG D1" without the comma.  Therefore, WildCAT issues a (late) "SYNTAX ERROR" message if it encounters an undelimited string of length 2 or more.

2.  CATALOG is a favorite routine to execute directly, bypassing the DOS Command Interpreter.  FID, for example, provides its CATALOG via the "external" entry to the File Manager, which means that the main entry at CATHNDLR must provide for a "regular" catalog.  It is also possible from machine language, however, to bypass both the CI and the FM.  This usually involves changing the exit JMP address at DONEXT2 (to return to the user's code) and then jumping directly into almost anywhere in the CATALOG code (see the Listing 1 labels that begin "at").  I believe most of these cases are covered, but you may find some programs, which provide an "internal" CATALOG, that just won't work with WildCAT.

3.  In order to both gain some patch space and provide the DIR/CAT short-form command name, the DOS command POSITION was eliminated.  You may have to look it up just to find out that it is, much less what it is.  Its relative rarity may be due to its implementation: it, like APPEND, finds its way through the file one byte at a time...all day long.  Any program that uses it will now get a syntax error.  If POSITION is really needed, it can be readily simulated by programming a read-loop to discard N-1 fields before processing the desired Nth field.

The following is a brief commentary on the assembly listing.  The paragraph numbers correspond to numbers in comment lines.

The page zero locations I used ($EB thru $EF) are free, i.e. not used by DOS, the Monitor, or the Basics.

(1) In CMDTBL, replace Integer CHAIN address with TYPE and DOCAT address with NewDOCAT.

(2) Rearrange some code (and change both references to it) to add a "print blank" capability.  The Command Interpreter uses its own vector to a "COUT" routine via CSW at $36; however, the File Manager (previously) used the Monitor COUT and CROUT routines for printing the catalog.  With WildCAT all of DOS now consistently uses the vector at $9FCA for output; plus it has a new BlankOUT routine, all within the original code space.

(3) Recode a very cumbersome form of the "indexed indirect jump" to use register Y and leave X (which is zero by a previous operation) so it can be used in NewDOCAT.

(4) Replace old DOCAT's 12 bytes of code with a JMP to NewDOCAT and use the remainder to space over to column 7 after the file length has been displayed.

(5) NewDOCAT saves the first character of FNAME and substitutes a zero to prevent buffer allocation.  It then loads 13, the new Catalog Function Code, and proceeds to CMDHNDLR2.  Function 13 enters the catalog code past the "allow for irregular, direct entry".

(6) In the keyword parameter table, change parms to allow a filename with CATALOG and a filename, drive, and slot with DIR.  Set new Function 13 address (previously a "no-op" to NOERROR) to WildCAT and change the range check to 14 to allow for it.

(7) Replace the Integer CHAIN code; PrtLOCK displays an asterisk or blank if the file is locked or not.

(8) Shorten the "NO BUFFERS AVAILABLE" message to "NO BUFFER" and re-use the space to decide which Basic is active, then JMP to the appropriate decimal print routine; used to print the free sector value and catalog filesizes.  The value to be printed has been previously loaded into A and X.

(9) First, eliminate the need for "NOT DIRECT COMMAND" error message and then re-use the space to check for a "regular" catalog (no filename) or for a catalog by filetype (undelimited, single character).  If more than a single, non-blank character is detected (ie, 2nd byte of FNAME is not blank), then "SYNTAX ERROR" message is issued.

(10) At beginning of catalog code allow for most normal points where the code could be directly entered.  The new "official" Function 13, WildCAT initializes the FM workarea (per normal) and branches to Read VTOC to "find" the first catalog sector.

(11) Freespace "prolog"; clear carry and branch around another likely "irregular" entry point.  Read first/next catalog sector, then lookup and save the filetype.  Setup Y with 30 for name length and branch to CkFNAME.

(12) AllowVTOC fakes a "regular" catalog and falls into a JSR to read the VTOC.  The BCC to initialize linecount is always taken; only if there had been an I/O error would the carry be set, in which case, control would have passed to the error-message-print exit anyway.

(13) PrtCat displays a catalog line.  Note that loc $24, CH, is "POKEd" with 7 for uniform spacing over to the filename.  If your printer interface board or 80-column card do not support this convention, then the display will not be properly spaced.  The DONEXT routine is unchanged.  SKIPLN has been re-arranged to allow init linecount, put out a carriage return, and check for a keypress (Ctrl-Q to quit) after 22 lines.  Note: This leaves the cursor in column 37; see below.

(14) CkFNAME "looks under the shell" to figure out what to do.  A caret indicates to check for a wildcard string.  After JSR to CkCAT, if the equal status is set, then branch to print the catalog line.  DoWild checks for the occurence of the wildcard string within the filename.  $B4C9,X indexes the name in the Catalog Sector; $AA75,Y indexes the wildcard string; CatNmLen counts from 30 to 0, to scan the whole name.

(15) FreeSpce counts the free sectors, as indicated by the VTOC, loads X and A with the count, and JMPs ToPrtDec.

(16) WaitCk79 provides the "wait" for TYPE; also checks and puts out a carriage return after 79 characters to avoid over- printing long lines on certain printers, such as the MX-80.

(17) TYPE displays the contents of a sequential or random text file.  A keypress will pause the display, and Ctrl-Q quits.
!np
(18) InvCOUT is used by both CATALOG and TYPE.  It converts hi- bit off characters to proper inverse.  It will optionally show control characters as inverse or allow them to "function" as- is; and it will optionally "shift" lower case letters to upper case, if you do not have a lower case adapter; see "...Options" above.  Loc $EA, decimal 234, is the Applesoft Hi-Res collision counter; it should always be zero, unless you POKE it.

(19) WaitCQ waits for a keypress and sets the equal status, if Ctrl-Q was pressed.

(20) Replace the inverted phrase DISK VOLUME with FREE SPACE=.

(21) The DOSCMDS list is moved down 6 bytes.  AllowENT re-uses these 6 bytes to force a blank in FName1 "under the shell" to ease "irregular" entries into the catalog code; and clears the carry in case the entry was 'atADC9' which also cleared the carry.  In the command list, TYPE replaces CHAIN and DIR replaces POSITION; change $A8BF:43 41 D4 to replace with CAT.

(22) Change the two references to DOSCMDS to the new location.  These two changes must be done last as the EXEC is changing the very code that is executing.

I would like to thank Lee Reynolds and Art Schumer for their helpful comments and suggestions.
