home *** CD-ROM | disk | FTP | other *** search
- ;****************************************************************************
- ;
- ; GoLDSub - Routinen für 'Game of Life - Duo'
- ;
- ;****************************************************************************
- ;
- ; void SetCell(bmap,x,y,col)
- ;
- ; Sets the cell at coordinates (x,y) to the color 'col'.
- ; Here x and y are not pixel-coordinates but 'cell-coordinates', i.e.
- ; the position of the cell is at window position (4x,3y).
- ; The BitMap is assumed to have 2 Planes and there is no check for
- ; legal coordinate values.
- ;
- ;****************************************************************************
- ;
- ; void ScanAgar(Agar,AuxAgar,CellTrans,xsize,ysize,cs)
- ;
- ; From 'Agar' the new types of the cells which change in the current
- ; cycle are computed and stored in 'AuxAgar'.
- ; 'Agar' and 'AuxAgar' are character arrays of 'xsize' columns and
- ; 'ysize' lines. 'CellTrans' is an array with 'cs' columns and as many
- ; lines as there are different types of cells. 'CellTrans[i][j]' contains
- ; the type of the cell into which a cell of type i has to be changed when
- ; the sum of the eight neighbouring cells yields j.
- ;
- ;****************************************************************************
- ;
- ; void ChangeAgar(bm,Agar,AuxAgar,xsize,ysize,xoffset,yoffset)
- ;
- ; The new types of the cells which change in the current cycle are read
- ; from 'AuxAgar' and used to update 'Agar' and the display.
- ; (xoffset,yoffset) are the cell-coordinates of the upper left corner
- ; of the output area in the BitMat 'bm'.
- ;
- ;****************************************************************************
- ;
- ; void DisplayAgar(bm,Agar,xsize,ysize,xoffset,yoffset)
- ;
- ; The 'Agar' of size 'xsize' x 'ysize' is displayed in the BitMap 'bm' at
- ; cell-coordinates (xoffset,yoffset).
- ;
- ;****************************************************************************
- ;
- ; void CountCells(Agar,BluSum,RedSum,Len)
- ;
- ; The number of blue and red cells in 'Agar' (which is interpreted as a
- ; character string of length 'Len + 1') is returned in '*BluSum' and
- ; '*RedSum', resp.
- ;
- ;****************************************************************************
- ;
- ; Created by
- ; Andreas Neubacher
- ;
- ; Hausleitnerweg 26
- ; 4020 Linz
- ; Austria
- ;
- ; E-mail: aneubach@risc.uni-linz.ac.at (Internet)
- ; k318577@alijku11 (Bitnet)
- ;
- ;****************************************************************************
- ;
- ; Copyright notice:
- ; I don't claim any copyright and put this code into the public domain.
- ;
- ;****************************************************************************
- ;
- ; 92-01-19 AN : Finished release version
- ;
- ;****************************************************************************
-
-
- section GoLDSub,code
-
- ;****************************************************************************
-
- xdef _SetCell ; C entry : void SetCell(bmap, x, y, col);
- ; struct BitMap *bmap;
- ; short x,y,col;
- xdef SetCell ; Assembler entry : A0 D0 D0 D1
- ; hi lo
- _SetCell
- movea.l 4(SP),A0
- move.l 8(SP),D0
- swap D0
- move.w 14(SP),D0
- move.l 16(SP),D1
-
- ; Register usage
- ;
- ; D0 ... x/y (hi-/lo-word), mask for nibble set/clear
- ; D1 ... col; offset for the byte, which contains the second line of the cell
- ; D2 ... offset for the byte, which contains the first line of the cell
- ; A0 ... pointer to the BitMap
- ; A1 ... pointer to the Bitplane
-
- SetCell
- move.l D2,-(SP)
- swap D1
- move.w (A0),D1 ; D1 := bmap->BytesPerRow
- move.w D1,D2
- add.w D2,D2
- add.w D1,D2 ; D2 := 3 * bmap->BytesPerRow
- mulu.w D0,D2 ; * y
-
- swap D0
- lsr.w #1,D0
- bcs ELSE1 ; IF x even THEN
- add.w D0,D2 ; D2 := D2 + x/2
- move.l #$008F0070,D0 ; D0 := maske for high nibble
- bra ENDIF1
- ELSE1 ; ELSE
- add.w D0,D2 ; D2 := D2 + x/2
- move.l #$00F80007,D0 ; D0 := maske for low nibble
- ENDIF1 ; ENDIF
- add.w D2,D1 ; D1 := D2 + bmap->BytesPerRow
-
- movea.l 8(A0),A1 ; A1 points to first Bitplane
- btst #16,D1
- beq ELSE2 ; IF col odd THEN
- or.b D0,(A1,D2.w) ; set cell
- or.b D0,(A1,D1.w) ; set cell
- bra ENDIF2
- ELSE2 ; ELSE
- swap D0
- and.b D0,(A1,D2.w) ; clear cell
- and.b D0,(A1,D1.w) ; clear cell
- swap D0
- ENDIF2 ; ENDIF
-
- movea.l 12(A0),A1 ; A1 points to second Bitplane
- btst #17,D1
- beq ELSE3 ; IF col > 1 THEN
- or.b D0,(A1,D2.w) ; set cell
- or.b D0,(A1,D1.w) ; set cell
- bra ENDIF3
- ELSE3 ; ELSE
- swap D0
- and.b D0,(A1,D2.w) ; clear cell
- and.b D0,(A1,D1.w) ; clear cell
- ENDIF3 ; ENDIF
-
- move.l (SP)+,D2
- rts
-
-
- ;****************************************************************************
-
-
- xdef _ScanAgar ; C entry : void ScanAgar(a, aa, ct, xs, ys, cs);
- ; char *a,*aa,*ct;
- ; short xs,ys,cs;
- xdef ScanAgar ; Assembler entry : A0 A1 A2 D0 D1 D2
-
- _ScanAgar
- movea.l 4(SP),A0
- movea.l 8(SP),A1
- movea.l 12(SP),A2
- move.l 16(SP),D0
- move.l 20(SP),D1
- move.l 24(SP),D2
-
- ; Register usage
- ;
- ; D0 ... 'xs'
- ; D1 ... 'ys', row counter
- ; D2 ... 'cs', sum of cell values
- ; D3 ... column counter
- ; A0 ... 'a'
- ; A1 ... 'aa'
- ; A2 ... 'ct'
- ; A3/A4 ... auxiliary pointers into 'a'
- ; A5/A6 ... pointers to second/third line of matrix 'ct'
-
- ScanAgar
- movem.l D3/A3-A6,-(SP)
-
- movea.l A0,A3
- adda.w D0,A3
- movea.l A3,A4
- adda.w D0,A4
- adda.w D0,A1
- addq.l #1,A1
-
- movea.l A2,A5
- adda.w D2,A5
- movea.l A5,A6
- adda.w D2,A6
-
- moveq #0,D2
- subq.w #3,D0 ; xs := xs - 3
- subq.w #3,D1 ; ys := ys - 3
- REPEAT1 ; REPEAT
- move.w D0,D3 ; D3 := xs
- REPEAT2 ; REPEAT
- move.b (A0)+,D2 ; D2 := sum over
- add.b (A0),D2 ; the eight
- add.b 1(A0),D2 ; neighbours
- add.b (A3)+,D2 ; of the
- add.b 1(A3),D2 ; current
- add.b (A4)+,D2 ; cell
- add.b (A4),D2 ;
- add.b 1(A4),D2 ;
- btst #0,(A3)
- beq ELSE4 ; IF current cell = 1 THEN
- move.b (A5,D2.w),(A1)+ ; curr. aux. cell := ct[1][D2]
- bra ENDIF4
- ELSE4 btst #1,(A3)
- bne ELSE5 ; ELSE IF current cell = 0 THEN
- move.b (A2,D2.w),(A1)+ ; curr. aux. cell := ct[0][D2]
- bra ENDIF4
- ELSE5 ; ELSE
- move.b (A6,D2.w),(A1)+ ; curr. aux. cell := ct[2][D2]
- ENDIF4 ; ENDIF
- dbf D3,REPEAT2 ; UNTIL row finished
- addq.l #2,A0
- addq.l #2,A1 ; next
- addq.l #2,A3 ; row
- addq.l #2,A4
- dbf D1,REPEAT1 ; UNTIL all rows finished
-
- movem.l (SP)+,D3/A3-A6
- rts
-
-
- ;****************************************************************************
-
-
- xdef _ChangeAgar ; C entry : void ChangeAgar(bm, a, aa, xs, ys, xo, yo);
- ; struct BitMap *bm;
- ; char *a,*aa;
- ; short xs,ys,xo,yo;
- xdef ChangeAgar ; Assembler entry : A0 A1 A2 D0 D1 D2 D2
- ; hi lo
- _ChangeAgar
- movea.l 4(SP),A0
- movea.l 8(SP),A1
- movea.l 12(SP),A2
- move.l 16(SP),D0
- move.l 20(SP),D1
- move.l 24(SP),D2
- swap D2
- move.w 30(SP),D2
-
- ; Register usage
- ;
- ; D0 ... x/y (hi-/lo-word)
- ; D1 ... value of current cell; color
- ; D2 ... x-offset
- ; D3 ... column counter
- ; D4 ... row counter
- ; D5 ... 'xs'
- ; D6 ... y-offset
- ; A0 ... 'bm'
- ; A2 ... pointer to current cell in 'aa'
- ; A3 ... pointer to current cell in 'a'
-
- ChangeAgar
- movem.l D2-D6/A3,-(SP)
-
- movea.l A1,A3
- add.w D0,A2
- addq.l #1,A2
- add.w D0,A3
- addq.l #1,A3
- subq.w #3,D0
- subq.w #3,D1
- move.w D1,D4
- move.w D2,D6
- add.w D1,D6
- swap D2
- add.w D0,D2
- move.w D0,D5
-
- REPEAT3 ; REPEAT
- move.w D5,D3
- REPEAT4 ; REPEAT
- move.b (A2),D1 ; D1 := current cell in 'aa'
- bne ELSE6 ; IF D1 = 0 THEN
- move.b D1,(A3) ; current cell in 'a' := D1
- moveq #2,D1 ; color := 2
- bra ENDIF7 ; GOTO ENDIF7
- ELSE6 cmp.b #2,D1
- bgt ENDIF6 ; ELSE IF D1 < 3 THEN
- beq ELSE7 ; IF D1 = 1 THEN
- move.b D1,(A3) ; current cell in 'a' := D1
- moveq #0,D1 ; color := 0
- bra ENDIF7 ; ELSE
- ELSE7 move.b D1,(A3) ; current cell in 'a' := D1
- moveq #1,D1 ; color := 1
- ENDIF7 ; ENDIF
- move.w D2,D0
- sub.w D3,D0
- swap D0
- move.w D6,D0
- sub.w D4,D0
- jsr SetCell ; SetCell(bm,D2-D3,D6-D4,color)
- ENDIF6 ; ENDIF
- addq.l #1,A2 ; next
- addq.l #1,A3 ; cell
- dbf D3,REPEAT4 ; UNTIL row finished
- addq.l #2,A2 ; next
- addq.l #2,A3 ; row
- dbf D4,REPEAT3 ; UNTIL all rows finished
-
- movem.l (SP)+,D2-D6/A3
- rts
-
-
- ;****************************************************************************
-
-
- xdef _DisplayAgar ; C entry : void DisplayAgar(bm, a, xs, ys, xo, yo);
- ; struct BitMap *bm;
- ; char *a;
- ; short xs,ys,xo,yo;
- xdef DisplayAgar ; Assembler entry : A0 A2 D0 D1 D2 D2
- ; hi lo
- _DisplayAgar
- movea.l 4(SP),A0
- movea.l 8(SP),A2
- move.l 12(SP),D0
- move.l 16(SP),D1
- move.l 20(SP),D2
- swap D2
- move.w 26(SP),D2
-
- ; Register usage
- ;
- ; D0 ... x/y (hi-/lo-word)
- ; D1 ... value of current cell; color
- ; D2 ... x-offset
- ; D3 ... y-offset
- ; D4 ... 'xs'
- ; D5 ... column counter
- ; D6 ... line counter
- ; A0 ... 'bm'
- ; A2 ... pointer to current cell in 'a'
-
- DisplayAgar
- movem.l D3-D6,-(SP)
-
- add.w D0,A2
- addq.l #1,A2
- subq.w #3,D0
- subq.w #3,D1
- move.w D1,D3
- add.w D2,D3
- move.w D1,D6
- swap D2
- add.w D0,D2
- move.w D0,D4
-
- REPEAT5 ; REPEAT
- move.w D4,D5
- REPEAT6 ; REPEAT
- move.b (A2)+,D1 ; D1 := current cell in 'a'
- bne ELSE8 ; IF D1 = 0 THEN
- moveq #2,D1 ; color := 2
- bra ENDIF8 ;
- ELSE8 btst #0,D1
- beq ELSE9 ; ELSE IF D1 = 1 THEN
- moveq #0,D1 ; color := 0
- bra ENDIF8 ; ELSE
- ELSE9 moveq #1,D1 ; color := 1
- ENDIF8 ; ENDIF
- move.w D2,D0
- sub.w D5,D0
- swap D0
- move.w D3,D0
- sub.w D6,D0
- jsr SetCell ; SetCell(bm,D2-D5,D3-D6,color)
- dbf D5,REPEAT6 ; UNTIL row finished
- addq.l #2,A2 ; next row
- dbf D6,REPEAT5 ; UNTIL all rows finished
-
- movem.l (SP)+,D3-D6
- rts
-
-
- ;****************************************************************************
-
-
- xdef _CountCells ; C entry : void CountCells(a, bluc, redc, len);
- ; char *a;
- ; short *redc,*bluc;
- ; unsigned short len;
- xdef CountCells ; Assembler entry : A0 A1 A2 D0
-
- _CountCells
- movea.l 4(SP),A0
- movea.l 8(SP),A1
- movea.l 12(SP),A2
- move.l 16(SP),D0
-
- ; Register usage
- ;
- ; D0 ... cell counter
- ; D1 ... counter for blue cells
- ; D2 ... counter for red cells
- ; D3 ... current cell
- ; A0 ... pointer to current cell
- ; A1 ... 'bluc'
- ; A2 ... 'redc'
-
- CountCells
- movem.l D2/D3,-(SP)
-
- moveq.l #0,D1
- move.l D1,D2
- REPEAT7 ; REPEAT
- move.b (A0)+,D3 ; get current cell
- bne ELSE10 ; IF cell = 0 THEN
- addq.w #1,D1 ; blue cell
- bra ENDIF10
- ELSE10
- btst #0,D3
- bne ENDIF10 ; ELSE IF cell = 2 THEN
- addq.w #1,D2 ; red cell
- ENDIF10 ; ENDIF
- dbf D0,REPEAT7 ; UNTIL all cells finished
-
- move.w D1,(A1)
- move.w D2,(A2)
-
- movem.l (SP)+,D2/D3
- rts
-
- END
-
-