English Amiga Board


Go Back   English Amiga Board > Support > support.WinUAE

 
 
Thread Tools
Old 28 January 2013, 16:08   #1
mark_k
Registered User
 
Join Date: Aug 2004
Location:
Posts: 2,700
Floppy drive timings and NTSC floppy unreliability

Following on from this in the WinUAE 2.6.0 beta thread I thought I'd post about the Amiga floppy timings.

There's some bug with WinUAE's floppy emulation which makes reading and/or writing disks unreliable when the display mode is NTSC. That applies to both NTSC Amiga emulation and PAL Amiga w/ECS Agnus in NTSC mode. It applies when the display is NTSC interlaced or non-interlaced. I suspect the cause is somehow related to scanlines in NTSC modes being alternately 227 and 228 colour clocks, as opposed to always 227 for PAL modes.

For further investigation, I thought about trying these things:
- Modify Kickstart to only output short frames in non-interlaced modes, see if that makes a difference.
- After booting with Kickstart 1.x, set the ECS programmable mode registers to exactly match NTSC output. Then set the BEAMCON0 LOLDIS bit and see if the problem goes away. What timing register values would be needed to exactly match native NTSC output for programmable modes?
- (Edit to add:) Check whether the problem happens in any programmed modes (EURO36, SUPER72 etc.). Also when using a programmed mode, try writing to BEAMCON0 to clear the LOLDIS bit and see whether the problem appears then.


But first, I looked at disk.cpp in the WinUAE source code and have some questions about constants used. In disk.cpp you have:
Code:
/* writable track length with normal 2us bitcell/300RPM motor, 12667 PAL, 12797 NTSC */
#define FLOPPY_WRITE_LEN (currprefs.floppy_write_length > 256 ? currprefs.floppy_write_length / 2 : (currprefs.ntscmode ? (12798 / 2) : (12668 / 2)))
...
/* (cycles/bitcell) << 8, normal = ((2us/280ns)<<8) = ~1828.5714 */
#define NORMAL_FLOPPY_SPEED (currprefs.ntscmode ? 1812 : 1829)
The 12667 PAL figure checks out, but the NTSC figure should be 12784 by my calculations. And NORMAL_FLOPPY_SPEED should be 1792 = 32*56 for both PAL and NTSC Amigas (again, by my calculations).

The NTSC subcarrier (colour clock) is 315/88 MHz = 3.57954545...MHz.
NTSC CPU clock is double that, i.e. 7.15909090...MHz.
NTSC "28M" clock is 4 times that, 28.63636363...MHz.

The PAL subcarrier frequency is 4.43361875MHz.
PAL CPU clock is 1.6 times that, 7.09379MHz.
PAL "28M" clock is 4 times that, 28.37516MHz.

Floppy bitcell timing (~2us) is 1 bit per 56 28M clocks.

Floppy drive rotation rate is 300rpm, i.e. one rotation takes 0.2 seconds.
So number of bitcells per disk revolution is 0.2 * (28M clock rate)/56. Which gives
PAL: 101339.857... bits => 12667.482... bytes per revolution
NTSC: 102272.7272... bits => 12784.090909... bytes per revolution

So where did the 12797 NTSC figure come from?

Last edited by mark_k; 28 January 2013 at 17:15.
mark_k is offline  
AdSense AdSense  
Old 30 January 2013, 17:16   #2
Toni Wilen
WinUAE developer
 
Join Date: Aug 2001
Location: Hämeenlinna/Finland
Age: 42
Posts: 19,943
Right, there is some weird stuff..

FLOPPY_WRITE_LEN and NORMAL_FLOPPY_SPEED should (at least I remember doing it this way long time ago) have been completely separate variables but it isn't that way anymore.

I'll think about this issue later.. This needs careful testing and checking because any kind of "wrong" change will break bit cell timing based copy protections.
Toni Wilen is offline  
Old 01 February 2013, 21:00   #3
mark_k
Registered User
 
