Setting cc65 IRQ/NMI for homebrew board?
Posted: Sun Jul 05, 2020 9:05 pm
Hi,
Back in 1988/89 I made my own 65C02 board for my own learning/experiments. Fast forward 30 years, i just recently came across cc65. i dusted off my micro board and low and behold, it still works
It has 32K of ram, so it's fine for writing C code. I first made a C# PC app to talk to the board. For cc65 to work, i modded a cfg file to match my board, and changed crt0.s to jump to the monitor after exiting main(). It's working fine so far ...cool.
For this board, on boot, the monitor(eprom) sets location $FFFA(NMI) to $00FA, and for $FFFE(IRQ) to $00FD. During boot, the monitor inits these locations($00FA and $00FD) with $40(RTI). Sooooo, back in the day when i'd write my asm apps (i used TASM back then), for IRQs, i'd put a $4C (abs JMP) at $00FD followed by the address of my IRQ routine at $00FE/$00FF. My question after all this(whew!), is how do i tell cc65 where to put the IRQ address of my C method? My guess is right now if i write:
#define STACK_SIZE 256
unsigned char TempStack[STACK_SIZE];
int main(void)
{
SEI(); // disable IRQ
set_irq(&IRQ_Routine, TempStack, STACK_SIZE);
CLI(); // enable IRQ
...
return EXIT_SUCCESS;
}
// IRQ handler
unsigned char IRQ_Routine(void)
{
...
return (IRQ_NOT_HANDLED);
}
...then cc65 is going to try to put the address of "IRQ_Routine" at $FFFE? ...which i don't want. I've Googled and come up with bits and pieces, but still unsure what to do.
For starter is guess i have to add the following to my cfg?
CONDES: type = interruptor,
label = __INTERRUPTOR_TABLE__,
count = __INTERRUPTOR_COUNT__,
segment = RODATA,
import = __CALLIRQ__;
..then add some kind of stub code in crt0? I'd like this to work for IRQ routines written in C and asm.
Any help, with examples, appreciated. Thanks!
Back in 1988/89 I made my own 65C02 board for my own learning/experiments. Fast forward 30 years, i just recently came across cc65. i dusted off my micro board and low and behold, it still works
For this board, on boot, the monitor(eprom) sets location $FFFA(NMI) to $00FA, and for $FFFE(IRQ) to $00FD. During boot, the monitor inits these locations($00FA and $00FD) with $40(RTI). Sooooo, back in the day when i'd write my asm apps (i used TASM back then), for IRQs, i'd put a $4C (abs JMP) at $00FD followed by the address of my IRQ routine at $00FE/$00FF. My question after all this(whew!), is how do i tell cc65 where to put the IRQ address of my C method? My guess is right now if i write:
#define STACK_SIZE 256
unsigned char TempStack[STACK_SIZE];
int main(void)
{
SEI(); // disable IRQ
set_irq(&IRQ_Routine, TempStack, STACK_SIZE);
CLI(); // enable IRQ
...
return EXIT_SUCCESS;
}
// IRQ handler
unsigned char IRQ_Routine(void)
{
...
return (IRQ_NOT_HANDLED);
}
...then cc65 is going to try to put the address of "IRQ_Routine" at $FFFE? ...which i don't want. I've Googled and come up with bits and pieces, but still unsure what to do.
For starter is guess i have to add the following to my cfg?
CONDES: type = interruptor,
label = __INTERRUPTOR_TABLE__,
count = __INTERRUPTOR_COUNT__,
segment = RODATA,
import = __CALLIRQ__;
..then add some kind of stub code in crt0? I'd like this to work for IRQ routines written in C and asm.
Any help, with examples, appreciated. Thanks!