3 ms·
Early DOS stuff was written in straight assembler, so to search for *.FOO you can just: Read a chunk of directory entries into a buffer. Set ptr to start of t
by ben509 8y ago
Early DOS stuff was written in straight assembler, so to search for *.FOO you can just:
Read a chunk of directory entries into a buffer.
Set ptr to start of the buffer.
Check the extension at ptr[8].
If extension matches, do a thing.
Set ptr to ptr + 32 and loop.
- anyfoo 8y agoYep, this sounds like the likely answer. Remember that when this structures came up, the “OS” was indeed just a bunch of hand-coded 8086 (and earlier) assembly routines.
- badsectoracula 8y agoSince the source code has been released [0], i decided to check it out and sadly it isn't that smart. Searching is implemented in DIR.ASM [1] by reading each entry one by one, matching is done only on the filename (encoded as 11 bytes for FILENAMEEXT) and it only handles "?". Note that this is for MS-DOS 2.0 which didn't handle "*.FOO" searches on the kernel side (the star expansion was done on the COMMAND.COM side via the MakeFcb [2] procedure). MS-DOS 3.0 introduced the star wildcard on the kernel side, so it might have taken advantage of that... but there isn't source code for MS-DOS 3.0. [0] https://github.com/Microsoft/MS-DOS/tree/master/v2.0/source https://github.com/Microsoft/MS-DOS/tree/master/v2.0/source [1] https://github.com/Microsoft/MS-DOS/blob/master/v2.0/source/DIR.ASM#L154 https://github.com/Microsoft/MS-DOS/blob/master/v2.0/source/... [2] https://github.com/Microsoft/MS-DOS/blob/master/v2.0/source/FCB.ASM#L30 https://github.com/Microsoft/MS-DOS/blob/master/v2.0/source/...
- stevekemp 8y agoMy memory is hazy, but the way that most DOS programs handled file iteration was to use FindFirst/FindNext, and that used data in the program-segment-prefix (PSP) - which was borrowed from CPM.
- badsectoracula 8y agoYes, the second link is essentially what "FindFirst" calls. A few lines below is the meat for "FindNext".
- anyfoo 8y agoWouldn’t you have to look how COMMAND.COM implemented * matching then, assuming that the filename buffer has a similar fixed length fields representation? Also note that DOS 2.0 incurred quite significant changes to fs code, as it was the first version to support directories. Before that, the namespace was flat.
- badsectoracula 8y agoAll commands (implemented in the TCODE?.ASM files) call PARSE_FILE_DESCRIPTOR (defined in MISC.ASM) which just calls MakeFcb (defined in FCB.ASM) that does the star parsing. See lines 127-133, CX contains the remainder of characters not parsed, if it is star the rest of the characters are replaced with ?s, so a FOO<star>.E<star> (...HN eats the stars) would become FOO?????.E?? (the subroutine MUSTGETWORD "under" MakeFcb does the actual replacing for each part, once for the filename and once for the extension - see the calls to it and how the CX is set up for the lengths). MS-DOS 1.25 does pattern matching mostly the same way [0]. The code is a bit simpler as it doesn't have the crazy macro stuff that MS-DOS 2.0 code has, but if you look a bit around the files, you'll see that it is mostly the same code just moved around and split in several files. The file scan works again in almost the same way, reading each directory entry one by one and doing the pattern matching after the fact. [0] https://github.com/Microsoft/MS-DOS/blob/master/v1.25/source/MSDOS.ASM#L557 https://github.com/Microsoft/MS-DOS/blob/master/v1.25/source...
- anyfoo 8y agoThanks for the thorough analysis! Very insightful. So the 8+3 structure still simplifies matching: To my recollection at least, in DOS a * would always wildcard out the rest of the filename component (I did not look in the code), so things like FOOxBAR.TXT weren't possible. That way though, the common x.TXT still is. Read "x" as *, because I could not for the life of me get the star work as a star within a word in this comment.