]> git.sur5r.net Git - cc65/commitdiff
Use new callirq function
authorcuz <cuz@b7a2c559-68d2-44c3-8de9-860c34a00d81>
Sun, 4 Apr 2004 14:28:57 +0000 (14:28 +0000)
committercuz <cuz@b7a2c559-68d2-44c3-8de9-860c34a00d81>
Sun, 4 Apr 2004 14:28:57 +0000 (14:28 +0000)
git-svn-id: svn://svn.cc65.org/cc65/trunk@2970 b7a2c559-68d2-44c3-8de9-860c34a00d81

libsrc/c128/crt0.s
libsrc/c64/Makefile
libsrc/c64/c64-joymouse.s [new file with mode: 0644]
libsrc/c64/crt0.s
libsrc/cbm510/crt0.s
libsrc/cbm610/crt0.s
libsrc/plus4/crt0.s

index dc31bae64d6c1ca2b608953fef148b5bfa62280a..247fdb7433b4d14ccb52b50c33707b7a08eaf833 100644 (file)
@@ -5,11 +5,11 @@
 ;
 
        .export         _exit
-       .import         condes, initlib, donelib
+       .import         callirq, initlib, donelib
        .import         zerobss
        .import         push0, callmain
         .import         RESTOR, BSOUT, CLRCH
-       .import         __IRQFUNC_TABLE__, __IRQFUNC_COUNT__
+       .import         __IRQFUNC_COUNT__
        .import         __RAM_START__, __RAM_SIZE__
 
         .include        "zeropage.inc"
@@ -171,10 +171,7 @@ IRQStub:
        pha                             ; And save on stack
        lda     #MMU_CFG_CC65           ; Bank 0 with kernal ROM
        sta     MMU_CR
-       ldy     #<(__IRQFUNC_COUNT__*2)
-               lda     #<__IRQFUNC_TABLE__
-       ldx     #>__IRQFUNC_TABLE__
-       jsr     condes                  ; Call the functions
+               jsr     callirq                 ; Call the functions
        pla                             ; Get old register value
        sta     MMU_CR
                jmp     IRQInd                  ; Jump to the saved IRQ vector
index 1dcfbca06a2375e8993c31b15cab50a1df73c506..e6d171996e82c835959c9bb199753037e7cce302 100644 (file)
@@ -60,7 +60,7 @@ EMDS = c64-georam.emd c64-ram.emd c64-ramcart.emd c64-reu.emd c64-vdc.emd
 
 JOYS = c64-hitjoy.joy c64-numpad.joy c64-ptvjoy.joy c64-stdjoy.joy
 
-MOUS = c64-1351.mou
+MOUS = c64-1351.mou c64-joymouse.mou
 
 SERS = c64-swlink.ser
 
