Work in progress

This commit is contained in:
alpine9000
2016-04-14 20:01:42 +10:00
parent fc6ed3a4b6
commit 8e896e1017
22 changed files with 1821 additions and 0 deletions
+54
View File
@@ -0,0 +1,54 @@
EXAMPLE_NAME=game1
# userstack used by bootblock
USERSTACK_ADDRESS=7fffc
# if you change this you must also change link.script.x
BASE_ADDRESS=4000
# note: this must be high enough not to conflict with MFMbufE
NUM_COLORS=8
BOOTBLOCK_ASM=alpine_bootblock.s
OBJS=out/init.o out/utils.o out/image.o out/blit.o
#IMAGES=gigi_full.png
#IMAGEDATA=$(addprefix out/, $(IMAGES:.png=.bin))
#SIZEDIMAGEDATA=$(addprefix out/, $(IMAGES:.png=.sized.png))
TILEMAPS=foreground.png background.png
TILEMAPDATA=$(addprefix out/, $(TILEMAPS:.png=.bin))
VASM_EXTRA_ARGS=-DNUM_COLORS=$(NUM_COLORS)
#SYMBOL_INFO=-M
LINKER_OPTIONS=-T link.script.x
include ../shared/base.mk
#out/%.sized.png: ../assets/%.png
# $(RESIZE) --width=352 --height=256 --blur=0.75 --input=$< --output=$@
out/%.bin: out/%.sized.png
$(IMAGECON) --input $< $(IMAGECON_ARGS) --quantize --colors $(NUM_COLORS) --output-bitplanes --output-palette-asm --output-grey-palette --output-palette $(DITHER) --output out/$*
out/foreground.bin: assets/tilemap.png
$(IMAGECON) --use-palette=assets/foreground.pal --input $< $(IMAGECON_ARGS) --colors $(NUM_COLORS) --output-bitplanes --output-palette --full-color-palette-file --output-palette-asm --output-grey-palette --output-palette --output-png --output out/foreground
out/background.bin: assets/tilemap.png
$(IMAGECON) --use-palette=assets/background.pal --input $< $(IMAGECON_ARGS) --colors $(NUM_COLORS) --output-bitplanes --output-palette --full-color-palette-file --output-palette-asm --output-grey-palette --output-palette --output-png --output out/background
out/tilemap-palette.s: assets/tilemap.png
$(IMAGECON) --use-palette=assets/palette.pal --full-color-palette-file --input=assets/tilemap.png --output-palette-asm --output=out/tilemap
out/foreground-map.s: foreground.tmx
../tools/mapgen/out/mapgen --depth=3 --input=foreground.tmx
mv foreground-map.s out
out/background-map.s: background.tmx
../tools/mapgen/out/mapgen --depth=3 --input=background.tmx
mv background-map.s out
out/blit.o: constants.i macros.i
out/main.o: out/background-map.s out/foreground-map.s $(TILEMAPDATA) $(IMAGEDATA) constants.i macros.i Makefile link.script.x assets/palette.pal out/tilemap-palette.s
out/init.o: constants.i Makefile
+13
View File
@@ -0,0 +1,13 @@
first simple game
=================
screenshot
----------
![Screenshot](screenshot.png?raw=true)
try it
------
* [Download disk image](bin/game1.adf?raw=true)
* <a href="http://alpine9000.github.io/ScriptedAmigaEmulator/#amiga_examples/game1.adf" target="_blank">Run in SAE</a>
+352
View File
@@ -0,0 +1,352 @@
*** hardware trackloader bootblock
*** original BootLoader.S by Photon ;NOTE: PC-relative code is PREFERRED.
*** see http://coppershade.org/asmskool/SOURCES/Photon-snippets/DDE5-BootLoader.S
*** this version hacked by alpine9000
include "../include/registers.i"
LoaderVars equ $100 ;Useful variables, see CPUinfo:
Loader equ $120 ;start of load script
MyUserStack equ USERSTACK_ADDRESS ;SSP is at a safe place, but set user
;stack.
MFMsync equ $4489 ;AmigaDOS standard sync marker.
MFMlen equ 12980 ;Legacy trackdata read length in bytes
ShortWt:MACRO ;CPU-independent nop;nop replacement
tst.w (a6)
ENDM
*** Boot Block starts here ***
Boot: dc.b 'DOS',0
dc.l 0,880
BootCode: ;gathers some data, turns off OS, copies itself to $100
*--- Fetch system info ---*
move.l 4.w,a6 ;execbase (will soon be destroyed)
move.l 294(a6),d4 ;CPUinfo in lowest byte for your use.
sub.l a4,a4 ;VBR will always be 0 when booting
;from floppy. No GetVBR needed.
*--- Fastmem available? ---*
if 1
move.l #$20004,d1 ;fast+largest
else
move.l #$20002,d1 ;chip+largest
endif
jsr -216(a6) ;AvailMem()
move.l d0,d5
sub.l #2048,d5 ;leave room for stacks to grow
moveq #4,d1
jsr -198(a6) ;AllocMem()
and.l #-8,d0
move.l d0,a5 ;Start Address
*--- OS off ---* ;you're nice'n all, but now you die.
lea $dff002,a6 ;Loader uses this custom base addr
tst.w (a6) ;wait out blitter
.wblit: btst #6,(a6)
bne.s .wblit
move.l #$7fff7fff,d1
move.l d1,$9a-2(a6) ;disable interrupts & req
move.w d1,$9c-2(a6) ;play it again Sam
sub.w #$20,d1 ;don't affect Sprite DMA until Vblank
move.w d1,$96-2(a6) ;disable DMA
lea MyUserStack,a7 ;some safe place compatible with
;platform requirements
*--- Copy rest of code/data to fixed address ---*
lea CopyStart(PC),a0
lea (LoaderVars).w,a1
moveq #(BootE-CopyStart)/8,d2
.copyl: move.l (a0)+,(a1)+
move.l (a0)+,(a1)+
dbf d2,.copyl
JMP (Loader).w ;Info from Exec passed in 4 registers
******************** $100.w ********************
CopyStart:
CPUinfo: dc.l 0 ;$100
FastMemSize: dc.l 0 ;$104
SysVBR: dc.l 0 ;$108
FastMemStart: dc.l 0 ;$10c
MFMcyl: dc.w 0
MFMhead: dc.w 0
MFMdrv: dc.w 0
MFMchk: dc.l 0
dc.w 0 ;padding to $120
dc.w 0 ;
dc.w 0 ;
LoadScript: ;At $120, sysinfo in 4 regs, a6=$dff002
lea CPUinfo(PC),a3 ;Use this for PC-rel in a pinch.
movem.l d4/d5/a4/a5,(a3)
bsr.s WaitEOF
lea NullCop(PC),a0
move.l a0,$80-2(a6) ;blank copper
move.w #$87d0,$96-2(a6) ;enable DMA (sprites enabled when used)
*--- load first part ---*
lea BASE_ADDRESS,a0 ; main entry point
if 1
moveq #2,d0 ;from sector 2
move.w #-1,d1 ;num sectors, - ==Step0
jsr LoadMFMB
move.l 4(a0),d1
add.l #512,d1
lsr.l #6,d1
lsr.l #3,d1
moveq #2,d0 ;from sector 2
jsr LoadMFMB
lea $dff000,a6 ;restore plain custombase addr for demo
move.l (a0),a0
jmp (a0) ; -> main entry point
else
-moveq #2,d0 ;from sector 2
move.w #-((mainEnd-mainStart)/512),d1;num sectors, - ==Step0
jsr LoadMFMB
jmp (a0) ; -> main entry point
endif
*** MFMLoader.S by Photon *** ;requires a6=$dff002
WaitEOF:
btst #0,5-2(a6)
beq.s WaitEOF
.w1: cmp.b #$37,6-2(a6)
bne.s .w1
.w2: cmp.b #$37,6-2(a6) ;wait for last PAL line, $138
beq.s .w2
rts
LoadMFMB: ;loadsectors.a0=dst,d0=startsec.W,d1=nrsecs.W(-=Step0)
MOVEM.L D0-D7/A0-A6,-(SP)
lea $bfd100,a4
bsr MotorOn
tst.w d1 ;if neg length,then Step0 first
bpl.s .NoSt0
neg.w d1
.St0: btst #4,$f01(a4) ;head on cyl 0?
beq.s .Rdy0
bsr.s StepOut
bra.s .St0
.Rdy0: lea MFMcyl(PC),a1
clr.w (a1)
.NoSt0: and.l #$ffff,d0
divu #22,d0 ;startcyl
sub.w MFMcyl(PC),d0 ;delta-step
beq.s .StRdy
bmi.s .StOut
subq.w #1,d0
.StIn: bsr.s StepIn
dbf d0,.StIn
bra.s .StRdy
not.w d0 ;=neg+sub#1
.StOut: bsr.s StepOut
dbf d0,.StIn
.StRdy: swap d0 ;startsec within cyl
cmp.w #11,d0
blt.s .Head0
sub.w #11,d0
bra.s .Head1
.Head0: bset #2,(a4)
lea MFMhead(PC),a1
clr.w (a1)
bsr LoadTrak ;read track+decode
beq.s .End
.Head1: bclr #2,(a4) ;Head 1
lea MFMhead(PC),a1
move.w #1,(a1)
bsr LoadTrak ;read track+decode
beq.s .End
bsr.s StepIn ;1 cyl forward
bra.s .Head0
.End: bsr.s MotorOff
MOVEM.L (SP)+,D0-D7/A0-A6
RTS
StepOut:
bset #1,(a4)
lea MFMcyl(PC),a1
subq.w #1,(a1)
ShortWt
bclr #0,(a4)
ShortWt
bset #0,(a4)
bsr.s StepWt
RTS
StepIn:
bclr #1,(a4)
lea MFMcyl(PC),a1
addq.w #1,(a1)
ShortWt
bclr #0,(a4)
ShortWt
bset #0,(a4)
bsr.s StepWt
RTS
StepWt:
moveq #67,d6 ;wait >3 ms
LeaveLine:
.loop1: move.b 6-2(a6),d7
.loop2: cmp.b 6-2(a6),d7
beq.s .loop2
dbf d6,.loop1
RTS
MotorOn:
move.w MFMdrv(PC),d7
addq.w #3,d7
or.b #$78,(a4)
bset d7,(a4)
ShortWt
bclr #7,(a4) ;turns motor on
ShortWt
bclr d7,(a4)
ShortWt
.DiskR: btst #5,$f01(a4) ;wait until motor running
bne.s .DiskR
RTS
MotorOff:
move.w MFMdrv(PC),d7
addq.w #3,d7
bset d7,(a4)
ShortWt
bset #7,(a4)
ShortWt
bclr d7,(a4)
RTS
LoadTrak: ;loadtrack+decode.a0=dst,d0=secoffs,d1=secsleft
MOVE.W D0,-(SP)
MOVE.W D1,-(SP)
;; lea (MFMbuf).w,a1
lea (MFMbuf),a1
move.w #2,$9c-2(a6) ;Clr Req
move.l a1,$20-2(a6)
move.w #$8210,$96-2(a6) ;DskEna
move.w #MFMsync,$7e-2(a6)
move.w #$9500,$9e-2(a6)
move.w #$4000,$24-2(a6)
move.w #$8000+MFMlen/2,$24-2(a6);DskLen(12980)+DmaEn
move.w #$8000+MFMlen/2,$24-2(a6);start reading MFMdata
.Wrdy:
btst #1,$1f-2(a6) ;wait until data read
beq.s .Wrdy
move.w d0,d2
add.w d1,d2 ;highest sec# (d0=lowest)
cmp.w #11,d2
ble.s .NoOvr
moveq #11,d2
.NoOvr: sub.w d0,d2 ;nrsecs
move.l #$55555555,d3 ;and-const
move.w d2,d1
subq.w #1,d1 ;loopctr
.FindS: cmp.w #MFMsync,(a1)+ ;search for a sync word
bne.s .FindS
cmp.b (a1),d3 ;search for 0-nibble
bne.s .FindS
move.l (a1)+,d4 ;decode fmtbyte/trk#,sec#,eow#
move.l (a1)+,d5
and.w d3,d4
and.w d3,d5
add.w d4,d4
or.w d5,d4
lsr.w #8,d4 ;sec#
sub.w d0,d4 ;do we want this sec?
bmi.s .Skip
cmp.w d2,d4
blt.s .DeCode
.Skip: lea 48+1024(a1),a1 ;nope
bra.s .FindS
.DeCode:lea 40(a1),a1 ;found a sec,skip unnecessary data
move.l a1,d6
lea MFMchk(PC),a1
clr.l (a1)
move.l d6,a1
move.l (a1)+,d6 ;decode data chksum.L
move.l (a1)+,d5
and.l d3,d6
and.l d3,d5
add.l d6,d6
or.l d5,d6 ;chksum
lea 512(a1),a2
add.w d4,d4 ;x512
lsl.w #8,d4
lea (a0,d4.w),a3 ;dest addr for this sec
moveq #127,d7
.DClup: move.l (a1)+,d4
move.l (a2)+,d5
and.l d3,d4
and.l d3,d5
eor.l d4,d6 ;EOR with checksum
eor.l d5,d6 ;EOR with checksum
add.l d4,d4
or.l d5,d4
move.l d4,(a3)+
dbf d7,.DClup ;chksum should now be 0 if correct
lea MFMchk(PC),a1
or.l d6,(a1) ;or with track total chksum
move.l a2,a1
dbf d1,.FindS ;decode next sec
MOVE.W (SP)+,D1
MOVE.W (SP)+,D0
move.l MFMchk(PC),d3 ;track total chksum OK?
bne LoadTrak ;no,retry
moveq #0,d0 ;set to start of track
move.w d2,d3
add.w d3,d3
lsl.w #8,d3
add.w d3,a0
sub.w d2,d1 ;sub #secs loaded
RTS
NullCop:
dc.w $1fc,0
dc.w $100,$0200
dc.w $96,$0020 ;ensure sprite DMA is off until needed
dc.w $ffdf,$fffe
dc.l -2
BootE:
*** Boot Block ends here ***
dc.b "BootLoader by Photon/Scoopex"
;pad bootblock to correct size
cnop 0,1024
;MFMbuf is placed here after bootblock end, $3c0.w or so when copied.
MFMbuf equ LoaderVars+(BootE-CopyStart)
MFMbufE equ MFMbuf+MFMlen ;lowest free address. $372e for a full bootblock.
mainStart:
incbin "out/main.bin"
cnop 0,512
mainEnd:
end
+8
View File
@@ -0,0 +1,8 @@
000 000 014 255
029 192 255 255
121 235 255 255
071 174 192 255
213 213 213 255
210 000 039 255
154 154 154 255
000 000 000 000
+8
View File
@@ -0,0 +1,8 @@
000 000 000 255
082 000 015 255
133 000 026 255
210 063 006 255
211 116 039 255
253 174 017 255
233 216 100 255
016 132 233 255
Binary file not shown.

