rename testcode/ to targettest/

This commit is contained in:
mrdudz
2020-09-29 19:14:46 +02:00
parent dcee493e94
commit 4777e98f57
82 changed files with 0 additions and 0 deletions

395
targettest/Makefile Normal file
View File

@@ -0,0 +1,395 @@
#
# Makefile for cc65 testcode
#
# This Makefile requires GNU make
#
# Run 'make SYS=<target>'; or, set a SYS env.
# var. to build for another target system.
SYS ?= c64
# Just the usual way to define a variable
# containing a single space character.
SPACE :=
SPACE +=
# Just the usual way to find out if we're
# using cmd.exe to execute make rules.
ifneq ($(shell echo),)
CMD_EXE = 1
endif
ifdef CMD_EXE
NULLDEV = nul:
DEL = -del /f
RMDIR = rmdir /s /q
else
NULLDEV = /dev/null
DEL = $(RM)
RMDIR = $(RM) -r
endif
ifdef CC65_HOME
AS = $(CC65_HOME)/bin/ca65
CC = $(CC65_HOME)/bin/cc65
CL = $(CC65_HOME)/bin/cl65
LD = $(CC65_HOME)/bin/ld65
else
AS := $(if $(wildcard ../bin/ca65*),../bin/ca65,ca65)
CC := $(if $(wildcard ../bin/cc65*),../bin/cc65,cc65)
CL := $(if $(wildcard ../bin/cl65*),../bin/cl65,cl65)
LD := $(if $(wildcard ../bin/ld65*),../bin/ld65,ld65)
endif
ifneq ($(filter disk testcode.%,$(MAKECMDGOALS)),)
ifdef CC65_HOME
TARGET_PATH = $(CC65_HOME)/target
else
TARGET_PATH := $(if $(wildcard ../target),../target,$(shell $(CL) --print-target-path))
endif
# If TARGET_PATH contains spaces then it is presumed to contain escaped spaces. GNU make
# has very limited support for paths containing spaces. $(wildcard) is the only function
# that is aware of escaped spaces. However, $(wildcard) never returns paths with escaped
# spaces !!! So if it e.g. finds 4 files in a path with 2 spaces then one ends up with a
# return value consisting of 12 plain words :-((
#
# Fortunately we can work around that behaviour here because we know that the files we
# are looking for have known extensions. So we can $(filter) the in our example above 12
# words for file extensions so we come up with 4 path fragments. Then we remove those
# path fragments with $(notdir) from the file names.
#
# So far so good. But here we want to process files from different paths in a single
# recipe further down below and therefore want to prepend the paths to the files with
# $(addprefix). However, $(foreach) isn't aware of escaped spaces (only $(wildcard) is).
# Therefore, we need to replace the spaces with some other character temporarily in order
# to have $(foreach) generate one invocation per file. We use the character '?' for that
# purpose here, just because it is known to not be part of file names.
#
# Inside the recipe generated per file we then replace the '?' again with a space. As we
# want to be compatible with cmd.exe for execution we're not using an escaped space but
# rather double-quote the whole path.
#
# Note: The "strange" $(wildcard) further down below just serves the purpose to unescape
# spaces for cmd.exe. This could have as well been done with another $(subst).
SUBST_TARGET_PATH := $(subst \$(SPACE),?,$(TARGET_PATH))
EMD := $(wildcard $(TARGET_PATH)/$(SYS)/drv/emd/*)
MOU := $(wildcard $(TARGET_PATH)/$(SYS)/drv/mou/*)
TGI := $(wildcard $(TARGET_PATH)/$(SYS)/drv/tgi/*)
EMD := $(addprefix $(SUBST_TARGET_PATH)/$(SYS)/drv/emd/,$(notdir $(filter %.emd,$(EMD))))
MOU := $(addprefix $(SUBST_TARGET_PATH)/$(SYS)/drv/mou/,$(notdir $(filter %.mou,$(MOU))))
TGI := $(addprefix $(SUBST_TARGET_PATH)/$(SYS)/drv/tgi/,$(notdir $(filter %.tgi,$(TGI))))
# This one comes with the VICE emulator.
# See http://vice-emu.sourceforge.net/
C1541 ?= c1541
# For this one, see https://applecommander.github.io/
AC ?= ac.jar
# For this one, see https://www.horus.com/~hias/atari/
DIR2ATR ?= dir2atr
endif
DISK_c64 = testcode.d64
DISK_apple2 = testcode.dsk
DISK_apple2enh = testcode.dsk
DISK_atari = testcode.atr
DISK_atarixl = testcode.atr
# --------------------------------------------------------------------------
# System-dependent settings
# For convenience, these groups and lines are sorted alphabetically, first
# by target-machine group, then by mission, then by program and sub-target.
# --------------------------------------------------------------------------
# Generic rules
.PHONY: all mostlyclean clean zip testcode disk
%: %.c
%: %.s
.c.o:
$(CC) $(CFLAGS) -Ors --codesize 500 -T -g -t $(SYS) $<
$(AS) $(<:.c=.s)
.s.o:
$(AS) $(ASFLAGS) -t $(SYS) $<
.PRECIOUS: %.o
.o:
ifeq ($(SYS),vic20)
$(LD) $(LDFLAGS_$(@F)_$(SYS)) $(LDFLAGS) -o $@ -C vic20-32k.cfg -m $@.map $^ $(SYS).lib
else
$(LD) $(LDFLAGS_$(@F)_$(SYS)) $(LDFLAGS) -o $@ -t $(SYS) -m $@.map $^ $(SYS).lib
endif
# --------------------------------------------------------------------------
# Lists of executables
# omitted: seek
EXELIST_c64 = \
arg-test \
clock \
clock-test \
conio \
cpeek-test \
cprintf \
cursor \
deb \
dir-test \
div-test \
em-test \
exec-test1 \
exec-test2 \
fileio-test \
ft \
getopt-test \
heaptest \
joy-test \
moddiv-test \
mouse-test \
mul-test \
posixio-test \
rename-test \
scanf-test \
ser-test \
strdup-test \
stroserror-test \
strqtok-test \
tinyshell \
uname-test
# omitted: seek clock-test mouse-test ser-test
EXELIST_vic20 = \
arg-test \
clock \
conio \
cpeek-test \
cprintf \
cursor \
deb \
dir-test \
div-test \
em-test \
exec-test1 \
exec-test2 \
fileio-test \
ft \
getopt-test \
heaptest \
joy-test \
moddiv-test \
mul-test \
posixio-test \
rename-test \
scanf-test \
strdup-test \
stroserror-test \
strqtok-test \
tinyshell \
uname-test
# omitted: cpeek-test, clock
EXELIST_apple2 = \
arg-test \
clock-test \
conio \
cprintf \
cursor \
deb \
dir-test \
div-test \
em-test \
exec-test1 \
exec-test2 \
fileio-test \
ft \
getopt-test \
heaptest \
joy-test \
moddiv-test \
mouse-test \
mul-test \
posixio-test \
rename-test \
scanf-test \
seek \
ser-test \
strdup-test \
stroserror-test \
strqtok-test \
tinyshell \
uname-test
EXELIST_apple2enh = $(EXELIST_apple2)
# omitted: cpeek-test
EXELIST_atari = \
arg-test \
clock-test \
clock \
conio \
cprintf \
cursor \
deb \
dir-test \
div-test \
em-test \
exec-test1 \
exec-test2 \
fileio-test \
ft \
getopt-test \
heaptest \
joy-test \
moddiv-test \
mouse-test \
mul-test \
posixio-test \
rename-test \
scanf-test \
seek \
ser-test \
strdup-test \
stroserror-test \
strqtok-test \
tinyshell \
uname-test
EXELIST_atarixl = $(EXELIST_atari)
# none of the testcode can work on the 2600
# EXELIST_atari2600 =
# none of the testcode can work on supervision
# EXELIST_supervision =
# Unlisted targets will try to build everything.
# That lets us learn what they cannot build, and what settings
# we need to use for programs that can be built and run.
ifndef EXELIST_$(SYS)
EXELIST_$(SYS) := ${patsubst %.c,%,$(wildcard *.c)}
endif
# --------------------------------------------------------------------------
# Rules to make the binaries and the disk
testcode: $(EXELIST_$(SYS))
disk: $(DISK_$(SYS))
all: testcode
make -C accelerator
make -C apple2
make -C atari
make -C atari5200
make -C cbm SYS=$(SYS)
make -C gamate
make -C pce
# --------------------------------------------------------------------------
# some programs link against getsp.o
mouse-test: mouse-test.o getsp.o
$(LD) $(LDFLAGS) -t $(SYS) -o $@ $^ $(SYS).lib
ifneq ($(SYS),vic20)
ft: ft.o getsp.o
$(LD) $(LDFLAGS) -t $(SYS) -o $@ $^ $(SYS).lib
tinyshell: tinyshell.o getsp.o
$(LD) $(LDFLAGS) -t $(SYS) -o $@ $^ $(SYS).lib
endif
# some programs need more memory on the vic20
ifeq ($(SYS),vic20)
ft: ft.o getsp.o
$(LD) $(LDFLAGS) -o $@ -C vic20-32k.cfg -m $@.map $^ $(SYS).lib
tinyshell: tinyshell.o getsp.o
$(LD) $(LDFLAGS) -o $@ -C vic20-32k.cfg -m $@.map $^ $(SYS).lib
endif
# --------------------------------------------------------------------------
# Rule to make a CBM disk with all testcode. Needs the c1541 program that comes
# with the VICE emulator.
define D64_WRITE_recipe
$(C1541) -attach $@ -write "$(subst ?,$(SPACE),$(file))" $(notdir $(file)) >$(NULLDEV)
endef # D64_WRITE_recipe
testcode.d64: testcode
@$(C1541) -format testcode,AA d64 $@ >$(NULLDEV)
$(foreach file,$(EXELIST_$(SYS)),$(D64_WRITE_recipe))
# $(foreach file,$(EMD) $(MOU) $(TGI),$(D64_WRITE_recipe))
# --------------------------------------------------------------------------
# Rule to make an Apple II disk with all testcode. Needs the AppleCommander
# program, available at https://applecommander.github.io/, and a template disk
# named 'prodos.dsk'.
define DSK_WRITE_BIN_recipe
$(if $(findstring BF00,$(LDFLAGS_$(notdir $(file))_$(SYS))), \
java -jar $(AC) -p $@ $(notdir $(file)).system sys <"$(wildcard $(TARGET_PATH)/$(SYS)/util/loader.system)")
java -jar $(AC) -as $@ $(notdir $(file)) <"$(file)"
endef # DSK_WRITE_BIN_recipe
define DSK_WRITE_REL_recipe
java -jar $(AC) -p $@ $(notdir $(file)) rel 0 <"$(subst ?,$(SPACE),$(file))"
endef # DSK_WRITE_REL_recipe
testcode.dsk: testcode
cp prodos.dsk $@
$(foreach file,$(EXELIST_$(SYS)),$(DSK_WRITE_BIN_recipe))
# $(foreach file,$(EMD) $(MOU) $(TGI),$(DSK_WRITE_REL_recipe))
# --------------------------------------------------------------------------
# Rule to make an Atari disk with all testcode. Needs the dir2atr program
# available at http://www.horus.com/~hias/atari/ and the MyDos4534 variant
# of dos.sys and dup.sys.
define ATR_WRITE_recipe
cp "$(subst ?,$(SPACE),$(file))" atr/$(notdir $(file))
endef # ATR_WRITE_recipe
testcode.atr: testcode
@mkdir atr
cp "dos.sys" atr/dos.sys
cp "dup.sys" atr/dup.sys
@$(foreach file,$(EXELIST_$(SYS)),$(ATR_WRITE_recipe))
# @$(foreach file,$(EMD) $(MOU) $(TGI),$(ATR_WRITE_recipe))
$(DIR2ATR) -d -b MyDos4534 3200 $@ atr
@$(RMDIR) atr
# --------------------------------------------------------------------------
# Clean-up rules
mostlyclean:
@$(DEL) *.lbl *.map *.o 2>$(NULLDEV)
# we cant use .s since we have asm files in the directory that we want to keep
@$(DEL) ${patsubst %.c,%.s,$(wildcard *.c)} 2>$(NULLDEV)
clean: mostlyclean
@$(DEL) $(EXELIST_$(SYS)) $(DISK_$(SYS)) 2>$(NULLDEV)
make -C accelerator clean
make -C apple2 clean
make -C atari clean
make -C atari5200 clean
make -C cbm SYS=$(SYS) clean
make -C gamate clean
make -C pce clean

View File

@@ -0,0 +1,58 @@
# Just the usual way to find out if we're
# using cmd.exe to execute make rules.
ifneq ($(shell echo),)
CMD_EXE = 1
endif
ifdef CMD_EXE
NULLDEV = nul:
DEL = -del /f
RMDIR = rmdir /s /q
else
NULLDEV = /dev/null
DEL = $(RM)
RMDIR = $(RM) -r
endif
ifdef CC65_HOME
AS = $(CC65_HOME)/bin/ca65
CC = $(CC65_HOME)/bin/cc65
CL = $(CC65_HOME)/bin/cl65
LD = $(CC65_HOME)/bin/ld65
else
AS := $(if $(wildcard ../../../bin/ca65*),../../../bin/ca65,ca65)
CC := $(if $(wildcard ../../../bin/cc65*),../../../bin/cc65,cc65)
CL := $(if $(wildcard ../../../bin/cl65*),../../../bin/cl65,cl65)
LD := $(if $(wildcard ../../../bin/ld65*),../../../bin/ld65,ld65)
endif
all: c64-scpu-test.prg c128-scpu-test.prg c64dtv-test.prg \
c64-c128-test.prg c128-test.prg chameleon-test.prg \
c65-test.prg turbomaster-test.prg
c64-scpu-test.prg: c64-c128-scpu-test.c
$(CL) -t c64 c64-c128-scpu-test.c -o c64-scpu-test.prg
c128-scpu-test.prg: c64-c128-scpu-test.c
$(CL) -t c128 c64-c128-scpu-test.c -o c128-scpu-test.prg
c64dtv-test.prg: c64dtv-test.c
$(CL) -t c64 c64dtv-test.c -o c64dtv-test.prg
c64-c128-test.prg: c64-c128-test.c
$(CL) -t c64 c64-c128-test.c -o c64-c128-test.prg
c128-test.prg: c64-c128-test.c
$(CL) -t c128 c64-c128-test.c -o c128-test.prg
chameleon-test.prg: chameleon-test.c
$(CL) -t c64 chameleon-test.c -o chameleon-test.prg
c65-test.prg: c65-test.c
$(CL) -t c64 c65-test.c -o c65-test.prg
turbomaster-test.prg: turbomaster-test.c
$(CL) -t c64 turbomaster-test.c -o turbomaster-test.prg
clean:
$(RM) *.prg

View File

@@ -0,0 +1,8 @@
/* C64/C128 SuperCPU accelerator test code. */
#define ACC_DETECT detect_scpu
#define ACC_GET_SPEED get_scpu_speed
#define ACC_SET_SPEED set_scpu_speed
#define ACC_NAME "SuperCPU"
#include "turbo-test.c"

View File

@@ -0,0 +1,8 @@
/* C128 in C64 mode accelerator test code. */
#define ACC_DETECT detect_c128
#define ACC_GET_SPEED get_c128_speed
#define ACC_SET_SPEED set_c128_speed
#define ACC_NAME "C128 CPU"
#include "turbo-test.c"

View File

@@ -0,0 +1,8 @@
/* C64DTV accelerator test code. */
#define ACC_DETECT detect_c64dtv
#define ACC_GET_SPEED get_c64dtv_speed
#define ACC_SET_SPEED set_c64dtv_speed
#define ACC_NAME "C64DTV"
#include "turbo-test.c"

View File

@@ -0,0 +1,8 @@
/* C65/C64DX in C64 mode accelerator test code. */
#define ACC_DETECT detect_c65
#define ACC_GET_SPEED get_c65_speed
#define ACC_SET_SPEED set_c65_speed
#define ACC_NAME "C65"
#include "turbo-test.c"

View File

@@ -0,0 +1,8 @@
/* C64 Chameleon accelerator test code. */
#define ACC_DETECT detect_chameleon
#define ACC_GET_SPEED get_chameleon_speed
#define ACC_SET_SPEED set_chameleon_speed
#define ACC_NAME "Chameleon cartridge"
#include "turbo-test.c"

View File

@@ -0,0 +1,57 @@
/* Accelerator test code. */
#ifndef ACC_DETECT
#error This file cannot be used directly (yet)
#endif
#include <time.h>
#include <accelerator.h>
#include <stdio.h>
#include <conio.h>
#include <stdlib.h>
static void print_time_taken(void)
{
clock_t curtime = clock();
clock_t newtime;
unsigned long i;
char buffer[10];
printf("Doing a speed test, please wait\n");
for (i = 0; i < 0x1000; i++) { }
newtime = clock() - curtime;
ultoa(newtime, buffer, 10);
printf("Time taken : %s\n", buffer);
}
static void print_current_speed(void)
{
unsigned char status;
status = ACC_GET_SPEED();
printf("Current "ACC_NAME" speed : %d\n", status + 1);
}
void main(void)
{
unsigned char status;
unsigned char speed = 0;
status = ACC_DETECT();
clrscr();
if (status == 0) {
printf("No "ACC_NAME" detected\n");
} else {
status = ACC_GET_SPEED();
print_current_speed();
/* cycle through all the speeds */
for (speed = SPEED_1X; speed <= SPEED_20X; ++speed) {
printf("Setting "ACC_NAME" speed to %d\n", speed + 1);
ACC_SET_SPEED(speed);
print_current_speed();
print_time_taken();
}
ACC_SET_SPEED(status);
}
}

View File

@@ -0,0 +1,8 @@
/* C64 Turbo Master accelerator test code. */
#define ACC_DETECT detect_turbomaster
#define ACC_GET_SPEED get_turbomaster_speed
#define ACC_SET_SPEED set_turbomaster_speed
#define ACC_NAME "Turbo Master cartridge"
#include "turbo-test.c"

View File

@@ -0,0 +1,71 @@
# For this one see https://applecommander.github.io/
AC ?= ac.jar
# Just the usual way to find out if we're
# using cmd.exe to execute make rules.
ifneq ($(shell echo),)
CMD_EXE = 1
endif
ifdef CMD_EXE
NULLDEV = nul:
DEL = -del /f
RMDIR = rmdir /s /q
else
NULLDEV = /dev/null
DEL = $(RM)
RMDIR = $(RM) -r
endif
ifdef CC65_HOME
AS = $(CC65_HOME)/bin/ca65
CC = $(CC65_HOME)/bin/cc65
CL = $(CC65_HOME)/bin/cl65
LD = $(CC65_HOME)/bin/ld65
else
AS := $(if $(wildcard ../../../bin/ca65*),../../../bin/ca65,ca65)
CC := $(if $(wildcard ../../../bin/cc65*),../../../bin/cc65,cc65)
CL := $(if $(wildcard ../../../bin/cl65*),../../../bin/cl65,cl65)
LD := $(if $(wildcard ../../../bin/ld65*),../../../bin/ld65,ld65)
endif
all: hgrshow hgrtest dhgrshow
disk: hgr.dsk dhgr.dsk
hgr.dsk: hgrshow hgrtest
cp prodos.dsk $@
java -jar $(AC) -as $@ hgrshow <hgrshow
java -jar $(AC) -as $@ hgrtest <hgrtest
java -jar $(AC) -p $@ astronaut.hgr bin 0x2000 <astronaut.hgr
java -jar $(AC) -p $@ chips.hgr bin 0x2000 <chips.hgr
java -jar $(AC) -p $@ macrometer.hgr bin 0x2000 <macrometer.hgr
java -jar $(AC) -p $@ mariner.hgr bin 0x2000 <mariner.hgr
java -jar $(AC) -p $@ rose.hgr bin 0x2000 <rose.hgr
java -jar $(AC) -p $@ werner.hgr bin 0x2000 <werner.hgr
java -jar $(AC) -p $@ winston.hgr bin 0x2000 <winston.hgr
hgrshow: hgrshow.c
$(CL) -Oirs -t apple2 --start-addr 0x4000 -m hgrshow.map $^
hgrtest: hgrtest.c werner.s
$(CL) -Oirs -t apple2 -C apple2-hgr.cfg -m hgrtest.map $^
dhgr.dsk: dhgrshow
cp prodos.dsk $@
java -jar $(AC) -as $@ dhgrshow <dhgrshow
java -jar $(AC) -p $@ catface.dhgr bin 0x2000 <catface.dhgr
java -jar $(AC) -p $@ gatsby.dhgr bin 0x2000 <gatsby.dhgr
java -jar $(AC) -p $@ girl.dhgr bin 0x2000 <girl.dhgr
java -jar $(AC) -p $@ monarch.dhgr bin 0x2000 <monarch.dhgr
java -jar $(AC) -p $@ superman.dhgr bin 0x2000 <superman.dhgr
java -jar $(AC) -p $@ venice.dhgr bin 0x2000 <venice.dhgr
dhgrshow: dhgrshow.c
$(CL) -Oirs -t apple2enh --start-addr 0x4000 -m dhgrshow.map $^
clean:
$(RM) hgr.dsk dhgr.dsk
$(RM) hgrshow hgrshow.map
$(RM) hgrtest hgrtest.map
$(RM) dhgrshow dhgrshow.map

Binary file not shown.

Binary file not shown.

BIN
targettest/apple2/chips.hgr Normal file

Binary file not shown.

View File

@@ -0,0 +1,45 @@
// cl65 -t apple2enh --start-addr 0x4000 dhgrshow.c
#include <tgi.h>
#include <conio.h>
#include <fcntl.h>
#include <string.h>
#include <unistd.h>
#include <dirent.h>
#include <peekpoke.h>
void main (void)
{
unsigned old;
DIR *dir;
struct dirent *ent;
old = videomode (VIDEOMODE_80x24);
tgi_install (a2e_hi_tgi);
tgi_init ();
POKE (0xC05E, 0);
dir = opendir (".");
while (ent = readdir (dir)) {
char *ext;
int hgr;
ext = strrchr (ent->d_name, '.');
if (!ext || strcasecmp (ext, ".dhgr"))
continue;
hgr = open (ent->d_name, O_RDONLY);
POKE (0xC055, 0);
read (hgr, (void*)0x2000, 0x2000);
POKE (0xC054, 0);
read (hgr, (void*)0x2000, 0x2000);
close (hgr);
if (cgetc () == '\r')
break;
}
closedir (dir);
tgi_uninstall ();
videomode (old);
}

Binary file not shown.

BIN
targettest/apple2/girl.dhgr Normal file

Binary file not shown.

View File

@@ -0,0 +1,37 @@
// cl65 -t apple2 --start-addr 0x4000 hgrshow.c
#include <tgi.h>
#include <conio.h>
#include <fcntl.h>
#include <string.h>
#include <unistd.h>
#include <dirent.h>
void main (void)
{
DIR *dir;
struct dirent *ent;
tgi_install (a2_hi_tgi);
tgi_init ();
dir = opendir (".");
while (ent = readdir (dir)) {
char *ext;
int hgr;
ext = strrchr (ent->d_name, '.');
if (!ext || strcasecmp (ext, ".hgr"))
continue;
hgr = open (ent->d_name, O_RDONLY);
read (hgr, (void*)0x2000, 0x2000);
close (hgr);
if (cgetc () == '\r')
break;
}
closedir (dir);
tgi_uninstall ();
}

View File

@@ -0,0 +1,26 @@
// cl65 -t apple2 -C apple2-hgr.cfg hgrtest.c werner.s
#include <tgi.h>
#include <conio.h>
#pragma code-name (push, "LOWCODE")
void say (const char* text)
{
tgi_setcolor (TGI_COLOR_BLACK);
tgi_outtextxy (41, 33, text);
}
#pragma code-name (pop)
void main (void)
{
tgi_install (a2_hi_tgi);
tgi_init ();
cgetc ();
say ("Hi Dude !");
cgetc ();
tgi_uninstall ();
}

Binary file not shown.

Binary file not shown.

Binary file not shown.

BIN
targettest/apple2/rose.hgr Normal file

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@@ -0,0 +1,2 @@
.segment "HGR"
.incbin "werner.hgr"

Binary file not shown.

19
targettest/arg-test.c Normal file
View File

@@ -0,0 +1,19 @@
#include <stdio.h>
#include <stdlib.h>
int main (int argc, char* argv[])
{
int I;
printf ("argc: %d\n", argc);
for (I = 0; I < argc; ++I) {
printf ("argv[%2d]: \"%s\"\n", I, argv[I]);
}
printf ("\n");
getchar ();
return EXIT_SUCCESS;
}

61
targettest/atari/Makefile Normal file
View File

@@ -0,0 +1,61 @@
# Just the usual way to find out if we're
# using cmd.exe to execute make rules.
ifneq ($(shell echo),)
CMD_EXE = 1
endif
ifdef CMD_EXE
NULLDEV = nul:
DEL = -del /f
RMDIR = rmdir /s /q
else
NULLDEV = /dev/null
DEL = $(RM)
RMDIR = $(RM) -r
endif
ifdef CC65_HOME
AS = $(CC65_HOME)/bin/ca65
CC = $(CC65_HOME)/bin/cc65
CL = $(CC65_HOME)/bin/cl65
LD = $(CC65_HOME)/bin/ld65
else
AS := $(if $(wildcard ../../../bin/ca65*),../../../bin/ca65,ca65)
CC := $(if $(wildcard ../../../bin/cc65*),../../../bin/cc65,cc65)
CL := $(if $(wildcard ../../../bin/cl65*),../../../bin/cl65,cl65)
LD := $(if $(wildcard ../../../bin/ld65*),../../../bin/ld65,ld65)
endif
all: charmapping.xex defdev.xex displaylist.xex mem.xex multi.xex ostype.xex \
scrcode.com sys.xex
charmapping.xex: charmapping.c
$(CL) -t atari -o charmapping.xex charmapping.c
defdev.xex: defdev.c
$(CL) -t atari -o defdev.xex defdev.c
displaylist.xex: displaylist.c
$(CL) -t atari -o displaylist.xex displaylist.c
mem.xex: mem.c ../getsp.s
$(CL) -t atari -o mem.xex mem.c ../getsp.s
multi.xex: multi-xex.s multi-xex.cfg
$(CL) -t atari -C multi-xex.cfg multi-xex.s -o multi.xex
ostype.xex: ostype.c
$(CL) -t atari -o ostype.xex ostype.c
scrcode.com: scrcode.s
# ca65 -t atari -o scrcode.o scrcode.s
# ld65 -C atari-asm.cfg -o scrcode.com scrcode.o
$(CL) -t atari -C atari-asm.cfg -o scrcode.com scrcode.s
sys.xex: sys.c
$(CL) -t atari -o sys.xex sys.c
clean:
$(RM) charmapping.xex
$(RM) defdev.xex
$(RM) displaylist.xex
$(RM) mem.xex
$(RM) multi.xex
$(RM) ostype.xex
$(RM) scrcode.o
$(RM) scrcode.com
$(RM) sys.xex

View File

@@ -0,0 +1,51 @@
; Sample using ATARI file format, by "atari-xex.cfg" linker configuration.
;
; This is a very simple example, shows a message to the screen, waits and
; returns to DOS.
;
; Compile with:
; cl65 -tatari -Catari-xex.cfg asm-xex.s -o prog.xex
.include "atari.inc"
; Default RUNAD is "start", export that:
.export start
; Write string to screen
.proc puts
sta ICBAL
stx ICBAH
lda #PUTREC
sta ICCOM
ldx #$FF
stx ICBLL
inx
stx ICBLH
jsr CIOV
rts
.endproc
; Write a message and exit
.proc start
lda #<msg
ldx #>msg
jsr puts
; Delay before returning to DOS
lda #0
tax
loop:
inx
cpx #$FF
adc #0
bcc loop
rts
.endproc
msg: .byte "Hello world", ATEOL

View File

@@ -0,0 +1,63 @@
/*
** testprogram for includes "atari_screen_charmap.h" and "atari_atascii_charmap.h"
**
** 19-Aug-2016, Christian Krueger
*/
#include <conio.h>
#include <atari.h>
#include <peekpoke.h>
#include <string.h>
char pcDefaultMappingString[] = "Hello Atari!";
#include <atari_screen_charmap.h>
char pcScreenMappingString[] = "Hello Atari!";
#include <atari_atascii_charmap.h>
char pcAtasciiMappingString[] = "Hello Atari!";
/* THIS WON'T work due to string merging/collection problems!
char* pcDefaultMappingString = "Hello Atari!";
#include <atari_screen_charmap.h>
char* pcScreenMappingString = "Hello Atari!";
#include <atari_atascii_charmap.h>
char* pcAtasciiMappingString = "Hello Atari!";
*/
int
main(void)
{
static unsigned char expectedAtasciiValues[] = { 40,101,108,108,111,0,33,116,97,114,105,1};
int returnValue = 0;
unsigned char* screen = (unsigned char*) PEEKW(88);
// check default (=atascii)
clrscr();
cputs(pcDefaultMappingString);
returnValue |= memcmp(screen, expectedAtasciiValues, sizeof(expectedAtasciiValues));
clrscr();
memcpy(screen, pcScreenMappingString, sizeof(expectedAtasciiValues));
returnValue |= memcmp(screen, expectedAtasciiValues, sizeof(expectedAtasciiValues));
clrscr();
cputs(pcAtasciiMappingString);
returnValue |= memcmp(screen, expectedAtasciiValues, sizeof(expectedAtasciiValues));
clrscr();
if (returnValue)
cputs("Test FAILED!");
else
cputs("Test passed.");
cputs("\n\rHit any key to exit...");
cgetc();
return returnValue;
}

19
targettest/atari/defdev.c Normal file
View File

@@ -0,0 +1,19 @@
/*
** testprogram printing the default device
**
** 26-Nov-2009, Christian Groessler
*/
#include <stdio.h>
#include <conio.h>
#include <atari.h>
#include <cc65.h>
extern char _defdev[];
int main(void)
{
printf("default device: %s\n", _defdev);
if (doesclrscrafterexit()) cgetc();
return 0;
}

View File

@@ -0,0 +1,64 @@
/*
** test program for ANTIC instructions as defined in "_antic.h"
**
** 23-Feb-2017, Christian Krueger
*/
#include <conio.h>
#include <atari.h>
// code is only for testing purposes, as screen and display list are not aligned,
// and jumps not set!
unsigned char DummyScreen[400];
void DisplayList = {
DL_BLK1,
DL_BLK2,
DL_BLK3,
DL_BLK4,
DL_BLK5,
DL_BLK6,
DL_BLK7,
DL_DLI(DL_BLK8),
DL_LMS(DL_CHR40x8x1),
DummyScreen,
DL_HSCROL(DL_CHR40x10x1),
DL_VSCROL(DL_CHR40x8x4),
DL_CHR40x16x4,
DL_LMS(DL_HSCROL(DL_VSCROL(DL_DLI(DL_CHR20x8x2)))),
DummyScreen+120,
DL_CHR20x16x2,
DL_MAP40x8x4,
DL_MAP80x4x2,
DL_MAP80x4x4,
DL_MAP160x2x2,
DL_MAP160x1x2,
DL_MAP160x2x4,
DL_MAP160x1x4,
DL_MAP320x1x1,
DL_JVB,
DL_JMP
};
/* We know that the sizeof expression is constant; don't tell us. */
#pragma warn (const-comparison, off)
int
main(void)
{
int returnValue = (sizeof DisplayList != 28); // assure only one byte per instruction!
clrscr();
if (returnValue)
cputs("Test FAILED!");
else
cputs("Test passed.");
cputs("\n\rHit any key to exit...");
cgetc();
return returnValue;
}

47
targettest/atari/mem.c Normal file
View File

@@ -0,0 +1,47 @@
/*
** show some memory stuff
**
** 04-Aug-2004, Christian Groessler
*/
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
#include <atari.h>
#include <cc65.h>
extern int getsp(void); /* comes from ../getsp.s */
unsigned char data = 0x12; /* data variable */
unsigned int *APPMHI = (unsigned int *)14; /* 14,15 */
unsigned char *RAMTOP = (unsigned char *)106; /* in pages */
unsigned int *LOMEM = (unsigned int *)128; /* used by BASIC */
unsigned int *MEMTOP = (unsigned int *)741;
unsigned int *MEMLO = (unsigned int *)743;
void *allocmem;
int main(void)
{
allocmem = malloc(257);
clrscr();
printf(" RAMTOP = %02X (%u) - $%04X (%u)\n",
*RAMTOP, *RAMTOP, *RAMTOP * 256, *RAMTOP * 256);
printf(" APPMHI = $%04X (%u)\n", *APPMHI, *APPMHI);
printf(" LOMEM = $%04X (%u) <BASIC only>\n", *LOMEM, *LOMEM);
printf(" MEMTOP = $%04X (%u)\n", *MEMTOP, *MEMTOP);
printf(" MEMLO = $%04X (%u)\n", *MEMLO, *MEMLO);
printf(" ----------------------\n");
printf(" main: $%04X (code)\n", &main);
printf(" data: $%04X (data)\n", &data);
printf(" _dos_type: $%04X (bss)\n", &_dos_type);
printf(" allocmem: $%04X (dyn. data)\n", allocmem);
printf(" sp: $%04X (stack ptr)\n", getsp());
if (allocmem) free(allocmem);
if (doesclrscrafterexit()) cgetc();
return(0);
}

View File

@@ -0,0 +1,35 @@
FEATURES {
STARTADDRESS: default = $2E00;
}
MEMORY {
ZP: file = "", define = yes, start = $0082, size = $007E;
# First memory segment in file, show message
LOADER: file = %O, start = $680, size = 128;
# First memory segment in file, load over COLOR registers:
COLOR: file = %O, start = $2C4, size = 5;
# Second memory segment, load at page 6:
PAGE6: file = %O, start = $600, size = 128;
# Third memory segment in file, load over SDLST register:
SDLST: file = %O, start = $230, size = 2;
# Main segment, load at "STARTADDRESS"
MAIN: file = %O, start = %S, size = $BC20 - %S;
}
FILES {
%O: format = atari;
}
FORMATS {
atari: runad = start,
initad = LOADER: show_load;
}
SEGMENTS {
ZEROPAGE: load = ZP, type = zp, optional = yes;
# Place segments in memory areas:
LOADER: load = LOADER, type = rw;
COLOR: load = COLOR, type = rw;
PAGE6: load = PAGE6, type = rw;
SDLST: load = SDLST, type = rw;
CODE: load = MAIN, type = rw;
RODATA: load = MAIN, type = ro optional = yes;
DATA: load = MAIN, type = rw optional = yes;
BSS: load = MAIN, type = bss, optional = yes, define = yes;
}

View File

@@ -0,0 +1,80 @@
; Multiple segment ATARI file format sample, using custom linker script.
;
; This sample defines a custom display-list screen with no code, writing all
; memory areas directly.
;
; See the linker script (multi-xex.cfg) for the definition of memory areas and
; segments.
;
; Compile with:
; cl65 -tatari -Cmulti-xex.cfg multi-xex.s -o prog.xex
.include "atari.inc"
.macpack atari
; Default RUNAD is "start", export that:
.export start, show_load
; Loader
.segment "LOADER"
show_load:
ldx #0 ; channel 0
lda #<msg_load
sta ICBAL,x ; address
lda #>msg_load
sta ICBAH,x
lda #$FF
sta ICBLL,x ; length
sta ICBLH,x
lda #PUTREC
sta ICCOM,x
jmp CIOV
msg_load:
.byte "Loading....", ATEOL
; We load color values directly into registers
.segment "COLOR"
.byte $16 ; COLOR0
.byte $46 ; COLOR1
.byte $00 ; COLOR2
.byte $6A ; COLOR3
.byte $82 ; COLOR4
; We load our display list over page 6
.segment "PAGE6"
display_list:
.byte DL_BLK8
.byte DL_BLK8
.byte DL_BLK8
.byte DL_BLK8
.byte DL_BLK8
.byte DL_BLK8
.byte DL_CHR20x8x2 | DL_LMS
.word screen_memory
.byte DL_CHR40x8x1
.byte DL_JVB
.word display_list
screen_memory:
; first text line: 20 bytes
scrcode " HeLlO wOrLd! "
; second text line, 40 bytes
.byte 0, 0, 0, 0, 0, 0, 0, 0,70,71,70,71,70,71,70,71,70,71,70,71
.byte 70,71,70,71,70,71,70,71,70,71,70,71, 0, 0, 0, 0, 0, 0, 0, 0
; We write directly to the display list pointer
.segment "SDLST"
.word display_list
; And we load our main program
.code
.proc start
; Jump forever
jmp start
.endproc

46
targettest/atari/ostype.c Normal file
View File

@@ -0,0 +1,46 @@
/*
** testprogram for get_ostype() and get_tv() functions
**
** 09-Jul-2004, chris@groessler.org
*/
#include <stdio.h>
#include <atari.h>
int main(void)
{
unsigned int t, v;
unsigned char palntsc;
unsigned char *rev;
unsigned char minor;
unsigned char c;
t = get_ostype(); /* get computer type */
v = get_tv(); /* get tv system */
palntsc = (v == AT_PAL);
minor = (t & AT_OS_TYPE_MINOR) >> 5;
switch(t & AT_OS_TYPE_MAIN) {
case AT_OS_UNKNOWN:
default:
printf("unknown system type !!\n");
break;
case AT_OS_400800:
if (minor == 1) rev = "A";
else rev = "B";
printf("it's a 400/800, %s, Rev. %s\n",palntsc ? "PAL" : "NTSC",rev);
break;
case AT_OS_1200XL:
if (minor == 1) rev = "10";
else rev = "11";
printf("it's a 1200XL, %s, Rev. %s\n",palntsc ? "PAL" : "NTSC",rev);
break;
case AT_OS_XLXE:
printf("is'a a XL/XE, %s, Rev. %d\n",palntsc ? "PAL" : "NTSC",minor);
break;
}
printf("hit <RETURN> to continue...\n");
c = getchar();
return 0;
}

View File

@@ -0,0 +1,63 @@
; Christian Groessler, 30-Aug-2005
;
; scrcode macro test
;
; compile with
; ca65 -I../../../asminc -tatari -o scrcode.o scrcode.s
; ld65 -tatari -o scrcode.com scrcode.o
.import __CODE_LOAD__, __BSS_LOAD__
.include "atari.inc"
.macpack atari
.code
rts ; SpartaDOS workaround
; entry point
lda #0
tay
tax
; display dispdata
disp: lda dispdata,x
sta (SAVMSC),y
inx
iny
cpx #disp_len
bne disp
; wait for key press
key: lda CH
cmp #255
beq key
rts
.data
dispdata: scrcode "fooBa", 'r', $66, 3+4
disp_len = * - dispdata
.export __AUTOSTART__: absolute = 1
.segment "AUTOSTRT"
.word $02E0
.word $02E1
.word __CODE_LOAD__+1
.export __EXEHDR__: absolute = 1
.segment "EXEHDR"
.word $FFFF
.segment "MAINHDR"
.word __CODE_LOAD__
.word __BSS_LOAD__ - 1
.end

39
targettest/atari/sys.c Normal file
View File

@@ -0,0 +1,39 @@
/*
** testprogram for _sys() function on Atari
**
** 17-Sep-2013, chris@groessler.org
**
** uses PUTCHR IOCB function to display a string
*/
#include <atari.h>
#include <6502.h>
#include <conio.h>
#define IOCB (OS.iocb[0])
static struct regs regs;
static struct __iocb *iocb = &IOCB; /* use IOCB #0 */
static char message[] = "I'm the sys test text\n";
int main(void)
{
/* setup IOCB for CIO call */
iocb->buffer = message;
iocb->buflen = sizeof(message) - 1;
iocb->command = IOCB_PUTCHR;
/* setup input registers */
regs.x = 0; /* IOCB #0 */
regs.pc = 0xe456; /* CIOV */
/* call CIO */
_sys(&regs);
if (regs.y != 1)
cprintf("CIO error 0x%02\r\n", regs.y);
cgetc();
return 0;
}

View File

@@ -0,0 +1,36 @@
# Just the usual way to find out if we're
# using cmd.exe to execute make rules.
ifneq ($(shell echo),)
CMD_EXE = 1
endif
ifdef CMD_EXE
NULLDEV = nul:
DEL = -del /f
RMDIR = rmdir /s /q
else
NULLDEV = /dev/null
DEL = $(RM)
RMDIR = $(RM) -r
endif
ifdef CC65_HOME
AS = $(CC65_HOME)/bin/ca65
CC = $(CC65_HOME)/bin/cc65
CL = $(CC65_HOME)/bin/cl65
LD = $(CC65_HOME)/bin/ld65
else
AS := $(if $(wildcard ../../../bin/ca65*),../../../bin/ca65,ca65)
CC := $(if $(wildcard ../../../bin/cc65*),../../../bin/cc65,cc65)
CL := $(if $(wildcard ../../../bin/cl65*),../../../bin/cl65,cl65)
LD := $(if $(wildcard ../../../bin/ld65*),../../../bin/ld65,ld65)
endif
all: hello
hello: hello.c
$(CL) -t atari5200 -o hello hello.c
clean:
$(RM) hello

View File

@@ -0,0 +1,109 @@
/*
** Fancy hello world program using cc65.
**
** Ullrich von Bassewitz (ullrich@von-bassewitz.de)
**
** TEST version for atari5200 conio, using all four colors
*/
#include <stdlib.h>
#include <string.h>
#include <conio.h>
#include <joystick.h>
/*****************************************************************************/
/* Data */
/*****************************************************************************/
static const char Text [] = "Hello world!";
static unsigned char colors[] = { COLOR_WHITE, COLOR_GREEN, COLOR_RED, COLOR_BLACK };
/*****************************************************************************/
/* Code */
/*****************************************************************************/
int main (void)
{
unsigned char XSize, YSize;
unsigned char PosY;
unsigned char i = 0;
/* Set screen colors */
(void) textcolor (COLOR_WHITE);
(void) bordercolor (COLOR_BLACK);
(void) bgcolor (COLOR_BLACK);
/* Clear the screen, put cursor in upper left corner */
clrscr ();
/* Ask for the screen size */
screensize (&XSize, &YSize);
/* Install joystick driver */
joy_install (joy_static_stddrv);
while (1) {
/* Draw a border around the screen */
/* Top line */
cputc (CH_ULCORNER);
chline (XSize - 2);
cputc (CH_URCORNER);
/* Vertical line, left side */
cvlinexy (0, 1, YSize - 2);
/* Bottom line */
cputc (CH_LLCORNER);
chline (XSize - 2);
cputc (CH_LRCORNER);
/* Vertical line, right side */
cvlinexy (XSize - 1, 1, YSize - 2);
/* Write the greeting in the mid of the screen */
gotoxy ((XSize - strlen (Text)) / 2, YSize / 2);
cprintf ("%s", Text);
PosY = wherey ();
textcolor (colors[i]); /* switch to color #0 */
cputsxy(3, ++PosY, "COLOR 0");
textcolor ((colors[i] + 1) & 3); /* switch to color #1 */
cputsxy(3, ++PosY, "COLOR 1");
textcolor ((colors[i] + 2) & 3); /* switch to color #2 */
cputsxy(3, ++PosY, "COLOR 2");
textcolor ((colors[i] + 3) & 3); /* switch to color #3 */ /* color #3 is the background color. So written text isn't visible. */
cputsxy(3, ++PosY, "COLOR 3");
/* Wait for the user to press and release a button */
while (!joy_read (JOY_1))
;
while (joy_read (JOY_1))
;
i = (i + 1) & 3;
/* Change colors */
textcolor (colors[i]);
bgcolor ((colors[i] + 3) & 3);
/* Clear the screen again */
clrscr ();
}
/* not reached */
joy_uninstall ();
/* Done */
return EXIT_SUCCESS;
}

39
targettest/cbm/Makefile Normal file
View File

@@ -0,0 +1,39 @@
# Run 'make SYS=<target>'; or, set a SYS env.
# var. to build for another target system.
SYS ?= c64
# Just the usual way to find out if we're
# using cmd.exe to execute make rules.
ifneq ($(shell echo),)
CMD_EXE = 1
endif
ifdef CMD_EXE
NULLDEV = nul:
DEL = -del /f
RMDIR = rmdir /s /q
else
NULLDEV = /dev/null
DEL = $(RM)
RMDIR = $(RM) -r
endif
ifdef CC65_HOME
AS = $(CC65_HOME)/bin/ca65
CC = $(CC65_HOME)/bin/cc65
CL = $(CC65_HOME)/bin/cl65
LD = $(CC65_HOME)/bin/ld65
else
AS := $(if $(wildcard ../../../bin/ca65*),../../../bin/ca65,ca65)
CC := $(if $(wildcard ../../../bin/cc65*),../../../bin/cc65,cc65)
CL := $(if $(wildcard ../../../bin/cl65*),../../../bin/cl65,cl65)
LD := $(if $(wildcard ../../../bin/ld65*),../../../bin/ld65,ld65)
endif
all: petscii.prg
petscii.prg: petscii.c
$(CL) -t $(SYS) -O -o petscii.prg petscii.c
clean:
$(DEL) petscii.prg

162
targettest/cbm/petscii.c Normal file
View File

@@ -0,0 +1,162 @@
/* this program prints all available "petscii" characters to screen, once
using putchar (which wraps to kernal i/o) and once using conio (which
will do direct videoram access). after that the produced screencodes
are compared (they should match) (related to issue #988 */
#include <conio.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#if defined(__C64__)
#define VRAMPEEK(x) (*(char*)(0x0400 + (x)))
#define VRAMPOKE(x, y) *(char*)(0x0400 + (x)) = (y)
#define CRAMPEEK(x) ((*(char*)(0xd800 + (x))) & 15)
#define CRAMPOKE(x, y) *(char*)(0xd800 + (x)) = (y)
#else
#error "this target is not supported yet"
#endif
unsigned char x, y, c;
unsigned char c1, c2;
unsigned char *p1, *p2;
int err = 0;
int main(void)
{
clrscr();
bgcolor(COLOR_BLACK);
bordercolor(COLOR_BLACK);
/* output all characters using putchar() */
c = 0;
for (y = 0; y < 16; y++) {
for (x = 0; x < 16; x++) {
/* skip the codes that are unprintable control codes */
if (!((c < 32) || ((c > 127) && (c < 160)))) {
gotoxy(x, y); putchar(c);
}
c++;
}
}
/* output all characters using conio */
c = 0;
for (y = 0; y < 16; y++) {
for (x = 0; x < 16; x++) {
/* skip the codes that are unprintable control codes */
if (!((c < 32) || ((c > 127) && (c < 160)))) {
gotoxy(x + 20, y); cputc(c);
}
c++;
}
}
/* compare the two outputs */
for (y = 0; y < 16; y++) {
for (x = 0; x < 16; x++) {
c1 = VRAMPEEK((y * 40) + x);
c2 = VRAMPEEK((y * 40) + x + 0x14);
if (c1 == c2) {
c = COLOR_GREEN;
} else {
c = COLOR_RED;
err = 1;
}
CRAMPOKE((y * 40) + x, c);
CRAMPOKE((y * 40) + x + 0x14, c);
}
}
/* show the result */
textcolor(COLOR_WHITE);
gotoxy(0, 17);
if (err) {
bordercolor(COLOR_RED);
cputs("errors detected");
} else {
bordercolor(COLOR_GREEN);
cputs("all fine");
}
cputs(" - press a key ");
cursor(1);
cgetc();
cursor(0);
clrscr();
bordercolor(COLOR_BLACK);
/* output all characters directly to the scree */
c = 0;
for (y = 0; y < 16; y++) {
for (x = 0; x < 16; x++) {
VRAMPOKE((y * 40) + x, c);
CRAMPOKE((y * 40) + x, c & 15);
c++;
}
}
/* read the characters with conio peek functions and output with conio */
for (y = 0; y < 16; y++) {
for (x = 0; x < 16; x++) {
gotoxy(x, y);
c1 = cpeekc();
c2 = cpeekrevers();
c = cpeekcolor();
gotoxy(x + 0x14, y);
revers(c2);
textcolor(c);
cputc(c1);
}
}
revers(0);
textcolor(COLOR_WHITE);
gotoxy(0, 17);
cputs("press a key to compare ");
cursor(1);
cgetc();
cursor(0);
/* compare the two outputs */
for (y = 0; y < 16; y++) {
for (x = 0; x < 16; x++) {
c = COLOR_GREEN;
c1 = VRAMPEEK((y * 40) + x);
c2 = VRAMPEEK((y * 40) + x + 0x14);
if (c1 != c2) {
c = COLOR_RED;
err = 1;
}
c1 = CRAMPEEK((y * 40) + x);
c2 = CRAMPEEK((y * 40) + x + 0x14);
if (c1 != c2) {
c = COLOR_RED;
err = 1;
}
CRAMPOKE((y * 40) + x, c);
CRAMPOKE((y * 40) + x + 0x14, c);
}
}
/* show the result */
revers(0);
textcolor(COLOR_WHITE);
gotoxy(0, 17);
if (err) {
bordercolor(COLOR_RED);
cputs("errors detected");
} else {
bordercolor(COLOR_GREEN);
cputs("all fine");
}
cputs(" - press a key ");
cursor(1);
cgetc();
cursor(0);
return 0;
}

110
targettest/clock-test.c Normal file
View File

@@ -0,0 +1,110 @@
/* Calendar-clock test program
**
** 2018-Sep-25, chris@groessler.org
** 2019-Dec-30, Greg King
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <errno.h>
#ifdef __CC65__
#include <conio.h>
#include <cc65.h>
#endif
static int print_time(void)
{
struct tm *cur_tm;
time_t cur_time = time(NULL);
if (cur_time == -1) {
printf("time() failed: %s\n", strerror(errno));
return 1;
}
cur_tm = localtime(&cur_time);
printf("time: %s\n", asctime(cur_tm));
// DEBUG:
printf("year=%d, mon=%d, mday=%d\nhour=%d, min=%d, sec=%d\n",
cur_tm->tm_year, cur_tm->tm_mon, cur_tm->tm_mday,
cur_tm->tm_hour, cur_tm->tm_min, cur_tm->tm_sec);
return 0;
}
int main(int argc, char **argv)
{
char c;
int s;
struct tm cur_time;
struct timespec new_time;
#ifdef __CC65__
/* If DOS automatically will clear the screen after the program exits,
** then wait for a key-press.
*/
if (doesclrscrafterexit())
atexit((void (*)(void))cgetc);
#endif
if (argc == 1) {
return print_time();
}
if (argc != 2) {
#if defined(__APPLE2__)
printf("USAGE: CALL2051 [:REM YY-MM-DD-HH-MM-SS]\n");
#elif defined(__ATMOS__) || defined(__CBM__)
printf("Usage: run [:rem YY-MM-DD-HH-MM-SS]\n");
#else
printf("Usage: %s [YY-MM-DD-HH-MM-SS]\n", argv[0]);
#endif
return 1;
}
memset(&cur_time, 0, sizeof cur_time);
s = sscanf(argv[1], "%d-%d-%d-%d-%d-%d",
&cur_time.tm_year, &cur_time.tm_mon, &cur_time.tm_mday,
&cur_time.tm_hour, &cur_time.tm_min, &cur_time.tm_sec);
if (s != 6 || cur_time.tm_year > 99 /* other input values aren't being verified */) {
printf("Invalid date-time format\n");
return 1;
}
cur_time.tm_year += 100; /* assume 21st century */
--cur_time.tm_mon;
memset(&new_time, 0, sizeof new_time);
new_time.tv_sec = mktime(&cur_time);
printf("\nYou are about to set the time to\n--> %s\nContinue (y/n)? ", ctime(&new_time.tv_sec));
do {
#ifdef __CC65__
c = cgetc();
#else
c = getchar();
#endif
} while (c != 'y' && c != 'Y' && c != 'n' && c != 'N');
printf("%c\n", c);
if (c == 'n' || c == 'N') {
printf("User abort\n");
return 0;
}
s = clock_settime(CLOCK_REALTIME, &new_time);
if (s) {
printf("clock_settime() failed: %s\n", strerror(errno));
return 1;
}
printf("Time set!\n\n");
//DEBUG test begin
return print_time();
//DEBUG test end
}
/* Local Variables: */
/* c-file-style: "cpg" */
/* c-basic-offset: 4 */
/* End: */