diff --git a/libsrc/c64/c64-joymouse.s b/libsrc/c64/c64-joymouse.s
new file mode 100644 (file)
index 0000000..833f21c
--- /dev/null
@@ -0,0 +1,389 @@
+;
+; Driver for a "joystick mouse".
+;
+; Ullrich von Bassewitz, 2004-03-29
+;
+
+        .include        "zeropage.inc"
+        .include        "mouse-kernel.inc"
+       .include        "c64.inc"
+
+        .macpack        generic
+
+; ------------------------------------------------------------------------
+; Header. Includes jump table
+
+.segment        "JUMPTABLE"
+
+HEADER:
+
+; Driver signature
+
+        .byte   $6d, $6f, $75           ; "mou"
+        .byte   MOUSE_API_VERSION       ; Mouse driver API version number
+
+; Jump table.
+
+        .addr   INSTALL
+        .addr   UNINSTALL
+        .addr   HIDE
+        .addr   SHOW
+        .addr   BOX
+        .addr   MOVE
+        .addr   BUTTONS
+        .addr   POS
+        .addr   INFO
+        .addr   IOCTL
+        .addr   IRQ
+
+; Callback table, set by the kernel before INSTALL is called
+
+CHIDE:  jmp     $0000                   ; Hide the cursor
+CSHOW:  jmp     $0000                   ; Show the cursor
+CMOVEX: jmp     $0000                   ; Move the cursor to X coord
+CMOVEY: jmp     $0000                   ; Move the cursor to Y coord
+
+
+;----------------------------------------------------------------------------
+; Constants
+
+SCREEN_HEIGHT   = 200
+SCREEN_WIDTH    = 320
+
+.enum   JOY
+        UP      = $01
+        DOWN    = $02
+        LEFT    = $04
+        RIGHT   = $08
+        FIRE    = $10
+.endenum
+
+;----------------------------------------------------------------------------
+; Global variables. The bounding box values are sorted so that they can be
+; written with the least effort in the BOX routine, so don't reorder them.
+
+.bss
+
+Vars:
+YPos:           .res    2               ; Current mouse position, Y
+XPos:           .res    2               ; Current mouse position, X
+YMax:          .res    2               ; Y2 value of bounding box
+XMax:          .res    2               ; X2 value of bounding box
+YMin:          .res    2               ; Y1 value of bounding box
+XMin:          .res    2               ; X1 value of bounding box
+Buttons:       .res    1               ; Button mask
+
+; Temporary value used in the int handler
+
+Temp:           .res    1
+
+; Default values for above variables
+
+.rodata
+
+.proc   DefVars
+        .word   SCREEN_HEIGHT/2         ; YPos
+        .word   SCREEN_WIDTH/2          ; XPos
+        .word   SCREEN_HEIGHT           ; YMax
+        .word   SCREEN_WIDTH            ; XMax
+        .word   0                       ; YMin
+        .word   0                       ; XMin
+       .byte   0                       ; Buttons
+.endproc
+
+.code
+
+;----------------------------------------------------------------------------
+; INSTALL routine. Is called after the driver is loaded into memory. If
+; possible, check if the hardware is present.
+; Must return an MOUSE_ERR_xx code in a/x.
+
+INSTALL:
+
+; Initialize variables. Just copy the default stuff over
+
+        ldx     #.sizeof(DefVars)-1
+@L1:    lda     DefVars,x
+        sta     Vars,x
+        dex
+        bpl     @L1
+
+; Be sure the mouse cursor is invisible and at the default location. We
+; need to do that here, because our mouse interrupt handler doesn't set the
+; mouse position if it hasn't changed.
+
+        sei
+        jsr     CHIDE
+        lda     XPos
+        ldx     XPos+1
+        jsr     CMOVEX
+        lda     YPos
+        ldx     YPos+1
+        jsr     CMOVEY
+        cli
+
+; Done, return zero (= MOUSE_ERR_OK)
+
+        ldx     #$00
+        txa
+        rts                             ; Run into UNINSTALL instead
+
+;----------------------------------------------------------------------------
+; UNINSTALL routine. Is called before the driver is removed from memory.
+; No return code required (the driver is removed from memory on return).
+
+UNINSTALL       = HIDE                  ; Hide cursor on exit
+
+;----------------------------------------------------------------------------
+; HIDE routine. Is called to hide the mouse pointer. The mouse kernel manages
+; a counter for calls to show/hide, and the driver entry point is only called
+; if the mouse is currently visible and should get hidden. For most drivers,
+; no special action is required besides hiding the mouse cursor.
+; No return code required.
+
+HIDE:   sei
+        jsr     CHIDE
+        cli
+        rts
+
+;----------------------------------------------------------------------------
+; SHOW routine. Is called to show the mouse pointer. The mouse kernel manages
+; a counter for calls to show/hide, and the driver entry point is only called
+; if the mouse is currently hidden and should become visible. For most drivers,
+; no special action is required besides enabling the mouse cursor.
+; No return code required.
+
+SHOW:   sei
+        jsr     CSHOW
+        cli
+        rts
+
+;----------------------------------------------------------------------------
+; BOX: Set the mouse bounding box. The parameters are passed as they come from
+; the C program, that is, maxy in a/x and the other parameters on the stack.
+; The C wrapper will remove the parameters from the stack when the driver
+; routine returns.
+; No checks are done if the mouse is currently inside the box, this is the job
+; of the caller. It is not necessary to validate the parameters, trust the
+; caller and save some code here. No return code required.
+
+BOX:    ldy     #5
+        sei
+        sta     YMax
+        stx     YMax+1
+
+@L1:    lda     (sp),y
+        sta     XMax,y
+        dey
+        bpl     @L1
+
+        cli
+               rts
+
+;----------------------------------------------------------------------------
+; MOVE: Move the mouse to a new position. The position is passed as it comes
+; from the C program, that is: X on the stack and Y in a/x. The C wrapper will
+; remove the parameter from the stack on return.
+; No checks are done if the new position is valid (within the bounding box or
+; the screen). No return code required.
+;
+
+MOVE:   sei                             ; No interrupts
+
+        sta     YPos
+        stx     YPos+1                  ; New Y position
+        jsr     CMOVEY                  ; Set it
+
+        ldy     #$01
+        lda     (sp),y
+        sta     XPos+1
+        tax
+        dey
+        lda     (sp),y
+        sta     XPos                    ; New X position
+
+        jsr     CMOVEX                 ; Move the cursor
+
+       cli                             ; Allow interrupts
+               rts
+
+;----------------------------------------------------------------------------
+; BUTTONS: Return the button mask in a/x.
+
+BUTTONS:
+       lda     Buttons
+       ldx     #$00
+       rts
+
+;----------------------------------------------------------------------------
+; POS: Return the mouse position in the MOUSE_POS struct pointed to by ptr1.
+; No return code required.
+
+POS:    ldy            #MOUSE_POS::XCOORD      ; Structure offset
+
+       sei                             ; Disable interrupts
+       lda     XPos                    ; Transfer the position
+       sta     (ptr1),y
+       lda     XPos+1
+       iny
+       sta     (ptr1),y
+       lda     YPos
+        iny
+        sta     (ptr1),y
+       lda     YPos+1
+       cli                             ; Enable interrupts
+
+        iny
+        sta     (ptr1),y                ; Store last byte
+
+       rts                             ; Done
+
+;----------------------------------------------------------------------------
+; INFO: Returns mouse position and current button mask in the MOUSE_INFO
+; struct pointed to by ptr1. No return code required.
+;
+; We're cheating here to keep the code smaller: The first fields of the
+; mouse_info struct are identical to the mouse_pos struct, so we will just
+; call _mouse_pos to initialize the struct pointer and fill the position
+; fields.
+
+INFO:   jsr    POS
+
+; Fill in the button state
+
+               lda     Buttons
+       ldy     #MOUSE_INFO::BUTTONS
+       sta     (ptr1),y
+
+       rts
+
+;----------------------------------------------------------------------------
+; IOCTL: Driver defined entry point. The wrapper will pass a pointer to ioctl
+; specific data in ptr1, and the ioctl code in A.
+; Must return an error code in a/x.
+;
+
+IOCTL:  lda     #<MOUSE_ERR_INV_IOCTL     ; We don't support ioclts for now
+        ldx     #>MOUSE_ERR_INV_IOCTL
+        rts
+
+;----------------------------------------------------------------------------
+; IRQ: Irq handler entry point. Called as a subroutine but in IRQ context
+; (so be careful).
+;
+
+IRQ:   lda     #$7F
+       sta     CIA1_PRA
+       lda     CIA1_PRB                ; Read joystick #0
+        and     #$1F
+       eor     #$1F                    ; Make all bits active high
+        sta     Temp
+
+; Check for a pressed button and place the result into Buttons
+
+        ldx     #$00                    ; Assume no button pressed
+        and     #JOY::FIRE              ; Check fire button
+        beq     @L0                     ; Jump if not pressed
+        ldx     #MOUSE_BTN_LEFT         ; Left (only) button is pressed
+@L0:    stx     Buttons
+
+; Check left/right
+
+        lda     Temp                    ; Read joystick #0
+               and     #(JOY::LEFT | JOY::RIGHT)
+        beq     @SkipX                 ;
+
+; We will cheat here and rely on the fact that either the left, OR the right
+; bit can be active
+
+               and     #JOY::RIGHT             ; Check RIGHT bit
+               bne     @Right
+       lda     #$FF
+       tax
+       bne     @AddX                   ; Branch always
+@Right:        lda     #$01
+       ldx     #$00
+
+; Calculate the new X coordinate (--> a/y)
+
+@AddX:  add     XPos
+       tay                             ; Remember low byte
+       txa
+       adc     XPos+1
+       tax
+
+; Limit the X coordinate to the bounding box
+
+       cpy     XMin
+       sbc     XMin+1
+       bpl     @L1
+               ldy     XMin
+               ldx     XMin+1
+       jmp     @L2
+@L1:   txa
+
+       cpy     XMax
+       sbc     XMax+1
+       bmi     @L2
+       ldy     XMax
+       ldx     XMax+1
+@L2:   sty     XPos
+       stx     XPos+1
+
+; Move the mouse pointer to the new X pos
+
+        tya
+        jsr     CMOVEX
+
+; Calculate the Y movement vector
+
+@SkipX: lda     Temp                    ; Read joystick #0
+               and     #(JOY::UP | JOY::DOWN)  ; Check up/down
+        beq     @SkipY                 ;
+
+; We will cheat here and rely on the fact that either the up, OR the down
+; bit can be active
+
+               lsr     a                       ; Check UP bit
+               bcc     @Down
+       lda     #$FF
+       tax
+       bne     @AddY
+@Down: lda     #$01
+       ldx     #$00
+
+; Calculate the new Y coordinate (--> a/y)
+
+@AddY:         add     YPos
+       tay                             ; Remember low byte
+       txa
+       adc     YPos+1
+       tax
+
+; Limit the Y coordinate to the bounding box
+
+       cpy     YMin
+       sbc     YMin+1
+       bpl     @L3
+               ldy     YMin
+               ldx     YMin+1
+       jmp     @L4
+@L3:   txa
+
+       cpy     YMax
+       sbc     YMax+1
+       bmi     @L4
+       ldy     YMax
+       ldx     YMax+1
+@L4:   sty     YPos
+       stx     YPos+1
+
+; Move the mouse pointer to the new X pos
+
+        tya
+        jmp     CMOVEY
+
+; Done
+
+@SkipY: rts
+
index 20f0827f6f662d92ae02243540c3344b18c56122..0f3c2d35f81a67d10c62df6d7504f270af7bc736 100644 (file)
@@ -5,11 +5,11 @@
 ;
 
        .export         _exit