Join Date: Aug 2004
Location:
Posts: 2,700
Okay I'm probably grasping at straws here but... In disk.cpp, in the DISK_update() function you have
Code:
void DISK_update (int tohpos)
{
	int dr;
	int cycles;
	int startcycle = disk_hpos;

	if (disk_hpos < 0) {
		disk_hpos = - disk_hpos;
		return;
	}

	cycles = (tohpos << 8) - disk_hpos;
	if (cycles <= 0)
		return;
	disk_hpos += cycles;
	if (disk_hpos >= (maxhpos << 8))
		disk_hpos %= 1 << 8;
	...
The precedence of the %= operator is lower than that of the << operator. So the last line there is doing disk_hpos %= (1 << 8), i.e. disk_hpos %= 256. Is that right? Shouldn't it instead be
disk_hpos %= (maxhpos << 8)

Quote:
Originally Posted by Toni Wilen View Post
I'll think about this issue later.. This needs careful testing and checking because any kind of "wrong" change will break bit cell timing based copy protections.
Are FLOPPY_WRITE_LEN and NORMAL_FLOPPY_SPEED used when accessing copy-protected disks (e.g. IPF files)? The track lengths would be as given in the IPF file, rather than generated by WinUAE in that case, wouldn't they? I guess the impact of the "wrong" values is that if you e.g. format a floppy disk and are using an extended ADF file, the track lengths are different from the nominal NTSC (or PAL) value.

Last edited by mark_k; 01 February 2013 at 21:15.
mark_k is offline  
Old 01 February 2013, 21:14   #4
Toni Wilen
WinUAE developer
 
Join Date: Aug 2001
Location: Hämeenlinna/Finland
Age: 42
Posts: 19,943
EDIT: I misunderstood your question.. It could be wrong, it has been long time since I worked with disk emulation..

EDIT2: It is correct. Possible "overflow" (low 8 bits) must remain for next scanline. disk_hpos &= 255; probably would have been clearer but <something> << 8 was used every else too.

Last edited by Toni Wilen; 01 February 2013 at 21:20.
Toni Wilen is offline  
Old 01 February 2013, 21:42   #5
mark_k
Registered User
 
Join Date: Aug 2004
Location:
Posts: 2,700
Code:
	cycles = (tohpos << 8) - disk_hpos;
	if (cycles <= 0)
		return;
	disk_hpos += cycles;	// Equivalent to disk_hpos = (tohpos << 8);

	if (disk_hpos >= (maxhpos << 8))
		disk_hpos %= 1 << 8;	// Equivalent to disk_hpos = 0; !!
disk_hpos += cycles is equivalent here to disk_hpos = (tohpos << 8). So disk_hpos modulo 256 is always 0. Therefore, when tohpos >= maxhpos you set disk_hpos to 0.

When tohpos == maxhpos, doesn't that mean that disk_hpos effectively skips forward one cycle? (Can DISK_update() ever be called with tohpos > maxhpos?)
mark_k is offline  
Old 01 February 2013, 23:53   #6
mark_k
Registered User
 
Join Date: Aug 2004
Location:
Posts: 2,700
Quote:
Originally Posted by mark_k View Post
For further investigation, I thought about trying these things:
...
- (Edit to add:) Check whether the problem happens in any programmed modes (EURO36, SUPER72 etc.). Also when using a programmed mode, try writing to BEAMCON0 to clear the LOLDIS bit and see whether the problem appears then.
I tried booting to a Multiscan:640x480 Workbench. According to the WinUAE log, the system wrote 0x1B88 to BEAMCON0. WinUAE says
warning: 1B88 written to BEAMCON0 PC=00F8FFC0
(Why the warning message, out of interest?)

Anyway, with Workbench in that mode I tried writing to BEAMCON0 with the LOLDIS bit clear (so writing 0x1388). The display changed to the same state as if I had written 0x0000 to BEAMCON0. Does that happen on a real Amiga too?
Edit: I screwed up, will try some more things later.
mark_k is offline  
Old 02 February 2013, 23:03   #7
mark_k
Registered User
 
Join Date: Aug 2004
Location:
Posts: 2,700
Also, the startcycle variable in DISK_update() isn't used.
mark_k is offline  
AdSense AdSense  
 


Currently Active Users Viewing This Thread: 1 (0 members and 1 guests)
 
Thread Tools

Similar Threads
Thread Thread Starter Forum Replies Last Post
Can I use external floppy drive as internal drive? Mrs Beanbag support.Hardware 6 12 December 2012 20:15
Noisy floppy drive or drive not reading properly HD disks? Old Fool support.Hardware 4 07 June 2010 16:09
would this floppy drive do? eLowar project.SPS (was CAPS) 18 02 October 2003 00:47
Floppy drive (again...) scaf support.Hardware 5 25 March 2003 17:15
HD Floppy Drive mrburns support.Hardware 2 15 September 2001 18:30

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off

Forum Jump


All times are GMT +2. The time now is 06:08.


Powered by vBulletin® Version 3.8.8 Beta 1
Copyright ©2000 - 2017, vBulletin Solutions, Inc.
Page generated in 0.19818 seconds with 12 queries