24
targettest/clock.c Normal file
View File

@@ -0,0 +1,24 @@
/*
** simple clock test
**
** 06-Nov-2001, Christian Groessler
*/
#include <stdio.h>
#include <conio.h>
#include <time.h>
int main(void)
{
printf("\ncc65 time routines test program\n");
printf("-------------------------------\n");
printf("clocks per second: %d\n", CLOCKS_PER_SEC);
printf("current clock: %ld\n", clock());
printf("hit <return> to exit...");
cgetc();
printf("\n");
return(0);
}

172
targettest/conio.c Normal file
View File

@@ -0,0 +1,172 @@
/*
* conio API test program
*
* keys:
*
* 1...0 change text color
* F5/F6 change border color
* F7/F8 change background color
*
*/
#include <conio.h>
#include <string.h>
#include <stdlib.h>
#include <joystick.h>
#if defined(__GAMATE__)
/* there is not enough screen space to show all 256 characters at the bottom */
#define NUMCHARS 128
#define NUMCOLS 4
#else
#define NUMCHARS 256
#define NUMCOLS 16
#endif
static char grid[5][5] = {
{CH_ULCORNER, CH_HLINE, CH_TTEE, CH_HLINE, CH_URCORNER},
{CH_VLINE, ' ', CH_VLINE, ' ', CH_VLINE },
{CH_LTEE, CH_HLINE, CH_CROSS, CH_HLINE, CH_RTEE },
{CH_VLINE, ' ', CH_VLINE, ' ', CH_VLINE },
{CH_LLCORNER, CH_HLINE, CH_BTEE, CH_HLINE, CH_LRCORNER}
};
void main(void)
{
unsigned int i, j, n;
unsigned char xsize, ysize, tcol, bgcol, bcol, inpos = 0;
#if defined(__NES__) || defined(__PCE__) || defined(__GAMATE__)
unsigned char joy;
joy_install(joy_static_stddrv);
#endif
clrscr();
screensize(&xsize, &ysize);
cputs("cc65 conio test\n\r");
cputs("Input:[ ]"); /* 8 spaces */
tcol = textcolor(0); /* memorize original textcolor */
bgcol = bgcolor(0); /* memorize original background color */
bcol = bordercolor(0); /* memorize original border color */
(void)bordercolor(bcol);
(void)bgcolor(bgcol);
cputsxy(0, 2, "Colors:" );
for (i = 0; i < 3; ++i) {
gotoxy(i, 3 + i);
for (j = 0; j < NUMCOLS; ++j) {
(void)textcolor(j);
cputc('X');
}
}
(void)textcolor(tcol);
cprintf("\n\n\r Screensize: %ux%u", xsize, ysize);
chlinexy(0, 6, xsize);
cvlinexy(0, 6, 3);
chlinexy(0, 8, xsize);
cvlinexy(xsize - 1, 6, 3);
cputcxy(0, 6, CH_ULCORNER);
cputcxy(xsize - 1, 6, CH_URCORNER);
cputcxy(0, 8, CH_LLCORNER);
cputcxy(xsize - 1, 8, CH_LRCORNER);
for (i = 0; i < 5; ++i) {
gotoxy(xsize - 5, i);
for (j = 0; j < 5; ++j) {
cputc(grid[i][j]);
}
}
gotoxy(0, ysize - 2 - ((NUMCHARS + xsize) / xsize));
revers(1);
for (i = 0; i < xsize; ++i) {
cputc('0' + i % 10);
}
revers(0);
for (i = 0; i < NUMCHARS; ++i) {
if ((i != '\n') && (i != '\r')) {
cputc(i);
} else {
cputc(' ');
}
}
while(wherex() > 0) {
cputc('#');
}
revers(1);
for (i = 0; i < xsize; ++i) {
cputc('0' + i % 10);
}
revers(0);
cursor(1);
for (;;) {
/* do the "rvs" blinking */
i = textcolor(COLOR_BLACK);
gotoxy(8, 2);
j = (++n / 16) & 1;
revers(j);
cputc(j ? 'R' : ' ');
revers(j ^ 1);
cputs(" rvs");
revers(0);
(void)textcolor(i);
gotoxy(7 + inpos, 1);
#if defined(__NES__) || defined(__PCE__) || defined(__GAMATE__)
/* not all targets have waitvsync */
waitvsync();
/* for targets that do not have a keyboard, read the first
joystick */
joy = joy_read(JOY_1);
cprintf("%02x", joy);
#else
i = cgetc();
switch (i) {
case CH_ENTER:
clrscr();
return;
case CH_CURS_LEFT:
inpos = (inpos - 1) % 8;
break;
case '0': case '1': case '2': case '3': case '4':
case '5': case '6': case '7': case '8': case '9':
(void)textcolor(i - '0');
break;
#ifdef CH_F5
case CH_F5:
bcol = (bcol + 1) & 0x0f;
(void)bordercolor(bcol);
break;
#endif
#ifdef CH_F6
case CH_F6:
bcol = (bcol - 1) & 0x0f;
(void)bordercolor(bcol);
break;
#endif
#ifdef CH_F7
case CH_F7:
bgcol = (bgcol + 1) & 0x0f;
(void)bgcolor(bgcol);
break;
#endif
#ifdef CH_F8
case CH_F8:
bgcol = (bgcol - 1) & 0x0f;
(void)bgcolor(bgcol);
break;
#endif
default:
cputc(i);
/* fallthrough */
case CH_CURS_RIGHT:
inpos = (inpos + 1) % 8;
}
#endif
}
}

