1
0
mirror of https://github.com/cc65/cc65.git synced 2024-06-11 05:29:33 +00:00

Merge pull request #374 from groessler/something_to_pull2

creativision target
This commit is contained in:
Oliver Schmidt 2017-02-15 16:03:43 +01:00 committed by GitHub
commit 21d94929dd
36 changed files with 1508 additions and 40 deletions

View File

@ -29,6 +29,7 @@ including
- the NEC PC-Engine (aka TurboGrafx-16).
- the Nintendo Entertainment System (NES) console.
- the Watara Supervision console.
- the VTech Creativision console.
- the Oric Atmos.
- the Oric Telestrat.
- the Lynx console.

42
asminc/creativision.inc Normal file
View File

@ -0,0 +1,42 @@
;*
;** VTech Creativision Definitions
;*
;** Screen
SCREEN_ROWS = 24
SCREEN_COLS = 32
SCREEN_PTR = $3A
CURSOR_X = $3C
CURSOR_Y = $3D
;** VDP
VDP_CONTROL_W = $3001
VDP_DATA_W = $3000
VDP_STATUS_R = $2001
VDP_DATA_R = $2000
;** PIA
PIA0_DATA = $1000
PIA0_STATUS = $1001
PIA1_DATA = $1002
PIA1_STATUS = $1003
;** General
CH_VLINE = 33
CH_HLINE = 34
CH_ULCORNER = 35
CH_URCORNER = 36
CH_LLCORNER = 37
CH_LRCORNER = 38
;** I/O (Zero-page variables)
ZP_KEYBOARD = $10
ZP_JOY0_DIR = $11
ZP_JOY1_DIR = $13
ZP_JOY0_BUTTONS = $16
ZP_JOY1_BUTTONS = $17
;** BIOS
BIOS_IRQ1_ADDR = $FF3F
BIOS_IRQ2_ADDR = $FF52
BIOS_NMI_RESET_ADDR = $F808

36
cfg/creativision.cfg Normal file
View File

@ -0,0 +1,36 @@
SYMBOLS {
__STACKSIZE__: type = weak, value = $0180;
}
MEMORY {
ZP: file = "", define = yes, start = $0020, size = $00E0;
RAM: file = "", define = yes, start = $01FA, size = $0206;
ROM: file = %O, define = yes, start = $B000, size = $1000;
}
SEGMENTS {
ZEROPAGE: load = ZP, type = zp;
ZP: load = ZP, type = zp, optional = yes;
VECTORS: load = ROM, run = RAM, type = rw, define = yes;
DATA: load = ROM, run = RAM, type = rw, define = yes, start = $0204;
BSS: load = RAM, type = bss, define = yes;
ONCE: load = ROM, type = ro, optional = yes;
CODE: load = ROM, type = ro;
INIT: load = ROM, type = ro;
RODATA: load = ROM, type = ro;
AUDIO: load = ROM, type = ro, optional = yes, start = $BF00;
SETUP: load = ROM, type = ro, start = $BFE8;
}
FEATURES {
CONDES: type = constructor,
label = __CONSTRUCTOR_TABLE__,
count = __CONSTRUCTOR_COUNT__,
segment = INIT;
CONDES: type = destructor,
label = __DESTRUCTOR_TABLE__,
count = __DESTRUCTOR_COUNT__,
segment = RODATA;
CONDES: type = interruptor,
label = __INTERRUPTOR_TABLE__,
count = __INTERRUPTOR_COUNT__,
segment = RODATA,
import = __CALLIRQ__;
}

177
doc/creativision.sgml Normal file
View File

@ -0,0 +1,177 @@
<!doctype linuxdoc system>
<article>
<title>VTech Creativision (aka Funvision) specific information for cc65
<author><url url="mailto:polluks+cc65@sdf.lonestar.org" name="Stefan A. Haubenthal">
<date>2016-04-14
<abstract>
An overview over the Creativision runtime system as it is implemented for the
cc65 C compiler.
</abstract>
<!-- Table of contents -->
<toc>
<!-- Begin the document -->
<sect>Overview<p>
This file contains an overview of the Creativision runtime system as it comes
with the cc65 C compiler. It describes the memory layout, Creativision specific header
files, available drivers, and any pitfalls specific to that platform.
Please note that Creativision specific functions are just mentioned here, they are
described in detail in the separate <url url="funcref.html" name="function
reference">. Even functions marked as "platform dependent" may be available on
more than one platform. Please see the function reference for more information.
<sect>Binary format<p>
The standard binary output format generated by the linker for the Creativision target
is a 4 kbyte machine language program. It is of course possible to change
this behaviour by using one of the different linker configs.
<sect>Memory layout<p>
cc65 generated programs with the default setup run with the I/O area enabled,
which gives a usable memory range of &dollar;B000 - &dollar;BEFF.
More ROM may need additional bankswitching code.
Special locations:
<descrip>
<tag/Text screen/
The text screen is located at VRAM &dollar;1000.
<tag/Stack/
The C runtime stack is located at &dollar;3FF and growing downwards.
<tag/Heap/
The C heap is located at the end of the program and grows towards the C
runtime stack.
</descrip><p>
<sect>Platform specific header files<p>
Programs containing Creativision specific code may use the <tt/creativision.h/ header file.
<sect1>Creativision specific functions<p>
<itemize>
<item>bios_playsound
<item>psg_delay
<item>psg_outb
<item>psg_silence
</itemize>
<!--<sect1>Hardware access<p>
The following pseudo variables declared in the <tt/creativision.inc/ include file do
allow access to hardware located in the address space.
<descrip>
<tag><tt/VDP/</tag>
The <tt/VDP/ defines allow access to the video chip.
</descrip><p>
<descrip>
<tag><tt/PIA/</tag>
The <tt/PIA/ defines allow access to the I/O chip.
</descrip><p>-->
<sect>Loadable drivers<p>
<sect1>Graphics drivers<p>
No graphics drivers are currently available for the Creativision.
<sect1>Extended memory drivers<p>
No extended memory drivers are currently available for the Creativision.
<sect1>Joystick drivers<p>
<descrip>
<tag><tt/creativision-stdjoy.joy (creativisionstd_joy)/</tag>
A joystick driver for the standard joystick is available.
</descrip><p>
<sect1>Mouse drivers<p>
No mouse drivers are currently available for the Creativision.
<sect1>RS232 device drivers<p>
No communication port drivers are currently available for the Creativision.
<sect>Limitations<p>
<sect1>Disk I/O<p>
The existing library for the Creativision doesn't implement C file
I/O. There are even no hacks for the <tt/read()/ and <tt/write()/ routines.
To be more concrete, this limitation means that you cannot use any of the
following functions (and a few others):
<itemize>
<item>fclose
<item>fopen
<item>fread
<item>fprintf
<item>fputc
<item>fscanf
<item>fwrite
<item>...
</itemize>
<sect>Other hints<p>
<sect>License<p>
This software is provided 'as-is', without any expressed or implied
warranty. In no event will the authors be held liable for any damages
arising from the use of this software.
Permission is granted to anyone to use this software for any purpose,
including commercial applications, and to alter it and redistribute it
freely, subject to the following restrictions:
<enum>
<item> The origin of this software must not be misrepresented; you must not
claim that you wrote the original software. If you use this software
in a product, an acknowledgment in the product documentation would be
appreciated but is not required.
<item> Altered source versions must be plainly marked as such, and must not
be misrepresented as being the original software.
<item> This notice may not be removed or altered from any source
distribution.
</enum>
</article>