After

Width:  |  Height:  |  Size: 4.4 KiB

+25
View File
@@ -0,0 +1,25 @@
000 000 000 255
082 000 015 255
133 000 026 255
210 063 006 255
211 116 039 255
253 174 017 255
233 216 100 255
016 132 233 255
000 000 014 255
029 192 255 255
121 235 255 255
071 174 192 255
213 213 213 255
210 000 039 255
154 154 154 255
000 000 000 000
232 174 100 255
252 114 100 255
171 049 027 255
004 050 117 255
020 155 173 255
030 236 255 255
252 115 009 255
255 255 011 255
255 255 255 255
Binary file not shown.

After

Width:  |  Height:  |  Size: 8.7 KiB

+11
View File
@@ -0,0 +1,11 @@
<?xml version="1.0" encoding="UTF-8"?>
<map version="1.0" orientation="orthogonal" renderorder="left-down" width="100" height="16" tilewidth="16" tileheight="16" nextobjectid="1">
<tileset firstgid="1" name="tilemap" tilewidth="16" tileheight="16" tilecount="320" columns="20">
<image source="assets/tilemap.png" width="320" height="256"/>
</tileset>
<layer name="background" width="100" height="16">
<data encoding="base64" compression="zlib">
eJztmMsNwjAMhrMAQxSVxwK8WYHHAiB1BNj/gC8VUhSc346bJhWH71I1ru3Yzt90zrkOpA08exBP5dqeveBdbh3HglgSK2IN2gvF5vsm8SHFT/Q7L+Jt7JPPzsDGgTgSJ+KcITbf534fY3Wh8ZPDul44GmIOvnshrsSNuGf0UZpvqZ+afIfqG5kfMTbEdsTcauLg8m0xB4aqkxJA8lNDHAilzI+pxIH0qVX/oRpuCvj6bQauy9mnVhoOja1GSunTVNDzuHG4luOwsmONpZZIsYX2uUTLcX1YgiYsmZr73OKf4c+XVJ0iOcM1Z2fj5LO1phrxc/JLp7TgXqX0NmJfM1ulOk+z52PUQ2iv0HtWrX0LpDWScp6Gep6rB8v8aRjy+1oNJblv09zNxerBz0nsvv4DB9VA2Q==
</data>
</layer>
</map>
+161
View File
@@ -0,0 +1,161 @@
include "includes.i"
xdef BlitFillColor
xdef BlitScroll
xdef BlitTile
xref BlueFill
;; A(mask) B(bob) C(bg) D(dest)
;; - - - -
;; 0 0 0 0
;; 0 0 1 1
;; 0 1 0 0
;; 0 1 1 1
;; 1 0 0 0
;; 1 0 1 0
;; 1 1 0 1
;; 1 1 1 1
BlitFillColor:
;; kills a0,d2,d3,d5,d5
;; a0 - bitplane
;; d0 - color#
;; d1 - height
;; d2 - ypos
movem.l d2-d5/a0,-(sp)
mulu.w #BITPLANE_WIDTH_BYTES*SCREEN_BIT_DEPTH,d2
add.l d2,a0
move.b #0,d3 ; bitplane #
.loop:
move.w d1,d4
btst d3,d0 ; is the color's bit set in this plane?
beq .zero
move.w #BC0F_DEST|$FF,d5 ; yes ? all ones
bra .doblit
.zero
move.w #BC0F_DEST|$0,d5 ; no ? all zeros
.doblit
WaitBlitter
move.w #0,BLTCON1(A6)
move.w d5,BLTCON0(A6)
move.w #BITPLANE_WIDTH_BYTES*(SCREEN_BIT_DEPTH-1),BLTDMOD(a6)
move.l a0,BLTDPTH(a6)
lsl.w #6,d4
ori.w #BITPLANE_WIDTH_WORDS,d4
move.w d4,BLTSIZE(a6)
add.b #1,d3
add.w #BITPLANE_WIDTH_BYTES,a0
cmp.b #SCREEN_BIT_DEPTH,d3 ; all planes for a single line done ?
bne .loop ; no ? do the next plane
movem.l (sp)+,d2-d5/a0
rts
_BlitScroll:
;; left scroll a screen wide region
;; a0 - dest bitplane pointer
;; a1 - source bitplane pointer
;; d0 - number of pixels to left shift on blit
;; d1 - height in pixels
;; d2 - y destination in pixels
movem.l d0-d2/a0-a1,-(sp)
add.l d1,d2 ; point to end of data for descending mode
mulu.w #BITPLANE_WIDTH_BYTES*SCREEN_BIT_DEPTH,d2
add.l d2,a0 ; end of dest bitplane
add.l d2,a1 ; end of source bitplane
WaitBlitter
swap d0 ; lsl.l #ASHIFTSHIFT,d0
lsr.l #4,d0 ; d0 has ASHIFTSHIFT bits set
ori.w #BC1F_DESC,d0 ; BLTCON1 value. shift and descending mode
move.w d0,BLTCON1(a6) ;
and.w #$f000,d0 ; keep the shift, remove the rest
ori.w #BC0F_SRCB|BC0F_SRCC|BC0F_DEST|$ca,d0 ; BLTCON0 value. shift, dma and logic function
move.w d0,BLTCON0(a6)
move.w #0,BLTBMOD(a6) ; no modulo, blitting full width data
move.w #0,BLTCMOD(a6) ;
move.w #0,BLTDMOD(a6) ;
move.l a1,BLTBPTH(a6) ; source
move.l a1,BLTCPTH(a6) ; background
move.l a0,BLTDPTH(a6) ; dest
move.w #$0000,BLTAFWM(a6) ; A DMA is disabled, but the channel is still used in the logic function
move.w #$ffff,BLTALWM(a6) ; as we use it for masking
move.w #$ffff,BLTADAT(a6) ; preload source mask so only BLTA?WM mask is used
mulu.w #SCREEN_BIT_DEPTH,d1
lsl.w #6,d1
ori.w #BITPLANE_WIDTH_WORDS,d1
move.w d1,BLTSIZE(a6)
movem.l (sp)+,d0-d2/a0-a1
rts
BlitTile:
;; a0 - dest bitplane pointer
;; a1 - source tile pointer
;; d2 - y tile index
WaitBlitter
movem.l d2/a0,-(sp)
move.w #0,BLTCON1(a6) ;
move.w #BC0F_SRCA|BC0F_DEST|$f0,BLTCON0(a6)
move.w #TILEMAP_WIDTH_BYTES-2,BLTAMOD(a6)
move.w #BITPLANE_WIDTH_BYTES-2,BLTDMOD(a6) ;
mulu.w #BITPLANE_WIDTH_BYTES*SCREEN_BIT_DEPTH*16,d2
add.l d2,a0
move.l a1,BLTAPTH(a6) ; source
move.l a0,BLTDPTH(a6) ; dest
move.w #$ffff,BLTAFWM(a6)
move.w #$ffff,BLTALWM(a6)
move.w #(16*SCREEN_BIT_DEPTH)<<6|(1),BLTSIZE(a6) ;rectangle size, starts blit
movem.l (sp)+,d2/a0
rts
BlueFill:
movem.l d0-a6,-(sp)
;; a0 - bitplane
;; d0 - color#
;; d1 - height
;; d2 - ypos
move.l foregroundOffscreen,a0
move.l #0,d0
move.l #256,d1
move.l #0,d2
jsr BlitFillColor
jsr WaitVerticalBlank
jsr SwitchBuffers
move.l foregroundOffscreen,a0
move.l #0,d0
move.l #256,d1
move.l #0,d2
jsr BlitFillColor
jsr WaitVerticalBlank
jsr SwitchBuffers
move.l backgroundOffscreen,a0
move.l #0,d0
move.l #256,d1
move.l #0,d2
jsr BlitFillColor
jsr WaitVerticalBlank
jsr SwitchBuffers
move.l backgroundOffscreen,a0
move.l #0,d0
move.l #256,d1
move.l #0,d2
jsr BlitFillColor
movem.l (sp)+,d0-a6
rts
+87
View File
@@ -0,0 +1,87 @@
include "includes.i"
xdef BlitChar8
DESCENDING equ 1
BLIT_LF_MINTERM equ $ca ; cookie cut
BLIT_WIDTH_WORDS equ 1 ; blit 2 words to allow shifting
BLIT_WIDTH_BYTES equ BLIT_WIDTH_WORDS*2
FONTMAP_WIDTH_BYTES equ 32
if MASKED_FONT==1
BLTCON0_VALUE equ BC0F_SRCA|BC0F_SRCB|BC0F_SRCC|BC0F_DEST|BLIT_LF_MINTERM
else
BLTCON0_VALUE equ BC0F_SRCB|BC0F_SRCC|BC0F_DEST|BLIT_LF_MINTERM
endif
BlitChar8:
;; a0 - bitplane
;; d0 - xpos
;; d1 - ypos
;; d2 - char
movem.l d0-d3/a0-a2,-(sp)
mulu.w #BITPLANE_WIDTH_BYTES*SCREEN_BIT_DEPTH,d1 ; ypos bytes
lea font(pc),a1 ; font pointer
sub.w #'!',d2 ; index = char - '!'
move.w d2,d3
lsr.w #5,d3 ; char / 32 = fontmap line
andi.w #$1f,d2 ; char index in line (char index - start of line index)
add.l #1,d3 ; while we have a weird font image, '!' starts on second line
mulu.w #FONTMAP_WIDTH_BYTES*SCREEN_BIT_DEPTH*FONT_HEIGHT,d3 ; d3 *= #FONTMAP_WIDTH_BYTES*SCREEN_BIT_DEPTH*FONT_HEIGHT
add.l #(FONT_HEIGHT*SCREEN_BIT_DEPTH*FONTMAP_WIDTH_BYTES)-FONTMAP_WIDTH_BYTES+0,a1 ; last word - descending mode
add.w d3,a1 ; add y offset in lines to font address
add.w d2,a1 ; add offset into font
lsr.w #3,d0 ; d0 = xpos bytes
add.l d0,a0 ; dest += XPOS_BYTES
add.l d1,a0 ; dest += YPOS_BYTES
add.l #(FONT_HEIGHT*SCREEN_BIT_DEPTH*BITPLANE_WIDTH_BYTES)-BITPLANE_WIDTH_BYTES+0,a0 ; last word - descending mode
WaitBlitter
if MASKED_FONT==1
move.w #FONTMAP_WIDTH_BYTES-BLIT_WIDTH_BYTES,BLTAMOD(a6) ; A modulo (only used for masked version)
endif
move.w #FONTMAP_WIDTH_BYTES-BLIT_WIDTH_BYTES,BLTBMOD(a6) ; B modulo
move.w #BITPLANE_WIDTH_BYTES-BLIT_WIDTH_BYTES,BLTCMOD(a6) ; C modulo
move.w #BITPLANE_WIDTH_BYTES-BLIT_WIDTH_BYTES,BLTDMOD(a6) ; D modulo
move.w #$ffff,BLTAFWM(a6) ; don't mask first word
btst #0,d2 ; check if odd or even char
beq .evenChar ;
.oddChar:
move.w #$00ff,BLTALWM(a6) ; select the second (odd) character in the word
move.w #BLTCON0_VALUE|$8000,BLTCON0(a6)
move.w #$8002,BLTCON1(a6) ; set the shift bits 12-15, bits 00-11 cleared
bra .continue
.evenChar:
move.w #$FF00,BLTALWM(a6) ; select the first character in the word
move.w #BLTCON0_VALUE,BLTCON0(a6)
move.w #$2,BLTCON1(a6) ; set the shift bits 12-15, bits 00-11 cleared
.continue:
move.l a1,BLTBPTH(a6) ; source bitplane
if MASKED_FONT==1
add.l #fontMask-font,a1
move.l a1,BLTAPTH(a6) ; mask bitplane
endif
move.l a0,BLTCPTH(a6) ; background top left corner
move.l a0,BLTDPTH(a6) ; destination top left corner
move.w #(FONT_HEIGHT*SCREEN_BIT_DEPTH)<<6|(BLIT_WIDTH_WORDS),BLTSIZE(a6) ;rectangle size, starts blit
movem.l (sp)+,d0-d3/a0-a2
rts
font:
incbin "out/font8x8.bin"
fontMask:
incbin "out/font8x8-mask.bin"
+39
View File
@@ -0,0 +1,39 @@
BACKGROUND_UPDATE_COUNT equ $3
FOREGROUND_DELAY_BIT equ 0
SCREEN_WIDTH equ 320
SCREEN_HEIGHT equ 256
SCREEN_WIDTH_BYTES equ (SCREEN_WIDTH/8)
SCREEN_WIDTH_WORDS equ SCREEN_WIDTH_BYTES/2
BITPLANE_WIDTH equ 352
BITPLANE_WIDTH_BYTES equ BITPLANE_WIDTH/8
BITPLANE_WIDTH_WORDS equ BITPLANE_WIDTH_BYTES/2
TILEMAP_WIDTH equ 320
TILEMAP_WIDTH_BYTES equ TILEMAP_WIDTH/8
TILEMAP_WIDTH_WORDS equ TILEMAP_WIDTH_BYTES/2
if NUM_COLORS==64
SCREEN_BIT_DEPTH equ 6
endif
if NUM_COLORS==32
SCREEN_BIT_DEPTH equ 5
endif
if NUM_COLORS==16
SCREEN_BIT_DEPTH equ 4
endif
if NUM_COLORS==8
SCREEN_BIT_DEPTH equ 3
endif
if NUM_COLORS==4
SCREEN_BIT_DEPTH equ 2
endif
if NUM_COLORS==2
SCREEN_BIT_DEPTH equ 1
endif
SCREEN_RES equ 8 ; 8=lo resolution, 4=hi resolution
RASTER_X_START equ $81 ; hard coded coordinates from hardware manual
RASTER_Y_START equ $2c
RASTER_X_STOP equ RASTER_X_START+SCREEN_WIDTH
RASTER_Y_STOP equ RASTER_Y_START+256
IMAGESIZE equ BITPLANE_WIDTH_BYTES*SCREEN_BIT_DEPTH*SCREEN_HEIGHT
+516
View File
@@ -0,0 +1,516 @@
dc.w $2c07,$fffe
dc.w COLOR01,$7dd
dc.w $2d07,$fffe
dc.w COLOR01,$9ec
dc.w $2e07,$fffe
dc.w COLOR01,$beb
dc.w $2f07,$fffe
dc.w COLOR01,$ce9
dc.w $3007,$fffe
dc.w COLOR01,$ed7
dc.w $3107,$fffe
dc.w COLOR01,$eb5
dc.w $3207,$fffe
dc.w COLOR01,$e93
dc.w $3307,$fffe
dc.w COLOR01,$d71
dc.w $3407,$fffe
dc.w COLOR01,$c50
dc.w $3507,$fffe
dc.w COLOR01,$a30
dc.w $3607,$fffe
dc.w COLOR01,$820
dc.w $3707,$fffe
dc.w COLOR01,$611
dc.w $3807,$fffe
dc.w COLOR01,$403
dc.w $3907,$fffe
dc.w COLOR01,$204
dc.w $3a07,$fffe
dc.w COLOR01,$116
dc.w $3b07,$fffe
dc.w COLOR01,$029
dc.w $3c07,$fffe
dc.w COLOR01,$04a
dc.w $3d07,$fffe
dc.w COLOR01,$16c
dc.w $3e07,$fffe
dc.w COLOR01,$28d
dc.w $3f07,$fffe
dc.w COLOR01,$3ae
dc.w $4007,$fffe
dc.w COLOR01,$5ce
dc.w $4107,$fffe
dc.w COLOR01,$7dd
dc.w $4207,$fffe
dc.w COLOR01,$9ec
dc.w $4307,$fffe
dc.w COLOR01,$beb
dc.w $4407,$fffe
dc.w COLOR01,$de9
dc.w $4507,$fffe
dc.w COLOR01,$ed6
dc.w $4607,$fffe
dc.w COLOR01,$eb4
dc.w $4707,$fffe
dc.w COLOR01,$e93
dc.w $4807,$fffe
dc.w COLOR01,$d71
dc.w $4907,$fffe
dc.w COLOR01,$c50
dc.w $4a07,$fffe
dc.w COLOR01,$a30
dc.w $4b07,$fffe
dc.w COLOR01,$820
dc.w $4c07,$fffe
dc.w COLOR01,$611
dc.w $4d07,$fffe
dc.w COLOR01,$403
dc.w $4e07,$fffe
dc.w COLOR01,$204
dc.w $4f07,$fffe
dc.w COLOR01,$117
dc.w $5007,$fffe
dc.w COLOR01,$029
dc.w $5107,$fffe
dc.w COLOR01,$04b
dc.w $5207,$fffe
dc.w COLOR01,$16c
dc.w $5307,$fffe
dc.w COLOR01,$28d
dc.w $5407,$fffe
dc.w COLOR01,$3ae
dc.w $5507,$fffe
dc.w COLOR01,$5ce
dc.w $5607,$fffe
dc.w COLOR01,$7dd
dc.w $5707,$fffe
dc.w COLOR01,$9ec
dc.w $5807,$fffe
dc.w COLOR01,$bea
dc.w $5907,$fffe
dc.w COLOR01,$de8
dc.w $5a07,$fffe
dc.w COLOR01,$ed6
dc.w $5b07,$fffe
dc.w COLOR01,$eb4
dc.w $5c07,$fffe
dc.w COLOR01,$e93
dc.w $5d07,$fffe
dc.w COLOR01,$d71
dc.w $5e07,$fffe
dc.w COLOR01,$c50
dc.w $5f07,$fffe
dc.w COLOR01,$a30
dc.w $6007,$fffe
dc.w COLOR01,$820
dc.w $6107,$fffe
dc.w COLOR01,$601
dc.w $6207,$fffe
dc.w COLOR01,$403
dc.w $6307,$fffe
dc.w COLOR01,$205
dc.w $6407,$fffe
dc.w COLOR01,$117
dc.w $6507,$fffe
dc.w COLOR01,$029
dc.w $6607,$fffe
dc.w COLOR01,$04b
dc.w $6707,$fffe
dc.w COLOR01,$16c
dc.w $6807,$fffe
dc.w COLOR01,$28d
dc.w $6907,$fffe
dc.w COLOR01,$3ae
dc.w $6a07,$fffe
dc.w COLOR01,$5ce
dc.w $6b07,$fffe
dc.w COLOR01,$7dd
dc.w $6c07,$fffe
dc.w COLOR01,$9ec
dc.w $6d07,$fffe
dc.w COLOR01,$bea
dc.w $6e07,$fffe
dc.w COLOR01,$de8
dc.w $6f07,$fffe
dc.w COLOR01,$ec6
dc.w $7007,$fffe
dc.w COLOR01,$eb4
dc.w $7107,$fffe
dc.w COLOR01,$e92
dc.w $7207,$fffe
dc.w COLOR01,$d71
dc.w $7307,$fffe
dc.w COLOR01,$b50
dc.w $7407,$fffe
dc.w COLOR01,$a30
dc.w $7507,$fffe
dc.w COLOR01,$810
dc.w $7607,$fffe
dc.w COLOR01,$601
dc.w $7707,$fffe
dc.w COLOR01,$403
dc.w $7807,$fffe
dc.w COLOR01,$205
dc.w $7907,$fffe
dc.w COLOR01,$117
dc.w $7a07,$fffe
dc.w COLOR01,$029
dc.w $7b07,$fffe
dc.w COLOR01,$04b
dc.w $7c07,$fffe
dc.w COLOR01,$16c
dc.w $7d07,$fffe
dc.w COLOR01,$28d
dc.w $7e07,$fffe
dc.w COLOR01,$3ae
dc.w $7f07,$fffe
dc.w COLOR01,$5ce
dc.w $8007,$fffe
dc.w COLOR01,$7dd
dc.w $8107,$fffe
dc.w COLOR01,$aec
dc.w $8207,$fffe
dc.w COLOR01,$bea
dc.w $8307,$fffe
dc.w COLOR01,$dd8
dc.w $8407,$fffe
dc.w COLOR01,$ec6
dc.w $8507,$fffe
dc.w COLOR01,$eb4
dc.w $8607,$fffe
dc.w COLOR01,$e92
dc.w $8707,$fffe
dc.w COLOR01,$d71
dc.w $8807,$fffe
dc.w COLOR01,$b50
dc.w $8907,$fffe
dc.w COLOR01,$a30
dc.w $8a07,$fffe
dc.w COLOR01,$810
dc.w $8b07,$fffe
dc.w COLOR01,$501
dc.w $8c07,$fffe
dc.w COLOR01,$303
dc.w $8d07,$fffe
dc.w COLOR01,$205
dc.w $8e07,$fffe
dc.w COLOR01,$117
dc.w $8f07,$fffe
dc.w COLOR01,$029
dc.w $9007,$fffe
dc.w COLOR01,$04b
dc.w $9107,$fffe
dc.w COLOR01,$16c
dc.w $9207,$fffe
dc.w COLOR01,$28d
dc.w $9307,$fffe
dc.w COLOR01,$4ae
dc.w $9407,$fffe
dc.w COLOR01,$6ce
dc.w $9507,$fffe
dc.w COLOR01,$8dd
dc.w $9607,$fffe
dc.w COLOR01,$aec
dc.w $9707,$fffe
dc.w COLOR01,$bea
dc.w $9807,$fffe
dc.w COLOR01,$dd8
dc.w $9907,$fffe
dc.w COLOR01,$ec6
dc.w $9a07,$fffe
dc.w COLOR01,$eb4
dc.w $9b07,$fffe
dc.w COLOR01,$e92
dc.w $9c07,$fffe
dc.w COLOR01,$d71
dc.w $9d07,$fffe
dc.w COLOR01,$b50
dc.w $9e07,$fffe
dc.w COLOR01,$930
dc.w $9f07,$fffe
dc.w COLOR01,$710
dc.w $a007,$fffe
dc.w COLOR01,$502
dc.w $a107,$fffe
dc.w COLOR01,$303
dc.w $a207,$fffe
dc.w COLOR01,$205
dc.w $a307,$fffe
dc.w COLOR01,$117
dc.w $a407,$fffe
dc.w COLOR01,$029
dc.w $a507,$fffe
dc.w COLOR01,$04b
dc.w $a607,$fffe
dc.w COLOR01,$16c
dc.w $a707,$fffe
dc.w COLOR01,$28e
dc.w $a807,$fffe
dc.w COLOR01,$4ae
dc.w $a907,$fffe
dc.w COLOR01,$6ce
dc.w $aa07,$fffe
dc.w COLOR01,$8dd
dc.w $ab07,$fffe
dc.w COLOR01,$aec
dc.w $ac07,$fffe
dc.w COLOR01,$cea
dc.w $ad07,$fffe
dc.w COLOR01,$dd8
dc.w $ae07,$fffe
dc.w COLOR01,$ec6
dc.w $af07,$fffe
dc.w COLOR01,$eb4
dc.w $b007,$fffe
dc.w COLOR01,$e92
dc.w $b107,$fffe
dc.w COLOR01,$d71
dc.w $b207,$fffe
dc.w COLOR01,$b50
dc.w $b307,$fffe
dc.w COLOR01,$930
dc.w $b407,$fffe
dc.w COLOR01,$711
dc.w $b507,$fffe
dc.w COLOR01,$502
dc.w $b607,$fffe
dc.w COLOR01,$303
dc.w $b707,$fffe
dc.w COLOR01,$205
dc.w $b807,$fffe
dc.w COLOR01,$117
dc.w $b907,$fffe
dc.w COLOR01,$039
dc.w $ba07,$fffe
dc.w COLOR01,$04b
dc.w $bb07,$fffe
dc.w COLOR01,$16d
dc.w $bc07,$fffe
dc.w COLOR01,$29e
dc.w $bd07,$fffe
dc.w COLOR01,$4ae
dc.w $be07,$fffe
dc.w COLOR01,$6ce
dc.w $bf07,$fffe
dc.w COLOR01,$8dd
dc.w $c007,$fffe
dc.w COLOR01,$aec
dc.w $c107,$fffe
dc.w COLOR01,$cea
dc.w $c207,$fffe
dc.w COLOR01,$dd8
dc.w $c307,$fffe
dc.w COLOR01,$ec6
dc.w $c407,$fffe
dc.w COLOR01,$eb4
dc.w $c507,$fffe
dc.w COLOR01,$e92
dc.w $c607,$fffe
dc.w COLOR01,$d61
dc.w $c707,$fffe
dc.w COLOR01,$b40
dc.w $c807,$fffe
dc.w COLOR01,$930
dc.w $c907,$fffe
dc.w COLOR01,$711
dc.w $ca07,$fffe
dc.w COLOR01,$502
dc.w $cb07,$fffe
dc.w COLOR01,$303
dc.w $cc07,$fffe
dc.w COLOR01,$205
dc.w $cd07,$fffe
dc.w COLOR01,$117
dc.w $ce07,$fffe
dc.w COLOR01,$039
dc.w $cf07,$fffe
dc.w COLOR01,$04b
dc.w $d007,$fffe
dc.w COLOR01,$17d
dc.w $d107,$fffe
dc.w COLOR01,$29e
dc.w $d207,$fffe
dc.w COLOR01,$4be
dc.w $d307,$fffe
dc.w COLOR01,$6ce
dc.w $d407,$fffe
dc.w COLOR01,$8dd
dc.w $d507,$fffe
dc.w COLOR01,$aec
dc.w $d607,$fffe
dc.w COLOR01,$cea
dc.w $d707,$fffe
dc.w COLOR01,$dd8
dc.w $d807,$fffe
dc.w COLOR01,$ec6
dc.w $d907,$fffe
dc.w COLOR01,$ea4
dc.w $da07,$fffe
dc.w COLOR01,$e82
dc.w $db07,$fffe
dc.w COLOR01,$d61
dc.w $dc07,$fffe
dc.w COLOR01,$b40
dc.w $dd07,$fffe
dc.w COLOR01,$930
dc.w $de07,$fffe
dc.w COLOR01,$711
dc.w $df07,$fffe
dc.w COLOR01,$502
dc.w $e007,$fffe
dc.w COLOR01,$303
dc.w $e107,$fffe
dc.w COLOR01,$205
dc.w $e207,$fffe
dc.w COLOR01,$017
dc.w $e307,$fffe
dc.w COLOR01,$039
dc.w $e407,$fffe
dc.w COLOR01,$05b
dc.w $e507,$fffe
dc.w COLOR01,$17d
dc.w $e607,$fffe
dc.w COLOR01,$29e
dc.w $e707,$fffe
dc.w COLOR01,$4be
dc.w $e807,$fffe
dc.w COLOR01,$6ce
dc.w $e907,$fffe
dc.w COLOR01,$8dd
dc.w $ea07,$fffe
dc.w COLOR01,$aeb
dc.w $eb07,$fffe
dc.w COLOR01,$cea
dc.w $ec07,$fffe
dc.w COLOR01,$dd8
dc.w $ed07,$fffe
dc.w COLOR01,$ec6
dc.w $ee07,$fffe
dc.w COLOR01,$ea4
dc.w $ef07,$fffe
dc.w COLOR01,$d82
dc.w $f007,$fffe
dc.w COLOR01,$c61
dc.w $f107,$fffe
dc.w COLOR01,$b40
dc.w $f207,$fffe
dc.w COLOR01,$920
dc.w $f307,$fffe
dc.w COLOR01,$711
dc.w $f407,$fffe
dc.w COLOR01,$502
dc.w $f507,$fffe
dc.w COLOR01,$303
dc.w $f607,$fffe
dc.w COLOR01,$105
dc.w $f707,$fffe
dc.w COLOR01,$017
dc.w $f807,$fffe
dc.w COLOR01,$03a
dc.w $f907,$fffe
dc.w COLOR01,$05b
dc.w $fa07,$fffe
dc.w COLOR01,$17d
dc.w $fb07,$fffe
dc.w COLOR01,$29e
dc.w $fc07,$fffe
dc.w COLOR01,$4be
dc.w $fd07,$fffe
dc.w COLOR01,$6ce
dc.w $fe07,$fffe
dc.w COLOR01,$8dd
dc.w $ff07,$fffe
dc.w COLOR01,$aeb
.verticalPositionWrapped:
dc.w $ffdf,$fffe
dc.w $7,$fffe
dc.w COLOR01,$cea
dc.w $107,$fffe
dc.w COLOR01,$dd8
dc.w $207,$fffe
dc.w COLOR01,$ec5
dc.w $307,$fffe
dc.w COLOR01,$ea3
dc.w $407,$fffe
dc.w COLOR01,$d82
dc.w $507,$fffe
dc.w COLOR01,$c61
dc.w $607,$fffe
dc.w COLOR01,$b40
dc.w $707,$fffe
dc.w COLOR01,$920
dc.w $807,$fffe
dc.w COLOR01,$711
dc.w $907,$fffe
dc.w COLOR01,$502
dc.w $a07,$fffe
dc.w COLOR01,$304
dc.w $b07,$fffe
dc.w COLOR01,$106
dc.w $c07,$fffe
dc.w COLOR01,$018
dc.w $d07,$fffe
dc.w COLOR01,$03a
dc.w $e07,$fffe
dc.w COLOR01,$05b
dc.w $f07,$fffe
dc.w COLOR01,$17d
dc.w $1007,$fffe
dc.w COLOR01,$29e
dc.w $1107,$fffe
dc.w COLOR01,$4be
dc.w $1207,$fffe
dc.w COLOR01,$6ce
dc.w $1307,$fffe
dc.w COLOR01,$8dd
dc.w $1407,$fffe
dc.w COLOR01,$aeb
dc.w $1507,$fffe
dc.w COLOR01,$ce9
dc.w $1607,$fffe
dc.w COLOR01,$dd7
dc.w $1707,$fffe
dc.w COLOR01,$ec5
dc.w $1807,$fffe
dc.w COLOR01,$ea3
dc.w $1907,$fffe
dc.w COLOR01,$d82
dc.w $1a07,$fffe
dc.w COLOR01,$c61
dc.w $1b07,$fffe
dc.w COLOR01,$b40
dc.w $1c07,$fffe
dc.w COLOR01,$920
dc.w $1d07,$fffe
dc.w COLOR01,$711
dc.w $1e07,$fffe
dc.w COLOR01,$502
dc.w $1f07,$fffe
dc.w COLOR01,$304
dc.w $2007,$fffe
dc.w COLOR01,$106
dc.w $2107,$fffe
dc.w COLOR01,$028
dc.w $2207,$fffe
dc.w COLOR01,$03a
dc.w $2307,$fffe
dc.w COLOR01,$05c
dc.w $2407,$fffe
dc.w COLOR01,$17d
dc.w $2507,$fffe
dc.w COLOR01,$39e
dc.w $2607,$fffe
dc.w COLOR01,$4be
dc.w $2707,$fffe
dc.w COLOR01,$6ce
dc.w $2807,$fffe
dc.w COLOR01,$8ed
dc.w $2907,$fffe
dc.w COLOR01,$aeb
dc.w $2a07,$fffe
dc.w COLOR01,$ce9
dc.w $2b07,$fffe
dc.w COLOR01,$dd7
dc.w $2c07,$fffe
dc.w COLOR01,$000
+28
View File
@@ -0,0 +1,28 @@
include "includes.i"
xdef CpuFillColor
CpuFillColor:
;; d0 - color index
;; a0 - bitplane pointer
movem.l d1-d4/a0,-(sp)
move.w #(SCREEN_HEIGHT)-1,d2
.fillLine
move.b #0,d1 ; bitplane #
.fillBitplane:
move.w #(SCREEN_WIDTH_BYTES/4)-1,d3 ; long word moves, so / 4
btst d1,d0 ; is the color's bit set in this plane?
beq .zero
move.l #$FFFFFFFF,d4 ; yes ? all ones
bra .loop
.zero
move.l #0,d4 ; no ? all zeros
.loop:
move.l d4,(a0)+ ; write the data to the plane's line
dbra d3,.loop
add.b #1,d1
cmp.b #SCREEN_BIT_DEPTH,d1 ; all planes for a single line done ?
bne .fillBitplane ; no ? do the next plane
dbra d2,.fillLine ; yes ? do the next line
movem.l (sp)+,d1-d4/a0
rts
+11
View File
@@ -0,0 +1,11 @@
<?xml version="1.0" encoding="UTF-8"?>
<map version="1.0" orientation="orthogonal" renderorder="left-down" width="100" height="8" tilewidth="16" tileheight="16" nextobjectid="1">
<tileset firstgid="1" name="tilemap" tilewidth="16" tileheight="16" tilecount="320" columns="20">
<image source="assets/tilemap.png" width="320" height="256"/>
</tileset>
<layer name="foreground" width="100" height="8">
<data encoding="base64" compression="zlib">
eJzTZGBgqMSBNUfl6CKHLC4KxIxAzISFHpWjjxyyuBgOvYyjcnSTQxYfLGlkJMuN5o/BJTeaPwaX3Gj+GFxyyOKDpc03kuWQxQHpIl+1
</data>
</layer>
</map>
+332
View File
@@ -0,0 +1,332 @@
include "includes.i"
xdef copperList
xdef copperListBpl1Ptr
xdef copperListBpl2Ptr
xdef backgroundOnscreen
xdef backgroundOffscreen
xdef foregroundOnscreen
xdef foregroundOffscreen
xdef foregroundScrollX
xdef backgroundScrollX
byteMap:
dc.l Entry
dc.l endCode-byteMap
Entry:
lea userstack,a7
lea CUSTOM,a6
move #$7ff,DMACON(a6) ; disable all dma
move #$7fff,INTENA(a6) ; disable all interrupts
jsr InstallPalette
move.w #$09e,COLOR00(a6)
move.w #$09e,COLOR08(a6)
lea Level3InterruptHandler,a3
move.l a3,LVL3_INT_VECTOR
;; d0 - fg bitplane pointer offset
;; d1 - bg bitplane pointer offset
move.l #0,d0
move.l #1,d1
jsr SwitchBuffers
move.w #(INTF_SETCLR|INTF_VERTB|INTF_INTEN),INTENA(a6)
move.w #(DMAF_BLITTER|DMAF_SETCLR!DMAF_MASTER),DMACON(a6)
jsr Init ; enable the playfield
Reset:
move.l #0,foregroundScrollX ; x pos (d1)
move.l #0,fg_shift ; shift counter (d2)
move.l #0,fg_tileIndex ; tile index (d3)
move.l #0,backgroundScrollX
move.l #0,bg_shift ; shift counter (d2)
move.l #0,bg_tileIndex ; tile index (d3)
move.l #BACKGROUND_UPDATE_COUNT,d6 (Frame count)
jsr BlueFill
move.l #0,frameCount
MainLoop:
move.l frameCount,d6
bsr RenderNextForegroundFrame
bsr RenderNextBackgroundFrame
jsr WaitVerticalBlank
bsr.s HoriScrollPlayfield
jsr SwitchBuffers ; takes bitplane pointer offset in d0
andi.b #BACKGROUND_UPDATE_COUNT,d6
bne .skipBackgroundUpdates
;; ---- Background updates ----------------------------------------
.backgroundUpdates:
add.l #1,backgroundScrollX
add.l #2,bg_tileIndex ; increment tile index by a word
bsr UpdateBackgroundShiftCounter
.skipBackgroundUpdates:
btst #FOREGROUND_DELAY_BIT,d6
beq .skipForegroundUpdates
;; ---- Foreground updates ----------------------------------------
.foregroundUpdates:
add.l #1,foregroundScrollX
cmp.l #8,fg_shift
bge .skip
add.l #2,fg_tileIndex ; increment foreground tile index
.skip:
bsr UpdateShiftCounter
.skipForegroundUpdates:
add.l #1,frameCount
bra MainLoop
HoriScrollPlayfield:
;; d0 - fg x position in pixels
;; d1 - bg x position in pixels
;; movem.l d0-d6,-(sp)
move.l backgroundScrollX,d0
move.w d0,d2
lsr.w #3,d0 ; bytes to scroll
and.w #$F,d2 ; pixels = 0xf - (hpos - (hpos_bytes*8))
move.w #$F,d0
sub.w d2,d0 ; bits to delay
move.w d0,d5 ; d5 == bg bits to delay
move.l foregroundScrollX,d0
move.w d0,d2
lsr.w #3,d0 ; bytes to scroll
and.w #$F,d2 ; pixels = 0xf - (hpos - (hpos_bytes*8))
move.w #$F,d0
sub.w d2,d0 ; bits to delay
lsl.w #4,d5
or.w d5,d0
move.w d0,BPLCON1(a6)
;; movem.l (sp)+,d0-d6
rts
RenderNextBackgroundFrame:
btst #FOREGROUND_DELAY_BIT,d6
beq .s1
lea backgroundMap,a2
add.l bg_tileIndex,a2
bsr RenderBackgroundTile
.s1:
rts
RenderNextForegroundFrame:
lea map,a2
add.l fg_tileIndex,a2
cmp.w #$FFFF,20(a2)
bne .skip
bra Reset
.skip:
bsr RenderForegroundTile
bsr ClearForegroundTile
rts
RenderForegroundTile:
;; a2 - address of tileIndex
move.l foregroundScrollX,d0
lsr.w #3,d0 ; bytes to scroll
move.l foregroundOffscreen,a0
add.l d0,a0
lea tilemap,a1
add.l #BITPLANE_WIDTH_BYTES-8,a0 ; dest
add.w (a2),a1 ; source tile
move.l fg_shift,d2
cmp.l #8,d2
bge .skip
jsr BlitTile
.skip:
rts
ClearForegroundTile
lea tilemap,a1
add.w #11520,a1 ; source tile
move.l fg_shift,d2
sub.l #32,a0
jsr BlitTile
rts
RenderBackgroundTile:
;; a2 - map
move.l backgroundScrollX,d0
lsr.w #3,d0 ; bytes to scroll
move.l backgroundOffscreen,a0
add.l d0,a0
lea backgroundTilemap,a1
add.l #BITPLANE_WIDTH_BYTES-2,a0 ; dest
add.w (a2),a1 ; source tile
move.l bg_shift,d2
jsr BlitTile
rts
UpdateShiftCounter:
cmp.l #15,fg_shift
bne .s1
move.l #0,fg_shift
bra .s2
.s1:
add.l #1,fg_shift
.s2:
rts
UpdateBackgroundShiftCounter:
cmp.l #15,bg_shift
bne .s1
move.l #0,bg_shift
bra .s2
.s1:
add.l #1,bg_shift
.s2:
rts
Level3InterruptHandler:
movem.l d0-a6,-(sp)
lea CUSTOM,a6
.checkVerticalBlank:
move.w INTREQR(a6),d0
and.w #INTF_VERTB,d0
beq.s .checkCopper
.verticalBlank:
move.w #INTF_VERTB,INTREQ(a6) ; clear interrupt bit
.checkCopper:
move.w INTREQR(a6),d0
and.w #INTF_COPER,d0
beq.s .interruptComplete
.copperInterrupt:
move.w #INTF_COPER,INTREQ(a6) ; clear interrupt bit
.interruptComplete:
movem.l (sp)+,d0-a6
rte
copperList:
copperListBpl1Ptr:
;; this is where bitplanes are assigned to playfields
;; http://amigadev.elowar.com/read/ADCD_2.1/Hardware_Manual_guide/node0079.html
;; 3 bitplanes per playfield, playfield1 gets bitplanes 1,3,5
dc.w BPL1PTL,0
dc.w BPL1PTH,0
dc.w BPL3PTL,0
dc.w BPL3PTH,0
dc.w BPL5PTL,0
dc.w BPL5PTH,0
copperListBpl2Ptr:
;; 3 bitplanes per playfield, playfield2 gets bitplanes 2,4,6
dc.w BPL2PTL,0
dc.w BPL2PTH,0
dc.w BPL4PTL,0
dc.w BPL4PTH,0
dc.w BPL6PTL,0
dc.w BPL6PTH,0
dc.l $fffffffe
InstallPalette:
include "out/tilemap-palette.s"
rts
foregroundOnscreen:
dc.l foregroundBitplanes1
foregroundOffscreen:
dc.l foregroundBitplanes2
backgroundOnscreen:
dc.l backgroundBitplanes1
backgroundOffscreen:
dc.l backgroundBitplanes2
tilemap:
incbin "out/foreground.bin"
backgroundTilemap:
incbin "out/background.bin"
map:
include "out/foreground-map.s"
dc.w $FFFF
backgroundMap:
include "out/background-map.s"
fg_shift:
dc.l 0
foregroundScrollX:
dc.l 0
fg_tileIndex:
dc.l 0
bg_shift:
dc.l 0
backgroundScrollX:
dc.l 0
bg_tileIndex:
dc.l 0
frameCount:
dc.l 0
section .bss
foregroundBitplanes1:
ds.b IMAGESIZE
ds.b BITPLANE_WIDTH_BYTES*20
foregroundBitplanes2:
ds.b IMAGESIZE
ds.b BITPLANE_WIDTH_BYTES*20
backgroundBitplanes1:
ds.b IMAGESIZE
ds.b BITPLANE_WIDTH_BYTES*20
backgroundBitplanes2:
ds.b IMAGESIZE
ds.b BITPLANE_WIDTH_BYTES*20
startUserstack:
ds.b $1000 ; size of stack
userstack:
end
0: UpdateFG
UpdateBG
RenderFG
RenderBG
SwapBufferFG
SwapBufferBG
1: RenderFG
SwapBufferFG
2: UpdateFG
RenderFG
RenderBG
SwapBufferFG
SwapBufferBG
2: RenderFG
SwapBufferFG
000
001
010
011
100
101
110
111
+52
View File
@@ -0,0 +1,52 @@
include "includes.i"
xdef SwitchBuffers
SwitchBuffers:
;; offscreen - bitplane address
;; movem.l d0/a0-a1,-(sp)
move.l foregroundScrollX,d0
lsr.l #3,d0 ; bytes to scroll
move.l foregroundOffscreen,a0
move.l foregroundOnscreen,foregroundOffscreen
move.l a0,foregroundOnscreen
move.l a0,a1
lea copperListBpl1Ptr,a0
jsr PokeBitplanePointers
btst #FOREGROUND_DELAY_BIT,d6 ; only swap the background buffer every second frame
beq .skipBackgroundSwap
move.l backgroundScrollX,d0
lsr.l #3,d0 ; bytes to scroll
move.l backgroundOffscreen,a0
move.l backgroundOnscreen,backgroundOffscreen
move.l a0,backgroundOnscreen
move.l a0,a1
lea copperListBpl2Ptr,a0
jsr PokeBitplanePointers
.skipBackgroundSwap:
;; movem.l (sp)+,d0/a0-a1
rts
PokeBitplanePointers:
; d0 = frame offset in bytes
; a0 = BPLP copper list address
; a1 = bitplanes pointer
;; movem.l d0-a6,-(sp)
add.l d0,a1 ; bitplane offset
moveq #SCREEN_BIT_DEPTH-1,d0
.bitplaneloop:
move.l a1,d1
move.w d1,2(a0)
swap d1
move.w d1,6(a0)
lea BITPLANE_WIDTH_BYTES(a1),a1
addq #8,a0
dbra d0,.bitplaneloop
;; movem.l (sp)+,d0-a6
rts
+9
View File
@@ -0,0 +1,9 @@
include "../include/registers.i"
include "../include/vector.i"
include "../include/beambits.i"
include "../include/bplconbits.i"
include "hardware/dmabits.i"
include "hardware/intbits.i"
include "hardware/blit.i"
include "constants.i"
include "macros.i"
+34
View File
@@ -0,0 +1,34 @@
include "includes.i"
xdef Init
;; custom chip base globally in a6
Init:
movem.l d0-a6,-(sp)
;; move #$7ff,DMACON(a6) ; disable all dma
;; move #$7fff,INTENA(a6) ; disable all interrupts
;; lea Level3InterruptHandler,a3
;; move.l a3,LVL3_INT_VECTOR
;; set up playfield
move.w #(RASTER_Y_START<<8)|RASTER_X_START,DIWSTRT(a6)
move.w #((RASTER_Y_STOP-256)<<8)|(RASTER_X_STOP-256),DIWSTOP(a6)
move.w #(RASTER_X_START/2-SCREEN_RES)-8,DDFSTRT(a6) ; -8 for extra scrolling word
move.w #(RASTER_X_START/2-SCREEN_RES)+(8*((SCREEN_WIDTH/16)-1)),DDFSTOP(a6)
;; enabled 2x the bitplanes as 2x playfields
move.w #(SCREEN_BIT_DEPTH*2<<12)|COLOR_ON|DBLPF,BPLCON0(a6)
move.w #BITPLANE_WIDTH_BYTES*SCREEN_BIT_DEPTH-SCREEN_WIDTH_BYTES-2,BPL1MOD(a6) ; -2 for extra scrolling word
move.w #BITPLANE_WIDTH_BYTES*SCREEN_BIT_DEPTH-SCREEN_WIDTH_BYTES-2,BPL2MOD(a6)
;; install copper list, then enable dma and selected interrupts
lea copperList,a0
move.l a0,COP1LC(a6)
move.w COPJMP1(a6),d0
move.w #(DMAF_BLITTER|DMAF_SETCLR!DMAF_COPPER!DMAF_RASTER!DMAF_MASTER),DMACON(a6)
;; move.w #PF2PRI,BPLCON2(a6)
;; move.w #(INTF_SETCLR|INTF_VERTB|INTF_INTEN),INTENA(a6)
movem.l (sp)+,d0-a6
rts
+28
View File
@@ -0,0 +1,28 @@
MEMORY
{
disk: org = 0x4000, len = 901120-0x4000
ram: org = 0x00000, len = 0x80000
}
SECTIONS
{
load : {
startCode = .;
*(.text)
*(.data)
*(CODE)
*(DATA)
endCode = .;
} > disk
noload ALIGN(512) : {
startData = .;
*(.noload)
endData = .;
} > disk
bss (NOLOAD) : {
. = endCode;
*(.bss)
} > ram;
}
+6
View File
@@ -0,0 +1,6 @@
WaitBlitter: macro
tst DMACONR(a6) ;for compatibility
.\@:
btst #6,DMACONR(a6)
bne.s .\@
endm
+47
View File
@@ -0,0 +1,47 @@
include "includes.i"
xdef WaitVerticalBlank
xdef WaitRaster
xdef Depack
WaitVerticalBlank:
movem.l d0,-(sp)
.loop: move.l $dff004,d0
and.l #$1ff00,d0
cmp.l #303<<8,d0 ; wait for the scan line
bne.b .loop
.loop2 move.l $dff004,d0
and.l #$1ff00,d0
cmp.l #303<<8,d0 ; wait for the scan line to pass (A4000 is fast!)
beq.b .loop2
movem.l (sp)+,d0
rts
WaitRaster: ;wait for rasterline d0.w. Modifies d0-d2/a0.
movem.l d0-a6,-(sp)
move.l #$1ff00,d2
lsl.l #8,d0
and.l d2,d0
lea $dff004,a0
.wr: move.l (a0),d1
and.l d2,d1
cmp.l d1,d0
bne.s .wr
movem.l (sp)+,d0-a6
rts
Depack:
;a0 = input buffer to be decompressed. Must be 16-bit aligned!
;a1 = output buffer. Points to the end of the data at exit
movem.l d0-a6,-(sp)
bsr doynaxdepack ; decompress data
movem.l (sp)+,d0-a6
rts
;; this is one FAST decompression routine!
include "../tools/external/doynamite68k/depacker_doynax.asm"