310
targettest/cpeek-test.c Normal file
View File

@@ -0,0 +1,310 @@
/* Test that the cpeek...() functions are the inverses of cputc(),
** revers(), and textcolor() for the full range of character codes.
**
** 2017-07-15, Greg King
** 2017-12-12, Groepaz
*/
#include <conio.h>
#include <cc65.h>
/* Standard location of the screen */
#if defined(__C128__) || defined(__C64__)
/* only 40-column screen */
# define SCREEN_RAM ((unsigned char*)0x0400)
#elif defined(__C16__) /* Plus4 also */
# define SCREEN_RAM ((unsigned char*)0x0C00)
#elif defined(__CBM510__)
# define SCREEN_RAM ((unsigned char*)0xF000)
# define COLOR_RAM ((unsigned char*)0xd400)
#elif defined(__CBM610__)
# define SCREEN_RAM ((unsigned char*)0xD000)
#elif defined(__PET__)
# define SCREEN_RAM ((unsigned char*)0x8000)
#elif defined(__VIC20__)
# define SCREEN_RAM ((unsigned char*)0x1000)
#else
# error This program cannot test that target.
# define SCREEN_RAM ((unsigned char*)0)
#endif
static unsigned char width;
/* Move the cursor backward one char with
** the recognition of a row change.
*/
static void chBack (void)
{
unsigned char y = wherey ();
unsigned char x = wherex ();
if (x == 0) {
x = width;
--y;
}
--x;
gotoxy (x, y);
}
/* Move the cursor forward one char with
** the recognition of a row change.
*/
static void chForth (void)
{
unsigned char y = wherey ();
unsigned char x = wherex ();
if (++x >= width) {
x = 0;
++y;
}
gotoxy (x, y);
}
/* A hack to get an unmodified byte from the
** screen memory at the current cursor position.
*/
static unsigned char peekChWithoutTranslation (void)
{
#if defined(__CBM610__)
return peekbsys ((unsigned)&SCREEN_RAM[wherey () * width + wherex ()]);
#else
return SCREEN_RAM[wherey () * width + wherex ()];
#endif
}
/* as above, but for color ram */
static unsigned char peekColWithoutTranslation (void)
{
#if defined(__CBM610__) || defined (__PET__)
return COLOR_WHITE;
#elif defined(__C128__) || defined(__C64__) || defined(__VIC20__) || defined(__CBM510__)
return COLOR_RAM[wherey () * width + wherex ()] & 0x0f;
#else
return COLOR_RAM[wherey () * width + wherex ()];
#endif
}
/* A test which outputs the given char, reads it back from
** screen memory, outputs the returned char at the next position,
** then compares the two screen memory bytes for identity.
**
** Note: cpeekc() must be tested indirectly because some platforms "fold" their
** character code-set into a smaller screen code-set. Therefore, cpeekc() might
** return an equivalent, but not equal, character to the one that was cputc().
*/
static unsigned char testCPeekC (char ch)
{
unsigned char ch2_a, ch2_b, ch2_c;
/* Test the given char-code, but not the
** special characters NEWLINE and RETURN
** (they don't put anything on the screen).
*/
if (('\n' == ch) || ('\r' == ch)
) {
return 1;
}
/* toggle revers mode every few chars so cpeekc gets tested for both */
revers ((ch >> 3) & 1);
/* output additional space every now and then, that way not only even or only
odd half of the character cell will be tested */
#if defined(__C64__)
if ((width == 80) && ((ch % 17) == 0)) {
cputc(' ');
}
#endif
/* Output the char to the screen. */
cputc (ch);
/* Move the cursor pos. to the previous output. */
chBack ();
/* Get back the written char without any translation. */
ch2_b = peekChWithoutTranslation ();
/* Get back the written char,
** including the translation, screen-code -> text.
*/
ch2_a = cpeekc ();
/* Move the cursor to the following writing position. */
chForth ();
/* Output again the char which was read back by cpeekc(). */
cputc (ch2_a);
/* Move the cursor pos. to the second output. */
chBack ();
/* Get back the second written char without any translation;
** and, compare it to the first untranslated char.
*/
ch2_c = peekChWithoutTranslation ();
if ((ch2_c != ch2_b)
#if defined(__C128__) || defined(__C64__)
/* VDC memory is not accessible, soft80 has no "videoram" */
&& (width == 40)
#endif
){
/* The test was NOT succesful.
** Output a diagnostic; and, return FAILURE.
*/
revers(0);
cprintf ("\r\nError on char: %#x was %#x instead.", ch, ch2_a);
cprintf ("\r\nRaw screen codes: %#x, %#x.", ch2_b, ch2_c);
cprintf ("\r\nscreen width: %#d", width);
return 0;
}
/* The test was succesful.
** Move the cursor to the following writing position.
*/
chForth ();
return 1;
}
static unsigned char testCPeekCol (char ch)
{
unsigned char ch2_a, ch2_b, ch2_c;
/* Output the char to the screen. */
textcolor (ch);
cputc ('*');
/* Move the cursor pos. to the previous output. */
chBack ();
/* Get back the written char without any translation. */
ch2_b = peekColWithoutTranslation ();
/* Get back the written char,
** including the translation, screen-code -> text.
*/
ch2_a = cpeekcolor ();
/* Move the cursor to the following writing position. */
chForth ();
/* Output again the char which was read back by cpeekc(). */
textcolor (ch2_a);
cputc ('x');
/* Move the cursor pos. to the second output. */
chBack ();
/* Get back the second written char without any translation;
** and, compare it to the first untranslated char.
*/
ch2_c = peekColWithoutTranslation ();
if ((ch2_c != ch2_b)
#if defined(__C128__)
/* VDC memory is not accessible */
&& (width == 40)
#endif
){
/* The test was NOT succesful.
** Output a diagnostic; and, return FAILURE.
*/
revers(0);
cprintf ("\r\nError on color: %#x was %#x instead.", ch, ch2_a);
cprintf ("\r\nRaw color codes: %#x, %#x.", ch2_b, ch2_c);
return 0;
}
/* The test was succesful.
** Move the cursor to the following writing position.
*/
chForth ();
return 1;
}
/* The main code initiates the screen for the tests, and sets the reverse flag.
** Then, it calls testCPeekC() for every char within 0..255.
** Then, it calls testCPeekCol() for each color
** Returns zero for success, one for failure.
*/
int main (void)
{
unsigned char i, c1, c2;
char s[10];
int ret = 0;
clrscr ();
revers (0);
textcolor(1);
bgcolor(0);
screensize (&width, &i);
#if defined(__VIC20__)
/* The VIC-20's screen is too small to hold the full test. */
i = 2;
#else
i = 0;
#endif
do {
if (!testCPeekC (i)) {
ret = 1;
goto exiterror;
}
} while (++i != 0); /* will wrap around when finished */
#if defined(__VIC20__)
cgetc();
#endif
/* test colors */
#if defined(__VIC20__)
clrscr ();
#endif
revers (0);
textcolor(1);
#if defined (__CBM610__) || defined (__PET__)
cprintf("\n\rno COLOR_RAM\n\r");
#elif defined (__C128__) || defined (__C64__)
if (width == 40) {
cprintf("\n\rCOLOR_RAM at $%04x\n\r", COLOR_RAM);
} else {
cprintf("\n\rno COLOR_RAM\n\r");
}
#else
cprintf("\n\rCOLOR_RAM at $%04x\n\r", COLOR_RAM);
#endif
do {
if (!testCPeekCol (i)) {
ret = 1;
goto exiterror;
}
} while (++i != 16); /* max 16 colors */
/* test revers */
textcolor(1); cputc('\n'); cputc('\r');
revers(0); cputc('x'); chBack (); c1 = cpeekrevers(); chForth();
revers(1); cputc('X'); chBack (); c2 = cpeekrevers(); chForth();
cputc('\n'); cputc('\r');
revers(c1); cputc('o');
revers(c2); cputc('O');
/* test cpeeks() */
revers(0);
cprintf("\n\rtest1234"); gotox(0); cpeeks(s, 8); cputs("\n");
cputs(s);
exiterror:
if (doesclrscrafterexit()) {
cgetc();
}
return ret;
}

38
targettest/cprintf.c Normal file
View File

@@ -0,0 +1,38 @@
/*
** test program for the cprintf() function
** (for the \r and \n special operators)
** CPG
**
** The output generated by this program should look
** like this:
**
** ---- top of screen --------
** 12345
** 67890
**
**
** 67890
**
** hit return to exit....
.
.
.
** ---- bottom of screen -----
*/
#include <stdio.h>
#include <conio.h>
int main(void)
{
clrscr();
cprintf("12345\n");
cprintf("67890\n");
gotoxy(0,4);
cprintf("12345\r");
cprintf("67890\r");
printf("\n\n");
printf("hit return to exit....\n");
fgetc(stdin);
return(0);
}

49
targettest/cursor.c Normal file
View File

@@ -0,0 +1,49 @@
/*
** test for conio cursor() function
** CPG 2002
**
** the cursor should be in the same state as mentioned in the printfs
*/
#include <conio.h>
#if 1
#define NEWLINE cprintf("\r\n")
#define PRINTF cprintf
#else
#include <stdio.h>
#define NEWLINE printf("\n")
#define PRINTF printf
#endif
int main(void)
{
char c;
NEWLINE;
cursor (1);
PRINTF("enter key (cursor on): ");
c = cgetc();
NEWLINE;
cursor (0);
PRINTF("enter key (cursor off): ");
c = cgetc();
NEWLINE;
PRINTF("enter key (cursor on): ");
cursor (1);
c = cgetc();
NEWLINE;
PRINTF("enter key (cursor off): ");
cursor (0);
c = cgetc();
NEWLINE;
PRINTF("hit any key to exit...");
c = cgetc();
NEWLINE;
return(0);
}

