I suspect this is a result of me being a 6502 assembler newbie (after over 40 years of using a BBC micro), but I'd be really grateful for another pair of eyes on this one.
I'm having a bit of a problem with setting up a timer and interrupt handler in a project involving sending MIDI data over a Music 2000 clone interface. I need a high-resolution timer so triggering an interrupt from one of the 1MHz VIA timers seems ideal for this job. I've read over the sections in the Advanced User Guide, "Advanced Machine Code Techniques for the BBC Micro", "Assembly Language Programming for the BBC Micro" and have watched Kieran Connell's excellent two-part introduction to interrupts and still can't get my code to work.
Below is a very, very basic setup that doesn't work for me. I had expected that this would start a timer that would set the T1 timer interrupt flag every 65535 clock cycles, thereby incrementing the "counter" counter. I would also expect to see the "handlerCalls" counter increment with every call to the handler.
What actually happens is:
- counter and handlerCalls remain at zero after running the program
- if I press Escape, handlerCalls increases by TWO. (counter remains zero; however, I would expect that as bit 6 of the IFR flag wouldn't be set)
Does anyone have any idea what I'm doing wrong? (I fully expect this to be in "schoolboy error" territory.)
Code: Select all
10 DIM START 100
20
30 counter=&70:?counter=0
40 handlerCalls=&71:?handlerCalls=0
50 oldIrq=&80
51
60 FOR pass=0 TO 3 STEP 3
61 P%=START
70 [
80 OPT pass
90
100 .init
110 SEI
120
130 LDA #&C0 \ Enable interrupt on
140 STA &FE6E \ user VIA.
150
160 LDA &204:STA oldIrq \
170 LDA &205:STA oldIrq+1 \ Store old interrupt vectors
180 LDA #(handler MOD 256)\ and set new ones for new
190 STA &204 \ handler.
200 LDA #(handler DIV 256)\
210 STA &205 \
220
230 LDA #&40 \ Set continuous
240 STA &FE6B \ interrupts.
250
260 LDA #&FF \
270 STA &FE64 \ Set timer
280 LDA #&FF \ parameters.
290 STA &FE65 \
300
310 CLI
320 RTS
330
340 .handler
350 LDA &FC:PHA
360 INC handlerCalls \ Check if handler is invoked.
370
380 LDA &FE6D \ Check bit 6 of
390 AND #&40 \ IFR register and exit
400 BEQ returnToOS \ if not set.
410
420 LDA &FE64 \ Clear low byte latch,
430 INC counter \ Increment number of times flag is set.
440 .returnToOS
450 PLA:STA &FC
460 JMP (oldIrq)
470
480 ]
490
500 NEXT pass
510
520 CALL init