1
0
mirror of https://github.com/cc65/cc65.git synced 2025-08-08 06:25:17 +00:00

Updated the cx16 library to the Commander X16 Kernal's prerelease 35.

This commit is contained in:
Greg King
2019-12-25 10:56:32 -05:00
parent cab4910a7d
commit 3fa253d31f
31 changed files with 508 additions and 271 deletions

View File

@@ -6,9 +6,40 @@
.if .def(__CX16__) .if .def(__CX16__)
; CX16 extended jump table ; CX16 extended jump table
GETJOY := $FF06 FB_INIT := $FEF6
MOUSE := $FF09 FB_GET_INFO := $FEF9
SCRMOD := $FF5F FB_SET_PALETTE := $FEFC
FB_CURSOR_POSITION := $FEFF
FB_CURSOR_NEXT_LINE := $FF02
FB_GET_PIXEL := $FF05
FB_GET_PIXELS := $FF08
FB_SET_PIXEL := $FF0B
FB_SET_PIXELS := $FF0E
FB_SET_8_PIXELS := $FF11
FB_SET_8_PIXELS_OPAQUE := $FF14
FB_FILL_PIXELS := $FF17
FB_FILTER_PIXELS := $FF1A
FB_MOVE_PIXELS := $FF1D
GRAPH_INIT := $FF20
GRAPH_CLEAR := $FF23
GRAPH_SET_WINDOW := $FF26
GRAPH_SET_COLORS := $FF29
GRAPH_DRAW_LINE := $FF2C
GRAPH_DRAW_RECT := $FF2F
GRAPH_MOVE_RECT := $FF32
GRAPH_DRAW_OVAL := $FF35
GRAPH_DRAW_IMAGE := $FF38
GRAPH_SET_FONT := $FF3B
GRAPH_GET_CHAR_SIZE := $FF3E
GRAPH_PUT_CHAR := $FF41
RESTORE_BASIC := $FF47
CLOCK_SET_DATE_TIME := $FF4D
CLOCK_GET_DATE_TIME := $FF50
JOYSTICK_SCAN := $FF53
JOYSTICK_GET := $FF56
SCRMOD := $FF5F
MOUSE_CONFIG := $FF68
MOUSE_GET := $FF6B
.endif .endif
.if .def(__C128__) .if .def(__C128__)
@@ -21,6 +52,9 @@
.if .def(__C128__) || .def(__CX16__) .if .def(__C128__) || .def(__CX16__)
; Extended jump table ; Extended jump table
CLSALL := $FF4A CLSALL := $FF4A
LKUPLA := $FF59
LKUPSA := $FF5C
PFKEY := $FF65
JSRFAR := $FF6E JSRFAR := $FF6E
INDFET := $FF74 INDFET := $FF74
INDSTA := $FF77 INDSTA := $FF77

View File

