11

I was wondering how the MS-DOS 6 DIR command works. I noticed that the floppy drive directory is cached so that the drive isn't read again when you run DIR a second time. In thinking there may be a situation where I want to force it to refresh the DIR results, I need to understand how it works so that I can code a utility to force a refresh.

Just running on a typical 486 MS-DOS 6 machine.

1
  • 2
    What situation are you thinking about? Floppy change is handled since the very first DOS version.
    – Raffzahn
    Sep 11, 2022 at 3:06

2 Answers 2

15

Hard to answer without knowing what DOS (MS, DR, ...) in what configuration and on what machine - or emulation thereof - this observation has been made.

So here just a rough overview of the general development:

DOS Buffers

DOS 1.x had dedicated buffers for various jobs. At least one for a single directory and a data sector - there might have as well been one for the FAT - for each drive.

DOS 2.0 introduced a more generic low level buffer management, seen in BUFF.ASM. It offered a series of file access buffers which could be set between 1 and 99 using the BUFFERS= option of CONFIG.SYS. Without a default value of MS-DOS was two. PC-DOS did set it according to system configuration:

  • 2 for a 128 KiB RAM with 180 KiB-Diskette
  • 3 for a 128 KiB RAM with 360 KiB-Diskette
  • 5 for 128 to 255 KiB RAM
  • 10 for 256 to 512 KiB RAM
  • 15 for 512 KiB and over

Those buffers were used for all disk access, regardless of sector type - although different use got different priority, FAT over Directory over Data.

Buffers Maketh System (Go)

Buffers are the essential building blocks of any nice and convenient high level function, like partial read from a sector, record wise operation, indexed access or alike. Just think of a file made up of fixed length records holding some journal one wants to read. Noone fetching one or more thereof wants to go thru the hassles of blocking/unblocking of records into sectors all the time, would you?

More so as sector size is a device and OS dependent value. So it should be the OSes task to provide some simple get-record/get-next-record function, shouldn't it? Then again, having such functions might perform quite terrible if reading a record would always include reading the sector - even with perfect timing that gets the speed down to 5 records a second. Same for every record write - and ways worse considering that Unix style character based read and write is standard today.

And that's where buffers come into play. Here DOS keeps some of the sectors last read to be peaked into again or modified with functions of different granularity. The speed gain is quite considerable. Just imagine a record size of maybe 32 bytes. With 512 byte sector 16 of them would be packed into a sector. Reading them sequential using a nice high level read-first/read-next interface would mean 16 reads, but having a buffer will get that down to a single read and 15 times just peeking into the buffer.

Sounds great, doesn't it?

Heck, it gets even better when reading past that sector, as now the system has to find the next one reading the FAT. With buffers, the FAT may still be in memory so it saves another read.

BTW, did I mention that a directory is simply a data base file with fixed size records of 32 bytes each? Or that COMMAND.COM is a very average user program using a high level find-first/find-next API to scan it?

Without Buffers a PC would be slower than a C64 (*2).

Buffers are Only Valid For Two Seconds

All read buffers have a life time of 2 seconds. After that they are invalidated. This was the direct result of tests done during development. (*1)

Classic MS-DOS (Before 3.0)

does not cache any FD or HD access in any way - that is, beside the buffers. COMMAND.COM does not cache the results of a directory scan, but restarts each time using the standard functions for directory access, like any other application.

In fact, in all DOS versions prior to 3.0, COMMAND.COM only uses the FCB based routines of INT 21h (Function 11h/12h). The new, Xenix like, Find First/Next calls (4Eh/4Fh), are not used, as seen in the source code (*3)

Starting with DOS 3.0

mechanics for buffer management were introduced to support networking, but DOS does (AFAIK) still use only write buffers. Management was made thru the new multiplex interrupt INT 2Fh using function group 12h.

With DOS 4.01, in 1988, and Windows 3.0, in 1990, SMARTDRIVE was added providing a way to use RAM for disk buffering - although its main purpose was to make sure bus master controllers would always find their data buffers in conventional memory.