38
targettest/deb.c Normal file
View File

@@ -0,0 +1,38 @@
/*
** test program for the debugger
**
** press 'd' to enter the debugger
**
*/
#include <stdio.h>
#include <conio.h>
#include <6502.h>
#include <dbg.h>
int main(void)
{
char c;
/* Initialize the debugger */
DbgInit (0);
clrscr();
cputsxy(4,10,"Debugger test...."); cgetc();
while(1) {
printf("press d to debug, q to exit....\n");
c = cgetc();
if (c == 'q') {
printf("exiting....\n");
return(0);
}
if (c == 'd') {
printf("entering debug...\n");
BREAK();
printf("return from debug...\n");
}
else {
printf("unknown key '%c'\n",c);
}
}
}

100
targettest/dir-test.c Normal file
View File

@@ -0,0 +1,100 @@
/*
first test for posix directory routines for the c64
kludges:
- currently uses cbm_open, which conflicts with standard i/o,
which in turn makes it infact kindof unuseable. this can
be easily changed however, since the only reason not to use
open/read was that it currently appends ,u,r to filenames
- the offset in current dir stream should better be calculated
from the values returned by "read".
- the type flag isnt filled in atm.
- scandir/alphasort/versionsort is missing
- some bits are currently untested (ie, unused in the testprogram)
27/02/2003 gpz
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <dirent.h>
#include <conio.h>
#if defined(__CBM__)
#include <cbm.h>
#elif defined(__APPLE2__)
#include <apple2.h>
#endif
int main(void)
{
char* name = ".";
unsigned char go = 0;
DIR *D;
register struct dirent* E;
/* Explain usage and wait for a key */
printf ("Use the following keys:\n"
" g -> go ahead without stop\n"
" q -> quit directory listing\n"
" r -> return to last entry\n"
" s -> seek back to start\n"
"Press any key to start ...\n");
cgetc ();
/* Open the directory */
D = opendir (name);
if (D == 0) {
printf("error opening %s: %s\n", name, strerror (errno));
return 1;
}
/* Output the directory */
errno = 0;
printf("contents of \"%s\":\n", name);
while ((E = readdir (D)) != 0) {
printf ("dirent.d_name[] : \"%s\"\n", E->d_name);
#if !defined(__ATARI__)
printf ("dirent.d_blocks : %10u\n", E->d_blocks);
#endif
printf ("dirent.d_type : %10d\n", E->d_type);
#if !defined(__APPLE2__) && !defined(__ATARI__)
printf ("telldir() : %10lu\n", telldir (D));
#endif
printf ("---\n");
if (!go) {
switch (cgetc ()) {
case 'g':
go = 1;
break;
case 'q':
goto done;
#if !defined(__APPLE2__) && !defined(__ATARI__)
case 'r':
seekdir (D, E->d_off);
break;
#endif
#if !defined(__ATARI__)
case 's':
rewinddir (D);
break;
#endif
}
}
}
done:
if (errno == 0) {
printf ("Done\n");
} else {
printf("Done: %d (%s)\n", errno, strerror (errno));
}
/* Close the directory */
closedir (D);
return 0;
}

45
targettest/div-test.c Normal file
View File

@@ -0,0 +1,45 @@
/* div-test.c
**
** This program tests the division and modulo operators
** and the div() library function.
*/
#include <cc65.h>
#include <stdbool.h>
#include <stdio.h>
#include <stdlib.h>
static bool test (int dividend, int divisor)
{
div_t result;
result = div (dividend, divisor);
printf ("%+d/%+d= %+d, %+d%%%+d= %+d, div()= %+d, %+d\n",
dividend, divisor, dividend / divisor,
dividend, divisor, dividend % divisor,
result.quot, result.rem);
return result.quot * divisor + result.rem != dividend;
}
int main (void)
{
bool t;
printf ("\nTest of division and modulus operations:\n\n");
t = test (+40, +3) ||
test (+40, -3) ||
test (-40, +3) ||
test (-40, -3);
if (t) {
printf ("\nThe div() function made a wrong result!\n");
}
if (doesclrscrafterexit ()) {
printf ("\nTap the Return key to quit. ");
getchar ();
}
return (int)t;
}

274
targettest/em-test.c Normal file
View File

@@ -0,0 +1,274 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <conio.h>
#include <em.h>
#define FORCE_ERROR1 0
#define FORCE_ERROR2 0
#define PAGE_SIZE 128 /* Size in words */
#define BUF_SIZE (PAGE_SIZE + PAGE_SIZE/2)
static unsigned buf[BUF_SIZE];
static void cleanup (void)
/* Remove the driver on exit */
{
em_unload ();
}
static void fill (register unsigned* page, register unsigned char count, register unsigned num)
{
register unsigned char i;
for (i = 0; i < count; ++i, ++page) {
*page = num;
}
}
static void cmp (unsigned page, register const unsigned* buf,
register unsigned char count, register unsigned num)
{
register unsigned char i;
for (i = 0; i < count; ++i, ++buf) {
if (*buf != num) {
cprintf ("\r\nData mismatch in page $%04X at $%04X\r\n"
"Data is $%04X (should be $%04X)\r\n",
page, buf, *buf, num);
#ifdef __ATARI__
cgetc ();
#endif
exit (EXIT_FAILURE);
}
}
}
static const char* em_error (int e)
{
switch (e) {
case EM_ERR_OK: return "ok";
case EM_ERR_NO_DRIVER: return "no driver";
case EM_ERR_CANNOT_LOAD: return "cannot load";
case EM_ERR_INV_DRIVER: return "invalid driver";
case EM_ERR_NO_DEVICE: return "no device";
case EM_ERR_INSTALLED: return "already installed";
}
return "unknown";
}
typedef struct emd_test_s {
char key;
char *displayname;
char *drivername;
} emd_test_t;
static emd_test_t drivers[] = {
#if defined(__APPLE2__)
{ '0', "Apple II auxiliary memory", "a2.auxmem.emd" },
#endif
#if defined(__APPLE2ENH__)
{ '0', "Apple II auxiliary memory", "a2e.auxmem.emd" },
#endif
#if defined(__ATARI__)
{ '0', "Atari 130XE memory", "atr130.emd" },
#endif
#if defined(__ATARIXL__)
{ '0', "Atari 130XE memory", "atrx130.emd" },
#endif
#if defined(__C16__)
{ '0', "C16 RAM above $8000", "c16-ram.emd" },
#endif
#if defined(__C64__)
{ '0', "C64 RAM above $D000", "c64-ram.emd" },
{ '1', "C64 256K", "c64-c256k.emd" },
{ '2', "Double Quick Brown Box", "c64-dqbb.emd" },
{ '3', "GEORAM", "c64-georam.emd" },
{ '4', "Isepic", "c64-isepic.emd" },
{ '5', "RamCart", "c64-ramcart.emd" },
{ '6', "REU", "c64-reu.emd" },
{ '7', "C128 VDC (in C64 mode)", "c64-vdc.emd" },
{ '8', "C64DTV himem", "dtv-himem.emd" },
{ '9', "65816 extra banks", "c64-65816.emd" },
{ 'k', "Kerberos", "c64-kerberos.emd" },
#endif
#if defined(__C128__)
{ '0', "C128 RAM in bank 1", "c128-ram.emd" },
{ '1', "C128 RAM in banks 1, 2 & 3", "c128-ram2.emd" },
{ '2', "GEORAM", "c128-georam.emd" },
{ '3', "RamCart", "c128-ramcart.emd" },
{ '4', "REU", "c128-reu.emd" },
{ '5', "VDC", "c128-vdc.emd" },
{ '6', "Internal Function RAM", "c128-ifnram.emd" },
{ '7', "External Function RAM", "c128-efnram.emd" },
#endif
#if defined(__CBM510__)
{ '0', "CBM5x0 RAM in bank 2", "cbm510-ram.emd" },
#endif
#if defined(__CBM610__)
{ '0', "CBM6x0/7x0 RAM in bank 2", "cbm610-ram.emd" },
#endif
{ 0, NULL, NULL }
};
int main (void)
{
unsigned char Res;
unsigned I;
unsigned Offs;
unsigned PageCount;
unsigned char X, Y;
struct em_copy c;
unsigned index;
signed char valid_key = -1;
char key;
clrscr ();
cputs ("Which RAM exp to test?\r\n\r\n");
for (index = 0; drivers[index].key; ++index) {
cprintf("%c: %s\r\n", drivers[index].key, drivers[index].displayname);
}
while (valid_key < 0) {
key = cgetc();
for (index = 0; drivers[index].key && valid_key < 0; ++index) {
if (key == drivers[index].key) {
valid_key = index;
}
}
}
clrscr ();
Res = em_load_driver (drivers[valid_key].drivername);
if (Res != EM_ERR_OK) {
cprintf ("Error in em_load_driver: %u\r\n%s\r\n", Res, em_error(Res));
cprintf ("os: %u, %s\r\n", _oserror, _stroserror (_oserror));
#ifdef __ATARI__
cgetc ();
#endif
exit (EXIT_FAILURE);
}
atexit (cleanup);
/* Get the number of available pages */
PageCount = em_pagecount ();
cprintf ("Loaded ok, page count = $%04X\r\n", PageCount);
/* TEST #1: em_map/em_use/em_commit */
cputs ("Testing em_map/em_use/em_commit");
/* Fill all pages */
cputs ("\r\n Filling ");
X = wherex ();
Y = wherey ();
for (I = 0; I < PageCount; ++I) {
/* Fill the buffer and copy it to em */
fill (em_use (I), PAGE_SIZE, I);
em_commit ();
/* Keep the user happy */
gotoxy (X, Y);
cputhex16 (I);
}
#if FORCE_ERROR1
((unsigned*) em_map (0x03))[0x73] = 0xFFFF;
em_commit ();
#endif
/* Check all pages */
cputs ("\r\n Comparing ");
X = wherex ();
Y = wherey ();
for (I = 0; I < PageCount; ++I) {
/* Get the buffer and compare it */
cmp (I, em_map (I), PAGE_SIZE, I);
/* Keep the user happy */
gotoxy (X, Y);
cputhex16 (I);
}
/* TEST #2: em_copyfrom/em_copyto. */
cputs ("\r\nTesting em_copyfrom/em_copyto");
/* We're filling now 384 bytes per run to test the copy routines with
** other sizes.
*/
PageCount = (PageCount * 2) / 3;
/* Setup the copy structure */
c.buf = buf;
c.count = sizeof (buf);
/* Fill again all pages */
cputs ("\r\n Filling ");
X = wherex ();
Y = wherey ();
c.page = 0;
c.offs = 0;
for (I = 0; I < PageCount; ++I) {
/* Fill the buffer and copy it to em */
fill (buf, BUF_SIZE, I ^ 0xFFFF);
em_copyto (&c);
/* Adjust the em offset */
Offs = c.offs + sizeof (buf);
c.offs = (unsigned char) Offs;
c.page += (Offs >> 8);
/* Keep the user happy */
gotoxy (X, Y);
cputhex16 (I);
}
#if FORCE_ERROR2
c.page = 0x03;
em_copyfrom (&c);
buf[0x73] = 0xFFFF;
em_copyto (&c);
#endif
/* Check all pages */
cputs ("\r\n Comparing ");
X = wherex ();
Y = wherey ();
c.page = 0;
c.offs = 0;
for (I = 0; I < PageCount; ++I) {
/* Get the buffer and compare it */
em_copyfrom (&c);
cmp (I, buf, BUF_SIZE, I ^ 0xFFFF);
/* Adjust the em offset */
Offs = c.offs + sizeof (buf);
c.offs = (unsigned char) Offs;
c.page += (Offs >> 8);
/* Keep the user happy */
gotoxy (X, Y);
cputhex16 (I);
}
/* Success */
cprintf ("\r\nPassed!\r\n");
#ifdef __ATARI__
cgetc ();
#endif
return 0;
}

24
targettest/exec-test1.c Normal file
View File

@@ -0,0 +1,24 @@
/*
** These programs test cc65's exec() program-chaining function.
** exec-test1 runs exec-test2 -- that tests the loading and starting of another
** program. Then, exec-test2 runs arg-test -- that tests command-line argument
** passing.
**
** 2013-08-24, Greg King
*/
#include <unistd.h>
#include <string.h>
#include <errno.h>
#include <conio.h>
int main (void) {
clrscr ();
cprintf ("\nExec-test #1 -- launching #2...\r\n");
exec ("exec-test2", "");
cprintf ("\nFailed to find #2:\r\n %s.\r\n", _stroserror (_oserror));
cgetc ();
return _oserror;
}

23
targettest/exec-test2.c Normal file
View File

@@ -0,0 +1,23 @@
/*
** These programs test cc65's exec() program-chaining function.
** exec-test1 runs exec-test2 -- that tests the loading and starting of another
** program. Then, exec-test2 runs arg-test -- that tests command-line argument
** passing.
**
** 2013-08-24, Greg King
*/
#include <unistd.h>
#include <string.h>
#include <errno.h>
#include <conio.h>
int main (void) {
cprintf ("\nExec-test #2 -- launching arg-test...\r\n\n");
exec ("arg-test", "arg1 arg2 \"\" arg4");
cprintf ("\nFailed to find arg-test:\r\n %s.\r\n", _stroserror (_oserror));
cgetc ();
return _oserror;
}

97
targettest/fileio-test.c Normal file
View File

@@ -0,0 +1,97 @@
#include <stdio.h>
#include <string.h>
#include <errno.h>
#include <fcntl.h>
FILE* Fopen (const char* Name, const char* Mode)
{
FILE* F;
printf ("Opening %s(%s): ", Name, Mode);
F = fopen (Name, Mode);
if (F) {
printf ("Ok (%d)\n", fileno (F));
} else {
printf (strerror (errno));
}
return F;
}
void Fwrite (FILE* F, const void* Buf, unsigned Size)
{
size_t Res;
Res = fwrite (Buf, 1, Size, F);
printf ("Writing %u bytes to %d: %u\n", Size, fileno (F), Res);
}
int Fread (FILE* F, void* Buf, unsigned Size)
{
size_t Res;
Res = fread (Buf, 1, Size, F);
printf ("Reading %u bytes from %d: %u\n", Size, fileno (F), Res);
return Res > 0? Res : 0;
}
void Fclose (FILE* F)
{
printf ("Closing %d:", fileno (F));
if (fclose (F) == 0) {
printf ("Ok\n");
} else {
printf (strerror (errno));
}
}
int main (void)
{
FILE* F1;
FILE* F2;
int Res;
static const char text1[] = "This goes into file #1\n";
static const char text2[] = "This goes into file #2\n";
static const char text3[] = "This goes into file #3\n";
static const char text4[] = "This goes into file #4\n";
static char Buf[200];
F1 = Fopen ("foobar1", "w");
F2 = Fopen ("foobar2", "w");
Fwrite (F1, text1, sizeof (text1) - 1);
Fwrite (F2, text2, sizeof (text2) - 1);
Fwrite (F1, text1, sizeof (text1) - 1);
Fwrite (F2, text2, sizeof (text2) - 1);
Fclose (F1);
Fclose (F2);
F1 = Fopen ("foobar3", "w");
F2 = Fopen ("foobar4", "w");
Fwrite (F1, text3, sizeof (text3) - 1);
Fwrite (F2, text4, sizeof (text4) - 1);
Fwrite (F1, text3, sizeof (text3) - 1);
Fwrite (F2, text4, sizeof (text4) - 1);
Fclose (F1);
Fclose (F2);
F1 = Fopen ("foobar1", "r");
Res = Fread (F1, Buf, sizeof (Buf));
printf ("%.*s", Res, Buf);
Res = Fread (F1, Buf, sizeof (Buf));
Fclose (F1);
return 0;
}

110
targettest/ft.c Normal file
View File

@@ -0,0 +1,110 @@
/*
** simple file I/O test
**
** 12-Jun-2000, Christian Groessler
**
** please compile with
** cl65 -tsystem ft.c getsp.s -o ft.com
**
** The program asks for a filename (if it hasn't
** got one from argv). I then opens the file,
** reads the the first 16 bytes and displays them
** (as hex values).
** The values of sp (cc65 runtime stack pointer)
** are displayed at some places. The displayed
** value should always be the same.
*/
#include <stdio.h>
#include <string.h>
#include <fcntl.h>
#include <errno.h>
#include <conio.h>
#include <unistd.h>
extern int getsp(void); /* is provided in getsp.s */
/* Atari's fd indirection table */
#ifdef __ATARI__
extern char __fd_index[];
struct fd_t {
char usage;
char iocb;
char dev;
char flag;
};
extern struct fd_t __fd_table[];
#endif
int main(int argc,char **argv)
{
char *filename,*x;
char buf[20];
int i,l,lr;
int fd;
int csp;
if (argc >= 2) {
filename = *(argv+1);
}
else {
printf("\nfilename: ");
x = fgets(buf,19,stdin);
printf("\n");
if (!x) {
printf("nothing read\n");
return(0);
}
#if 0
l = strlen(x);
printf("read: ");
for (i=0; i<l; i++) printf("%02X ",*(x+i)); printf("\n");
#endif
filename = x;
}
printf("using filename \"%s\"\n",filename);
csp = getsp();
printf("now opening file... sp = %d\n",csp);
fd = open(filename,O_RDONLY);
csp = getsp();
if (fd == -1) {
char x1 = _oserror;
printf("open failed: os: %d,\n\terrno: %d, sp = %d\n",x1,errno,csp);
cgetc();
return(0);
}
printf("open success -- handle = $%x, sp = %d\n",fd,csp);
#ifdef __ATARI__
printf("fd_index:\n ");
for (i=0; i<12; i++) printf("%02X ",__fd_index[i]);
printf("\nfd_table:\n");
for (i=0; i<8; i++) {
printf(" usa: %d, iocb: %02X, dev: %02X\n",
__fd_table[i].usage,
__fd_table[i].iocb,
__fd_table[i].dev);
}
#endif
lr = read(fd,buf,16); /* read first 16 bytes */
csp = getsp();
if (lr == -1) {
printf("read failed: %d (sp = %d)\n",errno,csp);
cgetc();
return(0);
}
l = close(fd);
if (l == -1) {
printf("close failed: %d\n",errno);
cgetc();
return(0);
}
csp = getsp();
printf("\n\nThe data read: (%d bytes, sp = %d)\n",lr,csp);
for (i=0; i<lr; i++) {
printf("%02X ",buf[i]);
if (!((i+1) & 7)) printf("\n");
}
printf("\n\npress return to exit...");
getchar();
return(0);
}

View File

@@ -0,0 +1,54 @@
# Just the usual way to find out if we're
# using cmd.exe to execute make rules.
ifneq ($(shell echo),)
CMD_EXE = 1
endif
ifdef CMD_EXE
NULLDEV = nul:
DEL = -del /f
RMDIR = rmdir /s /q
else
NULLDEV = /dev/null
DEL = $(RM)
RMDIR = $(RM) -r
endif
ifdef CC65_HOME
AS = $(CC65_HOME)/bin/ca65
CC = $(CC65_HOME)/bin/cc65
CL = $(CC65_HOME)/bin/cl65
LD = $(CC65_HOME)/bin/ld65
else
AS := $(if $(wildcard ../../../bin/ca65*),../../../bin/ca65,ca65)
CC := $(if $(wildcard ../../../bin/cc65*),../../../bin/cc65,cc65)
CL := $(if $(wildcard ../../../bin/cl65*),../../../bin/cl65,cl65)
LD := $(if $(wildcard ../../../bin/ld65*),../../../bin/ld65,ld65)
endif
all: audiotest.bin lcdtest.bin ctest.bin
audiotest.bin: audiotest.s
$(CL) -l audiotest.lst -t gamate -o audiotest.bin audiotest.s
lcdtest.bin: lcdtest.s
$(CL) -l lcdtest.lst -t gamate -o lcdtest.bin lcdtest.s
ctest.bin: ctest.c
$(CL) -l ctest.lst -t gamate -o ctest.bin ctest.c
nachtm.bin: nachtm.c
$(CL) -Os -l nachtm.lst -t gamate -o nachtm.bin nachtm.c
gamate-fixcart nachtm.bin
test1: lcdtest.bin
cd ~/Desktop/mame/winmess/ && wine mess.exe gamate -window -skip_gameinfo -cart ~/Desktop/cc65/github/cc65/testcode/lib/gamate/lcdtest.bin
test2: audiotest.bin
cd ~/Desktop/mame/winmess/ && wine mess.exe gamate -window -skip_gameinfo -cart ~/Desktop/cc65/github/cc65/testcode/lib/gamate/audiotest.bin
testc: ctest.bin
cd ~/Desktop/mame/winmess/ && wine mess.exe gamate -window -skip_gameinfo -cart ~/Desktop/cc65/github/cc65/testcode/lib/gamate/ctest.bin
testn: nachtm.bin
cd ~/Desktop/mame/winmess/ && wine mess.exe gamate -window -skip_gameinfo -cart ~/Desktop/cc65/github/cc65/testcode/lib/gamate/nachtm.bin
clean:
$(RM) lcdtest.o audiotest.o ctest.o
$(RM) lcdtest.bin audiotest.bin ctest.bin nachtm.bin
$(RM) audiotest.lst lcdtest.lst ctest.lst

View File