@@ -1,5 +1,5 @@
; ;
; CX16 definitions ; CX16 r35 definitions
; ;
; --------------------------------------------------------------------------- ; ---------------------------------------------------------------------------
@@ -44,11 +44,128 @@
; --------------------------------------------------------------------------- ; ---------------------------------------------------------------------------
; Zero page ; Zero page
; GEOS and graphics pseudo-registers
.struct gREG
.org $02
.union
r0 .word
.struct
r0L .byte
r0H .byte
.endstruct
.endunion
.union
r1 .word
.struct
r1L .byte
r1H .byte
.endstruct
.endunion
.union
r2 .word
.struct
r2L .byte
r2H .byte
.endstruct
.endunion
.union
r3 .word
.struct
r3L .byte
r3H .byte
.endstruct
.endunion
.union
r4 .word
.struct
r4L .byte
r4H .byte
.endstruct
.endunion
.union
r5 .word
.struct
r5L .byte
r5H .byte
.endstruct
.endunion
.union
r6 .word
.struct
r6L .byte
r6H .byte
.endstruct
.endunion
.union
r7 .word
.struct
r7L .byte
r7H .byte
.endstruct
.endunion
.union
r8 .word
.struct
r8L .byte
r8H .byte
.endstruct
.endunion
.union
r9 .word
.struct
r9L .byte
r9H .byte
.endstruct
.endunion
.union
r10 .word
.struct
r10L .byte
r10H .byte
.endstruct
.endunion
.union
r11 .word
.struct
r11L .byte
r11H .byte
.endstruct
.endunion
.union
r12 .word
.struct
r12L .byte
r12H .byte
.endstruct
.endunion
.union
r13 .word
.struct
r13L .byte
r13H .byte
.endstruct
.endunion
.union
r14 .word
.struct
r14L .byte
r14H .byte
.endstruct
.endunion
.union
r15 .word
.struct
r15L .byte
r15H .byte
.endstruct
.endunion
.endstruct
; Kernal ; Kernal
FNAM := $84 ; Pointer to filename FNAM := $84 ; Pointer to filename
KTEMP2 := $86 ; 2 bytes for temporary storage KTEMP2 := $86 ; 2 bytes for temporary storage
SCREEN_PTR := $88 ; Pointer to current row on text screen (16 bits) IMPARM := $88 ; Pointer for PRIMM function
IMPARM := $8A ; Pointer for PRIMM function SCREEN_PTR := $90 ; Pointer to current row on text screen (16 bits)
; BASIC ; BASIC
TXTPTR := $EE ; Pointer into BASIC source code TXTPTR := $EE ; Pointer into BASIC source code
@@ -58,41 +175,27 @@ TXTPTR := $EE ; Pointer into BASIC source code
BASIC_BUF := $0200 ; Location of command-line BASIC_BUF := $0200 ; Location of command-line
BASIC_BUF_LEN = 81 ; Maximum length of command-line BASIC_BUF_LEN = 81 ; Maximum length of command-line
CURS_COLOR := $027E ; Color under the cursor STATUS := $0275 ; Status from previous I/O operation
CHARCOLOR := $0286 ; Cursor's color nybbles (high: background, low: foreground) IN_DEV := $0279 ; Current input device number
STATUS := $0287 ; Status from previous I/O operation OUT_DEV := $027A ; Current output device number
IN_DEV := $028E ; Current input device number FNAM_LEN := $027D ; Length of filename
OUT_DEV := $028F ; Current output device number SECADR := $027F ; Secondary address
TIME := $0292 ; 60 Hz. clock (3 bytes, big-endian) DEVNUM := $0280 ; Device number
FNAM_LEN := $0298 ; Length of filename CURS_COLOR := $0373 ; Color under the cursor
SECADR := $029A ; Secondary address CHARCOLOR := $0377 ; Cursor's color nybbles (high: background, low: foreground)
DEVNUM := $029B ; Device number RVS := $0378 ; Reverse flag
KEY_COUNT := $029E ; Number of keys in input buffer CURS_FLAG := $037C ; 1 = cursor off
RVS := $029F ; Reverse flag CURS_BLINK := $037D ; Blink counter
CURS_FLAG := $02A3 ; 1 = cursor off CURS_CHAR := $037E ; Character under the cursor
CURS_BLINK := $02A4 ; Blink counter CURS_STATE := $037F ; Cursor blink state
CURS_CHAR := $02A5 ; Character under the cursor CURS_X := $0381 ; Cursor column
CURS_STATE := $02A6 ; Cursor blink state CURS_Y := $0384 ; Cursor row
CURS_X := $02A8 ; Cursor column LLEN := $0387 ; Line length
CURS_Y := $02AB ; Cursor row NLINES := $0388 ; Number of screen lines
LLEN := $02AE ; Line length
NLINES := $02AF ; Number of screen lines
JOY1 := $02BC ; 3 bytes of NES/SNES gamepad data
JOY2 := $02BF
; BASIC ; BASIC
VARTAB := $02DD ; Pointer to start of BASIC variables VARTAB := $03E3 ; Pointer to start of BASIC variables
MEMSIZE := $02E5 ; Pointer to highest BASIC RAM location (+1) MEMSIZE := $03EB ; Pointer to highest BASIC RAM location (+1)
; Kernal mouse
MSEPAR := $0371 ; mouse: $8x=sprite on, 1/2: scale
MOUSEL := $0372 ; min. x co-ordinate
MOUSER := $0374 ; max. x co-ordinate
MOUSET := $0376 ; min. y co-ordinate
MOUSEB := $0378 ; max. y co-ordinate
MOUSEX := $037A ; x co-ordinate
MOUSEY := $037C ; y co-ordinate
MOUSEBT := $037E ; buttons (bits 2: middle, 1: right, 0: left)
; --------------------------------------------------------------------------- ; ---------------------------------------------------------------------------
; Vector and other locations ; Vector and other locations
@@ -141,8 +244,13 @@ NMIVec := $0318
SPR_COLLIDED = %00000100 SPR_COLLIDED = %00000100
UART_IRQ = %00001000 UART_IRQ = %00001000
.endenum .endenum
; Internal RAM and registers ; Internal RAM and registers
VRAM := $000000
.struct
.org $000000
VRAM .res $020000 ; 128 Kibibytes
.endstruct
.scope COMPOSER ; Display composer .scope COMPOSER ; Display composer
.struct .struct
.org $0F0000 .org $0F0000
@@ -226,15 +334,29 @@ NMIVec := $0318
.scope SPRITE .scope SPRITE
.struct .struct
.org $0F4000 .org $0F4000
CTRL .byte ; Enables sprites CTRL .byte ; Enables sprite engine
COLLISION .byte COLLISION .byte
.endstruct .endstruct
.struct ATTRIB ; Sprite attributes
.org $0F5000
ADDR .addr ; Address and color mode
XX .word
YY .word
Z_FLIP .byte
SIZE_PAL .byte
.endstruct
.enum FLIP .enum FLIP
NONE = 0 NONE = 0
HORIZ HORIZ
VERT VERT
BOTH BOTH
.endenum .endenum
.enum DEPTH
DISABLE = 0 << 2
CANVAS = 1 << 2
LAYER0 = 2 << 2
LAYER1 = 3 << 2
.endenum
.enum ; Sprite geometry .enum ; Sprite geometry
WIDTH8 = 0 << 4 WIDTH8 = 0 << 4
WIDTH16 = 1 << 4 WIDTH16 = 1 << 4
@@ -247,13 +369,6 @@ NMIVec := $0318
COLORS16 = 0 << 7 COLORS16 = 0 << 7
COLORS256 = 1 << 7 COLORS256 = 1 << 7
.endenum .endenum
.enum DEPTH
DISABLE = 0 << 2
CANVAS = 1 << 2
LAYER0 = 2 << 2
LAYER1 = 3 << 2
.endenum
ATTRIB := $0F5000 ; Sprite attributes
.endscope .endscope
AUDIO := $0F6000 AUDIO := $0F6000
.scope SPI .scope SPI
@@ -334,3 +449,15 @@ NMIVec := $0318
KEYMAP .byte ; Current keyboard layout number (Read-Only) KEYMAP .byte ; Current keyboard layout number (Read-Only)
DETECT .byte 2 ; If is "16" string, then running on emulator (RO) DETECT .byte 2 ; If is "16" string, then running on emulator (RO)
.endstruct .endstruct
; ---------------------------------------------------------------------------
; Banked RAM and ROM
KEY_COUNT := $A00A ; (bank 0) Number of keys in input buffer
TIMER := $A03E ; (bank 0) 60 Hz. timer (3 bytes, big-endian)
.struct BANK
.org $A000
RAM .res $2000 ; 8 Kibibyte window into 512 Kibibytes or 2048 Kibibytes
ROM .res $4000 ; 16 Kibibyte window into 128 Kibibytes
.endstruct

View File

@@ -6,7 +6,7 @@ SYMBOLS {
__HIMEM__: type = weak, value = $9F00; __HIMEM__: type = weak, value = $9F00;
} }
MEMORY { MEMORY {
ZP: file = "", start = $0002, size = $0080 - $0002, define = yes; ZP: file = "", start = $0022, size = $0080 - $0022, define = yes;
LOADADDR: file = %O, start = %S - 2, size = $0002; LOADADDR: file = %O, start = %S - 2, size = $0002;
MAIN: file = %O, start = %S, size = __HIMEM__ - %S; MAIN: file = %O, start = %S, size = __HIMEM__ - %S;
} }

View File