Due the changes in DOS 3.0 all of this should be robust against parallel access and disk changes.

Management Calls Available

  • Every user of a file can of course flush its buffers by calling INT 21h function 68h Commit File. It will update all data blocks and directory entries.

  • Already since DOS 1.0 INT 21h Function 0Dh Disk Reset can be used to flush all unwritten buffers of all disk drive.

  • INT 2Fh offers several functions to manage the disk buffers, including invalidating, but these calls can only be made from within DOS, as they need a very specific environment. Also structures handled may differ between DOS versions.


In thinking there may be a situation where I want to force it to refresh the DIR results, I need to understand how it works so that I can code a utility to force a refresh.

It would be quite interesting to learn what situation that could be and how they may be invoked.


*1 - No, someone managing to do a disk swap in less than two isn't proving anything for real life usability.

*2 - Then again, a genuine 4.77 MHz IBM-PC isn't that much faster either.

*3 - The 2.x DOS kernel as well was still based around FCB calls. Much of the speed gain in DOS 3.0 was by flipping this. All disk access was rewritten to use Xenix calls as primary implementation. FCB calls were only provided as a compatibility layer atop the Xenix versions.

10
  • 1
    Note for classic DOS Microsoft put the MS-DOS 1.25 and 2.0 source on GitHub.
    – Brian
    Sep 11, 2022 at 2:57
  • 1
    DOS after 3.0 must have some sort of read buffers at least for the FAT. (Compare first DIR on a disk and time to "....Bytes Free" and any following, on a large disk). I guess that buffer lives in the command interpreter.
    – tofro
    Sep 11, 2022 at 8:18
  • 2
    When reading Raymond Chen's article, I thought "a (more) modern 3 1/2" disk can be changed in less than 2 seconds", tried it, and - yes, it can.
    – tofro
    Sep 11, 2022 at 8:20
  • 1
    I was watching youtu.be/8tzuIGf6x1Y?t=508 which has a hardware floppy toggle to swap between which drive is connected to the floppy cable. The side effect is that DOS doesn't recognize a disk was changed and the DIR results never change unless you physically swap disks. I thought it would be a cool project to write a utility that invalidates the cache, or something.
    – Thraka
    Sep 11, 2022 at 17:41
  • 1
    @Thraka Well, if such nice after-market stuff is considered legal, then no buffering can be done at all, as it enables unnoticeable drive swap. The only way to prevent this would be to to reread the floppy ID before each and every access, which includes repositioning the head to track 0. An incredible way to make floppy access even slower without gaining anything. Also, please add this to the question to make it clear what situation this this should solve.
    – Raffzahn
    Sep 11, 2022 at 20:50
-2

MS-DOS 6 introduced SMARTDRV which was a proper read cache driver, and it could also be configured for write cache. So you could easily retrieve data from a floppy and then the next time it wouldn't need to physically read it again. SMARTDRV was great, sped up systems enormously. There was never a need to manually refresh SMARTDRV's cache because if an edit was made to the disk, SMARTDRV knew about it.

4
  • 1
    Yes, but how is that relevant? The question was about how DIR gets cached, and, even if SMARTDRV is the mechanism involved, this answer just reads like a sales pitch, not an explanation.
    – ssokolow
    Sep 24, 2022 at 10:50
  • SmartDrv has nothing to do with the question. DOS simply knows that floppy has not been changed so it does not need to read the directory structure because it is already read in some cache/buffer.
    – Justme
    Sep 24, 2022 at 10:53
  • The question essentially is how DOS 6 was able to do two DIR commands on a floppy disk but only require one physical read. The answer is the SMARTDRV cache. The buffers structures were not read caches and they did not hold enough data to avoid the need for a physical read.
    – Geoff Vass
    Sep 25, 2022 at 11:10
  • As for "SmartDrv has nothing to do with the question" and "it is already read in some cache/buffer". Yes, the latter is SmartDrv.
    – Geoff Vass
    Sep 25, 2022 at 11:11

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.