@@ -0,0 +1,457 @@
;
; original audiotest.s by PeT (mess@utanet.at)
;
; cl65 -t gamate -o audiotest.bin audiotest.s
;
.include "gamate.inc"
.zeropage
addr: .word 0
psa: .word 0
readaddr: .word 0
editbuffer1: .byte 0,0,0,0, 0,0,0,0
writeaddr: .word 0
editbuffer2: .byte 0,0,0,0, 0,0,0,0
cursor: .byte 0
controlslast: .byte 0
controlsedge: .byte 0
.bss
temp_x: .byte 0
temp_y: .byte 0
temp_a: .byte 0
irq_count: .byte 0
nmi_count: .byte 0
psx: .byte 0
psy: .byte 0
xpos: .byte 0
ypos: .byte 0
.rodata
chars: .incbin "cga2.chr"
hex2asc: .byte "0123456789abcdef"
.code
;-------------------------------------------------------------------------------
.export IRQStub, NMIStub
.proc NMIStub
inc nmi_count
rts
.endproc
.proc IRQStub
inc irq_count
rts
.endproc
;-------------------------------------------------------------------------------
.export Start
.proc Start
sei
lda #0
sta ZP_IRQ_CTRL
lda #>AUDIO_BASE
sta writeaddr+1
sta readaddr+1
lda #<AUDIO_BASE
sta writeaddr
sta readaddr
lda #$10
sta editbuffer1+6
lda #$e
sta editbuffer2+5
lda #$ff
sta editbuffer2+3
lda #$ff
sta editbuffer2+4
lda #$0f
sta editbuffer2
lda #$0f
sta editbuffer2+1
lda #$0e
sta editbuffer2+2
lda #$38
sta editbuffer1+7
lda #0
sta LCD_XPOS
sta LCD_YPOS
sta irq_count
sta cursor
lda #1
sta nmi_count
cli
lda #LCD_MODE_INC_Y
sta LCD_MODE
jsr printy
lda #1
sta ZP_IRQ_CTRL
loop:
lda irq_count
loop1:
cmp irq_count
beq loop1
lda irq_count
and #7
bne loop1
lda #LCD_MODE_INC_Y
sta LCD_MODE
ldx #3
ldy #32
lda irq_count
jsr printhex
lda cursor
ldy #0
cmp #20
bcc firstline
sec
sbc #20
ldy #24
firstline:
sta LCD_X
sty LCD_Y
lda #' '
jsr printsign
norclearcursor:
jsr inputs
lda irq_count
and #8
bne nocursor
lda cursor
ldy #0
cmp #20
bcc firstline2
sec
sbc #20
ldy #24
firstline2:
sta LCD_X
sty LCD_Y
lda #'x'
jsr printsign
nocursor:
lda #LCD_MODE_INC_Y
sta LCD_MODE
jsr printy
jmp loop
.endproc
.proc printy
ldy #0
loop1:
tya
pha
asl
tax
lda readaddr,y
ldy #8
jsr printhex
pla
tay
iny
cpy #10
bne loop1
loop2:
tya
pha
tya
sec
sbc #10
asl
tax
lda readaddr,y
ldy #16
jsr printhex
pla
tay
iny
cpy #20
bne loop2
ldx #0
ldy #32
lda nmi_count
jsr printhex
rts
.endproc
;-------------------------------------------------------------------------------
.proc inputs
lda controlslast
eor JOY_DATA
and controlslast
eor #$ff
sta controlsedge
and #JOY_DATA_UP
bne notup
lda cursor
lsr
tay
bcs uplow
lda readaddr,y
clc
adc #$10
sta readaddr,y
jmp notup
uplow:
lda readaddr,y
clc
adc #1
sta readaddr,y
notup:
lda controlsedge
and #JOY_DATA_DOWN
bne notdown
lda cursor
lsr
tay
bcs downlow
lda readaddr,y
sec
sbc #$10
sta readaddr,y
jmp notdown
downlow:
lda readaddr,y
sec
sbc #1
sta readaddr,y
notdown:
lda controlsedge
and #JOY_DATA_LEFT
bne notleft
lda cursor
beq notleft
dec cursor
notleft:
lda controlsedge
and #JOY_DATA_RIGHT
bne notright
lda cursor
cmp #40
beq notright
inc cursor
notright:
lda controlsedge
and #JOY_DATA_START
bne notstart
lda #0
sta AUDIO_BASE
sta AUDIO_BASE+1
sta AUDIO_BASE+2
sta AUDIO_BASE+3
sta AUDIO_BASE+4
sta AUDIO_BASE+5
sta AUDIO_BASE+6
sta AUDIO_BASE+8
sta AUDIO_BASE+9
sta AUDIO_BASE+10
sta AUDIO_BASE+11
sta AUDIO_BASE+12
sta AUDIO_BASE+13
sta AUDIO_BASE+7
notstart:
lda controlsedge
and #JOY_DATA_SELECT
bne notselect
lda editbuffer1
sta AUDIO_BASE
lda editbuffer1+1
sta AUDIO_BASE+1
lda editbuffer1+2
sta AUDIO_BASE+2
lda editbuffer1+3
sta AUDIO_BASE+3
lda editbuffer1+4
sta AUDIO_BASE+4
lda editbuffer1+5
sta AUDIO_BASE+5
lda editbuffer1+6
sta AUDIO_BASE+6
lda editbuffer2
sta AUDIO_BASE+8
lda editbuffer2+1
sta AUDIO_BASE+9
lda editbuffer2+2
sta AUDIO_BASE+10
lda editbuffer2+3
sta AUDIO_BASE+11
lda editbuffer2+4
sta AUDIO_BASE+12
lda editbuffer2+5
sta AUDIO_BASE+13
lda editbuffer1+7
sta AUDIO_BASE+7
notselect:
lda controlsedge
and #JOY_DATA_FIRE_A
bne notbuttona
ldy #0
ldy #0
writea:
lda editbuffer1,y
sta (writeaddr),y
iny
cpy #8
bne writea
writeb:
lda editbuffer2-8,y
sta (writeaddr),y
iny
cpy #16
bne writeb
notbuttona:
lda controlsedge
and #JOY_DATA_FIRE_B
bne notbuttonb
ldy #0
reada:
lda (readaddr),y
sta editbuffer1,y
iny
cpy #8
bne reada
readb: lda (readaddr),y
sta editbuffer2-8,y
iny
cpy #16
bne readb
notbuttonb:
lda JOY_DATA
sta controlslast
rts
.endproc
;-------------------------------------------------------------------------------
.proc printstring
sta psa
stx psa+1
ldx #0
stx psx
sty psy
printstring2:
ldy #0
lda (psa),y
beq printstring1
ldx psx
stx LCD_X
ldy psy
sty LCD_Y
jsr printsign
inc psx
lda psa
clc
adc #1
sta psa
lda psa+1
adc #0
sta psa+1
jmp printstring2
printstring1:
rts
.endproc
.proc printstringy
sta psa
stx psa+1
printstring2:
ldy #0
lda (psa),y
beq printstring1
jsr printsign
lda psa
clc
adc #1
sta psa
lda psa+1
adc #0
sta psa+1
jmp printstring2
printstring1:
rts
.endproc
.proc printhex
pha
lsr
lsr
lsr
lsr
and #$0f
stx temp_x
tax
lda hex2asc,x
ldx temp_x
stx LCD_X
sty LCD_Y
jsr printsign
pla
and #$0f
inx
stx temp_x
tax
lda hex2asc,x
ldx temp_x
stx LCD_X
sty LCD_Y
jmp printsign
.endproc
.proc printsign
sty temp_y
stx temp_x
sta temp_a
lda temp_a
sta addr
lda #0
sta addr+1
asl addr
rol addr+1
asl addr
rol addr+1
asl addr
rol addr+1
lda addr
clc
adc #<chars
sta addr
lda addr+1
adc #>chars
sta addr+1
ldx #8
ldy #0
printsign1:
lda (addr),y
sta LCD_DATA
iny
dex
bne printsign1
ldx temp_x
ldy temp_y
rts
.endproc

BIN
targettest/gamate/cga2.chr Normal file

Binary file not shown.

52
targettest/gamate/ctest.c Normal file
View File

@@ -0,0 +1,52 @@
#include <gamate.h>
#include <time.h>
#include <conio.h>
unsigned char y = 0;
unsigned char x = 0;
unsigned short n;
int main(int argc, char *argv[])
{
clrscr();
gotoxy(0,0);cputs("Gamate C-Test");
textcolor(0);gotoxy(0,5);cputs("abcdABCD 0");
textcolor(1);gotoxy(0,6);cputs("abcdABCD 1");
textcolor(2);gotoxy(0,7);cputs("abcdABCD 2");
textcolor(3);gotoxy(0,8);cputs("abcdABCD 3");
while(1) {
textcolor(COLOR_BLACK);
n = clock();
gotoxy(0,2);cprintf("%04x %02x %02x %02x", n, x, y, *((unsigned char*)JOY_DATA));
switch((*((unsigned char*)JOY_DATA))) {
case 0xff ^ JOY_UP_MASK:
++y; if (y == 0xc8) y = 0;
break;
case 0xff ^ JOY_DOWN_MASK:
--y; if (y == 0xff) y = 0xc7;
break;
case 0xff ^ JOY_LEFT_MASK:
++x;
break;
case 0xff ^ JOY_RIGHT_MASK:
--x;
break;
case 0xff ^ JOY_BTN_A_MASK:
break;
}
waitvsync();
(*((unsigned char*)LCD_XPOS)) = x;
(*((unsigned char*)LCD_YPOS)) = y;
}
return 0;
}

421
targettest/gamate/lcdtest.s Normal file
View File

@@ -0,0 +1,421 @@
;
; original lcdtest.s by PeT (mess@utanet.at)
;
; cl65 -t gamate -o lcdtest.bin lcdtest.s
;
.include "gamate.inc"
.zeropage
addr: .word 0
psa: .word 0
.bss
temp_x: .byte 0
temp_y: .byte 0
temp_a: .byte 0
irq_count: .byte 0
nmi_count: .byte 0
psx: .byte 0
psy: .byte 0
count: .word 0
counted: .word 0
xpos: .byte 0
ypos: .byte 0
.rodata
chars: .incbin "cga2.chr"
hex2asc: .byte "0123456789abcdef"
format: .byte "IrqNmiCountXposYpos", 0
xdesc: .byte "0123456789abcdefghijklmnopqrstuv", 0
ydesc: .byte "0123456789ABCDEFGHIJKLMNOPQRSTUV", 0
.code
;-------------------------------------------------------------------------------
.export IRQStub, NMIStub
.proc NMIStub
inc nmi_count
rts
.endproc
.proc IRQStub
inc irq_count
lda count
sta counted
lda count+1
sta counted+1
lda #0
sta count
sta count+1
rts
.endproc
;-------------------------------------------------------------------------------
.export Start
.proc Start
sei
lda #0
sta ZP_IRQ_CTRL
lda #0
sta LCD_XPOS
sta LCD_YPOS
cli
lda #LCD_MODE_INC_Y
sta LCD_MODE
lda #0
sta LCD_X
lda #<xdesc
ldx #>xdesc
ldy #0
jsr printstring
lda #LCD_XPOS_PLANE2
sta LCD_X
lda #<xdesc
ldx #>xdesc
ldy #128
jsr printstring
lda #0
sta LCD_X
lda #<ydesc
ldx #>ydesc
ldy #0
sty LCD_Y
jsr printstringy
lda #(LCD_XPOS_PLANE2|(128/8)) ; ???
sta LCD_X
lda #<ydesc
ldx #>ydesc
ldy #0
sty LCD_Y
jsr printstringy
lda #<format
ldx #>format
ldy #8
jsr printstring
lda #0
sta LCD_MODE
lda #24/8
sta LCD_X
lda #24
sta LCD_Y
lda #'X'
jsr printsign
lda #$80
sta LCD_MODE
lda #32/8
sta LCD_X
lda #32
sta LCD_Y
lda #'Y'
jsr printsign
lda #$c0
sta LCD_MODE
lda #40/8
sta LCD_X
lda #40
sta LCD_Y
lda #'Z'
jsr printsign
lda #0
sta LCD_MODE
lda #LCD_XPOS_PLANE2|(48/8)
sta LCD_X
lda #48
sta LCD_Y
lda #'x'
jsr printsign
lda #$80
sta LCD_MODE
lda #(LCD_XPOS_PLANE2|(56/8))
sta LCD_X
lda #56
sta LCD_Y
lda #'y'
jsr printsign
lda #$c0
sta LCD_MODE
lda #(LCD_XPOS_PLANE2|(64/8))
sta LCD_X
lda #64
sta LCD_Y
lda #'z'
jsr printsign
lda #LCD_MODE_INC_Y|1
sta LCD_MODE
lda #16/8
sta LCD_X
lda #72
sta LCD_Y
lda #'V'
jsr printsign
lda #LCD_MODE_INC_Y|2
sta LCD_MODE
lda #24/8
sta LCD_X
lda #72
sta LCD_Y
lda #'V'
jsr printsign
lda #LCD_MODE_INC_Y|4
sta LCD_MODE
lda #32/8
sta LCD_X
lda #72
sta LCD_Y
lda #'V'
jsr printsign
lda #LCD_MODE_INC_Y|8
sta LCD_MODE
lda #40/8
sta LCD_X
lda #72
sta LCD_Y
lda #'V'
jsr printsign
lda #1
sta ZP_IRQ_CTRL
loop:
lda count
clc
adc #1
sta count
lda count+1
adc #0
sta count+1
lda irq_count
cmp irq_count
beq loop
jsr inputs
lda #LCD_MODE_INC_Y
sta LCD_MODE
jsr printy
jmp loop
.endproc
;-------------------------------------------------------------------------------
.proc printy
ldx #0
ldy #16
lda irq_count
jsr printhex
ldx #3
ldy #16
lda nmi_count
jsr printhex
ldx #6
ldy #16
lda counted+1
jsr printhex
ldx #8
ldy #16
lda counted
jsr printhex
ldx #11
ldy #16
lda xpos
jsr printhex
ldx #14
ldy #16
lda ypos
jsr printhex
rts
.endproc
.proc inputs
lda JOY_DATA
and #JOY_DATA_UP
bne notup
dec ypos
lda ypos
sta LCD_YPOS
notup:
lda JOY_DATA
and #JOY_DATA_DOWN
bne notdown
inc ypos
lda ypos
sta LCD_YPOS
notdown:
lda JOY_DATA
and #JOY_DATA_LEFT
bne notleft
dec xpos
lda xpos
sta LCD_XPOS
notleft:
lda JOY_DATA
and #JOY_DATA_RIGHT
bne notright
inc xpos
lda xpos
sta LCD_XPOS
notright:
lda JOY_DATA
and #JOY_DATA_START
bne notstart
notstart:
lda JOY_DATA
and #JOY_DATA_SELECT
bne notselect
notselect:
lda JOY_DATA
and #JOY_DATA_FIRE_A
bne notbuttona
notbuttona:
lda JOY_DATA
and #JOY_DATA_FIRE_B
bne notbuttonb
notbuttonb:
rts
.endproc
;-------------------------------------------------------------------------------
.proc printstring
sta psa
stx psa+1
ldx #0
stx psx
sty psy
printstring2:
ldy #0
lda (psa),y
beq printstring1
ldx psx
stx LCD_X
ldy psy
sty LCD_Y
jsr printsign
inc psx
lda psa
clc
adc #1
sta psa
lda psa+1
adc #0
sta psa+1
jmp printstring2
printstring1:
rts
.endproc
.proc printstringy
sta psa
stx psa+1
printstring2:
ldy #0
lda (psa),y
beq printstring1
jsr printsign
lda psa
clc
adc #1
sta psa
lda psa+1
adc #0
sta psa+1
jmp printstring2
printstring1:
rts
.endproc
.proc printhex
pha
lsr
lsr
lsr
lsr
and #$0f
stx temp_x
tax
lda hex2asc,x
ldx temp_x
stx LCD_X
sty LCD_Y
jsr printsign
pla
and #$0f
inx
stx temp_x
tax
lda hex2asc,x
ldx temp_x
stx LCD_X
sty LCD_Y
jmp printsign
.endproc
.proc printsign
sty temp_y
stx temp_x
sta temp_a
lda temp_a
sta addr
lda #0
sta addr+1
asl addr
rol addr+1
asl addr
rol addr+1
asl addr
rol addr+1
lda addr
clc
adc #<chars
sta addr
lda addr+1
adc #>chars
sta addr+1
ldx #8
ldy #0
printsign1:
lda (addr),y
sta LCD_DATA
iny
dex
bne printsign1
ldx temp_x
ldy temp_y
rts
.endproc

1157
targettest/gamate/nachtm.c Normal file

File diff suppressed because it is too large Load Diff

63
targettest/getopt-test.c Normal file
View File

@@ -0,0 +1,63 @@
/*
** This is part of a changed public domain getopt implementation that
** had the following text on top:
**
** I got this off net.sources from Henry Spencer.
** It is a public domain getopt(3) like in System V.
** I have made the following modifications:
**
** A test main program was added, ifdeffed by GETOPT.
** This main program is a public domain implementation
** of the getopt(1) program like in System V. The getopt
** program can be used to standardize shell option handling.
** e.g. cc -DGETOPT getopt.c -o getopt
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#define ARGCH ':'
#define BADCH '?'
#define ENDARGS "--"
#define NUMARGS 2
int main (int argc, char **argv)
{
char *optstring = argv[1];
char *argv0 = argv[0];
int opterr = 0;
int C;
char *opi;
if (argc != NUMARGS) {
fprintf (stderr, "Usage: %s optstring args\n", argv0);
exit (EXIT_FAILURE);
}
argv++;
argc--;
argv[0] = argv0;
while ((C = getopt (argc, argv, optstring)) != EOF) {
if (C == BADCH)
opterr++;
printf ("-%c ", C);
opi = strchr (optstring, C);
if (opi && opi[1] == ARGCH)
if (optarg)
printf ("\"%s\" ", optarg);
else
opterr++;
}
printf ("%s", ENDARGS);
while (optind < argc)
printf (" \"%s\"", argv[optind++]);
putchar ('\n');
return opterr;
}

12
targettest/getsp.s Normal file
View File

@@ -0,0 +1,12 @@
.export _getsp
.importzp sp
.proc _getsp
ldx sp+1
lda sp
rts
.endproc

239
targettest/heaptest.c Normal file
View File

@@ -0,0 +1,239 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <_heap.h>
static unsigned char* V[256];
static char* Alloc (void)
/* Allocate a random sized chunk of memory */
{
/* Determine the size */
unsigned char Size = (((unsigned char)rand()) & 0x7F) + 1;
/* Allocate memory */
unsigned char* P = malloc (Size);
/* Set the string to a defined value. We use the size, since this will
** also allow us to retrieve it later.
*/
if (P) {
memset (P, Size, Size);
} else {
printf ("Could not allocate %u bytes\n", Size);
exit (EXIT_FAILURE);
}
return P;
}
static void Free (unsigned char* P)
/* Check a memory block and free it */
{
unsigned char I;
/* Get the size of the block */
unsigned char Size = P[0];
/* Scan the block */
for (I = 1; I < Size; ++I) {
if (P[I] != Size) {
printf ("Scan failed - expected %02X, got %02X\n",
Size, P[I]);
exit (EXIT_FAILURE);
}
}
/* Free the block */
free (P);
}
static void FillArray (void)
/* Fill the array with randomly allocated memory chunks */
{
unsigned char I = 0;
do {
V[I] = Alloc ();
++I;
} while (I != 0);
}
static void ShowInfo (void)
/* Show heap info */
{
/* Count free blocks */
unsigned Count = 0;
register struct freeblock* P = _heapfirst;
while (P) {
++Count;
P = P->next;
}
printf ("%04X %04X %04X %04X %04X %u\n",
_heaporg, _heapptr, _heapend, _heapfirst, _heaplast, Count);
if (Count) {
P = _heapfirst;
while (P) {
printf ("%04X %04X %04X %04X(%u)\n",
(unsigned) P, P[2], P[1], P[0], P[0]);
P = P->next;
}
getchar ();
}
}
static void Test1 (void)
{
unsigned char I;
FillArray ();
for (I = 0; I < 0x80; ++I) {
Free (V[0x7F-I]);
Free (V[0x80+I]);
}
ShowInfo ();
}
static void Test2 (void)
{
unsigned char I;
FillArray ();
I = 0;
do {
Free (V[I]);
++I;
} while (I != 0);
ShowInfo ();
}
static void Test3 (void)
{
unsigned char I;
FillArray ();
I = 0;
do {
--I;
Free (V[I]);
} while (I != 0);
ShowInfo ();
}
static void Test4 (void)
{
unsigned char I;
FillArray ();
I = 0;
do {
Free (V[I]);
I += 2;
} while (I != 0);
I = 1;
do {
Free (V[I]);
I += 2;
} while (I != 1);
ShowInfo ();
}
static void Test5 (void)
{
unsigned char I;
FillArray ();
I = 0;
do {
Free (V[I]);
I += 2;
} while (I != 0);
do {
V[I] = Alloc ();
I += 2;
} while (I != 0);
I = 1;
do {
Free (V[I]);
I += 2;
} while (I != 1);
do {
V[I] = Alloc ();
I += 2;
} while (I != 1);
I = 0;
do {
Free (V[I]);
++I;
} while (I != 0);
ShowInfo ();
}
static void Test6 (void)
{
unsigned char I, J;
FillArray ();
I = J = 0;
do {
do {
Free (V[I]);
V[I] = Alloc ();
++I;
} while (I != 0);
++J;
} while (J < 5);
do {
Free (V[I]);
++I;
} while (I != 0);
ShowInfo ();
}
int main (void)
{
unsigned long T;
/* Show info at start */
ShowInfo ();
#if !defined(__APPLE2__)
/* Remember the time */
T = clock ();
#endif
/* Do the tests */
Test1 ();
Test2 ();
Test3 ();
Test4 ();
Test5 ();
Test6 ();
#if !defined(__APPLE2__)
/* Calculate the time and print it */
T = clock () - T;
printf ("Time needed: %lu ticks\n", T);
#endif
/* Done */
return EXIT_SUCCESS;
}

122
targettest/joy-test.c Normal file
View File

