Home » Archimedes archive » Zipped Apps » 6502em » !6502Em/src/6502Em130
!6502Em/src/6502Em130
This website contains an archive of files for the Acorn Electron, BBC Micro, Acorn Archimedes, Commodore 16 and Commodore 64 computers, which Dominic Ford has rescued from his private collection of floppy disks and cassettes.
Some of these files were originally commercial releases in the 1980s and 1990s, but they are now widely available online. I assume that copyright over them is no longer being asserted. If you own the copyright and would like files to be removed, please contact me.
| Tape/disk: | Home » Archimedes archive » Zipped Apps » 6502em |
| Filename: | !6502Em/src/6502Em130 |
| Read OK: | ✔ |
| File size: | E5B8 bytes |
| Load address: | 0000 |
| Exec address: | 0000 |
File contents
10REM > 6502Em
20REMINPUT"Hardware scroll ";HWScroll
30REMIF HWScroll<>0 THEN HWScroll=TRUE
40HWScroll=TRUE
50master=FALSE
60*RMENSURE 6502Support 0.00 RMRun <6502Em$Res>.65Support
70ON ERROR PROCerror
80
90REM V2. (bbc)
100
110IO_Podule%=FALSE
120
130DIM opcode(&100), bcd(&100), code 500*1024, buffer 1000
140DIM l%(100)
150DIM divloop1(10),divloop2(10),divjump(10)
160div%=0
170LIBRARY "<6502Em$Dir>.Src.Sound6"
180LIBRARY "<6502Em$Dir>.Src.Opcodes"
190LIBRARY "<6502Em$Dir>.Src.Screen"
200LIBRARY "<6502Em$Dir>.Src.HWScroll"
210
220electron%=FALSE
230master=FALSE
240PROCassemble
250
260PRINT(end-start)/1024
270OSCLI "Save <6502Em$Dir>.Code "+STR$~code+" "+STR$~(end+code)
280OSCLI "SetType <6502Em$Dir>.Code Data"
290
300master=TRUE
310PROCassemble
320PRINT(end-start)/1024
330OSCLI "Save <6502Em$Dir>.CodeM "+STR$~code+" "+STR$~(end+code)
340OSCLI "SetType <6502Em$Dir>.CodeM Data"
350
360END
370
380OSCLI"LOAD <6502Em$Dir>.OS1,2 "+STR$~(memory+&C000)
390OSCLI"LOAD <6502Em$Dir>.BASICII "+STR$~(memory+&8000)
400
410MODE 12
420CALL init+code
430PRINT"BOO"
440
450!pc_store=&D9CD << 16
460
470D%=memory : REM R3
480CALL start+code
490
500END
510DEFPROCassemble
520PROCclearmem(code,code+200*1024)
530R=1000 : S=1000 : T=1000
540
550A=4
560X=5
570Y=6
580F=7
590SP=8
600mem=3
610time=9
620zpc=10
630table=11
640
650a=-&100+0
660x=-&100+4
670y=-&100+8
680f=-&100+12
690sp=-&100+16
700pc_store=-&100+20
710T1mode=-&100+24
720T2mode=-&100+25
730T3mode=-&100+26
740T4mode=-&100+27
750T1=-&100+28
760T1R=-&100+32
770T2=-&100+36
780T2R=-&100+40
790T3=-&100+44
800T3R=-&100+48
810T4=-&100+52
820T4R=-&100+56
830screen=-&100+60
840screenR=-&100+64
850min=-&100+68
860sound_timer=-&100+72
870ifr=-&100+76
880ier=-&100+77
890ifr2=-&100+78
900ier2=-&100+79
910arc_screenstart=-&100+80
920tamper=-&100+84
930cursor_tamper=-&100+88
940ROMSEL_ON=-&100+92
950rom=-&100+96
960ROMRAM=-&100+100
970fe20=-&100+116
980tape_handle=-&100+117
990crt_regs=-&100+120
1000scratch=-&100+140
1010pal_regs=-&100+148
1020Palette=-&100+164
1030ACCCON=-&100+172
1040patch_on=-&100+176
1050pal_tamper=-&100+177
1060lastmode=-&100+178
1070fe10=-&100+179
1080tape_count=-&100+180
1090key_addr=-&100+184
1100screenstart_tamper=-&100+188
1110screenstart_previous=-&100+192
1120speedR=-&100+196
1130
1140enD=-&100+200 : REM don't go past this
1150
1160FORp=4 TO 6 STEP 2
1170div%=0
1180O%=code
1190l%=0
1200P%=0
1210opcode%=0
1220[OPTp
1230.Oa EQUD 0
1240.Ox EQUD 0
1250.Oy EQUD 0
1260.Of EQUD 0
1270.Osp EQUD 0
1280.Opc_store EQUD 0
1290.start_offset EQUD start
1300.trace EQUD 0
1310.trace2 EQUD 0
1320.init_addr EQUD init
1330.crt_addr EQUD 0 ; was crt_regs
1340.T1_addr EQUD 0 ; was T1
1350.ifr_addr EQUD 0 ; ifr
1360.column_counter_addr EQUD column_counter
1370.ROMSEL_addr EQUD 0 ; ROMSEL
1380.Palette_addr EQUD 0 ; Palette
1390.speed_addr EQUD screen_count+4
1400.elite_addr EQUD 0 ; elite
1410.opco_addr EQUD opcode(0) ; opcodetable
1420.bcd_addr EQUD bcd(0)
1430.sheila_writetab_addr EQUD sheila_writetab
1440.sheila_readtab_addr EQUD sheila_readtab
1450.sound_vectors_addr EQUD sound_buffs_addr
1460.patch_addr EQUD patch_screen
1470
1480.init ; only called once, before code called
1490ADR R0,0
1500;LDR R1,opco_addr
1510;ADD R1,R1,R0
1520;LDR R2,bcd_addr
1530;ADD R2,R2,R0
1540LDR R5,sheila_writetab_addr
1550ADD R5,R5,R0
1560LDR R6,sheila_readtab_addr
1570ADD R6,R6,R0
1580MOV R3,#255
1590.init_loop
1600;LDR R4,[R1,R3,LSL#2]
1610;ADD R4,R4,R0
1620;STR R4,[R1,R3,LSL#2]
1630;LDR R4,[R2,R3,LSL#2]
1640;ADD R4,R4,R0
1650;STR R4,[R2,R3,LSL#2]
1660LDR R4,[R5,R3,LSL#2]
1670ADD R4,R4,R0
1680STR R4,[R5,R3,LSL#2]
1690LDR R4,[R6,R3,LSL#2]
1700ADD R4,R4,R0
1710STR R4,[R6,R3,LSL#2]
1720SUBS R3,R3,#1
1730BPL init_loop
1740MOV PC,R14
1750
1760.start
1770STMFD R13!,{R1-R12,R14}
1780STR R13,return_addr
1790STR R0,roms_addr
1800;LDR R0,crt_addr
1810;ADR R1,0
1820;ADD R0,R0,R1
1830;SWI "6502_Init"
1840
1850BL blank_cursor
1860
1870MOV R0,#&9C00 : ADD R0,R0,#&40
1880STR R0,[mem,#screenR]
1890
1900SWI "6502_Getkeyaddr"
1910STR R0,[mem,#key_addr]
1920
1930ADR R0,block1
1940ADD R1,R0,#8
1950SWI "OS_ReadVduVariables"
1960LDR R9,[R1] ; screenstart
1970STR R9,[mem,#arc_screenstart]
1980MOV R9,#1
1990STRB R9,[mem,#tamper]
2000STRB R9,[mem,#pal_tamper]
2010STRB R9,[mem,#cursor_tamper]
2020
2030LDR time,[mem,#min]
2040LDR A,[mem,#a]
2050LDR X,[mem,#x]
2060LDR Y,[mem,#y]
2070LDR SP,[mem,#sp] : ORR SP,SP,#1
2080LDR F,[mem,#f]
2090LDR zpc,[mem,#pc_store]
2100
2110BL recalc_wrap
2120LDRB R0,[mem,#patch_on]
2130AND R0,R0,#%11111
2140BIC F,F,#&FF00
2150ORR F,F,R0,LSL#8
2160
2170;MOV time,#0
2180
2190LDRB R0,fe08_read
2200BIC R0,R0,#&81
2210STRB R0,fe08_read
2220
2230ADR R0,0
2240TST F,#%1000
2250LDREQ table,opco_addr
2260LDRNE table,bcd_addr
2270ADD table,table,R0
2280;SWI "6502_ReInit"
2290;SWI "6502_UpdateScreen
2300BL poke_updatepixelV
2310BL updatescreen
2320B fetch2
2330
2340.reset_bcdflag
2350ADR R1,0
2360TST F,#%1000
2370LDREQ table,opco_addr
2380LDRNE table,bcd_addr
2390ADD table,table,R1
2400MOV PC,R14
2410
2420.block1
2430EQUD 149 : EQUD -1
2440.block2
2450EQUD 0 : EQUD 0
2460
2470.screen_count
2480EQUD 0
2490EQUD 0
2500
2510.reg_comp
2520EQUD &FFEE << 16
2530
2540.trace_on
2550MOV R12,#1
2560STRB R12,trace
2570MOV PC,R14
2580
2590.show_regs
2600
2610;SWI "6502_Checkkdata"
2620LDR R0,[mem,#key_addr]
2630LDRB R0,[R0,#-4]
2640
2650
2660CMP R0,#&1F ; Insert
2670MOVEQ R1,#1
2680STREQ R1,trace2
2690
2700LDRB R0,trace2
2710CMP R0,#1
2720MOVNE PC,R14
2730
2740;LDR R0,reg_comp
2750;CMP R0,zpc
2760;MOVEQ R0,#1
2770;STREQB R0,trace
2780
2790;ADD R12,mem,#&DF00
2800;LDRB R12,[R12,#&DA]
2810;CMP R12,#0
2820;MOVEQ R12,#1
2830;STREQB R12,trace
2840
2850;LDRB R0,trace
2860;CMP R0,#1
2870;MOVNE PC,14
2880
2890FNshowregs
2900MOV PC,R14
2910
2920.read_ifr
2930LDRB R0,[mem,#ifr]
2940
2950LDR R1,[mem,#min]
2960SUB R1,R1,time
2970LDR R12,[mem,#screen]
2980SUB R12,R12,R1
2990CMP R12,#10
3000ORRLT R0,R0,#%10 ; vsync
3010;
3020;
3030; CMP zpc,#&8000 << 16
3040; ORRLT R0,R0,#%10 ; vsync
3050
3060
3070LDRB R1,[mem,#ier]
3080BIC R0,R0,#&80
3090ANDS R1,R1,R0
3100ORRNE R0,R0,#&80
3110
3120MOV PC,R14
3130
3140.read_ier
3150LDRB R0,[mem,#ier]
3160ORR R0,R0,#&80
3170MOV PC,R14
3180
3190.read_ifr2
3200LDRB R0,[mem,#ifr2]
3210LDRB R1,[mem,#ier2]
3220BIC R0,R0,#&80
3230ANDS R1,R1,R0
3240ORRNE R0,R0,#&80
3250MOV PC,R14
3260
3270.read_ier2
3280LDRB R0,[mem,#ier2]
3290ORR R0,R0,#&80
3300MOV PC,R14
3310
3320.ldrb41
3330
3340SUB R12,mem,#512 ; sheila
3350LDRB R1,[R12,#&C] ; PCR
3360LDRB R2,[mem,#ifr]
3370AND R13,R1,#%1110
3380TEQ R13, #%0010
3390TEQNE R13, #%0110
3400BICEQ R2,R2,#%11
3410BICNE R2,R2,#%10
3420STRB R2,[mem,#ifr]
3430
3440LDRB R0,[R12,#&4F]
3450MOV PC,R14
3460
3470.ldrb4F
3480
3490SUB R12,mem,#512 ; sheila
3500LDRB R0,[R12,#&4F]
3510MOV PC,R14
3520
3530
3540.readT4low_count
3550LDRB R1,[mem,#ifr2]
3560BIC R1,R1, #%00100000
3570STRB R1,[mem,#ifr2]
3580LDR R0,[mem,#T4]
3590LDR R1,[mem,#min]
3600SUB R0,R0,R1,LSL#15
3610ADD R0,R0,time,LSL#15
3620TST R0,#1 << 15 ; ???
3630SUBNE time,time,#1
3640MOV R0,R0,LSR#16
3650AND R0,R0,#&FF
3660MOV PC,R14
3670
3680.readT4high_count
3690LDR R0,[mem,#T4]
3700LDR R1,[mem,#min]
3710SUB R0,R0,R1,LSL#15
3720ADD R0,R0,time,LSL#15
3730TST R0,#1 << 15 ; ???
3740SUBNE time,time,#1
3750MOV R0,R0,LSR#24
3760MOV PC,R14
3770
3780.readT3low_count
3790LDR R1,[mem,#ifr2]
3800BIC R1,R1, #%1 << 6
3810STRB R1,[mem,#ifr2] ; clear T3 interrupt flag
3820LDR R0,[mem,#T3]
3830LDR R1,[mem,#min]
3840SUB R0,R0,R1,LSL#15
3850ADD R0,R0,time,LSL#15
3860TST R0,#1 << 15 ; ???
3870SUBNE time,time,#1
3880MOV R0,R0,LSR#16
3890AND R0,R0,#&FF
3900MOV PC,R14
3910
3920.readT3high_count
3930LDR R0,[mem,#T3]
3940LDR R1,[mem,#min]
3950SUB R0,R0,R1,LSL#15
3960ADD R0,R0,time,LSL#15
3970TST R0,#1 << 15 ; ???
3980SUBNE time,time,#1
3990MOV R0,R0,LSR#24
4000MOV PC,R14
4010
4020.readT3low_latch
4030LDRB R0,[mem,#T3R+2]
4040MOV PC,R14
4050
4060.readT3high_latch
4070LDRB R0,[mem,#T3R+3]
4080MOV PC,R14
4090
4100.ACRtemp
4110EQUD 0
4120
4130.writeACR2
4140;MOV R0,#0
4150;STRB R0,[mem,#T3mode]
4160SUB R0,mem,#512
4170LDRB R1,[R0,#&60]
4180ORR R1,R1,#&80
4190STRB R1,[R0,#&60]
4200;MOV R0,#1
4210;STRB R0,ACRtemp
4220MOV PC,R14
4230
4240.writeT3low_latch
4250STRB R0,[mem,#T3R+2]
4260MOV PC,R14
4270
4280.writeT3high_count
4290STRB R0,[mem,#T3R+3]
4300LDR R0,[mem,#T3R]
4310ADD R0,R0,#2 << 16
4320
4330CMP R0,time,LSL#15 ; fix Exile's speech
4340
4350BHI skip_T3adjust
4360LDRB R2,[mem,#ier2]
4370
4380TST R2,#%01000000
4390MOVNE time,R0,LSR#15
4400
4410.skip_T3adjust
4420LDR R1,[mem,#min]
4430ADD R0,R0,R1,LSL#15
4440SUB R0,R0,time,LSL#15
4450STR R0,[mem,#T3]
4460LDRB R1,[mem,#ifr2]
4470BIC R1,R1, #%1 << 6
4480STRB R1,[mem,#ifr2] ; clear T3 interrupt flag
4490;SUB R0,R0,#&D
4500SUB R0,mem,#512 ; sheila
4510
4520
4530LDRB R1,[R0,#&6B]
4540EOR R1,R1,#1<<7
4550ANDS R1,R1,#&C0
4560LDREQB R1,[R0,#&60]
4570BICEQ R1,R1,#&80
4580STREQB R1,[R0,#&60]
4590
4600LDRB R12,[mem,#crt_regs+9]
4610CMP R12,#3
4620MOVEQ PC,R14 ; fortress fudge
4630
4640MOV R0,#1 : STRB R0,[mem,#T3mode]
4650MOV PC,R14
4660
4670.writeT3high_latch
4680STRB R0,[mem,#T3R+3]
4690MOV PC,R14
4700
4710.writeT4low_latch
4720STRB R0,[mem,#T4R+2]
4730MOV PC,R14
4740
4750.writeT4high_count
4760LDRB R1,[mem,#T4R+2]
4770ADD R1,R1,R0,LSL#8
4780MOV R1,R1,LSL#16
4790LDR R0,[mem,#min]
4800ADD R1,R1,R0,LSL#15
4810SUB R1,R1,time,LSL#15
4820;ADD R1,R1,#2 << 16
4830ADD R1,R1,#1 << 16
4840STR R1,[mem,#T4]
4850LDRB R1,[mem,#ifr2]
4860BICS R1,R1, #%001 << 5
4870STRB R1,[mem,#ifr2]
4880MOV R0,#1 : STRB R0,[mem,#T4mode]
4890MOV PC,R14
4900
4910.readT2low_count
4920LDRB R1,[mem,#ifr]
4930BIC R1,R1, #%101 << 5
4940STRB R1,[mem,#ifr] ; clear T2 interrupt flag
4950LDR R0,[mem,#T2]
4960LDR R1,[mem,#min]
4970SUB R0,R0,R1,LSL#15
4980ADD R0,R0,time,LSL#15
4990TST R0,#1 << 15 ; ???
5000SUBNE time,time,#1
5010MOV R0,R0,LSR#16
5020AND R0,R0,#&FF
5030MOV PC,R14
5040
5050.readT2high_count
5060LDR R0,[mem,#T2]
5070LDR R1,[mem,#min]
5080SUB R0,R0,R1,LSL#15
5090ADD R0,R0,time,LSL#15
5100TST R0,#1 << 15 ; ???
5110SUBNE time,time,#1
5120MOV R0,R0,LSR#24
5130MOV PC,R14
5140
5150.readT1low_count
5160LDRB R1,[mem,#ifr]
5170BIC R1,R1, #%1 << 6
5180STRB R1,[mem,#ifr] ; clear T1 interrupt flag
5190LDR R0,[mem,#T1]
5200LDR R1,[mem,#min]
5210SUB R0,R0,R1,LSL#15
5220ADD R0,R0,time,LSL#15
5230TST R0,#1 << 15 ; ???
5240SUBNE time,time,#1
5250MOV R0,R0,LSR#16
5260AND R0,R0,#&FF
5270MOV PC,R14
5280
5290.readT1high_count
5300LDR R0,[mem,#T1]
5310LDR R1,[mem,#min]
5320SUB R0,R0,R1,LSL#15
5330ADD R0,R0,time,LSL#15
5340TST R0,#1 << 15 ; ???
5350SUBNE time,time,#1
5360MOV R0,R0,LSR#24
5370MOV PC,R14
5380
5390.readT1low_latch
5400LDRB R0,[mem,#T1R+2]
5410MOV PC,R14
5420
5430.readT1high_latch
5440LDRB R0,[mem,#T1R+3]
5450MOV PC,R14
5460
5470.writeT1low_latch
5480STRB R0,[mem,#T1R+2]
5490MOV PC,R14
5500
5510.writeT1high_count
5520STRB R0,[mem,#T1R+3]
5530LDR R0,[mem,#T1R]
5540LDR R1,[mem,#min]
5550ADD R0,R0,R1,LSL#15
5560SUB R0,R0,time,LSL#15
5570ADD R0,R0,#2 << 16
5580STR R0,[mem,#T1]
5590LDR R1,[mem,#ifr]
5600BIC R1,R1, #%1 << 6
5610STRB R1,[mem,#ifr] ; clear T1 interrupt flag
5620SUB R0,mem,#512 ; sheila
5630LDRB R1,[R0,#&40]
5640BIC R1,R1,#&80
5650STRB R1,[R0,#&40]
5660MOV R0,#1 : STRB R0,[mem,#T1mode]
5670MOV PC,R14
5680
5690.writeT1high_latch
5700STRB R0,[mem,#T1R+3]
5710MOV PC,R14
5720
5730.writeT2low_latch
5740STRB R0,[mem,#T2R+2]
5750MOV PC,R14
5760
5770.writeT2high_count
5780LDRB R1,[mem,#T2R+2]
5790ADD R1,R1,R0,LSL#8
5800MOV R1,R1,LSL#16
5810LDR R0,[mem,#min]
5820ADD R1,R1,R0,LSL#15
5830SUB R1,R1,time,LSL#15
5840ADD R1,R1,#2 << 16
5850STR R1,[mem,#T2]
5860LDR R1,[mem,#ifr]
5870BICS R1,R1, #%101 << 5
5880STRB R1,[mem,#ifr] ; clear T2 interrupt flag
5890MOV R0,#1 : STRB R0,[mem,#T2mode]
5900MOV PC,R14
5910
5920;.T1mode
5930;EQUD 1
5940;.T2mode
5950;EQUD 0
5960;.T3mode
5970;EQUD 1
5980;.T4mode
5990;EQUD 0
6000;.T1
6010;EQUD &1234 << 16
6020;.T1R
6030;EQUD 20000 << 16
6040;.T2
6050;EQUD 98765 << 16
6060;.T2R
6070;EQUD 255 << 16
6080;.T3
6090;EQUD 6777 << 16
6100;.T3R
6110;EQUD 6777 << 16
6120;.T4
6130;EQUD 7380 << 16
6140;.T4R
6150;EQUD 255 << 16
6160;.screen
6170;EQUD 432
6180;.screenR
6190;EQUD 40000
6200;.min
6210;EQUD 200
6220;.sound_timer
6230;EQUD 0
6240
6250
6260.keychk
6270EQUD 0
6280
6290.CLI
6300BIC F,F,#%100
6310ADD zpc,zpc,#1 << 16
6320LDRB R0,keychk
6330CMP R0,#0
6340BLEQ keyboard
6350;BL keyboard
6360FNfetch3(0,2)
6370
6380
6390
6400.fetch2
6410
6420LDR R0,[mem,#min]
6430SUB R0,R0,time
6440LDR R1,[mem,#sound_timer]
6450SUB R1,R1,R0
6460STR R1,[mem,#sound_timer]
6470
6480
6490MOV R0,#0 : STR R0,keychk
6500LDR R0,[mem,#min]
6510SUB R0,R0,time ; ***
6520LDR R1,[mem,#screen]
6530SUBS R1,R1,R0
6540STRGT R1,[mem,#screen]
6550BLLE vsync
6560
6570LDR R0,[mem,#min]
6580SUB R0,R0,time ; ***
6590LDR R1,speed
6600SUBS R1,R1,R0
6610STRGT R1,speed
6620BLLE speed_control
6630
6640; LDR R0,[mem,#T1mode]
6650; TST R0,#%1
6660; BEQ skip_timer1
6670
6680LDR R0,[mem,#min]
6690SUB R0,R0,time ; ***
6700LDR R1,[mem,#T1]
6710SUBS R1,R1,R0,LSL#15
6720STRGT R1,[mem,#T1]
6730BLLE timer1
6740.skip_timer1
6750
6760; LDR R0,[mem,#T2mode]
6770; TST R0,#%1
6780; BEQ skip_timer2
6790
6800LDR R0,[mem,#min]
6810SUB R0,R0,time ; ***
6820LDR R1,[mem,#T2]
6830SUBS R1,R1,R0,LSL#15
6840STR R1,[mem,#T2]
6850BLLE timer2
6860.skip_timer2
6870
6880; LDR R0,[mem,#T3mode]
6890; TST R0,#%1
6900; BEQ skip_timer3
6910
6920LDR R0,[mem,#min]
6930SUB R0,R0,time ; ***
6940LDR R1,[mem,#T3]
6950SUBS R1,R1,R0,LSL#15
6960STRGT R1,[mem,#T3]
6970BLLE timer3
6980.skip_timer3
6990
7000; LDR R0,[mem,#T4mode]
7010; TST R0,#%1
7020; MVNEQ R1,#0 ; -1
7030; STREQ R1,T4
7040; BEQ skip_timer4
7050
7060LDR R0,[mem,#min]
7070SUB R0,R0,time ; ***
7080LDR R1,[mem,#T4]
7090SUBS R1,R1,R0,LSL#15
7100STR R1,[mem,#T4]
7110BLLE timer4
7120.skip_timer4
7130
7140LDR R0,[mem,#min]
7150SUB R0,R0,time
7160LDR R1,[mem,#tape_count]
7170SUBS R1,R1,R0
7180STRGT R1,[mem,#tape_count]
7190BLLE tape_fetch
7200
7210LDRB R1,[mem,#ifr]
7220LDRB R2,[mem,#ifr2]
7230LDRB R12,[mem,#ier] : AND R1,R1,R12
7240LDRB R12,[mem,#ier2]: AND R2,R2,R12
7250;BIC R1,R1,#&80 : ;BIC R2,R2,#&80
7260
7270
7280;LDRB R0,[mem,#ier]
7290;BIC R0,R0,#%1 ; ignore keyboard interrupt
7300;ANDS R0,R0,R1
7310;ORRNE R1,R1,#&80
7320;LDRB R0,[mem,#ier2]
7330;ANDS R0,R0,R2
7340;ORRNE R2,R2,#&80
7350
7360TST F,#%100
7370BNE skip_do_interrupt
7380;TST R1,#&80
7390;TSTEQ R2,#&80
7400ANDS R1,R1,#%01111111
7410ANDEQS R2,R2,#%01111111
7420BEQ skip_do_interrupt
7430;CMP R13,#1
7440;BNE skip_do_interrupt
7450
7460.do_interrupt
7470FNdo_interrupt
7480
7490.skip_do_interrupt
7500
7510;BL keyboard MOVED TO CLI!!!
7520BL keys2
7530.skip_keys
7540LDR time,[mem,#T1]
7550MOV time,time,LSR#15
7560LDR R1,[mem,#screen]
7570CMP R1,#0 : MOVEQ R1,time
7580CMP R1,time
7590MOVLT time,R1
7600LDRB R1,[mem,#T2mode]
7610CMP R1,#0
7620BEQ skipT2
7630LDR R1,[mem,#T2]
7640
7650;RJW
7660MOVS R1,R1,LSR#15
7670MOVEQ R1,time
7680CMP R1,time
7690MOVLT time,R1
7700.skipT2
7710LDR R1,[mem,#T3]
7720MOVS R1,R1,LSR#15
7730
7740; RJW
7750MOVEQ R1,time
7760CMP R1,time
7770MOVLT time,R1
7780LDRB R1,[mem,#T4mode]
7790CMP R1,#0
7800BEQ skipT4
7810LDR R1,[mem,#T4]
7820
7830; RJW
7840MOVS R1,R1,LSR#15
7850MOVEQ R1,time
7860CMP R1,time
7870MOVLT time,R1
7880.skipT4
7890;CMP time,#0 : ;MOVEQ time,#1
7900SUB time,time,#4
7910STR time,[mem,#min]
7920FNfetch2
7930
7940.interrupt
7950
7960TST F,#%100
7970MOVNE PC,R14
7980
7990LDRB R1,[mem,#ifr]
8000LDRB R2,[mem,#ifr2]
8010LDRB R12,[mem,#ier] : AND R1,R1,R12
8020LDRB R12,[mem,#ier2]: AND R2,R2,R12
8030
8040ANDS R1,R1,#%01111111
8050ANDEQS R2,R2,#%01111111
8060MOVEQ PC,R14
8070
8080FNdo_interrupt
8090
8100MOV PC,R14
8110
8120.F10temp
8130EQUD 0
8140
8150.F10
8160SWI "6502_Getkdata"
8170STR R14,F10temp
8180MOV R0,#255
8190STRB R0,[mem,#lastmode]
8200BL updatescreen
8210BL force_update_pal
8211BL cursor
8220LDR PC,F10temp
8230
8240;.fetch3
8250.keys2
8260;SWI "6502_Checkkdata"
8270LDR R0,[mem,#key_addr]
8280LDRB R0,[R0,#-4]
8290
8300
8310CMP R0,#&1F ; Insert
8320MOVEQ R1,#1
8330STREQ R1,trace2
8340CMP R0,#10 ; F10
8350BEQ F10
8360CMP R0,#11 ; F11
8370CMPNE R0,#12 ; F12
8380CMPNE R0,#15 ; break
8390BEQ raw_exit2
8400MOV PC,R14
8410
8420.keyboard
8430MOV R0,#1 : STR R0,keychk
8440
8450
8460;SWI "6502_Checkkdata"
8470LDR R0,[mem,#key_addr]
8480LDRB R0,[R0,#-4]
8490CMP R0,#&FF : MOVEQ PC,R14
8500
8510
8520SWI "6502_Getkdata"
8530;CMP R0,#&FF : ;MOVEQ PC,R14
8540CMP R0,#&1F ; Insert
8550MOVEQ R1,#1
8560STREQ R1,trace2
8570CMP R0,#10 ; F10
8580BEQ F10
8590CMP R0,#15
8600CMPNE R0,#12
8610CMPNE R0,#11 ; F11
8620BEQ raw_exit
8630
8640;CMP R0,#0 ; escape
8650;LDREQB R0,[mem,#&FF]
8660;ORREQ R0,R0,#&80
8670;STREQB R0,[mem,#&FF]
8680LDRB R0,[R1,R0]
8690CMP R0,#&FF
8700;BEQ not_keyboard
8710MOVEQ PC,R14
8720
8730;B not_keyboard
8740CMP R0,#10 ; shift, ctrl
8750MOVLT PC,R14
8760LDRB R1,[mem,#ifr]
8770ORR R1,R1,#%1 ; interrupt is from keyboard
8780STRB R1,[mem,#ifr]
8790LDRB R0,[mem,#ier]
8800TST R0,#%1
8810MOVEQ PC,R14
8820FNdo_interrupt
8830MOV PC,R14
8840
8850
8860;.no_interrupt
8870;LDRB R0,trace2
8880;CMP R0,#0
8890;BEQ notrace2
8900;FNshowregs
8910;.notrace2
8920;FNfetch2
8930
8940.define_cursor
8950MOV R1,#0 : STRB R1,cursor_state
8960.define_cursor2
8970LDRB R1,cursor_state
8980CMP R1,#0:MOVNE PC,R14
8990
9000LDRB R1,[mem,#crt_regs+10] ; cursor start
9010
9020EOR R12,R1,#%100000
9030TST R12,#%1100000
9040BEQ blank_cursor
9050
9060LDRB R2,[mem,#crt_regs+11] ; cursor end
9070AND R1,R1,#31
9080AND R2,R2,#31
9090
9100SUBS R12,R2,R1
9110BLT blank_cursor
9120
9130
9140LDRB R12,[mem,#fe20]
9150EOR R12,R12,#%100000
9160
9170TST R12,#%1000
9180MOVEQ R13,#2 ; mode 5
9190MOVNE R13,#1
9200
9210MOV R0,#1
9220MOV R0,R0,LSL R13
9230TSTEQ R12,#%100000
9240MOVEQ R0,#8 ; mode 2
9250MOVEQ R13,#3
9260STRB R0,cursor_width
9270
9280TST R12,#%10 ; teletext
9290MVNNE R12,#7
9300MOVEQ R12,#1
9310
9320ADD R2,R2,R12
9330STRB R2,cursor_height
9340
9350;MOV R0,#1
9360;MOV R0,R0,LSL R13
9370;STRB R0,cursor_width
9380
9390
9400ADR R0,cursor_data
9410SUB R0,R0,R1,LSL R13
9420SUB R0,R0,R12,LSL R13
9430STR R0,cursor_block+6
9440
9450MOV R0,#21
9460ADR R1,cursor_block
9470SWI "OS_Word"
9480MOVS PC,R14
9490
9500.blank_cursor
9510MOV R1,#1 : STRB R1,cursor_state
9520.blank_cursor2
9530
9540ADR R1,cursor_block
9550ADR R0,blank_data
9560STR R0,cursor_block+6
9570MOV R0,#21
9580SWI "OS_Word"
9590MOV PC,R14
9600
9610.cursor_state
9620EQUD 0
9630
9640.cursor_flash
9650EQUD 0
9660.flash_state
9670EQUD 0
9680
9690;.not_keyboard
9700EQUW 0
9710.cursor_block
9720EQUB 0
9730EQUB 2 ; shape number
9740.cursor_width
9750EQUB 2 ; width in bytes
9760.cursor_height
9770EQUB 9 ; height in pixels
9780EQUB 0
9790EQUB 0
9800EQUD 0 ; address of data
9810
9820
9830ALIGN
9840.blank_data
9850EQUD 0
9860EQUD 0
9870EQUD 0
9880EQUD 0
9890EQUD 0
9900EQUD 0
9910EQUD 0
9920EQUD 0
9930EQUD 0
9940EQUD 0
9950EQUD 0
9960EQUD 0
9970EQUD 0
9980EQUD 0
9990EQUD 0
10000EQUD 0
10010EQUD 0
10020EQUD 0
10030EQUD 0
10040EQUD 0
10050EQUD 0
10060EQUD 0
10070EQUD 0
10080EQUD 0
10090EQUD 0
10100EQUD 0
10110EQUD 0
10120EQUD 0
10130EQUD 0
10140EQUD 0
10150EQUD 0
10160EQUD 0
10170.cursor_data
10180EQUD &FFFFFFFF
10190EQUD &FFFFFFFF
10200EQUD &FFFFFFFF
10210EQUD &FFFFFFFF
10220EQUD &FFFFFFFF
10230EQUD &FFFFFFFF
10240EQUD &FFFFFFFF
10250EQUD &FFFFFFFF
10260EQUD &FFFFFFFF
10270EQUD &FFFFFFFF
10280EQUD &FFFFFFFF
10290EQUD &FFFFFFFF
10300EQUD &FFFFFFFF
10310EQUD &FFFFFFFF
10320EQUD &FFFFFFFF
10330EQUD &FFFFFFFF
10340EQUD &FFFFFFFF
10350EQUD &FFFFFFFF
10360EQUD &FFFFFFFF
10370EQUD &FFFFFFFF
10380EQUD &FFFFFFFF
10390EQUD &FFFFFFFF
10400EQUD &FFFFFFFF
10410EQUD &FFFFFFFF
10420EQUD &FFFFFFFF
10430EQUD &FFFFFFFF
10440EQUD &FFFFFFFF
10450EQUD &FFFFFFFF
10460EQUD &FFFFFFFF
10470EQUD &FFFFFFFF
10480EQUD &FFFFFFFF
10490EQUD &FFFFFFFF
10500
10510.cursor7
10520
10530LDRB R0,[mem,#crt_regs+14]
10540LDRB R1,[mem,#crt_regs+15]
10550ADD R0,R1,R0,LSL#8
10560
10570LDRB R1,[mem,#crt_regs+12] : ;AND R1,R1,#%1111
10580LDRB R2,[mem,#crt_regs+13]
10590ADD R2,R2,R1,LSL#8
10600SUBS R0,R0,R2
10610MOVMI R0,#0
10620
10630;LDRB R12,[mem,#crt_regs+1] ; horiz. chars
10640;MOV R12,#40
10650
10660;FNdivmod(0,12,1,2,13) ; R0 = R0 MOD R12
10670 ; R2 = R0 DIV R12
10680;RSB R2,R2,#25
10690;MOV R2,R2,LSL#5
10700;ADD R2,R2,R2,LSR#2
10710;MOV R0,R0,LSL#5
10720;ADD R0,R0,R2,LSL#16
10730; We know that R0<1000
10740; R0 = R0 MOD 40
10750; R2 = R0 DIV 40
10760;FNdivmod(0,12,1,2,13)
10770MOV R2,#((25<<5)+(25<<3))<<16
10780CMP R0,#640
10790SUBGE R0,R0,#640
10800SUBGE R2,R2,#((1<<9)+(1<<7))<<16
10810CMP R0,#320
10820SUBGE R0,R0,#320
10830SUBGE R2,R2,#((1<<8)+(1<<6))<<16
10840CMP R0,#160
10850SUBGE R0,R0,#160
10860SUBGE R2,R2,#((1<<7)+(1<<5))<<16
10870CMP R0,#80
10880SUBGE R0,R0,#80
10890SUBGE R2,R2,#((1<<6)+(1<<4))<<16
10900CMP R0,#40
10910SUBGE R0,R0,#40
10920SUBGE R2,R2,#((1<<5)+(1<<3))<<16
10930
10940
10950ADD R0,R2,R0,LSL#5
10960STR R0,osword21_5_block1
10970ADR R1,osword21_5_block
10980MOV R0,#21
10990SWI "OS_Word" ; set pointer position
11000;MOV PC,R14
11001B define_cursor2
11010
11020;B cursor_cont
11030
11040.padding_to_align_osword
11050EQUB 0 : EQUB 0 : EQUB 0
11060.osword21_5_block
11070EQUB 5
11080.osword21_5_block1
11090EQUD 0
11100
11110EOR R0,R0,#&20 : ADD R0,R0,#&74 : AND R0,R0,#&FF
11120
11130
11140.cursor
11150MOV R0,#0 : STR R0,[mem,#cursor_tamper]
11160
11170\LDRB R1,[mem,#cursor_on]
11180\CMP R1,#0:\MOVNE PC,R14
11190TST F,#1 << 10 ; cursor on?
11200MOVEQ PC,R14
11210
11220LDRB R0,[mem,#fe20]
11230
11240TST R0,#%11100000
11250BEQ blank_cursor
11260
11270TST R0,#%10 ; teletext
11280BNE cursor7
11290
11300LDRB R0,[mem,#crt_regs+14]
11310LDRB R1,[mem,#crt_regs+15]
11320ADD R0,R1,R0,LSL#8
11330
11340LDRB R1,[mem,#crt_regs+12] : AND R1,R1,#%1111
11350LDRB R2,[mem,#crt_regs+13]
11360ADD R2,R2,R1,LSL#8
11370SUBS R0,R0,R2
11380MOVMI R0,#0
11390
11400.cursor_cont
11410
11420LDRB R12,[mem,#crt_regs+1] ; horiz. chars
11430
11440CMP R12,#0 : MOVEQ PC,R14
11450
11460;FNdivmod(0,12,1,2,13) ; R0 = R0 MOD R12
11470 ; R2 = R0 DIV R12
11480;RSB R2,R2,#32
11490;MOV R2,R2,LSL#5
11500
11510; We know R0<32*R12
11520; R0 = R0 MOD R12
11530; R2 = R0 DIV R12
11540MOV R2,#32<<21
11550CMP R0,R12,LSL#4
11560SUBGE R0,R0,R12,LSL#4
11570SUBGE R2,R2,#16<<21
11580CMP R0,R12,LSL#3
11590SUBGE R0,R0,R12,LSL#3
11600SUBGE R2,R2,#8<<21
11610CMP R0,R12,LSL#2
11620SUBGE R0,R0,R12,LSL#2
11630SUBGE R2,R2,#4<<21
11640CMP R0,R12,LSL#1
11650SUBGE R0,R0,R12,LSL#1
11660SUBGE R2,R2,#2<<21
11670CMP R0,R12
11680SUBGE R0,R0,R12
11690SUBGE R2,R2,#1<<21
11700
11710
11720LDRB R1,[mem,#fe20] : TST R1,#%10000 : MOVEQ R0,R0,LSL#1
11730;MOV R0,R0,LSL#4 ; these two surplus
11740;ADD R0,R0,R2,LSL#16 ;
11750ADD R0,R2,R0,LSL#4 ; this line missing in 1.30
11760STR R0,osword21_5_block1
11770ADR R1,osword21_5_block
11780MOV R0,#21
11790SWI "OS_Word" ; set pointer position
11800;MOV PC,R14
11801B define_cursor2
11810
11820.mono_time
11830EQUD 0
11840.speed
11850EQUD 0
11860
11870.speed_control
11880LDR R0,[mem,#speedR]
11890ADD R1,R1,R0
11900STR R1,speed
11910
11920LDR R1,mono_time
11930.mono_loop
11940SWI "OS_ReadMonotonicTime"
11950MOV R0,R0,LSR#1
11960CMP R0,R1
11970BEQ mono_loop
11980STR R0,mono_time
11990
12000MOV PC,R14
12010
12020
12030
12040.vsync
12050STR R14,vsyncR14
12060
12070
12080LDR R0,[mem,#screenR]
12090ADD R1,R1,R0
12100STR R1,[mem,#screen]
12110
12120LDRB R0,ldrb40_tamper
12130CMP R0,#1 : BLEQ ldrb40_update
12140
12150;BL trace_on
12160
12170;LDRB R1,screen_count
12180;SUBS R1,R1,#1
12190;LDRMIB R1,screen_count+4
12200;STRB R1,screen_count
12210LDR R0,[mem,#tamper]
12220CMP R0,#0
12230
12240BEQ no_tamper
12250MOV R0,#0
12260STR R0,[mem,#tamper]
12270;SWI "6502_UpdateScreen"
12280BL recalc_wrap
12290BL updatescreen
12300TST F,#1 << 10 ; cursor on?
12310;BLNE define_cursor
12320BLNE cursor
12330.no_tamper
12340LDRB R0,[mem,#pal_tamper]
12350CMP R0,#0
12360BLNE update_pal
12370
12380
12390LDR R0,[mem,#cursor_tamper]
12400CMP R0,#0
12410BLNE cursor
12420
12430
12440
12450SUB R0,mem,#512 ; sheila
12460LDRB R1,[R0,#&20]
12470TST R1,#%10 ; teletext?
12480;SWINE "6502_UpdateScreen"
12490BLNE updatescreen
12500ADD R0,R0,#&4D
12510;LDRB R1,[R0]
12520;LDRB R2,[R0,#1]
12530LDRB R1,[mem,#ifr]
12540LDRB R2,[mem,#ier]
12550ORR R1,R1,#%10 ; interrupt is from vsync
12560TST R2,#%10 ; is vsync interrupt enabled?
12570ORRNE R1,R1,#&80
12580;STRB R1,[R0]
12590STRB R1,[mem,#ifr]
12600;BEQ no_interrupt
12610;FNfetch2
12620
12630;TST F,#1 << 9
12640;BEQ skip_exact
12650
12660;LDR R1,mono_time
12670;.mono_loop
12680;SWI "OS_ReadMonotonicTime"
12690;MOV R0,R0,LSR#1
12700;CMP R0,R1
12710;BEQ mono_loop
12720;STR R0,mono_time
12730
12740.skip_exact
12750
12760TST F,#1 << 10 ; cursor on?
12770LDREQ PC,vsyncR14
12780
12790LDRB R1,cursor_state
12800CMP R1,#0
12810LDRNE PC,vsyncR14
12820
12830LDRB R1,[mem,#crt_regs+10]
12840TST R1,#%1000000 ; cursor blinking enabled?
12850LDREQ PC,vsyncR14
12860
12870LDRB R0,cursor_flash
12880SUBS R0,R0,#1
12890STRB R0,cursor_flash
12900LDRGE PC,vsyncR14
12910
12920TST R1,#%100000
12930MOVEQ R0,#15
12940MOVNE R0,#31
12950STRB R0,cursor_flash
12960
12970LDR R14,vsyncR14
12980LDRB R0,flash_state
12990EOR R0,R0,#1
13000STRB R0,flash_state
13010CMP R0,#0 : BEQ blank_cursor2
13020B define_cursor2
13030
13040;LDR PC,vsyncR14
13050.vsyncR14
13060EQUD 0
13070
13080.ldrb40
13090
13100LDRB R2,ldrb40_value
13110BIC R0,R0,#%110000
13120ORR R0,R0,R2
13130MOV R1,#1
13140STRB R1,ldrb40_tamper
13150MOV PC,R14
13160
13170.ldrb40_update
13180MOV R0,#%110000
13190STRB R0,ldrb40_value
13200MOV R0,#0
13210STRB R0,ldrb40_tamper
13220TST F,#1<<9 ; joystick
13230MOVEQ PC,R14
13240SWI &63F40 ; "XJoystick_Read"
13250BVS ldrb40_mouse
13260AND R1,R0,#&10000
13270MOV R0,#1
13280SWI &63F40 ; "XJoystick_Read"
13290MOVVS R0,#0
13300AND R0,R0,#&10000
13310ADD R1,R1,R0,LSL#1
13320AND R1,R1,#&30000
13330MOV R1,R1,LSR#(16-4)
13340
13350EOR R2,R1,#%110000
13360
13370;ADD R13,mem,#&FE00
13380;LDRB R0,[R13,#&40]
13390;BIC R0,R0,#%110000
13400STRB R2,ldrb40_value
13410;ORR R0,R0,R2
13420
13430MOV PC,R14
13440
13450.ldrb40_tamper
13460EQUD 0
13470.ldrb40_value
13480EQUD 0
13490
13500.ldrb40_mouse
13510MOV R13,R3
13520SWI "OS_Mouse"
13530MOV R3,R13
13540
13550MOV R2,R2,LSR#1
13560RSB R2,R2,#3
13570MOV R2,R2,LSL#4
13580;ADD R13,mem,#&FE00
13590;LDRB R0,[R13,#&40]
13600;BIC R0,R0,#%110000
13610STRB R2,ldrb40_value
13620;ORR R0,R0,R2
13630
13640MOV PC,R14
13650
13660.write_ADC_status
13670
13680TST F,#1<<9 ; joystick
13690MOVEQ PC,R14
13700
13710
13720BIC R12,R0,#%11110000
13730
13740MOV R0,R0,LSR#1
13750AND R0,R0,#%1 ; joystick number
13760SWI &63F40 ; "XJoystick_Read"
13770BVS write_ADC_mouse
13780
13790
13800TST R12,#%1 ; left/right or up/down
13810MOVEQ R0,R0,LSR#8
13820ADD R0,R0,#127
13830AND R0,R0,#&FF
13840RSBEQ R0,R0,#255
13850
13860MOV R1,R0,LSR#2
13870AND R1,R1,#%110000
13880ORR R12,R12,R1
13890ORR R12,R12,#%1000000
13900
13910SUB R1,mem,#512 ; sheila
13920
13930STRB R12,[R1,#&C0]
13940STRB R12,[R1,#&18]
13950
13960STRB R0,[R1,#&C1]
13970STRB R0,[R1,#&19]
13980MOV R12,#0
13990STRB R12,[R1,#&C2]
14000STRB R12,[R1,#&1A]
14010
14020MOV PC,R14
14030
14040.write_ADC_mouse
14050
14060MOV R13,R3
14070SWI "OS_Mouse"
14080MOV R3,R13
14090
14100MOV R2,#1024
14110SUB R2,R2,#1
14120SUBS R0,R2,R0
14130MOVLT R0,#0
14140
14150;CMP R0,#1024
14160;MOVGE R0,#1024
14170;SUBGE R0,R0,#1
14180
14190TST R12,#%1 ; left/right or up/down
14200MOVNE R0,R1
14210
14220MOV R1,R0,LSL#4
14230AND R1,R1,#%110000
14240ORR R12,R12,R1
14250ORR R12,R12,#%1000000
14260
14270SUB R1,mem,#512 ; sheila
14280
14290STRB R12,[R1,#&C0]
14300STRB R12,[R1,#&18]
14310
14320MOV R12,R0,LSR#2
14330STRB R12,[R1,#&C1]
14340STRB R12,[R1,#&19]
14350MOV R12,R0,LSL#6
14360STRB R12,[R1,#&C2]
14370STRB R12,[R1,#&1A]
14380
14390MOV PC,R14
14400
14410
14420.timer1
14430LDR R0,[mem,#T1R]
14440ADD R1,R1,R0
14450ADD R1,R1,#2 << 16
14460STR R1,[mem,#T1]
14470
14480SUB R0,mem,#512 ; sheila
14490
14500LDRB R1,[R0,#&4B] ; FE4B
14510TST R1,#%01000000
14520MOVEQ R2,#0
14530STREQB R2,[mem,#T1mode]
14540
14550TST R1,#%10000000
14560LDRNEB R2,[R0,#&40] ; FE40
14570EORNE R2,R2,#&80
14580STRNEB R2,[R0,#&40] ; FE40
14590
14600LDRB R1,[mem,#ifr]
14610ORR R1,R1,#%01000000 ; interrupt is from timer 1
14620STRB R1,[mem,#ifr]
14630
14640MOV PC,R14
14650
14660.timer2
14670LDRB R0,[mem,#T2mode]
14680CMP R0,#0
14690MOVEQ PC,R14
14700MOV R0,#0
14710STRB R0,[mem,#T2mode]
14720
14730LDRB R1,[mem,#ifr]
14740ORR R1,R1,#%00100000
14750STRB R1,[mem,#ifr]
14760
14770MOV PC,R14
14780
14790.timer3
14800LDR R0,[mem,#T3R]
14810ADD R1,R1,R0
14820STR R1,[mem,#T3]
14830
14840SUB R0,mem,#512 ; sheila
14850
14860LDRB R1,[R0,#&6B]
14870TST R1,#%01000000
14880BNE T3mode_skip2
14890
14900LDRB R1,[mem,#T3mode]
14910CMP R1,#1
14920;SWINE &100+ASC"1"
14930;SWIEQ &100+ASC"0"
14940BNE T3mode_skip
14950
14960.T3mode_skip2
14970LDRB R1,[mem,#ifr2]
14980ORR R1,R1,#%01000000
14990STRB R1,[mem,#ifr2]
15000
15010
15020;LDRB R1,[R0,#&6B] ; FE6B
15030;TST R1,#%01000000
15040;MOVEQ R2,#0
15050;MOVNE R2,#1
15060;STREQB R2,[mem,#T3mode]
15070;SWIEQ &100+ASC"z"
15080
15090.T3mode_skip
15100MOV R2,#0
15110STRB R2,[mem,#T3mode]
15120
15130;LDRB R1,[R0,#&6B] ; FE6B
15140;TST R1,#%10000000
15150;LDRB R2,[R0,#&60] ; FE60
15160;EORNE R2,R2,#&80
15170;ORREQ R2,R2,#&80
15180;STRB R2,[R0,#&60] ; FE60
15190
15200LDRB R1,[R0,#&6B] ; FE6B
15210EOR R1,R1,#&C0
15220TST R1,#&C0
15230LDRB R2,[R0,#&60] ; FE60
15240EOREQ R2,R2,#&80
15250ORRNE R2,R2,#&80
15260STRB R2,[R0,#&60] ; FE60
15270
15280
15290MOV PC,R14
15300.return_addr
15310EQUD 0
15320
15330.roms_addr
15340EQUD 0
15350
15360.timer4
15370LDRB R1,[mem,#T4mode]
15380CMP R1,#0
15390MOVEQ PC,R14
15400MOV R0,#0
15410STRB R0,[mem,#T4mode]
15420
15430
15440LDRB R1,[mem,#ifr2]
15450ORR R1,R1,#%00100000 ; interrupt is from timer 4
15460STRB R1,[mem,#ifr2]
15470
15480MOV PC,R14
15490
15500
15510;.trace2
15520;EQUD 0
15530
15540.reset
15550;MOV R1,#1
15560;STR R1,trace
15570MOV R0,#15 : MOV R1,#0 : SWI "OS_Byte"
15580MOV R0,#&10000
15590SUB R0,R0,#4
15600LDR R0,[mem,R0]
15610MOV zpc,R0,LSL#16
15620BIC F,F,#%1000 ; clear Decimal mode
15630ORR F,F,#%100 ; set interrupt disable
15640FNfetch2
15650
15660
15670.exit
15680MOV R0,#0
15690.raw_exit2
15700SWI "6502_Getkdata"
15710.raw_exit
15720STR time,[mem,#min]
15730STR A,[mem,#a]
15740STR X,[mem,#x]
15750STR Y,[mem,#y]
15760STR SP,[mem,#sp]
15770STR F,[mem,#f]
15780STR zpc,[mem,#pc_store]
15790LDR R13,return_addr
15800LDMFD R13!,{R1-R12,PC}
15810;MOV PC,R14
15820
15830
15840.fe08_read
15850EQUB 0
15860.fe08_write
15870EQUB 0
15880.fe09
15890EQUB 0
15900;.fe10
15910;EQUB 0
15920ALIGN
15930.tbuffer
15940EQUD 0
15950
15960.tape_fetch
15970;LDR R0,[mem,#tapeR]
15980;MOV R0,#&3400 ; 2000000/(1200/8)~=1200 baud
15990MOV R0,#&6000
16000ADDS R1,R1,R0
16010MOVLE R1,#&6000
16020
16030LDRB R0,[mem,#fe10]
16040TST R0,#&80 ; is *Motor on?
16050MOVEQ R1,#&100000
16060
16070STR R1,[mem,#tape_count]
16080
16090MOVEQ PC,R14
16100
16110LDRB R1,[mem,#tape_handle]
16120CMP R1,#0
16130MOVEQ PC,R14
16140
16150.tape_get
16160SWI "XOS_BGet"
16170MOVVS R1,#0
16180STRVSB R1,[mem,#tape_handle]
16190MOVVS PC,R14
16200
16210BCC tape_skip10
16220
16230MOV R0,#1
16240MOV R2,#0
16250SWI "XOS_Args" ; rewind tape to start
16260MOVVS R1,#0
16270STRVSB R1,[mem,#tape_handle]
16280MOVVS PC,R14
16290
16300.tape_skip10
16310
16320CMP R0,#&FF
16330BNE not_FF
16340SWIEQ "XOS_BGet"
16350CMP R0,#&FF
16360BEQ not_FF
16370
16380LDRB R1,fe08_read
16390BIC R1,R1,#%100
16400AND R0,R0,#%100
16410ORR R1,R1,R0
16420;ORR R1,R1,#&80 ; ??
16430STRB R1,fe08_read
16440
16450CMP R0,#0
16460
16470;MOV R0,#&10000
16480;STR R0,[mem,#tape_count]
16490
16500;B do_interrupt
16510MOVEQ PC,R14
16520
16530ORR R1,R1,#&80
16540STRB R1,fe08_read
16550B do_interrupt
16560
16570.not_FF
16580STRB R0,fe09
16590
16600
16610LDRB R0,fe08_write
16620TST R0,#&80 ; receive interrupt enable bit
16630MOVEQ PC,R14
16640
16650LDRB R0,fe08_read
16660ORR R0,R0,#&81
16670STRB R0,fe08_read
16680
16690B do_interrupt
16700;MOV PC,R14
16710
16720.readFE08
16730;LDRB R1,tbuffer
16740;LDRB R0,[mem,#&C2]
16750;CMP R0,#1
16760LDRB R0,fe08_read
16770;CMPEQ R1,#ASC"*"
16780;ORREQ R0,R0,#%100
16790;BICNE R0,R0,#%100
16800MOV PC,R14
16810
16820.readFE09
16830LDRB R0,fe08_read
16840BIC R0,R0,#&81
16850STRB R0,fe08_read
16860LDRB R0,fe09
16870MOV PC,R14
16880
16890.writeFE08
16900STRB R0,fe08_write
16910MOV PC,R14
16920
16930.writeFE09
16940MOV PC,R14
16950
16960.readFE10
16970MOV R0,#&A2
16980MOV PC,R14
16990
17000.writeFE10
17010STRB R0,[mem,#fe10]
17020MOV PC,R14
17030
17040.dummy
17050MOV PC,R14
17060
17070;.ROMSEL
17080;EQUD 0
17090
17100;.rom ; ROM paged in
17110;EQUD 0
17120
17130;.ROMRAM ; which banks are RAM?
17140;EQUD 0 : ;EQUD 0 : ;EQUD 0 : ;EQUD 0
17150
17160;.ACCCON
17170;EQUD 0
17180
17190
17200.swap_main_shadow
17210
17220STMFD mem,{R0-R2,R4-R11,R14}
17230ADD R14,mem,#&3000
17240SUB R13,mem,#&10000
17250MOV R12,#&5000
17260.swap_loop
17270LDMIA R14,{R0-R2,R4-R5}
17280;LDR R0,[R14,#0]
17290;LDR R1,[R14,#4]
17300;LDR R2,[R14,#8]
17310;LDR R4,[R14,#12]
17320;LDR R5,[R14,#16]
17330
17340LDMIA R13,{R6-R10}
17350;LDR R6,[R13,#0]
17360;LDR R7,[R13,#4]
17370;LDR R8,[R13,#8]
17380;LDR R9,[R13,#12]
17390;LDR R10,[R13,#16]
17400
17410STMIA R13!,{R0-R2,R4-R5}
17420;STR R0,[R13,#0]
17430;STR R1,[R13,#4]
17440;STR R2,[R13,#8]
17450;STR R4,[R13,#12]
17460;STR R5,[R13,#16]
17470
17480STMIA R14!,{R6-R10}
17490;STR R6,[R14,#0]
17500;STR R7,[R14,#4]
17510;STR R8,[R14,#8]
17520;STR R9,[R14,#12]
17530;STR R10,[R14,#16]
17540
17550;ADD R14,R14,#20
17560;ADD R13,R13,#20
17570SUBS R12,R12,#20
17580BHI swap_loop
17590
17600LDMEA mem,{R0-R2,R4-R11,R14}
17610B swap_exit
17620
17630
17640.strb_rom_ret2 ; between C000 AND E000
17650LDRB R2,[mem,#ACCCON]
17660TST R2,#%1000
17670;SUBNE R13,mem,#(&C000+&A000)
17680;STRNEB R0,[R13,R1]
17690STRNEB R0,[mem,R1]
17700MOV PC,R14
17710
17720.acccon
17730]
17740IF NOTmaster THEN [OPTp:MOV PC,R14:]
17750[OPTp
17760LDRB R1,[mem,#ACCCON]
17770STRB R0,[mem,#ACCCON]
17780EOR R2,R0,R1
17790
17800TST R2,#%1 ; main/shadow to be displayed
17810STRNEB R12,[mem,#tamper]
17820
17830;MOV PC,R14
17840
17850;TST R2,#%100 ; main/shadow to be paged in
17860;BNE swap_main_shadow
17870.swap_exit
17880
17890ANDS R2,R2,#%1000 ; filing system RAM
17900MOVEQ PC,R14
17910
17920STMFD mem,{R0-R2,R4-R9,R14}
17930
17940TST R1,#%1000
17950BEQ os_out
17960;BNE os_in
17970
17980.os_in ; RJW
17990LDR R12,roms_addr
18000ADD R12,R12,#16*16*1024 ; 17th ROM = OS3.2
18010MOV R13,#&2000
18020SUB R2,mem,#&B000
18030ADD mem,mem,#&C000
18040.os_in_loop
18050LDMIA mem, {R0,R1,R4,R5,R6,R7,R8,R9}
18060STMIA R2!, {R0,R1,R4,R5,R6,R7,R8,R9}
18070LDMIA R12!,{R0,R1,R4,R5,R6,R7,R8,R9}
18080STMIA (mem)!,{R0,R1,R4,R5,R6,R7,R8,R9}
18090SUBS R13,R13,#4*8
18100BGT os_in_loop
18110SUB mem,mem,#&E000
18120LDMEA mem,{R0-R2,R4-R9,PC}
18130
18140.os_out ; RJW
18150MOV R13,#&2000
18160SUB R2,mem,#&B000
18170ADD mem,mem,#&C000
18180.os_out_loop
18190LDMIA R2!,{R0,R1,R4,R5,R6,R7,R8,R9}
18200STMIA (mem)!,{R0,R1,R4,R5,R6,R7,R8,R9}
18210SUBS R13,R13,#4*8
18220BGT os_out_loop
18230SUB mem,mem,#&E000
18240LDMEA mem,{R0-R2,R4-R9,PC}
18250
18260.strb8000 ; greater than 8000
18270]
18280IF master THEN
18290[OPTp
18300CMP R1,#&E000
18310BGE strb_rom_ret
18320CMP R1,#&C000
18330BGE strb_rom_ret2
18340CMP R1,#&9000
18350BGE strb_rom
18360]
18370ELSE
18380[OPTp
18390CMP R1,#&C000
18400BGE strb_rom_ret
18410]
18420ENDIF
18430[OPTp
18440
18450LDRB R12,[mem,#rom]
18460TST R12,#&80
18470BEQ strb_rom
18480
18490;SUB R13,mem,#(&8000+&B000) ; 4k Private RAM
18500;STRB R0,[R13,R1]
18510STRB R0,[mem,R1]
18520MOV PC,R14
18530
18540.strb_rom
18550SUB R12,mem,#-ROMRAM
18560LDRB R13,[mem,#rom]
18570LDRB R13,[R12,R13]
18580CMP R13,#0
18590STREQB R0,[mem,R1]
18600MOV PC,R14
18610;B strb_rom_ret
18620
18630.romsel
18640LDRB R12,[mem,#ROMSEL_ON]
18650CMP R12,#0
18660MOVNE PC,R14
18670
18680LDRB R1,[mem,#rom]
18690
18700]
18710IF NOTmaster THEN
18720[OPTp
18730AND R0,R0,#%1111
18740CMP R0,R1 : MOVEQ PC,R14 ; WAR (used to) need this commented out!?!
18750B romsel_next
18760]
18770ENDIF
18780[OPTp
18790
18800AND R0,R0,#%10001111
18810
18820CMP R0,R1 : MOVEQ PC,R14 ; WAR (used to) need this commented out!?!
18830
18840EOR R2,R0,R1
18850ANDS R2,R2,#%10000000 ; private RAM bit
18860BEQ romsel_next ; bit not changed
18870
18880TST R1,#%10000000
18890BNE private_out ; map out private RAM
18900BEQ private_in ; map in private RAM
18910
18920
18930
18940.romsel_next
18950LDR R12,roms_addr
18960AND R2,R0,#&F ; socket number
18970LDRB R1,[mem,#rom]
18980AND R1,R1,#&F
18990STRB R0,[mem,#rom]
19000SUB R13,mem,#-ROMRAM
19010LDRB R13,[R13,R1]
19020CMP R13,#0 ; is the bank being paged out RAM?
19030BNE romsel2
19040
19050TST R0,#%10000000 ; private RAM mapped in?
19060MOVEQ R13,#&8000
19070MOVNE R13,#&9000
19080AND R0,R0,#&F
19090
19100ADD R2,R12,R1,LSL#14
19110ADDNE R2,R2,#&1000
19120ADD R12,R12,R0,LSL#14 ; R0*16*1024
19130ADDNE R12,R12,#&1000
19140ADR R1,romsel_loop_temp
19150STMIA R1,{R0,R4-R8,R14}
19160ADD mem,mem,R13
19170RSB R13,R13,#&C000
19180.romsel_loop
19190LDMIA mem,{R0,R1,R4,R5,R6,R7,R8,R14}
19200STMIA R2!,{R0,R1,R4,R5,R6,R7,R8,R14}
19210LDMIA R12!,{R0,R1,R4,R5,R6,R7,R8,R14}
19220STMIA (mem)!,{R0,R1,R4,R5,R6,R7,R8,R14}
19230SUBS R13,R13,#4*8
19240BNE romsel_loop
19250SUB mem,mem,#&C000
19260ADR R1,romsel_loop_temp
19270LDMIA R1,{R0,R4-R8,PC}
19280.romsel_loop_temp
19290EQUD 0:EQUD 0:EQUD 0:EQUD 0
19300EQUD 0:EQUD 0:EQUD 0:EQUD 0
19310
19320.romsel_empty
19330ADD R13,R2,R2,LSL#8
19340ADD R13,R13,R13,LSL#16
19350ADD R0,mem,#&8000
19360STR R13,[R0,#0]
19370STR R13,[R0,#4]
19380STR R13,[R0,#8]
19390STR R13,[R0,#12]
19400MOV PC,R14
19410
19420.romsel2
19430
19440SUB R13,mem,#-ROMRAM
19450LDRB R13,[R13,R2]
19460CMP R13,#2 ; is the bank being paged out empty?
19470BEQ romsel_empty
19480
19490TST R0,#%10000000 ; private RAM mapped in?
19500MOVEQ R13,#&8000
19510MOVNE R13,#&9000
19520AND R0,R0,#&F
19530
19540
19550ADD R12,R12,R0,LSL#14 ; R0*16*1024
19560ADDNE R12,R12,#&1000
19570ADD mem,mem,R13
19580RSB R13,R13,#&C000
19590ADR R1,romsel_loop_temp
19600STMIA R1,{R0,R4-R8,R14}
19610.romsel2_loop
19620LDMIA R12 !,{R0,R1,R4,R5,R6,R7,R8,R14}
19630STMIA (mem)!,{R0,R1,R4,R5,R6,R7,R8,R14}
19640;LDR R1,[R12],#4
19650;STR R1,[mem],#4 ; store byte from ROM in main memory map
19660SUBS R13,R13,#4*8
19670BNE romsel2_loop
19680SUB mem,mem,#&C000
19690ADR R1,romsel_loop_temp
19700LDMIA R1,{R0,R4-R8,PC}
19710
19720.private_in ; RJW
19730STMFD mem,{R0-R2,R4-R10}
19740LDR R2,roms_addr
19750AND R1,R1,#&F
19760ADD R2,R2,R1,LSL#14 ; R1*16*1024
19770SUB R12,mem,#&B000-&8000
19780MOV R13,#&1000
19790ADD mem,mem,#&8000
19800.priv_in_loop
19810LDMIA (mem), {R1,R4,R5,R6,R7,R8,R9,R10}
19820STMIA R2!, {R1,R4,R5,R6,R7,R8,R9,R10}
19830LDMIA R12!, {R1,R4,R5,R6,R7,R8,R9,R10}
19840STMIA (mem)!,{R1,R4,R5,R6,R7,R8,R9,R10}
19850SUBS R13,13,#4*8
19860BNE priv_in_loop
19870SUB mem,mem,#&9000
19880LDMEA mem,{R0-R2,R4-R10}
19890B romsel_next
19900
19910.private_out ; RJW
19920STMFD mem,{R0-R2,R4-R10}
19930LDR R2,roms_addr
19940LDRB R1,[mem,#rom]
19950AND R1,R0,#&F
19960ADD R2,R2,R1,LSL#14 ; R1*16*1024
19970SUB R12,mem,#&B000-&8000
19980MOV R13,#&1000
19990ADD mem,mem,#&8000
20000.priv_out_loop
20010LDMIA (mem), {R1,R4,R5,R6,R7,R8,R9,R10}
20020STMIA R12!, {R1,R4,R5,R6,R7,R8,R9,R10}
20030LDMIA R2!, {R1,R4,R5,R6,R7,R8,R9,R10}
20040STMIA (mem)!,{R1,R4,R5,R6,R7,R8,R9,R10}
20050SUBS R13,R13,#4*8
20060BNE priv_out_loop
20070SUB mem,mem,#&9000
20080LDMEA mem,{R0-R2,R4-R10}
20090B romsel_next
20100
20110.crt
20120SUB R1,mem,#512 ; sheila
20130LDRB R12,[R1,#0]
20140AND R12,R12,#%11111
20150CMP R12,#17
20160MOVHI PC,R14
20170;ADR R13,crt_regs
20180SUB R13,mem,#-crt_regs
20190LDRB R1,[R13,R12]
20200CMP R1,R0 : MOVEQ PC,R14 ; no change
20210STRB R0,[R13,R12]
20220ADD PC,PC,R12,LSL#2
20230MOV R0,R0 ; padding for pipeline
20240MOV PC,R14 ; reg 0
20250B new_horizvert ; reg 1
20260MOV PC,R14 ; reg 2
20270MOV PC,R14 ; reg 3
20280MOV PC,R14 ; reg 4
20290MOV PC,R14 ; reg 5
20300B new_horizvert ; reg 6
20310MOV PC,R14 ; reg 7
20320MOV PC,R14 ; reg 8
20330MOV PC,R14 ; reg 9
20340B cursor_start ; reg 10
20350B cursor_end ; reg 11
20360B crt12 ; reg 12
20370B crt13 ; reg 13
20380B cursor_changed ; reg 14
20390B cursor_changed ; reg 15
20400MOV PC,R14 ; reg 16
20410MOV PC,R14 ; reg 17
20420
20430
20440
20450CMP R12,#14 : CMPNE R12,#15 : MOVEQ R0,#1 : STREQ R0,[mem,#cursor_tamper]
20460CMP R12,#10 : BEQ cursor_start
20470CMP R12,#11 : BEQ cursor_end
20480CMP R12,#12 : BEQ crt12 : .crt12cont
20490CMP R12,#12
20500CMPNE R12,#13
20510CMPNE R12,#1
20520CMPNE R12,#6
20530MOVNE PC,R14
20540MOV R13,#1
20550STR R13,[mem,#tamper]
20560CMP R12,#1
20570CMPNE R12,#6
20580BEQ new_horizvert
20590;CMP R12,#13
20600;SWIEQ "6502_UpdateScreen"
20610CMP R12,#12
20620CMPNE R12,#13
20630MOVNE PC,R14
20640B recalc_wrap
20650
20660.cursor_changed
20670MOV R0,#1
20680STRB R0,[mem,#cursor_tamper]
20690MOV PC,R14
20700
20710.new_horizvert
20720MOV R13,#1
20730STR R13,[mem,#tamper]
20740SUB R12,R1,R0
20750CMP R12,#2
20760MOVLE PC,R14
20770MOV R12,#255 : STRB R12,[mem,#lastmode]
20780MOV PC,R14
20790
20800.crt12
20810CMP R0,#%0110
20820MOVLT R0,#%110
20830STRB R0,[R13,R12]
20840;B crt12cont
20850.crt13
20860
20870TST F,#1<<11
20880;]
20890;IF NOT HWScroll THEN
20900;[OPTp
20910MOVEQ R13,#1
20920STREQ R13,[mem,#tamper] ; don't want this for HW Scroll
20930BEQ recalc_wrap
20940;]
20950;ELSE
20960
20970;[OPTp
20980; HW scroll
20990LDR R12,updatepixelV
21000ADR R13,dohardware_scroll
21010CMP R12,R13
21020STRNE R13,updatepixelV
21030
21040B recalc_wrap
21050
21060.dohardware_scroll
21070; Here we do the hardware scrolling
21080STR R14,yuk
21090BL dohardwarescroll
21100BL poke_updatepixelV
21110LDR R14,yuk
21120; Then we go do the update as normal.
21130;LDR PC,dohardware_scrollV ; old contents of upV
21140LDR PC,updatepixelV
21150
21160.yuk
21170EQUD 0
21180
21190;.dohardware_scrollV
21200;EQUD 0
21210
21220.dohardwarescroll
21230FNdohardwarescroll
21240
21250;.screenwidthchanged
21260;MOV PC,R14
21270
21280.hardware_scroll_stack_space
21290]:P%+=256:O%+=256:[OPT p
21300.hardware_scroll_stack_space_top
21310]
21320
21330ENDIF
21340
21350[OPTp
21360; end of hardware scroll stuff
21370
21380.cursor_start
21390\LDRB R1,[mem,#cursor_on]
21400\CMP R1,#0:\MOVNE PC,R14
21410TST F,#1 << 10 ; cursor on?
21420MOVEQ PC,R14
21430LDRB R1,[mem,#crt_regs+11]
21440AND R1,R1,#%11111
21450AND R2,R0,#%11111
21460CMP R2,R1
21470BGT blank_cursor
21480
21490EOR R0,R0,#%100000
21500TST R0,#%1100000
21510BEQ blank_cursor
21520B define_cursor
21530
21540.cursor_end
21550\LDRB R1,[mem,#cursor_on]
21560\CMP R1,#0:\MOVNE PC,R14
21570TST F,#1 << 10 ; cursor on?
21580MOVEQ PC,R14
21590AND R1,R0,#%11111
21600LDRB R2,[mem,#crt_regs+10]
21610AND R2,R2,#%11111
21620CMP R2,R1
21630BGT blank_cursor
21640B define_cursor
21650;MOV PC,R14
21660
21670.link
21680EQUD 0
21690
21700.caps_lock
21710AND R0,R0,#%1000
21720MOV R1,R0,LSL#1
21730MOV R0,#202
21740MOV R2,#%11101111
21750SWI "OS_Byte"
21760MOV R0,#118
21770SWI "OS_Byte"
21780MOV PC,R14
21790
21800.latch
21810;ORR R0,R0,#%110000
21820;STRB R0,[mem,R1] ; no fire buttons
21830ANDS R2,R0,#%111
21840
21850;RJW
21860;CMP R2,#0
21870TSTEQ F,#1<<12 ; sound on?
21880BEQ sound_latch
21890CMP R2,#3
21900BEQ latch_keyb
21910CMP R2,#6
21920BEQ caps_lock
21930LDRB R12,[mem,#crt_regs+19]
21940CMP R2,#4
21950ANDEQ R13,R0,#%1000
21960BICEQ R12,R12,#%1
21970ORREQ R12,R12,R13,LSR#3
21980CMP R2,#5
21990ANDEQ R13,R0,#%1000
22000BICEQ R12,R12,#%10
22010ORREQ R12,R12,R13,LSR#2
22020STRB R12,[mem,#crt_regs+19]
22030
22040.recalc_wrap
22050LDRB R12,[mem,#crt_regs+19]
22060ANDS R12,R12,#%11
22070MOVNE R13,#&5800
22080MOVEQ R13,#&4000
22090CMP R12,#%10
22100MOVEQ R13,#&3000
22110CMP R12,#%01
22120MOVEQ R13,#&6000
22130
22140LDRB R12,[mem,#crt_regs+13]
22150LDRB R2,[mem,#crt_regs+12]
22160AND R2,R2,#%1111
22170ADD R12,R12,R2,LSL#8
22180
22190CMP R13,R12,LSL#3
22200MOVGT R13,R12,LSL#3
22210
22220SUB R12,mem,#512 ; sheila
22230LDRB R12,[R12,#&20]
22240
22250TST R12,#%10 ; teletext?
22260MOVNE R13,#&7C00
22270
22280;AND F,F,#&FF
22290BIC F,F,#&FF000000
22300BIC F,F,#&FF0000
22310ORR F,F,R13,LSL#16
22320;STR R13,wrap_addr
22330MOV PC,R14
22340
22350
22360.latch_keyb
22370
22380AND R2,R0,#%1000
22390STRB R2,key_write_ena
22400CMP R2,#%1000
22410MOVNE PC,R14
22420MOV R2,#0
22430STRB R2,column_counter
22440MOV PC,R14
22450
22460.printer_write
22470SWI &102
22480SWI &101
22490SWI "OS_WriteC"
22500MOV R0,#152 : MOV R1,#3
22510SWI "OS_Byte" ; check printer buffer
22520BCS printer_on
22530MOV R0,#21 : MOV R1,#3
22540SWI "OS_Byte" ; flush buffer
22550.printer_on
22560SWI &103
22570LDRB R0,[mem,#ifr2]
22580ORR R0,R0,#%10
22590STRB R0,[mem,#ifr2]
22600MOV PC,R14
22610
22620.regB_41
22630
22640SUB R12,mem,#512 ; sheila
22650LDRB R1,[R12,#&C] ; PCR
22660LDRB R2,[mem,#ifr]
22670AND R13,R1,#%1110
22680TEQ R13, #%0010
22690TEQNE R13, #%0110
22700BICEQ R2,R2,#%11
22710BICNE R2,R2,#%10
22720STRB R2,[mem,#ifr]
22730.regB_4F
22740SUB R12,mem,#512 ; sheila
22750
22760STRB R0,sound_data ; keep a copy in sound_data
22770
22780LDRB R2,[R12,#&43] ; R2=data direction
22790AND R1,R0,R2
22800;MOV R1,R0
22810ANDS R0,R1,#%01110000 : MOVNE R0,#0 : STRNEB R0,column_counter
22820;EOR R1,R1,#&FF
22830;SWI "6502_Getkeyaddr"
22840LDR R0,[mem,#key_addr]
22850LDRB R2,[R0] ; shift pressed?
22860CMP R2,#0
22870ADDNE R0,R0,#256
22880
22890AND R2,R1,#&F
22900CMP R2,#&F ; column counter disabled?
22910BEQ disable_column_counter
22920LDRB R2,column_counter
22930CMP R2,#&F
22940BEQ check_row
22950
22960;BIC R1,R1,#&80
22970LDRB R0,[R0,R1]
22980;EOR R0,R0,R1,LSR#7 ; ************
22990;EOR R0,R0,#1
23000;CMP R0,#0 : ;MOVEQ R1,#0
23010ORR R0,R1,R0,LSL#7
23020;MOV R0,R1,LSL#7
23030;MOV R0,R1
23040;ADD R0,R1,R1,LSL#7
23050
23060;MOV R0,#&81
23070;MOV R2,#&FF
23080;SWI "OS_Byte"
23090;CMP R0,#98 ; space
23100;CMP R1,#&FF
23110;MOVEQ R0,#&80
23120;MOVNE R0,#0
23130STRB R0,[R12,#&4F]
23140STRB R0,[R12,#&41]
23150MOV PC,R14
23160
23170.column_counter
23180EQUD 0
23190.key_write_ena
23200EQUD 0
23210
23220.disable_column_counter
23230STRB R2,column_counter
23240.check_row
23250AND R1,R1,#%00001111
23260MOV R13,#0
23270;SWI "6502_Getkeyaddr"
23280LDR R0,[mem,#key_addr]
23290LDRB R2,[R0] ; shift pressed?
23300CMP R2,#0
23310ADDNE R0,R0,#256
23320
23330.row_loop
23340LDRB R2,[R0,R1]
23350ORR R13,R13,R2
23360ADD R1,R1,#%10000
23370TST R1,#%1110000
23380BNE row_loop
23390ANDS R12,R13,#%1
23400LDRNEB R13,[mem,#ifr]
23410ORRNE R13,R13,R12
23420STRNEB R13,[mem,#ifr]
23430SUB R0,mem,#512 ; sheila
23440LDRB R1,[R0,#&4F]
23450BIC R1,R1,#&80
23460ORR R1,R1,R12,LSL#7
23470STRB R1,[R0,#&4F]
23480STRB R1,[R0,#&41]
23490MOV PC,R14
23500
23510.interrupt_flags
23520LDRB R2,[mem,#ifr]
23530BIC R2,R2,R0
23540STRB R2,[mem,#ifr]
23550MOV PC,R14
23560
23570
23580.interrupt_enable
23590LDRB R1,[mem,#ier]
23600TST R0,#&80
23610BICEQ R1,R1,R0
23620ORRNE R1,R1,R0
23630ORR R1,R1,#&80 ; &81
23640STRB R1,[mem,#ier]
23650;TST time,#%1
23660;SUBNE time,time,#1
23670MOV PC,R14
23680
23690.interrupt_flags2
23700LDRB R2,[mem,#ifr2]
23710BIC R2,R2,R0
23720STRB R2,[mem,#ifr2]
23730MOV PC,R14
23740
23750
23760.interrupt_enable2
23770LDRB R1,[mem,#ier2]
23780TST R0,#&80
23790BICEQ R1,R1,R0
23800ORRNE R1,R1,R0
23810ORR R1,R1,#&80 ; &81
23820STRB R1,[mem,#ier2]
23830MOV PC,R14
23840
23850.flash
23860;LDRB R1,elite
23870;CMP R1,#0
23880;BNE skip_fe20
23890TST F,#1 << 8 ; patch on?
23900BNE skip_fe20
23910LDRB R12,[mem,#fe20]
23920AND R1,R12,#%11100
23930AND R2,R0, #%11100
23940CMP R1,R2
23950MOVNE R2,#1
23960STRNEB R2,[mem,#tamper]
23970
23980AND R1,R12,#%11100000
23990AND R2,R0, #%11100000
24000CMP R1,R2
24010MOVNE R2,#1
24020STRNEB R2,[mem,#cursor_tamper]
24030
24040.skip_fe20
24050LDRB R12,[mem,#fe20]
24060STRB R0,[mem,#fe20]
24070TST R0,#%1
24080MOVEQ R0,#9
24090MOVNE R0,#10
24100MOV R1,#0
24110SWI "OS_Byte"
24120B poke_updatepixelV ; includes MOV PC,R14
24130;MOV PC,R14
24140
24150;.fe20
24160;EQUD 0
24170
24180;.crt_regs
24190;EQUD 0
24200;EQUD 0
24210;EQUD 0
24220;EQUD 0
24230;EQUD 0
24240
24250; include the sound code here contained in the Sound library
24260FNsound_latch
24270
24280
24290FNscreen
24300
24310]
24320IF HWScroll THEN [OPTp:FNhardwarescroll:]
24330[OPTp
24340
24350
24360.FFpage
24370;SUB time,time,#1
24380MOV PC,R14
24390
24400.update_pal
24410LDRB R1,[mem,#Palette]
24420CMP R1,#0
24430MOVNE PC,R14
24440.force_update_pal
24450STR R14,[mem,#Palette+4]
24460SUB R13,mem,#-pal_regs
24470LDRB R0,[R13,#0]
24480BL do_pal
24490LDRB R0,[R13,#1]
24500BL do_pal
24510LDRB R0,[R13,#2]
24520BL do_pal
24530LDRB R0,[R13,#3]
24540BL do_pal
24550LDRB R0,[R13,#4]
24560BL do_pal
24570LDRB R0,[R13,#5]
24580BL do_pal
24590LDRB R0,[R13,#6]
24600BL do_pal
24610LDRB R0,[R13,#7]
24620BL do_pal
24630LDRB R0,[R13,#8]
24640BL do_pal
24650LDRB R0,[R13,#9]
24660BL do_pal
24670LDRB R0,[R13,#10]
24680BL do_pal
24690LDRB R0,[R13,#11]
24700BL do_pal
24710LDRB R0,[R13,#12]
24720BL do_pal
24730LDRB R0,[R13,#13]
24740BL do_pal
24750LDRB R0,[R13,#14]
24760BL do_pal
24770LDRB R0,[R13,#15]
24780BL do_pal
24790MOV R14,#0:STRB R14,[mem,#pal_tamper]
24800LDR PC,[mem,#Palette+4]
24810
24820
24830.palette
24840SUB R12,mem,#-pal_regs
24850STRB R0,[R12,R0,LSR#4]
24860
24870LDRB R1,[mem,#Palette]
24880CMP R1,#0
24890MOVNE PC,R14
24900
24910MOV R1,#255:STRB R1,[mem,#pal_tamper]
24920MOV PC,R14
24930
24940.do_pal
24950LDRB R1,[mem,#fe20]
24960TST R1,#%10
24970MOVNE PC,R14 ; mode 7
24980AND R1,R1,#%11100
24990CMP R1,#%11100 : BEQ twocolpal
25000CMP R1,#%01000 : BEQ twocolpal
25010CMP R1,#%11000 : BEQ fourcolpal
25020CMP R1,#%00100 : BEQ fourcolpal
25030
25040
25050.sixteencolpal
25060AND R1,R0,#&F
25070MOV R0,R0,LSR#4
25080EOR R1,R1,#7
25090
25100;CMP R0,#0 ; for Exile
25110;SWINE ETC ETC
25120
25130SWI &100+19
25140SWI "OS_WriteC"
25150MOV R0,R1
25160SWI "OS_WriteC"
25170SWI &100
25180SWI &100
25190SWI &100
25200MOV PC,R14
25210
25220.twocolpal
25230AND R1,R0,#&F
25240MOV R0,R0,LSR#7
25250EOR R1,R1,#7
25260CMP R0,#1
25270MOVEQ R0,#3 ; mode 4 fix
25280SWI &100+19
25290SWI "OS_WriteC"
25300MOV R0,R1
25310SWI "OS_WriteC"
25320SWI &100
25330SWI &100
25340SWI &100
25350MOV PC,R14
25360
25370.fourcolpal
25380AND R1,R0,#&F
25390AND R0,R0, #%10100000
25400TST R0, #%10000000
25410ORRNE R0,R0,#%01000000
25420BICNE R0,R0,#%10000000
25430MOV R0,R0,LSR#5
25440EOR R1,R1,#7
25450SWI &100+19
25460SWI "OS_WriteC"
25470MOV R0,R1
25480SWI "OS_WriteC"
25490SWI &100
25500SWI &100
25510SWI &100
25520MOV PC,R14
25530
25540.osbput
25550MOV R0,A,LSR#24
25560MOV R1,Y,LSR#24
25570SWI "XOS_BPut"
25580BVS swi_error
25590B opcode(&60) ; rts
25600
25610.osbget
25620MOV R0,A,LSR#24
25630MOV R1,Y,LSR#24
25640SWI "XOS_BGet"
25650BVS swi_error
25660MOV A,R0,LSL#24
25670FNsetupC
25680B opcode(&60) ; rts
25690
25700.swi_error
25710ADD mem,mem,#&100
25720ADD mem,mem,#&002
25730MOV R1,#0 ; BRK
25740STRB R1,[mem,#-2]
25750LDRB R1,[R0] ; error no
25760STRB R1,[mem,#-1]
25770ADD R0,R0,#4
25780MOV R14,#0
25790
25800.swi_err_loop
25810LDRB R13,[R0,R14]
25820CMP R13,#0
25830;MOV R13,#ASC"A"
25840STRB R13,[mem,R14]
25850ADD R14,R14,#1
25860MOVEQ R14,#255
25870CMP R14,#253
25880BLE swi_err_loop
25890
25900MOV zpc,#&100 << 16
25910SUB mem,mem,#&100
25920SUB mem,mem,#&002
25930FNfetch2
25940
25950.return_ROMSEL
25960LDRB R0,[mem,#rom]
25970MOV PC,R14
25980
25990.return_ACCCON
26000LDRB R0,[mem,#ACCCON]
26010MOV PC,R14
26020
26030
26040
26050.strb_rom_ret
26060
26070.sheila
26080SUBS R2,R1,#&FE00
26090MOVLT PC,R14
26100SUBS R2,R2,#&100
26110MOVGE PC,R14
26120;BGE FFpage
26130
26140TST time,#%1
26150SUBNE time,time,#1
26160SUBEQ time,time,#2
26170
26180;STRB R0,[mem,R1]
26190SUB R2,mem,#&10000:STRB R0,[R2,R1]
26200
26210AND R2,R1,#&FF
26220;ADR R1,sheila_writetab
26230LDR PC,[PC,R2,LSL#2]
26240EQUD 0 ; padding for pipeline
26250.sheila_writetab
26260; 0-F
26270EQUD dummy
26280EQUD crt
26290EQUD dummy
26300EQUD crt
26310EQUD dummy
26320EQUD crt
26330EQUD dummy
26340EQUD crt
26350EQUD writeFE08
26360EQUD writeFE09
26370FNequd(6,dummy)
26380; 10-17
26390EQUD writeFE10
26400FNequd(7,dummy)
26410; 18-1F
26420EQUD write_ADC_status
26430FNequd(7,dummy)
26440; 20-2F
26450EQUD flash
26460EQUD palette
26470FNequd(14,dummy)
26480; 30-3F
26490FNequd(4,romsel)
26500EQUD acccon
26510FNequd(11,romsel)
26520; 40-4F
26530EQUD latch
26540EQUD regB_41
26550EQUD dummy
26560EQUD dummy
26570EQUD writeT1low_latch
26580EQUD writeT1high_count
26590EQUD writeT1low_latch
26600EQUD writeT1high_latch
26610EQUD writeT2low_latch
26620EQUD writeT2high_count
26630EQUD dummy
26640EQUD dummy
26650EQUD dummy
26660EQUD interrupt_flags
26670EQUD interrupt_enable
26680EQUD regB_4F
26690; 50-5F
26700EQUD latch
26710EQUD regB_41
26720EQUD dummy
26730EQUD dummy
26740EQUD writeT1low_latch
26750EQUD writeT1high_count
26760EQUD writeT1low_latch
26770EQUD writeT1high_latch
26780EQUD writeT2low_latch
26790EQUD writeT2high_count
26800EQUD dummy
26810EQUD dummy
26820EQUD dummy
26830EQUD interrupt_flags
26840EQUD interrupt_enable
26850EQUD regB_4F
26860; 60-7F
26870]
26880IF IO_Podule% THEN
26890[OPTp
26900FNequd(&20,IOpodule_Write)
26910]
26920ELSE
26930[OPTp
26940EQUD dummy
26950EQUD printer_write
26960EQUD dummy
26970EQUD dummy
26980EQUD writeT3low_latch
26990EQUD writeT3high_count
27000EQUD writeT3low_latch
27010EQUD writeT3high_latch
27020EQUD writeT4low_latch
27030EQUD writeT4high_count
27040EQUD dummy
27050EQUD writeACR2
27060EQUD dummy
27070EQUD interrupt_flags2
27080EQUD interrupt_enable2
27090EQUD printer_write
27100
27110EQUD dummy
27120EQUD printer_write
27130EQUD dummy
27140EQUD dummy
27150EQUD writeT3low_latch
27160EQUD writeT3high_count
27170EQUD writeT3low_latch
27180EQUD writeT3high_latch
27190EQUD writeT4low_latch
27200EQUD writeT4high_count
27210EQUD dummy
27220EQUD dummy
27230EQUD dummy
27240EQUD interrupt_flags2
27250EQUD interrupt_enable2
27260EQUD printer_write
27270]
27280ENDIF
27290
27300[OPTp
27310; 80-BF
27320FNequd(&40,dummy)
27330; C0-CF
27340EQUD write_ADC_status
27350FNequd(15,dummy)
27360; D0-FF
27370FNequd(&30,dummy)
27380
27390.ldrb_FFpage
27400;SUB time,time,#1
27410MOV PC,R14
27420
27430.ldrb8000 ; greater than 8000
27440
27450CMP R1,#&FE00
27460BHS ldrb_sheila
27470
27480LDRB R0,[mem,R1]
27490MOV PC,R14
27500
27510
27520;MOV R1,R1,LSR#16
27530]
27540IF master THEN
27550[OPTp
27560.ldrb16_8000 ; greater than 8000
27570
27580CMP R1,#&FE00 << 16
27590BHS ldrb16_sheila
27600
27610LDRB R0,[mem,R1,LSR#16]
27620MOV PC,R14
27630
27640.ldrb16_screen
27650CMP R1,#&8000 << 16
27660BHS ldrb16_8000
27670
27680LDRB R12,[mem,#ACCCON]
27690
27700CMP zpc,#&C000 << 16
27710MOVLT R13,R12,LSR#1
27720MOVGE R13,R12
27730CMP zpc,#&E000 << 16
27740MOVGE R13,R12,LSR#1 ; now bit 1 of R13 is what
27750 ; we must look at
27760
27770TST R13,#%10
27780SUBNE R13,mem,#(&3000+&10000) ; shadow screen memory
27790;MOVEQ R13,mem
27800LDRNEB R0,[R13,R1,LSR#16]
27810LDREQB R0,[mem,R1,LSR#16]
27820MOV PC,R14
27830]
27840ELSE
27850[OPTp
27860.ldrb16_screen
27870CMP R1,#&FE00 << 16
27880BHS ldrb16_sheila
27890
27900LDRB R0,[mem,R1,LSR#16]
27910MOV PC,R14
27920]
27930ENDIF
27940
27950IF master THEN
27960[OPTp
27970
27980.ldrb_screen
27990.ldrb3000 ; greater than 3000
28000
28010CMP R1,#&8000
28020BHS ldrb8000
28030
28040LDRB R12,[mem,#ACCCON]
28050
28060CMP zpc,#&C000 << 16
28070MOVLT R13,R12,LSR#1
28080MOVGE R13,R12
28090CMP zpc,#&E000 << 16
28100MOVGE R13,R12,LSR#1 ; now bit 1 of R13 is what
28110 ; we must look at
28120
28130TST R13,#%10
28140SUBNE R13,mem,#(&3000+&10000) ; shadow screen memory
28150;MOVEQ R13,mem
28160LDRNEB R0,[R13,R1]
28170LDREQB R0,[mem,R1]
28180MOV PC,R14
28190]
28200ELSE
28210[OPTp
28220.ldrb_screen
28230.ldrb3000 ; greater than 3000
28240CMP R1,#&FE00
28250BHS ldrb_sheila
28260LDRB R0,[mem,R1]
28270MOV PC,R14
28280]
28290ENDIF
28300
28310[OPTp
28320
28330.ldrb16_sheila
28340MOV R12,R1,LSR#16
28350B ldrb_sheila2
28360
28370.ldrb_sheila
28380MOV R12,R1
28390
28400.ldrb_sheila2
28410LDRB R0,[mem,R12]
28420
28430SUBS R2,R12,#&FE00
28440MOVLT PC,R14
28450SUBS R2,R2,#&100
28460BGE ldrb_FFpage
28470
28480SUB R2,mem,#&10000:LDRB R0,[R2,R12]
28490
28500SUB time,time,#1
28510
28520AND R2,R12,#&FF
28530;ADR R1,sheila_readtab
28540LDR PC,[PC,R2,LSL#2]
28550EQUD 0 ; padding for pipeline
28560.sheila_readtab
28570; 0-F
28580FNequd(8,dummy)
28590EQUD readFE08
28600EQUD readFE09
28610FNequd(6,dummy)
28620; 10-2F
28630EQUD readFE10
28640FNequd(&1F,dummy)
28650; 30-3F
28660FNequd(4,return_ROMSEL)
28670FNequd(4,return_ACCCON)
28680FNequd(8,dummy)
28690; 40-4F
28700EQUD ldrb40
28710EQUD ldrb41
28720EQUD dummy
28730EQUD dummy
28740EQUD readT1low_count
28750EQUD readT1high_count
28760EQUD readT1low_latch
28770EQUD readT1high_latch
28780EQUD readT2low_count
28790EQUD readT2high_count
28800EQUD dummy
28810EQUD dummy
28820EQUD dummy
28830EQUD read_ifr
28840EQUD read_ier
28850EQUD ldrb4F
28860; 50-5F
28870EQUD ldrb40
28880EQUD ldrb41
28890EQUD dummy
28900EQUD dummy
28910EQUD readT1low_count
28920EQUD readT1high_count
28930EQUD readT1low_latch
28940EQUD readT1high_latch
28950EQUD readT2low_count
28960EQUD readT2high_count
28970EQUD dummy
28980EQUD dummy
28990EQUD dummy
29000EQUD read_ifr
29010EQUD read_ier
29020EQUD ldrb4F
29030; 60-6F
29040]
29050IF IO_Podule% THEN
29060[OPTp
29070FNequd(&20,IOpodule_Read)
29080]
29090ELSE
29100[OPTp
29110EQUD dummy
29120EQUD dummy
29130EQUD dummy
29140EQUD dummy
29150EQUD readT3low_count
29160EQUD readT3high_count
29170EQUD readT3low_latch
29180EQUD readT3high_latch
29190EQUD readT4low_count
29200EQUD readT4high_count
29210EQUD dummy
29220EQUD dummy
29230EQUD dummy
29240EQUD read_ifr2
29250EQUD read_ier2
29260EQUD dummy
29270
29280EQUD dummy
29290EQUD dummy
29300EQUD dummy
29310EQUD dummy
29320EQUD readT3low_count
29330EQUD readT3high_count
29340EQUD readT3low_latch
29350EQUD readT3high_latch
29360EQUD readT4low_count
29370EQUD readT4high_count
29380EQUD dummy
29390EQUD dummy
29400EQUD dummy
29410EQUD read_ifr2
29420EQUD read_ier2
29430EQUD dummy
29440]
29450ENDIF
29460
29470[OPTp
29480; 80-FF
29490FNequd(&80,dummy)
29500
29510FNsound_misc
29520
29530.opcode7
29540SWI &100+ASC"O"
29550SWI &100+ASC"p"
29560SWI &100+ASC"7"
29570SWI &100+ASC" "
29580FNprint(zpc)
29590B opcode7
29600
29610FNalign16 ; fit into cache better?
29620
29630FNopcodes
29640
29650.patch_screen
29660MOV PC,R14
29670.patch_pixel
29680MOV PC,R14
29690
29700.end
29710]
29720NEXT
29730OSCLI"Load <6502Em$Dir>.SRC.revtable "+STR$~(code+mode0tab)
29740OSCLI"Load <6502Em$Dir>.SRC.mode1tab "+STR$~(code+mode1tab)
29750OSCLI"Load <6502Em$Dir>.SRC.Hmode2tab "+STR$~(code+mode2tab)
29760OSCLI"Load <6502Em$Dir>.SRC.Hmode4tab "+STR$~(code+mode4tab)
29770OSCLI"Load <6502Em$Dir>.SRC.Hmode5tab "+STR$~(code+mode5tab)
29780
29790ENDPROC
29800
29810DE
29820DEFF
29830
29840
29850DEFFNldrb2(R,S)
29860IF R<>0 OR S<>1 THEN STOP
29870IF master THEN
29880[OPTp
29890;LDRB R,[mem,S]
29900;CMP S,#&FE00
29910;BLHS ldrb_sheila
29920CMP S,#&3000
29930LDRLOB R,[mem,S]
29940BLHS ldrb_screen
29950]
29960ELSE
29970[OPTp
29980LDRB R,[mem,S]
29990CMP S,#&FE00
30000BLHS ldrb_sheila
30010]
30020ENDIF
30030=""
30040
30050DEFFNldrb16(R,S)
30060IF R<>0 OR S<>1 THEN STOP
30070IF master THEN
30080[OPTp
30090;LDRB R,[mem,S,LSR#16]
30100;CMP S,#&FE00 << 16
30110;BLHS ldrb16_sheila
30120CMP S,#&3000 << 16
30130LDRLOB R,[mem,S,LSR#16]
30140BLHS ldrb16_screen
30150]
30160ELSE
30170[OPTp
30180LDRB R,[mem,S,LSR#16]
30190CMP S,#&FE00 << 16
30200BLHS ldrb16_sheila
30210]
30220ENDIF
30230=""
30240
30250DEFFNstrb(R,S)
30260IF R<>0 OR S<>1 THEN ERROR
30270[OPTp
30280CMP S,F,LSR#16 ; wrap_addr
30290;CMP S,#&3000
30300STRLTB R,[mem,S]
30310BLGE strb
30320]
30330=""
30340
30350DEFFNstrb16(R,S)
30360IF R<>0 OR S<>1 THEN ERROR
30370[OPTp
30380;CMP S,#&C000 << 16
30390;STRLOB R,[mem,S,LSR#16]
30400MOV S,S,LSR#16
30410CMP S,F,LSR#16 ; wrap_addr
30420;CMP S,#&3000
30430STRLTB R,[mem,S]
30440BLGE strb ; 16
30450]
30460=""
30470
30480DEFFNshowregs
30490[OPTp
30500FNprint(zpc)
30510FNprint(A)
30520FNprint(X)
30530FNprint(Y)
30540FNprint(SP)
30550FNprint(F)
30560ADD R12,mem,#&DF00
30570LDRB R12,[R12,#&DA]
30580MOV R12,R12,LSL#24
30590FNprint2(12)
30600SWI &10A
30610;SWI "OS_NewLine"
30620]
30630=""
30640
30650DEFFNprint(R)
30660CASE R OF
30670WHEN zpc : A$=FNprint4(R)
30680WHEN F : [OPTp:MOV R2,F,LSL#24:FNprint2(2):]
30690OTHERWISE
30700A$=FNprint2(R)
30710ENDCASE
30720=""
30730
30740WHEN A : A$=FNprint2(R)
30750WHEN X : A$=FNprint2(R)
30760WHEN Y : A$=FNprint2(R)
30770WHEN SP : [OPTp:SWI &100+ASC"1":FNprint2(SP):]
30780WHEN F : A$=FNprintflags
30790ENDCASE
30800=""
30810
30820DEFFNprintflags
30830[OPTp
30840TST F,#%1<<7 : SWIEQ &100+ASC"n" : SWINE &100+ASC"N"
30850TST F,#%1<<6 : SWIEQ &100+ASC"v" : SWINE &100+ASC"V"
30860TST F,#%1<<5 : SWIEQ &100+ASC"0" : SWINE &100+ASC"1"
30870TST F,#%1<<4 : SWIEQ &100+ASC"b" : SWINE &100+ASC"B"
30880TST F,#%1<<3 : SWIEQ &100+ASC"d" : SWINE &100+ASC"D"
30890TST F,#%1<<2 : SWIEQ &100+ASC"i" : SWINE &100+ASC"I"
30900TST F,#%1<<1 : SWIEQ &100+ASC"z" : SWINE &100+ASC"Z"
30910TST F,#%1<<0 : SWIEQ &100+ASC"c" : SWINE &100+ASC"C"
30920SWI &120
30930]
30940=""
30950
30960DEFFNprint2(R)
30970LOCALI%
30980[OPTp
30990MOV R1,R
31000]
31010FORI%=0 TO 1
31020[OPT p
31030MOV R1,R1,ROR#28
31040AND R0,R1,#&F
31050CMP R0,#10
31060ADDGE R0,R0,#7
31070ADD R0,R0,#48
31080SWI "OS_WriteC"
31090]
31100NEXT
31110[OPTp
31120SWI &120
31130]
31140=""
31150
31160DEFFNprint4(R)
31170LOCALI%
31180[OPTp
31190MOV R1,R
31200]
31210FORI%=0 TO 3
31220[OPT p
31230MOV R1,R1,ROR#28
31240AND R0,R1,#&F
31250CMP R0,#10
31260ADDGE R0,R0,#7
31270ADD R0,R0,#48
31280SWI "OS_WriteC"
31290]
31300NEXT
31310[OPTp
31320SWI &120
31330]
31340=""
31350
31360DEFFNprint32(R)
31370LOCALI%
31380[OPTp
31390MOV R1,R
31400]
31410FORI%=0 TO 31
31420[OPT p
31430MOV R1,R1,ROR#28
31440AND R0,R1,#&F
31450CMP R0,#10
31460ADDGE R0,R0,#7
31470ADD R0,R0,#48
31480SWI "OS_WriteC"
31490]
31500NEXT
31510[OPTp
31520SWI &120
31530]
31540=""
31550
31560DEFFNprints(A$)
31570[OPTp
31580SWI "OS_WriteS"
31590EQUS A$
31600EQUB 10
31610EQUB 13
31620EQUB 0
31630ALIGN
31640]
31650=""
31660
31670DEFFNundoc(A%)
31680IF opcode%<>A% THEN STOP
31690[OPTp
31700;TST F,#%1000
31710;SWIEQ &100+ASC"d"
31720;SWINE &100+ASC"D"
31730
31740;SWI &100+ASC(LEFT$(RIGHT$("0"+STR$~A%,2),1))
31750;SWI &100+ASC(RIGHT$(STR$~A%,1))
31760;SWI &100+ASC" "
31770;FNprint(zpc)
31780;SWI &100+ASC" ":;SWI &100+ASC" "
31790
31800;MOV R0,#15 : ;SWI "OS_Byte"
31810;SWI 4
31820]
31830=""
31840
31850DEFFNequd(A%,B%)
31860LOCALI%
31870FORI%=1 TO A%
31880[OPTp
31890EQUD B%
31900]
31910NEXT
31920=""
31930
31940DEFFNdo_interrupt
31950[OPTp
31960MOV R0,zpc,LSR#24
31970FNpush(0)
31980MOV R0,zpc,LSR#16
31990FNpush(0)
32000BIC F,F,#%10000 ; clear BRK flag
32010FNpush(F)
32020ORR F,F,#%100 ; !!!!!!
32030MOV R0,#&FF00 : ADD R0,R0,#&FE
32040LDR zpc,[mem,R0]
32050MOV zpc,zpc,LSL#16
32060]
32070=""
32080
32090DEFFNdivmod(A,B,C,D,E)
32100div%+=1
32110[OPTp
32120MOV C,#1
32130MOV D,#0
32140MOV E,B
32150.divloop1(div%)
32160MOV B,B,LSL#1
32170MOV C,C,LSL#1
32180CMP B,A
32190BLO divloop1(div%)
32200
32210.divloop2(div%)
32220CMP B,A : BLS divjump(div%)
32230CMP B,E : BLS divjump(div%)
32240MOV B,B,LSR#1
32250MOV C,C,LSR#1
32260B divloop2(div%)
32270.divjump(div%)
32280CMP B,A
32290SUBLS A,A,B
32300ADDLS D,D,C
32310CMP B,E
32320BHI divloop2(div%)
32330]
32340=""
32350
32360DEFFNshadow
32370IF master THEN
32380[OPTp
32390LDRB R2,[mem,#ACCCON]
32400;EOR R2,R2,R2,LSR#2
32410TST R2,#%1
32420SUBNE R13,mem,#&13000
32430MOVEQ R13,mem
32440]
32450ELSE
32460[OPTp
32470MOV R13,mem
32480]
32490ENDIF
32500=""
32510DEFPROCclearmem(S%,E%)
32520P%=buffer
32530[OPT2
32540EQUD S% ; memory
32550EQUD E% ; memory+&8000
32560.clear
32570MOV R0,#0
32580LDR R1,buffer
32590LDR R2,buffer+4
32600.loop
32610STR R0,[R1],#4
32620CMP R1,R2
32630BNE loop
32640MOV PC,R14
32650]
32660CALL clear
32670ENDPROC
32680
32690DEFFNfetch2
32700[OPTp
32710LDRB R2,[mem,zpc,LSR#16]
32720ADD PC,table,R2,LSL#8
32730]
32740=""
32750
32760DEFFNfetch3(N%,T%)
32770IF N%<>0 THEN [OPTp:ADD zpc,zpc,#N% << 16:]
32780[OPTp
32790FNshowregs2
32800SUBS time,time,#T%
32810LDRPLB R2,[mem,zpc,LSR#16]
32820ADDPL PC,table,R2,LSL#8
32830B fetch2
32840]
32850=""
32860
32870DEFFNfetch(N%,T%)
32880IF N%<>0 THEN [OPTp:ADD zpc,zpc,#N% << 16:]
32890[OPTp
32900FNshowregs2
32910SUBS time,time,#T%
32920LDRPLB R2,[mem,zpc,LSR#16]
32930ADDPL PC,table,R2,LSL#8
32940B fetch2
32950]
32960opcode%+=1
32970IF bcd_loop%=0 THEN
32980IF opcode(opcode%-1)=0 THEN STOP
32990IF opcode(opcode%)<>0 AND p=0 THEN STOP
33000IF P%-opcode(0)>opcode%*4*64 THEN PRINT~opcode%
33010P%=opcode(0)+opcode%*4*64
33020O%=code+P%
33030ELSE
33040P%=bcd(0)+opcode%*4*64
33050O%=code+P%
33060ENDIF
33070=""
33080DEFFNbcd(A%) :
33090IF P%>opcode(0)+(A%+256)*4*64 THEN STOP
33100P%=opcode(0)+(A%+256)*4*64 : O%=code+P% : =""
33110
33120DEFFNalign16
33130WHILE (P% AND 15)<>0
33140P%+=1 : O%+=1
33150ENDWHILE
33160=""
33170DEF PROCerror
33180REPORT:PRINT " at line ";ERL
33190END
33200
33210DEFFNshowregs2
33220[OPTp
33230;BL show_regs
33240]
33250=""
� > 6502Em
%�INPUT"Hardware scroll ";HWScroll
&�IF HWScroll<>0 THEN HWScroll=TRUE
(HWScroll=�
2master=�
<;*RMENSURE 6502Support 0.00 RMRun <6502Em$Res>.65Support
F� � �error
P
Z� V2. (bbc)
d
nIO_Podule%=�
x
�9� opcode(&100), bcd(&100), code 500*1024, buffer 1000
�
� l%(100)
�+� divloop1(10),divloop2(10),divjump(10)
�
div%=0
� ț "<6502Em$Dir>.Src.Sound6"
�!ț "<6502Em$Dir>.Src.Opcodes"
� ț "<6502Em$Dir>.Src.Screen"
�"ț "<6502Em$Dir>.Src.HWScroll"
�
�electron%=�
�master=�
�
�assemble
�
�(end-start)/1024
7� "Save <6502Em$Dir>.Code "+�~code+" "+�~(end+code)
&� "SetType <6502Em$Dir>.Code Data"
"
,master=�
6
�assemble
@�(end-start)/1024
J8� "Save <6502Em$Dir>.CodeM "+�~code+" "+�~(end+code)
T'� "SetType <6502Em$Dir>.CodeM Data"
^
h�
r
|0�"LOAD <6502Em$Dir>.OS1,2 "+�~(memory+&C000)
�2�"LOAD <6502Em$Dir>.BASICII "+�~(memory+&8000)
�
�� 12
�� init+code
�
�"BOO"
�
�!pc_store=&D9CD << 16
�
�D%=memory : � R3
�� start+code
�
��
���assemble
!�clearmem(code,code+200*1024)
R=1000 : S=1000 : T=1000
&A=4
0X=5
:Y=6
DF=7
NSP=8
X mem=3
b
time=9
l
zpc=10
vtable=11
�
�
a=-&100+0
�
x=-&100+4
�
y=-&100+8
�f=-&100+12
�sp=-&100+16
�pc_store=-&100+20
�T1mode=-&100+24
�T2mode=-&100+25
�T3mode=-&100+26
�T4mode=-&100+27
�T1=-&100+28
�T1R=-&100+32
T2=-&100+36
T2R=-&100+40
T3=-&100+44
T3R=-&100+48
*T4=-&100+52
4T4R=-&100+56
>screen=-&100+60
HscreenR=-&100+64
Rmin=-&100+68
\sound_timer=-&100+72
fifr=-&100+76
pier=-&100+77
zifr2=-&100+78
�ier2=-&100+79
�arc_screenstart=-&100+80
�tamper=-&100+84
�cursor_tamper=-&100+88
�ROMSEL_ON=-&100+92
�rom=-&100+96
�ROMRAM=-&100+100
�fe20=-&100+116
�tape_handle=-&100+117
�crt_regs=-&100+120
�scratch=-&100+140
�pal_regs=-&100+148
�Palette=-&100+164
ACCCON=-&100+172
patch_on=-&100+176
pal_tamper=-&100+177
$lastmode=-&100+178
.fe10=-&100+179
8tape_count=-&100+180
Bkey_addr=-&100+184
L screenstart_tamper=-&100+188
V"screenstart_previous=-&100+192
`speedR=-&100+196
j
t(enD=-&100+200 : � don't go past this
~
��p=4 � 6 � 2
�
div%=0
�O%=code
�l%=0
�P%=0
�
opcode%=0
� [OPTp
�).Oa EQUD 0
�).Ox EQUD 0
�).Oy EQUD 0
�).Of EQUD 0
�).Osp EQUD 0
).Opc_store EQUD 0
,.start_offset EQUD start
(.trace EQUD 0
(.trace2 EQUD 0
(+.init_addr EQUD init
27.crt_addr EQUD 0 ; was crt_regs
<1.T1_addr EQUD 0 ; was T1
F..ifr_addr EQUD 0 ; ifr
P5.column_counter_addr EQUD column_counter
Z1.ROMSEL_addr EQUD 0 ; ROMSEL
d2.Palette_addr EQUD 0 ; Palette
n5.speed_addr EQUD screen_count+4
x0.elite_addr EQUD 0 ; elite
�>.opco_addr EQUD opcode(0) ; opcodetable
�-.bcd_addr EQUD bcd(0)
�6.sheila_writetab_addr EQUD sheila_writetab
�5.sheila_readtab_addr EQUD sheila_readtab
�7.sound_vectors_addr EQUD sound_buffs_addr
�3.patch_addr EQUD patch_screen
�
�0.init ; only called once, before code called
�ADR R0,0
�;LDR R1,opco_addr
�;ADD R1,R1,R0
�;LDR R2,bcd_addr
�;ADD R2,R2,R0
LDR R5,sheila_writetab_addr
ADD R5,R5,R0
LDR R6,sheila_readtab_addr
"ADD R6,R6,R0
,MOV R3,#255
6.init_loop
@;LDR R4,[R1,R3,LSL#2]
J;ADD R4,R4,R0
T;STR R4,[R1,R3,LSL#2]
^;LDR R4,[R2,R3,LSL#2]
h;ADD R4,R4,R0
r;STR R4,[R2,R3,LSL#2]
|LDR R4,[R5,R3,LSL#2]
�ADD R4,R4,R0
�STR R4,[R5,R3,LSL#2]
�LDR R4,[R6,R3,LSL#2]
�ADD R4,R4,R0
�STR R4,[R6,R3,LSL#2]
�SUBS R3,R3,#1
�BPL init_loop
�MOV PC,R14
�
�
.start
�STMFD R13!,{R1-R12,R14}
�STR R13,return_addr
�STR R0,roms_addr
;LDR R0,crt_addr
;ADR R1,0
;ADD R0,R0,R1
&;SWI "6502_Init"
0
:BL blank_cursor
D
N"MOV R0,#&9C00 : ADD R0,R0,#&40
XSTR R0,[mem,#screenR]
b
lSWI "6502_Getkeyaddr"
vSTR R0,[mem,#key_addr]
�
�ADR R0,block1
�ADD R1,R0,#8
�SWI "OS_ReadVduVariables"
�!LDR R9,[R1] ; screenstart
�!STR R9,[mem,#arc_screenstart]
�
MOV R9,#1
�STRB R9,[mem,#tamper]
�STRB R9,[mem,#pal_tamper]
� STRB R9,[mem,#cursor_tamper]
�
�LDR time,[mem,#min]
�LDR A,[mem,#a]
LDR X,[mem,#x]
LDR Y,[mem,#y]
"LDR SP,[mem,#sp] : �R SP,SP,#1
LDR F,[mem,#f]
*LDR zpc,[mem,#pc_store]
4
>BL recalc_wrap
HLDRB R0,[mem,#patch_on]
R� R0,R0,#%11111
\BIC F,F,#&FF00
f�R F,F,R0,LSL#8
p
z;MOV time,#0
�
�LDRB R0,fe08_read
�BIC R0,R0,#&81
�STRB R0,fe08_read
�
�ADR R0,0
�TST F,#%1000
�LDREQ table,opco_addr
�LDRNE table,bcd_addr
�ADD table,table,R0
�;SWI "6502_ReInit"
�;SWI "6502_UpdateScreen
�BL poke_updatepixelV
BL updatescreen
B fetch2
$.reset_bcdflag
.ADR R1,0
8TST F,#%1000
BLDREQ table,opco_addr
LLDRNE table,bcd_addr
VADD table,table,R1
`MOV PC,R14
j
t.block1
~EQUD 149 : EQUD -1
�.block2
�EQUD 0 : EQUD 0
�
�.screen_count
�
EQUD 0
�
EQUD 0
�
�
.reg_comp
�EQUD &FFEE << 16
�
�
.trace_on
�MOV R12,#1
STRB R12,trace
MOV PC,R14
.show_regs
(
2;SWI "6502_Checkkdata"
<LDR R0,[mem,#key_addr]
FLDRB R0,[R0,#-4]
P
Z
dCMP R0,#&1F ; Insert
n�Q R1,#1
xSTREQ R1,trace2
�
�LDRB R0,trace2
�
CMP R0,#1
�MOVNE PC,R14
�
�;LDR R0,reg_comp
�;CMP R0,zpc
�
;�Q R0,#1
�;STREQB R0,trace
�
�;ADD R12,mem,#&DF00
�;LDRB R12,[R12,#&DA]
�;CMP R12,#0
;�Q R12,#1
;STREQB R12,trace
";LDRB R0,trace
,;CMP R0,#1
6;MOVNE PC,14
@
J
�showregs
TMOV PC,R14
^
h
.read_ifr
rLDRB R0,[mem,#ifr]
|
�LDR R1,[mem,#min]
�SUB R1,R1,time
�LDR R12,[mem,#screen]
�SUB R12,R12,R1
�CMP R12,#10
��RLT R0,R0,#%10 ; vsync
�;
�;
�; CMP zpc,#&8000 << 16
�; �RLT R0,R0,#%10 ; vsync
�
�
�LDRB R1,[mem,#ier]
BIC R0,R0,#&80
�S R1,R1,R0
�RNE R0,R0,#&80
&
0MOV PC,R14
:
D
.read_ier
NLDRB R0,[mem,#ier]
X�R R0,R0,#&80
bMOV PC,R14
l
v.read_ifr2
�LDRB R0,[mem,#ifr2]
�LDRB R1,[mem,#ier2]
�BIC R0,R0,#&80
��S R1,R1,R0
��RNE R0,R0,#&80
�MOV PC,R14
�
�.read_ier2
�LDRB R0,[mem,#ier2]
��R R0,R0,#&80
�MOV PC,R14
�
�.ldrb41
SUB R12,mem,#512 ; sheila
LDRB R1,[R12,#&C] ; PCR
LDRB R2,[mem,#ifr]
*� R13,R1,#%1110
4TEQ R13, #%0010
>TEQNE R13, #%0110
HBICEQ R2,R2,#%11
RBICNE R2,R2,#%10
\STRB R2,[mem,#ifr]
f
pLDRB R0,[R12,#&4F]
zMOV PC,R14
�
�.ldrb4F
�
�SUB R12,mem,#512 ; sheila
�LDRB R0,[R12,#&4F]
�MOV PC,R14
�
�
�.readT4low_count
�LDRB R1,[mem,#ifr2]
�BIC R1,R1, #%00100000
�STRB R1,[mem,#ifr2]
�LDR R0,[mem,#T4]
LDR R1,[mem,#min]
SUB R0,R0,R1,LSL#15
ADD R0,R0,time,LSL#15
$TST R0,#1 << 15 ; ???
.SUBNE time,time,#1
8MOV R0,R0,LSR#16
B� R0,R0,#&FF
LMOV PC,R14
V
`.readT4high_count
jLDR R0,[mem,#T4]
tLDR R1,[mem,#min]
~SUB R0,R0,R1,LSL#15
�ADD R0,R0,time,LSL#15
�TST R0,#1 << 15 ; ???
�SUBNE time,time,#1
�MOV R0,R0,LSR#24
�MOV PC,R14
�
�.readT3low_count
�LDR R1,[mem,#ifr2]
�BIC R1,R1, #%1 << 6
�1STRB R1,[mem,#ifr2] ; clear T3 interrupt flag
�LDR R0,[mem,#T3]
�LDR R1,[mem,#min]
SUB R0,R0,R1,LSL#15
ADD R0,R0,time,LSL#15
TST R0,#1 << 15 ; ???
SUBNE time,time,#1
(MOV R0,R0,LSR#16
2� R0,R0,#&FF
<MOV PC,R14
F
P.readT3high_count
ZLDR R0,[mem,#T3]
dLDR R1,[mem,#min]
nSUB R0,R0,R1,LSL#15
xADD R0,R0,time,LSL#15
�TST R0,#1 << 15 ; ???
�SUBNE time,time,#1
�MOV R0,R0,LSR#24
�MOV PC,R14
�
�.readT3low_latch
�LDRB R0,[mem,#T3R+2]
�MOV PC,R14
�
�.readT3high_latch
�LDRB R0,[mem,#T3R+3]
�MOV PC,R14
�
.ACRtemp
EQUD 0
".writeACR2
,;MOV R0,#0
6;STRB R0,[mem,#T3mode]
@SUB R0,mem,#512
JLDRB R1,[R0,#&60]
T�R R1,R1,#&80
^STRB R1,[R0,#&60]
h;MOV R0,#1
r;STRB R0,ACRtemp
|MOV PC,R14
�
�.writeT3low_latch
�STRB R0,[mem,#T3R+2]
�MOV PC,R14
�
�.writeT3high_count
�STRB R0,[mem,#T3R+3]
�LDR R0,[mem,#T3R]
�ADD R0,R0,#2 << 16
�
�+CMP R0,time,LSL#15 ; fix Exile's speech
�
�BHI skip_T3adjust
LDRB R2,[mem,#ier2]
TST R2,#%01000000
&MOVNE time,R0,LSR#15
0
:.skip_T3adjust
DLDR R1,[mem,#min]
NADD R0,R0,R1,LSL#15
XSUB R0,R0,time,LSL#15
bSTR R0,[mem,#T3]
lLDRB R1,[mem,#ifr2]
vBIC R1,R1, #%1 << 6
�1STRB R1,[mem,#ifr2] ; clear T3 interrupt flag
�;SUB R0,R0,#&D
�SUB R0,mem,#512 ; sheila
�
�
�LDRB R1,[R0,#&6B]
�� R1,R1,#1<<7
��S R1,R1,#&C0
�LDREQB R1,[R0,#&60]
�BICEQ R1,R1,#&80
�STREQB R1,[R0,#&60]
�
�LDRB R12,[mem,#crt_regs+9]
CMP R12,#3
�Q PC,R14 ; fortress fudge
%MOV R0,#1 : STRB R0,[mem,#T3mode]
*MOV PC,R14
4
>.writeT3high_latch
HSTRB R0,[mem,#T3R+3]
RMOV PC,R14
\
f.writeT4low_latch
pSTRB R0,[mem,#T4R+2]
zMOV PC,R14
�
�.writeT4high_count
�LDRB R1,[mem,#T4R+2]
�ADD R1,R1,R0,LSL#8
�MOV R1,R1,LSL#16
�LDR R0,[mem,#min]
�ADD R1,R1,R0,LSL#15
�SUB R1,R1,time,LSL#15
�;ADD R1,R1,#2 << 16
�ADD R1,R1,#1 << 16
�STR R1,[mem,#T4]
�LDRB R1,[mem,#ifr2]
�BICS R1,R1, #%001 << 5
STRB R1,[mem,#ifr2]
%MOV R0,#1 : STRB R0,[mem,#T4mode]
MOV PC,R14
$
..readT2low_count
8LDRB R1,[mem,#ifr]
BBIC R1,R1, #%101 << 5
L0STRB R1,[mem,#ifr] ; clear T2 interrupt flag
VLDR R0,[mem,#T2]
`LDR R1,[mem,#min]
jSUB R0,R0,R1,LSL#15
tADD R0,R0,time,LSL#15
~TST R0,#1 << 15 ; ???
�SUBNE time,time,#1
�MOV R0,R0,LSR#16
�� R0,R0,#&FF
�MOV PC,R14
�
�.readT2high_count
�LDR R0,[mem,#T2]
�LDR R1,[mem,#min]
�SUB R0,R0,R1,LSL#15
�ADD R0,R0,time,LSL#15
�TST R0,#1 << 15 ; ???
�SUBNE time,time,#1
MOV R0,R0,LSR#24
MOV PC,R14
.readT1low_count
(LDRB R1,[mem,#ifr]
2BIC R1,R1, #%1 << 6
<0STRB R1,[mem,#ifr] ; clear T1 interrupt flag
FLDR R0,[mem,#T1]
PLDR R1,[mem,#min]
ZSUB R0,R0,R1,LSL#15
dADD R0,R0,time,LSL#15
nTST R0,#1 << 15 ; ???
xSUBNE time,time,#1
�MOV R0,R0,LSR#16
�� R0,R0,#&FF
�MOV PC,R14
�
�.readT1high_count
�LDR R0,[mem,#T1]
�LDR R1,[mem,#min]
�SUB R0,R0,R1,LSL#15
�ADD R0,R0,time,LSL#15
�TST R0,#1 << 15 ; ???
�SUBNE time,time,#1
�MOV R0,R0,LSR#24
�MOV PC,R14
.readT1low_latch
LDRB R0,[mem,#T1R+2]
"MOV PC,R14
,
6.readT1high_latch
@LDRB R0,[mem,#T1R+3]
JMOV PC,R14
T
^.writeT1low_latch
hSTRB R0,[mem,#T1R+2]
rMOV PC,R14
|
�.writeT1high_count
�STRB R0,[mem,#T1R+3]
�LDR R0,[mem,#T1R]
�LDR R1,[mem,#min]
�ADD R0,R0,R1,LSL#15
�SUB R0,R0,time,LSL#15
�ADD R0,R0,#2 << 16
�STR R0,[mem,#T1]
�LDR R1,[mem,#ifr]
�BIC R1,R1, #%1 << 6
�0STRB R1,[mem,#ifr] ; clear T1 interrupt flag
�SUB R0,mem,#512 ; sheila
�LDRB R1,[R0,#&40]
BIC R1,R1,#&80
STRB R1,[R0,#&40]
%MOV R0,#1 : STRB R0,[mem,#T1mode]
&MOV PC,R14
0
:.writeT1high_latch
DSTRB R0,[mem,#T1R+3]
NMOV PC,R14
X
b.writeT2low_latch
lSTRB R0,[mem,#T2R+2]
vMOV PC,R14
�
�.writeT2high_count
�LDRB R1,[mem,#T2R+2]
�ADD R1,R1,R0,LSL#8
�MOV R1,R1,LSL#16
�LDR R0,[mem,#min]
�ADD R1,R1,R0,LSL#15
�SUB R1,R1,time,LSL#15
�ADD R1,R1,#2 << 16
�STR R1,[mem,#T2]
�LDR R1,[mem,#ifr]
�BICS R1,R1, #%101 << 5
�0STRB R1,[mem,#ifr] ; clear T2 interrupt flag
%MOV R0,#1 : STRB R0,[mem,#T2mode]
MOV PC,R14
;.T1mode
*;EQUD 1
4;.T2mode
>;EQUD 0
H;.T3mode
R;EQUD 1
\;.T4mode
f;EQUD 0
p;.T1
z;EQUD &1234 << 16
� ;.T1R
�;EQUD 20000 << 16
�;.T2
�;EQUD 98765 << 16
� ;.T2R
�;EQUD 255 << 16
�;.T3
�;EQUD 6777 << 16
� ;.T3R
�;EQUD 6777 << 16
�;.T4
�;EQUD 7380 << 16
� ;.T4R
;EQUD 255 << 16
;.screen
;EQUD 432
$
;.screenR
.;EQUD 40000
8 ;.min
B
;EQUD 200
L;.sound_timer
V;EQUD 0
`
j
t.keychk
~
EQUD 0
�
�.CLI
�BIC F,F,#%100
�ADD zpc,zpc,#1 << 16
�LDRB R0,keychk
�
CMP R0,#0
�BLEQ keyboard
�;BL keyboard
��fetch3(0,2)
�
�
�
.fetch2
LDR R0,[mem,#min]
SUB R0,R0,time
(LDR R1,[mem,#sound_timer]
2SUB R1,R1,R0
<STR R1,[mem,#sound_timer]
F
P
ZMOV R0,#0 : STR R0,keychk
dLDR R0,[mem,#min]
nSUB R0,R0,time ; ***
xLDR R1,[mem,#screen]
�SUBS R1,R1,R0
�STRGT R1,[mem,#screen]
�BLLE vsync
�
�LDR R0,[mem,#min]
�SUB R0,R0,time ; ***
�LDR R1,speed
�SUBS R1,R1,R0
�STRGT R1,speed
�BLLE speed_control
�
�; LDR R0,[mem,#T1mode]
�; TST R0,#%1
; BEQ skip_timer1
LDR R0,[mem,#min]
"SUB R0,R0,time ; ***
,LDR R1,[mem,#T1]
6SUBS R1,R1,R0,LSL#15
@STRGT R1,[mem,#T1]
JBLLE timer1
T.skip_timer1
^
h; LDR R0,[mem,#T2mode]
r; TST R0,#%1
|; BEQ skip_timer2
�
�LDR R0,[mem,#min]
�SUB R0,R0,time ; ***
�LDR R1,[mem,#T2]
�SUBS R1,R1,R0,LSL#15
�STR R1,[mem,#T2]
�BLLE timer2
�.skip_timer2
�
�; LDR R0,[mem,#T3mode]
�; TST R0,#%1
�; BEQ skip_timer3
�
LDR R0,[mem,#min]
SUB R0,R0,time ; ***
LDR R1,[mem,#T3]
&SUBS R1,R1,R0,LSL#15
0STRGT R1,[mem,#T3]
:BLLE timer3
D.skip_timer3
N
X; LDR R0,[mem,#T4mode]
b; TST R0,#%1
l; MVNEQ R1,#0 ; -1
v; STREQ R1,T4
�; BEQ skip_timer4
�
�LDR R0,[mem,#min]
�SUB R0,R0,time ; ***
�LDR R1,[mem,#T4]
�SUBS R1,R1,R0,LSL#15
�STR R1,[mem,#T4]
�BLLE timer4
�.skip_timer4
�
�LDR R0,[mem,#min]
�SUB R0,R0,time
�LDR R1,[mem,#tape_count]
SUBS R1,R1,R0
STRGT R1,[mem,#tape_count]
BLLE tape_fetch
*LDRB R1,[mem,#ifr]
4LDRB R2,[mem,#ifr2]
>%LDRB R12,[mem,#ier] : � R1,R1,R12
H%LDRB R12,[mem,#ier2]: � R2,R2,R12
R%;BIC R1,R1,#&80 : ;BIC R2,R2,#&80
\
f
p;LDRB R0,[mem,#ier]
z.;BIC R0,R0,#%1 ; ignore keyboard interrupt
�;�S R0,R0,R1
�;�RNE R1,R1,#&80
�;LDRB R0,[mem,#ier2]
�;�S R0,R0,R2
�;�RNE R2,R2,#&80
�
�TST F,#%100
�BNE skip_do_interrupt
�;TST R1,#&80
�;TSTEQ R2,#&80
��S R1,R1,#%01111111
��EQS R2,R2,#%01111111
�BEQ skip_do_interrupt
;CMP R13,#1
;BNE skip_do_interrupt
$.do_interrupt
.�do_interrupt
8
B.skip_do_interrupt
L
V;BL keyboard �D � CLI!!!
`BL keys2
j.skip_keys
tLDR time,[mem,#T1]
~MOV time,time,LSR#15
�LDR R1,[mem,#screen]
�CMP R1,#0 : �Q R1,time
�CMP R1,time
�MOVLT time,R1
�LDRB R1,[mem,#T2mode]
�
CMP R1,#0
�BEQ skipT2
�LDR R1,[mem,#T2]
�
�;RJW
�MOVS R1,R1,LSR#15
��Q R1,time
CMP R1,time
MOVLT time,R1
.skipT2
LDR R1,[mem,#T3]
(MOVS R1,R1,LSR#15
2
< ; RJW
F�Q R1,time
PCMP R1,time
ZMOVLT time,R1
dLDRB R1,[mem,#T4mode]
n
CMP R1,#0
xBEQ skipT4
�LDR R1,[mem,#T4]
�
� ; RJW
�MOVS R1,R1,LSR#15
��Q R1,time
�CMP R1,time
�MOVLT time,R1
�.skipT4
�;CMP time,#0 : ;�Q time,#1
�SUB time,time,#4
�STR time,[mem,#min]
��fetch2
�
.interrupt
TST F,#%100
"MOVNE PC,R14
,
6LDRB R1,[mem,#ifr]
@LDRB R2,[mem,#ifr2]
J%LDRB R12,[mem,#ier] : � R1,R1,R12
T%LDRB R12,[mem,#ier2]: � R2,R2,R12
^
h�S R1,R1,#%01111111
r�EQS R2,R2,#%01111111
|
�Q PC,R14
�
��do_interrupt
�
�MOV PC,R14
�
�.F10temp
�
EQUD 0
�
�.F10
�SWI "6502_Getkdata"
�STR R14,F10temp
�MOV R0,#255
�STRB R0,[mem,#lastmode]
BL updatescreen
BL force_update_pal
BL cursor
LDR PC,F10temp
&
0;.fetch3
:
.keys2
D;SWI "6502_Checkkdata"
NLDR R0,[mem,#key_addr]
XLDRB R0,[R0,#-4]
b
l
vCMP R0,#&1F ; Insert
��Q R1,#1
�STREQ R1,trace2
�CMP R0,#10 ; F10
�BEQ F10
�CMP R0,#11 ; F11
�CMPNE R0,#12 ; F12
�CMPNE R0,#15 ; break
�BEQ raw_exit2
�MOV PC,R14
�
�
.keyboard
�MOV R0,#1 : STR R0,keychk
�
!
!;SWI "6502_Checkkdata"
!LDR R0,[mem,#key_addr]
! LDRB R0,[R0,#-4]
!*CMP R0,#&FF : �Q PC,R14
!4
!>
!HSWI "6502_Getkdata"
!R;CMP R0,#&FF : ;�Q PC,R14
!\CMP R0,#&1F ; Insert
!f�Q R1,#1
!pSTREQ R1,trace2
!zCMP R0,#10 ; F10
!�BEQ F10
!�CMP R0,#15
!�CMPNE R0,#12
!�CMPNE R0,#11 ; F11
!�BEQ raw_exit
!�
!�;CMP R0,#0 ; escape
!�;LDREQB R0,[mem,#&FF]
!�;�REQ R0,R0,#&80
!�;STREQB R0,[mem,#&FF]
!�LDRB R0,[R1,R0]
!�CMP R0,#&FF
!�;BEQ not_keyboard
"
�Q PC,R14
"
";B not_keyboard
"$CMP R0,#10 ; shift, ctrl
".MOVLT PC,R14
"8LDRB R1,[mem,#ifr]
"B-�R R1,R1,#%1 ; interrupt is from keyboard
"LSTRB R1,[mem,#ifr]
"VLDRB R0,[mem,#ier]
"`TST R0,#%1
"j
�Q PC,R14
"t�do_interrupt
"~MOV PC,R14
"�
"�
"�;.no_interrupt
"�;LDRB R0,trace2
"�;CMP R0,#0
"�;BEQ notrace2
"�;�showregs
"�;.notrace2
"�;�fetch2
"�
"�.define_cursor
"�$MOV R1,#0 : STRB R1,cursor_state
# .define_cursor2
#
LDRB R1,cursor_state
#CMP R1,#0:MOVNE PC,R14
#
#(-LDRB R1,[mem,#crt_regs+10] ; cursor start
#2
#<� R12,R1,#%100000
#FTST R12,#%1100000
#PBEQ blank_cursor
#Z
#d+LDRB R2,[mem,#crt_regs+11] ; cursor end
#n� R1,R1,#31
#x� R2,R2,#31
#�
#�SUBS R12,R2,R1
#�BLT blank_cursor
#�
#�
#�LDRB R12,[mem,#fe20]
#�� R12,R12,#%100000
#�
#�TST R12,#%1000
#��Q R13,#2 ; mode 5
#�MOVNE R13,#1
#�
#�
MOV R0,#1
$MOV R0,R0,LSL R13
$TSTEQ R12,#%100000
$�Q R0,#8 ; mode 2
$"
�Q R13,#3
$,STRB R0,cursor_width
$6
$@TST R12,#%10 ; teletext
$JMVNNE R12,#7
$T
�Q R12,#1
$^
$hADD R2,R2,R12
$rSTRB R2,cursor_height
$|
$�;MOV R0,#1
$�;MOV R0,R0,LSL R13
$�;STRB R0,cursor_width
$�
$�
$�ADR R0,cursor_data
$�SUB R0,R0,R1,LSL R13
$�SUB R0,R0,R12,LSL R13
$�STR R0,cursor_block+6
$�
$�MOV R0,#21
$�ADR R1,cursor_block
$�SWI "OS_Word"
%MOVS PC,R14
%
%.blank_cursor
%&$MOV R1,#1 : STRB R1,cursor_state
%0.blank_cursor2
%:
%DADR R1,cursor_block
%NADR R0,blank_data
%XSTR R0,cursor_block+6
%bMOV R0,#21
%lSWI "OS_Word"
%vMOV PC,R14
%�
%�.cursor_state
%�
EQUD 0
%�
%�.cursor_flash
%�
EQUD 0
%�.flash_state
%�
EQUD 0
%�
%�;.not_keyboard
%�
EQUW 0
%�.cursor_block
%�
EQUB 0
&EQUB 2 ; shape number
&.cursor_width
&EQUB 2 ; width in bytes
& .cursor_height
&*EQUB 9 ; height in pixels
&4
EQUB 0
&>
EQUB 0
&HEQUD 0 ; address of data
&R
&\
&f ALIGN
&p.blank_data
&z
EQUD 0
&�
EQUD 0
&�
EQUD 0
&�
EQUD 0
&�
EQUD 0
&�
EQUD 0
&�
EQUD 0
&�
EQUD 0
&�
EQUD 0
&�
EQUD 0
&�
EQUD 0
&�
EQUD 0
&�
EQUD 0
&�
EQUD 0
'
EQUD 0
'
EQUD 0
'
EQUD 0
'$
EQUD 0
'.
EQUD 0
'8
EQUD 0
'B
EQUD 0
'L
EQUD 0
'V
EQUD 0
'`
EQUD 0
'j
EQUD 0
't
EQUD 0
'~
EQUD 0
'�
EQUD 0
'�
EQUD 0
'�
EQUD 0
'�
EQUD 0
'�
EQUD 0
'�.cursor_data
'�EQUD &FFFFFFFF
'�EQUD &FFFFFFFF
'�EQUD &FFFFFFFF
'�EQUD &FFFFFFFF
'�EQUD &FFFFFFFF
'�EQUD &FFFFFFFF
( EQUD &FFFFFFFF
(
EQUD &FFFFFFFF
(EQUD &FFFFFFFF
(EQUD &FFFFFFFF
((EQUD &FFFFFFFF
(2EQUD &FFFFFFFF
(<EQUD &FFFFFFFF
(FEQUD &FFFFFFFF
(PEQUD &FFFFFFFF
(ZEQUD &FFFFFFFF
(dEQUD &FFFFFFFF
(nEQUD &FFFFFFFF
(xEQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
(�EQUD &FFFFFFFF
)
).cursor7
)
)"LDRB R0,[mem,#crt_regs+14]
),LDRB R1,[mem,#crt_regs+15]
)6ADD R0,R1,R0,LSL#8
)@
)J0LDRB R1,[mem,#crt_regs+12] : ;� R1,R1,#%1111
)TLDRB R2,[mem,#crt_regs+13]
)^ADD R2,R2,R1,LSL#8
)hSUBS R0,R0,R2
)rMOVMI R0,#0
)|
)�.;LDRB R12,[mem,#crt_regs+1] ; horiz. chars
)�;MOV R12,#40
)�
)�);�divmod(0,12,1,2,13) ; R0 = R0 � R12
)�) ; R2 = R0 � R12
)�;RSB R2,R2,#25
)�;MOV R2,R2,LSL#5
)�;ADD R2,R2,R2,LSR#2
)�;MOV R0,R0,LSL#5
)�;ADD R0,R0,R2,LSL#16
)�; We know that R0<1000
)�; R0 = R0 � 40
)�; R2 = R0 � 40
*;�divmod(0,12,1,2,13)
*!MOV R2,#((25<<5)+(25<<3))<<16
*CMP R0,#640
*&SUBGE R0,R0,#640
*0$SUBGE R2,R2,#((1<<9)+(1<<7))<<16
*:CMP R0,#320
*DSUBGE R0,R0,#320
*N$SUBGE R2,R2,#((1<<8)+(1<<6))<<16
*XCMP R0,#160
*bSUBGE R0,R0,#160
*l$SUBGE R2,R2,#((1<<7)+(1<<5))<<16
*vCMP R0,#80
*�SUBGE R0,R0,#80
*�$SUBGE R2,R2,#((1<<6)+(1<<4))<<16
*�CMP R0,#40
*�SUBGE R0,R0,#40
*�$SUBGE R2,R2,#((1<<5)+(1<<3))<<16
*�
*�
*�ADD R0,R2,R0,LSL#5
*�STR R0,osword21_5_block1
*�ADR R1,osword21_5_block
*�MOV R0,#21
*�(SWI "OS_Word" ; set pointer position
*�;MOV PC,R14
*�B define_cursor2
+
+;B cursor_cont
+
+ .padding_to_align_osword
+*EQUB 0 : EQUB 0 : EQUB 0
+4.osword21_5_block
+>
EQUB 5
+H.osword21_5_block1
+R
EQUD 0
+\
+f0� R0,R0,#&20 : ADD R0,R0,#&74 : � R0,R0,#&FF
+p
+z
+�.cursor
+�+MOV R0,#0 : STR R0,[mem,#cursor_tamper]
+�
+�\LDRB R1,[mem,#cursor_on]
+�\CMP R1,#0:\MOVNE PC,R14
+�TST F,#1 << 10 ; cursor on?
+�
�Q PC,R14
+�
+�LDRB R0,[mem,#fe20]
+�
+�TST R0,#%11100000
+�BEQ blank_cursor
+�
,TST R0,#%10 ; teletext
,BNE cursor7
,
,$LDRB R0,[mem,#crt_regs+14]
,.LDRB R1,[mem,#crt_regs+15]
,8ADD R0,R1,R0,LSL#8
,B
,L/LDRB R1,[mem,#crt_regs+12] : � R1,R1,#%1111
,VLDRB R2,[mem,#crt_regs+13]
,`ADD R2,R2,R1,LSL#8
,jSUBS R0,R0,R2
,tMOVMI R0,#0
,~
,�.cursor_cont
,�
,�-LDRB R12,[mem,#crt_regs+1] ; horiz. chars
,�
,�CMP R12,#0 : �Q PC,R14
,�
,�);�divmod(0,12,1,2,13) ; R0 = R0 � R12
,�) ; R2 = R0 � R12
,�;RSB R2,R2,#32
,�;MOV R2,R2,LSL#5
,�
,�; We know R0<32*R12
- ; R0 = R0 � R12
-
; R2 = R0 � R12
-MOV R2,#32<<21
-CMP R0,R12,LSL#4
-(SUBGE R0,R0,R12,LSL#4
-2SUBGE R2,R2,#16<<21
-<CMP R0,R12,LSL#3
-FSUBGE R0,R0,R12,LSL#3
-PSUBGE R2,R2,#8<<21
-ZCMP R0,R12,LSL#2
-dSUBGE R0,R0,R12,LSL#2
-nSUBGE R2,R2,#4<<21
-xCMP R0,R12,LSL#1
-�SUBGE R0,R0,R12,LSL#1
-�SUBGE R2,R2,#2<<21
-�CMP R0,R12
-�SUBGE R0,R0,R12
-�SUBGE R2,R2,#1<<21
-�
-�
-�9LDRB R1,[mem,#fe20] : TST R1,#%10000 : �Q R0,R0,LSL#1
-�2;MOV R0,R0,LSL#4 ; these two surplus
-�;ADD R0,R0,R2,LSL#16 ;
-�:ADD R0,R2,R0,LSL#4 ; this line missing in 1.30
-�STR R0,osword21_5_block1
-�ADR R1,osword21_5_block
.MOV R0,#21
.(SWI "OS_Word" ; set pointer position
.;MOV PC,R14
.B define_cursor2
."
.,.mono_time
.6
EQUD 0
.@
.speed
.J
EQUD 0
.T
.^.speed_control
.hLDR R0,[mem,#speedR]
.rADD R1,R1,R0
.|STR R1,speed
.�
.�LDR R1,mono_time
.�.mono_loop
.�SWI "OS_ReadMonotonicTime"
.�MOV R0,R0,LSR#1
.�
CMP R0,R1
.�BEQ mono_loop
.�STR R0,mono_time
.�
.�MOV PC,R14
.�
.�
.�
/
.vsync
/STR R14,vsyncR14
/
/&
/0LDR R0,[mem,#screenR]
/:ADD R1,R1,R0
/DSTR R1,[mem,#screen]
/N
/XLDRB R0,ldrb40_tamper
/b"CMP R0,#1 : BLEQ ldrb40_update
/l
/v;BL trace_on
/�
/�;LDRB R1,screen_count
/�;SUBS R1,R1,#1
/�;LDRMIB R1,screen_count+4
/�;STRB R1,screen_count
/�LDR R0,[mem,#tamper]
/�
CMP R0,#0
/�
/�BEQ no_tamper
/�
MOV R0,#0
/�STR R0,[mem,#tamper]
/�;SWI "6502_UpdateScreen"
/�BL recalc_wrap
0BL updatescreen
0TST F,#1 << 10 ; cursor on?
0;BLNE define_cursor
0 BLNE cursor
0*.no_tamper
04LDRB R0,[mem,#pal_tamper]
0>
CMP R0,#0
0HBLNE update_pal
0R
0\
0fLDR R0,[mem,#cursor_tamper]
0p
CMP R0,#0
0zBLNE cursor
0�
0�
0�
0�SUB R0,mem,#512 ; sheila
0�LDRB R1,[R0,#&20]
0�TST R1,#%10 ; teletext?
0�;SWINE "6502_UpdateScreen"
0�BLNE updatescreen
0�ADD R0,R0,#&4D
0�;LDRB R1,[R0]
0�;LDRB R2,[R0,#1]
0�LDRB R1,[mem,#ifr]
0�LDRB R2,[mem,#ier]
1+�R R1,R1,#%10 ; interrupt is from vsync
1-TST R2,#%10 ; is vsync interrupt enabled?
1�RNE R1,R1,#&80
1$;STRB R1,[R0]
1.STRB R1,[mem,#ifr]
18;BEQ no_interrupt
1B;�fetch2
1L
1V;TST F,#1 << 9
1`;BEQ skip_exact
1j
1t;LDR R1,mono_time
1~;.mono_loop
1�;SWI "OS_ReadMonotonicTime"
1�;MOV R0,R0,LSR#1
1�;CMP R0,R1
1�;BEQ mono_loop
1�;STR R0,mono_time
1�
1�.skip_exact
1�
1�TST F,#1 << 10 ; cursor on?
1�LDREQ PC,vsyncR14
1�
1�LDRB R1,cursor_state
2
CMP R1,#0
2
LDRNE PC,vsyncR14
2
2LDRB R1,[mem,#crt_regs+10]
2(/TST R1,#%1000000 ; cursor blinking enabled?
22LDREQ PC,vsyncR14
2<
2FLDRB R0,cursor_flash
2PSUBS R0,R0,#1
2ZSTRB R0,cursor_flash
2dLDRGE PC,vsyncR14
2n
2xTST R1,#%100000
2�
�Q R0,#15
2�MOVNE R0,#31
2�STRB R0,cursor_flash
2�
2�LDR R14,vsyncR14
2�LDRB R0,flash_state
2�� R0,R0,#1
2�STRB R0,flash_state
2�!CMP R0,#0 : BEQ blank_cursor2
2�B define_cursor2
2�
2�;LDR PC,vsyncR14
2�
.vsyncR14
3
EQUD 0
3
3.ldrb40
3"
3,LDRB R2,ldrb40_value
36BIC R0,R0,#%110000
3@�R R0,R0,R2
3J
MOV R1,#1
3TSTRB R1,ldrb40_tamper
3^MOV PC,R14
3h
3r.ldrb40_update
3|MOV R0,#%110000
3�STRB R0,ldrb40_value
3�
MOV R0,#0
3�STRB R0,ldrb40_tamper
3�TST F,#1<<9 ; joystick
3�
�Q PC,R14
3�!SWI &63F40 ; "XJoystick_Read"
3�BVS ldrb40_mouse
3�� R1,R0,#&10000
3�
MOV R0,#1
3�!SWI &63F40 ; "XJoystick_Read"
3�MOVVS R0,#0
3�� R0,R0,#&10000
3�ADD R1,R1,R0,LSL#1
4� R1,R1,#&30000
4MOV R1,R1,LSR#(16-4)
4
4&� R2,R1,#%110000
40
4:;ADD R13,mem,#&FE00
4D;LDRB R0,[R13,#&40]
4N;BIC R0,R0,#%110000
4XSTRB R2,ldrb40_value
4b;�R R0,R0,R2
4l
4vMOV PC,R14
4�
4�.ldrb40_tamper
4�
EQUD 0
4�.ldrb40_value
4�
EQUD 0
4�
4�.ldrb40_mouse
4�MOV R13,R3
4�SWI "OS_Mouse"
4�MOV R3,R13
4�
4�MOV R2,R2,LSR#1
4�RSB R2,R2,#3
5MOV R2,R2,LSL#4
5;ADD R13,mem,#&FE00
5;LDRB R0,[R13,#&40]
5 ;BIC R0,R0,#%110000
5*STRB R2,ldrb40_value
54;�R R0,R0,R2
5>
5HMOV PC,R14
5R
5\.write_ADC_status
5f
5pTST F,#1<<9 ; joystick
5z
�Q PC,R14
5�
5�
5�BIC R12,R0,#%11110000
5�
5�MOV R0,R0,LSR#1
5�!� R0,R0,#%1 ; joystick number
5�!SWI &63F40 ; "XJoystick_Read"
5�BVS write_ADC_mouse
5�
5�
5�(TST R12,#%1 ; left/right or up/down
5��Q R0,R0,LSR#8
5�ADD R0,R0,#127
6� R0,R0,#&FF
6RSBEQ R0,R0,#255
6
6$MOV R1,R0,LSR#2
6.� R1,R1,#%110000
68�R R12,R12,R1
6B�R R12,R12,#%1000000
6L
6VSUB R1,mem,#512 ; sheila
6`
6jSTRB R12,[R1,#&C0]
6tSTRB R12,[R1,#&18]
6~
6�STRB R0,[R1,#&C1]
6�STRB R0,[R1,#&19]
6�MOV R12,#0
6�STRB R12,[R1,#&C2]
6�STRB R12,[R1,#&1A]
6�
6�MOV PC,R14
6�
6�.write_ADC_mouse
6�
6�MOV R13,R3
6�SWI "OS_Mouse"
7 MOV R3,R13
7
7MOV R2,#1024
7SUB R2,R2,#1
7(SUBS R0,R2,R0
72MOVLT R0,#0
7<
7F;CMP R0,#1024
7P;MOVGE R0,#1024
7Z;SUBGE R0,R0,#1
7d
7n(TST R12,#%1 ; left/right or up/down
7xMOVNE R0,R1
7�
7�MOV R1,R0,LSL#4
7�� R1,R1,#%110000
7��R R12,R12,R1
7��R R12,R12,#%1000000
7�
7�SUB R1,mem,#512 ; sheila
7�
7�STRB R12,[R1,#&C0]
7�STRB R12,[R1,#&18]
7�
7�MOV R12,R0,LSR#2
7�STRB R12,[R1,#&C1]
8STRB R12,[R1,#&19]
8MOV R12,R0,LSL#6
8STRB R12,[R1,#&C2]
8"STRB R12,[R1,#&1A]
8,
86MOV PC,R14
8@
8J
8T.timer1
8^LDR R0,[mem,#T1R]
8hADD R1,R1,R0
8rADD R1,R1,#2 << 16
8|STR R1,[mem,#T1]
8�
8�SUB R0,mem,#512 ; sheila
8�
8�LDRB R1,[R0,#&4B] ; FE4B
8�TST R1,#%01000000
8��Q R2,#0
8�STREQB R2,[mem,#T1mode]
8�
8�TST R1,#%10000000
8�LDRNEB R2,[R0,#&40] ; FE40
8��NE R2,R2,#&80
8�STRNEB R2,[R0,#&40] ; FE40
8�
9LDRB R1,[mem,#ifr]
93�R R1,R1,#%01000000 ; interrupt is from timer 1
9STRB R1,[mem,#ifr]
9&
90MOV PC,R14
9:
9D.timer2
9NLDRB R0,[mem,#T2mode]
9X
CMP R0,#0
9b
�Q PC,R14
9l
MOV R0,#0
9vSTRB R0,[mem,#T2mode]
9�
9�LDRB R1,[mem,#ifr]
9��R R1,R1,#%00100000
9�STRB R1,[mem,#ifr]
9�
9�MOV PC,R14
9�
9�.timer3
9�LDR R0,[mem,#T3R]
9�ADD R1,R1,R0
9�STR R1,[mem,#T3]
9�
9�SUB R0,mem,#512 ; sheila
:
:LDRB R1,[R0,#&6B]
:TST R1,#%01000000
: BNE T3mode_skip2
:*
:4LDRB R1,[mem,#T3mode]
:>
CMP R1,#1
:H;SWINE &100+�"1"
:R;SWIEQ &100+�"0"
:\BNE T3mode_skip
:f
:p.T3mode_skip2
:zLDRB R1,[mem,#ifr2]
:��R R1,R1,#%01000000
:�STRB R1,[mem,#ifr2]
:�
:�
:�;LDRB R1,[R0,#&6B] ; FE6B
:�;TST R1,#%01000000
:�
;�Q R2,#0
:�;MOVNE R2,#1
:�;STREQB R2,[mem,#T3mode]
:�;SWIEQ &100+�"z"
:�
:�.T3mode_skip
:�
MOV R2,#0
;STRB R2,[mem,#T3mode]
;
;;LDRB R1,[R0,#&6B] ; FE6B
;$;TST R1,#%10000000
;.;LDRB R2,[R0,#&60] ; FE60
;8;�NE R2,R2,#&80
;B;�REQ R2,R2,#&80
;L;STRB R2,[R0,#&60] ; FE60
;V
;`LDRB R1,[R0,#&6B] ; FE6B
;j� R1,R1,#&C0
;tTST R1,#&C0
;~LDRB R2,[R0,#&60] ; FE60
;��EQ R2,R2,#&80
;��RNE R2,R2,#&80
;�STRB R2,[R0,#&60] ; FE60
;�
;�
;�MOV PC,R14
;�.return_addr
;�
EQUD 0
;�
;�.roms_addr
;�
EQUD 0
;�
<