View File

@ -140,6 +140,9 @@
<tag><htmlurl url="cbm610.html" name="cbm610.html"></tag>
Topics specific to the Commodore 610.
<tag><htmlurl url="creativision.html" name="creativision.html"></tag>
Topics specific to the Creativision Console.
<tag><htmlurl url="lynx.html" name="lynx.html"></tag>
Topics specific to the Atari Lynx Game Console.

70
include/creativision.h Normal file
View File

@ -0,0 +1,70 @@
/*****************************************************************************/
/* */
/* creativision.h */
/* */
/* Creativision system specific definitions */
/* */
/* */
/* */
/* (C) 2013 cvemu */
/* (C) 2017 Christian Groessler <chris@groessler.org> */
/* */
/* */
/* This software is provided 'as-is', without any expressed or implied */
/* warranty. In no event will the authors be held liable for any damages */
/* arising from the use of this software. */
/* */
/* Permission is granted to anyone to use this software for any purpose, */
/* including commercial applications, and to alter it and redistribute it */
/* freely, subject to the following restrictions: */
/* */
/* 1. The origin of this software must not be misrepresented; you must not */
/* claim that you wrote the original software. If you use this software */
/* in a product, an acknowledgment in the product documentation would be */
/* appreciated but is not required. */
/* 2. Altered source versions must be plainly marked as such, and must not */
/* be misrepresented as being the original software. */
/* 3. This notice may not be removed or altered from any source */
/* distribution. */
/* */
/*****************************************************************************/
#ifndef _CVISION_H
#define _CVISION_H
/* Character codes */
#define CH_VLINE 33
#define CH_HLINE 34
#define CH_ULCORNER 35
#define CH_URCORNER 36
#define CH_LLCORNER 37
#define CH_LRCORNER 38
/* no support for dynamically loadable drivers */
#define DYN_DRV 0
/* Colours - from TMS9918 */
#define C_TRANSPARENT 0
#define C_BLACK 1
#define C_MED_GREEN 2
#define C_LIGHT_GREEN 3
#define C_DARK_BLUE 4
#define C_LIGHT_BLUE 5
#define C_DARK_RED 6
#define C_CYAN 7
#define C_MED_RED 8
#define C_LIGHT_RED 9
#define C_DARK_YELLOW 10
#define C_LIGHT_YELLOW 11
#define C_DARK_GREEN 12
#define C_MAGENTA 13
#define C_GREY 14
#define C_WHITE 15
/* Protos */
void __fastcall__ psg_outb(unsigned char b);
void __fastcall__ psg_delay(unsigned char b);
void psg_silence(void);
void __fastcall__ bios_playsound(void *a, unsigned char b);
#endif /* #ifndef _CVISION_H */

View File

@ -22,6 +22,7 @@ TARGETS = apple2 \
atari2600 \
atari5200 \
atmos \
creativision \
$(CBMS) \
$(GEOS) \
gamate \

View File

@ -0,0 +1,15 @@
;*
;** _scrsize.s
;*
.export screensize
.include "creativision.inc"
.proc screensize
ldx #SCREEN_COLS
ldy #SCREEN_ROWS
rts
.endproc

View File

@ -0,0 +1,62 @@
; Boxchars
boxchars:
; Vertical Line
.byte $18
.byte $18
.byte $18
.byte $18
.byte $18
.byte $18
.byte $18
.byte $18
; Horizontal Line
.byte $00
.byte $00
.byte $00
.byte $FF
.byte $00
.byte $00
.byte $00
.byte $00
; Top Left
.byte $00
.byte $00
.byte $00
.byte $1F
.byte $18
.byte $18
.byte $18
.byte $18
; Top Right
.byte $00
.byte $00
.byte $00
.byte $F8
.byte $18
.byte $18
.byte $18
.byte $18
; Bottom Left
.byte $18
.byte $18
.byte $18
.byte $1F
.byte $00
.byte $00
.byte $00
.byte $00
; Bottom Right
.byte $18
.byte $18
.byte $18
.byte $F8
.byte $00
.byte $00
.byte $00
.byte $00