-       .import         initlib, donelib, condes
+       .import         initlib, donelib, callirq
                .import         zerobss, push0
        .import         callmain
         .import         RESTOR, BSOUT, CLRCH
-       .import         __IRQFUNC_TABLE__, __IRQFUNC_COUNT__
+       .import         __IRQFUNC_COUNT__
        .import         __RAM_START__, __RAM_SIZE__     ; Linker generated
 
         .include        "zeropage.inc"
@@ -142,10 +142,7 @@ L2:        lda     zpsave,x
 
 IRQStub:
        cld                             ; Just to be sure
-       ldy     #<(__IRQFUNC_COUNT__*2)
-               lda     #<__IRQFUNC_TABLE__
-       ldx     #>__IRQFUNC_TABLE__
-       jsr     condes                  ; Call the functions
+               jsr     callirq                 ; Call the functions
                jmp     IRQInd                  ; Jump to the saved IRQ vector
 
 ; ------------------------------------------------------------------------
index 829aed4c7a7d4433dac9ad9a46b66c93679eea7b..b8918533562e8860b6b97f629f69dd56d3ca8067 100644 (file)
@@ -6,11 +6,11 @@
 
        .export         _exit
 
-       .import         _clrscr, initlib, donelib, condes
+       .import         _clrscr, initlib, donelib, callirq_y
        .import         push0, callmain
        .import         __CHARRAM_START__, __CHARRAM_SIZE__, __VIDRAM_START__
        .import         __BSS_RUN__, __BSS_SIZE__, __EXTZP_RUN__
