From: jdresser@altair88.UUCP (Jay Dresser)
Newsgroups: comp.sys.amiga.programmer
Subject: DAT A/V
Distribution: world
Date: 18 Dec 92 01:05:34 PST
Organization: Only Amiga make's it possible


So I got this DAT backup drive, and I was thinking about reading and
displaying images with audio continuously.  Here are some calculations:

Assume DAT delivers 176,400b/s.  This is CD rate (44,100*2*2).  DAT
actually delivers more because it goes 48,000 s/s, (the drive spec is like
184,000b/s) but we'll ignore that for now.  Plus, assuming 44,100 gives us
something that works for CD-ROM too.

Assume 48,000 bytes/frame (simple HAM mode) for video image.  This divides
out to 3.675 frames/s.  So let's go with 3 frames/sec, and the extra .675
(32,400b/s) for audio.

32,400b/s gives us a lot for a single channel of audio, or 2 channels at
16,200s/s, or a single high quality channel.  Since 3f/s is pretty meager
video, 16,200s/s audio (8kHz cutoff) is adequate.

So every 1/3 second (20 video frames) we read 48,000b of video image, and
10,800 (32,400/3) bytes of audio.  Since we will want to double buffer, I
would simply have 2 buffers of chip memory that has the 58,800 (48,000 +
10,800) byte buffers.

One more little detail.  We want the 16 color register for the HAM to look
good.  Since each frame will display for 20 video frames, I'll make a
copper list that is 20 frames long.  It will load the audio LOC once, then
load the video, wait, load video, wait, (and so on for 20 frames), and swap
buffers.  So there are 2 of these 20 frame long copper lists.  The end of
one loads the address of the other into COP1LOC so as to page flip, and
also interrupts the CPU to sync it (tell it to read the next buffer from
tape).

Did you know that the copper can call a subroutine?  They conveniently
provided that second copper address COP2LOC.  The COP1LOC is automatically
loaded at VBLANK, but the second one is for whatever you want.  So you load
the address of the subroutine in COP1LOC, the return address in COP2LOC,
strobe COPJMP1 which jumps to the subroutine, which does whatever and ends
with a strobe of COPJMP2 which returns.  This allows you to call a copper
routine from multiple places in your copper list without changing memory.
Just thought that one up, but not sure if I need that here, at least not
the multiple call part (because colors only loaded once for the 20 frames).

What I did want to do is load a copper list fragment with the other stuff
off the tape which could be a clean little piece of "position independent"
copper code that I could call to load the 16 color registers.  Thus each
(buffer-sized) block that I would load from tape would look like this:

	48,000	6 planes of HAM data
	    68	copper routine
	10,800	audio data

Since the colors only need to be loaded once per image, the copper routine
only needs to be called once, but having a routine like that means I just
need to read the data into the buffer and don't need to fuck with it with
the CPU (i.e.  merging data into a copper list).  The buffers are static and
the copper lists are static.  Once I allocate the buffers, and write the
copper lists, nothing needs to be changed.  Just read from tape.

So here is what I think the copper list would be like:

; even buffer (a):

cop_list_a1:

	CWAIT	0,TOP_SCREEN-1		; wait for scan line 44

	CMOVE	BPLCON0,(NUM_PLANES<<12)+512
	CMOVE	BPLCON1,0		; shift (none)
	CMOVE	BPLCON2,36		; priority (sprites on top)
	CMOVE	DDFSTRT,$38		; data fetch start
	CMOVE	DDFSTOP,$D0		; data fetch stop

	CMOVE	DIWSTRT,$2C81		; window start
	CMOVE	DIWSTOP,$F4C1		; window stop

	CMOVE	BPL1MOD,PLANE_MODULO	; modulos
	CMOVE	BPL2MOD,PLANE_MODULO	;

	CMOVEL	BPL0PT,plane0a		; bit planes
	CMOVEL	BPL1PT,plane1a		;
	CMOVEL	BPL2PT,plane2a		;
	CMOVEL	BPL3PT,plane3a		;
	CMOVEL	BPL4PT,plane4a		;
	CMOVEL	BPL5PT,plane5a		;

	CMOVEL	SPR0PT,0		; SPRITE POINTERS MUST BE LOADED
	CMOVEL	SPR1PT,0		; EVERY FRAME
	CMOVEL	SPR2PT,0
	CMOVEL	SPR3PT,0
	CMOVEL	SPR4PT,0
	CMOVEL	SPR5PT,0
	CMOVEL	SPR6PT,0
	CMOVEL	SPR7PT,0

	CMOVEL	AUD0LOC,buffer_a_audio_channel_1
	CMOVEL	AUD1LOC,buffer_a_audio_channel_2

