mirror of
https://github.com/irmen/prog8.git
synced 2024-10-19 07:23:56 +00:00
changed system irq/rasterirq setting routines
This commit is contained in:
parent
4aca8bb8df
commit
a95677564e
@ -304,27 +304,13 @@ asmsub disable_runstop_and_charsetswitch() clobbers(A) {
|
|||||||
}}
|
}}
|
||||||
}
|
}
|
||||||
|
|
||||||
asmsub set_irqvec_excl() clobbers(A) {
|
asmsub set_irq(uword handler @AY, ubyte useKernal @Pc) clobbers(A) {
|
||||||
%asm {{
|
|
||||||
sei
|
|
||||||
lda #<_irq_handler
|
|
||||||
sta c64.CINV
|
|
||||||
lda #>_irq_handler
|
|
||||||
sta c64.CINV+1
|
|
||||||
cli
|
|
||||||
rts
|
|
||||||
_irq_handler jsr set_irqvec._irq_handler_init
|
|
||||||
jsr irq.irq
|
|
||||||
jsr set_irqvec._irq_handler_end
|
|
||||||
lda #$ff
|
|
||||||
sta c64.VICIRQ ; acknowledge raster irq
|
|
||||||
lda c64.CIA1ICR ; acknowledge CIA1 interrupt
|
|
||||||
jmp c64.IRQDFEND ; end irq processing - don't call kernel
|
|
||||||
}}
|
|
||||||
}
|
|
||||||
|
|
||||||
asmsub set_irqvec() clobbers(A) {
|
|
||||||
%asm {{
|
%asm {{
|
||||||
|
sta _modified+1
|
||||||
|
sty _modified+2
|
||||||
|
lda #0
|
||||||
|
adc #0
|
||||||
|
sta _use_kernal
|
||||||
sei
|
sei
|
||||||
lda #<_irq_handler
|
lda #<_irq_handler
|
||||||
sta c64.CINV
|
sta c64.CINV
|
||||||
@ -333,9 +319,23 @@ asmsub set_irqvec() clobbers(A) {
|
|||||||
cli
|
cli
|
||||||
rts
|
rts
|
||||||
_irq_handler jsr _irq_handler_init
|
_irq_handler jsr _irq_handler_init
|
||||||
jsr irq.irq
|
_modified jsr $ffff ; modified
|
||||||
jsr _irq_handler_end
|
jsr _irq_handler_end
|
||||||
jmp c64.IRQDFRT ; continue with normal kernel irq routine
|
lda _use_kernal
|
||||||
|
bne +
|
||||||
|
lda #$ff
|
||||||
|
sta c64.VICIRQ ; acknowledge raster irq
|
||||||
|
lda c64.CIA1ICR ; acknowledge CIA1 interrupt
|
||||||
|
; end irq processing - don't use kernal's irq handling
|
||||||
|
pla
|
||||||
|
tay
|
||||||
|
pla
|
||||||
|
tax
|
||||||
|
pla
|
||||||
|
rti
|
||||||
|
+ jmp c64.IRQDFRT ; continue with normal kernal irq routine
|
||||||
|
|
||||||
|
_use_kernal .byte 0
|
||||||
|
|
||||||
_irq_handler_init
|
_irq_handler_init
|
||||||
; save all zp scratch registers and the X register as these might be clobbered by the irq routine
|
; save all zp scratch registers and the X register as these might be clobbered by the irq routine
|
||||||
@ -388,7 +388,7 @@ IRQ_SCRATCH_ZPWORD2 .word 0
|
|||||||
}}
|
}}
|
||||||
}
|
}
|
||||||
|
|
||||||
asmsub restore_irqvec() clobbers(A) {
|
asmsub restore_irq() clobbers(A) {
|
||||||
%asm {{
|
%asm {{
|
||||||
sei
|
sei
|
||||||
lda #<c64.IRQDFRT
|
lda #<c64.IRQDFRT
|
||||||
@ -404,8 +404,15 @@ asmsub restore_irqvec() clobbers(A) {
|
|||||||
}}
|
}}
|
||||||
}
|
}
|
||||||
|
|
||||||
asmsub set_rasterirq(uword rasterpos @ AY) clobbers(A) {
|
asmsub set_rasterirq(uword handler @AY, uword rasterpos @R0, ubyte useKernal @Pc) clobbers(A) {
|
||||||
%asm {{
|
%asm {{
|
||||||
|
sta _modified+1
|
||||||
|
sty _modified+2
|
||||||
|
lda #0
|
||||||
|
adc #0
|
||||||
|
sta _use_kernal
|
||||||
|
lda cx16.r0
|
||||||
|
ldy cx16.r0+1
|
||||||
sei
|
sei
|
||||||
jsr _setup_raster_irq
|
jsr _setup_raster_irq
|
||||||
lda #<_raster_irq_handler
|
lda #<_raster_irq_handler
|
||||||
@ -415,13 +422,24 @@ asmsub set_rasterirq(uword rasterpos @ AY) clobbers(A) {
|
|||||||
cli
|
cli
|
||||||
rts
|
rts
|
||||||
|
|
||||||
|
_use_kernal .byte 0
|
||||||
|
|
||||||
_raster_irq_handler
|
_raster_irq_handler
|
||||||
jsr set_irqvec._irq_handler_init
|
jsr set_irq._irq_handler_init
|
||||||
jsr irq.irq
|
_modified jsr $ffff ; modified
|
||||||
jsr set_irqvec._irq_handler_end
|
jsr set_irq._irq_handler_end
|
||||||
lda #$ff
|
lda #$ff
|
||||||
sta c64.VICIRQ ; acknowledge raster irq
|
sta c64.VICIRQ ; acknowledge raster irq
|
||||||
jmp c64.IRQDFRT
|
lda _use_kernal
|
||||||
|
bne +
|
||||||
|
; end irq processing - don't use kernal's irq handling
|
||||||
|
pla
|
||||||
|
tay
|
||||||
|
pla
|
||||||
|
tax
|
||||||
|
pla
|
||||||
|
rti
|
||||||
|
+ jmp c64.IRQDFRT ; continue with kernal irq routine
|
||||||
|
|
||||||
_setup_raster_irq
|
_setup_raster_irq
|
||||||
pha
|
pha
|
||||||
@ -445,28 +463,6 @@ _setup_raster_irq
|
|||||||
}}
|
}}
|
||||||
}
|
}
|
||||||
|
|
||||||
asmsub set_rasterirq_excl(uword rasterpos @ AY) clobbers(A) {
|
|
||||||
%asm {{
|
|
||||||
sei
|
|
||||||
jsr set_rasterirq._setup_raster_irq
|
|
||||||
lda #<_raster_irq_handler
|
|
||||||
sta c64.CINV
|
|
||||||
lda #>_raster_irq_handler
|
|
||||||
sta c64.CINV+1
|
|
||||||
cli
|
|
||||||
rts
|
|
||||||
|
|
||||||
_raster_irq_handler
|
|
||||||
jsr set_irqvec._irq_handler_init
|
|
||||||
jsr irq.irq
|
|
||||||
jsr set_irqvec._irq_handler_end
|
|
||||||
lda #$ff
|
|
||||||
sta c64.VICIRQ ; acknowledge raster irq
|
|
||||||
jmp c64.IRQDFEND ; end irq processing - don't call kernel
|
|
||||||
|
|
||||||
}}
|
|
||||||
}
|
|
||||||
|
|
||||||
; ---- end of C64 specific system utility routines ----
|
; ---- end of C64 specific system utility routines ----
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -41,19 +41,6 @@ internal class AstChecker(private val program: Program,
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// there can be an optional single 'irq' block with a 'irq' subroutine in it,
|
|
||||||
// which will be used as the 60hz irq routine in the vm if it's present
|
|
||||||
val irqBlocks = program.modules.flatMap { it.statements }.filter { it is Block && it.name=="irq" }.map { it as Block }
|
|
||||||
if(irqBlocks.size>1)
|
|
||||||
errors.err("more than one 'irq' block", irqBlocks[0].position)
|
|
||||||
for(irqBlock in irqBlocks) {
|
|
||||||
val irqSub = irqBlock.subScope("irq") as? Subroutine
|
|
||||||
if (irqSub != null) {
|
|
||||||
if (irqSub.parameters.isNotEmpty() || irqSub.returntypes.isNotEmpty())
|
|
||||||
errors.err("irq entrypoint subroutine can't have parameters and/or return values", irqSub.position)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
super.visit(program)
|
super.visit(program)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -16,8 +16,7 @@ import prog8.compiler.IErrorReporter
|
|||||||
import java.nio.file.Path
|
import java.nio.file.Path
|
||||||
|
|
||||||
private val alwaysKeepSubroutines = setOf(
|
private val alwaysKeepSubroutines = setOf(
|
||||||
Pair("main", "start"),
|
Pair("main", "start")
|
||||||
Pair("irq", "irq")
|
|
||||||
)
|
)
|
||||||
|
|
||||||
private val asmJumpRx = Regex("""[\-+a-zA-Z0-9_ \t]+(jmp|jsr)[ \t]+(\S+).*""", RegexOption.IGNORE_CASE)
|
private val asmJumpRx = Regex("""[\-+a-zA-Z0-9_ \t]+(jmp|jsr)[ \t]+(\S+).*""", RegexOption.IGNORE_CASE)
|
||||||
|
@ -139,26 +139,12 @@ IRQ Handling
|
|||||||
============
|
============
|
||||||
|
|
||||||
Normally, the system's default IRQ handling is not interfered with.
|
Normally, the system's default IRQ handling is not interfered with.
|
||||||
You can however install your own IRQ handler.
|
You can however install your own IRQ handler (for clean separation, it is advised to define it inside its own block).
|
||||||
This is possible ofcourse by doing it all using customized inline assembly,
|
There are a few library routines available to make setting up C-64 60hz IRQs and Raster IRQs a lot easier (no assembly code required).
|
||||||
but there are a few library routines available to make setting up C-64 IRQs and raster IRQs a lot easier (no assembly code required).
|
|
||||||
|
|
||||||
For the C64 these routines are::
|
For the C64 these routines are::
|
||||||
|
|
||||||
c64.set_irqvec()
|
c64.set_irq(uword handler_address, boolean useKernal)
|
||||||
c64.set_irqvec_excl()
|
c64.set_rasterirq(uword handler_address, uword rasterline, boolean useKernal)
|
||||||
|
c64.restore_irq() ; set everything back to the systems default irq handler
|
||||||
c64.set_rasterirq( <raster line> )
|
|
||||||
c64.set_rasterirq_excl( <raster line> )
|
|
||||||
|
|
||||||
c64.restore_irqvec() ; set it back to the systems default irq handler
|
|
||||||
|
|
||||||
If you activate an IRQ handler with one of these, it expects the handler to be defined
|
|
||||||
as a subroutine ``irq`` in the module ``irq`` so like this::
|
|
||||||
|
|
||||||
irq {
|
|
||||||
sub irq() {
|
|
||||||
; ... irq handling here ...
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
|
@ -2,6 +2,8 @@
|
|||||||
TODO
|
TODO
|
||||||
====
|
====
|
||||||
|
|
||||||
|
- rename kernel -> kernal
|
||||||
|
- add sys.halt() that is smart on the 65c02
|
||||||
- add sound to the cx16 tehtriz
|
- add sound to the cx16 tehtriz
|
||||||
|
|
||||||
- add const arrays and cost strings
|
- add const arrays and cost strings
|
||||||
|
@ -23,7 +23,7 @@ main {
|
|||||||
|
|
||||||
c64.SCROLX &= %11110111 ; 38 column mode
|
c64.SCROLX &= %11110111 ; 38 column mode
|
||||||
|
|
||||||
c64.set_rasterirq(200) ; enable animation
|
c64.set_rasterirq(&irq.irq, 200, false) ; enable animation via raster interrupt
|
||||||
|
|
||||||
ubyte target_height = 10
|
ubyte target_height = 10
|
||||||
ubyte active_height = 24
|
ubyte active_height = 24
|
||||||
|
@ -7,7 +7,7 @@ main {
|
|||||||
|
|
||||||
sub start() {
|
sub start() {
|
||||||
txt.print("playing the music from boulderdash,\nmade in 1984 by peter liepa.\n\n")
|
txt.print("playing the music from boulderdash,\nmade in 1984 by peter liepa.\n\n")
|
||||||
c64.set_rasterirq(60) ; enable raster irq
|
c64.set_rasterirq(&irq.irq, 60, true) ; enable playback via raster irq
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -5,7 +5,7 @@ main {
|
|||||||
|
|
||||||
sub start() {
|
sub start() {
|
||||||
c64.SCROLY &= %11101111 ; blank the screen
|
c64.SCROLY &= %11101111 ; blank the screen
|
||||||
c64.set_rasterirq_excl(40) ; register exclusive raster irq handler
|
c64.set_rasterirq(&irq.irq, 40, false) ; register exclusive raster irq handler
|
||||||
|
|
||||||
repeat {
|
repeat {
|
||||||
; enjoy the moving bars :)
|
; enjoy the moving bars :)
|
||||||
|
@ -46,7 +46,7 @@ main {
|
|||||||
}
|
}
|
||||||
|
|
||||||
c64.SPENA = 255 ; enable all sprites
|
c64.SPENA = 255 ; enable all sprites
|
||||||
c64.set_rasterirq(51) ; enable animation
|
c64.set_rasterirq(&irq.irq, 255, true) ; enable animation
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -7,18 +7,11 @@ main {
|
|||||||
; $1F9C0 - $1F9FF PSG registers
|
; $1F9C0 - $1F9FF PSG registers
|
||||||
|
|
||||||
sub start() {
|
sub start() {
|
||||||
|
c64.set_rasterirq(&irq.irq, 100, true)
|
||||||
|
|
||||||
ubyte xx=33
|
sys.wait(100)
|
||||||
when xx {
|
|
||||||
1 -> {
|
c64.restore_irq()
|
||||||
}
|
|
||||||
2 -> {
|
|
||||||
}
|
|
||||||
else -> {
|
|
||||||
}
|
|
||||||
else -> {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
; uword freq = 1181
|
; uword freq = 1181
|
||||||
; cx16.vpoke(1, $f9c0, lsb(freq))
|
; cx16.vpoke(1, $f9c0, lsb(freq))
|
||||||
@ -28,3 +21,21 @@ main {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
irq {
|
||||||
|
uword counter = 0
|
||||||
|
|
||||||
|
sub irq() {
|
||||||
|
c64.EXTCOL++
|
||||||
|
ubyte xx
|
||||||
|
repeat 20 {
|
||||||
|
xx++
|
||||||
|
}
|
||||||
|
c64.EXTCOL--
|
||||||
|
|
||||||
|
@($0400) = lsb(counter)
|
||||||
|
@($0401) = msb(counter)
|
||||||
|
|
||||||
|
counter++
|
||||||
|
}
|
||||||
|
}
|
||||||
|
@ -37,7 +37,7 @@ main {
|
|||||||
c64.SPRPTR[i] = $0a00/64
|
c64.SPRPTR[i] = $0a00/64
|
||||||
}
|
}
|
||||||
c64.SPENA = 255 ; enable all sprites
|
c64.SPENA = 255 ; enable all sprites
|
||||||
c64.set_rasterirq(220) ; enable animation
|
c64.set_rasterirq(&irq.irq, 230, true) ; enable animation
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user