@@ -11,13 +11,13 @@ SYMBOLS {
__BANKRAMSIZE__: type = weak, value = $2000; # 8K banked RAM __BANKRAMSIZE__: type = weak, value = $2000; # 8K banked RAM
} }
MEMORY { MEMORY {
ZP: file = "", define = yes, start = $0002, size = $0080 - $0002; ZP: file = "", define = yes, start = $0022, size = $0080 - $0022;
LOADADDR: file = %O, start = %S - 2, size = $0002; LOADADDR: file = %O, start = %S - 2, size = $0002;
HEADER: file = %O, define = yes, start = %S, size = $000D; HEADER: file = %O, define = yes, start = %S, size = $000D;
MAIN: file = %O, define = yes, start = __HEADER_LAST__, size = __HIMEM__ - __HEADER_LAST__; MAIN: file = %O, define = yes, start = __HEADER_LAST__, size = __HIMEM__ - __HEADER_LAST__;
BSS: file = "", start = __ONCE_RUN__, size = __HIMEM__ - __ONCE_RUN__ - __STACKSIZE__; BSS: file = "", start = __ONCE_RUN__, size = __HIMEM__ - __ONCE_RUN__ - __STACKSIZE__;
BRAM00ADDR: file = "%O.00", start = __BANKRAMSTART__ - 2, size = $0002; # BRAM00ADDR: file = "%O.00", start = __BANKRAMSTART__ - 2, size = $0002;
BRAM00: file = "%O.00", start = __BANKRAMSTART__, size = __BANKRAMSIZE__; # BRAM00: file = "%O.00", start = __BANKRAMSTART__, size = __BANKRAMSIZE__;
BRAM01ADDR: file = "%O.01", start = __BANKRAMSTART__ - 2, size = $0002; BRAM01ADDR: file = "%O.01", start = __BANKRAMSTART__ - 2, size = $0002;
BRAM01: file = "%O.01", start = __BANKRAMSTART__, size = __BANKRAMSIZE__; BRAM01: file = "%O.01", start = __BANKRAMSTART__, size = __BANKRAMSIZE__;
BRAM02ADDR: file = "%O.02", start = __BANKRAMSTART__ - 2, size = $0002; BRAM02ADDR: file = "%O.02", start = __BANKRAMSTART__ - 2, size = $0002;
@@ -62,8 +62,8 @@ SEGMENTS {
INIT: load = MAIN, type = rw; INIT: load = MAIN, type = rw;
ONCE: load = MAIN, type = ro, define = yes; ONCE: load = MAIN, type = ro, define = yes;
BSS: load = BSS, type = bss, define = yes; BSS: load = BSS, type = bss, define = yes;
BRAM00ADDR: load = BRAM00ADDR, type = ro, optional = yes; # BRAM00ADDR: load = BRAM00ADDR, type = ro, optional = yes;
BANKRAM00: load = BRAM00, type = rw, define = yes, optional = yes; # BANKRAM00: load = BRAM00, type = rw, define = yes, optional = yes;
BRAM01ADDR: load = BRAM01ADDR, type = ro, optional = yes; BRAM01ADDR: load = BRAM01ADDR, type = ro, optional = yes;
BANKRAM01: load = BRAM01, type = rw, define = yes, optional = yes; BANKRAM01: load = BRAM01, type = rw, define = yes, optional = yes;
BRAM02ADDR: load = BRAM02ADDR, type = ro, optional = yes; BRAM02ADDR: load = BRAM02ADDR, type = ro, optional = yes;

View File

@@ -8,7 +8,7 @@ SYMBOLS {
__HIMEM__: type = weak, value = $9F00; __HIMEM__: type = weak, value = $9F00;
} }
MEMORY { MEMORY {
ZP: file = "", define = yes, start = $0002, size = $0080 - $0002; ZP: file = "", define = yes, start = $0022, size = $0080 - $0022;
LOADADDR: file = %O, start = %S - 2, size = $0002; LOADADDR: file = %O, start = %S - 2, size = $0002;
HEADER: file = %O, define = yes, start = %S, size = $000D; HEADER: file = %O, define = yes, start = %S, size = $000D;
MAIN: file = %O, define = yes, start = __HEADER_LAST__, size = __HIMEM__ - __HEADER_LAST__; MAIN: file = %O, define = yes, start = __HEADER_LAST__, size = __HIMEM__ - __HEADER_LAST__;

View File

@@ -62,7 +62,7 @@ Special locations:
<tag/Bank RAM/ <tag/Bank RAM/
Bank RAM is located at &dollar;A000 - &dollar;BFFF. It's an eight-Kibibyte Bank RAM is located at &dollar;A000 - &dollar;BFFF. It's an eight-Kibibyte
window into a half Mibibyte or two Mibibytes of banked RAM. window into a half Mebibyte or two Mebibytes of banked RAM.
<tag/Bank ROM/ <tag/Bank ROM/
Bank ROM is located at &dollar;C000 - &dollar;FFFF. It's a sixteen-Kibibyte Bank ROM is located at &dollar;C000 - &dollar;FFFF. It's a sixteen-Kibibyte
@@ -229,8 +229,9 @@ point to <tt/cX16-std.joy (cx16_std_joy)/.
<descrip> <descrip>
<tag><tt/cX16-std.joy (cX16_std_joy)/</tag> <tag><tt/cX16-std.joy (cX16_std_joy)/</tag>
Supports up to two NES (and SNES) controllers connected to the joystick ports Supports up to two NES (and SNES) controllers connected to the joystick ports
of the CX16. It reads the four directions, and the A, B, Select, and Start of the CX16. It reads the four directions, and the <bf/A/, <bf/B/,
buttons. Buttons A and B are the primary and secondary fire buttons. <bf/Select/, and <bf/Start/ buttons. Buttons <bf/A/ and <bf/B/ are
the first and second fire buttons.
</descrip><p> </descrip><p>
@@ -243,6 +244,9 @@ point to <tt/cX16-std.mou (cx16_std_mou)/.
<tag><tt/cX16-std.mou (cX16_std_mou)/</tag> <tag><tt/cX16-std.mou (cX16_std_mou)/</tag>
Supports a standard 3-button mouse connected to the PS/2 mouse port of the Supports a standard 3-button mouse connected to the PS/2 mouse port of the
Commander X16. Commander X16.
Currently (r35), this driver doesn't support <tt/mouse_move()/
and <tt/mouse_setbox()/.
</descrip><p> </descrip><p>

View File

@@ -168,7 +168,7 @@ unsigned char __fastcall__ kbrepeat (unsigned char mode);
#if !defined(__CBM610__) && !defined(__PET__) #if !defined(__CBM610__) && !defined(__PET__)
void waitvsync (void); void waitvsync (void);
/* Wait for the start of the next frame */ /* Wait for the start of the next video field. */
#endif #endif
/*****************************************************************************/ /*****************************************************************************/

View File

@@ -44,7 +44,19 @@
/* Additional output character codes */
#define CH_COLOR_SWAP 0x01
#define CH_UNDERLINE 0x04
#define CH_BOLD 0x06
#define CH_BACKSPACE 0x08
#define CH_ITALIC 0x0B
#define CH_OUTLINE 0x0C
#define CH_FONT_ISO 0x0F
#define CH_FONT_PET 0x8F
/* Additional key defines */ /* Additional key defines */
#define CH_SHIFT_TAB 0x18
#define CH_HELP 0x84
#define CH_F1 0x85 #define CH_F1 0x85
#define CH_F2 0x89 #define CH_F2 0x89
#define CH_F3 0x86 #define CH_F3 0x86
@@ -163,7 +175,7 @@ struct __emul {
}; };
#define EMULATOR (*(volatile struct __emul)0x9FB0) #define EMULATOR (*(volatile struct __emul)0x9FB0)
/* An array window into the half Mibibyte or two Mibibytes of banked RAM */ /* An array window into the half Mebibyte or two Mebibytes of banked RAM */
#define BANK_RAM ((unsigned char[0x2000])0xA000) #define BANK_RAM ((unsigned char[0x2000])0xA000)

View File

@@ -1,19 +1,28 @@
; ;
; Ullrich von Bassewitz, 21.09.1998 ; 1998-09-21, Ullrich von Bassewitz
; 2019-12-25, Greg King
; ;
; clock_t clock (void); ; clock_t clock (void);
; ;
.include "cbm.inc"
.export _clock .export _clock
.importzp sreg .importzp sreg
.include "cbm.inc"
.macpack cpu
.proc _clock .proc _clock
lda #0 ; Byte 3 is always zero ; Some accelerator adaptors have CMOS ICs.
sta sreg+1
.if (.cpu & ::CPU_ISET_65SC02)
stz sreg + 1
.else
lda #$00 ; Byte 3 always is zero
sta sreg + 1
.endif
jsr RDTIM jsr RDTIM
sty sreg sty sreg
rts rts

View File

@@ -1,10 +1,6 @@
; ;
; Ullrich von Bassewitz, 26.10.2000
;
; Screen size variables ; Screen size variables
; ;
.export screensize
.import SCREEN .import SCREEN
.export screensize := SCREEN
screensize := SCREEN

View File

@@ -1,7 +1,7 @@
; ;
; 2019-09-16, Greg King ; 2019-12-21, Greg King
; ;
; This module supplies the load addresses that are expected ; This module supplies some load addresses that are expected
; by a Commander X16 in the first two bytes of banked RAM load files. ; by a Commander X16 in the first two bytes of banked RAM load files.
; ;
@@ -9,9 +9,11 @@
; this module to get included into the output files. ; this module to get included into the output files.
.export __BANKRAMADDR__: abs = 1 .export __BANKRAMADDR__: abs = 1
.if 0 ; bank 0 is used by Kernal
.segment "BRAM00ADDR" .segment "BRAM00ADDR"
.addr *+2 .addr *+2
.endif
.segment "BRAM01ADDR" .segment "BRAM01ADDR"

View File

@@ -1,5 +1,5 @@
; ;
; 2019-10-01, Greg King ; 2019-12-22, Greg King
; ;
; char cgetc (void); ; char cgetc (void);
; /* Return a character from the keyboard. */ ; /* Return a character from the keyboard. */
@@ -7,13 +7,13 @@
.export _cgetc .export _cgetc
.import cursor, GETIN .import _kbhit, cursor, GETIN
.include "cx16.inc" .include "cx16.inc"
.macpack generic .macpack generic
_cgetc: ldx KEY_COUNT ; Get number of characters _cgetc: jsr _kbhit
bnz L3 ; Jump if there are already chars waiting bnz L3 ; Jump if there are already chars waiting
; Switch the cursor on if wanted. ; Switch the cursor on if wanted.
@@ -22,7 +22,7 @@ _cgetc: ldx KEY_COUNT ; Get number of characters
tay tay
lda cursor lda cursor
jsr setcursor jsr setcursor
L1: lda KEY_COUNT L1: jsr _kbhit
bze L1 ; Wait for key bze L1 ; Wait for key
tya tya
eor #%00000001 ; (Cursor flag uses negative logic) eor #%00000001 ; (Cursor flag uses negative logic)

36
libsrc/cx16/clock.s Normal file
View File

@@ -0,0 +1,36 @@
;
; 1998-09-21, Ullrich von Bassewitz
; 2019-12-25, Greg King
;
; clock_t clock (void);
;
.constructor initclock
.export _clock
.import SETTIM, RDTIM
.importzp sreg
; clock() counts the amount of time that the process has run.
; Therefore, reset it when the program begins.
.proc initclock
lda #$00
tax
tay
jmp SETTIM
.endproc
.proc _clock
stz sreg + 1 ; Byte 3 always is zero
jsr RDTIM
sty sreg
rts
.endproc

View File

@@ -1,5 +1,5 @@
; ;
; Start-up code for cc65 (CX16 version) ; Start-up code for cc65 (CX16 r35 version)
; ;
.export _exit .export _exit
@@ -46,7 +46,7 @@ _exit:
jsr donelib jsr donelib
.if 0 ; We no longer need to preserve zero-page space for cc65's variables. .if 0 ; We don't need to preserve zero-page space for cc65's variables.
; Copy back the zero-page stuff. ; Copy back the zero-page stuff.
ldx #zpspace-1 ldx #zpspace-1
@@ -83,14 +83,14 @@ init:
and #<~$07 and #<~$07
sta VIA1::PRB sta VIA1::PRB
; Change to the first RAM bank. ; Change to the second RAM bank.
lda VIA1::PRA2 lda VIA1::PRA2
sta ramsave ; Save the current RAM bank number sta ramsave ; Save the current RAM bank number
lda #$00 ; Choose RAM bank zero lda #$01
sta VIA1::PRA2 sta VIA1::PRA2
.if 0 ; We no longer need to preserve zero-page space for cc65's variables. .if 0 ; We don't need to preserve zero-page space for cc65's variables.
; Save the zero-page locations that we need. ; Save the zero-page locations that we need.
ldx #zpspace-1 ldx #zpspace-1
@@ -107,7 +107,7 @@ L1: lda sp,x
sta sp sta sp
stx sp+1 ; Set argument stack ptr stx sp+1 ; Set argument stack ptr
; Switch to the second charset. ; Switch to the lower/UPPER PetSCII charset.
lda #$0E lda #$0E
jsr CHROUT jsr CHROUT

View File

@@ -1,5 +1,5 @@
; ;
; 2019-09-20, Greg King ; 2019-12-22, Greg King
; ;
; unsigned char get_tv (void); ; unsigned char get_tv (void);
; /* Return the video mode the machine is using. */ ; /* Return the video mode the machine is using. */
@@ -11,9 +11,6 @@
.proc _get_tv .proc _get_tv
php
sei ; Don't let interrupts interfere
; Point to the video output register. ; Point to the video output register.
stz VERA::CTRL ; Use port 0 stz VERA::CTRL ; Use port 0
@@ -25,7 +22,6 @@
sty VERA::ADDR+2 sty VERA::ADDR+2
lda VERA::DATA0 lda VERA::DATA0
plp ; Re-enable interrupts
and #$07 ; Get the type of output signal and #$07 ; Get the type of output signal
rts rts
.endproc .endproc

View File

@@ -1,8 +1,8 @@
; ;
; Standard joystick driver for the CX16. ; Standard joystick driver for the CX16.
; May be installed multiple times when statically linked to the application. ; May be installed multiple times when statically linked to an application.
; ;
; 2019-11-15 Greg King ; 2019-12-24, Greg King
; ;
.include "joy-kernel.inc" .include "joy-kernel.inc"
@@ -14,6 +14,8 @@
.macpack generic .macpack generic
.macpack module .macpack module
.importzp tmp1
; ------------------------------------------------------------------------ ; ------------------------------------------------------------------------
; Header. Includes jump table ; Header. Includes jump table
@@ -75,51 +77,21 @@ COUNT: lda #<JOY_COUNT
; ------------------------------------------------------------------------ ; ------------------------------------------------------------------------
; READ: Read a particular joystick passed in .A . ; READ: Read a particular joystick passed in .A .
READ: php READ: and #%00000001
bit #JOY_COUNT - $01 jsr JOYSTICK_GET
sei sta tmp1
bnz pad2 txa
bit #%00001110 ; Is it NES or SNES controller?
bze nes
; Read game pad 1 asl tmp1 ; Get SNES's B button
pad1: ldy JOY1 ; Allow JOY1 to be reread between interrupts
sty JOY1 + 2
lda JOY1 + 1
bit #%00001110
bze nes1
asl JOY1 + 2 ; Get SNES's B button
ror a ; Put it next to the A button ror a ; Put it next to the A button
asl JOY1 + 2 ; Drop SNES's Y button asl tmp1 ; Drop SNES's Y button
asl a ; Get back the B button asl a ; Get back the B button
ror JOY1 + 2 ror tmp1
asl a ; Get SNES's A button asl a ; Get SNES's A button
ror JOY1 + 2 ; Make byte look like NES pad ror tmp1 ; Make byte look like NES pad
nes1: lda JOY1 + 2 nes: lda tmp1 ; The controllers give zeroes for "pressed"
plp eor #%11111111 ; We want ones for "pressed"
eor #%11111111 ; (The controllers use negative logic)
rts
; Read game pad 2
pad2: ldy JOY2
sty JOY2 + 2
lda JOY2 + 1
bit #%00001110
bze nes2
asl JOY2 + 2
ror a
asl JOY2 + 2
asl a
ror JOY2 + 2
asl a
ror JOY2 + 2
nes2: lda JOY2 + 2
plp
eor #%11111111
rts rts

View File

@@ -1,5 +1,5 @@
; ;
; 2019-11-14, Greg King ; 2019-12-22, Greg King
; ;
; Link an interrupt handler if joysticks are used by a program. ; Link an interrupt handler if joysticks are used by a program.
; ;
@@ -14,7 +14,7 @@ joy_libref:
lda VERA::IRQ_FLAGS lda VERA::IRQ_FLAGS
lsr a lsr a
bcc not_vsync bcc not_vsync
jsr GETJOY ; Bit-bang game controllers jsr JOYSTICK_SCAN ; Bit-bang game controllers
clc ; Let other Jiffy handlers run clc ; Let other Jiffy handlers run
not_vsync: not_vsync:
rts rts

View File

@@ -1,5 +1,5 @@
; ;
; 2019-11-06, Greg King ; 2019-12-22, Greg King
; ;
; unsigned char kbhit (void); ; unsigned char kbhit (void);
; /* Returns non-zero (true) if a typed character is waiting. */ ; /* Returns non-zero (true) if a typed character is waiting. */
@@ -11,7 +11,10 @@
.proc _kbhit .proc _kbhit
ldy VIA1::PRA2 ; (KEY_COUNT is in RAM bank 0)
stz VIA1::PRA2
lda KEY_COUNT ; Get number of characters lda KEY_COUNT ; Get number of characters
sty VIA1::PRA2
tax ; High byte of return (only its zero/nonzero ... tax ; High byte of return (only its zero/nonzero ...
rts ; ... state matters) rts ; ... state matters)
.endproc .endproc

View File

@@ -1,60 +1,94 @@
; ;
; 2019-11-05, Greg King ; 2019-12-22, Greg King
; ;
; CX16 Kernal functions ; CX16 Kernal functions
; ;
.include "cbm_kernal.inc" .include "cbm_kernal.inc"
.export GETJOY .export FB_INIT
.export MOUSE .export FB_GET_INFO
.export SCRMOD .export FB_SET_PALETTE
.export FB_CURSOR_POSITION
.export FB_CURSOR_NEXT_LINE
.export FB_GET_PIXEL
.export FB_GET_PIXELS
.export FB_SET_PIXEL
.export FB_SET_PIXELS
.export FB_SET_8_PIXELS
.export FB_SET_8_PIXELS_OPAQUE
.export FB_FILL_PIXELS
.export FB_FILTER_PIXELS
.export FB_MOVE_PIXELS
.export GRAPH_INIT
.export GRAPH_CLEAR
.export GRAPH_SET_WINDOW
.export GRAPH_SET_COLORS
.export GRAPH_DRAW_LINE
.export GRAPH_DRAW_RECT
.export GRAPH_MOVE_RECT
.export GRAPH_DRAW_OVAL
.export GRAPH_DRAW_IMAGE
.export GRAPH_SET_FONT
.export GRAPH_GET_CHAR_SIZE
.export GRAPH_PUT_CHAR
.export RESTORE_BASIC
.export CLOCK_SET_DATE_TIME
.export CLOCK_GET_DATE_TIME
.export JOYSTICK_SCAN
.export JOYSTICK_GET
.export SCRMOD
.export MOUSE_CONFIG
.export MOUSE_GET
.export CLSALL .export CLSALL
.export JSRFAR .export LKUPLA
.export INDFET .export LKUPSA
.export INDSTA .export PFKEY
.export INDCMP .export JSRFAR
.export PRIMM .export INDFET
.export INDSTA
.export INDCMP
.export PRIMM
.export CINT .export CINT
.export IOINIT .export IOINIT
.export RAMTAS .export RAMTAS
.export RESTOR .export RESTOR
.export VECTOR .export VECTOR
.export SETMSG .export SETMSG
.export SECOND .export SECOND
.export TKSA .export TKSA
.export MEMTOP .export MEMTOP
.export MEMBOT .export MEMBOT
.export SCNKEY .export SCNKEY
.export SETTMO .export SETTMO
.export ACPTR .export ACPTR
.export CIOUT .export CIOUT
.export UNTLK .export UNTLK
.export UNLSN .export UNLSN
.export LISTEN .export LISTEN
.export TALK .export TALK
.export READST .export READST
.export SETLFS .export SETLFS
.export SETNAM .export SETNAM
.export OPEN .export OPEN
.export CLOSE .export CLOSE
.export CHKIN .export CHKIN
.export CKOUT .export CKOUT
.export CLRCH .export CLRCH
.export BASIN .export BASIN
.export CHRIN .export CHRIN
.export BSOUT .export BSOUT
.export CHROUT .export CHROUT
.export LOAD .export LOAD
.export SAVE .export SAVE
.export SETTIM .export SETTIM
.export RDTIM .export RDTIM
.export STOP .export STOP
.export GETIN .export GETIN
.export CLALL .export CLALL
.export UDTIM .export UDTIM
.export SCREEN .export SCREEN
.export PLOT .export PLOT
.export IOBASE .export IOBASE

View File

@@ -1,53 +1,63 @@
; ;
; Default mouse callbacks for the CX16 ; Default mouse callbacks for the CX16
; ;
; 2019-11-09, Greg King ; 2019-12-25, Greg King
; ;
; All functions in this module should be interrupt safe ; All functions in this module should be interrupt-safe
; because they might be called from an interrupt handler. ; because they might be called from an interrupt handler.
; ;
.export _mouse_def_callbacks .export _mouse_def_callbacks
.include "cbm_kernal.inc"
.include "cx16.inc" .include "cx16.inc"
; --------------------------------------------------------------------------
; Hide the mouse pointer. Always called with interrupts disabled.
.code msprite:
stz VERA::CTRL ; set address for VERA's data port zero
hide: ldx #$00 ; Don't change sprite's scale lda #<(VERA::SPRITE::ATTRIB::Z_FLIP + 0 * 8)
lda #$00 ; Disable sprite ldx #>(VERA::SPRITE::ATTRIB::Z_FLIP + 0 * 8)
jmp MOUSE ldy #^(VERA::SPRITE::ATTRIB::Z_FLIP + 0 * 8) | VERA::INC0
sta VERA::ADDR
stx VERA::ADDR+1
sty VERA::ADDR+2
rts
; -------------------------------------------------------------------------- ; --------------------------------------------------------------------------
; Show the mouse pointer. Always called with interrupts disabled. ; Hide the mouse pointer.
show: ldx #$00 hide: jsr msprite
lda #<-$01 ; Enable sprite lda VERA::DATA0
jmp MOUSE and #<~VERA::SPRITE::DEPTH::LAYER1
sta VERA::DATA0
rts
; -------------------------------------------------------------------------- ; --------------------------------------------------------------------------
; Prepare to move the mouse pointer. Always called with interrupts disabled. ; Show the mouse pointer.
show: jsr msprite
lda VERA::DATA0
ora #VERA::SPRITE::DEPTH::LAYER1
sta VERA::DATA0
rts
; --------------------------------------------------------------------------
; Prepare to move the mouse pointer.
prep: ; Fall through prep: ; Fall through
; -------------------------------------------------------------------------- ; --------------------------------------------------------------------------
; Draw the mouse pointer. Always called with interrupts disabled. ; Draw the mouse pointer.
draw: ; Fall through draw: ; Fall through
; -------------------------------------------------------------------------- ; --------------------------------------------------------------------------
; Move the mouse pointer X position to the value in .XA . Always called with ; Move the mouse pointer X position to the value in .XA .
; interrupts disabled.
movex: ; Already set by drivers movex: ; Already set by drivers
; Fall through ; Fall through
; -------------------------------------------------------------------------- ; --------------------------------------------------------------------------
; Move the mouse pointer Y position to the value in .XA . Always called with ; Move the mouse pointer Y position to the value in .XA .
; interrupts disabled.
movey: rts ; Already set by drivers movey: rts ; Already set by drivers

View File

@@ -1,7 +1,7 @@
; ;
; Driver for the Commander X16 Kernal's mouse driver. ; Driver for the Commander X16 Kernal's mouse driver.
; ;
; 2019-11-16, Greg King ; 2019-12-25, Greg King
; ;
.include "zeropage.inc" .include "zeropage.inc"
@@ -66,18 +66,16 @@ SCREEN_HEIGHT = 480 - 1
;---------------------------------------------------------------------------- ;----------------------------------------------------------------------------
; Global variables. ; Global variables.
XPos := ptr3 ; Current mouse position, X
YPos := ptr4 ; Current mouse position, Y
.bss .bss
XPos := MOUSEX ; Current mouse position, X Box:
YPos := MOUSEY ; Current mouse position, Y XMin: .res 2 ; X1 value of bounding box
XMax: .res 2 ; X2 value of bounding box
XMin := MOUSEL ; X1 value of bounding box YMin: .res 2 ; Y1 value of bounding box
XMax := MOUSER ; X2 value of bounding box YMax: .res 2 ; Y2 value of bounding box
YMin := MOUSET ; Y1 value of bounding box
YMax := MOUSEB ; Y2 value of bounding box
Box := XMin
Buttons := MOUSEBT ; button status bits
.rodata .rodata
@@ -121,22 +119,22 @@ INSTALL:
bpl @L1 bpl @L1
ldx #$00 ; Don't change sprite's scale ldx #$00 ; Don't change sprite's scale
lda #$01 ; Initiate and show sprite lda #$01 ; Create sprite
jsr MOUSE jsr MOUSE_CONFIG
; Be sure the mouse cursor is invisible, and at the default location. We ; Be sure the mouse cursor is invisible, and at the default location. We
; need to do that here, because the mouse interrupt handler might not set ; need to do that here, because the mouse interrupt handler might not set
; the mouse position if it hasn't changed. ; the mouse position if it hasn't changed.
sei
jsr CHIDE jsr CHIDE
.if 0
lda XPos lda XPos
ldx XPos+1 ldx XPos+1
jsr CMOVEX jsr CMOVEX
lda YPos lda YPos
ldx YPos+1 ldx YPos+1
jsr CMOVEY jsr CMOVEY
cli .endif
; Done, return zero ; Done, return zero
@@ -148,7 +146,10 @@ INSTALL:
; UNINSTALL routine -- is called before the driver is removed from memory. ; UNINSTALL routine -- is called before the driver is removed from memory.
; No return code required (the driver is removed from memory on return). ; No return code required (the driver is removed from memory on return).
UNINSTALL := HIDE ; Hide cursor on exit UNINSTALL: ; Disable mouse on exit
lda #$00
tax
jmp MOUSE_CONFIG
;---------------------------------------------------------------------------- ;----------------------------------------------------------------------------
; HIDE routine -- is called to hide the mouse pointer. The mouse kernel manages ; HIDE routine -- is called to hide the mouse pointer. The mouse kernel manages
@@ -181,6 +182,7 @@ SETBOX: sta ptr1
lda (ptr1) lda (ptr1)
ldy #$01 ldy #$01
php
sei sei
sta XMin sta XMin
lda (ptr1),y lda (ptr1),y
@@ -191,10 +193,12 @@ SETBOX: sta ptr1
iny iny
lda (ptr1),y lda (ptr1),y
sta YMax sta YMax
cli plp
rts rts
;; Note: SETBOX and GETBOX currently have no effect!
;---------------------------------------------------------------------------- ;----------------------------------------------------------------------------
; GETBOX: Return the mouse bounding box. The parameters are passed as they ; GETBOX: Return the mouse bounding box. The parameters are passed as they
; come from the C program, that is, a pointer to a mouse_box struct in .XA . ; come from the C program, that is, a pointer to a mouse_box struct in .XA .
@@ -222,7 +226,10 @@ GETBOX: sta ptr1
; No checks are done to see if the new position is valid (within ; No checks are done to see if the new position is valid (within
; the bounding box or the screen). No return code required. ; the bounding box or the screen). No return code required.
MOVE: sei ; No interrupts ;; Note: This function currently has no effect!
MOVE: php
sei ; No interrupts
sta YPos sta YPos
stx YPos+1 ; New Y position stx YPos+1 ; New Y position
@@ -237,14 +244,16 @@ MOVE: sei ; No interrupts
sta XPos ; New X position sta XPos ; New X position
jsr CMOVEX ; Move the cursor jsr CMOVEX ; Move the cursor
cli ; Allow interrupts plp ; Allow interrupts
rts rts
;---------------------------------------------------------------------------- ;----------------------------------------------------------------------------
; BUTTONS: Return the CBM 1351 button mask in .XA . ; BUTTONS: Return the CBM 1351 button mask in .XA .
BUTTONS: BUTTONS:
lda Buttons ldx #XPos
jsr MOUSE_GET
and #%00000111 and #%00000111
tax tax
lda ButtMask,x lda ButtMask,x
@@ -255,9 +264,9 @@ BUTTONS:
; POS: Return the mouse position in the MOUSE_POS struct pointed to by ptr1. ; POS: Return the mouse position in the MOUSE_POS struct pointed to by ptr1.
; No return code required. ; No return code required.
POS: ldy #MOUSE_POS::XCOORD ; Structure offset POS: jsr BUTTONS
sei ; Disable interrupts POS1: ldy #MOUSE_POS::XCOORD ; Structure offset
lda XPos ; Transfer the position lda XPos ; Transfer the position
sta (ptr1),y sta (ptr1),y
lda XPos+1 lda XPos+1
@@ -267,8 +276,6 @@ POS: ldy #MOUSE_POS::XCOORD ; Structure offset
iny iny
sta (ptr1),y sta (ptr1),y
lda YPos+1 lda YPos+1
cli ; Enable interrupts
iny iny
sta (ptr1),y ; Store last byte sta (ptr1),y ; Store last byte
rts ; Done rts ; Done
@@ -282,20 +289,15 @@ POS: ldy #MOUSE_POS::XCOORD ; Structure offset
; call mouse_pos to initialize the struct pointer, and fill the position ; call mouse_pos to initialize the struct pointer, and fill the position
; fields. ; fields.
INFO: jsr POS INFO: jsr BUTTONS ; Will not touch ptr1
; Fill in the button state
jsr BUTTONS ; Will not touch ptr1
ldy #MOUSE_INFO::BUTTONS ldy #MOUSE_INFO::BUTTONS
sta (ptr1),y sta (ptr1),y
rts jmp POS1
;---------------------------------------------------------------------------- ;----------------------------------------------------------------------------
; IOCTL: Driver defined entry point. The wrapper will pass a pointer to ioctl ; IOCTL: Driver defined entry point. The wrapper will pass a pointer to ioctl
; specific data in ptr1, and the ioctl code in A. ; specific data in ptr1, and the ioctl code in A.
; Must return an error code in .XA . ; Must return an error code in .XA .
;
IOCTL: lda #<MOUSE_ERR_INV_IOCTL ; We don't support ioctls, for now IOCTL: lda #<MOUSE_ERR_INV_IOCTL ; We don't support ioctls, for now
ldx #>MOUSE_ERR_INV_IOCTL ldx #>MOUSE_ERR_INV_IOCTL

View File

@@ -1,7 +1,7 @@
; ;
; Address of the static standard mouse driver ; Address of the static standard mouse driver
; ;
; 2019-11-08,Greg King ; 2019-11-08, Greg King
; ;
; const void mouse_static_stddrv[]; ; const void mouse_static_stddrv[];
; ;

View File

@@ -1,5 +1,5 @@
; ;
; 2019-11-06, Greg King ; 2019-12-22, Greg King
; ;
; void __fastcall__ set_tv (unsigned char); ; void __fastcall__ set_tv (unsigned char);
; /* Set the video mode the machine will use. */ ; /* Set the video mode the machine will use. */
@@ -11,9 +11,6 @@
.proc _set_tv .proc _set_tv
php
sei ; Don't let interrupts interfere
; Point to the video output register. ; Point to the video output register.
stz VERA::CTRL ; Use port 0 stz VERA::CTRL ; Use port 0
@@ -25,6 +22,5 @@
stx VERA::ADDR+2 stx VERA::ADDR+2
sta VERA::DATA0 sta VERA::DATA0
plp ; Re-enable interrupts
rts rts
.endproc .endproc

View File

@@ -9,7 +9,7 @@
.import utscopy .import utscopy
__sysuname := utscopy __sysuname := utscopy
;-------------------------------------------------------------------------- ;--------------------------------------------------------------------------
; Data. We define a fixed utsname struct here, and just copy it. ; Data. We define a fixed utsname struct here, and just copy it.

View File

@@ -1,11 +1,10 @@
; ;
; Address of the static standard TGI driver ; Address of the static standard TGI driver
; ;
; 2019-11-06, Greg King ; 2019-12-22, Greg King
; ;
; const void tgi_static_stddrv[]; ; const void tgi_static_stddrv[];
; ;
.import _cx16_640x4c_tgi .import _cx16_320x8b_tgi
.export _tgi_static_stddrv := _cx16_320x8b_tgi
.export _tgi_static_stddrv := _cx16_640x4c_tgi

View File

@@ -1,7 +1,7 @@
; ;
; Name of the standard TGI driver ; Name of the standard TGI driver
; ;
; 2019-11-06, Greg King ; 2019-12-22, Greg King
; ;
; const char tgi_stddrv[]; ; const char tgi_stddrv[];
; ;
@@ -9,5 +9,4 @@
.export _tgi_stddrv .export _tgi_stddrv
.rodata .rodata
_tgi_stddrv: .asciiz "cx16-320x8b.tgi"
_tgi_stddrv: .asciiz "cx16-640x4c.tgi"

View File

@@ -1,19 +1,18 @@
; ;
; 2019-10-22, Greg King ; 2019-12-22, Greg King
; ;
; Set the __far__ address that VERA will use for data access. ; Set the __far__ address that VERA will use for data access.
; This is a support function for the fastcall functions vpeek() and vpoke(). ; This is a support function for the fastcall functions vpeek() and vpoke().
; ;
.export vset .export vaddr0
.importzp sreg .importzp sreg
.include "cx16.inc" .include "cx16.inc"
vset: ldy sreg vaddr0: stz VERA::CTRL ; set address for VERA's data port zero
sei ; don't let interrupt handlers interfere ldy sreg
stz VERA::CTRL ; set address for VERA's data port zero
sta VERA::ADDR sta VERA::ADDR
stx VERA::ADDR+1 stx VERA::ADDR+1
sty VERA::ADDR+2 sty VERA::ADDR+2

View File

@@ -1,5 +1,5 @@
; ;
; 2019-10-22, Greg King ; 2019-12-22, Greg King
; ;
; unsigned char fastcall vpeek (unsigned long addr); ; unsigned char fastcall vpeek (unsigned long addr);
; /* Get a byte from a location in VERA's internal address space. */ ; /* Get a byte from a location in VERA's internal address space. */
@@ -7,13 +7,11 @@
.export _vpeek .export _vpeek
.import vset .import vaddr0
.include "cx16.inc" .include "cx16.inc"
_vpeek: php ; (vset blocks interrupts) _vpeek: jsr vaddr0 ; put VERA's address
jsr vset ; put VERA's address
ldx #>$0000 ldx #>$0000
lda VERA::DATA0 ; read VERA port zero lda VERA::DATA0 ; read VERA port zero
plp
rts rts

View File

@@ -1,5 +1,5 @@
; ;
; 2019-10-22, Greg King ; 2019-12-22, Greg King
; ;
; void fastcall vpoke (unsigned char data, unsigned long addr); ; void fastcall vpoke (unsigned char data, unsigned long addr);
; /* Put a byte into a location in VERA's internal address space. ; /* Put a byte into a location in VERA's internal address space.
@@ -9,13 +9,11 @@
.export _vpoke .export _vpoke
.import vset, popa .import vaddr0, popa
.include "cx16.inc" .include "cx16.inc"
_vpoke: php ; (vset blocks interrupts) _vpoke: jsr vaddr0 ; put VERA's address
jsr vset ; put VERA's address
jsr popa jsr popa
sta VERA::DATA0 ; write data to VERA port zero sta VERA::DATA0 ; write data to VERA port zero
plp
rts rts

View File

@@ -1,9 +1,10 @@
; ;
; 2019-09-26, Greg King ; 2019-12-23, Greg King
; ;
; void waitvsync (void); ; void waitvsync (void);
; /* Wait for the start of the next video field. */
; ;
; VERA's vertical sync causes IRQs which increment the jiffy clock. ; VERA's vertical sync causes IRQs which increment the jiffy timer.
; ;
.export _waitvsync .export _waitvsync
@@ -11,7 +12,10 @@
.include "cx16.inc" .include "cx16.inc"
_waitvsync: _waitvsync:
lda TIME + 2 ldx VIA1::PRA2 ; (TIMER is in RAM bank 0)
: cmp TIME + 2 stz VIA1::PRA2
lda TIMER + 2
: cmp TIMER + 2
beq :- ; Wait for next jiffy beq :- ; Wait for next jiffy
stx VIA1::PRA2
rts rts

View File

@@ -87,6 +87,7 @@ static long Member (long AllocSize)
/* Check the size for a reasonable value */ /* Check the size for a reasonable value */
if (AllocSize >= 0x1000000) { if (AllocSize >= 0x1000000) {
ErrorSkip ("Range error"); ErrorSkip ("Range error");
AllocSize = 1;
} }
/* Return the size */ /* Return the size */
@@ -193,7 +194,13 @@ static long DoStructInternal (long Offs, unsigned Type)
if (CurTok.Tok == TOK_SEP) { if (CurTok.Tok == TOK_SEP) {
ErrorSkip ("Address is missing"); ErrorSkip ("Address is missing");
} else { } else {
Offs = Member (1); Offs = ConstExpression ();
/* Check the address for a reasonable value */
if (Offs >= 0x1000000) {
ErrorSkip ("Range error");
Offs = 0;
}
} }
break; break;