; call copper routine for colors

	CMOVEL	COP1LOC,copcolor_a
	CMOVEL	COP2LOC,return1a
	CMOVE	COL1JMP,0		; strobe

return1a:

; wait bottom
	CMOVEL	COP1LOC,cop_list_a2
	CWAIT	255,255 		; wait for "BOVP"

cop_list_a2:

( repeat above )

; call copper routine for colors

	CMOVEL	COP1LOC,copcolor_a
	CMOVEL	COP2LOC,return2a
	CMOVE	COL1JMP,0		; strobe

return2a:

; wait bottom
	CMOVEL	COP1LOC,cop_list_a3
	CWAIT	255,255 		; wait for "BOVP"

cop_list_a3:

...

( repeat above for 20 frames )

cop_list_a20:

; wait bottom
	CMOVE	INTREQ,SET+INTF_COPER	; notify CPU of page flip
( now we flip for double buffer )
	CMOVEL	COP1LOC,cop_list_b1	; flip to other copper list
	CWAIT	255,255 		; wait for "BOVP"

; odd buffer (b):

cop_list_b1:

( this list like buffer a except we reference buffer b )

... (20 frames of copper list)

; wait bottom
	CMOVE	INTREQ,SET+INTF_COPER	; notify CPU of page flip
	CMOVEL	COP1LOC,cop_list_a1	; back to first buffer
	CWAIT	255,255 		; wait for "BOVP"


**************  double buffer in chipmem, filled by DAT read  ***************

buffer_a:

; 48,000 bytes of plane data.
plane0a: DS.B	8000
plane1a: DS.B	8000
plane2a: DS.B	8000
plane3a: DS.B	8000
plane4a: DS.B	8000
plane5a: DS.B	8000

; 68 byte of copper subroutine
copcolor_a:
	CMOVE	COLOR00,$04F
	CMOVE	COLOR01,$09F
	CMOVE	COLOR02,$0FC
	CMOVE	COLOR03,$0F3
	CMOVE	COLOR04,$6F0
	CMOVE	COLOR05,$FF0
	CMOVE	COLOR06,$FB0
	CMOVE	COLOR07,$F70
	CMOVE	COLOR08,$F40
	CMOVE	COLOR09,$F00
	CMOVE	COLOR10,$F05
	CMOVE	COLOR11,$F0A
	CMOVE	COLOR12,$F0E
	CMOVE	COLOR13,$C0F
	CMOVE	COLOR14,$80F
	CMOVE	COLOR15,$40F
	CMOVE	COPJMP2,0		; "return"
; (actually just a DS.B 68, but this is what is read off tape)


; 10,800 bytes audio data
buffer_a_audio_channel_1: DS.B 5400
buffer_a_audio_channel_2: DS.B 5400

; total: 58,868 bytes per buffer, loaded from DAT and swapped 3 times/sec.

buffer_b:

; repeat as above


Now if I only had enough video frames to actually do an animation!  (months
of Rayshade!) If I get motivated, I'll just use some little repeated
sequence of frames just to prove the viability of the idea.

DAT tapes come in 60, 90, and 120 minutes.  A feature length movie, at
3 fps.  If you could stand 160x100, you'd have 12 fps.  Tolerable.


-- Jay Dresser, jdresser@altair88.net.netcom.com
Xref: sparky comp.sys.amiga.programmer:17479 comp.sys.amiga.hardware:21711