Floppy controller questions

Allison ajp166 at bellatlantic.net
Wed Aug 24 13:23:46 CDT 2005


>
>Subject: Re: Floppy controller questions
>   From: "Dwight K. Elvey" <dwight.elvey at amd.com>
>   Date: Wed, 24 Aug 2005 09:36:49 -0700 (PDT)
>     To: cctalk at classiccmp.org
>
>>Yep, remember the worst case for "fast is 13us!  I'd plan for that.
>>Also the slow rates will give you nominal 32us (27us worst case).
>>
>>>Isn't learning fun?
>---snip---
>
>Hi
> One thing to consider is that you can unroll the loop and just
>fetch or write data and increment the pointer. Even on an
>8080, this is reasonably fast. If you know the speed of the
>processor and the speed of the controller, you don't have to
>check the data ready bit every time. You just need to do it
>often enough to resync things. Another trick, if you are
>using a loop, is that you can make the loop partially unrolled.
>You only modify the counter once every few data read or writes.
>You do, say, 4 bytes at a time. Any odd amounts needed can
>be unrolled.
> Using any one of these tricks will get you in the range.
>On a PC, the main issue is that you need to shut down all
>interrupts and be aware of refresh if it uses memory cycles.
> On a processor that I was playing with, I found that the
>processor was too fast for the FDC chip. It was only
>running a 4 MHz instruction speed.
>Dwight

You can do that with care.

One oddity is the 765 will assert DRQ (dma request) before the 
data is in the buffer and a .5uS delay is needed on DRQ for ultra 
fast DMA systems.  I found this out with 4mhz z80 using processor 
stall: read the DMA input port, IF DRQ not TRUE then assert CPU WAIT/
until true. Thsi is fast enough as it's waiting on an IN A,DMAport
and will grab the buffer as soon as DRQ is true.  If you can have
the CPU wait on DRQ the loop is very tight.  For Z80/8080:

ugly 8080 flavor for transfers up to 1KB:

  ;  HL is memory pointer
  ;  A is temp
  ;  B is transfer length *4
  ;  Zero flag affected by DCR B
  DMAIO:  IN DMAport  ; wait if DMA is not asserted
          mov M,A
          INX H       ; HL<-HL+1
          IN DMAport  ; wait if DMA is not asserted
          mov M,A
          INX H       ; HL<-HL+1
          IN DMAport  ; wait if DMA is not asserted
          mov M,A
          INX H       ; HL<-HL+1
          IN DMAport  ; wait if DMA is not asserted
          mov M,A
          INX H       ; HL<-HL+1
          DCR  B      ; B is dmatransfer down counter
          JNZ  DMAIO  ; loop if not Zero, more to go.
          ...

It's 35 cycles in z80 for the slowest part of the loop
and 34 for 8080.  Z80 IN port is 11cy!

Why four bytes pwer transfer? one it makes doing 512 or
1024 bytes per sector with a 8bit counter (lower overhead)
and doing a 765 format only requires 4 bytes per sector
(C, H, R and N)!

A 2mhz 8080 will actually run this for 8" DD (13us case)
successfuly even though the last leg of the loop is 
17.5us as you have 16us +13us worst case before an 
overrun occurs and the next step in the loop is not 
as slow. Note waits for refresh will blow the works
and Z80s systems that use processor refresh are not 
likely to behave well if the FDC hangs (no disk or 
blank inserted) too long.

A 6502 can easily do it.

>From a system perspective I prefer DMA.  I like to free 
up CPU cycles to do "stuff" and make hardware do repeatitive
stuff like basic transfers.  However the DMA does not have \
to be complex or even a LSI (8257 or 8237). A simple gating
logic plus an upcounter of sufficient length is enough and 
it can even be to a fixed address (host buffer in the case 
of CP/M deblocking). Things like background tasks are then
easier to implement to utilize otherwise wasted IO loops 
(wait for keyboard!). The most obvious interrupt driven 
background tasks to implement are printer output buffering
or modem input buffering.


Allison





More information about the cctalk mailing list