-       .import         __IRQFUNC_TABLE__, __IRQFUNC_COUNT__
+       .import         __IRQFUNC_COUNT__
        .import         scnkey, UDTIM
 
        .include        "zeropage.inc"
@@ -540,9 +540,7 @@ irq:    pha
 
                ldy     irqcount
         beq     irqskip
-               lda     #<__IRQFUNC_TABLE__
-       ldx     #>__IRQFUNC_TABLE__
-       jsr     condes                  ; Call the functions
+               jsr     callirq_q               ; Call the functions
 
 ; Done with chained IRQ handlers, check the TPI for IRQs and handle them
 
index c6b073bb0cc550d8204ac28e851045357e9929ed..8cd91d726a5c6ba16e6b0cca1d891130f935ea76 100644 (file)
@@ -6,10 +6,10 @@
 
        .export         _exit, BRKVec
 
-       .import         condes, initlib, donelib
+       .import         callirq_y, initlib, donelib
        .import         push0, callmain
        .import         __BSS_RUN__, __BSS_SIZE__, __EXTZP_RUN__
-       .import         __IRQFUNC_TABLE__, __IRQFUNC_COUNT__
+       .import         __IRQFUNC_COUNT__
        .import         scnkey, UDTIM
 
        .include        "zeropage.inc"