@@ -0,0 +1,122 @@
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <conio.h>
#include <joystick.h>
#ifdef JOYSTICK_DRIVER
/* A statically linked driver was named on the compiler's command line.
** Make sure that it is used instead of a dynamic one.
*/
# undef DYN_DRV
# define DYN_DRV 0
/*
** Link existing drivers this way:
**
** cl65 -DJOYSTICK_DRIVER=c64_hitjoy_joy -o joy-test.prg joy-test.c
**
** For testing a new driver, you need to uncomment the declaration below,
** and link your driver this way:
**
** co65 ../../target/c64/drv/joy/c64-hitjoy.joy -o hitjoy.s --code-label _hitjoy
** cl65 -DJOYSTICK_DRIVER=hitjoy -o joy-test.prg joy-test.c hitjoy.s
*/
/* extern char JOYSTICK_DRIVER; */
#else
/* Use a dynamically loaded driver, by default. */
# ifndef DYN_DRV
# define DYN_DRV 1
# endif
#endif
int main (void)
{
unsigned char j;
unsigned char i, count;
unsigned char Res;
clrscr ();
#if DYN_DRV
Res = joy_load_driver (joy_stddrv);
#elif defined(JOYSTICK_DRIVER)
Res = joy_install (&JOYSTICK_DRIVER);
#else
Res = joy_install (&joy_static_stddrv);
#endif
if (Res != JOY_ERR_OK) {
cprintf ("Error in joy_load_driver: %u\r\n", Res);
#if DYN_DRV
cprintf ("OS: %u, %s\r\n", _oserror, _stroserror (_oserror));
#endif
return EXIT_FAILURE;
}
count = joy_count ();
#if defined(__ATARI5200__) || defined(__CREATIVISION__)
cprintf ("JOYSTICKS: %u.", count);
#else
cprintf ("Driver supports %u joystick%s", count, count == 1 ? "." : "s.");
#endif
while (1) {
for (i = 0; i < count; ++i) {
j = joy_read (i);
#if defined(__NES__) || defined(__CX16__)
/* two lines for each device */
gotoxy (0, i * 2 +1);
cprintf ("%2u:%-6s%-6s%-6s%-6s\r\n"
" %-6s%-6s%-6s%-6s $%02X",
i,
JOY_UP(j) ? " up " : " ---- ",
JOY_DOWN(j) ? " down " : " ---- ",
JOY_LEFT(j) ? " left " : " ---- ",
JOY_RIGHT(j) ? " right" : " ---- ",
JOY_BTN_1(j) ? "btn A " : " ---- ",
JOY_BTN_2(j) ? "btn B " : " ---- ",
JOY_BTN_3(j) ? "select" : " ---- ",
JOY_BTN_4(j) ? " start" : " ---- ",
j);
#else
/* one line for each device */
gotoxy (0, i + 1);
# if defined(__ATARI5200__) || defined(__CREATIVISION__)
cprintf ("%1u:%-3s%-3s%-3s%-3s%-3s %02X",
i,
JOY_UP(j) ? " U " : " - ",
JOY_DOWN(j) ? " D " : " - ",
JOY_LEFT(j) ? " L " : " - ",
JOY_RIGHT(j) ? " R " : " - ",
JOY_BTN_1(j) ? " 1 " : " - ",
j);
# else
cprintf ("%2u: %-6s%-6s%-6s%-6s%-6s $%02X",
i,
JOY_UP(j) ? " up " : " ---- ",
JOY_DOWN(j) ? " down " : " ---- ",
JOY_LEFT(j) ? " left " : " ---- ",
JOY_RIGHT(j) ? "right " : " ---- ",
JOY_BTN_1(j) ? "button" : " ---- ",
j);
# endif
#endif
}
/* Show any pressed keys; so that we can verify that the keyboard is working. */
if (kbhit ()) {
#if defined(__NES__) || defined(__CX16__)
gotoxy (1, i * 2 + 2);
#else
gotoxy (1, i + 2);
#endif
cprintf ("keyboard: $%02X", cgetc ());
}
}
return EXIT_SUCCESS;
}

36
targettest/moddiv-test.c Normal file
View File

@@ -0,0 +1,36 @@
#include <stdlib.h>
#include <stdio.h>
int main (void)
{
int a, b;
int div, mod;
printf ("Please note that this program does an\n"
"exhaustive test for the division and\n"
"modulo operation and therefore runs for\n"
"almost ever. On my box, it's nearly two\n"
"days in warp mode of VICE.\n\n");
a = 0;
do {
b = 1;
do {
div = a / b;
mod = a % b;
if (div * b + mod != a) {
printf ("Found problems:\n"
" Result of %u / %u is %u\n"
" Result of %u %% %u is %u\n",
a, b, div, a, b, mod);
return EXIT_FAILURE;
}
++b;
} while (b != 0);
if ((a & 0xFF) == 0) {
printf ("%5u ", a);
}
++a;
} while (a != 0);
return EXIT_SUCCESS;
}

431
targettest/mouse-test.c Normal file
View File

@@ -0,0 +1,431 @@
/*
** Test program for mouse drivers.
** Supportsthe C64/C128/CBM510/Atari/Apple2.
**
** 2001-09-13, Ullrich von Bassewitz
** 2013-09-05, Greg King
**
** Compile with "-DSTATIC_MOUSE" to statically link all available drivers.
** Compile with "-DMOUSE_DRIVER=<driver_sym>" to statically link the given driver.
** E.g., -DMOUSE_DRIVER=atrst_mou to just link with the Atari ST mouse driver.
*/
#include <stdbool.h>
#include <stdlib.h>
#include <string.h>
#include <mouse.h>
#include <pen.h>
#include <conio.h>
#include <ctype.h>
#include <dbg.h>
#include <cc65.h>
#define max(a,b) (((a) > (b)) ? (a) : (b))
#define min(a,b) (((a) < (b)) ? (a) : (b))
extern int getsp(void);
#define NO_DEBUG
#define NO_JAIL
#ifdef __ATARI__
extern const struct mouse_callbacks mouse_pm_callbacks;
extern const struct mouse_callbacks mouse_txt_callbacks;
//#define MOUSE_CALLBACK mouse_def_callbacks
#define MOUSE_CALLBACK mouse_pm_callbacks
//#define MOUSE_CALLBACK mouse_txt_callbacks
#else
#define MOUSE_CALLBACK mouse_def_callbacks
#endif
#if defined(MOUSE_DRIVER) || defined(STATIC_MOUSE)
/* A statically linked driver was named on the compiler's command line.
** Make sure that it is used instead of a dynamic one.
*/
# undef DYN_DRV
# define DYN_DRV 0
#else
/* Use a dynamically loaded driver, by default. */
# ifndef DYN_DRV
# define DYN_DRV 1
# endif
#endif
#ifdef __CBM__
/* Set dark-on-light colors. */
const unsigned char mouse_def_pointercolor = COLOR_BLACK;
#endif
static void __fastcall__ CheckError (const char* S, unsigned char Error)
{
if (Error != MOUSE_ERR_OK) {
cprintf ("\n%s: %s(%u)\r\n", S, mouse_geterrormsg (Error), Error);
/* Wait for a key-press, so that some platforms can show the error
** message before they remove the current screen.
*/
if (doesclrscrafterexit ()) {
cgetc ();
}
exit (EXIT_FAILURE);
}
}
#if DYN_DRV
/* Points to the dynamic driver's name. */
static const char *mouse_name;
static void DoWarning (void)
/* Warn the user that a driver is needed for this program. */
{
cprintf ("Warning: This program needs\r\n"
"the driver with the name\r\n"
" %s\r\n"
"on a disk! Press 'y' if you have it;\r\n"
"or, any other key to exit.\r\n", mouse_stddrv);
if (tolower (cgetc ()) != 'y') {
exit (EXIT_SUCCESS);
}
cprintf ("OK. Please wait patiently...\r\n");
}
#else
unsigned char *mouse_drv_use;
#endif
#ifdef __ATARI__
#ifdef __ATARIXL__
#define MSENAME_EXT "X"
#define MSESTAT_0 atrxjoy_mou
#define MSESTAT_1 atrxst_mou
#define MSESTAT_2 atrxami_mou
#define MSESTAT_3 atrxtrk_mou
#define MSESTAT_4 atrxtt_mou
#else
#define MSENAME_EXT ""
#define MSESTAT_0 atrjoy_mou
#define MSESTAT_1 atrst_mou
#define MSESTAT_2 atrami_mou
#define MSESTAT_3 atrtrk_mou
#define MSESTAT_4 atrtt_mou
#endif
#define MSENAME_0 "ATR" MSENAME_EXT "JOY.MOU"
#define MSENAME_1 "ATR" MSENAME_EXT "ST.MOU"
#define MSENAME_2 "ATR" MSENAME_EXT "AMI.MOU"
#define MSENAME_3 "ATR" MSENAME_EXT "TRK.MOU"
#define MSENAME_4 "ATR" MSENAME_EXT "TT.MOU"
#elif defined(__C64__) || defined(__C128__)
#ifdef __C64__
#define MSENAME_EXT "c64-"
#define MSESTAT_0 c64_joy_mou
#define MSESTAT_1 c64_1351_mou
#define MSESTAT_2 c64_inkwell_mou
#define MSESTAT_3 c64_pot_mou
#else
#define MSENAME_EXT "c128-"
#define MSESTAT_0 c128_joy_mou
#define MSESTAT_1 c128_1351_mou
#define MSESTAT_2 c128_inkwell_mou
#define MSESTAT_3 c128_pot_mou
#endif
#define MSENAME_0 MSENAME_EXT "joy.mou"
#define MSENAME_1 MSENAME_EXT "1351.mou"
#define MSENAME_2 MSENAME_EXT "inkwell.mou"
#define MSENAME_3 MSENAME_EXT "pot.mou"
#endif
static void __fastcall__ ShowState (unsigned char Jailed, unsigned char Invisible)
/* Display jail and cursor states. */
{
cclearxy (0, 7, 32);
gotoxy (0, 7);
cprintf ("Pointer is %svisible%s.", Invisible? "in" : "", Jailed? " and jailed" : "");
}
#ifdef __ATARIXL__
extern char _HIDDEN_RAM_SIZE__, _HIDDEN_RAM_LAST__, _HIDDEN_RAM_START__;
#endif
#if DYN_DRV
int main (int argc, char *argv[])
#else
int main (void)
#endif
{
struct mouse_info info;
struct mouse_box full_box, small_box;
unsigned char width, height;
char C;
bool Invisible = true, Done = false, Jailed = false;
#ifdef __ATARIXL__
cprintf ("adding heap: $%04X bytes at $%04X\r\n",
&_HIDDEN_RAM_SIZE__ - (&_HIDDEN_RAM_LAST__ - &_HIDDEN_RAM_START__),
&_HIDDEN_RAM_LAST__);
_heapadd (&_HIDDEN_RAM_LAST__, (size_t)(&_HIDDEN_RAM_SIZE__ - (&_HIDDEN_RAM_LAST__ - &_HIDDEN_RAM_START__)));
cgetc ();
#endif
#ifndef NO_DEBUG
/* Initialize the debugger */
DbgInit (0);
#endif
/* Set dark-on-light colors. Clear the screen. */
#if defined(__CBM__) && !defined(__VIC20__)
(void) bordercolor (COLOR_GRAY2);
(void) bgcolor (COLOR_WHITE);
(void) textcolor (COLOR_GRAY1);
#else
(void) bordercolor (COLOR_BLUE);
(void) bgcolor (COLOR_WHITE);
(void) textcolor (COLOR_BLACK);
#endif
cursor (0);
clrscr ();
/* If a lightpen driver is installed, then it can get a calibration value
** from this file (if it exists). Or, the user can adjust the pen; and,
** the value will be put into this file, for the next time.
** (Other drivers will ignore this.)
*/
#if defined(__C64__) || defined(__C128__) || defined(__CBM510__)
pen_adjust ("pen.dat");
#endif
#if DYN_DRV
/* If a dynamically loadable driver is named on the command line,
** then use that driver instead of the standard one.
*/
if (argc > 1) {
mouse_name = argv[1];
} else {
#if defined(__ATARI__) || defined(__C64__) || defined(__C128__)
char selection, flag = 0;
cprintf ("Select mouse driver:\r\n"
" 0 - Joystick\r\n"
#ifdef __ATARI__
" 1 - ST Mouse\r\n"
" 2 - Amiga Mouse\r\n"
" 3 - Atari Trakball\r\n"
" 4 - Atari TouchPad\r\n"
#else
" 1 - 1351 Mouse\r\n"
" 2 - Inkwell Mouse\r\n"
" 3 - Paddle\r\n"
#endif
"Enter selection: ");
while (1) {
switch (selection = cgetc ()) {
case '0': mouse_name = MSENAME_0; flag = 1; break;
case '1': mouse_name = MSENAME_1; flag = 1; break;
case '2': mouse_name = MSENAME_2; flag = 1; break;
case '3': mouse_name = MSENAME_3; flag = 1; break;
#ifdef __ATARI__
case '4': mouse_name = MSENAME_4; flag = 1; break;
#endif
}
if (flag) break;
}
cprintf ("%c\r\nOK, loading \"%s\",\r\nplease wait patiently...\r\n", selection, mouse_name);
#else
/* Output a warning about the standard driver that is needed. */
DoWarning ();
mouse_name = mouse_stddrv;
#endif
}
/* Load and install the driver. */
CheckError ("mouse_load_driver",
mouse_load_driver (&MOUSE_CALLBACK, mouse_name));
#else /* not DYN_DRV */
#if !defined(MOUSE_DRIVER) && (defined(__ATARI__) || defined(__C64__) || defined(__C128__))
{
char selection, flag = 0;
cprintf ("Select mouse driver:\r\n"
" 0 - Joystick\r\n"
#ifdef __ATARI__
" 1 - ST Mouse\r\n"
" 2 - Amiga Mouse\r\n"
" 3 - Atari Trakball\r\n"
" 4 - Atari TouchPad\r\n"
#else
" 1 - 1351 Mouse\r\n"
" 2 - Inkwell Mouse\r\n"
" 3 - Paddle\r\n"
#endif
"Enter selection: ");
while (1) {
switch (selection = cgetc ()) {
case '0': mouse_drv_use = MSESTAT_0; flag = 1; break;
case '1': mouse_drv_use = MSESTAT_1; flag = 1; break;
case '2': mouse_drv_use = MSESTAT_2; flag = 1; break;
case '3': mouse_drv_use = MSESTAT_3; flag = 1; break;
#ifdef __ATARI__
case '4': mouse_drv_use = MSESTAT_4; flag = 1; break;
#endif
}
if (flag) break;
}
}
#else
mouse_drv_use = mouse_static_stddrv;
#endif
/* Install the driver. */
CheckError ("mouse_install",
mouse_install (&MOUSE_CALLBACK,
# ifdef MOUSE_DRIVER
MOUSE_DRIVER
# else
#if defined(__ATARI__) || defined(__C64__) || defined(__C128__)
mouse_drv_use
#else
mouse_static_stddrv
#endif
# endif
));
#endif
#ifndef NO_JAIL
/* Get the initial bounding box. */
mouse_getbox (&full_box);
#endif
screensize (&width, &height);
top:
clrscr ();
/* Print a help line */
cputs (" d)ebug h)ide q)uit s)how j)ail");
gotoxy (1, 20);
cprintf ("SP: $%04X", getsp());
/* Put a cross at the center of the screen. */
gotoxy (width / 2 - 3, height / 2 - 1);
#if defined(__CBM__)
cprintf ("%3u,%3u\r\n%*s\xDB", width / 2 * 8 + 4, height / 2 * 8 + 4,
width / 2, "");
#else
cprintf ("%3u,%3u\r\n%*s+", width / 2 * 8 + 4, height / 2 * 8 + 4,
width / 2, "");
#endif
/* Test loop */
ShowState (Jailed, Invisible);
do {
/* Get the current co-ordinates and button states; and, print them. */
mouse_info (&info);
gotoxy (0, 2);
cprintf (" X = %3d\r\n", info.pos.x);
cprintf (" Y = %3d\r\n", info.pos.y);
cprintf (" B1 = %c\r\n", (info.buttons & MOUSE_BTN_LEFT) ?
#ifdef __CBM__
0x5F
#else
'v'
#endif
: '^');
cprintf (" B2 = %c", (info.buttons & MOUSE_BTN_RIGHT) ?
#ifdef __CBM__
0x5F
#else
'v'
#endif
: '^');
/* Handle user input */
if (kbhit ()) {
cclearxy (1, 9, 23);
switch (tolower (C = cgetc ())) {
#ifndef NO_DEBUG
case 'd':
BREAK();
/* The debugger might have changed the colors.
** Restore them.
*/
#ifdef __CBM__
(void) bordercolor (COLOR_GRAY2);
(void) bgcolor (COLOR_WHITE);
(void) textcolor (COLOR_GRAY1);
#else
(void) bordercolor (COLOR_BLUE);
(void) bgcolor (COLOR_WHITE);
(void) textcolor (COLOR_BLACK);
#endif
/* The debugger changed the screen; restore it. */
goto top;
#endif
case 'h':
mouse_hide ();
ShowState (Jailed, ++Invisible);
break;
#ifndef NO_JAIL
case 'j':
if (Jailed) {
mouse_setbox (&full_box);
Jailed = false;
} else {
small_box.minx = max (info.pos.x - 10, full_box.minx);
small_box.miny = max (info.pos.y - 10, full_box.miny);
small_box.maxx = min (info.pos.x + 10, full_box.maxx);
small_box.maxy = min (info.pos.y + 10, full_box.maxy);
mouse_setbox (&small_box);
Jailed = true;
}
ShowState (Jailed, Invisible);
break;
#endif
case 's':
mouse_show ();
if (Invisible) {
ShowState (Jailed, --Invisible);
}
break;
case 'q':
Done = true;
break;
default:
gotoxy (1, 9);
cprintf ("Spurious character: $%02X", C);
}
}
} while (!Done);
#if DYN_DRV
/* Uninstall and unload the driver. */
CheckError ("mouse_unload", mouse_unload ());
#else
/* Uninstall the static driver. */
CheckError ("mouse_uninstall", mouse_uninstall ());
#endif
/* Say goodbye */
cputsxy (0, height / 2 + 3, "Goodbye!");
return EXIT_SUCCESS;
}

170
targettest/mul-test.c Normal file
View File

@@ -0,0 +1,170 @@
/* mul-test.c -- Test the multiplication operator. */
#include <time.h>
#include <conio.h>
#include <ctype.h>
/* Number of elements in the progress bar. Use a power of 2, to avoid the
** multiplication (which is about to be tested).
*/
#define BAR_ELEMENTS 32U
#if defined(__CBM__)
static const unsigned char revers_bar[8] = {
0, 0, 0, 0, 0, 1, 1, 1
};
static const unsigned char small_bar[8] = {
' ', 0xa5, 0xb4, 0xb5, 0xa1, 0xb6, 0xaa, 0xa7
};
#elif defined(__ATARI__)
#endif
/* Screen co-ordinates for the progress meter */
static unsigned char Width, Height;
static unsigned char X, Y;
static void ProgressMeter (unsigned Val)
/* Print the progress bar. */
{
gotoxy (X, Y);
cprintf (" %5lu/65536\r\n", (unsigned long) Val);
revers (1);
cclear (Val / (unsigned)(65536U / BAR_ELEMENTS));
/* Commodore and Atari computers can show eight times greater precision. */
#if defined(__CBM__)
Val = (Val / (unsigned)(65536U / BAR_ELEMENTS / 8)) % 8;
revers (revers_bar[Val]);
cputc (small_bar[Val]);
#elif defined(__ATARI__)
#endif
revers (0);
}
int main(void)
{
char C;
/* Clock variables */
clock_t Ticks;
clock_t Wait;
unsigned Days;
unsigned Hours;
unsigned Minu;
unsigned Sec;
unsigned Milli;
/* Actual test variables */
register unsigned lhs = 0;
register unsigned rhs = 0;
register unsigned res;
/* Clear the screen, and output an informational message. */
clrscr ();
screensize (&Width, &Height);
cprintf ("This program does an exhaustive test of\r\n"
"the multiplication routine. It runs for\r\n"
"several days; so, please wait very\r\n"
"patiently (or, speed up your emulator).\r\n"
"\n"
"Progress: ");
/* Remember the current position for the progress bar */
X = wherex ();
Y = wherey ();
/* Mark the maximum limit of the bar. */
revers (1);
cputcxy (BAR_ELEMENTS, Y, ' ');
cputcxy (BAR_ELEMENTS, Y + 1, ' ');
revers (0);
/* [Targets that have clock() will define CLOCKS_PER_SEC.] */
#ifdef CLOCKS_PER_SEC
/* Start timing the test. */
Ticks = clock();
#endif
do {
/* Update the progress bar */
ProgressMeter (lhs);
/* Enable this to test the progress-meter code.
** (And, run emulators at their maximun speed.)
*/
#if 0
continue;
#endif
/* Do one row of tests */
res = 0;
do {
if (lhs * rhs != res) {
#ifdef CLOCKS_PER_SEC
Wait = clock ();
#endif
gotoxy (0, Y+3);
cprintf ("Error on %u * %u: %u != %u\r\n", lhs, rhs, lhs * rhs, res);
cprintf ("Press a key -- 'Q' to quit. ");
cursor (1);
C = toupper (cgetc ());
cclearxy (0, Y+3, Width);
cclearxy (0, Y+4, Width);
#ifdef CLOCKS_PER_SEC
/* Don't time the user's interaction. */
Ticks += clock () - Wait;
#endif
if (C == 'Q') {
goto Done;
}
}
if (kbhit () && toupper (cgetc ()) == 'Q') {
goto Done;
}
res += lhs;
} while (++rhs != 0);
} while (++lhs != 0);
Done:
#ifdef CLOCKS_PER_SEC
/* Calculate the time used */
Ticks = clock() - Ticks;
Milli = ((Ticks % CLOCKS_PER_SEC) * 1000) / CLOCKS_PER_SEC;
Sec = (unsigned) (Ticks / CLOCKS_PER_SEC);
Minu = Sec / 60;
Hours = Minu / 60;
Days = Hours / 24;
Hours %= 24;
Minu %= 60;
Sec %= 60;
/* Print the time used */
gotoxy (0, Y+3);
cprintf ("Time used:\r\n"
" %u days,\r\n"
" %u hours,\r\n"
" %u minutes,\r\n"
" %u.%03u seconds.\n", Days, Hours, Minu, Sec, Milli);
#endif
cprintf ("\rTap a key, to exit. ");
cgetc();
return 0;
}

58
targettest/pce/Makefile Normal file
View File

@@ -0,0 +1,58 @@
# Just the usual way to find out if we're
# using cmd.exe to execute make rules.
ifneq ($(shell echo),)
CMD_EXE = 1
endif
ifdef CMD_EXE
NULLDEV = nul:
DEL = -del /f
RMDIR = rmdir /s /q
else
NULLDEV = /dev/null
DEL = $(RM)
RMDIR = $(RM) -r
endif
ifdef CC65_HOME
AS = $(CC65_HOME)/bin/ca65
CC = $(CC65_HOME)/bin/cc65
CL = $(CC65_HOME)/bin/cl65
LD = $(CC65_HOME)/bin/ld65
else
AS := $(if $(wildcard ../../../bin/ca65*),../../../bin/ca65,ca65)
CC := $(if $(wildcard ../../../bin/cc65*),../../../bin/cc65,cc65)
CL := $(if $(wildcard ../../../bin/cl65*),../../../bin/cl65,cl65)
LD := $(if $(wildcard ../../../bin/ld65*),../../../bin/ld65,ld65)
endif
.PHONY: all clean test
# Size of cartridge to generate.
# Possible values:
# 8K = 0x2000
# 16K = 0x4000
# 32K = 0x8000
CARTSIZE := 0x2000
ifeq (${CARTSIZE},0x8000)
COUNT := 3
else
COUNT := 1
endif
all: conio.pce
%.pce: %.bin
dd if=$< bs=8K skip=${COUNT} > $@
dd if=$< bs=8K count=${COUNT} >> $@
%.bin: %.c ../../../lib/pce.lib
../../../bin/cl65 -t pce $< -Wl -D__CARTSIZE__=${CARTSIZE} -m $*.map -o $@
clean:
$(RM) conio.o conio.???
test: conio.pce
mednafen -force_module pce $<