View File

@ -0,0 +1,26 @@
;*
;* void cclearxy (unsigned char x, unsigned char y, unsigned char length);
;* void cclear (unsigned char length);
;*
.export _cclearxy, _cclear
.import popa, _gotoxy, cputdirect
.importzp tmp1
_cclearxy:
pha ; Save length
jsr popa ; get Y
jsr _gotoxy
pla
_cclear:
cmp #0 ; Zero length?
beq L2
sta tmp1
L1: lda #$20 ; Space
jsr cputdirect
dec tmp1
bne L1
L2: rts

View File

@ -0,0 +1,14 @@
;* cgetc
.export _cgetc
.include "creativision.inc"
_cgetc:
lda #$80
L1: bit ZP_KEYBOARD
bpl L1
lda ZP_KEYBOARD
and #$7F
rts

View File

@ -0,0 +1,24 @@
;* void chlinexy (unsigned char x, unsigned char y, unsigned char length);
;* void chline (unsigned char length);
.export _chlinexy, _chline
.import popa, _gotoxy, cputdirect
.importzp tmp1
.include "creativision.inc"
_chlinexy:
pha ; Save the length
jsr popa ; Get y
jsr _gotoxy ; Call this one, will pop params
pla ; Restore the length
_chline:
cmp #0 ; Is the length zero?
beq L9 ; Jump if done
sta tmp1
L1: lda #CH_HLINE ; Horizontal line, screen code
jsr cputdirect ; Direct output
dec tmp1
bne L1
L9: rts

View File

@ -0,0 +1,41 @@
;*
;* clrscr
;*
;* NB: All screen functions assume Graphics Mode 1 in a default configuration.
;* Therefore, this is hard coded to use $1000-$12FF as screen VRAM.
.export _clrscr
.include "creativision.inc"
_clrscr:
sei ; Disable interrupts. Default INT handler reads VDP_STATUS
; and would lose any setup done here.
lda #$00 ; VRAM offset low
sta VDP_CONTROL_W
lda #$50 ; VRAM offset high ($10 OR $40)
sta VDP_CONTROL_W
lda #$C0 ; Space from ROM setup
ldx #0
ldy #3
L1: sta VDP_DATA_W
inx
bne L1
dey
bne L1
cli ; Let interrupts go again
lda #0
sta CURSOR_X
sta CURSOR_Y
sta <SCREEN_PTR
lda #$10
sta >SCREEN_PTR
rts

View File

@ -0,0 +1,13 @@
;*
;* unsigned char __fastcall__ textcolor (unsigned char color);
;* unsigned char __fastcall__ bgcolor (unsigned char color);
;* unsigned char __fastcall__ bordercolor (unsigned char color);
;*
.export _textcolor, _bgcolor, _bordercolor
.import return0
.include "creativision.inc"
_bordercolor = return0;
_textcolor = return0;
_bgcolor = return0;

125
libsrc/creativision/cputc.s Normal file
View File

@ -0,0 +1,125 @@
;
; Written by Groepaz/Hitmen <groepaz@gmx.net>
; Cleanup by Ullrich von Bassewitz <uz@cc65.org>
;
; void cputcxy (unsigned char x, unsigned char y, char c);
; void cputc (char c);
;
.export _cputcxy, _cputc, cputdirect, putchar
.export newline
.constructor initconio
.import popa, _gotoxy
.import setcursor
.importzp tmp3,tmp4
.include "creativision.inc"
.include "boxchars.inc"
;-----------------------------------------------------------------------------
.code
_cputcxy:
pha ; Save C
jsr popa ; Get Y
jsr _gotoxy ; Set cursor, drop x
pla ; Restore C
; Plot a character - also used as internal function
_cputc: cmp #$0D ; CR?
bne L1
lda #0
sta CURSOR_X
beq plot ; Recalculate pointers
L1: cmp #$0A ; LF?
beq newline ; Recalculate pointers
; Printable char of some sort
cputdirect:
jsr putchar ; Write the character to the screen
; Advance cursor position
advance:
ldy CURSOR_X
iny
cpy #SCREEN_COLS
bne L3
inc CURSOR_Y ; new line
ldy #0 ; + cr
L3: sty CURSOR_X
jmp plot
newline:
inc CURSOR_Y
; Set cursor position, calculate RAM pointers
plot: ldy CURSOR_X
ldx CURSOR_Y
jmp setcursor ; Set the new cursor
; Write one character to the screen without doing anything else, return X
; position in Y
putchar:
cmp #$5B
bcc IS_UPPER
clc
sbc #$1F
IS_UPPER:
cmp #$20
bcc BAD_CHAR
pha
lda SCREEN_PTR
sei
sta VDP_CONTROL_W
lda SCREEN_PTR+1
ora #$40
sta VDP_CONTROL_W
pla
clc
adc #160
sta VDP_DATA_W
cli
BAD_CHAR:
jmp plot
;-----------------------------------------------------------------------------
; Initialize the conio subsystem. Code goes into the INIT segment, which may
; be reused after startup.
.segment "INIT"
initconio:
lda #$0
sta SCREEN_PTR
lda #$10
sta SCREEN_PTR+1
; Copy box characters to slot
sei
lda #08
sta VDP_CONTROL_W
lda #$46
sta VDP_CONTROL_W
ldx #0
LL: lda boxchars,x
sta VDP_DATA_W
inx
cpx #48
bne LL
cli
jmp plot

104
libsrc/creativision/crt0.s Normal file
View File

@ -0,0 +1,104 @@
;
; Startup code for cc65 (CreatiVision version)
;
.export _exit
.export __STARTUP__ : absolute = 1 ; Mark as startup
.export irq2
.import zerobss, copydata
.import initlib, donelib, callmain
.import __VECTORS_LOAD__, __VECTORS_RUN__, __VECTORS_SIZE__
.import __ZP_LAST__, __STACKSIZE__, __RAM_START__
.include "creativision.inc"
.include "zeropage.inc"
; ------------------------------------------------------------------------
entry:
; Init the CPU
sei
cld
; Copy the IRQ vectors
ldx #<__VECTORS_SIZE__ - 1
: lda __VECTORS_LOAD__,x
sta __VECTORS_RUN__,x
dex
bpl :-
; Setup the CPU stack ptr
ldx #<__RAM_START__ - 1
txs
; Start interrupts
cli
; Clear the BSS data
jsr zerobss
; Copy data from ROM to RAM
jsr copydata
; Setup the argument stack ptr
lda #<(__ZP_LAST__ + __STACKSIZE__)
ldx #>(__ZP_LAST__ + __STACKSIZE__)
sta sp
stx sp+1
; Call module constructors
jsr initlib
; Call main()
jsr callmain
; Call module destructors. This is also the _exit entry.
_exit: jsr donelib
; TODO: Replace with some sort of reset
loop: jmp loop
; ------------------------------------------------------------------------
; Define the IRQ vectors.
.segment "VECTORS"
irq1: jmp BIOS_IRQ1_ADDR
irq2: jmp BIOS_IRQ2_ADDR
; ------------------------------------------------------------------------
; Define CART setup values for BIOS.
.segment "SETUP"
; BIOS Jump Start
; This is where the entry point of the program needs to be
.addr entry
.addr irq2
.res 4
; VDP Setup
; This sets to Graphics Mode 1
.byte $00 ; Register 0
.byte $C0 ; Register 1 16K RAM, Active Display, Mode 1
.byte $04 ; Register 2 Name Table at $1000 - $12FF
.byte $60 ; Register 3 Colour Table at $1800 - $181F
.byte $00 ; Register 4 Pattern Table at $0000 - $07FF
.byte $10 ; Register 5 Sprite Attribute at $0800 - $087F
.byte $01 ; Register 6 Sprite Pattern
.byte $F1 ; Register 7 Text colour Foreground / background
.res 4
; BIOS Vector after NMI or RESET
; Keeping with retail cartridges, we jump back to BIOS ROM and have it
; setup zeropage etc, and show the Creativision logo and copyright.
.addr BIOS_NMI_RESET_ADDR
; BIOS Short Interrupt Handler
; Vectored from BIOS ROM:FE2C. This should contain a pointer to the user's
; BIOS interrupt handler.
.addr irq1
; ------------------------------------------------------------------------

172
libsrc/creativision/ctype.s Normal file
View File

@ -0,0 +1,172 @@
;
; Ullrich von Bassewitz, 02.06.1998
;
; Character specification table.
;
; The tables are readonly, put them into the rodata segment
.rodata
; The following 256 byte wide table specifies attributes for the isxxx type
; of functions. Doing it by a table means some overhead in space, but it
; has major advantages:
;
; * It is fast. If it were'nt for the slow parameter passing of cc65, one
; could even define macros for the isxxx functions (this is usually
; done on other platforms).
;
; * It is highly portable. The only unportable part is the table itself,
; all real code goes into the common library.
;
; * We save some code in the isxxx functions.
;
;
; Bit assignments:
;
; 0 - Lower case char
; 1 - Upper case char
; 2 - Numeric digit
; 3 - Hex digit (both, lower and upper)
; 4 - Control character
; 5 - The space character itself
; 6 - Other whitespace (that is: '\f', '\n', '\r', '\t' and '\v')
; 7 - Space or tab character
.export __ctype
__ctype:
.repeat 2 ; 2 times for normal and inverted
.byte $10 ; 0/00 ___ctrl_@___
.byte $10 ; 1/01 ___ctrl_A___
.byte $10 ; 2/02 ___ctrl_B___
.byte $10 ; 3/03 ___ctrl_C___
.byte $10 ; 4/04 ___ctrl_D___
.byte $10 ; 5/05 ___ctrl_E___
.byte $10 ; 6/06 ___ctrl_F___
.byte $10 ; 7/07 ___ctrl_G___
.byte $10 ; 8/08 ___ctrl_H___
.byte $D0 ; 9/09 ___ctrl_I___
.byte $50 ; 10/0a ___ctrl_J___
.byte $50 ; 11/0b ___ctrl_K___
.byte $50 ; 12/0c ___ctrl_L___
.byte $50 ; 13/0d ___ctrl_M___
.byte $10 ; 14/0e ___ctrl_N___
.byte $10 ; 15/0f ___ctrl_O___
.byte $10 ; 16/10 ___ctrl_P___
.byte $10 ; 17/11 ___ctrl_Q___
.byte $10 ; 18/12 ___ctrl_R___
.byte $10 ; 19/13 ___ctrl_S___
.byte $10 ; 20/14 ___ctrl_T___
.byte $10 ; 21/15 ___ctrl_U___
.byte $10 ; 22/16 ___ctrl_V___
.byte $10 ; 23/17 ___ctrl_W___
.byte $10 ; 24/18 ___ctrl_X___
.byte $10 ; 25/19 ___ctrl_Y___
.byte $10 ; 26/1a ___ctrl_Z___
.byte $10 ; 27/1b ___ctrl_[___
.byte $10 ; 28/1c ___ctrl_\___
.byte $10 ; 29/1d ___ctrl_]___
.byte $10 ; 30/1e ___ctrl_^___
.byte $10 ; 31/1f ___ctrl_____
.byte $A0 ; 32/20 ___SPACE___
.byte $00 ; 33/21 _____!_____
.byte $00 ; 34/22 _____"_____
.byte $00 ; 35/23 _____#_____
.byte $00 ; 36/24 _____$_____
.byte $00 ; 37/25 _____%_____
.byte $00 ; 38/26 _____&_____
.byte $00 ; 39/27 _____'_____
.byte $00 ; 40/28 _____(_____
.byte $00 ; 41/29 _____)_____
.byte $00 ; 42/2a _____*_____
.byte $00 ; 43/2b _____+_____
.byte $00 ; 44/2c _____,_____
.byte $00 ; 45/2d _____-_____
.byte $00 ; 46/2e _____._____
.byte $00 ; 47/2f _____/_____
.byte $0C ; 48/30 _____0_____
.byte $0C ; 49/31 _____1_____
.byte $0C ; 50/32 _____2_____
.byte $0C ; 51/33 _____3_____
.byte $0C ; 52/34 _____4_____
.byte $0C ; 53/35 _____5_____
.byte $0C ; 54/36 _____6_____
.byte $0C ; 55/37 _____7_____
.byte $0C ; 56/38 _____8_____
.byte $0C ; 57/39 _____9_____
.byte $00 ; 58/3a _____:_____
.byte $00 ; 59/3b _____;_____
.byte $00 ; 60/3c _____<_____
.byte $00 ; 61/3d _____=_____
.byte $00 ; 62/3e _____>_____
.byte $00 ; 63/3f _____?_____
.byte $00 ; 64/40 _____@_____
.byte $0A ; 65/41 _____A_____
.byte $0A ; 66/42 _____B_____
.byte $0A ; 67/43 _____C_____
.byte $0A ; 68/44 _____D_____
.byte $0A ; 69/45 _____E_____
.byte $0A ; 70/46 _____F_____
.byte $02 ; 71/47 _____G_____
.byte $02 ; 72/48 _____H_____
.byte $02 ; 73/49 _____I_____
.byte $02 ; 74/4a _____J_____
.byte $02 ; 75/4b _____K_____
.byte $02 ; 76/4c _____L_____
.byte $02 ; 77/4d _____M_____
.byte $02 ; 78/4e _____N_____
.byte $02 ; 79/4f _____O_____
.byte $02 ; 80/50 _____P_____
.byte $02 ; 81/51 _____Q_____
.byte $02 ; 82/52 _____R_____
.byte $02 ; 83/53 _____S_____
.byte $02 ; 84/54 _____T_____
.byte $02 ; 85/55 _____U_____
.byte $02 ; 86/56 _____V_____
.byte $02 ; 87/57 _____W_____
.byte $02 ; 88/58 _____X_____
.byte $02 ; 89/59 _____Y_____
.byte $02 ; 90/5a _____Z_____
.byte $00 ; 91/5b _____[_____
.byte $00 ; 92/5c _____\_____
.byte $00 ; 93/5d _____]_____
.byte $00 ; 94/5e _____^_____
.byte $00 ; 95/5f _UNDERLINE_
.byte $00 ; 96/60 ___grave___
.byte $09 ; 97/61 _____a_____
.byte $09 ; 98/62 _____b_____
.byte $09 ; 99/63 _____c_____
.byte $09 ; 100/64 _____d_____
.byte $09 ; 101/65 _____e_____
.byte $09 ; 102/66 _____f_____
.byte $01 ; 103/67 _____g_____
.byte $01 ; 104/68 _____h_____
.byte $01 ; 105/69 _____i_____
.byte $01 ; 106/6a _____j_____
.byte $01 ; 107/6b _____k_____
.byte $01 ; 108/6c _____l_____
.byte $01 ; 109/6d _____m_____
.byte $01 ; 110/6e _____n_____
.byte $01 ; 111/6f _____o_____
.byte $01 ; 112/70 _____p_____
.byte $01 ; 113/71 _____q_____
.byte $01 ; 114/72 _____r_____
.byte $01 ; 115/73 _____s_____
.byte $01 ; 116/74 _____t_____
.byte $01 ; 117/75 _____u_____
.byte $01 ; 118/76 _____v_____
.byte $01 ; 119/77 _____w_____
.byte $01 ; 120/78 _____x_____
.byte $01 ; 121/79 _____y_____
.byte $01 ; 122/7a _____z_____
.byte $00 ; 123/7b _____{_____
.byte $00 ; 124/7c _____|_____
.byte $00 ; 125/7d _____}_____
.byte $00 ; 126/7e _____~_____
.byte $40 ; 127/7f ____DEL____
.endrepeat

View File

@ -0,0 +1,29 @@
;
; Ullrich von Bassewitz, 08.08.1998
;
; void cvlinexy (unsigned char x, unsigned char y, unsigned char length);
; void cvline (unsigned char length);
;
.export _cvlinexy, _cvline
.import popa, _gotoxy, putchar, newline
.importzp tmp1
.include "creativision.inc"
_cvlinexy:
pha ; Save the length
jsr popa ; Get y
jsr _gotoxy ; Call this one, will pop params
pla ; Restore the length and run into _cvline
_cvline:
cmp #0 ; Is the length zero?
beq L9 ; Jump if done
sta tmp1
L1: lda #CH_VLINE ; Vertical bar
jsr putchar ; Write, no cursor advance
jsr newline ; Advance cursor to next line
dec tmp1
bne L1
L9: rts

View File

@ -0,0 +1,19 @@
;
; Ullrich von Bassewitz, 2003-05-02
;
; void gotox (unsigned char x);
;
.export _gotox
.import setcursor
.include "creativision.inc"
.proc _gotox
sta CURSOR_X ; Set new position
tay
ldx CURSOR_Y
jmp setcursor ; Set the cursor to the new position
.endproc

View File

@ -0,0 +1,22 @@
;
; Ullrich von Bassewitz, 06.08.1998
;
; void gotoxy (unsigned char x, unsigned char y);
;
.export _gotoxy
.import setcursor
.import popa
.include "creativision.inc"
.proc _gotoxy
sta CURSOR_Y ; Set Y
jsr popa ; Get X
sta CURSOR_X ; Set X
tay
ldx CURSOR_Y
jmp setcursor ; Set the cursor position
.endproc

View File

@ -0,0 +1,19 @@
;
; Ullrich von Bassewitz, 2003-05-02
;
; void gotoy (unsigned char y);
;
.export _gotoy
.import setcursor
.include "creativision.inc"
.proc _gotoy
sta CURSOR_Y ; Set new position
tax
ldy CURSOR_X
jmp setcursor ; Set the cursor to the new position
.endproc

40
libsrc/creativision/irq.s Normal file
View File

@ -0,0 +1,40 @@
;
; IRQ handling (CreatiVision version)
;
.export initirq, doneirq
.import callirq, irq2
.include "creativision.inc"
; ------------------------------------------------------------------------
.segment "ONCE"
initirq:
lda #<IRQStub
ldx #>IRQStub
jmp setvec
; ------------------------------------------------------------------------
.code
doneirq:
lda #<BIOS_IRQ2_ADDR
ldx #>BIOS_IRQ2_ADDR
setvec: sei
sta irq2+1
stx irq2+2
cli
rts
; ------------------------------------------------------------------------
.segment "CODE"
IRQStub:
cld ; Just to be sure
jsr callirq ; Call the functions
jmp BIOS_IRQ2_ADDR ; Jump to the BIOS IRQ vector

View File

@ -0,0 +1,193 @@
;
; Standard joystick driver for the Creativision.
;
; Christian Groessler, 2017-02-06
;
.include "zeropage.inc"
.include "joy-kernel.inc"
.include "joy-error.inc"
.include "creativision.inc"
.macpack module
; ------------------------------------------------------------------------
; Header. Includes jump table
module_header _creativisionstd_joy
; Driver signature
.byte $6A, $6F, $79 ; "joy"
.byte JOY_API_VERSION ; Driver API version number
; Library reference
.addr $0000
; Button state masks (8 values)
.byte $10 ; JOY_UP
.byte $04 ; JOY_DOWN
.byte $20 ; JOY_LEFT
.byte $08 ; JOY_RIGHT
.byte $01 ; JOY_FIRE (button #1)
.byte $02 ; JOY_FIRE2 (button #2)
.byte $00 ; Future expansion
.byte $00 ; Future expansion
; Jump table.
.addr INSTALL
.addr UNINSTALL
.addr COUNT
.addr READJOY
.addr 0 ; IRQ entry not used
; ------------------------------------------------------------------------
; Constants
JOY_COUNT = 2 ; Number of joysticks we support
; ------------------------------------------------------------------------
; Code
.code
; ------------------------------------------------------------------------
; INSTALL routine. Is called after the driver is loaded into memory. If
; possible, check if the hardware is present and determine the amount of
; memory available.
; Must return an JOY_ERR_xx code in a/x.
;
INSTALL:
lda #JOY_ERR_OK
ldx #0
; rts ; Fall through
; ------------------------------------------------------------------------
; UNINSTALL routine. Is called before the driver is removed from memory.
; Can do cleanup or whatever. Must not return anything.
;
UNINSTALL:
rts
; ------------------------------------------------------------------------
; COUNT: Return the total number of available joysticks in a/x.
;
COUNT:
lda #<JOY_COUNT
ldx #>JOY_COUNT
rts
; ------------------------------------------------------------------------
; READ: Read a particular joystick passed in A.
;
READJOY:
and #1 ; fix joystick number
bne READJOY_1 ; read right joystick
; Read left joystick
ldx ZP_JOY0_DIR
lda ZP_JOY0_BUTTONS
jmp convert ; convert joystick state to sane cc65 values
; Read right joystick
READJOY_1:
ldx ZP_JOY1_DIR
lda ZP_JOY1_BUTTONS
lsr a
lsr a
;jmp convert ; convert joystick state to sane cc65 values
; fall thru...
; ------------------------------------------------------------------------
; convert: make runtime lib compatible values
; A - buttons
; X - direction
;
convert:
ldy #0
sty retval ; initialize return value
; ------
; buttons:
; Port values are for the left hand joystick (right hand joystick
; values were shifted to the right to be identical).
; Why are there two bits indicating a pressed trigger?
; According to the "Second book of programs for the Dick Smith Wizard"
; (pg. 88ff), the left hand fire button gives the value of
; %00010001 and the right hand button gives %00100010
; Why two bits? Am I missing something? Can there be cases that just
; one of those bits is set?
; We just test if any of those two bits is not zero...
tay
and #%00010001
beq cnv_1
inc retval ; left button pressed
cnv_1: tya
and #%00100010
beq cnv_2
lda #$02
ora retval
sta retval ; right button pressed
; ------
; direction:
cnv_2: txa
; tested with https://sourceforge.net/projects/creativisionemulator
; $49 - %01001001 - up
; $41 - %01000001 - down
; $4D - %01001101 - left
; $45 - %01000101 - right
;
; are these correct? "Second book of programs for the Dick Smith Wizard" pg. 85 says something different
; ignored for now...
; $85 - %10000101 - up + right
; $8D - %10001101 - down + left
; $89 - %10001001 - up + left
; $85 - %10000101 - down + right (emulator bug?)
bit testbit ; bit #0 set?
beq done ; no, no direction
and #%00001100 ; mask out other bits
lsr a
lsr a
tax
lda #%00000100 ; init bitmask
loop: dex
bmi done2
asl a
bne loop
done2: ora retval
rts
done: lda retval
rts
; ------------------------------------------------------------------------
;
.data
testbit:.byte $01
; ------------------------------------------------------------------------
;
.bss
retval: .res 0

View File

@ -0,0 +1,12 @@
;
; Address of the static standard joystick driver
;
; Christian Groessler, 2017-02-06
;
; const void joy_static_stddrv[];
;
.export _joy_static_stddrv
.import _creativisionstd_joy
_joy_static_stddrv := _creativisionstd_joy

View File

@ -0,0 +1,8 @@
;
; Oliver Schmidt, 2013-05-31
;
.export joy_libref
.import _exit
joy_libref := _exit

View File

@ -0,0 +1,22 @@
;
; Ullrich von Bassewitz, 2003-03-07
;
; Setup arguments for main
;
.constructor initmainargs, 24
.import __argc, __argv
;---------------------------------------------------------------------------
; Get possible command-line arguments. Goes into the special INIT segment,
; which may be reused after the startup code is run
.segment "INIT"
.proc initmainargs
rts
.endproc

63
libsrc/creativision/psg.s Normal file
View File

@ -0,0 +1,63 @@
; void __fastcall__ psg_outb( unsigned char b );
; void __fastcall__ psg_delayms( unsigned char c);
; void __fastcall__ bios_playsound( void *b, unsigned char c);
; void psg_silence( void );
.export _psg_outb, _psg_silence, _psg_delay
.export _bios_playsound
.import popa
.include "creativision.inc"
_psg_outb:
;* Let BIOS output the value
jmp $FE77
_psg_silence:
jmp $FE54
_psg_delay:
tay
l1: lda #200
l2: sbc #1
bne l2
lda #200
l3: sbc #1
bne l3
dey
bne l1
rts
;* Creativision Sound Player
;*
;* Based on BIOS sound player.
;* Pass a pointer to a set of note triples, terminated with a tempo byte
;* and the len (max 255)
_bios_playsound:
pha ; Save Length Byte
sei
lda #$D5 ; BIOS volume table low
sta $4
lda #$FC ; BIOS volume table high
sta $5
jsr popa ; Get Sound table pointer low
sta $0
jsr popa ; Get Sound table pointer high
sta $1
pla
tay ; Put length in Y
dey
php
jmp $FBED ; Let BIOS do it's thing

View File

@ -0,0 +1,36 @@
;
; Written by Groepaz/Hitmen <groepaz@gmx.net>
; Cleanup by Ullrich von Bassewitz <uz@cc65.org>
;
; Set the cursor position
.export setcursor
.include "creativision.inc"
;-----------------------------------------------------------------------------
.proc setcursor
tya
clc
adc addrlo,x
sta SCREEN_PTR
lda addrhi,x
adc #0
sta SCREEN_PTR+1
rts
.endproc
;-----------------------------------------------------------------------------
; Tables with screen addresses
addrlo: .repeat SCREEN_ROWS,line
.byte <($1000+(line*SCREEN_COLS))
.endrepeat
addrhi: .repeat SCREEN_ROWS,line
.byte >($1000+(line*SCREEN_COLS))
.endrepeat

View File

@ -0,0 +1,36 @@
;
; Ullrich von Bassewitz, 2003-08-12
;
; unsigned char __fastcall__ _sysuname (struct utsname* buf);
;
.export __sysuname, utsdata
.import utscopy
__sysuname = utscopy
;--------------------------------------------------------------------------
; Data. We define a fixed utsname struct here and just copy it.
.rodata
utsdata:
; sysname
.asciiz "cc65"
; nodename
.asciiz ""
; release
.byte ((.VERSION >> 8) & $0F) + '0'
.byte '.'
.byte ((.VERSION >> 4) & $0F) + '0'
.byte $00
; version
.byte (.VERSION & $0F) + '0'
.byte $00
; machine
.asciiz "CREATIVISION"

View File

@ -0,0 +1,16 @@
;
; Ullrich von Bassewitz, 2003-05-02
;
; unsigned char wherex (void);
;
.export _wherex
.include "creativision.inc"
.proc _wherex
lda CURSOR_X
ldx #$00
rts
.endproc

View File

@ -0,0 +1,16 @@
;
; Ullrich von Bassewitz, 2003-05-02
;
; unsigned char wherey (void);
;
.export _wherey
.include "creativision.inc"
.proc _wherey
lda CURSOR_Y
ldx #$00
rts
.endproc

View File

@ -282,6 +282,10 @@ static void SetSys (const char* Sys)
NewSymbol ("__GEOS_CBM__", 1);
break;
case TGT_CREATIVISION:
NewSymbol ("__CREATIVISION__", 1);
break;
case TGT_GEOS_APPLE:
NewSymbol ("__GEOS__", 1);
NewSymbol ("__GEOS_APPLE__", 1);

View File

@ -234,6 +234,10 @@ static void SetSys (const char* Sys)
DefineNumericMacro ("__GEOS_CBM__", 1);
break;
case TGT_CREATIVISION:
DefineNumericMacro ("__CREATIVISION__", 1);
break;
case TGT_GEOS_APPLE:
DefineNumericMacro ("__GEOS__", 1);
DefineNumericMacro ("__GEOS_APPLE__", 1);

View File

@ -134,7 +134,7 @@ static const unsigned char CTPET[256] = {
/* One entry in the target map */
typedef struct TargetEntry TargetEntry;
struct TargetEntry {
char Name[12]; /* Target name */
char Name[13]; /* Target name */
target_t Id; /* Target id */
};
@ -142,38 +142,39 @@ struct TargetEntry {
** Allows multiple entries for one target id (target name aliases).
*/
static const TargetEntry TargetMap[] = {
{ "apple2", TGT_APPLE2 },
{ "apple2enh", TGT_APPLE2ENH },
{ "atari", TGT_ATARI },
{ "atari2600", TGT_ATARI2600 },
{ "atari5200", TGT_ATARI5200 },
{ "atarixl", TGT_ATARIXL },
{ "atmos", TGT_ATMOS },
{ "bbc", TGT_BBC },
{ "c128", TGT_C128 },
{ "c16", TGT_C16 },
{ "c64", TGT_C64 },
{ "c65", TGT_C65 },
{ "cbm510", TGT_CBM510 },
{ "cbm610", TGT_CBM610 },
{ "gamate", TGT_GAMATE },
{ "geos", TGT_GEOS_CBM },
{ "geos-apple", TGT_GEOS_APPLE },
{ "geos-cbm", TGT_GEOS_CBM },
{ "lunix", TGT_LUNIX },
{ "lynx", TGT_LYNX },
{ "module", TGT_MODULE },
{ "nes", TGT_NES },
{ "none", TGT_NONE },
{ "osic1p", TGT_OSIC1P },
{ "pce", TGT_PCENGINE },
{ "pet", TGT_PET },
{ "plus4", TGT_PLUS4 },
{ "sim6502", TGT_SIM6502 },
{ "sim65c02", TGT_SIM65C02 },
{ "supervision", TGT_SUPERVISION },
{ "telestrat", TGT_TELESTRAT },
{ "vic20", TGT_VIC20 },
{ "apple2", TGT_APPLE2 },
{ "apple2enh", TGT_APPLE2ENH },
{ "atari", TGT_ATARI },
{ "atari2600", TGT_ATARI2600 },
{ "atari5200", TGT_ATARI5200 },
{ "atarixl", TGT_ATARIXL },
{ "atmos", TGT_ATMOS },
{ "bbc", TGT_BBC },
{ "c128", TGT_C128 },
{ "c16", TGT_C16 },
{ "c64", TGT_C64 },
{ "c65", TGT_C65 },
{ "cbm510", TGT_CBM510 },
{ "cbm610", TGT_CBM610 },
{ "creativision", TGT_CREATIVISION },
{ "gamate", TGT_GAMATE },
{ "geos", TGT_GEOS_CBM },
{ "geos-apple", TGT_GEOS_APPLE },
{ "geos-cbm", TGT_GEOS_CBM },
{ "lunix", TGT_LUNIX },
{ "lynx", TGT_LYNX },
{ "module", TGT_MODULE },
{ "nes", TGT_NES },
{ "none", TGT_NONE },
{ "osic1p", TGT_OSIC1P },
{ "pce", TGT_PCENGINE },
{ "pet", TGT_PET },
{ "plus4", TGT_PLUS4 },
{ "sim6502", TGT_SIM6502 },
{ "sim65c02", TGT_SIM65C02 },
{ "supervision", TGT_SUPERVISION },
{ "telestrat", TGT_TELESTRAT },
{ "vic20", TGT_VIC20 },
};
#define MAP_ENTRY_COUNT (sizeof (TargetMap) / sizeof (TargetMap[0]))
@ -199,6 +200,7 @@ static const TargetProperties PropertyTable[TGT_COUNT] = {
{ "apple2", CPU_6502, BINFMT_BINARY, CTNone },
{ "apple2enh", CPU_65C02, BINFMT_BINARY, CTNone },
{ "geos-cbm", CPU_6502, BINFMT_BINARY, CTNone },
{ "creativision", CPU_6502, BINFMT_BINARY, CTNone },
{ "geos-apple", CPU_65C02, BINFMT_BINARY, CTNone },
{ "lunix", CPU_6502, BINFMT_O65, CTNone },
{ "atmos", CPU_6502, BINFMT_BINARY, CTNone },

View File

@ -71,6 +71,7 @@ typedef enum {
TGT_APPLE2,
TGT_APPLE2ENH,
TGT_GEOS_CBM,
TGT_CREATIVISION,
TGT_GEOS_APPLE,
TGT_LUNIX,
TGT_ATMOS,
@ -89,7 +90,7 @@ typedef enum {
/* Collection of target properties */
typedef struct TargetProperties TargetProperties;
struct TargetProperties {
const char Name[12]; /* Name of the target */
const char Name[13]; /* Name of the target */
cpu_t DefaultCPU; /* Default CPU for this target */
unsigned char BinFmt; /* Default binary format for this target */
const unsigned char* CharMap; /* Character translation table */

View File

@ -46,7 +46,7 @@ int main (void)
clrscr ();
count = joy_count ();
#ifdef __ATARI5200__
#if defined(__ATARI5200__) || defined(__CREATIVISION__)
cprintf ("JOYSTICKS: %d", count);
#else
cprintf ("Driver supports %d joystick(s)", count);
@ -55,13 +55,13 @@ int main (void)
for (i = 0; i < count; ++i) {
gotoxy (0, i+1);
j = joy_read (i);
#ifdef __ATARI5200__
#if defined(__ATARI5200__) || defined(__CREATIVISION__)
cprintf ("%1d:%-3s%-3s%-3s%-3s%-3s%-3s",
i,
(j & joy_masks[JOY_UP])? " U " : " u ",
(j & joy_masks[JOY_DOWN])? " D " : " d ",
(j & joy_masks[JOY_LEFT])? " L " : " l ",
(j & joy_masks[JOY_RIGHT])? " R " : " r ",
(j & joy_masks[JOY_UP])? " U " : " ",
(j & joy_masks[JOY_DOWN])? " D " : " ",
(j & joy_masks[JOY_LEFT])? " L " : " ",
(j & joy_masks[JOY_RIGHT])? " R " : " ",
(j & joy_masks[JOY_FIRE])? " 1 " : " ",
(j & joy_masks[JOY_FIRE2])? " 2 " : " ");
#else