@@ -435,8 +435,8 @@ irq:    pha
         lda     ExecReg
         sta     IndReg                  ; Be sure to address our segment
        tsx
-               lda     $105,x                  ; Get the flags from the stack
-       and     #$10                    ; Test break flag
+               lda     $105,x                  ; Get the flags from the stack
+       and     #$10                    ; Test break flag
                bne     dobrk
 
 ; It's an IRQ
@@ -447,9 +447,7 @@ irq:    pha
 
                ldy     irqcount
         beq     irqskip
-               lda     #<__IRQFUNC_TABLE__
-       ldx     #>__IRQFUNC_TABLE__
-       jsr     condes                  ; Call the functions
+               jsr     callirq_y               ; Call the functions
 
 ; Done with chained IRQ handlers, check the TPI for IRQs and handle them
 
index b962abd967cc70a66a1e6e09b604982444bd303e..5b2757ea34f18f4163ca01bbe9264ba0a56d0fe1 100644 (file)
@@ -7,9 +7,9 @@
        .export         _exit
         .export         brk_jmp
 
-       .import         condes, initlib, donelib
+       .import         callirq_y, initlib, donelib
        .import         push0, callmain, zerobss
-       .import         __IRQFUNC_TABLE__, __IRQFUNC_COUNT__
+       .import         __IRQFUNC_COUNT__
 
         .include        "zeropage.inc"
        .include        "plus4.inc"
@@ -59,7 +59,7 @@ L1:   lda     sp,x
 ; usable RAM.
 
                tsx
-               stx     spsave          ; save system stk ptr
+               stx     spsave          ; save system stk ptr
 
         lda     #<$FD00
         sta     sp
@@ -96,7 +96,7 @@ L1:   lda     sp,x
 
 ; Back from main (this is also the _exit entry). Run module destructors.
 
-_exit:         pha                     ; Save the return code
+_exit:         pha                     ; Save the return code
        lda     #0
         sta     irqcount        ; Disable custom IRQ handlers
         jsr    donelib         ; Run module destructors
@@ -153,9 +153,7 @@ IRQ:    cld                 ; Just to be sure
 
        ldy     irqcount
        beq     @L1
-               lda     #<__IRQFUNC_TABLE__
-       ldx     #>__IRQFUNC_TABLE__
-       jsr     condes                  ; Call the IRQ functions
+        jsr     callirq_y       ; Call the IRQ functions
 
 ; Since the ROM handler will end with an RTI, we have to fake an IRQ return
 ; on stack, so we get control of the CPU after the ROM handler and can switch
@@ -165,10 +163,10 @@ IRQ:    cld                       ; Just to be sure
         pha
         lda     #<irq_ret
         pha
-               php                     ; Push faked IRQ frame on stack
-       pha                     ; Push faked A register
-       pha                     ; Push faked X register
-       pha                     ; Push faked Y register
+               php                     ; Push faked IRQ frame on stack
+       pha                     ; Push faked A register
+       pha                     ; Push faked X register
+       pha                     ; Push faked Y register
         sta     ENABLE_ROM      ; Switch to ROM
         jmp     (IRQVec)        ; Jump indirect to kernal irq handler