kiteasm -l life.asm lst2ram -s -f -2 life.lstメモリの初期化は以下のように $readmemh を利用する。
initial begin $readmemh( "life.ram", MEM ); end
;; ;; Life Game 48x16 for LCD Monitor on ATLYS Board ;; .word MAIN ; Start Vector .word 0 .word 0 .word 0 .word 0 .word 0 .word 0 .word 0 .word 0 .word 0 .word 0 .word 0 .word 0 .word 0 .word 0 .word 0 MAIN: ld16 #STACK ; sp = 0x800 mv sp, acc ;; ;; Main Loop ;; NEXT1: ;; ;; Display DATA1 area ;; call disp ; copy DATA1 to Display call wait ; wait ;; ;; Clear DATA2 area ;; ld16 #768 st X ld DAT2 mv ixr, acc LOOP3: ld #0 st ixr, 0 inc ixr, ixr ld X dec acc, acc st X jpz NEXT3 jp LOOP3 ;; ;; for( x=0 ; x<48 ; x++ ) ;; NEXT3: ld #0 FOR1: st X sub #48 jpz FOREND1 ;; ;; for( y=0 ; y<16 ; y++ ) ;; ld #0 FOR2: st Y sub #16 jpz FOREND2 BODY: ld #0 ; NoOf = 0 st NoOf ld X ; if( what1(x-1,y-1) ) NoOf++; dec acc, acc push ld Y dec acc, acc push call what1 jpz SKIP1 ld NoOf inc acc, acc st NoOf SKIP1: pop ld Y ; if( what1(x-1 ,y ) ) NoOf++; push call what1 jpz SKIP2 ld NoOf inc acc, acc st NoOf SKIP2: pop ld Y ; if( what1(x-1,y+1) ) NoOf++; inc acc, acc push call what1 jpz SKIP3 ld NoOf inc acc, acc st NoOf SKIP3: pop pop ld X ; if( what1(x ,y-1) ) NoOf++; push ld Y dec acc, acc push call what1 jpz SKIP4 ld NoOf inc acc, acc st NoOf SKIP4: pop ld Y ; if( what1(x ,y+1) ) NoOf++; inc acc, acc push call what1 jpz SKIP5 ld NoOf inc acc, acc st NoOf SKIP5: pop pop ld X ; if( what1(x+1,y-1) ) NoOf++; inc acc, acc push ld Y dec acc, acc push call what1 jpz SKIP6 ld NoOf inc acc, acc st NoOf SKIP6: pop ld Y ; if( what1(x+1,y ) ) NoOf++; push call what1 jpz SKIP7 ld NoOf inc acc, acc st NoOf SKIP7: pop ld Y ; if( what1(x+1,y+1) ) NoOf++; inc acc, acc push call what1 jpz SKIP8 ld NoOf inc acc, acc st NoOf SKIP8: pop pop ld X ; if( what1(x,y) ) { push ld Y push call what1 jpz CENTER0 CENTER1:ld NoOf ; if( NoOf == 2 || NoOf == 3 ) sub #2 ; set1(x,y); jpz SET ; else ld NoOf ; set0(x,y); sub #3 jpz SET jp DEL CENTER0:ld NoOf ; } else { sub #3 ; if( NoOf == 3 ) jpz SET ; set1(x,y); DEL: call SET0 jp SKIP10 SET: call SET1 ; } SKIP10: pop pop ld Y ; y++; inc acc, acc jp FOR2 ; };// forend y FOREND2:ld X ; x++; inc acc, acc jp FOR1 ; };// forend x FOREND1:ld16 #768 ; Copy DATA2 -> DATA1 area st X ld DAT1 st PTR1 ld DAT2 st PTR2 LOOP4: ld PTR2 mv ixr, acc ld ixr, 0 push ld PTR1 mv ixr, acc pop st ixr,0 ld PTR1 inc acc, acc st PTR1 ld PTR2 inc acc, acc st PTR2 ld X dec acc, acc st X jpz NEXT1 ; Goto Main Loop jp LOOP4 ;; ;; What1(x,y) return 0 and set Z flag ;; if thare is no object in DATA1[x,y] ;; what1: mv ixr, sp call check ; area check jpz return ; if out of area call adgen ; acc = Y*48+X st PTR1 ld16 #PTR1 mv ixr, acc ld DAT1 add ixr, 0 ; acc = DATA1+Y*48+X mv ixr, acc ld ixr, 0 ; acc = *(DATA1+Y*48+X) or #0 return: ret ;; ;; check boundary ;; check: ld ixr, 2 ; load X sub #-1 ; if out of left side then return Z jpz return ld ixr, 2 sub #48 ; if out of right side then return Z jpz return ld ixr, 1 ; load Y sub #-1 ; if out of upper side then return Z jpz return ld ixr, 1 sub #16 ; if out of lower side then return Z ret ; return NZ if within area ;; ;; acc = 48*Y+X ;; adgen: ld ixr, 1 ; acc = Y add ixr, 1 ; acc = 2*Y add ixr, 1 ; acc = 3*Y asl ; acc = 6*Y asl ; acc = 12*Y asl ; acc = 24*Y asl ; acc = 48*Y add ixr, 2 ; acc = 48*Y + X ret ;; ;; SET1(x,y) sets "1" into DATA2[x,y] ;; SET1: mv ixr, sp call adgen ; acc = Y*48+X st PTR1 ld16 #PTR1 mv ixr, acc ld DAT2 add ixr, 0 ; acc = DATA2+Y*48+X mv ixr, acc ld #1 st ixr, 0 ; *(DAT2+Y*48+X) = 1 ret ;; ;; SET0(x,y) sets "0" into DATA2[x,y] ;; SET0: mv ixr, sp call adgen ; acc = Y*80+X st PTR1 ld16 #PTR1 mv ixr, acc ld DAT2 add ixr, 0 ; acc = DATA2+Y*80+X mv ixr, acc ld #0 st ixr, 0 ; *(DAT2+Y*80+X) = 0 ret ;; ;; Display : Copy DATA -> VRAM area ;; disp: ld #16 st Y ld16 #VRAM940 st PTR2 ; ptr2 = dest. pointer ld DAT1 st PTR1 ; ptr1 = DATA1 pointer disp1: ld #48 st X ; X = 48 disp5: ld PTR1 mv ixr, acc ld ixr, 0 push ld PTR2 mv ixr, acc pop or #0 jpz disp2 ld #0x4f ; 'O' jp disp3 disp2: ld #0x20 ; ' ' disp3: st ixr,0 ld PTR1 ; ptr1++ inc acc, acc st PTR1 ld PTR2 ; ptr2++ inc acc, acc st PTR2 ld X ; x-- dec acc, acc st X jpz disp4 jp disp5 disp4: ld PTR2 ; ptr2 += 32 add #32 st PTR2 ld Y ; y-- dec acc, acc st Y jpz return jp disp1 ;; ;; wait ;; wait: ld #10 LOOP22: push ld #0 LOOP2: dec acc, acc jpz LOOP21 jp LOOP2 LOOP21: pop dec acc, acc jpz return jp LOOP22 ;; ;; ;; DAT1: .word DATA1 ; DATA1 pointer DAT2: .word DATA2 ; DATA2 pointer X: .word 0 ; Variable x Y: .word 0 ; Variable y PTR1: .word 0 ; General pointer 1 PTR2: .word 0 ; General pointer 2 NoOf: .word 0 ; Number of object ;; Current space DATA1: .space 24 ; line 0 .word 1 .space 11 .space 12 .space 22 ; line 1 .word 1 .word 0 .word 1 .space 11 .space 12 .space 12 ; line 2 .word 1 .word 1 .space 6 .word 1 .word 1 .space 12 .word 1 .word 1 .space 12 .space 11 ; line 3 .word 1 .space 3 .word 1 .space 4 .word 1 .word 1 .space 12 .word 1 .word 1 .space 12 .word 1 ; line 4 .word 1 .space 8 .word 1 .space 5 .word 1 .space 3 .word 1 .word 1 .space 14 .space 12 .word 1 ; line 5 .word 1 .space 8 .word 1 .space 3 .word 1 .word 0 .word 1 .word 1 .space 4 .word 1 .word 0 .word 1 .space 11 .space 12 .space 10 ; line 6 .word 1 .space 5 .word 1 .space 7 .word 1 .space 11 .space 12 .space 11 ; line 7 .word 1 .space 3 .word 1 .space 20 .space 12 .space 12 ; line 8 .word 1 .word 1 .space 22 .space 12 .space 336 DATA2: .space 768 ; Next space .data 0x800 STACK: VRAM: .data 0x940 VRAM940: