Merge pull request #34 from FeralChild64/master

Various compatibility fixes
This commit is contained in:
gardners authored and GitHub committed 2019-10-26 10:42:44 +10:30
commit b7fd149811
261 files changed
+5247 -2112

No files matched your search

+113 -10
View File
@@ -1,7 +1,7 @@
# Configuring the build
It's not possible to provide ROM builds that suit everyone needs - therefore configuration files were introduced, separately for each of the hardware targets:
It's not possible to provide ROM builds that suit everyone needs - therefore configuration files were introduced, few predefined configurations are provided with sane defaults:
* [`c64/,,config_generic.s`](c64/,,config_generic.s)
* [`c64/,,config_mega65.s`](c64/,,config_mega65.s)
@@ -11,7 +11,33 @@ Just edit them and recompile the project. To enable particular option - uncommen
Note however, that features do not came for free - enabling them needs some additional ROM space (in BASIC segment, in KERNAL segment, or in both), which is VERY limited on the target machines. Some options might be unavailable for speecific targets - read the comments in the configuration files. Some options might also carry compatibility and/or performance hit - so choose wisely.
Sane defaults are already present - different for each target.
## Hardware platform and brand
### `CONFIG_PLATFORM_COMMODORE_64`
Commodore 64 is the only hardware platform available now - and the main one, as the Open ROMs API is meant to be compatible with the Commodore 64.
Since Open ROMs is highly modular, it should be possible to add other platforms in the future (like 8-bit Atari computers or Commander X16), if they share the following common characteristics:
* MOS 6502 CPU or compatible
* 8KB ROM area `$A000`-`$BFFF`
* 8KB ROM area `$E000`-`$FFFF`
### `CONFIG_MB_MEGA_65`, `CONFIG_MB_ULTIMATE_64`
Select if the ROM is going to be used exclusively on the specific motherboard. It prevents from enabling options not having sense, skips initialization of C128-only registers, etc.
### `CONFIG_BRAND_GENERIC`
If you don't know which variant to choose - select this one.
### `CONFIG_BRAND_TESTING`
Use this one for any kind of testing/experimental build.
### `CONFIG_BRAND_MEGA_65`, `CONFIG_BRAND_ULTIMATE_64`
Select if you are using appropriate motherboard.
## Processor instruction set
@@ -30,10 +56,17 @@ If unsure - select this one.
Choose if your CPU supports the Western Design Center 65C02 instruction set, like:
* WDC 65C02 - used in the Turbo Master accelerator
* CSG 65CE02
* CSG 4510 - used in the Commodore 65 prototypes
It enables some speed/size code optimizations. Warning - this is untested!
It enables some speed/size code optimizations.
### `CONFIG_CPU_CSG_65CE02`
Choose if your CPU supports the Commodore Semiconductor Group 65CE02 instruction set, like:
* CSG 65CE02
* CSG 4510 - microcontroller used in the Commodore 65 prototypes
It enables some speed/size code optimizations.
### `CONFIG_CPU_WDC_65816`
@@ -42,9 +75,9 @@ Choose if your CPU supports the 16-bit Western Design Center 65816 instruction s
* WDC 65C816 - used in the Flash 8 accelerator
* WDC 65C816S - used in the SuperCPU accelerator
It enables some speed/size code optimizations. Warning - this is untested!
It enables some speed/size code optimizations.
## Memory models
## Memory model
Different layouts of memory are possible - but they can be selected at compile time only.
@@ -80,13 +113,83 @@ Cause the system to support SIDs in `$D4xx` and `$D5xx` ranges, respectively.
Each of them needs a couple of bytes in KERNAL segment - but they can share some code, and `$D4xx` range support replaces the standard `$D400` address handling, so exact amount depends on the exact configuration.
## Miscelaneous features
## Keyboard
Original keyboard support routine is just horrible. It does nothing to prevent ghosting - press A+S+D at the same time - it prints F. Try to use joystick connected to control port 1 - it outputs phantom characters. The Open ROMs provides much more sophisticated routines to prevent such problems.
### `CONFIG_LEGACY_SCNKEY`
Uses old Open ROMs keyboard scanning routine, which is basically example routine by TWW/CTR, hacked to work within Kernal. It's greatest advantage is multi-key rollover, it's disadvantages - it's much less compatible (uses several bytes of memory which are normally free for user software - thus, it is considered legacy for now), does not support all the system variables (`RPTFLG` and `KEYLOG` are unsupported), and ignores the configuration options - this can be changed, but it requires some effort.
Needs 30-250 more space in KERNAL segment (depending on the features enabled for current default routine). If unsure - disable.
### `CONFIG_KEYBOARD_C128`
Allows to use additional keys found on the C128 keyboard. NOTE: might be buggy, on VICE emulator I can't get all the keys working.
Needs about 130 bytes more space in KERNAL segment. If unsure - disable.
### `CONFIG_KEYBOARD_C128_CAPS_LOCK`
Allows to use CAPS LOCK key on the C128 keyboard, this is independent from `CONFIG_KEYBOARD_C128`. Support is C64-safe (there is a protection against false-positive reading on the C64).
Needs about 50 bytes more space in KERNAL segment. If unsure - disable.
### `CONFIG_KEY_REPEAT_DEFAULT`
Enables key repetition by default during the startup (sets `RPTFLG`).
Needs 5 bytes more space in KERNAL segment.
### `CONFIG_KEY_REPEAT_ALWAYS`
Enables the key repetition and ignores `RPTFLG`.
Saves 22 bytes from KERNAL segment.
### `CONFIG_KEY_FAST_SCAN`
Performs somee speed optimizations in the keyboard scanning routine, at the eexpense of some more ROM space.
Needs 13 bytes more space in KERNAL segment. Only disable if you are running out of ROM space.
### `CONFIG_JOY1_CURSOR` and `CONFIG_JOY2_CURSOR`
Joystick movement also moves the cursor.
Needs about 65 bytes of ROM space to handle both joysticks.
## Eye candy
### `CONFIG_COLORS_BRAND`
Tries to adjust the color scheme to the selected brand. Some brands might not support this.
### `CONFIG_BANNER_SIMPLE`, `CONFIG_BANNER_FANCY`, `CONFIG_BANNER_BRAND`
Select startup banner - either a simple one, or with some colorful elements. `CONFIG_BANNER_BRAND` heavily depends on the selected brand, not all the brands support it.
Richer banners need more BASIC segment, varies between brands.
### `CONFIG_BANNER_PAL_NTSC`
If enabled, prints video system on startup banner. Eye candy only.
Feature needs some bytes in BASIC (depending on banner type) and about 25 bytes in KERNAL segment.
## Software features
### `CONFIG_PANIC_SCREEN`
If enabled, certain fatal errors will produce a nice bluescreen instead of just resetting the machine.
Feature needs over 100 bytes in KERNAL segment. If unsure - enable.
### `CONFIG_DOS_WEDGE`
If enabled, a simple DOS wedge is available from the direct mode - supports `@<drive_number>`, `@<command>`, `@$`, `@$<params>` and `@` commands.
Feature needs about 330 bytes in BASIC segment.
Feature needs about 330 bytes in BASIC segment. If unsure - enable.
### `CONFIG_BCD_SAFE_INTERRUPTS`
@@ -104,4 +207,4 @@ Replaces `RTS` stubbed routines implementation with one causing a break.
### `CONFIG_DBG_PRINTF`
Makes 'printf' routine available.
Makes `printf` routine available.
+66 -36
View File
@@ -1,17 +1,26 @@
# Source files
SRCDIR_COMMON = c64/aliases
SRCDIR_BASIC_COMMON = $(SRCDIR_COMMON) c64/basic
SRCDIR_KERNAL_COMMON = $(SRCDIR_COMMON) c64/kernal c64/kernal/assets c64/kernal/jumptable c64/kernal/iec c64/kernal/interrupts c64/kernal/print
SRCDIR_COMMON = c64/aliases
SRCDIR_BASIC_generic = $(SRCDIR_BASIC_COMMON) c64/basic/,target_generic
SRCDIR_BASIC_mega65 = $(SRCDIR_BASIC_COMMON) c64/basic/,target_mega65
SRCDIR_BASIC_ultimate64 = $(SRCDIR_BASIC_COMMON) c64/basic/,target_ultimate64
SRCDIR_BASIC = $(SRCDIR_COMMON) \
c64/basic \
c64/basic/commands \
c64/basic/init \
c64/basic/rom_revision
SRCDIR_KERNAL_generic = $(SRCDIR_KERNAL_COMMON) c64/kernal/,target_generic
SRCDIR_KERNAL_mega65 = $(SRCDIR_KERNAL_COMMON) c64/kernal/,target_mega65
SRCDIR_KERNAL_ultimate64 = $(SRCDIR_KERNAL_COMMON) c64/kernal/,target_ultimate64
SRCDIR_KERNAL = $(SRCDIR_COMMON) \
c64/kernal \
c64/kernal/assets \
c64/kernal/jumptable \
c64/kernal/iec \
c64/kernal/init \
c64/kernal/interrupts \
c64/kernal/iostack \
c64/kernal/keyboard \
c64/kernal/print \
c64/kernal/screen \
c64/kernal/stubs
SRC_TOOLS = $(wildcard src/tools/*.c,src/tools/*.cc)
@@ -26,6 +35,7 @@ TOOL_COLLECT_DATA = build/tools/collect_data
TOOL_COMPRESS_TEXT = build/tools/compress_text
TOOL_PNGPREPARE = build/tools/pngprepare
TOOL_BUILD_SEGMENT = build/tools/build_segment
TOOL_RELEASE = build/tools/release
TOOL_SIMILARITY = build/tools/similarity
TOOL_ASSEMBLER = assembler/KickAss.jar
@@ -34,6 +44,7 @@ TOOLS_LIST = $(pathsubst src/tools/%,build/tools/%,$(basename $(SRC_TOOLS)))
# List of targets
STD_TARGET_LIST = build/kernal_generic.rom build/basic_generic.rom \
build/kernal_testing.rom build/basic_testing.rom \
build/kernal_mega65.rom build/basic_mega65.rom \
build/kernal_ultimate64.rom build/basic_ultimate64.rom \
build/chargen.rom
@@ -59,30 +70,25 @@ all: $(STD_TARGET_LIST) $(EXT_TARGET_LIST)
clean:
@rm -rf build
updatebin: $(STD_TARGET_LIST)
updatebin: $(STD_TARGET_LIST) $(TOOL_RELEASE)
$(TOOL_RELEASE) -i ./build -o ./bin basic_generic.rom kernal_generic.rom basic_testing.rom kernal_testing.rom basic_mega65.rom kernal_mega65.rom basic_ultimate64.rom kernal_ultimate64.rom
cp build/chargen.rom bin/chargen.rom
cp build/basic_generic.rom bin/basic_generic.rom
cp build/kernal_generic.rom bin/kernal_generic.rom
cp build/basic_mega65.rom bin/basic_mega65.rom
cp build/kernal_mega65.rom bin/kernal_mega65.rom
cp build/basic_ultimate64.rom bin/basic_ultimate64.rom
cp build/kernal_ultimate64.rom bin/kernal_ultimate64.rom
# Rules - tools
$(TOOL_PNGPREPARE): src/pngprepare.c Makefile
$(TOOL_PNGPREPARE): src/pngprepare.c
@mkdir -p build/tools
$(CC) -O2 -Wall -I/usr/local/include -L/usr/local/lib -o $@ $< -lpng
$(TOOL_COMPRESS_TEXT): src/compress_text.c Makefile
$(TOOL_COMPRESS_TEXT): src/compress_text.c
@mkdir -p build/tools
$(CC) -O2 -Wall -I/usr/local/include -L/usr/local/lib -o $@ $< -lm
build/tools/%: src/%.c Makefile
build/tools/%: src/%.c
@mkdir -p build/tools
$(CC) -O2 -Wall -o $@ $<
build/tools/%: src/%.cc Makefile
build/tools/%: src/%.cc src/common.h
@mkdir -p build/tools
$(CXX) -O2 -Wall -o $@ $<
@@ -94,44 +100,56 @@ build/chargen.rom: $(TOOL_PNGPREPARE) assets/8x8font.png
# Dependencies - BASIC and KERNAL
build/target_generic/OUTB.BIN build/target_generic/BASIC_combined.vs: \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_BASIC) $(SRCDIR_BASIC_generic) \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_BASIC) $(SRCDIR_BASIC) \
c64/,,config_generic.s build/target_generic/KERNAL_combined.sym \
$(foreach dir,$(SRCDIR_BASIC_generic),$(wildcard $(dir)/*.s))
$(foreach dir,$(SRCDIR_BASIC),$(wildcard $(dir)/*.s))
build/target_testing/OUTB.BIN build/target_generic/BASIC_combined.vs: \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_BASIC) $(SRCDIR_BASIC) \
c64/,,config_testing.s build/target_testing/KERNAL_combined.sym \
$(foreach dir,$(SRCDIR_BASIC),$(wildcard $(dir)/*.s))
build/target_mega65/OUTB.BIN build/target_mega65/BASIC_combined.vs: \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_BASIC) $(SRCDIR_BASIC_mega65) \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_BASIC) $(SRCDIR_BASIC) \
c64/,,config_mega65.s build/target_mega65/KERNAL_combined.sym \
$(foreach dir,$(SRCDIR_BASIC_mega65),$(wildcard $(dir)/*.s))
$(foreach dir,$(SRCDIR_BASIC),$(wildcard $(dir)/*.s))
build/target_ultimate64/OUTB.BIN build/target_ultimate64/BASIC_combined.vs: \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_BASIC) $(SRCDIR_BASIC_ultimate64) \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_BASIC) $(SRCDIR_BASIC) \
c64/,,config_ultimate64.s build/target_ultimate64/KERNAL_combined.sym \
$(foreach dir,$(SRCDIR_BASIC_ultimate64),$(wildcard $(dir)/*.s))
$(foreach dir,$(SRCDIR_BASIC),$(wildcard $(dir)/*.s))
build/target_generic/OUTK.BIN build/target_generic/KERNAL_combined.vs build/target_generic/KERNAL_combined.sym: \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_KERNAL) $(SRCDIR_KERNAL_generic) \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_KERNAL) $(SRCDIR_KERNAL) \
c64/,,config_generic.s \
$(foreach dir,$(SRCDIR_KERNAL_generic),$(wildcard $(dir)/*.s))
$(foreach dir,$(SRCDIR_KERNAL),$(wildcard $(dir)/*.s))
build/target_testing/OUTK.BIN build/target_testing/KERNAL_combined.vs build/target_testing/KERNAL_combined.sym: \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_KERNAL) $(SRCDIR_KERNAL) \
c64/,,config_testing.s \
$(foreach dir,$(SRCDIR_KERNAL),$(wildcard $(dir)/*.s))
build/target_mega65/OUTK.BIN build/target_mega65/KERNAL_combined.vs build/target_mega65/KERNAL_combined.sym: \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_KERNAL) $(SRCDIR_KERNAL_mega65) \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_KERNAL) $(SRCDIR_KERNAL) \
c64/,,config_mega65.s \
$(foreach dir,$(SRCDIR_KERNAL_mega65),$(wildcard $(dir)/*.s))
$(foreach dir,$(SRCDIR_KERNAL),$(wildcard $(dir)/*.s))
build/target_ultimate64/OUTK.BIN build/target_ultimate64/KERNAL_combined.vs build/target_ultimate64/KERNAL_combined.sym: \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_KERNAL) $(SRCDIR_KERNAL_ultimate64) \
$(TOOL_ASSEMBLER) $(TOOL_BUILD_SEGMENT) $(GEN_KERNAL) $(SRCDIR_KERNAL) \
c64/,,config_ultimate64.s \
$(foreach dir,$(SRCDIR_KERNAL_ultimate64),$(wildcard $(dir)/*.s))
$(foreach dir,$(SRCDIR_KERNAL),$(wildcard $(dir)/*.s))
build/target_generic/newrom: build/target_generic/OUTB.BIN build/target_generic/OUTK.BIN
build/target_testing/newrom: build/target_testing/OUTB.BIN build/target_testing/OUTK.BIN
build/target_mega65/newrom: build/target_mega65/OUTB.BIN build/target_mega65/OUTK.BIN
build/target_ultimate64/newrom: build/target_ultimate64/OUTB.BIN build/target_ultimate64/OUTK.BIN
build/kernal_generic.rom: build/target_generic/newrom
build/kernal_testing.rom: build/target_testing/newrom
build/kernal_mega65.rom: build/target_mega65/newrom
build/kernal_ultimate64.rom: build/target_ultimate64/newrom
build/basic_generic.rom: build/target_generic/newrom
build/basic_testing.rom: build/target_testing/newrom
build/basic_mega65.rom: build/target_mega65/newrom
build/basic_ultimate64.rom: build/target_ultimate64/newrom
build/symbols_generic.vs: build/target_generic/BASIC_combined.vs build/target_generic/KERNAL_combined.vs
build/symbols_testing.vs: build/target_testing/BASIC_combined.vs build/target_testing/KERNAL_combined.vs
build/symbols_mega65.vs: build/target_mega65/BASIC_combined.vs build/target_mega65/KERNAL_combined.vs
build/symbols_ultimate64.vs: build/target_ultimate64/BASIC_combined.vs build/target_ultimate64/KERNAL_combined.vs
@@ -145,13 +163,13 @@ build/,generated/packed_messages.s: $(TOOL_COMPRESS_TEXT)
build/target_%/OUTB.BIN build/target_%/BASIC_combined.vs:
@mkdir -p build/target_$*
@rm -f $@* build/target_$*/BASIC*
@$(TOOL_BUILD_SEGMENT) -a ../../$(TOOL_ASSEMBLER) -s BASIC -i BASIC-$* -o OUTB.BIN -d build/target_$* -l a000 -h e4d2 c64/,,config_$*.s $(SRCDIR_BASIC_$*) $(GEN_BASIC)
@$(TOOL_BUILD_SEGMENT) -a ../../$(TOOL_ASSEMBLER) -s BASIC -i BASIC-$* -o OUTB.BIN -d build/target_$* -l a000 -h e4d2 c64/,,config_$*.s $(SRCDIR_BASIC) $(GEN_BASIC)
.PRECIOUS: build/target_%/OUTK.BIN build/target_%/KERNAL_combined.vs build/target_%/KERNAL_combined.sym
build/target_%/OUTK.BIN build/target_%/KERNAL_combined.vs build/target_%/KERNAL_combined.sym:
@mkdir -p build/target_$*
@rm -f $@* build/target_$*/KERNAL*
@$(TOOL_BUILD_SEGMENT) -a ../../$(TOOL_ASSEMBLER) -s KERNAL -i KERNAL-$* -o OUTK.BIN -d build/target_$* -l e4d3 -h ffff c64/,,config_$*.s $(SRCDIR_KERNAL_$*) $(GEN_KERNAL)
@$(TOOL_BUILD_SEGMENT) -a ../../$(TOOL_ASSEMBLER) -s KERNAL -i KERNAL-$* -o OUTK.BIN -d build/target_$* -l e4d3 -h ffff c64/,,config_$*.s $(SRCDIR_KERNAL) $(GEN_KERNAL)
.PRECIOUS: build/target_%/newrom
build/target_%/newrom:
@@ -183,7 +201,7 @@ build/symbols_hybrid.vs: build/target_generic/KERNAL_combined.vs
# Rules - platform 'Mega 65' specific
build/newc65.rom: build/kernal_mega65.rom build/basic_mega65.rom build/chargen.rom Makefile
build/newc65.rom: build/kernal_mega65.rom build/basic_mega65.rom build/chargen.rom
dd if=/dev/zero bs=4096 count=10 of=build/newc65.rom
cat build/basic_mega65.rom build/chargen.rom build/chargen.rom build/kernal_mega65.rom >> build/newc65.rom
dd if=/dev/zero bs=65536 count=1 of=build/padding
@@ -192,16 +210,28 @@ build/newc65.rom: build/kernal_mega65.rom build/basic_mega65.rom build/chargen.r
# Rules - tests
.PHONY: test test_generic test_mega65 test_ultimate64 test_m65 testremote testsimilarity
.PHONY: test test_generic test_generic_x128 test_hybrid test_testing \
test_mega65 test_mega65_xemu test_m65 \
test_ultimate64 \
testremote testsimilarity
test: test_generic
test_generic: build/kernal_generic.rom build/basic_generic.rom build/symbols_generic.vs
x64 -kernal build/kernal_generic.rom -basic build/basic_generic.rom -moncommands build/symbols_generic.vs -8 empty.d64
test_generic_x128: build/kernal_generic.rom build/basic_generic.rom build/symbols_generic.vs
x128 -go64 -kernal64 build/kernal_generic.rom -basic64 build/basic_generic.rom -moncommands build/symbols_generic.vs -8 empty.d64
test_testing: build/kernal_testing.rom build/basic_testing.rom build/symbols_testing.vs
x64 -kernal build/kernal_testing.rom -basic build/basic_testing.rom -moncommands build/symbols_testing.vs -8 empty.d64
test_mega65: build/kernal_mega65.rom build/basic_mega65.rom build/symbols_mega65.vs
x64 -kernal build/kernal_mega65.rom -basic build/basic_mega65.rom -moncommands build/symbols_mega65.vs -8 empty.d64
test_mega65_xemu: build/newc65.rom
../xemu/build/bin/xc65.native -dmarev 2 -rom build/newc65.rom
test_ultimate64: build/kernal_ultimate64.rom build/basic_ultimate64.rom build/symbols_ultimate64.vs
x64 -kernal build/kernal_ultimate64.rom -basic build/basic_ultimate64.rom -moncommands build/symbols_ultimate64.vs -8 empty.d64
+86 -67
View File
@@ -3,8 +3,8 @@
Here are the features of the Open ROMs not found in the original ROMs from the 80s (many of them are [configurable](CONFIG.md)):
* improved keyboard scanning, supports multi-key roll-over and rejection of spurious joystick input
* joystick (port 1) can be used to move text cursor
* improved keyboard scanning, supports anti-ghosting and is resistant to joystick interference (one variant even supports multi-keyy rollover)
* joystick can be used to move text cursor
* uses RAM under ROM and I/O: 61438 bytes free
* cold/warm start silences multiple SID chips - all $D4xx and $D5xx addresses
* wark start due to BRK prints out the instruction address
@@ -29,7 +29,7 @@ The following ROM features are currently missing:
* tape support
* RS-232 support
* breaking Kernal routines with RUN/STOP key
* NMI andling is incomplete
* NMI handling is incomplete
# API status
@@ -62,8 +62,8 @@ Note: vectors at `$0300` are not supported yet - for now only the locations belo
| `(00306)` | `$A71A` | `QPLOP` | NOT DONE | some implementation exists, but not connected here |
| `(00308)` | `$A7E4` | `GONE` | NOT DONE | some implementation exists, but not connected here |
| `(0030A)` | `$AE86` | `EVAL` | NOT DONE | some implementation exists, but not connected here |
| `($A000)` | | cold start | PARTIAL | |
| `($A002)` | | warm start | PARTIAL | |
| `($A000)` | `$E394` | cold start | PARTIAL | |
| `($A002)` | `$E3B7` | warm start | PARTIAL | |
<br />
@@ -76,10 +76,15 @@ Not all of them - only these we want to have implemented.
| Address | Name | Status | Remarks |
| :-------: | :----------- | :------: | :------------------------------------------------: |
| `$A004` | revision str | DONE | |
| `$A68E` | RUNC | NOT DONE | |
| `$A7AE` | NEWSTT | NOT DONE | |
| `$A408` | REASON | NOT DONE | |
| `$A453` | (unknown) | NOT DONE | |
| `$A533` | LINKPRG | DONE | |
| `$A644` | new | NOT DONE | |
| `$A659` | set txt ptr | NOT DONE | |
| `$A68E` | RUNC | DONE | |
| `$A7AE` | NEWSTT | PARTIAL | redirected to RUN command |
| `$AB1E` | STROUT | DONE | |
| `$BDCD` | LINPRT | NOT DONE | |
| `$BDCD` | LINPRT | DONE | temporary implementation |
| `$E3BF` | INIT | NOT DONE | |
| `$E422` | INITMSG | DONE | |
| `$E453` | RVECT | NOT DONE | |
@@ -94,53 +99,53 @@ NOTE: Even the 'DONE' routines won't support features described as missing in on
<br />
| Address | Unofficial | Name | Status | Remarks |
| :-------: | :--------: | :---------- | :------: | :------------------------------------------------: |
| `($028F)` | | `KEYLOG` | NOT DONE | |
| `$FF81` | `$FF5B` | `CINT` | DONE | |
| `$FF84` | `$FDA3` | `IOINIT` | PARTIAL | CIA initialization incomplete |
| `$FF87` | `$FD50` | `RAMTAS` | DONE | |
| `$FF8A` | `$FD15` | `RESTOR` | DONE | |
| `$FF8D` | `$FD1A` | `VECTOR` | DONE | |
| `$FF90` | | `SETMSG` | DONE | |
| `$FF93` | | `SECOND` | DONE | |
| `$FF96` | | `TKSA` | DONE | |
| `$FF99` | | `MEMTOP` | DONE | |
| `$FF9C` | | `MEMBOT` | DONE | |
| `$FF9F` | | `SCNKEY` | DONE | could be better integrated with ROM (aliases) |
| `$FFA2` | | `SETTMO` | DONE | |
| `$FFA5` | | `ACPTR` | DONE | |
| `$FFA8` | | `CIOUT` | DONE | |
| `$FFAB` | | `UNTLK` | DONE | |
| `$FFAE` | | `UNLSN` | DONE | |
| `$FFB1` | | `LISTEN` | DONE | |
| `$FFB4` | | `TALK` | DONE | |
| `$FFB7` | | `READST` | DONE | |
| `$FFBA` | | `SETFLS` | DONE | |
| `$FFBD` | | `SETNAM` | DONE | |
| `$FFC0` | `$F34A` | `OPEN` | DONE | |
| `$FFC3` | `$F291` | `CLOSE` | DONE | |
| `$FFC6` | `$F20E` | `CHKIN` | DONE | |
| `$FFC9` | `$F250` | `CKOUT` | PARTIAL | |
| `$FFCC` | `$F333` | `CLRCHN` | DONE | |
| `$FFCF` | `$F157` | `CHRIN` | PARTIAL | |
| `$FFD2` | `$F1CA` | `CHROUT` | PARTIAL | |
| `$FFD5` | `$F49E` | `LOAD` | PARTIAL | not yet clear what's this entry doing |
| `($0330)` | `$F4A5` | `LOAD` | PARTIAL | no VERIFY support, no STOP key, check $F49E addr |
| `$FFD8` | `$F5DD` | `SAVE` | NOT DONE | |
| `($0332)` | `$F5ED` | `SAVE` | NOT DONE | |
| `$FFDB` | | `SETTIM` | DONE | |
| `$FFDE` | | `RDTIM` | DONE | |
| `$FFE1` | `$F6ED` | `STOP` | DONE | |
| `$FFE4` | `$F13E` | `GETIN` | PARTIAL | only some devices supported |
| `$FFE7` | `$F32F` | `CLALL` | DONE | |
| `$FFEA` | | `UDTIM` | DONE | |
| `$FFED` | | `SCREEN` | DONE | |
| `$FFF0` | `$E50A` | `PLOT` | PARTIAL | |
| `$FFF3` | | `IOBASE` | DONE | |
| `($FFFA)` | | NMI vec | PARTIAL | |
| `($FFFC)` | | RESET vec | PARTIAL | |
| `($FFFE)` | | IRQ/BRK vec | PARTIAL | |
| Address | Unofficial | Name | Status | Remarks |
| :-------: | :--------: | :---------- | :------: | :--------------------------------------------------: |
| `($028F)` | | `KEYLOG` | DONE | |
| `$FF81` | `$FF5B` | `CINT` | DONE | |
| `$FF84` | `$FDA3` | `IOINIT` | PARTIAL | CIA initialization might be incomplete |
| `$FF87` | `$FD50` | `RAMTAS` | PARTIAL | probably shouldn't touch VIC and CIA's |
| `$FF8A` | `$FD15` | `RESTOR` | DONE | |
| `$FF8D` | `$FD1A` | `VECTOR` | DONE | |
| `$FF90` | | `SETMSG` | DONE | |
| `$FF93` | | `SECOND` | DONE | |
| `$FF96` | | `TKSA` | DONE | |
| `$FF99` | `$FE25` | `MEMTOP` | DONE | |
| `$FF9C` | | `MEMBOT` | DONE | |
| `$FF9F` | | `SCNKEY` | DONE | |
| `$FFA2` | | `SETTMO` | DONE | |
| `$FFA5` | | `ACPTR` | DONE | |
| `$FFA8` | | `CIOUT` | DONE | |
| `$FFAB` | | `UNTLK` | DONE | |
| `$FFAE` | | `UNLSN` | DONE | |
| `$FFB1` | | `LISTEN` | DONE | |
| `$FFB4` | | `TALK` | DONE | |
| `$FFB7` | | `READST` | DONE | |
| `$FFBA` | | `SETFLS` | DONE | |
| `$FFBD` | | `SETNAM` | DONE | |
| `$FFC0` | `$F34A` | `OPEN` | DONE | |
| `$FFC3` | `$F291` | `CLOSE` | DONE | |
| `$FFC6` | `$F20E` | `CHKIN` | DONE | |
| `$FFC9` | `$F250` | `CKOUT` | PARTIAL | |
| `$FFCC` | `$F333` | `CLRCHN` | DONE | |
| `$FFCF` | `$F157` | `CHRIN` | PARTIAL | |
| `$FFD2` | `$F1CA` | `CHROUT` | PARTIAL | |
| `$FFD5` | `$F49E` | `LOAD` | PARTIAL | not yet clear what's this entry doing |
| `($0330)` | `$F4A5` | `LOAD` | PARTIAL | no VERIFY support, no STOP key, check $F49E addr |
| `$FFD8` | `$F5DD` | `SAVE` | NOT DONE | |
| `($0332)` | `$F5ED` | `SAVE` | NOT DONE | |
| `$FFDB` | | `SETTIM` | DONE | |
| `$FFDE` | | `RDTIM` | DONE | |
| `$FFE1` | `$F6ED` | `STOP` | DONE | |
| `$FFE4` | `$F13E` | `GETIN` | PARTIAL | only keyboard supported |
| `$FFE7` | `$F32F` | `CLALL` | DONE | |
| `$FFEA` | | `UDTIM` | DONE | |
| `$FFED` | | `SCREEN` | DONE | |
| `$FFF0` | `$E50A` | `PLOT` | DONE | |
| `$FFF3` | | `IOBASE` | DONE | |
| `($FFFA)` | | NMI vec | PARTIAL | |
| `($FFFC)` | `$FCE2` | RESET vec | PARTIAL | |
| `($FFFE)` | | IRQ/BRK vec | PARTIAL | |
<br />
@@ -150,17 +155,31 @@ Not all of them - only these we want to have implemented.
<br />
| Address | Name | Status | Remarks |
| :-------: | :------------------ | :------: | :------------------------------------------------: |
| `$E544` | clear screen | DONE | |
| `$E50C` | set cursor position | PARTIAL | |
| `$E5A0` | setup VIC II & IO | PARTIAL | |
| `$EA31` | default IRQ | PARTIAL | |
| `$EA7E` | ack CIA1 + below | DONE | |
| `$EA81` | ret from IRQ/NMI | DONE | |
| `$FD30` | default vectors | DONE | |
| `$FE47` | default NMI | PARTIAL | |
| `$FE66` | default BRK | DONE | |
| `$FF80` | revision byte | DONE | |
| Address | Name | Status | Remarks |
| :-------: | :--------------------------- | :------: | :------------------------------------------------: |
| `$E518` | legacy part of CINT | DONE | |
| `$E51B` | init screen keyboard, no VIC | DONE | |
| `$E544` | clear screen | DONE | |
| `$E50C` | set cursor position | PARTIAL | |
| `$E566` | home cursor | NOT DONE | |
| `$E5A0` | setup VIC II & IO | DONE | |
| `$E6B6` | advance cursor | NOT DONE | |
| `$E701` | previous line | NOT DONE | |
| `$E716` | screen CHROUT | NOT DONE | |
| `$E8EA` | scroll line | NOT DONE | |
| `$E96C` | insert line on top | NOT DONE | |
| `$E9FF` | clear line | NOT DONE | |
| `$EA31` | default IRQ | PARTIAL | |
| `$EA7E` | ack CIA1 + below | DONE | |
| `$EA81` | ret from IRQ/NMI | DONE | |
| `$F142` | get key from buffer | DONE | |
| `$F646` | IEC close | NOT DONE | |
| `$FD30` | default vectors | DONE | |
| `$FD90` | (unknown) | NOT DONE | |
| `$FD90` | (unknown) | NOT DONE | |
| `$FE2D` | memtop set part | DONE | |
| `$FE47` | default NMI | PARTIAL | |
| `$FE66` | default BRK | DONE | |
| `$FF80` | revision byte | DONE | |
<br />
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
+56 -1
View File
@@ -1,16 +1,44 @@
.const CONFIG_ID = $00 // should be 1 byte, different for each config file!
//
// Please read CONFIG.md before modifying this file!
//
// Idea:
// - sane defaults for the original Commodore 64/128 machines
// - do not enable features which are a significant compatibility risk
// Hardware platform and brand
#define CONFIG_PLATFORM_COMMODORE_64
// #define CONFIG_MB_MEGA_65
// #define CONFIG_MB_ULTIMATE_64
#define CONFIG_BRAND_GENERIC
// #define CONFIG_BRAND_TESTING
// #define CONFIG_BRAND_MEGA_65
// #define CONFIG_BRAND_ULTIMATE_64
// Processor instruction set
#define CONFIG_CPU_MOS_6502
// #define CONFIG_CPU_WDC_65C02
// #define CONFIG_CPU_CSG_65CE02
// #define CONFIG_CPU_WDC_65816
// Memory model
#define CONFIG_MEMORY_MODEL_38K
// #define CONFIG_MEMORY_MODEL_60K
// Multiple SID support
// #define CONFIG_SID_2ND
.const CONFIG_SID_2ND_ADDRESS = $D420
@@ -20,9 +48,36 @@
// #define CONFIG_SID_D4XX
// #define CONFIG_SID_D5XX
// Keyboard settings
// #define CONFIG_LEGACY_SCNKEY
#define CONFIG_KEYBOARD_C128 // incomplete
#define CONFIG_KEYBOARD_C128_CAPS_LOCK
// #define CONFIG_KEY_REPEAT_DEFAULT
// #define CONFIG_KEY_REPEAT_ALWAYS
#define CONFIG_KEY_FAST_SCAN
#define CONFIG_JOY1_CURSOR
#define CONFIG_JOY2_CURSOR
// Eye candy
#define CONFIG_COLORS_BRAND
// #define CONFIG_BANNER_SIMPLE
#define CONFIG_BANNER_FANCY
// #define CONFIG_BANNER_BRAND
#define CONFIG_SHOW_PAL_NTSC
// Software features
#define CONFIG_PANIC_SCREEN
#define CONFIG_DOS_WEDGE
#define CONFIG_BCD_SAFE_INTERRUPTS
#define CONFIG_EXTENDED_SCNKEY // for now has to be enabled
// Debug options
// #define CONFIG_DBG_STUBS_BRK
// #define CONFIG_DBG_PRINTF
+60 -3
View File
@@ -1,15 +1,45 @@
.const CONFIG_ID = $01 // should be 1 byte, different for each config file!
//
// Please read CONFIG.md before modifying this file!
//
// Idea:
// - sane defaults for the Mega 65 FPGA computer
// - do not enable features which are a significant compatibility risk
// - unless VICE gains Commodore 65 (or at least Flash8 cartridge) emulation support,
// do not enable CPU-specific optimizations; ROMs would be hard to test
// Hardware platform and brand
#define CONFIG_PLATFORM_COMMODORE_64
#define CONFIG_MB_MEGA_65
// #define CONFIG_MB_ULTIMATE_64
// #define CONFIG_BRAND_GENERIC
// #define CONFIG_BRAND_TESTING
#define CONFIG_BRAND_MEGA_65
// #define CONFIG_BRAND_ULTIMATE_64
// Processor instruction set
#define CONFIG_CPU_MOS_6502
// #define CONFIG_CPU_WDC_65C02
// #define CONFIG_CPU_CSG_65CE02
// #define CONFIG_CPU_WDC_65816
// #define CONFIG_MEMORY_MODEL_38K
#define CONFIG_MEMORY_MODEL_60K
// Memory model configuration
#define CONFIG_MEMORY_MODEL_38K
// #define CONFIG_MEMORY_MODEL_60K
// Multiple SID support
#define CONFIG_SID_2ND
.const CONFIG_SID_2ND_ADDRESS = $D420
@@ -20,9 +50,36 @@
// #define CONFIG_SID_D4XX
// #define CONFIG_SID_D5XX
// Keyboard settings
// #define CONFIG_LEGACY_SCNKEY
// #define CONFIG_KEYBOARD_C128 // incomplete
// #define CONFIG_KEYBOARD_C128_CAPS_LOCK
// #define CONFIG_KEY_REPEAT_DEFAULT
// #define CONFIG_KEY_REPEAT_ALWAYS
#define CONFIG_KEY_FAST_SCAN
#define CONFIG_JOY1_CURSOR
#define CONFIG_JOY2_CURSOR
// Eye candy
#define CONFIG_COLORS_BRAND
// #define CONFIG_BANNER_SIMPLE
// #define CONFIG_BANNER_FANCY
#define CONFIG_BANNER_BRAND
// #define CONFIG_SHOW_PAL_NTSC
// Software features
#define CONFIG_PANIC_SCREEN
#define CONFIG_DOS_WEDGE
#define CONFIG_BCD_SAFE_INTERRUPTS
#define CONFIG_EXTENDED_SCNKEY // for now has to be enabled
// Debug options
// #define CONFIG_DBG_STUBS_BRK
// #define CONFIG_DBG_PRINTF
+84
View File
@@ -0,0 +1,84 @@
.const CONFIG_ID = $F0 // should be 1 byte, different for each config file!
//
// Please read CONFIG.md before modifying this file!
//
// Idea:
// - enable compatibility-risky features
// - enable code not normally used - to make sure they still compile
// Hardware platform and brand
#define CONFIG_PLATFORM_COMMODORE_64
// #define CONFIG_MB_MEGA_65
// #define CONFIG_MB_ULTIMATE_64
// #define CONFIG_BRAND_GENERIC
#define CONFIG_BRAND_TESTING
// #define CONFIG_BRAND_MEGA_65
// #define CONFIG_BRAND_ULTIMATE_64
// Processor instruction set
#define CONFIG_CPU_MOS_6502
// #define CONFIG_CPU_WDC_65C02
// #define CONFIG_CPU_CSG_65CE02
// #define CONFIG_CPU_WDC_65816
// Memory model configuration
// #define CONFIG_MEMORY_MODEL_38K
#define CONFIG_MEMORY_MODEL_60K
// Multiple SID support
#define CONFIG_SID_2ND
.const CONFIG_SID_2ND_ADDRESS = $D420
// #define CONFIG_SID_3RD
.const CONFIG_SID_3RD_ADDRESS = $D440
// #define CONFIG_SID_D4XX
// #define CONFIG_SID_D5XX
// Keyboard settings
#define CONFIG_LEGACY_SCNKEY
// #define CONFIG_KEYBOARD_C128 // incomplete
// #define CONFIG_KEYBOARD_C128_CAPS_LOCK
// #define CONFIG_KEY_REPEAT_DEFAULT
// #define CONFIG_KEY_REPEAT_ALWAYS
#define CONFIG_KEY_FAST_SCAN
#define CONFIG_JOY1_CURSOR
#define CONFIG_JOY2_CURSOR
// Eye candy
// #define CONFIG_COLORS_BRAND
// #define CONFIG_BANNER_SIMPLE
#define CONFIG_BANNER_FANCY
// #define CONFIG_BANNER_BRAND
// #define CONFIG_SHOW_PAL_NTSC
// Software features
#define CONFIG_PANIC_SCREEN
#define CONFIG_DOS_WEDGE
#define CONFIG_BCD_SAFE_INTERRUPTS
// Debug options
// #define CONFIG_DBG_STUBS_BRK
#define CONFIG_DBG_PRINTF
+56 -1
View File
@@ -1,16 +1,44 @@
.const CONFIG_ID = $02 // should be 1 byte, different for each config file!
//
// Please read CONFIG.md before modifying this file!
//
// Idea:
// - sane defaults for the Ultimate 64 FPGA computer
// - do not enable features which are a significant compatibility risk
// Hardware platform and brand
#define CONFIG_PLATFORM_COMMODORE_64
// #define CONFIG_MB_MEGA_65
#define CONFIG_MB_ULTIMATE_64
// #define CONFIG_BRAND_GENERIC
// #define CONFIG_BRAND_TESTING
// #define CONFIG_BRAND_MEGA_65
#define CONFIG_BRAND_ULTIMATE_64
// Processor instruction set
#define CONFIG_CPU_MOS_6502
// #define CONFIG_CPU_WDC_65C02
// #define CONFIG_CPU_CSG_65CE02
// #define CONFIG_CPU_WDC_65816
// Memory model configuration
#define CONFIG_MEMORY_MODEL_38K
// #define CONFIG_MEMORY_MODEL_60K
// Multiple SID support
// #define CONFIG_SID_2ND
.const CONFIG_SID_2ND_ADDRESS = $D420
@@ -20,9 +48,36 @@
#define CONFIG_SID_D4XX
#define CONFIG_SID_D5XX
// Keyboard settings
// #define CONFIG_LEGACY_SCNKEY
// #define CONFIG_KEYBOARD_C128 // incomplete
// #define CONFIG_KEYBOARD_C128_CAPS_LOCK
// #define CONFIG_KEY_REPEAT_DEFAULT
// #define CONFIG_KEY_REPEAT_ALWAYS
#define CONFIG_KEY_FAST_SCAN
#define CONFIG_JOY1_CURSOR
#define CONFIG_JOY2_CURSOR
// Eye candy
#define CONFIG_COLORS_BRAND
// #define CONFIG_BANNER_SIMPLE
#define CONFIG_BANNER_FANCY
// #define CONFIG_BANNER_BRAND
#define CONFIG_SHOW_PAL_NTSC
// Software features
#define CONFIG_PANIC_SCREEN
#define CONFIG_DOS_WEDGE
#define CONFIG_BCD_SAFE_INTERRUPTS
#define CONFIG_EXTENDED_SCNKEY // for now has to be enabled
// Debug options
// #define CONFIG_DBG_STUBS_BRK
// #define CONFIG_DBG_PRINTF
+131 -12
View File
@@ -1,9 +1,102 @@
// Various configuration dependent aliases/macros/checks
//
// Various configuration dependent aliases/macros/checks
//
// Check that memory model configuration is correct
// Check that platform configuration is correct
{
.var selected = 0;
#if CONFIG_PLATFORM_COMMODORE_64
.eval selected++
#endif
.if (selected != 1) .error "Please select exactly one CONFIG_PLATFORM_* option"
}
// Check that motherboard extras configuration is correct
{
.var selected = 0;
#if CONFIG_MB_MEGA_65
.eval selected++
#endif
#if CONFIG_MB_ULTIMATE_64
.eval selected++
#endif
.if (selected > 1) .error "Please select at most one CONFIG_MB_* option"
#if !CONFIG_PLATFORM_COMMODORE_64 && CONFIG_BRAND_MEGA_65 &&
.error "CONFIG_BRAND_MEGA_65 can only be used with CONFIG_PLATFORM_COMMODORE_64"
#endif
#if !CONFIG_PLATFORM_COMMODORE_64 && CONFIG_BRAND_ULTIMATE_64 &&
.error "CONFIG_BRAND_ULTIMATE_64 can only be used with CONFIG_PLATFORM_COMMODORE_64"
#endif
}
// Check that brand configuration is correct
{
.var selected = 0;
#if CONFIG_BRAND_GENERIC
.eval selected++
#endif
#if CONFIG_BRAND_TESTING
.eval selected++
#endif
#if CONFIG_BRAND_MEGA_65
.eval selected++
#endif
#if CONFIG_BRAND_ULTIMATE_64
.eval selected++
#endif
.if (selected != 1) .error "Please select exactly one CONFIG_BRAND_* option"
#if CONFIG_MB_MEGA_65 && !(CONFIG_BRAND_MEGA_65 || CONFIG_BRAND_TESTING)
.error "Please select brand either matching the CONFIG_MB_*, or a testing one"
#endif
#if CONFIG_MB_ULTIMATE_64 && !(CONFIG_BRAND_ULTIMATE_64 || CONFIG_BRAND_TESTING)
.error "Please select brand either matching the CONFIG_MB_*, or a testing one"
#endif
}
// Check that processor configuration is correct
{
.var selected = 0;
#if CONFIG_CPU_MOS_6502
.eval selected++
#endif
#if CONFIG_CPU_WDC_65C02
.eval selected++
#endif
#if CONFIG_CPU_CSG_65CE02
.eval selected++
#endif
#if CONFIG_CPU_WDC_65816
.eval selected++
#endif
.if (selected != 1) .error "Please select exactly one CONFIG_CPU_* option"
}
// Check that memory model configuration is correct
{
.var selected = 0;
@@ -20,32 +113,54 @@
// Check that processor configuration is correct
// Check that startup banner configuration is correct
{
.var selected = 0;
#if CONFIG_CPU_MOS_6502
#if CONFIG_BANNER_SIMPLE
.eval selected++
#endif
#if CONFIG_CPU_WDC_65C02
#if CONFIG_BANNER_FANCY
.eval selected++
#endif
#if CONFIG_CPU_WDC_65816
#if CONFIG_BANNER_BRAND
.eval selected++
#endif
.if (selected != 1) .error "Please select exactly one CONFIG_CPU_* option"
.if (selected != 1) .error "Please select exactly one CONFIG_BANNER_* option"
#if CONFIG_BANNER_BRAND && !CONFIG_BRAND_MEGA_65
.error "CONFIG_BANNER_BRAND is not supported for your CONFIG_BRAND_*"
#endif
#if CONFIG_BANNER_BRAND && CONFIG_BRAND_MEGA_65 && CONFIG_SHOW_PAL_NTSC
.error "MEGA65 brand banner does not support showing PAL/NTSC"
#endif
}
// Handle processor configuration
// Check if keyboard options are correct
#if CONFIG_CPU_WDC_65C02 || CONFIG_CPU_WDC_65816
{
#if CONFIG_LEGACY_SCNKEY && (CONFIG_KEYBOARD_C128 || CONFIG_KEYBOARD_C128_CAPS_LOCK)
.error "CONFIG_LEGACY_SCNKEY and CONFIG_KEYBOARD_C128* are mutually exclusive"
#endif
#if (CONFIG_MB_MEGA_65 || CONFIG_MB_ULTIMATE_64) && (CONFIG_KEYBOARD_C128 || CONFIG_KEYBOARD_C128_CAPS_LOCK)
.error "Selected CONFIG_MB_* is not compatible with CONFIG_KEYBOARD_C128*"
#endif
}
// Handle processor configuration
#if CONFIG_CPU_WDC_65C02 || CONFIG_CPU_CSG_65CE02 || CONFIG_CPU_WDC_65816
#define HAS_BCD_SAFE_INTERRUPTS
#define HAS_BCD_SAFE_RESET
.pseudocommand phx { .byte $DA }
.pseudocommand phy { .byte $5A }
@@ -54,13 +169,17 @@
#endif
// Handle misc configuration entrues
// Handle configuration of various features
#if CONFIG_BCD_SAFE_INTERRUPTS
#define HAS_BCD_SAFE_INTERRUPTS
#endif
// Stub configuration
// Handle configuration of debug infrastructure
.macro STUB_IMPLEMENTATION_RTS() {
rts
+165
View File
@@ -0,0 +1,165 @@
//
// Provide pseudocommands to make CPU optimizations easier
//
//
// These are not exactly for optimization - but to encourage proper usage of panic screen
//
.pseudocommand panic code
{
// If case no panic screen is used, we can skip providing error codes within Kernal
#if CONFIG_PANIC_SCREEN || !SEGMENT_KERNAL
lda code
#endif
jmp ($E4B7)
}
//
// Stack manipulation - some CPUs will leave .A unchanged, some will use it as temporary storage, so consider .A trashed
//
.pseudocommand phx_trash_a
{
#if CONFIG_CPU_WDC_65C02 || CONFIG_CPU_CSG_65CE02 || CONFIG_CPU_WDC_65816
phx
#else
txa
pha
#endif
}
.pseudocommand phy_trash_a
{
#if CONFIG_CPU_WDC_65C02 || CONFIG_CPU_CSG_65CE02 || CONFIG_CPU_WDC_65816
phy
#else
tya
pha
#endif
}
.pseudocommand plx_trash_a
{
#if CONFIG_CPU_WDC_65C02 || CONFIG_CPU_CSG_65CE02 || CONFIG_CPU_WDC_65816
plx
#else
pla
tax
#endif
}
.pseudocommand ply_trash_a
{
#if CONFIG_CPU_WDC_65C02 || CONFIG_CPU_CSG_65CE02 || CONFIG_CPU_WDC_65816
ply
#else
pla
tay
#endif
}
//
// Branches with far offsets, substitutes by Bxx + JMP for CPUs not supporting the instruction
//
.pseudocommand bcs_far dst
{
#if CONFIG_CPU_CSG_65CE02
.var offset = mod($10000 + dst.getValue() - *, $10000)
.byte $B3, mod(offset, $100), floor(offset / $100)
#else
bcc __l
jmp dst
__l:
#endif
}
.pseudocommand bcc_far dst
{
#if CONFIG_CPU_CSG_65CE02
.var offset = mod($10000 + dst.getValue() - *, $10000)
.byte $93, mod(offset, $100), floor(offset / $100)
#else
bcs __l
jmp dst
__l:
#endif
}
.pseudocommand beq_far dst
{
#if CONFIG_CPU_CSG_65CE02
.var offset = mod($10000 + dst.getValue() - *, $10000)
.byte $F3, mod(offset, $100), floor(offset / $100)
#else
bne __l
jmp dst
__l:
#endif
}
.pseudocommand bne_far dst
{
#if CONFIG_CPU_CSG_65CE02
.var offset = mod($10000 + dst.getValue() - *, $10000)
.byte $D3, mod(offset, $100), floor(offset / $100)
#else
beq __l
jmp dst
__l:
#endif
}
.pseudocommand bmi_far dst
{
#if CONFIG_CPU_CSG_65CE02
.var offset = mod($10000 + dst.getValue() - *, $10000)
.byte $33, mod(offset, $100), floor(offset / $100)
#else
bpl __l
jmp dst
__l:
#endif
}
.pseudocommand bpl_far dst
{
#if CONFIG_CPU_CSG_65CE02
.var offset = mod($10000 + dst.getValue() - *, $10000)
.byte $13, mod(offset, $100), floor(offset / $100)
#else
bmi __l
jmp dst
__l:
#endif
}
.pseudocommand bvc_far dst
{
#if CONFIG_CPU_CSG_65CE02
.var offset = mod($10000 + dst.getValue() - *, $10000)
.byte $53, mod(offset, $100), floor(offset / $100)
#else
bvs __l
jmp dst
__l:
#endif
}
.pseudocommand bvs_far dst
{
#if CONFIG_CPU_CSG_65CE02
.var offset = mod($10000 + dst.getValue() - *, $10000)
.byte $73, mod(offset, $100), floor(offset / $100)
#else
bvc __l
jmp dst
__l:
#endif
}
+6
View File
@@ -1,4 +1,10 @@
// Error codes for 'panic' pseudocommand
.const P_ERR_NONE = $00
.const P_ERR_ROM_MISMATCH = $01 // this value has to be stable as long as possible
// Kernal error codes - returned in the A register
// Described in 'Commodore 64 Programmer's Reference Guide', page 306
+22 -2
View File
@@ -1,8 +1,11 @@
//
// Names of hardware registers - slightly modified names from C64 Programmer's Reference Guide
// Names of hardware registers - names from C64 Programmer's Reference Guide, sometimes slightly modified
//
#if CONFIG_PLATFORM_COMMODORE_64
// CPU memory registers
.label CPU_D6510 = $00
@@ -61,7 +64,14 @@
.label VIC_SP5COL = $D02C
.label VIC_SP6COL = $D02D
.label VIC_SP7COL = $D02E
#if !CONFIG_MB_MEGA_65 && !CONFIG_MB_ULTIMATE_64
.label VIC_XSCAN = $D02F // C128 only
.label VIC_CLKRATE = $D030 // C128 only
#endif
// SID registers
.label __SID_BASE = $D400 // base address of the chip
@@ -154,3 +164,13 @@
.const BIT_CIA2_PRA_DAT_OUT = $20 // 1 - low (pulled), 0 - high (released)
.const BIT_CIA2_PRA_CLK_IN = $40 // 0 - low (pulled), 1 - high (released)
.const BIT_CIA2_PRA_DAT_IN = $80 // 0 - low (pulled), 1 - high (released)
#if CONFIG_MB_MEGA_65
.const C65_EXTKEYS_PR = $D607
.const C65_EXTKEYS_DDR = $D608
#endif
#endif
+154
View File
@@ -0,0 +1,154 @@
//
// PETSCII codes for all the supported keys, for all the keyboards
//
// - [CM64] Compute's Mapping the Commodore 64
// - [CM128] Compute's Mapping the Commodore 128
// - https://github.com/MEGA65/c65-specifications/blob/master/c65manualupdated.txt
// - https://en.wikipedia.org/wiki/PETSCII
//
// Not really PETSCII codes, but bitmask values for SHFLAG variable
// [CM64] page 68, [CM128] page 212
.const KEY_FLAG_SHIFT = %00000001
.const KEY_FLAG_VENDOR = %00000010
.const KEY_FLAG_CTRL = %00000100
.const KEY_FLAG_ALT = %00001000 // C65 / C128
.const KEY_CAPS_LOCK = %00010000 // C65 / C128
.const KEY_FLAG_NO_SCRL = %00100000 // C65 / C128, Open ROMs unofficial
// Note - the following PETSCII codes are currently unassigned, can be used for further extensions:
//
// $01, $04, $06, $0A, $0B, $0C, $0F, $18, $82
.const KEY_NA = $00 // to indicate that no key is presed
// PETSCII codes for our extended screen editor XXX implement these
.const KEY_BOTTOM = $02 // CTRL+B - Open ROMs unofficial, DolphinDOS compatible
.const KEY_TAB_FW = $8F // CTRL+>, TAB - Open ROMs unofficial, original TAB conflicts with C64 PETSCII
.const KEY_TAB_BW = $80 // CTRL+<, SHIFT+TAB - Open ROMs unofficial, original TAB conflicts with C64 PETSCII
// PETSCII codes for certain C128 and C65 functionalities XXX implement these
.const KEY_BELL = $07 // C65 / C128, no key
.const KEY_ESC = $1B // C65 / C128
// PETSCII codes for programmable keys
.const KEY_STOP = $03
.const KEY_RUN = $83
.const KEY_F1 = $85
.const KEY_F2 = $86
.const KEY_F3 = $87
.const KEY_F4 = $88
.const KEY_F5 = $89
.const KEY_F6 = $8A
.const KEY_F7 = $8B
.const KEY_F8 = $8C
.const KEY_F9 = $10 // C65
.const KEY_F10 = $15 // C65
.const KEY_F11 = $16 // C65
.const KEY_F12 = $17 // C65
.const KEY_F13 = $19 // C65
.const KEY_F14 = $1A // C65
.const KEY_HELP = $84 // C65, also used for our C128 support
// PETSCII codes for cursor keys
.const KEY_CRSR_UP = $91
.const KEY_CRSR_DOWN = $11
.const KEY_CRSR_LEFT = $9D
.const KEY_CRSR_RIGHT = $1D
// PETSCII codes for colors
.const KEY_RVS_ON = $12 // CTRL+9
.const KEY_RVS_OFF = $92 // CTRL+0
.const KEY_BLACK = $90 // CTRL+1
.const KEY_WHITE = $05 // CTRL+2
.const KEY_RED = $1C // CTRL+3
.const KEY_CYAN = $9F // CTRL+4
.const KEY_PURPLE = $9C // CTRL+5
.const KEY_GREEN = $1E // CTRL+6
.const KEY_BLUE = $1F // CTRL+7
.const KEY_YELLOW = $9E // CTRL+8
.const KEY_ORANGE = $81 // VENDOR+1
.const KEY_BROWN = $95 // VENDOR+2
.const KEY_LT_RED = $96 // VENDOR+3
.const KEY_GREY_1 = $97 // VENDOR+4
.const KEY_GREY_2 = $98 // VENDOR+5
.const KEY_LT_GREEN = $99 // VENDOR+6
.const KEY_LT_BLUE = $9A // VENDOR+7
.const KEY_GREY_3 = $9B // VENDOR+8
// PETSCII codes for case toggle
.const KEY_SHIFT_ON = $09 // no key
.const KEY_SHIFT_OFF = $08 // no key
.const KEY_TXT = $0E // no key
.const KEY_GFX = $8E // no key
// PETSCII codes for other non-printable characters
.const KEY_RETURN = $0D
.const KEY_CLR = $93
.const KEY_HOME = $13
.const KEY_INS = $94
.const KEY_DEL = $14
// PETSCII codes for printable characters
.const KEY_SPACE = $20
.const KEY_EXCLAMATION = $21
.const KEY_QUOTE = $22
.const KEY_HASH = $23
.const KEY_DOLLAR = $24
.const KEY_PERCENT = $25
.const KEY_AMPERSAND = $26
.const KEY_APOSTROPHE = $27
.const KEY_R_BRACKET_L = $28
.const KEY_R_BRACKET_R = $29
.const KEY_ASTERISK = $2A
.const KEY_PLUS = $2B
.const KEY_COMA = $2C
.const KEY_MINUS = $2D
.const KEY_FULLSTOP = $2E
.const KEY_SLASH = $2F
.const KEY_0 = $30
.const KEY_1 = $31
.const KEY_2 = $32
.const KEY_3 = $33
.const KEY_4 = $34
.const KEY_5 = $35
.const KEY_6 = $36
.const KEY_7 = $37
.const KEY_8 = $38
.const KEY_9 = $39
.const KEY_COLON = $3A
.const KEY_SEMICOLON = $3B
.const KEY_LT = $3C
.const KEY_EQ = $3D
.const KEY_GT = $3E
.const KEY_QUESTION = $3F
// XXX finish this: $4x, $5x, $6x, $7x, $Ax, $Bx, $Cx, $Dx, $Ex, $Fx
+8 -53
View File
@@ -104,51 +104,22 @@
.label CNTDN = $A5 // -- NOT IMPLEMENTED --
.label BUFPNT = $A6 // -- NOT IMPLEMENTED --
.label INBIT = $A7 // -- NOT IMPLEMENTED --
#if CONFIG_EXTENDED_SCNKEY
// Reuse RS232 variables, since they should not be used by other things.
// Carefully avoid $A7 which is used by 64NET
.label KeyQuantity = $A8 // 1 byte
.label BufferNew = $A9 // 3 bytes
#else
#if !CONFIG_LEGACY_SCNKEY
.label BITCI = $A8 // -- NOT IMPLEMENTED --
.label RINONE = $A9 // -- NOT IMPLEMENTED --
.label RIDDATA = $AA // -- NOT IMPLEMENTED --
.label RIPRTY = $AB // -- NOT IMPLEMENTED --
#endif
.label SAL = $AC // $AC-$AD -- NOT IMPLEMENTED -- (implemented screen part)
.label EAL = $AE // $AE-$AF -- NOT IMPLEMENTED -- [!] used also by screen editor, for temporary color storage when scrolling
.label CMP0 = $B0 // $B0-$B1 temporary tape storage, [!] here used for BRK instruction address
.label TAPE1 = $B2 // $B2-$B3 tape buffer pointer
#if CONFIG_EXTENDED_SCNKEY
// Reuse RS232 variables, since they should not be used by other things.
// This one should be initialized in cinit to $FF
.label BufferQuantity = $B4 // 1 byte
#else
#if !CONFIG_LEGACY_SCNKEY
.label BITTS = $B4 // -- NOT IMPLEMENTED --
#endif
.label NXTBIT = $B5 // -- NOT IMPLEMENTED --
#if CONFIG_EXTENDED_SCNKEY
// Reuse RS232 variables, since they should not be used by other things.
// Carefully avoiding $A7 which is used by 64NET
.label TempZP = $B6 // 1 byte
#else
#if !CONFIG_LEGACY_SCNKEY
.label RODATA = $B6 // -- NOT IMPLEMENTED --
#endif
.label FNLEN = $B7 // current file name length
@@ -182,7 +153,7 @@
.label INSRT = $D8 // insert mode flag/counter
.label LDTBL = $D9 // $D9-$F2 screen line link table, [!] our usage is different XXX give more details
.label USER = $F3 // $F3-$F4 pointer to current color RAM location
.label KEYTAB = $F5 // $F5-$F6 -- NOT IMPLEMENTED --
.label KEYTAB = $F5 // $F5-$F6 pointer to keyboard lookup table
.label RIBUF = $F7 // $F7-$F8 -- NOT IMPLEMENTED --
.label ROBUF = $F9 // $F9-$FA -- NOT IMPLEMENTED --
// $FB $FB-$FE -- UNUSED -- free for user software
@@ -200,13 +171,8 @@
.label BUF = $200 // $200-$250, BASIC line editor input buffer (81 bytes)
#if CONFIG_EXTENDED_SCNKEY
// $250-$258 is the 81st - 88th characters in BASIC input, a carry over from VIC-20
// and not used on C64, so safe for us to use, probably.
.label ScanResult = $250 // 8 bytes
#endif
// and not used on C64 - they are used if CONFIG_LEGACY_SCNKEY is enabled.
// [!] XXX document $251-$258 usage
.label LAT = $259 // $259-$262, logical file numbers (table, 10 bytes)
@@ -220,7 +186,7 @@
.label GDCOL = $287 // color of character under cursor
.label HIBASE = $288 // high byte of start of screen
.label XMAX = $289 // max keyboard buffer size
.label RPTFLG = $28A // -- NOT IMPLEMENTED --
.label RPTFLG = $28A // whether to repeat keys (highest bit set = repeat)
.label KOUNT = $28B // key repeat counter
.label DELAY = $28C // -- NOT IMPLEMENTED --
.label SHFLAG = $28D // bucky keys (SHIFT/CTRL/C=) flags
@@ -228,25 +194,14 @@
.label KEYLOG = $28F // $28F-$290 routine to setup keyboard decoding
.label MODE = $291 // flag, is case switch allowed
.label AUTODN = $292 // -- NOT IMPLEMENTED -- screen scroll disable
#if CONFIG_EXTENDED_SCNKEY
// Reuse RS232 variables, since they should not be used by other things.
// This one should be initialized in cinit to $FF
.label BufferOld = $293 // 3 bytes
.label Buffer = $297 // 4 bytes
#else
#if !CONFIG_LEGACY_SCNKEY
.label M51CRT = $293 // -- NOT IMPLEMENTED -- mock 6551
.label M51CDR = $294 // -- NOT IMPLEMENTED -- mock 6551
.label M51AJB = $295 // $295-$296 -- NOT IMPLEMENTED -- mock 6551
.label RSSTAT = $297 // -- NOT IMPLEMENTED -- mock 6551, RS-232 status
.label BITNUM = $298 // -- NOT IMPLEMENTED --
.label BAUDOF = $299 // $299-$29A -- NOT IMPLEMENTED --
#endif
.label RIDBE = $29B // -- NOT IMPLEMENTED --
.label RIDBS = $29C // -- NOT IMPLEMENTED --
.label RODBS = $29D // -- NOT IMPLEMENTED --
@@ -275,7 +230,7 @@
#if SEGMENT_BASIC
.label shift_mem_up = tiny_nmi_handler + shift_mem_up_routine - tiny_nmi_handler_routine
.label shift_mem_down = tiny_nmi_handler + shift_mem_down_routine - tiny_nmi_handler_routine
#endif // SEGMENT_BASIC
#endif
#endif // CONFIG_MEMORY_MODEL_60K
+11
View File
@@ -4,10 +4,21 @@
#import "KERNAL_combined.sym"
#if CONFIG_PANIC_SCREEN
.label panic = KERNAL.panic
#endif
.label hw_entry_reset = KERNAL.hw_entry_reset
#if CONFIG_DBG_PRINTF
.label printf = KERNAL.printf
#endif
.label plot_set = KERNAL.plot_set
.label print_hex_byte = KERNAL.print_hex_byte
.label print_return = KERNAL.print_return
.label print_space = KERNAL.print_space
#if CONFIG_SHOW_PAL_NTSC
.label print_pal_ntsc = KERNAL.print_pal_ntsc
#endif
@@ -1,10 +0,0 @@
// Target-specific hooks
.macro TARGET_HOOK_BANNER() {
.text " OPEN ROMS, "
.byte $00
}
@@ -1,12 +0,0 @@
// Target-specific hooks
.macro TARGET_HOOK_BANNER() {
.text " OPEN ROMS FOR ULTIMATE 64"
.byte $0D, $0D
.text " "
.byte $00
}
+2
View File
@@ -0,0 +1,2 @@
This address is called at least by the Simon's BASIC cartridge.
@@ -1,5 +1,5 @@
// XXX provide documentation and implementation
setup_keydecode:
REASON:
STUB_IMPLEMENTATION()
+3
View File
@@ -0,0 +1,3 @@
This routine is probably used by many cartridges and other software to initialize parts of the system. At least the UCart uses it - see here:
- https://www.elektroda.pl/rtvforum/topic3293027.html
+4
View File
@@ -0,0 +1,4 @@
// XXX provide documentation and implementation
STUB_IMPLEMENTATION()
+7
View File
@@ -0,0 +1,7 @@
This routine is used to launch other software. It is used by:
- Uncrunch (see https://github.com/mist64/pucrunch/blob/master/uncrunch.asm)
- FileBrowser64 (FB64) - found by debugging
and probably others.
+91
View File
@@ -0,0 +1,91 @@
//
// Well-known BASIC routine, described in:
//
// - [CM64] Compute's Mapping the Commodore 64 - page 95
// - https://www.lemon64.com/forum/viewtopic.php?t=64721&sid=bc400a5a6d404f8f092e4d32a92f5de7
//
LINKPRG:
// Start by getting pointer to the first line
jsr init_oldtxt
linkprg_loop:
// Is the pointer to the end of the program
ldy #1
#if CONFIG_MEMORY_MODEL_60K
ldx #<OLDTXT+0
jsr peek_under_roms
cmp #$00
#else // CONFIG_MEMORY_MODEL_38K
lda (OLDTXT),y
#endif
bne !+
// End of program
rts
!:
// Now search forward to find the end of the line
// Skip forward pointer and line number
ldy #4
linkprg_end_of_line_search:
#if CONFIG_MEMORY_MODEL_60K
ldx #<OLDTXT+0
jsr peek_under_roms
#else // CONFIG_MEMORY_MODEL_38K
lda (OLDTXT),y
#endif
cmp #$00
beq !+
// Not yet end of line
iny
bne linkprg_end_of_line_search
// line too long
jmp do_STRING_TOO_LONG_error
!:
// Found end of line, so update pointer
// First, skip over the $00 char
iny
// Now overwrite the pointer (carefully)
//
tya
clc
adc OLDTXT+0
pha
php
ldy #0
#if CONFIG_MEMORY_MODEL_60K
ldx #<OLDTXT+0
jsr poke_under_roms
#else // CONFIG_MEMORY_MODEL_38K
sta (OLDTXT),y
#endif
plp
lda OLDTXT+1
adc #0
ldy #1
#if CONFIG_MEMORY_MODEL_60K
jsr poke_under_roms
#else // CONFIG_MEMORY_MODEL_38K
sta (OLDTXT),y
#endif
sta OLDTXT+1
pla
sta OLDTXT+0
jmp linkprg_loop
+3
View File
@@ -0,0 +1,3 @@
This routine is probably used by many cartridges and other software to initialize parts of the system. At least the UCart uses it - see here:
- https://www.elektroda.pl/rtvforum/topic3293027.html
+5
View File
@@ -0,0 +1,5 @@
// XXX provide documentation and real implementation
new:
STUB_IMPLEMENTATION()
+6
View File
@@ -0,0 +1,6 @@
This routine is used to launch other software. It is used by:
- Exomizer (see https://github.com/bitshifters/exomizer/blob/master/exomizer/exomizer115.txt)
- FileBrowser64 (FB64) - found by debugging
and probably others.
+7
View File
@@ -0,0 +1,7 @@
// XXX provide documentation and implementation
// see: https://www.lemon64.com/forum/viewtopic.php?t=64721&sid=bc400a5a6d404f8f092e4d32a92f5de7
// https://www.lemon64.com/forum/viewtopic.php?t=70680&sid=3ff66caf7f5fdf2a3c2ff2ee31fc3fd8
setcharptr:
STUB_IMPLEMENTATION()
+24 -2
View File
@@ -1,5 +1,27 @@
// XXX provide documentation and implementation
// Well-known BASIC routine, described in:
//
// - [CM64] Compute's Mapping the Commodore 64 - page 97
// - https://www.c64-wiki.com/wiki/BASIC-ROM
// - https://csdb.dk/forums/?roomid=11&topicid=137233
//
// XXX use this routine to initialize TXTPTR
RUNC:
STUB_IMPLEMENTATION()
// According to WIKI, we should load $7A/$7B with $2B-1/$2C-1), this does not makes sense.
// But CSDB claims, that it should 'set current character pointer to start of basic - 1' - this
// looks sane, also checked that the original BASIC routine does this (short test program)
// Let's initialize TXTPTR using TXTTAB
lda TXTTAB+0
sec
sbc #$01
sta TXTPTR+0
lda TXTTAB+1
sbc #$00
sta TXTPTR+1
rts
+8 -2
View File
@@ -1,3 +1,9 @@
This routine is mentionned in the cartridge writing tutorial here: https://codebase64.org/doku.php?id=base:assembling_your_own_cart_rom_image
This routine is used to launch other software. It is used by:
- Exomizer (see https://github.com/bitshifters/exomizer/blob/master/exomizer/exomizer115.txt)
- FileBrowser64 (FB64) - found by debugging
and probably others. It is also mentionned in the cartridge writing tutorial here:
- https://codebase64.org/doku.php?id=base:assembling_your_own_cart_rom_image
We have to implement (or at least provide stub), otherwise cartridges will crash.
+15 -2
View File
@@ -1,5 +1,18 @@
// XXX provide documentation and implementation
// Well-known BASIC routine, described in:
//
// - [CM64] Compute's Mapping the Commodore 64 - page 97
// - https://www.lemon64.com/forum/viewtopic.php?t=64721&sid=bc400a5a6d404f8f092e4d32a92f5de7
// - https://www.lemon64.com/forum/viewtopic.php?t=70680&sid=3ff66caf7f5fdf2a3c2ff2ee31fc3fd8
// - https://codebase64.org/doku.php?id=base:assembling_your_own_cart_rom_image
NEWSTT:
STUB_IMPLEMENTATION()
// XXX Real implementation is more complicated, it's actually a part
// of the BASIC main loop. It is, however, often called by various
// utilities to simply run the software which was just loaded or
// uncompressed.
// For now, let's cheat a little - this should provide some compatibility:
jmp cmd_run
+3 -4
View File
@@ -7,9 +7,8 @@ STROUT:
// Setup pointer
sty FRESPC+1
sta FRESPC+0
txa
pha
phx_trash_a
// Get offset ready
ldy #$00
@@ -29,6 +28,6 @@ STROUT:
iny
bne !-
!:
pla
pla // XXX can we use plx_trash_a here?
tax
rts
+2 -4
View File
@@ -2,8 +2,7 @@
basic_do_error:
// Save error number
txa
pha
phx_trash_a
// Print ? at start
jsr print_return
@@ -11,8 +10,7 @@ basic_do_error:
jsr JCHROUT
// Print main part of error message
pla
tax
plx_trash_a
jsr print_packed_message
// Print ERROR at end
-20
View File
@@ -112,26 +112,6 @@ not_a_token:
cmp #$3a
beq basic_skip_char
#if CONFIG_DOS_WEDGE
// Are we in direct mode?
// DOS Wedge is a hacky solution (inelegant, but convenient),
// BASIC programmers should implement communication with drives
// the standard way, handling channels properly. Besides,
// current implementation does not support characters under ROM
ldx CURLIN+1
cpx #$ff
bne !+
// We are in direct mode, allow wedge to handle '@' sign
// XXX Maybe it should be allowed only as the first command?
cmp #$40
bne !+
jsr basic_consume_character
jmp wedge_dos
!:
#endif // CONFIG_DOS_WEDGE
// If all else fails, it's a syntax error
jmp do_SYNTAX_error
+28 -11
View File
@@ -7,6 +7,10 @@ basic_main_loop:
// Tell user we are ready
jsr ready_message
// Enable Kernal messages
lda #$80
jsr JSETMSG
basic_read_next_line:
// Read a line of input
ldx #$00
@@ -35,12 +39,13 @@ got_line_of_input:
// Strip leading spaces from the line
remove_leading_spaces:
lda $0200
lda BUF
cmp #$20
bne !+
ldx #1
rsl_l1: lda $0200,x
sta $01ff,x
rsl_l1:
lda BUF,x
sta BUF-1,x
inx
cpx __tokenise_work1
bne rsl_l1
@@ -57,11 +62,23 @@ rsl_l1: lda $0200,x
lda __tokenise_work1
beq basic_read_next_line
#if CONFIG_DOS_WEDGE
// Check if DOS wedge should take over
lda BUF
cmp #$40 // '@'
bne !+
ldx __tokenise_work1 // here is the size of input
jmp wedge_dos
!:
#endif // CONFIG_DOS_WEDGE
// Else, tokenise the line
jsr tokenise_line
// Has the user entered a line of BASIC beginning with a number?
lda $0200
lda BUF
cmp #$30
bcc not_a_line
cmp #$39
@@ -78,9 +95,9 @@ rsl_l1: lda $0200,x
sta __tokenise_work1
// Try to read line number
lda #<$0200
lda #<BUF
sta TXTPTR+0
lda #>$0200
lda #>BUF
sta TXTPTR+1
jsr basic_parse_line_number
@@ -94,13 +111,13 @@ rsl_l1: lda $0200,x
// Skip any spaces after the line number
ldx __tokenise_work1
skip_spaces:
lda $0200,x
lda BUF,x
cmp #$20
bne !+
inx
bne skip_spaces
!: stx __tokenise_work1
// First, clear all variables, so that we only have to shove BASIC text around.
// (We could later remove this requirement, and the only effect should be
// to slow things down, and that you might have to either CLR if there is no
@@ -131,9 +148,9 @@ not_a_line:
// Actually interpret the line
// Setup pointer to the statement
lda #<$0200
lda #<BUF
sta TXTPTR+0
lda #>$0200
lda #>BUF
sta TXTPTR+1
// There is no stored line, so zero that pointer out
@@ -144,7 +161,7 @@ not_a_line:
// Put invalid line number in current line number value,
// so that we know we are in direct mode
// (Compute's Mapping the 64 p19)
lda #$ff
lda #$FF
sta CURLIN+1
jmp basic_execute_statement
+3 -1
View File
@@ -7,4 +7,6 @@
LINPRT:
STUB_IMPLEMENTATION()
// XXX This is temporary, to allow some software to work!
// To be replaced by real impleementation.
jmp print_integer
-31
View File
@@ -1,31 +0,0 @@
cmd_sys:
jsr basic_end_of_statement_check
bcc !+
// SYS requires an argument
jmp do_SYNTAX_error
!:
jsr basic_parse_line_number
// setup call
lda #$4C // JMP opcode
sta USRPOK
lda LINNUM+0
sta USRADD+0
lda LINNUM+1
sta USRADD+1
// Setup the register values
lda SPREG
pha
ldy SYREG
ldx SXREG
lda SAREG
plp
// Call the routine.
jsr USRPOK
jmp basic_execute_statement
@@ -1,5 +1,5 @@
cmd_stop:
ldx #38 // "BREAK"
ldx #30 // "BREAK"
jsr print_packed_message
// Are we in direct mode
@@ -8,7 +8,7 @@ cmd_stop:
beq !+
// Not direct mode
ldx #37
ldx #31
jsr print_packed_message
lda CURLIN+1
@@ -4,10 +4,7 @@
cmd_list:
// Set current line pointer to start of memory
lda TXTTAB+0
sta OLDTXT+0
lda TXTTAB+1
sta OLDTXT+1
jsr init_oldtxt
list_loop:
@@ -82,16 +79,20 @@ list_print_loop:
cmp #$22
bne list_not_quote
lda QTSW
eor #$ff
eor #$FF
sta QTSW
lda #$22
jmp list_is_literal
list_not_quote:
// Check quote mode, and display as literal if required
ldx QTSW
bne list_is_literal
cmp #$7f
cmp #$FF
beq list_is_pi
cmp #$7F
bcc list_is_literal
// Display a token
@@ -99,8 +100,7 @@ list_not_quote:
// Save registers
tax
pha
tya
pha
phy_trash_a
// Get pointer to compressed keyword list
lda #<packed_keywords
@@ -118,8 +118,7 @@ list_not_quote:
ldy #$ff
jsr packed_word_search
pla
tay
ply_trash_a
pla
cmp #$8f
@@ -132,7 +131,12 @@ list_not_quote:
list_not_rem:
iny
bne list_print_loop
bne list_print_loop // branch always
list_is_pi:
lda #$7E
// FALLTROUGH
list_is_literal:
jsr JCHROUT
@@ -140,9 +144,6 @@ list_is_literal:
bne list_print_loop
list_end_of_line:
// Clear reverse flag
lda #$92
jsr JCHROUT
// Print end of line
jmp print_return
@@ -11,15 +11,6 @@ cmd_load:
// middle of a program. For safety, we do.
jsr basic_do_clr
// Setup Kernal to print control messages or not
lda #$80 // display control messages and omit error messages
ldx CURLIN+1
cpx #$FF
beq !+
lda #$00 // direct mode - don't display anything
!:
jsr JSETMSG
// Set filename and length
lda #$00
sta FNLEN
@@ -102,7 +93,9 @@ got_loadaddress:
lda #$00 // LOAD not verify
jsr JLOAD
php
pha
jsr print_return
pla
plp
bcc !+
@@ -121,7 +114,7 @@ got_loadaddress:
// Now relink the loaded program, as we cannot trust the line
// links supplied. For example, the VICE virtual drive emulation
// always supplies $0101 as the address of the next line.
jsr basic_relink_program
jsr LINKPRG
// After LOADing, we either start the program from the beginning,
// or go back to the READY prompt if LOAD was called from direct mode.
@@ -131,87 +124,3 @@ got_loadaddress:
// XXX - should run program if LOAD was used in program mode
jmp basic_main_loop
basic_relink_program:
// Start by getting pointer to the first line
jsr init_oldtxt
basic_relink_loop:
// Is the pointer to the end of the program
ldy #1
#if CONFIG_MEMORY_MODEL_60K
ldx #<OLDTXT+0
jsr peek_under_roms
cmp #$00
#else // CONFIG_MEMORY_MODEL_38K
lda (OLDTXT),y
#endif
bne !+
// End of program
rts
!:
// Now search forward to find the end of the line
// Skip forward pointer and line number
ldy #4
end_of_line_search:
#if CONFIG_MEMORY_MODEL_60K
ldx #<OLDTXT+0
jsr peek_under_roms
#else // CONFIG_MEMORY_MODEL_38K
lda (OLDTXT),y
#endif
cmp #$00
beq !+
// Not yet end of line
iny
bne end_of_line_search
// line too long
jmp do_STRING_TOO_LONG_error
!:
// Found end of line, so update pointer
// First, skip over the $00 char
iny
// Now overwrite the pointer (carefully)
//
tya
clc
adc OLDTXT+0
pha
php
ldy #0
#if CONFIG_MEMORY_MODEL_60K
ldx #<OLDTXT+0
jsr poke_under_roms
#else // CONFIG_MEMORY_MODEL_38K
sta (OLDTXT),y
#endif
plp
lda OLDTXT+1
adc #0
ldy #1
#if CONFIG_MEMORY_MODEL_60K
jsr poke_under_roms
#else // CONFIG_MEMORY_MODEL_38K
sta (OLDTXT),y
#endif
sta OLDTXT+1
pla
sta OLDTXT+0
jmp basic_relink_loop
File renamed without changes.
File renamed without changes.
@@ -2,11 +2,12 @@ cmd_run:
// RUN clears all variables
jsr basic_do_clr
cmd_goto:
// Disable Kernal messages
lda #$00
jsr JSETMSG
// Reset line pointer to first line of program.
lda TXTTAB+0
sta OLDTXT+0
lda TXTTAB+1
sta OLDTXT+1
jsr init_oldtxt
jsr basic_end_of_statement_check
bcs !+
+68
View File
@@ -0,0 +1,68 @@
cmd_sys:
jsr basic_end_of_statement_check
bcc !+
// SYS requires an argument
jmp do_SYNTAX_error
!:
//
// XXX Temporary ugly hack to support 'SYS PI*656'
//
ldy #$00
cmd_sys_hack_loop:
lda (TXTPTR), y
cmp cmd_sys_hack_str, y
bne cmd_sys_hack_not_needed
lda (TXTPTR), y
beq cmd_sys_hack_apply
iny
bne cmd_sys_hack_loop // branch always
cmd_sys_hack_apply:
lda #<2060
sta LINNUM+0
lda #>2060
sta LINNUM+1
bne cmd_sys_setup_call // always jumps
cmd_sys_hack_not_needed:
//
// XXX End of hack
//
jsr basic_parse_line_number
cmd_sys_setup_call:
lda #$4C // JMP opcode
sta USRPOK
lda LINNUM+0
sta USRADD+0
lda LINNUM+1
sta USRADD+1
// Setup the register values
lda SPREG
pha
ldy SYREG
ldx SXREG
lda SAREG
plp
// Call the routine.
jsr USRPOK
jmp basic_execute_statement
//
// XXX Temporary ugly hack to support 'SYS PI*656'
//
cmd_sys_hack_str:
.byte $FF, $AC, $36, $35, $36, $00
File renamed without changes.
+1 -1
View File
@@ -150,7 +150,7 @@ do_basic_error:
beq !+
// We were in a program, so show IN <line>
ldx #37
ldx #31
jsr print_packed_message
lda CURLIN+1
-44
View File
@@ -1,44 +0,0 @@
//
// Well-known BASIC routine, described in:
//
// - [CM64] Compute's Mapping the Commodore 64 - page 212
//
// Prints the start-up messages
//
INITMSG:
// Print startup banner, up to 255 characters
ldx #$00
!:
lda startup_banner, x
beq !+ // 0 means end of banner
jsr JCHROUT
inx
bne !-
!:
// Print PAL/NTSC
ldx #30 // NTSC
lda TVSFLG
beq !+
ldx #31 // PAL
!:
jsr print_packed_message
// Work out free bytes, display them
jsr basic_do_new
sec
lda MEMSIZ+0
sbc TXTTAB+0
tax
lda MEMSIZ+1
sbc TXTTAB+1
jsr print_integer
jsr print_space
// Print rest of the start up message
ldx #34
jmp print_packed_message
File renamed without changes.
File renamed without changes.
@@ -1,7 +1,9 @@
// BASIC Cold start entry point
// Compute's Mapping the 64 p211
basic_cold_start:
//
// Continuation of the BASIC cold start routine
//
basic_cold_start_internal:
// Setup vectors at $300
ldy #$0B
@@ -1,6 +1,9 @@
// Clear screen etc, show READY prompt.
basic_warm_start:
//
// Continuation of the BASIC cold start routine
//
basic_warm_start_real:
#if CONFIG_MEMORY_MODEL_60K
// We need our helpers to get to filenames under ROMs or IO area
@@ -8,6 +11,7 @@ basic_warm_start:
#endif
// If warm start caused by BRK, print it address
// XXX sys 58235 also triggers this - to be fixed
lda CMP0
ora CMP0+1
beq !+
+22
View File
@@ -0,0 +1,22 @@
// BASIC Cold start entry point
// Compute's Mapping the 64 p211
basic_cold_start:
// Before doing anything, check if we have a compatible BASIC/KERNAL pair
ldy #(__rom_revision_basic_end - rom_revision_basic - 1)
!:
lda rom_revision_basic, y
cmp rom_revision_kernal, y
beq !+
panic #P_ERR_ROM_MISMATCH
!:
dey
bpl !--
// Remaining part wouldn't fit here
jmp basic_cold_start_internal
+8
View File
@@ -0,0 +1,8 @@
The address of the BASIC cold start routine (see Compute's Mapping the Commodore 64, page 211) is well known, see for example here:
- https://www.lemon64.com/forum/viewtopic.php?t=70680&sid=3ff66caf7f5fdf2a3c2ff2ee31fc3fd8
Fixing this routine also has a great advantage for us - since it's address lies in the uppeer ROM region, it's easier to bailout
when someone tries to use our 'kernal.rom' with the original 'basic.rom'.
@@ -0,0 +1,5 @@
// Clear screen etc, show READY prompt.
basic_warm_start:
jmp basic_warm_start_real
+5
View File
@@ -0,0 +1,5 @@
This is a well-known address, needed even for some BASIC programming - it's a common target for a SYS command. See for example here:
- http://ready64.org/articoli/_files/043_pokesc64.txt
sys 58235 - Warm Start
+11
View File
@@ -0,0 +1,11 @@
//
// Well-known BASIC routine, described in:
//
// - [CM64] Compute's Mapping the Commodore 64 - page 212
//
// Prints the start-up messages
//
INITMSG:
jmp initmsg_real
File renamed without changes.
+21
View File
@@ -0,0 +1,21 @@
//
// Print out the amount of free bytes - for the startup banner
//
initmsg_bytes_free:
jsr basic_do_new
sec
lda MEMSIZ+0
sbc TXTTAB+0
tax
lda MEMSIZ+1
sbc TXTTAB+1
jsr print_integer
// Print rest of the start up message
ldx #34
jmp print_packed_message
+95
View File
@@ -0,0 +1,95 @@
// Routine is too long to fit in the original location
initmsg_real:
#if CONFIG_BANNER_SIMPLE
lda #<startup_banner
ldy #>startup_banner
jsr STROUT
ldx #$02
ldy #$02
jsr plot_set
lda #<rom_revision_basic_string
ldy #>rom_revision_basic_string
jsr STROUT
ldx #$04
ldy #$02
jsr plot_set
#if CONFIG_SHOW_PAL_NTSC
jsr print_pal_ntsc
#endif
jsr initmsg_bytes_free
ldx #$07
ldy #$00
jmp plot_set
#elif CONFIG_BANNER_FANCY
lda #<rainbow_logo
ldy #>rainbow_logo
jsr STROUT
ldx #$01
ldy #$0A
jsr plot_set
lda #<startup_banner
ldy #>startup_banner
jsr STROUT
ldx #$03
ldy #$0A
jsr plot_set
lda #<pre_revision_string
ldy #>pre_revision_string
jsr STROUT
lda #<rom_revision_basic_string
ldy #>rom_revision_basic_string
jsr STROUT
ldx #$05
ldy #$00
jsr plot_set
#if CONFIG_SHOW_PAL_NTSC
jsr print_pal_ntsc
#endif
jsr initmsg_bytes_free
ldx #$07
ldy #$00
jmp plot_set
#elif CONFIG_BANNER_BRAND && CONFIG_BRAND_MEGA_65
lda #<startup_banner
ldy #>startup_banner
jsr STROUT
lda #<rom_revision_basic_string
ldy #>rom_revision_basic_string
jsr STROUT
ldx #$03
ldy #$12
jsr plot_set
jsr initmsg_bytes_free
ldx #$05
ldy #$00
jmp plot_set
#endif
@@ -1,10 +1,72 @@
// Target-specific hooks
//
// Startup banner, to be displayed during cold start
//
.macro TARGET_HOOK_BANNER() {
.macro BANNER_TEXT() {
// New banner from Retrofan
#if CONFIG_BRAND_GENERIC
.text "OPEN ROMS GENERIC BUILD"
#elif CONFIG_BRAND_TESTING
.text "OPEN ROMS TESTING BUILD"
#elif CONFIG_BRAND_MEGA_65
.text "OPEN ROMS FOR MEGA65"
#elif CONFIG_BRAND_ULTIMATE_64
.text "OPEN ROMS FOR ULTIMATE 64"
#endif
}
startup_banner:
#if CONFIG_BANNER_SIMPLE
.text " "
BANNER_TEXT()
.byte $00
#elif CONFIG_BANNER_FANCY
BANNER_TEXT()
.byte $00
rainbow_logo:
{
#if CONFIG_COLORS_BRAND && CONFIG_BRAND_MEGA_65
.var SET_COLOR_0 = $05
.var SET_COLOR_1 = $9A
.var SET_COLOR_2 = $1E
.var SET_COLOR_3 = $9E
.var SET_COLOR_4 = $96
#else
.var SET_COLOR_0 = $05
.var SET_COLOR_1 = $1C
.var SET_COLOR_2 = $9E
.var SET_COLOR_3 = $1E
.var SET_COLOR_4 = $9F
#endif
.byte SET_COLOR_1, $12, $A4, $A4, $A4, $A4, $A4, $A4, $A4, $0D
.byte SET_COLOR_2, $12, $A4, $A4, $A4, $A4, $A4, $A4, $0D
.byte SET_COLOR_3, $12, $A4, $A4, $A4, $A4, $A4, $0D
.byte SET_COLOR_4, $12, $A4, $A4, $A4, $A4, $92
.byte SET_COLOR_0, $00
}
pre_revision_string:
.text "RELEASE "
.byte $00
#elif CONFIG_BANNER_BRAND && CONFIG_BRAND_MEGA_65
// Fancy Mega65 banner - from Retrofan
.byte $9a, $12, $20, $20, $7f, $a9, $20, $20, $1f, $20, $9a, $20, $20, $20
.byte $20, $1f, $20, $9a, $a9, $20, $20, $20, $92, $a1, $1f, $12, $20, $9a, $a9, $20
.byte $20, $20, $7f, $1f, $20, $20, $9a, $a3, $a3, $a3, $a3, $a3, $a3, $a3, $1f, $20
@@ -21,7 +83,7 @@
.byte $20, $20, $1f, $20, $20, $96, $a3, $a3, $a3, $a3, $1f
.byte $92, $0D, $0D, $05, $00
// Original Deft-supplied banner
// Original Mega65 banner - supplied by Deft
// .byte $9A,$12,$A3,$A3,$A3,$A3,$A3,$A3,$DF,$9B,$92,$20,$05,$12,$A0,$A0
// .byte $DF,$9B,$92,$20,$05,$12,$A0,$A0,$DF,$9B,$92,$20,$05,$12,$A0,$A0
// .byte $DF,$9B,$92,$20,$05,$12,$A0,$A0,$DF,$9A,$92,$20,$05,$20,$20,$20
@@ -38,4 +100,4 @@
// .byte $12,$DF,$92,$7F,$9B,$20,$9A,$20,$9B,"0.2.0.0",$0D
// .byte $0D,$05,$92,$00
}
#endif
+1 -2
View File
@@ -5,8 +5,7 @@
print_integer:
pha
txa
pha
phx_trash_a
// Clear temporary output
lda #$00
+8 -16
View File
@@ -32,15 +32,13 @@ packed_message_search:
found_message_in_token_stream:
// Now print each word in the message
tya
pha
phy_trash_a
lda packed_message_tokens,y
cmp #$ff
beq !+
jsr print_packed_word
jsr print_space
pla
tay
ply_trash_a
iny
bne found_message_in_token_stream
!:
@@ -139,16 +137,14 @@ next_packed_word_char:
tax
// Save Y so it doesn't get clobbered by CHROUT
tya
pha
phy_trash_a
// X=1-14 = first 14 chars, so subtract one
lda packed_message_chars-1,x
jsr JCHROUT
// See if there is a char in the low nybl to print
pla
tay
ply_trash_a
lda (FRESPC),y
and #$0f
beq end_of_packed_word
@@ -158,8 +154,7 @@ next_packed_word_char:
has_lo_nybl_char:
// We need to print the low nybl char as well
tax
tya
pha
phy_trash_a
// Skip lower nybls of $F or $0 in nybl packed
// bytes, as these do not encode characters
@@ -173,8 +168,7 @@ has_nybl:
lda packed_message_chars-1,x
jsr JCHROUT
!:
pla
tay
ply_trash_a
// FALLTHROUGH
no_lo_nybl_char:
@@ -204,8 +198,7 @@ next_is_literal_char:
unpack_literal_char:
// Output the literal char, and ready for next char
iny
tya
pha
phy_trash_a
lda (FRESPC),y
jsr JCHROUT
pla
@@ -222,7 +215,6 @@ is_uncommon_char:
// We need to print the low nybl char as well
tax
tya
pha
phy_trash_a
jmp has_nybl
File renamed without changes.
File renamed without changes.
+2
View File
@@ -0,0 +1,2 @@
Special case - we need a constant memory location where we can put an ID and a revision string. According to Compute's Mapping the Commodore 64 (page 117) this area is unused - so a perfect place.
@@ -0,0 +1,27 @@
//
// !!! PROPOSAL ONLY !!! PROPOSAL ONLY !!! NOT FOR USING EXTERNALLY YET !!!
//
//
// Do not change! Locations of the following data should be constant - now and forever!
//
// If you want to integrate Open ROMs support in your emulator, FPGA ccomputer, etc. - this
// is the official way to recognize the ROM and it's revision.
//
rom_revision_basic:
// $BF52
.text "OR" // project signature, after "Open ROMs"
.byte CONFIG_ID // config file ID, might change between revisions
rom_revision_basic_string:
// $BF55
.text "(DEVEL SNAPSHOT)" // actual ROM revision string; up to 16 characters
.byte $00 // marks the end of string
__rom_revision_basic_end:
+2
View File
@@ -0,0 +1,2 @@
Special case - we need a constant memory location where we can put an ID and a revision string. According to Compute's Mapping the Commodore 64 (page 213) this area is unused - so a perfect place.
@@ -0,0 +1,41 @@
//
// !!! PROPOSAL ONLY !!! PROPOSAL ONLY !!! NOT FOR USING EXTERNALLY YET !!!
//
//
// Do not change! Locations of the following data should be constant - now and forever!
//
// If you want to integrate Open ROMs support in your emulator, FPGA ccomputer, etc. - this
// is the official way to recognize the ROM and it's revision.
//
// $E4B7
// This vector is to be used by non-Kernal ROMs, if they want to
// complain about incompatible ROM releases - don't use it directly,
// use a 'panic' pseudocommand with error code (will be passed using .A)
// #P_ERR_ROM_MISMATCH - it should remain stable even between releases
#if CONFIG_PANIC_SCREEN
.word panic
#else
.word hw_entry_reset
#endif
rom_revision_kernal:
// $E4B9
.text "OR" // project signature, after "Open ROMs"
.byte CONFIG_ID // config file ID, might change between revisions
rom_revision_kernal_string:
// $E4BC
.text "(DEVEL SNAPSHOT)" // actual ROM revision string; up to 16 characters
.byte $00 // marks the end of string
__rom_revision_kernal_end:
-7
View File
@@ -1,7 +0,0 @@
//
// Startup banner, to be displayed durin cold start
//
startup_banner:
TARGET_HOOK_BANNER()
+19 -3
View File
@@ -1,8 +1,15 @@
#if CONFIG_DOS_WEDGE
// .X has to contain size of the buffer
wedge_dos:
// Prepare buffer - finish it with '0'
lda #$00
sta BUF,x
// Close all the channels, so that wedge has full control
jsr JCLALL
@@ -12,6 +19,16 @@ wedge_dos:
ldy #$0F
jsr JSETFLS
// Setup necessary parts of BASIC
lda #<(BUF+1)
sta TXTPTR+0
lda #>(BUF+1)
sta TXTPTR+1
lda #$FF
sta CURLIN+1
// Now we have to check what the user wants us to do
// Check if user asked for a status
@@ -210,13 +227,12 @@ wedge_dos_clean_exit:
jsr JCLALL
// Print new line
jsr print_return
jmp basic_end_of_line
jmp basic_main_loop
wedge_dos_basic_error:
pha
jsr JCLALL
pla
tax
plx_trash_a
dex
jmp do_basic_error
@@ -1,6 +0,0 @@
// Target-specific hooks
.macro TARGET_HOOK_LOAD() {
}
@@ -1,6 +0,0 @@
// Target-specific hooks
.macro TARGET_HOOK_LOAD() {
}
@@ -1,9 +0,0 @@
// Target-specific hooks
.macro TARGET_HOOK_LOAD() {
// XXX disabled for now - the current file opening API is not
// really suitable for easy usage from Kernal
// jsr u64_load
}
+47 -13
View File
@@ -5,40 +5,74 @@
// Double underscore prevents labels from being passed to VICE (would confuse monitor)
.label __MSG_KERNAL_SEARCHING_FOR = __kernal_message_searching_for - __kernal_messages_start
.label __MSG_KERNAL_LOADING = __kernal_message_loading - __kernal_messages_start
.label __MSG_KERNAL_VERIFYING = __kernal_message_verifying - __kernal_messages_start
.label __MSG_KERNAL_SAVING = __kernal_message_saving - __kernal_messages_start
.label __MSG_KERNAL_FROM_HEX = __kernal_message_from_hex - __kernal_messages_start
.label __MSG_KERNAL_TO_HEX = __kernal_message_to_hex - __kernal_messages_start
.label __MSG_KERNAL_SEARCHING_FOR = __msg_kernalsearching_for - __msg_kernal_first
.label __MSG_KERNAL_LOADING = __msg_kernalloading - __msg_kernal_first
.label __MSG_KERNAL_VERIFYING = __msg_kernalverifying - __msg_kernal_first
.label __MSG_KERNAL_SAVING = __msg_kernalsaving - __msg_kernal_first
.label __MSG_KERNAL_FROM_HEX = __msg_kernalfrom_hex - __msg_kernal_first
.label __MSG_KERNAL_TO_HEX = __msg_kernalto_hex - __msg_kernal_first
#if CONFIG_SHOW_PAL_NTSC
.label __MSG_KERNAL_PAL = __msg_kernalpal - __msg_kernal_first
.label __MSG_KERNAL_NTSC = __msg_kernalntsc - __msg_kernal_first
#endif
#if CONFIG_PANIC_SCREEN
.label __MSG_KERNAL_PANIC = __msg_kernalpanic - __msg_kernal_first
.label __MSG_KERNAL_PANIC_ROM_MISMATCH = __msg_kernalpanic_rom_mismatch - __msg_kernal_first
#endif
__kernal_messages_start:
__msg_kernal_first:
__kernal_message_searching_for:
__msg_kernalsearching_for:
.byte $0D
.text "SEARCHING FOR"
.byte $80 + $20 // end of string mark + space
__kernal_message_loading:
__msg_kernalloading:
.byte $0D
.text "LOADIN"
.byte $80 + $47 // end of string mark + 'G'
__kernal_message_verifying:
__msg_kernalverifying:
.byte $0D
.text "VERIFYIN"
.byte $80 + $47 // end of string mark + 'G'
__kernal_message_saving:
__msg_kernalsaving:
.byte $0D
.text "SAVIN"
.byte $80 + $47 // end of string mark + 'G'
__kernal_message_from_hex:
__msg_kernalfrom_hex:
.text " FROM "
.byte $80 + $24 // end of string mark + '$'
__kernal_message_to_hex:
__msg_kernalto_hex:
.text " TO "
.byte $80 + $24 // end of string mark + '$'
#if CONFIG_SHOW_PAL_NTSC
__msg_kernalpal:
.text "PAL,"
.byte $80 + $20 // end of string mark + space
__msg_kernalntsc:
.text "NTSC,"
.byte $80 + $20 // end of string mark + space
#endif // CONFIG_SHOW_PAL_NTSC
#if CONFIG_PANIC_SCREEN
__msg_kernalpanic:
.text "KERNAL PANI"
.byte $80 + $43 // end of string mark + 'C'
__msg_kernalpanic_rom_mismatch:
.text " - ROM MISMATC"
.byte $80 + $48 // end of string mark + 'H'
#endif // CONFIG_PANIC_SCREEN
-72
View File
@@ -1,72 +0,0 @@
// Key board matrixes: unshifted, shifted, control and C= modified
// 64 bytes for each
keyboard_matrixes:
// Unshifted matrix built by refering to
// Compute's Mapping the 64 p38-39
// and C64 PRG pages 379-381
.byte $14,$0D,$1D,$88,$85,$86,$87,17
.byte $33,87,$41,$34,$5A,83,$45,$00
.byte $35,$52,$44,$36,$43,$46,$54,88
.byte $37,$59,$47,$38,$42,$48,$55,$56
.byte $39,$49,$4A,$30,$4D,$4B,$4F,$4E
.byte $2B,$50,$4C,45,46,58,$40,44
.byte $5C,$2A,59,$13,$00,$3D,$5E,$2F
.byte $31,$5F,$00,$32,$20,$00,$51,$03
// Shifted keyboard
// Values computed by running a program like:
// 10 GETA$:IFA$=""GOTO10
// 20 ?ASC(A$):GOTO10
// and converting the values
.byte $94,$8D,$9D,$8C,$89,$8A,$8B,$91
.byte $23,$77,$61,$24,$7A,$73,$65,$00
.byte $25,$72,$64,$26,$63,$66,$74,$78
.byte $27,$79,$67,$28,$62,$68,$75,$76
.byte $29,$69,$6A,$92,$6D,$6B,$6F,$6E
.byte $DB,$70,$6C,$DD,$3E,$5B,$BA,$3C
.byte $A9,$C0,$5D,$93,$00,$3D,$DE,$3F
.byte $21,$5F,$00,$22,$A0,$00,$71,$83
// Vendor key modified keyboard
.byte $94,$8D,$9D,$8C,$89,$8A,$8B,$91
.byte $96,$B3,$B0,$97,$AD,$AE,$B1,$00
.byte $98,$B2,$AC,$99,$BC,$BB,$A3,$BD
.byte $9A,$B7,$A5,$9B,$BF,$B4,$B8,$BE
.byte $30,$A2,$B5,$30,$A7,$A1,$B9,$AA
.byte $A6,$AF,$B6,$DC,$3E,$5B,$A4,$3C
.byte $A8,$DF,$5D,$93,$00,$3D,$DE,$3F
.byte $81,$5F,$00,$95,$a0,$00,$AB,$83
// Control modified keyboard
.byte $00,$00,$00,$00,$00,$00,$00,$00
.byte $1C,$17,$01,$9F,$1A,$13,$05,$00
.byte $9C,$12,$04,$1E,$03,$06,$14,$18
.byte $1F,$19,$07,$9E,$02,$08,$15,$16
.byte $12,$09,$0A,$92,$0D,$0B,$0F,$0E
.byte $00,$10,$0C,$00,$00,$1B,$00,$00
.byte $1C,$00,$1D,$00,$00,$1F,$1E,$00
.byte $90,$06,$00,$05,$00,$00,$11,$00
keyboard_matrix_lookup:
// Work out if normal, shifted, control or Vendor
// modified keyboard.
// Table contains the offsets into keyboard_matrixes
// that should be used for different values of
// the bottom 3 bits of key_bucky_state
// Interaction is simple to work out when playing
// with a C64:
// CONTROL trumps SHIFT or Vendor
// Vendor + SHIFT = DOES NOTHING
// All 3 does CONTROL
.byte $00 // Normal
.byte $40 // Shifted
.byte $80 // Control
.byte $80 // Control + SHIFT
.byte $C0 // Vendor
.byte $C0 // Vendor + SHIFT
.byte $80 // Vendor+ CTRL
.byte $80 // Vendor + CTRL + SHIFT
-96
View File
@@ -1,96 +0,0 @@
// We have the following variables:
// BLNSW (cursor blink switch)
// BLNCT (cursor blink countdown)
// GDBLN (cursor saved character)
// BLNON (if cursor is visible)
// GDCOL (colour under cursor)
// USER (current screen line colour pointer)
// PNT (current screen line pointer)
// PNTR (current screen x position)
show_cursor_if_enabled:
lda BLNSW
beq !+
rts
!: lda BLNON
beq show_cursor
rts
show_cursor:
// Set cursor as though it had just finished the off phase,
// so that the call to blink_cursor paints it
lda #$00
sta BLNCT
sta BLNON
jsr blink_cursor
// Then set the timeout to 1 frame, so that the cursor
// blinks under key repeat conditions, like on the original KERNAL
lda #$01
sta BLNCT
rts
blink_cursor:
// Is the cursor enabled?
lda BLNSW
bne no_blink_cursor
// Do we need to redraw things?
dec BLNCT
bpl no_blink_cursor
// Check if cursor was visible or not, and toggle
lda BLNON
bne undraw_cursor
draw_cursor:
jsr calculate_screen_line_pointer
ldy PNTR
lda (PNT),y
sta GDBLN
eor #$80
sta (PNT),y
// Also set cursor colour
lda (USER),y
sta GDCOL
lda COLOR
sta (USER),y
lda #1
sta BLNON
jmp reset_blink_timer
undraw_cursor:
jsr calculate_screen_line_pointer
lda GDBLN
ldy PNTR
sta (PNT),y
lda GDCOL
sta (USER),y
lda #0
sta BLNON
// Fall through
reset_blink_timer:
// Rest blink counter
// (Compute's Mapping the 64, p39-40)
lda #20
sta BLNCT
no_blink_cursor:
rts
disable_cursor:
lda #$80
sta BLNSW
// FALL THROUGH
hide_cursor_if_visible:
lda BLNON
bne undraw_cursor
rts
enable_cursor:
lda #$00
sta BLNSW
rts
+3 -3
View File
@@ -5,7 +5,7 @@
// - [RG64] C64 Programmer's Reference Guide - page 275 (CHKIN) / 276 (CKOUT)
// - [CM64] Compute's Mapping the Commodore 64 - page 229
//
// CPU registers that has to be preserved (see [RG64]): .Y
// CPU registers that has to be preserved (see [RG64]): .Y, possibly .A (XXX - see [CM64], page 213)
//
@@ -14,8 +14,7 @@
chkin_real:
// Store Y for preservation
tya
pha
phy_trash_a
// Reset status
jsr kernalstatus_reset
@@ -59,6 +58,7 @@ chkin_set_device:
// FALLTROUGH
// Common part for booth CHKIN and CKOUT
// XXX add CPU-dependent optimizations here
chkinout_end:
tax
+16 -75
View File
@@ -9,6 +9,7 @@
//
// XXX keyboard part currently does not preserve register Y, to be fixed!
// XXX try to make chrin_real unnecessary (try to fit this into original location)
// Reads a byte of input, unless from keyboard.
// If from keyboard, then it gets a whole line of input, and returns the first char.
@@ -43,8 +44,7 @@ chrin_done_fail:
chrin_keyboard:
// Save X
txa
pha
phx_trash_a
chrin_repeat:
@@ -64,8 +64,7 @@ chrin_repeat:
// Return carriage return and clear pending input flag
lda #$00
sta CRSW
pla
tax
plx_trash_a
clc
lda #$0d
rts
@@ -73,33 +72,31 @@ chrin_repeat:
not_end_of_input:
// Return next byte of waiting input and advance index
tay
pla
tax
plx_trash_a
lda (LXSP),y
jsr screen_code_to_petscii
inc CRSW
clc
rts
read_from_keyboard:
jsr enable_cursor
jsr cursor_enable
// Wait for a key
lda NDX
beq chrin_repeat
lda KEYD
cmp #$0d
cmp #$0D
bne not_enter
jsr disable_cursor
jsr cursor_disable
jsr pop_keyboard_buffer
jsr hide_cursor_if_visible
jsr cursor_hide_if_visible
// It was enter.
// Note that we have a line of input to return, and return the first byte thereof
// after computing and storing its length.
@@ -112,7 +109,7 @@ read_from_keyboard:
sta LXSP+1
// Calculate length
jsr get_current_line_logical_length
jsr screen_get_current_line_logical_length
tay
iny
!: dey
@@ -126,8 +123,7 @@ read_from_keyboard:
sta CRSW
// Return first char of line
ldy #$00
pla
tax
plx_trash_a
lda (LXSP),y
jsr screen_code_to_petscii
clc
@@ -137,74 +133,19 @@ empty_line:
// For an empty line, just return the carriage return
// (and don't forget to actually print the carriage return, so that
// the cursor advances and screen scrolls as required)
pla
tax
plx_trash_a
clc
lda #$0d
rts
not_enter:
// Print character
lda KEYD
// XXX add support for SHIFT + RUN/STOP ($84) and function keys (should be configurable)
jsr CHROUT
jsr pop_keyboard_buffer
// Keep looking for input from keyboard until carriage return
jmp chrin_repeat
pop_keyboard_buffer:
// Pop key out of keyboard buffer
// Disable interrupts while reading from keyboard buffer
// so that no race conditions can occur
sei
ldx #$00
ldy #$01
!: lda KEYD,y
sta KEYD,x
inx
iny
cpy XMAX
bne !-
dec NDX
cli
rts
screen_code_to_petscii:
cmp #$1b
bcs not_alpha
clc
adc #$40
rts
not_alpha:
cmp #$40
bcs not_punctuation
rts
not_punctuation:
cmp #$5b
bcs not_shifted
clc
adc #$80
rts
not_shifted:
cmp #$80
bcs not_vendor
// $60-$7F -> $A0-$BF
clc
adc #$40
// FALLTROUGH
not_vendor:
rts
-889
View File
@@ -1,889 +0,0 @@
//
// Official Kernal routine, described in:
//
// - [RG64] C64 Programmer's Reference Guide - page 278/279
// - [CM64] Compute's Mapping the Commodore 64 - page 228
//
// CPU registers that has to be preserved (see [RG64]): .Y
//
chrout_real:
sta SCHAR
// Save X and Y values
// (Confirmed by writing a test program that X and Y
// don't get modified, in agreement with C64 PRG's
// description of CHROUT)
txa
pha
tya
pha
php
// Determine the device number
lda DFLTO
cmp #$03 // screen
beq chrout_screen
jsr iec_check_devnum
bcs chrout_done_unknown_device // not a supported device
chrout_iec:
lda SCHAR
jsr JCIOUT
bcc chrout_done
// FALLTROUGH
chrout_done_fail:
jsr show_cursor_if_enabled
plp
// Restore X and Y
pla
tay
pla
tax
sec // indicate failure
rts
chrout_done_unknown_device:
jsr show_cursor_if_enabled
plp
// Restore X and Y
pla
tay
pla
tax
// End wioth error
jmp lvs_device_not_found_error
chrout_done:
jsr show_cursor_if_enabled
plp
// Restore X and Y
pla
tay
pla
tax
lda SCHAR
clc // indicate success
rts
chrout_screen:
// Crude implementation of character output
sei // XXX why do we need to disable interrupts?
jsr hide_cursor_if_visible
lda SCHAR
tax
// Check for special characters
cmp #$00
bne not_00
jmp chrout_done
not_00:
// Linefeed (simply ignored)
// Trivia: BASIC does CRLF with READY. prompt
cmp #$0a
bne not_0a
jmp chrout_done
not_0a:
// Carriage return
cmp #$0d
bne not_0d
// RETURN clears quote and insert modes
lda #$00
sta QTSW
sta INSRT
jmp screen_advance_to_next_line
not_0d:
cmp #$94
bne not_94
// Insert (shift-DELETE)
// Abort if line already max length, ie 79th char is not a space
jsr get_current_line_logical_length
cmp #79
bne definitely_not_too_long
tay
lda (PNT),y
cmp #$20
beq definitely_not_too_long
// Line is too long to extend
jmp chrout_done
definitely_not_too_long:
// Work out if line needs to be expanded, and if so expand it
ldy #39
lda (PNT),y
cmp #$20
beq no_need_to_extend
jsr screen_grow_logical_line
no_need_to_extend:
// Shuffle chars towards end of line
jsr get_current_line_logical_length
tay
!:
// Note: While the following routine is obvious to any skilled
// in the art as the most obvious simple and efficient solution,
// if the screen writes are before the colour writes, it results
// in a relatively long verbatim stretch of bytes when compared to
// the C64 KERNAL. Thus we have swapped the order, just to reduce
// the potential for any argument of copyright infringement, even
// though we really don't believe that the routine can be copyrighted
// due to the lack of creativity.
dey
lda (USER),y
iny
sta (USER),y
dey
lda (PNT),y
iny
sta (PNT),y
dey
cpy PNTR
bne !-
// Increase insert mode count (which causes quote-mode like behaviour)
inc INSRT
// Put space in the inserted gap
lda #$20
sta (PNT),y
jmp chrout_done
not_94:
// DELETE in insert mode embeds control character
ldx INSRT
bne not_14
cmp #$14
bne not_14
// Delete
ldx PNTR
bne delete_non_zero_column
delete_at_column_0:
ldy TBLX
bne not_row_0
// delete from row 0, col 0 does nothing
jmp chrout_done
not_row_0:
// Column 0 delete just moves us to the end of the
// previous line, without actually deleting anything
dec TBLX
jsr get_current_line_logical_length
lda LNMX
sta PNTR
jsr calculate_screen_line_pointer
jmp chrout_done
delete_non_zero_column:
// Copy rest of line down
jsr get_current_line_logical_length
ldy PNTR
cpy LNMX
beq done_delete
dey
!:
iny
lda (PNT),y
dey
sta (PNT),y
iny
lda (USER),y
dey
sta (USER),y
iny
cpy LNMX
bne !-
// Clear char at end of line
jsr get_current_line_logical_length
tay
lda #$20
sta (PNT),y
done_delete:
dec PNTR
jmp chrout_done
not_14:
// Check for quote mode
ldx QTSW
bne is_quote_mode
ldx INSRT
bne is_quote_mode
jmp not_quote_mode
is_quote_mode:
// Is it a control code?
// control codes are $00-$1f and $80-$9f
// (from reading C64 PRG p379-381)
// so we can just check if bits 5 or 6 are set, and if so,
// then it isn't a control character.
pha
and #$60
bne !+
// Yes, a control code in quote mode means we display it as a reverse character
pla
// Low control codes are just +$80
clc
adc #$80
// If it overflowed, then it is a high control code,
// so we need to make it be $80 + $40 + char
// as we will have flipped back to just $00 + char, we should
// now add $c0 if C is set from overflow
bcc low_ctrl_char
adc #$bf // C=1, so adding $BF + C = add $C0
low_ctrl_char:
jmp output_literal_char
!:
pla
not_quote_mode:
// Check for colours
ldx #$f
colour_check_loop:
cmp colour_codes,x
bne !+
stx COLOR
jmp chrout_done
!: dex
bpl colour_check_loop
// Compute's Mapping the 64 p38
cmp #$12
bne not_12
lda #$80
sta RVS
jmp chrout_done
not_12:
// Compute's Mapping the 64 p 38
cmp #$92
bne not_92
lda #$00
sta RVS
jmp chrout_done
not_92:
// Check for cursor movement keys
cmp #$11
bne not_11
lda PNTR
clc
adc #40
sta PNTR
// We need to advance the pointer manually, as normalising
// now will break things. The pointer update is required
// so that we can tell if we really are on the bottom phys
// screen line or not
jsr scroll_up_if_on_last_line
jsr calculate_screen_line_pointer
jmp chrout_done
not_11:
cmp #$1d
bne not_1d
inc PNTR
jsr calculate_screen_line_pointer
jmp chrout_done
not_1d:
cmp #$91
bne not_91
lda PNTR
sec
sbc #40
sta PNTR
jsr calculate_screen_line_pointer
jmp chrout_done
not_91:
cmp #$9d
bne not_9d
dec PNTR
jsr calculate_screen_line_pointer
jmp chrout_done
not_9d:
// Home cursor
cmp #$13
bne not_13
lda #0
sta PNTR
sta TBLX
jsr calculate_screen_line_pointer
jmp chrout_done
not_13:
// Clear screen
cmp #$93
bne not_clearscreen
jsr clear_screen
jmp chrout_done
not_clearscreen:
// Convert PETSCII to screen code
// Don't print other control codes
cmp #$1f
bcs !+
jmp chrout_done
!:
// Codes $C0-$DF become $40-$5F
// But
cmp #$e0
bcs !+
cmp #$c0
bcc !+
and #$7f
jmp output_literal_char // not high char
!:
// Range $20-$3F is unchanged
cmp #$40
bcc output_literal_char // not high char
// Unshifted letters and symbols from $40-$5F
// all end up being -$40
// (C64 PRG p376)
// But anything >= $80 needs to be -$40
// (C64 PRG p380-381)
// And bit 7 should be cleared, only to be
// set by reverse video
sec
sbc #$40
// Fix shifted chars by adding $20 again
cmp #$20
bcc output_literal_char // not high char
cmp #$40
bcs output_literal_char // not high char
clc
adc #$20
output_literal_char:
// Write normal character on the screen
pha
ldy PNTR
ora RVS // Compute's Mapping the 64 p38
sta (PNT),y
// Decrement number of chars waiting to be inserted
lda INSRT
beq !+
dec INSRT
!:
pla
cmp #$22
bne not_quote
// Toggle quote flag if required
lda QTSW
eor #$80
sta QTSW
not_quote:
// Set colour
lda COLOR
sta (USER),y
// Advance the column, and scroll screen down if we need
// to insert a 2nd line in this logical line.
// (eg Compute's Mapping the 64 p41)
ldx TBLX
iny
sty PNTR
cpy #40
bne !+
jsr screen_grow_logical_line
ldy PNTR
!:
cpy #80
bcc no_screen_advance_to_next_line
lda #0
sta PNTR
jmp screen_advance_to_next_line
no_screen_advance_to_next_line:
jmp chrout_done
screen_grow_logical_line:
ldy TBLX
// Don't grow line if it is already grown
lda LDTBL,y
bpl !+
jmp not_last_line // doneb grow line
!:
lda #$80
sta LDTBL,y
// Now make space for the extra line added.
// If we are on the last physical line of the screen,
// Then we need to scroll the screen up
jsr scroll_up_if_on_last_line
// Scroll screen down to make space
// As we are scrolling down, we start from the end,
// and work backwards. We can't be as simple and efficient
// here as we are for scrolling up, because we don't know
// how much must be scrolled.
// Simple solution is to work out how many physical lines
// need shifting down, and then move lines at a time after
// initialising the pointers to the end area of the screen.
ldx #25-2
ldy #0
count_rows_loop:
dex
lda LDTBL,y
bpl !+
dex
!: iny
cpy TBLX
bne count_rows_loop
cpx #0
beq no_copy_down
bmi no_copy_down
// Set pointers to end of screen line, and one line
// above. (It is always one physical line, because
// this can only happen when expanding a line from 40 to
// 80 characters).
// XXX - This is not very efficient, and longer than it
// needs to be. Better would be to work out size to
// copy, and count it down in a pointer somewhere, so
// that loop iteration logic is simpler.
lda HIBASE
clc
adc #3
sta PNT+1
sta SAL+1
lda #>$DBC0
sta EAL+1
sta USER+1
lda #<$03C0
sta PNT+0
sta USER+0
// souce address is line above
sec
sbc #40
sta SAL+0
sta EAL+0
copy_line_down_loop:
ldy #39
cl_inner:
lda (EAL),y
sta (USER),y
lda (SAL),y
sta (PNT),y
dey
bpl cl_inner
// Decrement all pointers by 40
// Low bytes are in common pairs
// Old source is new destination
// Use different registers to minimise byte similarity with C64 KERNAl
ldy SAL+1
sty PNT+1
lda EAL+1
ldy SAL+0
sta USER+1
sty PNT+0
sty USER+0
// Decrementing source pointers
lda SAL+0
sec
sbc #<40
sta SAL+0
sta EAL+0
lda SAL+1
sbc #>40
sta SAL+1
// convert to screen equivalent
sec
sbc HIBASE
clc
adc #>$D800
sta EAL+1
dex
bne copy_line_down_loop
no_copy_down:
jsr calculate_screen_line_pointer
// Erase newly inserted line
ldy #79
!:
lda COLOR
sta (USER),y
lda #$20
sta (PNT),y
dey
cpy #40
bne !-
rts
not_last_line:
rts
scroll_up_if_on_last_line:
// Colour RAM is always in fixed place, so is easiest
// to use to check if we are on the last line.
// The last line is at $D800 + 24*40 = $DBC0
lda USER+1
cmp #>$DBC0
bne not_last_line
lda USER+0
cmp #<$DBC0
beq is_last_line
jsr get_current_line_logical_length
clc
adc USER+0
cmp #<$DBE7-1
bcc not_last_line
is_last_line:
dec TBLX
// FALL THROUGH
scroll_screen_up:
// Now scroll the whole screen up either one or two lines
// based on whether the first screen line is linked or not.
// Get pointers to start of screen + colour RAM
lda HIBASE
sta PNT+1
sta SAL+1
lda #>$D800
sta USER+1
sta EAL+1
lda #$00
sta PNT+0
sta USER+0
// Get pointers to screen/colour RAM source
lda LDTBL+0
bmi !+
lda #40
.byte $2C // BIT $nnnn to skip next instruction
!:
lda #80
sta SAL+0
sta EAL+0
// Copy first three pages
ldy #$00
ldx #3
scroll_copy_loop:
lda (EAL),y
sta (USER),y
lda (SAL),y
sta (PNT),y
iny
bne scroll_copy_loop
inc SAL+1
inc PNT+1
inc EAL+1
inc USER+1
dex
bne scroll_copy_loop
// Copy last partial page
// We need to copy 1000-(3*256)-line length
// = 232 - line length
lda SAL+0
lda #232
sec
sbc SAL+0
tax
scroll_copy_loop2:
lda (EAL),y
sta (USER),y
lda (SAL),y
sta (PNT),y
iny
dex
bne scroll_copy_loop2
// Fill in scrolled up area
ldx SAL+0
scroll_copy_loop3:
lda COLOR
sta (USER),y
lda #$20
sta (PNT),y
iny
dex
bne scroll_copy_loop3
// Shift line linkage list
ldy #0
ldx #24
link_copy:
lda LDTBL+1,y
sta LDTBL+0,y
iny
dex
bne link_copy
// Clear line link flag of last line
stx LDTBL+24
// Restore correct line pointers
jsr calculate_screen_line_pointer
rts
get_current_line_logical_length:
ldy TBLX
lda LDTBL,y
bpl line_not_linked_del
lda #79
.byte $2c // BIT absolute mode, which we use to skip the next two instruction bytes
line_not_linked_del:
lda #39
sta LNMX
rts
screen_advance_to_next_line:
// jsr hide_cursor_if_visible
// Go to start of line
lda #0
sta PNTR
// Advance line number
ldy TBLX
// Do quick fix to line pointer to work out if it is off
// the bottom of the screen.
ldx #40
lda LDTBL,y
bmi !+
.byte $2c
!: ldx #80
txa
clc
adc PNT+0
sta PNT+0
lda PNT+1
adc #0
sta PNT+1
inc TBLX
// Check if it will trigger scrolling
// Work out if we have gone off the bottom of the screen?
// 1040 > 1024, so if high byte of screen pointer is >= (HIBASE+4),
// then we are off the bottom of the screen
lda PNT+1
sec
sbc HIBASE
cmp #3
bcc !+
lda PNT+0
cmp #$e7
bcc !+
// Off the bottom of the screen
jsr scroll_screen_up
!:
jsr calculate_screen_line_pointer
jmp chrout_done
add_40_to_screen_x:
lda PNTR
clc
adc #40
sta PNTR
rts
normalise_screen_x_y:
// Normalise X and Y values
// If X < 0, then make X = X + 40 (or 80, if previous line is linked)
!: lda PNTR
bpl x_not_negative
dec TBLX
// Check that we didn't go backwards off the top of the screen
bpl !+
lda #0
sta TBLX
!: jsr add_40_to_screen_x
// Check if line is linked, if so, add 40 again
ldy TBLX
lda LDTBL,y
bpl !+
jsr add_40_to_screen_x
!:
x_not_negative:
// Work out if X is too big
ldy TBLX
lda LDTBL,y
bpl !+
lda #79
.byte $2C // BIT $nnnn, used to skip next instruction
!: lda #39
cmp PNTR
bcs x_not_too_big
// X value is too big, so subtract 40 and increment Y
lda PNTR
sec
sbc #40
sta PNTR
inc TBLX
x_not_too_big:
// Make sure Y isn't negative
lda TBLX
bpl !+
lda #0
sta TBLX
!:
// Make sure Y isn't too large for absolute size of
// screen
cmp #24
bcc !+
lda #24
sta TBLX
!:
// Make sure Y isn't too much for the screen, taking
// into account the line link table
ldy #24 // max allowable line
ldx #0
link_count_loop:
lda LDTBL,x
bpl !+
dey
!: inx
cpx #25
bne link_count_loop
tya
cmp TBLX
bcs y_ok
sta TBLX
y_ok:
rts
calculate_screen_line_pointer:
jsr normalise_screen_x_y
// Reset pointer to start of screen
lda HIBASE
sta PNT+1
lda #0
sta PNT+0
// Add 40 for every line, or 80 if the lines are linked
ldx TBLX
!:
// Stop if we have counted enough lines
beq !+
// Add 40 or 80 based on whether the line is linked
// or not.
ldy #40
// -1 offset is because we count down from N to 1, not
// N-1 to 0.
lda LDTBL-1,x
bpl cslp_l1
ldy #80
cslp_l1:
// Add computed line length to pointer value
tya
clc
adc PNT+0
sta PNT+0
lda PNT+1
adc #0
sta PNT+1
// Loop back to next line
dex
jmp !-
!:
// FALL THROUGH
update_colour_line_pointer:
// Now setup pointer to colour RAM
lda PNT+0
sta USER+0
lda PNT+1
sec
sbc HIBASE
clc
adc #>$d800
sta USER+1
rts
advance_screen_pointer_40_bytes:
lda PNT+0
clc
adc #<40
sta PNT+0
sta USER+0
lda PNT+1
adc #>40
sta PNT+1
sec
sbc HIBASE
clc
adc #>$D800
sta USER+1
jmp update_colour_line_pointer
-105
View File
@@ -1,105 +0,0 @@
//
// Official Kernal routine, described in:
//
// - [RG64] C64 Programmer's Reference Guide - page 280
// - [CM64] Compute's Mapping the Commodore 64 - page 242
//
// CPU registers that has to be preserved (see [RG64]): none
//
cint_real:
// According to [CM64], this routine checks for PAL/NTSC. It's definitely not done
// within the 'BRK' part, this can be easily checked - POKE something
// to address 678 on a real C64, press STOP+RESTORE, the value won't change
// Detect video system (PAL/NTSC), use Graham's method, as it's short and reliable
// see here: https://codebase64.org/doku.php?id=base:detect_pal_ntsc
lda #$C8 // preparation, as the VIC might be uninitialized
sta VIC_SCROLX
cint_w0:
lda VIC_RASTER
cint_w1:
cmp VIC_RASTER
beq cint_w1
bmi cint_w0
// Result in A, if no interrupt happened during the test:
// #$37 -> 312 rasterlines, PAL, VIC 6569
// #$06 -> 263 rasterlines, NTSC, VIC 6567R8
// #$05 -> 262 rasterlines, NTSC, VIC 6567R56A
cmp #$07
bcs cint_pal
cint_ntsc:
// NTSC C64 (https://codebase64.org/doku.php?id=base:cpu_clocking),
// is clocked at 1.022727 MHz, so that 1/60s is 17045 CPU cycles
ldy #<17045
ldx #>17045
sty CIA1_TIMALO
stx CIA1_TIMAHI
lda #$00
beq !+
cint_pal:
lda #$01
!:
sta TVSFLG
// Setup KEYLOG vector - XXX is it proper place?
lda #<setup_keydecode
sta KEYLOG+0
lda #>setup_keydecode
sta KEYLOG+1
cint_brk: // entry for BRK and STOP+RESTORE - XXX, where should it start?
jsr setup_vicii
// Initialise cursor blink flags (Compute's Mapping the 64 p215)
lda #$00
sta BLNSW
// Set keyboard decode vector (Compute's Mapping the 64 p215)
// Set initial variables for our improved keyboard scan routine
lda #$FF
ldx #6
!: sta BufferOld,x
dex
bpl !-
sta BufferQuantity
// Set key repeat delay (Compute's Mapping the 64 p215)
// Making some numbers up here: Repeat every ~1/10th sec
// But require key to be held for ~1/3sec before
// repeating (Compute's Mapping the 64 p58)
ldx #22-2 // Fudge factor to match speed
stx DELAY
// Set current colour for text (Compute's Mapping the 64 p215)
ldx #$01 // default is light blue ($0E), but we use a different one
stx COLOR
// Set maximum keyboard buffer size (Compute's Mapping the 64 p215)
ldx #10
stx XMAX
// Put non-zero value in MODE to enable case switch
stx MODE
// Set default I/O devices (see SCINIT description at http://sta.c64.org/cbm64krnfunc.html)
jsr clrchn_reset
// Fallthrough/jump to screen clear routine (Compute's Mapping the 64 p215)
jmp clear_screen
+1 -1
View File
@@ -25,7 +25,7 @@ clrchn_real:
// Handle IEC output device
jsr UNLSN
!:
clrchn_reset: // entry needed by CHRIN
clrchn_reset: // entry needed by setup_vicii
// Set input device number to keyboard
lda #$00
sta DFLTN
-22
View File
@@ -1,22 +0,0 @@
setup_vicii:
// XXX there is more to setup within this routine
// Set up default IO values (Compute's Mapping the 64 p215)
lda #$1B // Enable text mode
sta VIC_SCROLY
lda #$C8 // 40 column etc
sta VIC_SCROLX
// Compute's Mapping the 64, p156
// We use a different colour scheme of white text on all blue
lda #$06
sta VIC_EXTCOL
sta VIC_BGCOL0
// Turn off sprites (observed hanging around after running programs and resetting)
lda #$00
sta VIC_SPENA
rts
+2 -19
View File
@@ -8,26 +8,9 @@
// CPU registers that has to be preserved (see [RG64]): .X, .Y
//
// XXX currently does not preserve registers, to be fixed!
GETIN:
// Wait for a key
lda NDX
bne !+
// XXX this should be a dispatcher for several different devices!
// Nothing in keyboard buffer to read
sec
lda #$00
rts
!:
lda KEYD
pha
jsr pop_keyboard_buffer
pla
clc
rts
jmp read_kb_buf
-6
View File
@@ -1,6 +0,0 @@
// Our implementation is longer than the original one,
// placing it here would cause a collision with CHKIN
CHROUT:
jmp chrout_real
+75
View File
@@ -0,0 +1,75 @@
//
// Official Kernal routine, described in:
//
// - [RG64] C64 Programmer's Reference Guide - page 278/279
// - [CM64] Compute's Mapping the Commodore 64 - page 228
//
// CPU registers that has to be preserved (see [RG64]): .Y
//
CHROUT:
sta SCHAR
// Save X and Y values
// (Confirmed by writing a test program that X and Y
// don't get modified, in agreement with C64 PRG's
// description of CHROUT)
phx_trash_a
phy_trash_a
php
// Determine the device number
lda DFLTO
cmp #$03 // screen
bne !+
jmp chrout_screen
!:
jsr iec_check_devnum
bcs chrout_done_unknown_device // not a supported device
chrout_iec:
lda SCHAR
jsr JCIOUT
bcc chrout_done_success
// FALLTROUGH
chrout_done_fail:
plp
// Restore X and Y
ply_trash_a
plx_trash_a
sec // indicate failure
rts
chrout_done_unknown_device:
plp
// Restore X and Y
ply_trash_a
plx_trash_a
// End wioth error
jmp lvs_device_not_found_error
chrout_done_success:
plp
// Restore X and Y
ply_trash_a
plx_trash_a
lda SCHAR
clc // indicate success
rts
-3
View File
@@ -36,9 +36,6 @@ LOAD:
jsr install_ram_routines
#endif
// Allow platform-specific routine to takeover the flow
TARGET_HOOK_LOAD()
// Check whether we support the requested device
lda FA
and #$FC
+3
View File
@@ -0,0 +1,3 @@
Address adjusted to support $FE2D - routine which is probably used by many cartridges and other software to initialize parts of the system. At least the UCart uses it - see here:
- https://www.elektroda.pl/rtvforum/topic3293027.html
@@ -14,9 +14,10 @@ MEMTOP:
ldy MEMSIZK+1
ldx MEMSIZK+0
rts
memtop_set:
// FALLTROUGH
memtop_set: // for compatibility reasons this has to start at $FE2D
sty MEMSIZK+1
stx MEMSIZK+0
-6
View File
@@ -1,6 +0,0 @@
// Our implementation is longer than the original one,
// placing it here would cause a collision with OPEN
CINT:
jmp cint_real
-10
View File
@@ -1,10 +0,0 @@
// Home the cursor
// (Compute's Mapping the 64 p216)
home_cursor:
lda #$00
sta PNTR // x position
sta TBLX // y position
jmp set_pointer_to_current_screen_line
File renamed without changes.
+4 -8
View File
@@ -14,10 +14,8 @@ iec_return_success:
lda #$00
sta C3PO
// Restore registers
pla
tay
pla
tax
ply_trash_a
plx_trash_a
// Report success
clc
rts
@@ -30,9 +28,7 @@ iec_return_DEVICE_NOT_FOUND:
lda #$00
sta C3PO
// Restore registers
pla
tay
pla
tax
ply_trash_a
plx_trash_a
// Report error
jmp kernalerror_DEVICE_NOT_FOUND
Loaded 100 of 261 files, more files were not shown because too many files have changed in this diff. Show more