161
targettest/pce/conio.c Normal file
View File

@@ -0,0 +1,161 @@
#include <pce.h>
#include <conio.h>
#include <time.h>
#include <joystick.h>
#include <string.h>
#include <stdlib.h>
static int datavar = 10;
static char hex[16] = { "0123456789abcdef" };
static char charbuf[0x20];
static char colbuf[0x20];
void main(void)
{
int stackvar = 42;
int i, j;
clock_t clk;
char* p;
unsigned char xsize, ysize, n, nn;
joy_install(&joy_static_stddrv);
clrscr();
screensize(&xsize, &ysize);
cputs("hello world");
gotoxy(0,0);
cpeeks(charbuf, 11);
gotoxy(12,0);
cputs(charbuf);
cputsxy(0, 2, "colors:" );
for (i = 0; i < 16; ++i) {
textcolor(i);
cputc(hex[i]);
}
for (i = 0; i < 16; ++i) {
gotoxy(7 + i, 2);
charbuf[i] = cpeekc();
colbuf[i] = cpeekcolor();
}
gotoxy(25, 2);
for (i = 0; i < 16; ++i) {
textcolor(colbuf[i]);
cputc(charbuf[i]);
}
textcolor(1);
gotoxy(0,4);
cprintf("datavar: %02x\n\r", datavar);
cprintf("stackvar: %02x\n\r", stackvar);
j = joy_count();
gotoxy(0,9);
cprintf("Found %d Joysticks.", j);
for (i = 0; i < 4; ++i) {
gotoxy(0, 16 + i);
p = malloc(16);
memcpy(p, "0123456789abcdef", 16);
cprintf("alloc'ed at: %04p - %c%c%c%c%c%c%c%c%c%c%c%c%c%c%c%c", p,
p[0],p[1],p[2],p[3],p[4],p[5],p[6],p[7],
p[8],p[9],p[10],p[11],p[12],p[13],p[14],p[15]
);
}
memcpy(p, main, i = 0); /* test that a zero length doesn't copy 64K */
gotoxy(0,ysize - 1);
for (i = 0; i < xsize; ++i) {
cputc('0' + i % 10);
}
gotoxy(0,ysize - 2 - ((256 + xsize) / xsize));
for (i = 0; i < xsize; ++i) {
cputc('0' + i % 10);
}
for (i = 0; i < (xsize * 5); ++i) {
cputc('#');
}
gotoxy(0,ysize - 1 - ((256 + xsize) / xsize));
for (i = 0; i < 256; ++i) {
if ((i != '\n') && (i != '\r')) {
cputc(i);
}
}
i = get_tv();
gotoxy(30,0);
cputs("TV Mode: ");
switch(i) {
case TV_NTSC:
cputs("NTSC");
break;
case TV_PAL:
cputs("PAL");
break;
case TV_OTHER:
cputs("OTHER");
break;
}
cprintf(" %dx%d", xsize, ysize);
for(;;) {
gotoxy(13,4);
cprintf("%02x", datavar);
gotoxy(13,5);
cprintf("%02x", stackvar);
++datavar; ++stackvar;
gotoxy(0,7);
clk = clock();
cprintf("clock: %08lx", clk);
for (i = 0; i < 4; ++i) {
gotoxy(0, 11 + i);
j = joy_read (i);
cprintf ("pad %d: %02x %-6s%-6s%-6s%-6s%-6s%-6s%-6s%-6s",
i, j,
JOY_UP(j)? " up " : " ---- ",
JOY_DOWN(j)? " down " : " ---- ",
JOY_LEFT(j)? " left " : " ---- ",
JOY_RIGHT(j)? "right " : " ---- ",
JOY_BTN_I(j)? "btn I " : " ---- ",
JOY_BTN_II(j)? "btn II" : " ---- ",
JOY_SELECT(j)? "select" : " ---- ",
JOY_RUN(j)? " run " : " ---- ");
}
gotoxy(xsize - 10, 3);
nn = (n >> 5) & 1;
revers(nn);
cputc(nn ? 'R' : ' ');
cputs(" revers");
revers(0);
for (i = 0; i < 9; ++i) {
gotoxy(xsize - 10 + i, 3);
charbuf[i] = cpeekc();
colbuf[i] = cpeekrevers();
}
gotoxy(xsize - 10, 4);
for (i = 0; i < 9; ++i) {
revers(colbuf[i]);
cputc(charbuf[i]);
}
if ((n & 0x1f) == 0x00) {
nn = p[15];
((char*)memmove(p + 1, p, 15))[-1] = nn;
gotoxy(22, 19);
cprintf("%c%c%c%c%c%c%c%c%c%c%c%c%c%c%c%c",
p[0],p[1],p[ 2],p[ 3],p[ 4],p[ 5],p[ 6],p[ 7],
p[8],p[9],p[10],p[11],p[12],p[13],p[14],p[15]);
}
waitvsync();
++n;
}
}

86
targettest/posixio-test.c Normal file
View File

@@ -0,0 +1,86 @@
#include <stdio.h>
#include <errno.h>
#include <fcntl.h>
#include <unistd.h>
int Open (const char* Name, int Flags)
{
int fd;
printf ("Opening %s: ", Name);
fd = open (Name, Flags);
printf ("%d\n", fd);
return fd;
}
void Write (int fd, const void* Buf, unsigned Size)
{
int Res;
Res = write (fd, Buf, Size);
printf ("Writing %u bytes to %d: %d\n", Size, fd, Res);
}
int Read (int fd, void* Buf, unsigned Size)
{
int Res;
Res = read (fd, Buf, Size);
printf ("Reading %u bytes from %d: %d\n", Size, fd, Res);
return Res > 0? Res : 0;
}
void Close (int fd)
{
printf ("Closing %d: %d\n", fd, close (fd));
}
int main (void)
{
int fd1, fd2;
int Res;
static const char text1[] = "This goes into file #1\n";
static const char text2[] = "This goes into file #2\n";
static const char text3[] = "This goes into file #3\n";
static const char text4[] = "This goes into file #4\n";
static char Buf[200];
fd1 = Open ("foobar1", O_WRONLY|O_CREAT|O_TRUNC);
fd2 = Open ("foobar2", O_WRONLY|O_CREAT|O_TRUNC);
Write (fd1, text1, sizeof (text1) - 1);
Write (fd2, text2, sizeof (text2) - 1);
Write (fd1, text1, sizeof (text1) - 1);
Write (fd2, text2, sizeof (text2) - 1);
Close (fd1);
Close (fd2);
fd1 = Open ("foobar3", O_WRONLY|O_CREAT|O_TRUNC);
fd2 = Open ("foobar4", O_WRONLY|O_CREAT|O_TRUNC);
Write (fd1, text3, sizeof (text3) - 1);
Write (fd2, text4, sizeof (text4) - 1);
Write (fd1, text3, sizeof (text3) - 1);
Write (fd2, text4, sizeof (text4) - 1);
Close (fd1);
Close (fd2);
fd1 = Open ("foobar1", O_RDONLY);
Res = Read (fd1, Buf, sizeof (Buf));
printf ("%.*s", Res, Buf);
Res = Read (fd1, Buf, sizeof (Buf));
Close (fd1);
return 0;
}

115
targettest/rename-test.c Normal file
View File

@@ -0,0 +1,115 @@
/* rename-test.c
**
**
** A simple test of the rename function.
**
** 2008-10-06, Greg King
*/
#include <errno.h>
#include <stdio.h>
#include <stdlib.h>
static FILE* file;
static int r;
static char name1[16], name2[16];
int main(void)
{
/* Generate two temporary file-names that have a random, unused spelling. */
_randomize();
for (;;) {
r = rand();
sprintf(name1, "r%04.4u.1", (unsigned)r);
sprintf(name2, "r%04.4u.2", (unsigned)r);
/* Ensure that neither file-name exists. */
errno = 0;
file = fopen(name1, "r");
if (file != NULL) {
fclose(file);
continue; /* try a different spelling */
}
/* Make sure that fopen() failed for the right reason. */
if (errno != ENOENT) {
perror("Disk error with first name");
return EXIT_FAILURE;
}
errno = 0;
file = fopen(name2, "r");
if (file != NULL) {
fclose(file);
continue;
}
if (errno != ENOENT) {
perror("Disk error with second name");
return EXIT_FAILURE;
}
break; /* neither one exists; do next step */
}
/* Create the first file.
** Close it without writing anything because only its name is important.
*/
printf("Creating file: %s\n", name1);
file = fopen(name1, "w");
if (file == NULL) {
_poserror("Disk error making first file");
return EXIT_FAILURE;
}
fclose(file);
/* Verify that the file-name exists now. */
file = fopen(name1, "r");
if (file == NULL) {
_poserror("Cannot find first name");
return EXIT_FAILURE;
}
fclose(file);
/* Whew! Finally, we get to the reason why this program exists:
** Confirm that the first file-name can be changed into the second
** file-name.
*/
printf("Renaming %s to %s\n", name1, name2);
r = rename(name1, name2);
if (r < 0) {
_poserror("rename() failed");
return EXIT_FAILURE;
}
/* Verify that the first file-name no longer exists. */
file = fopen(name1, "r");
if (file != NULL) {
fclose(file);
_poserror("First name still exists");
return EXIT_FAILURE;
}
/* Verify that the second file-name exists now. */
file = fopen(name2, "r");
if (file == NULL) {
_poserror("Cannot find second name");
return EXIT_FAILURE;
}
fclose(file);
printf("Success!\n");
/* Delete the second (temporary) name. */
printf("Removing %s\n", name2);
r = remove(name2);
if (r < 0) {
_poserror("remove() failed");
return EXIT_FAILURE;
}
printf("rename() passed the test.\n");
return EXIT_SUCCESS;
}

282
targettest/scanf-test.c Normal file
View File

@@ -0,0 +1,282 @@
/*
** scanf-test.c
**
** Tests that the scanf family of functions scans and converts its input data
** correctly.
**
** Note: When this program uses conio, it doesn't guard against printing off
** the bottom of the screen. So, you might have a problem on platforms with
** "short" screens.
**
** 2005-01-26, Greg King
*/
/* Define USE_STDIO, when you want to use the stdio functions.
** Do not define it, when you want to use the conio functions.
*/
#define USE_STDIO
#include <stdio.h>
#include <string.h>
#ifdef USE_STDIO
# define SCANF scanf
# define PRINTF printf
#else
# include <conio.h>
/* Unlike other conio input functions, cscanf() echoes what you type. */
# define SCANF cscanf
# define PRINTF cprintf
#endif
#define ARRAYSIZE(a) (sizeof (a) / sizeof (a)[0])
typedef enum {
INT,
CHAR
} TYPE;
typedef union {
int nvalue;
const char *svalue;
} VALUE;
static const struct {
const char *input, *format;
int rvalue;
TYPE type1;
VALUE v1;
TYPE type2;
VALUE v2;
} test_data[] = {
/* Input sequences for character specifiers must be less than 80 characters
** long. These format strings are allowwed a maximum of two assignment
** specifications.
*/
/* Test that literals match, and that they aren't seen as conversions.
** Test that integer specifiers can handle end-of-file.
*/
{"qwerty Dvorak", "qwerty Dvorak", 0 , INT, {0}, INT, {0}},
{"qwerty" , "qwerty %d%i" , EOF, INT, {0}, INT, {0}},
{"qwerty " , "qwerty %d%i" , EOF, INT, {0}, INT, {0}},
/* Test that integer specifiers scan properly. */
{"qwerty a" , "qwerty %d%i", 0, INT, {0} , INT, {0}},
{"qwerty -" , "qwerty %d%i", 0, INT, {0} , INT, {0}},
{"qwerty -9" , "qwerty %d%i", 1, INT, {-9} , INT, {0}},
{"qwerty -95" , "qwerty %d%i", 1, INT, {-95} , INT, {0}},
{"qwerty -95a" , "qwerty %d%i", 1, INT, {-95} , INT, {0}},
{"qwerty -95a 1", "qwerty %d%i", 1, INT, {-95} , INT, {0}},
{"qwerty -a" , "qwerty %d%i", 0, INT, {0} , INT, {0}},
{"qwerty -95 1" , "qwerty %d%i", 2, INT, {-95} , INT, {1}},
{"qwerty 95 2", "qwerty %i" , 1, INT, {95} , INT, {0}},
{"qwerty -95 +2", "qwerty %x%o", 2, INT, {-0x95}, INT, {02}},
{"qwerty 0X9E 02", "qwerty %i%i", 2, INT, {0x9e} , INT, {2}},
{"qwerty 095 2", "qwerty %i%i", 2, INT, {0} , INT, {95}},
{"qwerty 0e5 2", "qwerty %i%i", 1, INT, {0} , INT, {0}},
/* [String pointers are cast as (int),
** in order to avoid cc65 warnings.]
*/
/* Test that character specifiers can handle end-of-file. */
{"qwerty" , "qwerty %s%s" , EOF, CHAR, {(int)""}, CHAR, {(int)""}},
{"qwerty ", "qwerty %s%s" , EOF, CHAR, {(int)""}, CHAR, {(int)""}},
{"qwerty" , "qwerty %c%c" , EOF, CHAR, {(int)""}, CHAR, {(int)""}},
{"qwerty ", "qwerty %c%c" , EOF, CHAR, {(int)""}, CHAR, {(int)""}},
{"qwerty" , "qwerty %[ a-z]%c", EOF, CHAR, {(int)""}, CHAR, {(int)""}},
{"qwerty ", "qwerty %[ a-z]%c", EOF, CHAR, {(int)""}, CHAR, {(int)""}},
{"qwerty ", "qwerty%s%s" , EOF, CHAR, {(int)""}, CHAR, {(int)""}},
/* Test that character specifiers scan properly. */
{"123456qwertyasdfghzxcvbn!@#$%^QWERTYASDFGHZXCV"
"BN7890-=uiop[]\\jkl;'m,./&*()_+UIOP{}|JKL:\"M<>?",
"%79s%79s", 2,
CHAR, {(int)"123456qwertyasdfghzxcvbn!@#$%^QWERTYASDFGHZXCV"
"BN7890-=uiop[]\\jkl;'m,./&*()_+UIO"}, CHAR, {(int)"P{}|JKL:\"M<>?"}},
{"qwerty ", "qwerty%c%c" , 2, CHAR, {(int)" "} , CHAR, {(int)" "}},
{"qwerty ", "qwerty%2c%c" , 2, CHAR, {(int)" "} , CHAR, {(int)" "}},
{"qwerty ", "qwerty%2c%2c" , 1, CHAR, {(int)" "} , CHAR, {(int)" "}},
{"qwerty ", "qwerty%[ a-z]%c", 1, CHAR, {(int)" "}, CHAR, {(int)""}},
{"qwerty q", "qwerty%[ a-z]%c", 1, CHAR, {(int)" q"}, CHAR, {(int)""}},
{"qwerty Q", "qwerty%[ a-z]%c", 2, CHAR, {(int)" "}, CHAR, {(int)"Q"}},
{"qwerty-QWERTY-", "%[q-ze-]%[-A-Z]" , 2, CHAR, {(int)"qwerty-"},
CHAR, {(int)"QWERTY-"}},
/* Test the space-separation of strings. */
{"qwerty qwerty" , "qwerty%s%s", 1, CHAR, {(int)"qwerty"},
CHAR, {(int)""}},
{"qwerty qwerty Dvorak", "qwerty%s%s", 2, CHAR, {(int)"qwerty"},
CHAR, {(int)"Dvorak"}},
/* Test the mixxing of types. */
{"qwerty abc3", "qwerty%s%X" , 1, CHAR, {(int)"abc3"} , INT , {0}},
{"qwerty abc3", "qwerty%[ a-z]%X" , 2, CHAR, {(int)" abc"} , INT , {3}},
{"qwerty abc3", "qwerty%[ a-z3]%X", 1, CHAR, {(int)" abc3"}, INT , {0}},
{"qwerty abc3", "qwerty%[ A-Z]%X" , 2, CHAR, {(int)" "} , INT ,
{0xabc3}},
{"qwerty 3abc", "qwerty%i%[ a-z]" , 2, INT , {3} , CHAR,
{(int)"abc"}},
{"qwerty 3abc", "qwerty%i%[ A-Z]" , 1, INT , {3} , CHAR,
{(int)""}},
/* Test the character-count specifier. */
{" 95 5", "%n%i" , 1, INT , {0} , INT, {95}},
{" a5 5", "%n%i" , 0, INT , {0} , INT, {0}},
{" a5 5", "%x%n" , 1, INT , {0xa5} , INT, {4}},
{" a5 5", " %4c%n", 1, CHAR, {(int)"a5 5"}, INT, {6}},
{" 05a9" , "%i%n" , 1, INT , {5} , INT, {3}},
/* Test assignment-suppression. */
{" 95 6", "%n%*i" , 0, INT , {0} , INT, {0}},
{" a5 6", "%*x%n" , 0, INT , {4} , INT, {0}},
{" a5 6", "%*x%n%o", 1, INT , {4} , INT, {6}},
{" a5 6", " %*4c%d", 0, CHAR, {(int)""}, INT, {0}},
{"The first number is 7. The second number is 8.\n",
"%*[ .A-Za-z]%d%*[ .A-Za-z]%d", 2, INT, {7}, INT, {8}},
};
/* Test the char, short, and long specification-modifiers. */
static const struct {
const char *input, *format;
long value;
} type_data[] = {
{"+123456789", "%hhd", (signed char)123456789L},
{" 123456789", "%hd" , (unsigned short)123456789L},
{" 123456789", "%ld" , 123456789L},
{"-123456789", "%lld", -123456789L},
};
static void Pause(void) {
#ifdef USE_STDIO
printf("\n");
#else
cprintf("\r\nTap a key to see the next test. ");
cgetc();
clrscr();
#endif
}
int main(void) {
long n0;
unsigned t;
int c, n1 = 12345, n2, n3;
char s1[80], s2[80];
void *p1 = main, *p2 = main, *p3 = main, *p4 = main;
#ifndef USE_STDIO
clrscr();
cursor(1);
#endif
/* Test that scanf() can recognize percent-signs in the input.
** Test that integer converters skip white-space.
** Test that "%i" can scan a single zero digit (followed by EOF).
*/
sscanf("% \r\n\f\v\t 0", "%%%i", &n1);
if (n1 != 0)
PRINTF("sscanf()'s \"%%%%%%i\" couldn't scan either a \"%%\" "
"or a single zero digit.\r\n\n");
/* Test scanf()'s return-value: EOF if input ends before the first
** conversion-attempt begins; an assignment-count, otherwise.
** Test that scanf() properly converts and assigns the correct number
** of arguments.
*/
PRINTF("Testing scanf()'s return-value,\r\nconversions, and assignments...\r\n");
for (t = 0; t < ARRAYSIZE(test_data); ++t) {
/* Prefill the arguments with zeroes. */
n1 = n2 = 0;
memset(s1, '\0', sizeof s1);
memset(s2, '\0', sizeof s2);
c=sscanf(test_data[t].input, test_data[t].format,
/* Avoid warning messages about different
** pointer-types, by casting them to void-pointers.
*/
test_data[t].type1 == INT ? (void *)&n1 : (void *)s1,
test_data[t].type2 == INT ? (void *)&n2 : (void *)s2);
if (c != test_data[t].rvalue)
PRINTF("Test #%u returned %d instead of %d.\r\n",
t + 1, c, test_data[t].rvalue);
if (test_data[t].type1 == INT) {
if (test_data[t].v1.nvalue != n1)
PRINTF("Test #%u assigned %i, instead of %i,\r\n"
"\tto the first argument.\r\n\n",
t + 1, n1, test_data[t].v1.nvalue);
}
else { /* test_data[t].type1 == CHAR */
if (strcmp(test_data[t].v1.svalue, s1))
PRINTF("Test #%u assigned\r\n\"%s\",\r\n"
"\tinstead of\r\n\"%s\",\r\n"
"\tto the first argument.\r\n\n",
t + 1, s1, test_data[t].v1.svalue);
}
if (test_data[t].type2 == INT) {
if (test_data[t].v2.nvalue != n2)
PRINTF("Test #%u assigned %i, instead of %i,\r\n"
"\tto the second argument.\r\n\n",
t + 1, n2, test_data[t].v2.nvalue);
}
else { /* test_data[t].type2 == CHAR */
if (strcmp(test_data[t].v2.svalue, s2))
PRINTF("Test #%u assigned\r\n\"%s\",\r\n"
"\tinstead of\r\n\"%s\",\r\n"
"\tto the second argument.\r\n\n",
t + 1, s2, test_data[t].v2.svalue);
}
}
Pause();
/* Test the char, short, and long specification-modifiers. */
PRINTF("Testing scanf()'s type-modifiers...\r\n");
for (t = 0; t < ARRAYSIZE(type_data); ++t) {
n0 = 0L;
sscanf(type_data[t].input, type_data[t].format, &n0);
if (type_data[t].value != n0)
PRINTF("Test #%u assigned %li instead of %li.\r\n",
t + 1, n0, type_data[t].value);
}
Pause();
/* Test that the pointer specification
** can convert what printf() generates.
*/
PRINTF("Testing \"%%p\"...\r\n");
sprintf(s1, "%p %p %p %p", NULL, NULL,
Pause, /* static (program) storage */
&c); /* automatic (stack) storage */
sscanf(s1, "%p%p%p %p", &p1, &p2, &p3, &p4);
if (p1 != NULL || p2 != NULL ||
p3 != (void *)Pause || p4 != (void *)&c)
PRINTF("p1 is %p, p2 is %p; they should be %p.\r\n"
"scanf() assigned %p to p3, instead of %p.\r\n"
"scanf() assigned %p to p4, instead of %p.\r\n",
p1, p2, NULL,
p3, Pause,
p4, &c);
/* Test that scanf() can scan typed input.
** Retest that "%i" can decode radix prefixxes.
*/
do {
Pause();
PRINTF("Type 3 signed numbers,\r\n"
"separated by white-space:\r\n"
"octal decimal hexadecimal\r\n"
"? ");
c = SCANF("%i %i %i", &n1, &n2, &n3);
PRINTF("\r\n\nscanf() returned %i.\r\n"
"The numbers are:\r\n"
" %+o octal,\r\n"
" %+d decimal,\r\n"
" %+#X hexadecimal.\r\n",
c, n1, n2, n3);
} while (c > 0);
return 0;
}

209
targettest/seek.c Normal file
View File

@@ -0,0 +1,209 @@
/*
** seek test program
*/
#include <stdio.h>
#include <string.h>
#include <errno.h>
#include <unistd.h>
int main(int argc, char **argv)
{
char *filename,*x;
char buf[20];
FILE *file;
long pos;
off_t fsz;
int fd;
if (argc <= 1) {
printf("\nfilename: ");
x = fgets(buf,19,stdin);
printf("\n");
if (!x) {
return(0);
}
x[strcspn(x, "\r\n")] = 0;
filename = x;
}
else {
filename = *(argv+1);
}
file = fopen(filename,"rb");
if (!file) {
fprintf(stderr,"cannot open %s: %s\n",filename,strerror(errno));
return(1);
}
if (fread(buf, 10, 1, file) != 1) {
fprintf(stderr,"short read, aborted\n");
fclose(file);
return(1);
}
pos = ftell(file);
if (pos == -1) {
fprintf(stderr,"ftell returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
printf("reading 10 bytes from file\n");
printf("current file pos: %ld\n", pos);
printf("get file size (lseek): ");
fd = *(char *)file; /* kids, don't do this at home */
fsz = lseek(fd, 0, SEEK_END);
if (fsz == -1) {
fprintf(stderr,"lseek returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
printf("%ld (fd = %d)\n", (long)fsz, fd);
printf("get file size (fseek): ");
pos = fseek(file, 0, SEEK_END);
if (pos != 0) {
fprintf(stderr,"fseek returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
pos = ftell(file);
if (pos == -1) {
fprintf(stderr,"ftell returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
printf("%ld\n",pos);
printf("positioning at offset 100: ");
pos = fseek(file, 100, SEEK_SET);
if (pos != 0) {
fprintf(stderr,"fseek returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
pos = ftell(file);
if (pos == -1) {
fprintf(stderr,"ftell returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
if (pos == 100) {
printf("Ok\n");
}
else {
printf("failed! cur pos = %ld\n",pos);
fclose(file);
return(1);
}
printf("seeking back 44 bytes: ");
pos = fseek(file, -44, SEEK_CUR);
if (pos != 0) {
fprintf(stderr,"fseek returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
pos = ftell(file);
if (pos == -1) {
fprintf(stderr,"ftell returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
if (pos == 56) {
printf("Ok\n");
}
else {
printf("failed! cur pos = %ld\n",pos);
fclose(file);
return(1);
}
printf("seeking forward 111 bytes: ");
pos = fseek(file, 111, SEEK_CUR);
if (pos != 0) {
fprintf(stderr,"fseek returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
pos = ftell(file);
if (pos == -1) {
fprintf(stderr,"ftell returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
if (pos == 167) {
printf("Ok\n");
}
else {
printf("failed! cur pos = %ld\n",pos);
fclose(file);
return(1);
}
printf("seeking 13 bytes before eof: ");
pos = fseek(file, -13, SEEK_END);
if (pos != 0) {
fprintf(stderr,"fseek returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
pos = ftell(file);
if (pos == -1) {
fprintf(stderr,"ftell returned -1: %s\n", strerror(errno));
fclose(file);
return(1);
}
if (pos == fsz - 13) {
printf("Ok\n");
}
else {
printf("failed! cur pos = %ld\n",pos);
fclose(file);
return(1);
}
printf("seeking before sof:\n\t");
pos = fseek(file, -fsz, SEEK_CUR);
if (pos != 0) {
printf("Ok, error %s\n", strerror(errno));
}
else {
printf("NOT OK, no error\n");
fclose(file);
return(1);
}
/* ProDOS on the Apple II only supports 24-bit file offsets,
** so anything beyond that should be an error. I don't know
** about other platforms, but I'm guessing no 6502-based
** operating systems support 32-bit offsets?
*/
printf("seeking to position 2^24:\n\t");
pos = lseek(fd, 0x1000000L, SEEK_SET);
if (pos == -1) {
printf("Ok, error %s\n", strerror(errno));
}
else {
printf("NOT OK, returned %ld but expected -1\n", pos);
fclose(file);
return(1);
}
printf("trying invalid value for whence:\n\t");
pos = lseek(fd, 0L, 3);
if (pos == -1) {
printf("Ok, error %s\n", strerror(errno));
}
else {
printf("NOT OK, returned %ld but expected -1\n", pos);
fclose(file);
return(1);
}
fclose(file);
return(0);
}

74
targettest/ser-test.c Normal file
View File

@@ -0,0 +1,74 @@
#include <stdio.h>
#include <stdlib.h>
#include <serial.h>
#include <conio.h>
#include <dbg.h>
#if defined(__C64__)
#define DRIVERNAME "c64-swlink.ser"
#elif defined(__C128__)
#define DRIVERNAME "c128-swlink.ser"
#elif defined(__PLUS4__)
#define DRIVERNAME "plus4-stdser.ser"
#elif defined(__CBM610__)
#define DRIVERNAME "cbm610-std.ser"
#elif defined(__APPLE2ENH__)
#define DRIVERNAME "a2e.ssc.ser"
#elif defined(__APPLE2__)
#define DRIVERNAME "a2.ssc.ser"
#elif defined(__ATARIXL__)
#define DRIVERNAME "atrxrdev.ser"
#elif defined(__ATARI__)
#define DRIVERNAME "atrrdev.ser"
#else
#define DRIVERNAME "unknown"
#error "Unknown target system"
#endif
static const struct ser_params Params = {
SER_BAUD_9600, /* Baudrate */
SER_BITS_8, /* Number of data bits */
SER_STOP_1, /* Number of stop bits */
SER_PAR_NONE, /* Parity setting */
SER_HS_HW /* Type of handshake to use */
};
static void CheckError (const char* Name, unsigned char Error)
{
if (Error != SER_ERR_OK) {
fprintf (stderr, "%s: %d\n", Name, Error);
exit (EXIT_FAILURE);
}
}
int main (void)
{
char Res;
char C;
CheckError ("ser_load_driver", ser_load_driver (DRIVERNAME));
CheckError ("ser_open", ser_open (&Params));
while (1) {
if (kbhit ()) {
C = cgetc ();
if (C == '1') {
break;
} else {
CheckError ("ser_put", ser_put (C));
printf ("%c", C);
}
}
Res = ser_get (&C);
if (Res != SER_ERR_NO_DATA) {
CheckError ("ser_get", Res);
printf ("%c", C);
}
}
CheckError ("ser_unload", ser_unload ());
return EXIT_SUCCESS;
}

108
targettest/strdup-test.c Normal file
View File

@@ -0,0 +1,108 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include <_heap.h>
static unsigned char* V[256];
static void ShowInfo (void)
/* Show heap info */
{
/* Count free blocks */
unsigned Count = 0;
unsigned** P = (unsigned**) _heapfirst;
while (P) {
++Count;
P = P[1];
}
printf ("%04X %04X %04X %04X %04X %u\n",
_heaporg, _heapptr, _heapend, _heapfirst, _heaplast, Count);
if (Count) {
P = (unsigned**) _heapfirst;
while (P) {
printf ("%04X %04X %04X %04X(%u)\n",
(unsigned) P, P[2], P[1], P[0], P[0]);
P = P[1];
}
getchar ();
}
}
static const char* RandStr (void)
/* Create a random string */
{
static char S [300];
unsigned Len = (rand () & 0xFF) + (sizeof (S) - 0xFF - 1);
unsigned I;
char C;
for (I = 0; I < Len; ++I) {
do {
C = rand() & 0xFF;
} while (C == 0);
S[I] = C;
}
S[Len] = '\0';
return S;
}
static void FillArray (void)
/* Fill the string array */
{
unsigned char I = 0;
do {
V[I] = strdup (RandStr ());
++I;
} while (I != 0);
}
static void FreeArray (void)
/* Free all strings in the array */
{
unsigned char I = 0;
do {
free (V[I]);
++I;
} while (I != 0);
}
int main (void)
{
unsigned long T;
/* Show info at start */
ShowInfo ();
#if !defined(__APPLE2__)
/* Remember the time */
T = clock ();
#endif
/* Do the tests */
FillArray ();
ShowInfo ();
FreeArray ();
ShowInfo ();
#if !defined(__APPLE2__)
/* Calculate the time and print it */
T = clock () - T;
printf ("Time needed: %lu ticks\n", T);
#endif
/* Done */
return EXIT_SUCCESS;
}

View File

@@ -0,0 +1,31 @@
#include <stdio.h>
#include <string.h>
#include <conio.h>
int main (void)
{
unsigned char error = 0;
unsigned char line = 0;
unsigned char maxx, maxy;
screensize (&maxx, &maxy);
do {
printf ("%2d: %s\n", error, _stroserror (error));
if (line == maxy-3) {
printf ("Press any key...\n");
if (cgetc () == 'q') {
return 0;
}
clrscr ();
line = 0;
} else {
++line;
}
++error;
} while (error != 0);
return 0;
}

51
targettest/strqtok-test.c Normal file
View File

@@ -0,0 +1,51 @@
/* strqtok-test.c
**
** 2014-04-21, Paul Foerster
** 2014-05-20, Greg King
**
** This program tests that strqtok() correctly will parse strings
** with quotation marks in them. It should show this list of tokens
** from the test strings:
**
** >This<
** > is only <
** >a<
** >short<
** >quoting<
** >test , honoring blanks, commas<
** >and<
** >(4)<
** >empty<
** ><
** ><
** ><
** ><
** >strings, EOT <
**
** It shouldn't show
**
** >Bogus token<
**
*/
#include <string.h>
#include <stdio.h>
void main (void)
{
/* b[] and s[] are declared as automatic, not static, variables
** because strqtok() will change them.
** They must be defined together; and, b[] must be defined first
** (because they're copied onto the top-down stack).
*/
char b[] = "Bogus token ";
char s[] = " This , \" is only \"a short "
"quoting\"test , honoring blanks"
", commas\", and (4) empty \"\"\"\"\"\"\"\" \"strings, EOT ";
char* t = strqtok (s, " ,");
while (t != NULL) {
printf (">%s<\n", t);
t = strqtok (NULL, " ,");
}
}

503
targettest/tinyshell.c Normal file
View File

@@ -0,0 +1,503 @@
/*
** Simple ("tiny") shell to test filename and directory functions.
** Copyright (c) 2013,2016 Christian Groessler, chris@groessler.org
*/
#define VERSION_ASC "0.91"
#ifdef __ATARI__
#define UPPERCASE /* define (e.g. for Atari) to convert filenames etc. to upper case */
#define HAVE_SUBDIRS
#endif
#ifdef __APPLE2__
#define HAVE_SUBDIRS
#endif
#ifdef __CC65__
#define CHECK_SP
#endif
#define KEYB_BUFSZ 127
#define PROMPT ">>> "
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <unistd.h>
#ifndef __CC65__
#include <sys/stat.h>
#include <sys/param.h>
#define HAVE_SUBDIRS
#else
#define MAXPATHLEN 64
#endif
#include <sys/types.h>
#include <fcntl.h>
#include <dirent.h>
#ifdef CHECK_SP
extern unsigned int getsp(void); /* comes from getsp.s */
#endif
#define CMD_NOTHING 0
#define CMD_INVALID 1
#define CMD_HELP 2
#define CMD_QUIT 3
#define CMD_LS 4
#define CMD_MKDIR 5
#define CMD_RMDIR 6
#define CMD_CHDIR 7
#define CMD_RM 8
#define CMD_RENAME 9
#define CMD_COPY 10
#define CMD_PWD 11
#define CMD_CLS 12
#define CMD_VERBOSE 13
#define CMD_EXEC 14
static unsigned char verbose;
static unsigned char terminate;
static unsigned char cmd;
static unsigned char *cmd_asc, *arg1, *arg2, *arg3, *args; /* 'args': everything after command */
static unsigned char keyb_buf[KEYB_BUFSZ + 1];
static unsigned char keyb_buf2[KEYB_BUFSZ + 1];
static size_t cpbuf_sz = 4096;
struct cmd_table {
unsigned char *name;
unsigned char code;
} cmd_table[] = {
{ "help", CMD_HELP },
{ "quit", CMD_QUIT },
{ "q", CMD_QUIT },
{ "exit", CMD_QUIT },
{ "ls", CMD_LS },
{ "dir", CMD_LS },
{ "md", CMD_MKDIR },
#ifdef HAVE_SUBDIRS
{ "mkdir", CMD_MKDIR },
{ "rd", CMD_RMDIR },
{ "rmdir", CMD_RMDIR },
{ "cd", CMD_CHDIR },
{ "chdir", CMD_CHDIR },
#endif
{ "rm", CMD_RM },
{ "del", CMD_RM },
{ "cp", CMD_COPY },
{ "copy", CMD_COPY },
{ "mv", CMD_RENAME },
{ "ren", CMD_RENAME },
{ "pwd", CMD_PWD },
{ "exec", CMD_EXEC },
#ifdef __ATARI__
{ "cls", CMD_CLS },
#endif
{ "verbose", CMD_VERBOSE },
{ NULL, 0 }
};
static void banner(void)
{
puts("\"tiny\" command line shell, v" VERSION_ASC);
puts("written by chris@groessler.org");
puts("type 'help' for help\n");
}
static void get_command(void)
{
unsigned char i = 0;
#ifdef CHECK_SP
static char firstcall = 1;
static unsigned int good_sp;
unsigned int sp;
if (firstcall)
sp = good_sp = getsp();
else
sp = getsp();
if (sp != good_sp) {
printf("SP: 0x%04X ***MISMATCH*** 0x%04X\n", sp, good_sp);
}
else if (verbose)
printf("SP: 0x%04X\n", sp);
#endif
arg1 = arg2 = arg3 = NULL;
/* issue prompt */
printf(PROMPT);
/* get input from the user */
if (! fgets(keyb_buf, KEYB_BUFSZ, stdin)) {
puts("");
cmd = CMD_QUIT;
return;
}
/* put everything after first string into 'args' */
strcpy(keyb_buf2, keyb_buf); /* use a backup copy for 'args' */
/* skip over the first non-whitespace item */
cmd_asc = strtok(keyb_buf2, " \t\n");
if (cmd_asc)
args = strtok(NULL, ""); /* get everything */
else
*args = 0; /* no arguments */
/* split input into cmd, arg1, arg2, arg3 */
/* get and parse command */
cmd_asc = strtok(keyb_buf, " \t\n");
if (! cmd_asc) {
cmd = CMD_NOTHING;
return;
}
cmd = CMD_INVALID;
while (cmd_table[i].name) {
if (! strcmp(cmd_table[i].name, cmd_asc)) {
cmd = cmd_table[i].code;
break;
}
i++;
}
/* get arguments */
arg1 = strtok(NULL, " \t\n");
if (! arg1)
return;
arg2 = strtok(NULL, " \t\n");
if (! arg2)
return;
arg3 = strtok(NULL, " \t\n");
}
static void cmd_help(void)
{
puts("quit, exit - exit shell");
puts("ls, dir - display current directory");
puts(" and drive contents");
puts("rm, del - delete file");
puts("cp, copy - copy file");
puts("mv, ren - rename file");
puts("cd, chdir - change directory or drive");
puts("md, mkdir - make directory or drive");
puts("rd, rmdir - remove directory or drive");
puts("exec - run program");
#ifdef __ATARI__
puts("cls - clear screen");
#endif
puts("verbose - set verbosity level");
}
static void cmd_ls(void)
{
DIR *dir;
unsigned char *arg;
struct dirent *dirent;
#ifdef __ATARI__
char need_free = 0;
#endif
if (arg2) {
puts("usage: ls [dir]");
return;
}
/* print directory listing */
if (arg1) {
#ifdef UPPERCASE
strupr(arg1);
#endif
#ifdef __ATARI__
/* not sure if this shouldn't be done by the runtime lib */
if (*(arg1 + strlen(arg1) - 1) == ':' || *(arg1 + strlen(arg1) - 1) == '>') {
arg = malloc(strlen(arg1) + 4);
if (! arg) {
printf("malloc failed: %s", strerror(errno));
return;
}
need_free = 1;
memcpy(arg, arg1, strlen(arg1) + 1);
strcat(arg, "*.*");
}
else
#endif
arg = arg1;
}
else
arg = ".";
if (verbose)
printf("Buffer addr: %p\n", arg);
dir = opendir(arg);
#ifdef __ATARI__
if (need_free) free(arg);
#endif
if (! dir) {
puts("opendir failed");
return;
}
while (dirent = readdir(dir))
puts(dirent->d_name);
closedir(dir);
}
static void cmd_rm(void)
{
if (!arg1 || arg2) {
puts("usage: rm <file>");
return;
}
#ifdef UPPERCASE
strupr(arg1);
#endif
if (unlink(arg1))
printf("remove failed: %s\n", strerror(errno));
}
#ifdef HAVE_SUBDIRS
static void cmd_mkdir(void)
{
if (!arg1 || arg2) {
puts("usage: mkdir <dir>");
return;
}
#ifdef UPPERCASE
strupr(arg1);
#endif
if (mkdir(arg1, 0777))
printf("mkdir failed: %s\n", strerror(errno));
}
static void cmd_rmdir(void)
{
if (!arg1 || arg2) {
puts("usage: rmdir <dir>");
return;
}
#ifdef UPPERCASE
strupr(arg1);
#endif
if (rmdir(arg1))
printf("rmdir failed: %s\n", strerror(errno));
}
static void cmd_chdir(void)
{
if (!arg1 || arg2) {
puts("usage: cddir <dir>");
return;
}
#ifdef UPPERCASE
strupr(arg1);
#endif
if (chdir(arg1))
printf("chdir failed: %s\n", strerror(errno));
}
static void cmd_pwd(void)
{
char *buf;
if (arg1) {
puts("usage: pwd");
return;
}
buf = malloc(MAXPATHLEN);
if (! buf) {
printf("malloc %u bytes failed: %s\n", MAXPATHLEN, strerror(errno));
return;
}
if (verbose)
printf("Buffer addr: %p\n", buf);
if (!getcwd(buf, MAXPATHLEN)) {
printf("getcwd failed: %s\n", strerror(errno));
free(buf);
return;
}
puts(buf);
free(buf);
}
#endif /* #ifdef HAVE_SUBDIRS */
static void cmd_rename(void)
{
if (!arg2 || arg3) {
puts("usage: mv <oldname> <newname>");
return;
}
#ifdef UPPERCASE
strupr(arg1);
strupr(arg2);
#endif
if (rename(arg1, arg2))
printf("rename failed: %s\n", strerror(errno));
}
static void cmd_exec(void)
{
unsigned char *progname, *arguments;
progname = strtok(args, " \t\n");
if (! progname) {
puts("usage: exec <progname> [arguments]");
return;
}
arguments = strtok(NULL, "");
/*printf("exec: %s %s\n", progname, arguments ? arguments : "");*/
(void)exec(progname, arguments);
printf("exec error: %s\n", strerror(errno));
}
static void cmd_copy(void)
{
int srcfd = -1, dstfd = -1;
unsigned char *buf;
int readsz, writesz;
if (!arg2 || arg3) {
puts("usage: cp <src> <dest>");
return;
}
#ifdef UPPERCASE
strupr(arg1);
strupr(arg2);
#endif
buf = malloc(cpbuf_sz);
if (! buf) {
printf("malloc %u bytes failed: %s\n", cpbuf_sz, strerror(errno));
return;
}
if (verbose)
printf("Buffer addr: %p\n", buf);
while (1) {
if (srcfd == -1) {
srcfd = open(arg1, O_RDONLY);
if (srcfd < 0) {
printf("open(%s) failed: %s\n", arg1, strerror(errno));
break;
}
}
readsz = read(srcfd, buf, cpbuf_sz);
if (readsz < 0) {
printf("read error: %s\n", strerror(errno));
break;
}
if (! readsz)
break;
if (dstfd == -1) {
dstfd = open(arg2, O_WRONLY | O_CREAT | O_TRUNC, 0777);
if (dstfd < 0) {
printf("open(%s) failed: %s\n", arg2, strerror(errno));
break;
}
}
writesz = write(dstfd, buf, readsz);
if (writesz < 0 || writesz != readsz) {
printf("write error: %s\n", strerror(errno));
break;
}
if (readsz != cpbuf_sz)
break;
}
free(buf);
if (srcfd >= 0) close(srcfd);
if (dstfd >= 0) close(dstfd);
}
#ifdef __ATARI__
static void cmd_cls(void)
{
printf("\f");
}
#endif
static void cmd_verbose(void)
{
unsigned long verb;
char *endptr;
if (!arg1 || arg2) {
puts("usage: verbose <level>");
return;
}
verb = strtoul(arg1, &endptr, 10);
if (verb > 255 || *endptr) {
puts("invalid verbosity level");
return;
}
verbose = verb;
printf("verbosity level set to %d\n", verbose);
}
static void run_command(void)
{
switch (cmd) {
default: puts("internal error"); return;
case CMD_NOTHING: return;
case CMD_INVALID: puts("invalid command"); return;
case CMD_HELP: cmd_help(); return;
case CMD_QUIT: terminate = 1; return;
case CMD_LS: cmd_ls(); return;
case CMD_RM: cmd_rm(); return;
#ifdef HAVE_SUBDIRS
case CMD_CHDIR: cmd_chdir(); return;
case CMD_MKDIR: cmd_mkdir(); return;
case CMD_RMDIR: cmd_rmdir(); return;
case CMD_PWD: cmd_pwd(); return;
#endif
case CMD_EXEC: cmd_exec(); return;
case CMD_RENAME: cmd_rename(); return;
case CMD_COPY: cmd_copy(); return;
#ifdef __ATARI__
case CMD_CLS: cmd_cls(); return;
#endif
case CMD_VERBOSE: cmd_verbose(); return;
}
}
int main(void)
{
banner();
while (! terminate) {
get_command();
run_command();
}
return 0;
}
/* Local Variables: */
/* c-file-style: "cpg" */
/* c-basic-offset: 4 */
/* End: */

26
targettest/uname-test.c Normal file
View File

@@ -0,0 +1,26 @@
#include <stdio.h>
#include <stdlib.h>
#include <sys/utsname.h>
int main (void)
{
/* Get the uname data */
struct utsname buf;
if (uname (&buf) != 0) {
perror ("uname");
return EXIT_FAILURE;
}
/* Print it */
printf ("sysname: \"%s\"\n", buf.sysname);
printf ("nodename: \"%s\"\n", buf.nodename);
printf ("release: \"%s\"\n", buf.release);
printf ("version: \"%s\"\n", buf.version);
printf ("machine: \"%s\"\n", buf.machine);
/* Done */
return EXIT_SUCCESS;
}