* for
Emacs: -*- mode:indented-text; mode:outline-minor -*-
ZCN v1.2 - (c) 1994-1999 Russell
Marks
A free CP/M-like
operating system for the Amstrad NC100.
* License
This
program is free software; you can redistribute it and/or modify
it under
the terms of the GNU General Public License as published by
the Free
Software Foundation; either version 2 of the License, or (at
your option)
any later version.
This program is distributed in the hope that it
will be useful, but
WITHOUT ANY WARRANTY; without even the implied
warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for
more details.
You should have received a copy of the GNU General
Public License
along with this program; if not, write to the Free
Software
Foundation, 59 Temple Place - Suite 330, Boston, MA 02111-1307,
USA.
[The GNU GPL is in the file `COPYING'.]
*
About ZCN
ZCN is an alternative operating system for the NC100.
Features
include:
- a high level of CP/M compatibility
-
fast switching between ZCN and the ROM software, and file transfer
between the two
- can run BBC Basic
(from ROM) as if it were a native ZCN program
- command processor (shell)
with many internal commands
- many external commands and third-party
programs
- optional online help (using `man')
- 46k free for programs
to run in
- terminal emulator with 120x10 text resolution
- keyboard
handler with 128-char keyboard buffer
- context saving while power is
off
- support for the serial port at speeds up to 19200 baud
-
printer (i.e. parallel port) support
- auto power-off after a given idle
time
- warnings when main, backup, or memory card batteries are low
-
console redirection to serial port or printer
- washes whiter than other
powders
ZCN is modelled quite closely on the CP/M operating system
common on
8080 and Z80 machines in the late 70s and early 80s. (It is
most
common in the UK today on Amstrad PCWs.) I decided to do this as
there
is a great deal of public domain and other zero cost software
for
CP/M, including text editors, simple C compilers, Z80 assemblers,
a
few games, etc. CP/M is also, in my opinion, well suited to running
on
small Z80 systems. ZCN's CP/M compatibility is sufficient to run
most
CP/M 2.2 programs.
** Should I use ZCN?
You
should probably consider using ZCN if you like the idea of a
portable CP/M
box, or want to use the NC100 as something a bit closer
to a `real
computer'. These are the two reasons I originally started
writing
ZCN.
** Warning!
If you want to still be able to
use the built-in ROM software without
losing any of your current data, you
*MUST* transfer and run the
`rrinit' program before trying to run ZCN. If
you don't, you'll lose
any data held in the 64k of internal memory! (This
means losing not
only any files in both the upper and lower memory, but
also any
configuration.)
If you don't care about the ROM
software, or don't care about losing
currently-held data, you shouldn't
bother with `rrinit'.
(There's more on `rrinit' at the appropriate
point below.)
** Requirements
ZCN needs the
following to install and run successfully:
- An Amstrad NC100
Notepad
- At least one PCMCIA memory card, which will need to be
reformatted
in ZCN's format
-
A computer with a serial link to the NC100, and the
capability to send files using the XMODEM
protocol
If you want to save the data currently in the internal
memory, the
memory card must be at least 128k (64k of it will be used to
save the
memory).
You will also need a basic knowledge of using
CP/M, though a
reasonably capable MS-DOS and/or Unix user should be able
to get along
ok. (Hey, it worked for me... :-))
*
Installing ZCN
The installation guide below assumes you are
installing from a Unix or
MS-DOS machine. It should be clear what to do on
other machines
though; you just need to know how to XMODEM a file across,
and how to
send a plain ASCII file. Normally the easiest way is to use a
serial
comms program of some sort.
** Getting ZCN up and
running for the first time
*** Saving your existing data
[If
you don't care about using the ROM software, or don't mind losing
all the
data in the internal memory, skip ahead to the next section,
`Booting ZCN
via a Serial Link'.]
ZCN uses the NC100's 64k of RAM as more normal
computers generally use
RAM - as an area to load programs into, and an
area to use for
temporary workspace, etc. Unfortunately, this is not
compatible with
the way the built-in software works, so you'll lose all
your existing
data in memory unless you save it first. `rrinit' is a
program which
lets you save your data like this. (You'll be able to
restore it later
using `runrom'. More on that later on.)
To run
`rrinit', you'll need a memory card of at least 128k in size.
It should
probably be the card you intend to copy ZCN onto, but it
doesn't have to
be. Bear in mind that the card will be reformatted in
ZCN's format, and
any data currently on it will be lost!
You must also have at least
one file stored in memory on your NC100,
as the ROM software doesn't let
you do serial file transfers
otherwise. (If you haven't got any files in
memory, just create a
small file with the word processor. It doesn't
matter what's in it or
what it's called, just that it's there.)
First
you need to setup the serial link. You should set the baud rate
to 2400
baud on the `remote' computer, as transfers seem to be a bit
hairy (for
the ROM software at least) at higher speeds.
After that, *make sure
there isn't any memory card in the NC100's
slot*, then do the
following:
Key Reason
--- ------
Function
+ S go to terminal program
Menu,
down*3, left*2, Stop use 2400
baud
(you may
need more or less lefts,
depending
on the current setting)
<type a few characters on the NC100 and
`remote' computer to check
the
link is working ok>
<start XMODEM send (or `upload') of `rrinit.bin'
on `remote' computer>
Stop quit
terminal program
Function + L load
document
Menu, T, M, rrinit, return XMODEM
receive `rrinit'
<wait for transfer to finish>
Stop return to file
selector
<now insert the memory card>
Menu, F, <possibly
Y>, Stop format card (answer `Y' if
it prompts you)
<make sure the `rrinit' file is the
currently-highlighted one>
Menu, T, P, Stop write rrinit to memory card
Stop exit file selector
Function + X run rrinit
[NB:
`rrinit.bin' is in the `bin' subdirectory.]
Almost immediately after
you do the function-X, rrinit should say
"Snapshot written - press
Stop". Pressing Stop then returns you to the
NC100's main menu.
Now
you should be ready to run ZCN, so here goes...
*** Booting
ZCN via a Serial Link
[If you are upgrading an existing version of
ZCN, skip ahead to
`Installing a new version using an old one', which will
be rather more
appropriate.]
First you need to setup the serial
link. You should set the baud rate
to 2400 baud on the `remote' computer,
as transfers seem to be a bit
hairy at higher speeds. (ZCN itself can cope
with file transfers at up
to 19200, but the ROM software seems to be more
picky. So for this
transfer, it's best to stick with 2400.)
Now
you should cold-boot the NC100. Do this by turning it off and,
while
holding down Function, Stop and `<-Del', turning it back on.
Next
you should do the following:
Key Reason
--- ------
Function + S go to terminal program
Menu,
down*3, left*2, Stop set speed to 2400
baud
<type a few characters on the NC100 and `remote' computer to
check
the link is working
ok>
<start XMODEM send (or `upload') of `zcn.bin' on `remote'
computer>
Stop quit
terminal program
Function + N, x, return create
junk document
x put
junk in it
Function + L load
document
Menu, T, M, tmp, return XMODEM
receive `tmp'
<wait for transfer to finish>
Function + B enter basic
"*LOAD
TMP 6000" load system (omit
the quotes :-))
"CALL &6000" start
ZCN (ditto)
[NB: `zcn.bin'
is in the `bin' subdirectory.]
(It was necessary to create the junk
file above so that Function-L
would work; there's no way to get the menu
which lets you XMODEM
receive a file without any files in memory.
Yuck.)
(Also, note that you will need a reasonably complete serial
lead for
the ROM software's XMODEM transfer to work (this doesn't apply to
ZCN
itself, which needs only the minimal out/in/gnd connection (plus
CTS
if serial output is to work, though that can just be soldered to
RTS)).
Any lead you *buy* should be fine, but if you've knocked up
your own
only-three-pins-connected job you'll need to borrow a better
lead from
someone for this transfer. :-) However, for an alternative
approach, see
`badlead.txt'.)
You should then end up with a screen looking
something like:
ZCN v1.2
(1999-03-03 16:20) ROM v1.06
A>
A>
(The version numbers and
date/time of assembly may vary - don't worry,
that's because I don't often
update the above `screenshot'. :-))
The `A>' is the ZCN command
processor's prompt. It'll probably be
there twice because you pressed
enter at the end of "CALL &6000" and
it was still pressed
the first time ZCN prompted for a command line,
so it just prompted again.
(ZCN didn't know that it was pressed before
- it wasn't running
then.)
If you ran `rrinit' before booting ZCN, skip the next
paragraph. Let
me put that another way - IF YOU RAN `rrinit', DO *NOT* DO
`format a:'
OR YOU WILL LOSE THE DATA IT SAVED. (`format b:' etc. is
fine,
though.)
Those of you who didn't run `rrinit' should now
make sure you have
your PCMCIA card in the card slot, and type `format
a:'. If it prompts
you asking if you want to reformat it, press `y'. You
should see the
message `Formatting complete' almost immediately
(formatting memory
cards is a very simple operation).
If the
card you're using is 512k or 1024k, type `format b:', which
formats the
2nd logical drive (the 2nd 256k of the card).
If the card is 1024k,
follow this by typing `format c:' and finally
`format d:'.
If
the card is larger than 1024k, you've got more money than sense, as
the
NC100 can't access the rest. :-)
Now you can make a bootable ZCN
drive on your card. Do this by typing
`sys a:'.
Since this is
the first time you've added the system to this card,
you'll get lots of
`addblk..' messages. This means that ZCN is moving
the whole logical drive
up 1k (one block). This is necessary to ensure
that you can add a new
version of ZCN to a card without having to
reformat it. If you ever want
to add a new version of ZCN to the card,
you can just boot it via the
serial link as you did here and then do
`sys a:' again. In fact, you can
also do it without ever leaving ZCN -
see the section `Installing a new
version using an old one' below.
When the message `copying...done.'
appears, the card is bootable.
You may have noticed, while the
system was being copied, there was a
rather curious small black bar at the
bottom-left of the screen. This
is the `drive light' for logical drive A:.
Whenever this bar appears,
part of the card's memory is paged in that
belongs to that logical
drive, i.e. the `disk' is being accessed. The
`drive light' for
logical drive B: is to the right of that, C:'s is to the
right of
that, as is D:'s. It won't usually be `on' as much in general as
it
was for the `sys a:' command; don't worry about this, it's
perfectly
normal.
You should now check that the system is
bootable. This gives you an
opportunity to learn the booting procedure. As
the NC100 remembers
what you were doing when you turn it off, you should
only ever need to
reboot the system from scratch like this to: 1. check
bootable cards,
2. reboot after a crash, or 3. reboot after changing the
lithium
backup battery. (When you change normal batteries, there's no need
to
reboot - the backup battery takes over until the new batteries
are
in.)
*** Rebooting to test a bootable card, or after
a crash
Going from when the NC100 is still on, you should:
1.
Press the on/off switch to turn the computer off. If it didn't turn
off,
remove the main batteries (not the lithium one) and disconnect
from the
mains adaptor, and then reinstall/reconnect. (The on/off
switch will work
fine usually, but sometimes when the NC100 crashes it
stops working
because of memory corruption.)
2. Hold down the Function, Stop and
`<-Del' keys and press the on/off
switch. This restarts the machine from
scratch.
Assuming you're now at the `enter time' screen or the main
menu, it
doesn't matter which:
3. Make sure your bootable ZCN
card is in the slot, and press
`Function' and `X'. This should boot ZCN
and leave you at the `A>'
prompt.
An alternative method (for
testing a bootable card) is to use the
`cboot' command.
****
Ye Olde Boot Method
Just for hysterical raisins, I've left in the
instructions detailing
how you *used* to have to reboot. Not much fun.
:-)
Skip this unless you're interested.
Steps 1 and 2
were as above, and then...
3. Press `Function' and `B'.
4.
Make sure you have a bootable ZCN card in the card slot.
5. Type in
any one of the following lines, whichever is most
convenient. (Type only
one of them, and type them exactly as shown.)
P%=102:[:LD A,128:OUT
(16),A:]
!102=&10D3803E
!102=282296382
6. Press the
on/off switch.
ZCN should now boot from logical drive A: on the
card. If it doesn't,
PANIC. :-)
(You'll probably have to
transfer ZCN via serial link again to get it
to boot, if it really won't
boot off the card.)
As to the choice of which lines to type in in
step 5... The latter two
aren't too bad to write down if your memory isn't
really up to
remembering any of them. The first one is probably fairly
memorable if
you've done much Z80 programming.
That said, I've
managed to memorise the last one, so it might be worth
trying that if you
can.
Now, aren't you glad you don't have to do that any more?
:-)
*** Getting the first program across
So you've
got your shiny new operating system across, and it's there,
and... it's
not doing very much really, is it? To fix that, you'll
need to get some
interesting programs across to your ZCN system. But
in order to do that,
you first need to get a reasonable comms program
across which will make
serial transfer easier.
This implies that getting the first program
across is hard. :-)
Well, it's harder, at any rate. ZCN has a simple
`internal command' (a
program already in memory, which doesn't need to be
loaded off the
card) called `rexec' which reads a uuencoded file from the
serial port
and writes it to the memory card under the filename given.
Now, a
uuencoded file is a binary file, such as a program, converted
to
`normal' readable ASCII characters by a program called,
reasonably
enough, `uuencode'. :-)
On a Unix machine,
`uuencode' will usually be part of the system - it
was originally written
to help with transferring binary files across
7-bit links between Unix
machines. For example, from my Linux box I
could do:
uuencode
wibble.com wibble.com >/dev/ttyS1
...to send the program
`wibble.com' to my NC100, which is connected to
my second serial
port.
One of the best `first programs' in my experience is QTERM. A
version
patched for use under ZCN is in the `support' directory. There is
also
a copy of this already uuencoded, called `qterm.uue'.
What
you should do to send the program is to first type `rexec
qterm.com' on
the NC100, then start the uuencode (if Unix) or `ASCII
upload' the
`qterm.uue' file (if MS-DOS). (It's easiest to again do
this transfer at
2400 baud on your `remote' computer, as ZCN defaults
to 2400 baud - but
that's a bit slow, and you can use `stty' to change
speed if you want,
e.g. `stty 19200' sets the speed to 19200 baud.)
If it works, you
should get a dot printed as each line is processed,
then a short delay at
the end while the file is written.
(If it doesn't work, try pressing
both ctrl and C (i.e. ^C) to abort
the `rexec' and start again.)
(If
you're using MS-DOS and your comms program doesn't have any `ASCII
upload'
facility: 1. do something like `copy qterm.uue com2:' from the
DOS prompt,
and 2. get a new comms program.)
Once you get QTERM across, you can
run it by giving the command
`qterm'. You'll need to read the QTERM
documentation in
`support/qterm' to learn about all its features, but
here's the bare
minimum for transferring things to/from the NC100:
You
can type Control+\ followed by Q to quit QTERM. More usefully, you
can
type Control+\ then R to receive a file (this is what you'll want
first
off) and type something like `x wibble.com' in answer to the
prompt
`Mode?'. Control+\ then S sends a file and works the same way.
(If
you used `rrinit' to save your data, now would be a good time to
make a
backup copy of the `runrom.ram' file it created, by sending it
to your
main machine using QTERM.)
You can find many free CP/M programs on
the oak.oakland.edu ftp site
under /pub/cpm. That's where I got QTERM
from, for example. Note that
some of the programs there, particularly
those that use the BIOS disk
routines, may not work under ZCN. Since many
of the programs there are
stored in .LBR format, you'll probably want to
use the `lar' program
in the `support' directory. Look at the README there
for more info.
** Installing a new version using an old
one
I noted earlier that you could actually install a new version of
ZCN
using an old one - i.e. without ever leaving ZCN. Here's how to
do
that.
First, you need to get the `zcn.bin' file across. You
can do this with
`rexec' or (better) `qterm', as described above. At the
NC100 end you
should give it a filename ending in `.com', as it acts just
like a
normal executable program. `zcn.com' is a good name, for
example.
Then after getting `zcn.com' (or whatever) across, you
simply run it,
in this case by typing `zcn'. When the new version boots,
test it out
a bit to make sure it's working ok; you can then delete the
`.com'
file and install it on the card with `era zcn.com' and `sys
a:'.
** Installation epilogue
By now, you should
have a running ZCN system with a bootable card and
some file transfer
program. You may now want to transfer other
programs in the `bin' and
`support' directories, which together make
what I would consider a fully
functional ZCN system. None of the
programs are necessary, but you're likely
to find many useful:
- Programs you should transfer if at all
possible are `ls', `optdir',
`zde', `pipe', `submit', `pmarc', `pmext', `bbcbas', `runrom', and
`rrxfer'.
- If you want online
help, and it's better than you might think,
you'll want `man' (be sure to transfer `manpages.pma' too, or
it
won't work - see the `MAN'
section under `External Commands' for
details).
- `spell' may be useful if yu kant spel wurth a
dam. :-)
- `calc' runs the ROM calculator program under ZCN, and
since
floating-point calculators
for CP/M are few and far between, this
can be quite handy.
- `nswp' is a file manager which may be
worth a look; alternatively,
`zselx' is a simpler file manager which is somewhat like nswp but
full-screen, and also has the advantage that
the .com file is less
than half
the size.
- `rogue' can be a nice time-waster - oh sorry,
"game" - especially
for
AD&D fans. :-)
- `cpmtris' is a reasonable tetris clone.
-
If you own a microsoft-compatible serial mouse, you might want to
take a look at `zcnpaint', a mouse-based
paint program I wrote a
while
back. Documentation is in the `External Commands' section,
later on.
- If you like the idea
of a graphical front-end which works a bit like
the ROM software's menus (but which is hugely more flexible),
you
may want to try `zap' (but be
sure to transfer `zapdesc.bin' too -
see the `ZAP' section under `External Commands' for details).
-
And somewhat inevitably, there are many more. :-)
Frankly, it might
be a good idea to simply transfer the lot, if you
have room. The programs
in `bin' are described later on in `External
Commands'; the programs in
`support' are described in the README
there.
The rest of the
documentation in this file covers using ZCN and
programming for it, as
well as details of some of the internals.
As such, while I've tried
to assume little previous experience or
knowledge throughout this section
of the documentation, the rest of
this file will assume varying amounts.
It should be possible for
anyone with experience of CP/M to follow most of
the ZCN Manual, but
some is intended for programmers or simply for whoever
is interested.
Those of you who ran `rrinit' to save your data and
are now beginning
to panic because I've said so little about how you get
it back into
memory :-) should probably skip ahead to the section `Running
the ROM
software from ZCN' and read that before reading the manual
proper.
If you're a Z80 programmer new to CP/M and/or ZCN, you may
want to
look at `zcnprog.txt', my guide to programming CP/M and ZCN.
It
documents all the CP/M 2.2 BDOS calls, and all the `zcnlib'
routines.
If you have any problems, feel free to write/email
(addresses are at
the end of this file), and I'll do my best to help. If
you're writing,
please include an SAE if you can, it saves me time and
trouble.
* The ZCN Manual
** Rationale
The
ZCN Manual tends to concentrate on differences from normal CP/M in
everyday
use. I've tried to cover some of how CP/M works, but not all
that much.
Parts of it may be in a rather confusing and messed-up
order, as to a
certain extent I've just scrawled down documentation
for commands etc. as
I've added them.
I recommend that you read at least up until the
`ZCN for hackers'
section. I know it's a lot to read, but it will almost
certainly be
worth it, as ZCN is quite an oddball mix of ideas and
programs, and
there will almost certainly be something there that's new to
you.
Also be sure to read the `Q&A' section below.
The
manual is more than a little informal, as you may already have
noticed. In
my humble opinion, far too many manuals are stuffy and
unreadable. In
stark contrast, the ZCN manual is chatty and
unreadable. Much better.
:-)
** Q&A
This section attempts to cover some
of the more astonishing things ZCN
does. As for what I mean by
`astonishing':
"A program should follow the `Law of Least
Astonishment'. What is this
law? It is simply that the program should
always respond to the user
in the way that astonishes him
least."
-- James Geoffrey,
"The Tao of Programming"
ZCN, ah, bends this law at times.
:-)
*** Why do some programs show the file FOO.TXT as FOO.TwT?
This
is to do with, and yes I know this sounds bizarre, ZCN's support
for the
power on/off switch. Turning the machine off is actually done
under software
control, and the way it needs to work, combined with
the way CP/M works,
means that with some programs you may see
filenames with `w' as the second
character of the extension. A few
programs may even force the actual files
to have a `w' there (this is
very unlikely, but there might be one or two
programs that do it).
For technical reasons, there's little I can do
to prevent either of
the problems. The NC100 simply wasn't designed to run
CP/M, and ZCN
just does the best it can with what it's got. For a more
technical
explanation of why this happens, see the section `The Power
On/off
Switch' near the end of this file.
*** Why do I get
rubbish from the serial port?
Whenever you turn on the NC100 under
ZCN, the serial port is enabled.
During this process, a spurious `serial
input' interrupt is generated
which is difficult to filter out for various
reasons. This usually
ends up putting a random character in the serial
input buffer. This is
harmless and can be ignored.
If you get a
whole load of rubbish chars, you probably either have
parity enabled at
the other end or are using the wrong baud rate.
*** Why are the
letters so SMALL!?
I wanted to get as many lines as possible. I
think it's worth the
smaller characters to get 10 lines rather than 8 with
the ROM
software. I hope the characters are readable; I think they are,
but
I'm obviously rather biased. They're narrow to keep the aspect
ratio
as `normal' as possible, and because 4-bit wide characters are
much
easier and faster to draw than 6-bit wide ones such as the ROM
software
uses.
*** Why does zero look round, and O rectangular?
Before
ZCN v1.1, you simply couldn't tell zero and O apart in ZCN's
font (both
were round). Since, unfortunately, the characters were too
small to:
-
put a slash through the zero;
- put a dot in the centre of the zero (it
makes it look like an 8!);
- make the zero more diamond-like;
- make
the zero narrower;
...I decided to make the O rectangular instead.
(This is an unusual
approach, but isn't entirely without precedent.) It's
not ideal, but
at least you can tell which is which.
If you
really can't stand this, and you'd rather they were both round,
do this,
but be careful to type it in correctly!
poke ebda 44
poke
ebde 44
(Note that this causes problems with the copy cursor in
`bbcbas'
though - it'll think both 0 and O are zeroes. And it'll
affect
`dmp2txt' in much the same way.)
You could put these
commands in your `autoexec.sub' if you wanted this
all the time (more on
SUB files later), or you could just rewrite ZCN
with the altered font
using `sys a:'.
*** Why do some characters look like random
blotches?
ZCN only has character bitmaps for characters in the range
32-126, the
so-called `printable characters'. If a character outside this
range is
printed which is not a control code, an effectively random
collection
of pixels is printed.
This usually happens when a
character was printed which had the high
bit set. If the offending
character was received from the serial port,
try disabling parity on the
other machine.
*** It says `Disk Full', but I've got plenty of room
left!
This probably means that the drive's directory table is full.
Usually
under ZCN there's a maximum of 64 files per drive (but see
below).
When you run out of directory space, it's often interpreted
by
programs as `disk full'. It does have the same effect, as in order
to
write any more you'll have to move or delete one or more files.
You
may, in fact, be allowed less than 64 files. If a file is larger
than 16k,
it will take up more than one directory space - it'll use
one for each 16k
of the file.
*** Why is QTERM's display when sending/receiving files
messed up?
QTERM's file transfer display is designed for a terminal
with 12 lines
or more. ZCN only has 10, so the line which shows the number
of errors
sometimes overprints the line showing the number of packets done
so
far. I'm afraid there isn't much that can be done about this
without
patching QTERM - but hopefully it's not that much of a
problem.
*** How can I patch programs without DDT/SID?
Unfortunately,
the (possibly unusual, since they were for fairly `odd'
machines and may
have been modified) copies of DDT and SID I've tried
didn't work on ZCN;
or rather, they worked to a certain extent, but
they seemed to overwrite
the call at 0030h, which is a Bad Thing on
ZCN.
Personally, I
don't think this is that much of a problem. I use `wade'
instead (look in
the `support' directory for a copy) which is, dare I
say it, rather nicer
than DDT and SID. :-)
*** Why does the ROM ask me to set the time when
I turn the NC on?
NC100s with ROM v1.00 seem to be quite pedantic
about having the time
set. If the time *isn't* set, the ROM demands you
set it, which loses
you any saved context - and if ZCN was running, it
resets the machine
into the bargain. :-( This is a bug in the original
ROM, and although
it was fixed in the later v1.06 (which is in my NC100,
for example),
this doesn't help you if you have machine with the earlier
ROM (you
can check which ROM you have with ZCN's `ver' command).
The
only way to `fix' it is to set the time, as you might imagine.
(You can do
this either with the ROM's time setting screen or with
ZCN's `timeset'
command.) Fortunately, once the time is set it tends
to stay that way.
:-)
** Running the ROM software from ZCN
[This is
deliberately early on in the manual (earlier than it might
otherwise make
sense for it to be) so that it isn't too hard to find
for anyone skipping
ahead from `Installation epilogue'.]
*** About `runrom'
To
run the ROM software from ZCN, just use the `runrom' program - i.e.
do
`runrom' and it boots the ROM software. If you have an existing
`runrom.ram'
file - this file is a snapshot of an already-booted
machine, usually with
files in memory etc. - be sure to start with
that in the current drive and
user area. If no `runrom.ram' file is
found in the current drive/user, the
memory is zeroed and the ROM
booted from scratch.
Note that you
can only run `runrom' from a bootable card. (It'll exit
with an error if
you try to run it on one which isn't.) It's
complicated to fully explain
why, but the basic reason it's necessary
is so that there's a safe way
back to ZCN from the ROM software.
You also need either an existing
`runrom.ram' snapshot file, or 64k
free on the current drive in order to
create one. The reason for this
latter requirement is much easier to
explain - a snapshot is always
saved when you return to ZCN, and the disk
space for it is allocated
in advance.
When the ROM software is
started, you can use it exactly as you
normally would.
(If you
used `rrinit' to save your existing memory, the `rrinit' file
will still
be there when you do `runrom'. Feel free to delete it; it's
not needed any
more.)
When you want to return to ZCN, *make sure the card you ran
`runrom'
from is in the card slot*, then press `Function' and `X'.
(It's
probably best to leave this card in the slot throughout so you
don't
need to worry about whether it's in or not - but you may find
this
inconvenient. It's up to you.)
When you return to ZCN (in
fact just before), a snapshot of the memory
is saved in `runrom.ram'.
After that, ZCN is rebooted.
So in summary, it's:
-
`runrom' on a bootable card to go from ZCN to the ROM s/w.
-
Function-X *with the same card in the slot* to return to ZCN.
By the
way, you may notice that the screen is corrupted for a (very)
short while
when switching between ZCN and the ROM or vice versa. This
is meant to
happen, and is nothing to worry about.
There is one extra detail to
cover. Imagine this situation - when
using the ROM software, something terrible
happens and you manage to
make it crash. (This isn't that difficult if
you're messing about with
machine code in BBC Basic; also, there are one
or two bugs in the ROM
which can lead to crashes in certain obscure
situations.) The only way
out, as usual with a crash, is to reboot.
Obviously, in this situation
you're not going to want a snapshot to be
saved when you do
function-X! No problem. Just make sure you're holding
both shift keys
when you do function-X - i.e. while holding down both
shifts and the
function key, press X - and no snapshot will be saved. So
the next
time you do `runrom', your previous data will still be
intact.
Now you know how to switch between ZCN and the ROM
software, you may
be wondering how useful this really is without the ability
to copy
files between the two. That's where `rrxfer' comes in.
***
About `rrxfer'
`rrxfer' lets you copy files to/from a `runrom.ram'
snapshot file, and
thus to effectively copy files to/from your ROM
software setup.
Rrxfer uses an 80-column-friendly layout and no
inverse video if the
console output is going to the serial port or
printer.
**** How to use it
The program is relatively
straightforward to use. You start it up with
plain `rrxfer', then when the
menu line comes up (it'll take a little
while as it has to load most of
the snapshot first), press one of
these keys:
- `r' to list the
ROM files (i.e. the files in the snapshot). Files in
both the ROM's
`upper' and `lower' memory areas are listed.
- `z' to list the ZCN
files (i.e. the files in the current
drive/user). I'm afraid there's no
way to transfer files to/from a
different drive or user area than the one
the snapshot is in. (You can
probably get around this, though, by copying
files or using `umv'
before/after running rrxfer, as appropriate.)
-
`g' to get a file - to copy a ROM file to ZCN. Note that any
existing ZCN
file with the same name will be overwritten. The filename
you type must
exactly match the ROM file's name - case is significant
in ROM filenames.
The copy made is automatically given a reasonable
ZCN name; non-printable
ASCII chars, spaces, colons, asterisks and
question marks are all
converted to underscores. If you choose `g'
then change your mind, just
type in an empty filename (that is, just
press enter) to abort.
If
the ROM file isn't found, or there isn't enough room on the ZCN
drive to
write the copy, you'll get an error message saying so.
- `p' to put
a file - to copy a ZCN file to the ROM's file area. Note
that any existing
ROM file with the same name will be overwritten
(more precisely, the
existing file is deleted first, whether in upper
or lower memory). The
copy is always written in lower memory. (Again,
you can enter an empty
filename to abort.) The copy made is given a
ROM filename which matches
how you typed the ZCN file's name, which
means you have a degree of
control over the ROM file's name.
Here's an example of what that
means - say you have a file `foo.txt'.
If you type the name as `foo.txt',
the ROM file written is `foo.txt'.
Simple enough. But you could also type
it as `Foo.txt', as that still
refers to the same ZCN file, and the ROM
file will then be called
that. (As I mentioned above, case is significant
for ROM files.)
`FOO.TXT', `fOo.TxT', and `foo .txt' are other possibilities.
If the NC100's
real-time clock has been set (either via the ROM or
with ZCN's `timeset'),
the file is written with the current time/date.
If the clock isn't set,
however, they're written with a `zero'
time/date. The ROM interprets this
as midnight on "90-00-00" [sic].
If the ZCN file isn't
found, or there isn't enough room in the
snapshot's lower memory to write
the copy, you'll get an error message
saying so.
- finally, `q'
quits rrxfer. This may take a little while if you wrote
any files to the
lower memory (i.e. used `put'), as the lower memory
part of the snapshot
has to be rewritten.
The menu line lists these keys with a (very)
brief description of what
they do.
**** Problems
There's
one main problem when transferring files between the ROM
software and ZCN
- the ROM software stores file sizes exactly, while
ZCN (being CP/M-like)
only stores them to the nearest 128-byte
`record'.
For file
tranfers in the ROM -> ZCN direction, this is usually not a
problem.
Rrxfer always makes sure an extra ^Z is added to end of any
files
transferred, so text files are ok. (This can cause some
difficulties for
binary files assumed to be of a given size though -
screen dumps are
probably the main example, and how to deal with those
is covered in the
`Hints and tips' section below.)
The problem is in the ZCN -> ROM
direction. Now, if you think about
it, this doesn't seem like it should be
a problem for the ROM stuff -
XMODEM file transfers work with 128-byte
records too, and it has no
problems dealing with those! Unfortunately, it
seems to be the XMODEM
receive routine which deals with them (probably by
stripping trailing
^Z's), rather than being some general capacity of the
file I/O.
This means that we need to check each of the ROM
software's programs
in turn to see how it copes with it. Now, the only
ones with which you
can get at files written by rrxfer are the word
processor and BBC
Basic. The word processor shows any trailing ^Z's
literally, as a
series of little right-arrows. These are then easily
deleted. As for
BBC Basic, it seems to simply ignore junk at the end of
its Basic
files. If you *EXEC a file, it'll leave right-arrows on the
screen,
but as with the word processor these are easy enough to delete
(in
Basic pressing Stop is probably easiest). Note also that BBC Basic can
be
run natively on ZCN (and is 10% faster), so running it under the
ROM
software probably isn't that attractive anyway.
Text files written
by some CP/M programs may cause more problems than
others. For example,
since you need only one ^Z to end a CP/M text
file, some programs only
write one, and don't worry about whatever
junk may be in the rest of the
record. If you have this problem, and
the junk causes difficulties,
there's an easy solution - just load the
file up into ZDE and save it
before transferring with rrxfer. (ZDE
always fills up the remainder of the
last record with ^Z's. By the
way, it'll prompt you because the file is
unchanged - just press `Y'.)
**** An example session
Here's
an example of an rrxfer session:
rus@amnesia:/b/0>rrxfer
Reading
lower memory from snapshot...
[R]OM files, [Z]CN files, [G]et (ROM->ZCN), [P]ut
(ZCN->ROM), [Q]uit
ADDRESS BOOK
1k foobar 1k
new2 1k new6 1k
autoexec.sub
1k HELLO.BAS 1k
new3 1k new7 1k
COPY.BAS
1k hello.bas 1k
new4 1k sw.txt 2k
FILLER
9k new1 1k
new5 1k TRY.BAS 1k
36k free in
lower memory
[R]OM files, [Z]CN
files, [G]et (ROM->ZCN), [P]ut (ZCN->ROM), [Q]uit
radfreq.txt 1k
runrom.ram 64k sw.txt 2k
13k free
on drive
[R]OM files, [Z]CN files,
[G]et (ROM->ZCN), [P]ut (ZCN->ROM), [Q]uit
Get which ROM file?
hello.bas
File copied OK.
[R]OM files, [Z]CN files, [G]et (ROM->ZCN), [P]ut
(ZCN->ROM), [Q]uit
Get which ROM file? flurgle
Error writing ZCN
file! (ROM file not found, or ZCN disk full)
[R]OM files, [Z]CN files, [G]et (ROM->ZCN), [P]ut
(ZCN->ROM), [Q]uit
Put which ZCN file? radfreq.txt
File copied
OK.
[R]OM files, [Z]CN files,
[G]et (ROM->ZCN), [P]ut (ZCN->ROM), [Q]uit
Put which ZCN file?
wibble
Error writing file! (ZCN file not found, or not enough low
memory)
[R]OM files, [Z]CN files,
[G]et (ROM->ZCN), [P]ut (ZCN->ROM), [Q]uit
ADDRESS BOOK 1k
HELLO.BAS 1k new4 1k sw.txt 2k
autoexec.sub
1k hello.bas 1k
new5 1k TRY.BAS 1k
COPY.BAS
1k new1 1k
new6 1k
FILLER 9k
new2 1k new7 1k
foobar
1k new3 1k
radfreq.txt 1k
35k free in lower memory
[R]OM files, [Z]CN files, [G]et
(ROM->ZCN), [P]ut (ZCN->ROM), [Q]uit
hello.bas 1k
radfreq.txt 1k runrom.ram 64k sw.txt 2k
12k free on drive
[R]OM files, [Z]CN files, [G]et (ROM->ZCN), [P]ut
(ZCN->ROM), [Q]uit
Writing lower memory to snapshot...
done.
****
Bugs
There's one bug in rrxfer that I'm aware of:
- You
can't `put' an address book (due to the filename required). This
probably
isn't that big a deal, as address books are in a funny format
anyway.
***
Hints and tips
`runrom.ram' is just a normal file. If you make a
backup of this file,
you're backing up your ROM software setup and all the
files it has in
memory. Backing up all your files has rarely been *this*
easy... :-)
Equally, because it's a normal file, you can save space
if (like me)
you don't use the ROM software much by compressing the
snapshot with
pmarc (using something like `pmarc snap runrom.ram'). You'll
have to
decompress it again (with pmext) before using `runrom', of course,
but
it could save you quite a bit of disk space in the meantime.
ROM
software screen dumps can't be viewed as-is on ZCN, because rrxfer
adds an
extra record to the ZCN copy to allow for the ^Z it always
adds. (This
means that trying to view it the usual `get f000' way will
crash the
machine!) So the full sequence for getting a ROM s/w screen
dump and
loading it on ZCN goes like this:
- Make sure you have at least 9k
free on the ZCN drive with
`runrom.ram' on.
- On ZCN, do `runrom' to start the ROM
stuff.
- Make sure there's at least 4608 bytes free in the upper
memory.
- Do whatever it is you need to, to get the screen right for the
dump.
- Do Ctrl-Shift-S. This saves `s.a' and `s.b'.
- Do Function-X
to return to ZCN.
- Start up rrxfer.
- Get `s.b', and quit. (`s.a'
isn't of interest.)
- Do `get 100 s.b', then `save 16 dump'.
- `get
f000 dump' now loads the screen dump.
- Delete `s.b' if you want, you
don't need it any more.
** Command Prompt
When ZCN
is waiting for you to issue a command, it gives a short
prompt ending in
`>'. This prompt tells you which drive is the default
drive; the drive
which files are assumed to be on unless you
explicitly specify
another.
If drive A is current the prompt would normally be `A>'.
This may not
always be the case however - there may be a number or `*'
displayed
between the drive letter and the `>'. See `User Numbers' for
more
details.
If you like, you can redefine the prompt ZCN uses
to suit your own
tastes. See the description of the `%' command (listed
as
`%prompt_string') in the `Internal Commands' section for details.
**
Wildcards
Wildcards in ZCN (and CP/M, and even MS-DOS) have a
curious quirk that
you may not be aware of. When you specify part of a
filename or
extension then use a wildcard, it matches even files that have
no more
characters after the part you specified.
This is fine
for wildcards like `foo*.txt', which matches `foo.txt',
`foo2.txt' and
`foobar.txt'. Where it gets weird is for `foo?.txt',
which obviously
matches `foo2.txt' but (perhaps unexpectedly) also
matches `foo.txt'! The
reason for this is that the file isn't really
called `foo.txt' as far as
the system is concerned; it sees it as
`foo_____txt' (I'm using
underscores to represent spaces for clarity).
The wildcard `foo?.txt', or
`foo?____txt', matches this as the `?' by
definition matches any
character.
Rational or not, having `foo?.txt' match `foo.txt' is
bound to confuse
anyone who's used to Unix, where it wouldn't match, and
might even
confuse some MS-DOS or CP/M users who haven't noticed it before.
I
thought it was a bug the first time I noticed it. :-)
**
The Keyboard
The NC100's keyboard is, shall we say, a little odd.
Certainly some
keys are in the `wrong' place.
The way ZCN fixes
this and maps the non-obvious keys is shown below:
Key Acts
like ASCII code Reason
--- --------- ---------- ------
Function Control <none> Nice big key
Stop Escape 27 In the right place
<-Del Delete 127 In the right place
Del-> ^G 7 WordStar-like
Menu ` 96 No real backquote key
Cursor Up ^E 5 WordStar-like
Cursor Left ^S 19 WordStar-like
Cursor Right ^D 4 WordStar-like
Cursor Down ^X 24 WordStar-like
The
`symbol' key acts as a Meta key - it sets bit 7 of any key
pressed. (PC
folks should think of it as analogous to `Alt', but
different.)
Ctrl+Space
returns ASCII 0 (i.e. NUL). Note that this may not be sent
by some
terminal programs (though QTERM seems to be ok). The built-in
command
`sertest' does send it, so you could always use that.
It is possible
to make the `Caps Lock' key act like a control key, if
you like that - see
`CAPSCTRL' in the `Internal Commands' section for
details.
You
cannot stop a program's output by using ^S. However, you can pause
a
program's output at any time by holding both the `control' and
`symbol'
keys simultaneously. The output starts again when you let go.
You
can get a dump of the current screen at any time by pressing
Control-LeftShift-S
(you must use the real Control key for this). The
middle 60 pixel lines of
the screen memory are simply saved to the
file `screen.dmp', including the
`wasted' bytes, giving 64 bytes per
line. The top two and the last-but-one
pixel lines are used as
temporary storage during the screen dump, so don't
worry if they
appear corrupted for a second or two. You'll get a screen flash
(or
beep) when the dump has been written, and you can then carry on
with
whatever you were doing.
On a Unix box with the `netpbm'
or `pbmplus' utilities installed, you
can convert a `screen.dmp' file to a
PBM file with something like this:
(echo P4;echo 512 60;cat
screen.dmp) | pnmcut 0 0 480 60 >foo.pbm
You can then convert to
other formats with things like ppmtogif, etc.
** The
Screen
The NC100's screen has a pixel resolution of 480x64. ZCN
provides a
character screen of 120x10 with 4x6 character cells, leaving
two pixel
lines at the top and bottom free. The leftmost 32 pixels on the
bottom
pixel line are used by the `drive lights' (see `Logical
Drives').
** The Terminal Driver
*** Control
Codes
Programs often have patch areas (or installation programs)
which need
to know which sequences to send to do cursor movement, etc. For
that
reason, and for programmers of course :-), the console control
codes
are listed here. Those listed as `(reserved)' have no effect.
Code Hex Dec Description
^@ 00
0 (ignored)
^A 01
1 clear screen, home cursor
^B 02
2 bold off
^C 03
3 cursor on
^D 04
4 cursor off
^E 05
5 bold on
^F 06
6 clear to end of screen
^G 07
7 bell (by default, this flashes the
screen)
^H 08 8 backspace
^I 09
9 tab (8 chars wide, i.e.
1,9,17,25,33,...)
^J 0A 10 linefeed
^K 0B 11 (reserved)
^L 0C 12 (ignored)
^M 0D 13 carriage return
^N 0E 14 italics ("underline") off
^O 0F 15 italics ("underline") on
^P 10 16 move cursor - 10h, then 20h+y, then 20h+x
(see below)
^Q 11 17 (ignored)
^R 12 18 insert line
^S 13 19 (ignored)
^T 14 20 delete line
^U 15 21 scroll up
^V 16 22 (reserved)
^W 17 23 scroll down
^X 18 24 true video (i.e. turn off reverse
video)
^Y 19 25 reverse
video
^Z 1A 26 move cursor right one
column
^[ 1B 27 VT52
escape code prefix (see below)
^\ 1C 28 (reserved)
^] 1D 29 move cursor up one line
^^ 1E 30 home cursor without clearing screen
^_ 1F 31 clear to end of line
In pre-v1.2
versions of ZCN, the y location for ^P was 46h+y. This is
still supported,
but is deprecated and may not be supported by a
future version of ZCN -
you should switch to using 20h+y instead.
Some VT52-like escape
codes are supported, mostly so that Mallard
Basic will work comfortably on
ZCN. These all start with ^[ (ESC).
Those supported are ESC-D to backspace,
ESC-C to move the cursor right
one column, and ESC-K to clear to the end
of the current line. (In
fact, at the moment, ESC followed by anything
other than `D' or `C'
acts like ESC-K.) No other VT52 escape codes are
implemented.
However, one extra feature of ESC is that it
counteracts any CR/LF
output immediately after. So if you're writing a
program where you
want to avoid the CR/LF which ZCN normally outputs when
a program
exits, you can easily do this by just outputting an ESC before
you
exit. (Be warned that this doesn't work on ZCN versions earlier
than
v1.2, though, and obviously it won't work if console output is
redirected
to the serial port.)
While I'm on the subject, here's another brief
aside for programmery
types. :-) If for some reason you need to know the
current cursor
location, you can use this bit of Z80 to read it (it reads
the x
position into B and the y pos. into C):
ld ix,(1)
ld b,(ix-5)
ld
c,(ix-4)
Using this is a Bad Idea in general, and it won't work on
old
(pre-v1.1) versions of ZCN, but it's there if you need it.
***
Unix termcap/terminfo entries
Skip this if you don't use any version
of Unix.
Since the NC100 can be used as a convenient and portable
terminal to
Unix systems, it's a good idea to have a termcap/terminfo
entry to
hand so you can run full-screen programs on it. Note that they
will
have to be able to cope with using such a small number of lines
-
Emacs and Nethack can, for example (though Nethack isn't too happy
about
it).
Here's a termcap entry for an NC100 running ZCN:
zcn|amstrad
nc100 running zcn:\
:cl=^A:co#120:li#10:cm=^P%+
%+ :le=^H:bs:am:sf=^U:sb=^W:sr=^W:\
:ce=^_:so=^Y:mr=^Y:se=^X:us=^O:ue=^N:me=^X^N:al=^R:dl=^T:it#8:\
:cr=^M:do=^J:nl=^J:ms:vi=^D:ve=^C:ta=^I:up=^]:nd=^Z:cd=^F:
However,
termcap is rapidly falling into disuse these days, so most
people will
probably want a terminfo entry instead. Here's the one I
use:
zcn|amstrad
nc100 running zcn,
cols#120,
lines#10, am, clear=^A, cr=^M, bel=^G,
cub1=^H,
cuf1=^Z, cuu1=^], cud1=^J, ind=^U, ri=^W,
cup=^P%p1%'
'%+%c%p2%' '%+%c, home=^^,
el=^_,
ed=^F, il1=^R, dl1=^T,
smso=^Y,
rmso=^X, smul=^O, rmul=^N, bold=^E, rev=^Y,
sgr0=^B^N^X, msgr, civis=^D, cnorm=^C,
ht=^I, it#8, km,
You may have
problems using Emacs, for a couple of reasons. The common
problem with
XON/XOFF flow control doesn't apply since ZCN avoids it
like the plague;
instead, there are two other problems.
Because of the way the direct
console I/O BDOS function works, some
CP/M terminal programs may not send
^@ (ASCII 0, or NUL). This'd be a
real pain when using Emacs. The simplest
solution is to use the
built-in command `sertest', which has the added
advantage of being
faster than most other terminal programs since it
really is very
simple indeed, and can call functions in ZCN directly
rather than
having to use the BDOS entry point. (My tests indicate that
`sertest'
is nearly twice as fast as QTERM.)
You may also have
problems getting the `Symbol' key to work as a Meta
key. There shouldn't
be a problem if Emacs is using terminfo - the
terminfo entry above
specifies `km' which should get it working
properly. (Certainly that works
for me.) But if for whatever reason it
doesn't work, you might want to try
putting this in your ~/.emacs file
to fix it:
(if (equal (getenv "TERM")
"nc100")
(set-input-mode nil nil t))
(If
that doesn't work, it could be down to the stty settings `cs8'
and/or
`-istrip' not being set.)
** Rebooting
There are
two main rebooting possiblities available when switching on
the NC100
running ZCN. They are:
1. Cold boot of the ROM software. Do this by
holding down Function,
Stop and `<-Del' while turning the computer on.
You should only need
to do this if a program crashes, etc. You should then
use Function-X
to boot ZCN from your bootable card.
2. Cold
boot of ZCN. (This isn't fully `cold', as it just restarts the
copy of ZCN
in memory.) Do this by holding down both shift keys while
turning the
computer on. Use this to clear any random wedgitude that
may have
occurred, or to test your `autoexec.sub' (see later).
You can also,
from the ZCN command-line, use `cboot' to do a fully
`cold' boot of ZCN
from the memory card.
** CP/M Compatibility
ZCN
aims at close CP/M compatibility - enough to get the majority of
freely
available programs running. Most programs work. This section
describes
what facilities are provided, and lists programs which are
known to not
work under ZCN.
*** BDOS Functions
The following BDOS
functions are provided, and are believed to be
working correctly:
0,
1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19,
20, 21,
22, 23, 24, 25, 26, 29, 32, 33, 34, 36, 37.
These ones work but have
known problems:
35 - gives incorrect results for files with
holes.
40 - the same as function 34, i.e. it doesn't actually do the zero
fill.
These not done:
27,
28, 31.
There are some additional (ZCN-specific) functions;
some are mentioned
later. Full descriptions are given in `zcnprog.txt',
but the ultimate
reference is `zcnfunc.z' in the `src' directory. So, in
other words,
RTFS. :-)
*** BIOS Functions
ZCN
has a rather sparse BIOS jumptable which omits all the
disk-related
functions. I am very reluctant to add them as it would
take a fair chunk
of memory to implement. (ZCN's internals work
differently to CP/M, which
would make writing them tricky, too.)
Still, the existing BIOS is enough
for most programs.
*** Zero Page etc.
ZCN uses the
memory at addresses 0000h-00FFh as follows:
address(es) description
00h-02h jump to warm boot routine
03h ZCN does not implement CP/M's IOBYTE;
instead, this
byte
contains the contents of 80h when the last
program finished (this lets you check the exit
status
of a Hitech C
program)
04h-04h unused
(but set to zero by warm boot)
05h-07h jump
to BDOS
08h-2Fh usable by
user programs (as on CP/M)
30h-32h jump
to NMI poweroff routine (see note 1)
33h-37h part of NMI poweroff routine
38h-3Ah unused jump to maskable interrupt
routine (see note 2);
usable
by user programs
3Bh-5Bh reserved
(actually unused)
5Ch-6Bh initialised
part of FCB 1 (see note 1)
6Ch-7Bh initialised
part of FCB 2
7Ch-7Fh remainder
of FCB 1
80h size of command
tail at 0081h
81h-FFh command
tail (command line minus command name)
Note to programmers: Please
do not *depend* on any of the `unused'
sections above being available for
your use (unless your program is
taking over control of the machine
completely).
Note 1:
Pressing the on/off switch when the
NC100 is on causes a non-maskable
interrupt - that is, it disables
interrupts, puts pc on the stack, and
jumps to 0066h. This is the 2nd
char. of the filename extension in FCB
1 - there's some ad hackery in ZCN
to try and deal with the problems
this causes. As far as I know it's
successful, except that sometimes
you will see a filename printed with the
2nd char. of the extension
appearing as a lowercase `w'. I don't think
there's anything I can do
about that. Anyway, the value that's actually
stored at 0066h is F7h -
`rst 30h'. The maskable interrupt routine and
BDOS both fix this byte
if it's been changed.
Note
2:
The maskable interrupt routine is responsible for the
following:
- Fixing 0066h if it's been changed (see note 1 for
details).
- Keyboard input/buffering.
- Serial port
input/buffering.
- Auto poweroff timeout and the actual auto poweroff
itself.
- Updating `drive lights'.
See `Tight Interrupts' (in
the hacker's guide section) for what
happens when minimal interrupts are
in use.
The reason there's still a jump to the interrupt handler at
0038h is
in case there's some program out there which explicitly selects
IM1
for some reason and expects ZCN to cope with this.
Note
3:
Although 0008h-002Fh is available for use by user programs, ZCN
puts a
jump instruction at 0028h (which it's ok to overwrite). The jump
at
0028h is to allow ZCN's internal commands to use `rst 28h' as an
indirect
call to a inline string output routine, thus saving a few
bytes. It's not
a good idea to call this yourself - it doesn't exist
on other CP/Ms, and
didn't even exist on ZCN until v1.1. However, if
you're really determined
to ignore my advice on this :-), look at
`ilprint' in `src/misc.z' for how
to call it.
Unusually for a CP/M system, the BDOS entry point
(the address at
0006h) is the very start of system code; all addresses
from that one
upwards are used by ZCN, except for the screen memory which
starts at
F000h. Programs which leave space for a CCP will still work, as
will
those which don't - all parts of ZCN interact directly with
each
other, and should never be overwritten. Note that this
monolithic
approach means you will presumably never be able to run any
version of
ZCPR on a ZCN system unless someone's prepared to hack up
both
programs.
*** Non-working Programs
Essentially,
programs which need disk BIOS functions don't work. This
included (the
last time I tested) superdir, `dr24.com', and zx 3.1.
Another
possible problem is the whole 66h thing (more on this
elsewhere) - usually
this just results in the odd spurious `w' being
printed :-), but it can
cause real problems with some odd programs.
The ones I've found so far
that are affected are nulu and kermit.
** Tips on using
certain programs with ZCN
*** Hitech C
**** Getting
Hitech C
Native CP/M Hitech C is free. It's very slow and
memory/disk hungry
and Z80-specific and the optimisation is quite awful, but
it's very
ANSI-compatible (well, for a CP/M C compiler ;-)) and excellent
for
compiling short (<2000 line) C programs. It's available from
oak.oakland.edu
in /pub/cpm/hitech-c, and probably also available from
any decent CP/M PD
distributor.
**** How to run it on ZCN
Programs compiled
with Hitech C (which fit in memory!) work on ZCN
just fine, though any use
of any exec() or system() call will fail. A
few of the programs in the
`support' dir were compiled with Hitech C
using the excellent `cpm' CP/M
emulator on my Linux box.
As for the compiler, things are more
problematic. The compiler driver
`c.com' doesn't seem to work on ZCN for
some reason, so you have to
run the passes by hand. Even then, most of the
passes need a LOT of
memory to run. You'll need to use `bigrun' to run
them. (Be sure to
read the warnings in the `bigrun' section first!) Here's
an example
SUB file `hc.sub', designed to run on drive B: with `libc.lib'
on
drive A:, which acts as a simple replacement for `c.com':
---------------------------
cut here ----------------------------
submit hc.sub *
defrag -q
b:
'cpp:
cpp -DCPM -Dz80 -I $1 hctemp1
ifnpeek 3 0 quitsub era
hctemp?
'p1:
bigrun p1 hctemp1 hctemp2 hctemp3
ifnpeek 3 0
quitsub era hctemp?
era hctemp3
'cgen:
bigrun cgen hctemp2 hctemp1
ifnpeek
3 0 quitsub era hctemp?
era hctemp2
'zas:
bigrun zas -N
hctemp1
ifnpeek 3 0 quitsub ; era hctemp?;era hctemp1.obj
era
hctemp1
'link:
link -Z -C100H -o$1om crtcpm.obj hctemp1.obj $2 $3 $4
a:libc.lib
ifnpeek 3 0 quitsub ; era hctemp1.obj;era $1om
era
hctemp1.obj
"compiled ok.
--------------------------- cut here
----------------------------
All the `ifnpeek's make sure it quits
and cleans up temporary files if
any pass fails. The last two
`ifnpeek..quitsub' commands need `semi'
to be on your machine as `;.com' -
failing that, you could replace
them respectively with `ifnpeek 3 0
quitsub era hctemp?' and `ifnpeek
3 0 quitsub era $1om' at the cost of
possibly leaving a hctemp1.obj
file lying around.
For the SUB
file to work, you'll also need much of Hitech C on your
machine
(unsurprisingly :-)). Specifically, you need `cgen.com',
`cpp.com',
`crtcpm.obj', `link.com', `p1.com', and `zas.com'. You'll
also need
`libc.lib' on drive A:, as I mentioned above, and you'll
need any headers
you want to use - certainly you'll want `stdio.h',
and probably `stdlib.h'
and `string.h'. It may be a good idea to make
a .pma archive of all the
header files, so you can get at any you
need. (Such an archive is 9k
rather than the 30k the headers take
uncompressed.)
To compile
with floating-point support, you'll also need `libf.lib',
and will need to
compile with something like `hc foo.c libf.lib'.
You need an awful
lot of disk space to run Hitech C. You can't
realistically run it on
anything less than a 512k card, and a 1024k
card might be preferable if
you want to have enough disk space free to
do other things too. When I
last tried it on my 512k card, on the A:
drive I had `headers.pma' and
`libc.lib' taking up 69k, and on B: I
had the various required COM files
and headers taking up roughly 190k.
Total disk space required, 259k - and
that didn't include the 32k
needed for `bigrun' to work, nor did it
include the space needed for
Hitech C's temporary files. (Which can be 30
or 40k.) So it
effectively took about 330k.
Oh, and another
point - as I've said, it's not exactly fast. On ZCN,
it takes 50 seconds
to compile a "hello world" program!
Personally, I dumped
it and use `bbcbas' instead when I want to
program on the NC100 itself.
It's about 50 times smaller ;-), and
there's no waiting for things to
compile.
**** Realistic System Requirements for Hitech C
For
serious use, I personally wouldn't run the compiler itself on a
CP/M box
of less than around 20MHz clock speed, 60k TPA, 1 Mb disk -
to run it with
less than that you'd have to be pretty patient. A good
CP/M/Z80 emulator
on a 486 or better is a perfect environment.
(Consider `zsim' for MS-DOS,
`cpm' for Linux and presumably other
386-based Unix; others I'm not sure
of (`cpm' uses 386 assembly to get
the high speed, and isn't
CPU-portable). Some sort of emulation is
probably your only option - I
don't know of any *real* CP/M system
which could run it at a reasonable
speed.)
**** Bugs in the library
There's one bug I've
noticed in Hitech C's libc library - fgets() will
not read lines longer
than the buffer size correctly. I suspect it's
implemented as gets() from
a stream, which is not ANSI at all. This
may not worry you, but if it
does, here's something you could put
right at the end of stdio.h as a
workaround (minus the `cut' lines of
course :-)):
---------------------------
cut here ----------------------------
char *myfgets(char *s,int size,FILE
*stream)
{
char *ptr=s;
int f,c;
for(f=0;f<size-1;f++)
{
c=fgetc(stream);
if(c==EOF) break;
*ptr++=c;
if(c=='\n')
break;
}
*ptr=0;
if(c==EOF) return(NULL);
return(s);
}
#define
fgets myfgets
--------------------------- cut here
----------------------------
I think this fits the ANSI standard.
Certainly it's a lot better than
the Hitech C implementation, 'cos it
works. :-)
If you're feeling adventurous, you could fix the library
itself (not
too hard if you use `libr'), but this is left as an exercise
for the
reader. :-)
*** Mallard Basic
Mallard
Basic is, if nothing else, the first commercial program I've
got to run
under ZCN. (Though it's a bit painful compared to BBC
Basic. :-))
I
added a couple of extra control codes to the terminal driver to cope
with
MB's expectation of a VT52 - namely, ESC-C, ESC-D and ESC-K. (I'm
surprised
it uses them, really. You can implement all it needs with
straight ascii
codes like BS and CR. It'd be slower, but would work on
everything.)
If
you want basic to use the full width of the screen and correctly
wrap long
lines, do `width 120,120' after starting up.
My +3 CP/M manual only
describes the keys MB uses in terms of the
unusual +3 keyboard - in case
the PCW manual does something similar,
I'll describe what the keys are on
the NC100 here:
Key
Function
^A
Move back along line being written/edited
^F Move forward along line
^_ Move up on multi-line line (if you see
what I mean)
^^ Move down on
multi-line line
<-Del Delete
char to left of cursor
^G
Delete char under cursor (NB: Del-> also sends ^G)
^W
<char> Moves forward to specified character
^S <char> Delete
all between cursor and specified character
^S enter To delete to end of line
^I Toggle between insert and overstrike
(NB: Tab also sends ^I)
Stop
Abandon changes to program line
Basic (my copy at least) only
has around 16k available on startup.
This is unfortunate, but there isn't
much I can do about that with
only 64k total! (Note that MB *does not*
work with `bigrun', it
crashes the machine, so don't even think about
trying that!)
*** QTERM
Assuming you have QTERM
4.3f patched for ZCN (there's a copy in the
`support' directory), an easy
way to take backups is using YMODEM
batch transfers.
For
example, when logged into my Linux box I would run `rb' - a YMODEM
batch
receive program - then do ^\ s to send, then `xy *.*' to send
all the
files on the current drive. At 19200 baud on a full (256k)
drive this
takes between 3 and 5 minutes.
You may want to do `user 255' before
running QTERM if you have files
on the drive in other user areas - this
will make sure you backup all
files in all user areas. Be sure to see
`User Numbers' for more about
user area 255, as there are some potential
problems associated with
using it, particularly if two different files
exist on the same drive
in different user areas with the same
filename.
** Logical Drives
Cards of 256k or less
have only one drive, drive A:. 512k cards have
two - A: and B:. 1024k
cards, the largest allowed, have four, A:, B:,
C: and D:. These logical
drives are completely independent of one
another, but drive A: must be
formatted for drives B:, C: and D: to be
readable.
You make a
drive current by typing its name, e.g. `b:'.
** User
Numbers
[Note that I use `user', `user number' and `user area'
pretty much
interchangeably. Sorry if this makes it sound more confusing
than it
need be. :-)]
ZCN supports CP/M user numbers 0 to 15.
You can change user numbers
with the `user' command, but not (yet) in the
`0a:', `a0:' or `0:'
manner. This gives you a little more than a flat
filesystem (or disk);
you might describe it as a segmented filesystem, but
that sounds like
the partitioning scheme used on PCs, which it definitely
isn't
anything like. It's more like having 16 different directories - all
at
the same level - rather than one, and having them numbered rather than
named.
0 is the default `directory', or user area.
For the uninitiated -
user numbers were in CP/M to allow different
users of a CP/M machine to
keep their files separate. The way it
worked meant that they would have to
keep not just data files, but
also any programs they wanted to run, in
that single user area.
It gets worse; the way the feature was used
in practice meant that you
had a single user wanting to move files across
user areas, run
programs from other user areas, etc.
I'll admit
now that ZCN doesn't handle user areas very well at all.
However, this
section tells you what it does different from generic
CP/M.
(Note
that user numbers are separate from drives - i.e. if you do
`a:', `user
1', `dir b:' it will show all files in user area 1 of
drive B:.)
***
Prompt
The `A>'-style prompt is actually only used in the default
user area
0. In user areas 1 to 15, the user area is printed before the
`>', as
in `A1>'. In user area 255, it becomes `A*>', with the
`*' meant to
indicate the wildcard-like action of user 255 (see below for
more on
this user area).
*** Execution
When running
a COM or SUB file, ZCN tries the following things:
1. Try
current/specified drive and current user.
2. Try current/specified drive
and user 0.
3. If no drive was specified, try drive A: and user 0.
This
means that user area 0 (and especially user 0 on A:, if you're
using a
card larger than 256k) is a good place to put programs.
*** User
Area 255
In addition to the usual 0-15, ZCN allows you to use user
area 255.
This isn't a user area as such, but acts like all the files on
the
drive are in the current user.
User area 255 is mostly
read-only, though it does allow `umv' (see
below), and file deletion. The
reasoning behind it being read-only is
that files in different user areas
are allowed to have the same name.
If the file is written to, it's not
clear which file should be changed
or added to. Having two files with the
same name also causes problems
when reading from user area 255. You would
get (effectively)
randomly-chosen 16k chunks from any files with the same
name.
In general, you should only read files in user area 255 if
they only
appear in the directory listing once. The `ls' program, which
you
should probably be using in preference to `dir' anyway, will report
`***
WARNING: duplicate files found! ***' if two or more files share
the same
filename. (The warning will only appear once, no matter how
many filename
conflicts there are.)
This probably all sounds rather worrying, but
the situation's not
really that bad. If you make sure no filenames occur
more than once
across all user areas, you have absolutely nothing to worry
about.
Even if you don't, you just have to be sure to not read the
offending
files from user area 255. (You couldn't do this and get meaningful
results
in any case - how could ZCN tell which file you're referring
to?)
***
UMV internal command
This command allows you to move files matching
a given filespec from
the current user area to another, e.g. `umv *.com 0'
would move all
COM files in the current area to user area 0. An easy way
to put all
files in user area 0 is `user 255' then `umv *.* 0'.
**
Warning about using the Serial and Parallel ports
There is no
timeout when, say, the printer is busy or serial data
cannot be sent. ZCN
will simply keep trying. To interrupt this if it
happens, I'm afraid
you'll have to do a cold boot - turn the machine
off, then hold down both
shift keys while turning it back on.
Apologies for the inconvenience.
:-(
** Using the Serial Port or Printer as the Console
Under
ZCN it's possible to use the serial port (instead of the
keyboard/screen)
for console input and/or output. To use the serial
port for console output
you should use the command `>s'. For serial
input do `<s'. To use
the serial port for both input and output, use
`|s' (that's a pipe
character, as given by shift-\, then an `s').
To redirect console
input/output back to the NC100 itself, just use
the above without the
trailing `s', e.g. use `|' (pipe) alone to
restore normality. You can also
use `<' and `>' to only restore normal
input or output
respectively.
As well as serial redirection, you can direct console
output to a
printer connected to the parallel port. This is *as well as*
output to
the screen though, so you can see what you're doing. :-) For
printer
output of this kind do `>p'. You can also use `|p', which has
the same
effect as doing `|' then `>p'. (`<p' is also accepted, but
simply does
the same as `<'.) Again, you should use `|' to return to
normal.
A brief note in case it's not obvious - redirecting to the
printer
won't have the desired effect if you're printing to a
PostScript
printer. (ZCN's console output doesn't make much sense at the
best of
times, but it makes far less sense as a PostScript program,
trust
me...) Then again, if you're using a PS printer with an NC100
you're
probably completely insane, so maybe it won't matter to you.
:-)
Using the `semi' external command described later, a crude
but
effective way to print a text file is:
semi >p; cat file.txt; |
(The
`semi' should be replaced with a semicolon if you rename the
command as I
do; see the description of `semi' for details.)
ZCN makes the
following demands of a terminal (or terminal emulator,
or printer):
-
It must use ASCII encoding for characters 32-126 inclusive.
- When a CR
(13) is sent, it must move the cursor to the leftmost
column.
- When
an LF (10) is sent, it must move the cursor to the next line.
Preferably
it should do this without moving the cursor to the leftmost
column, but
ZCN itself does not require this.
- For the `buffered line input' function
to work (as used for the
command-line and by many programs), BS (8) must
move the cursor back
one character non-destructively and space (32) must
erase any
character previously shown.
These are pretty minimal
requirements. However, the last requirement
means that a printer can't
properly implement the BS/space/BS ZCN uses
to backspace destructively -
usually the new characters will simply be
printed over the old.
You
should also note that the `cls' internal command works by simply
clearing
the screen memory and homing the cursor, so it can't clear
the screen of a
terminal.
** The Command Shell (CCP)
[CCP really
stands for Console Command Processor, lest you think I'm
incredibly dim or
some such... :-)]
*** Command Line Editing
The only
command line editing available is delete-previous-char, and
there is no
way to recall previous commands. Sorry.
You can abort the entered
command line without executing it by
pressing ^C.
*** Battery
level warnings
The low battery level warnings are part of the CCP -
if any of the
batteries are low, you get a warning printed before each CCP
prompt.
For example, if the main batteries are low, you get something
like:
*** Main batteries
low ***
A>
You
can keep using the NC100 under ZCN while batteries are low, but
you run
the risk of losing data etc. in memory should the battery
level get too
low.
If you do keep using the NC100 when batteries are low, you
should note
that if you need to use any of the builtin software (to reboot
from a
memory card after a crash, for example), it will demand that
you
replace the main/backup batteries (whichever is low) before
continuing.
(You could just run it off the mains adaptor for a while
instead.)
For
some sorts of batteries this may happen even if you're not using
the ROM -
what seems to happen is that the voltage goes too low for
the NC to work,
so the power flickers off, in response to which the
voltage goes up
slightly, enough for the NC to come back on (into the
ROM OS, as it had
effectively crashed). This can happen several times.
As far as I
know, the ROM software does not check for low memory card
batteries as ZCN
does. I suspect that this feature of the NC100, while
documented, was not
correctly implemented, and you should not rely on
the NC100 to report when
a memory card's battery is low. Instead, you
should replace memory card
batteries at the interval suggested by the
manufacturer (often once a
year). In my case, my card started randomly
losing data about 6 months after
I should have changed the battery.
[The documentation for my 512k
memory card says this:
The
battery condition is output from the card as a signal that some
computers can read. This signal will
indicate one of three states:-
1. Battery good.
2. Battery low, should be changed as soon as
possible. Data
maintained.
3. Battery
discharged, data LOST.
I strongly suspect that the NC100 treats
states 1 and 2 above as
`battery ok' and treats state 3 as `battery low'!
(Experimentation
seems to support this theory.)]
No battery
level warnings occur at any other time than when displaying
the CCP
prompt. If you have been using a program continuously for a
long time and
suspect that batteries may be low, you should quit to
the CCP to
check.
You can disable battery warning messages by doing `batwarn
0'.
By the way, the tests I've tried suggest that rechargeable
batteries
give roughly 8 hours use between rechargings (possibly more,
depending
on the type). It's more difficult to tell how long you generally
have
between the `batteries low' warning and effectively dead
batteries,
but it seems to be something like 30 minutes for
`conventional'
rechargeables. It's much shorter and more variable for
the
chargeable-in-two-hours kind - anything between 1 and 5 minutes.
***
Internal Commands
ZCN has several of the normal internal commands
provided by CP/M's
CCP, such as `dir'. It also provides many extra
commands which I found
useful, and modifies the behaviour of others. This
section lists the
internal commands (in alphabetical order), what they do,
and how to
use them.
Note that a few internal commands which
require args (a filename, for
example), such as `note' and `ren', will
just say "Args?" if they're
used without any.
****
!! [command args]
Jump to 100h, effectively running the previous
command again with new
arguments. You must *only* do this if you know the
command is
re-entrant, or if you like living dangerously. It can also be
used to
run a command previously loaded with `get' (see below).
****
"any text
Echo the text after the double quote (") exactly
as it appears (except
that the `$' character will terminate the line, if
it arises). This
one of the very few commands that does not have its
command tail
uppercased before it sees it (the others being ' and `%').
It's
intended for use in SUB files (see `SUB files' below).
A
variant of this command is similar but starts with a single quote
(').
This also echoes the text exactly, but omits the CCP's CR/LF
after echoing
it, meaning that the cursor stays on the same line.
****
%prompt_string
Set the CCP's prompt. (While you can use this command
anywhere, it's
really intended to be used in `autoexec.sub' so that ZCN
uses the
specified prompt all the time.) The maximum allowed prompt size
is 25
chars - if you try to specify one larger than that, it is
silently
truncated.
The text after the initial `%' is printed
verbatim apart from these
codes:
Code Translates as...
%a current
user area
%b current user area, if
non-zero (otherwise, prints nothing)
%c space
left on current drive
%d current
drive letter
%e current drive
letter in lowercase
%% a literal
percent sign
(The `%c' number takes a little time to appear, so may
not be such a
good thing to put into the prompt as you might initially
think.
Personally, I find the slight delay distracting.)
Other
two-char combinations starting with `%' don't output anything
(though you
shouldn't depend on this). A `%' right at the end of the
prompt string is
printed as a literal percent sign.
The default prompt string is
`%d%b>' (which could be defined with the
command `%%d%b>'). Here's
another example prompt string, the prompt I
use on my machine -
`rus@amnesia:/%e/%a>'. It gives a prompt not
dissimilar from the prompt
I use on my Linux box, and shows one way
you can get something which looks
a bit like a `path' into the prompt.
(MS-DOS users might like to try
`%d:\%a>' or `%d:\%b>' for a similar
effect.)
****
BATWARN <0 or 1>
Disables/re-enable low battery warnings. You
should use this like
`batwarn 0' to disable battery warnings if you
appreciate that the
main batteries are low (for example), but want to
carry on without
getting `*** Main batteries are low ***' in your face all
the time. Be
careful when doing this, because it's an inherently dangerous
thing to
do, and be sure to change the relevant batteries as soon as
possible.
**** BDOSDBUG <0 or 1>
Enable (or
disable) display of which BDOS function is being called as
it is called.
The function number is displayed in hex - for example,
`[0A]' would
indicate that the program is reading a line of text from
the console.
Enabling this output can be useful when debugging
programs. For various
reasons, functions 2 (console output) and 46
(get disk free space) are
treated slightly differently from other BDOS
functions, and as a result
are not reported on.
**** CAT filename
Display a
^Z-terminated text file from beginning to end, without
pausing. (^C
quits.)
(This means it's not a true `cat' command - that is, it
doesn't
concatenate files - but simply a synonym for `type'. Still, it's
handy
for Unix fans like me. :-))
**** CAPSCTRL <0 or
1>
Disable/enable swapping the functions of the `Caps Lock' and
`Control'
keys. (It's off by default - i.e. the keys do what they say they
do.)
This option may be useful if you like having a control key above
the
left shift key (rather than below it). That said, the `Function'
key
always acts like a control key no matter what.
Note that
this swaps the functions of the keys at quite a low level -
if you've
enabled the key-swapping, then whenever ZCN requires you to
press the
physical `Control' key (for screen dumps and for pausing
output) you will
*have* to use the `Caps Lock' key instead.
**** CBOOT
Cold
boot ZCN from the memory card. If the card is not bootable, or
there's no card
in the slot, ZCN will say "Bad crd/drv/format" rather
than
booting.
**** CD n
Set current user area to number `n',
or to number 255 if `n' is an
asterisk. If `n' is omitted, acts like `cd
0'. This alias for `user'
should make slightly more sense to MS-DOS and
Unix users, though the
flat `directory' structure in CP/M makes their `cd'
commands a poor
analogy, to be honest. Still, at least it's easier to
type, right? :-)
**** CRLF <0 or 1>
Disable (or
re-enable) the line-break (CR/LF) after a program exits.
Generally you'll
always want this on, but it can be useful to turn it
off temporarily in a
SUB file. (An easy way to get a CR/LF should you
need one after `crlf 0'
is to use `"' or `vdu 13 10'.) Just make sure
you remember to
re-enable it afterwards, or it'll all be a bit
confusing. :-)
Note
that this doesn't affect the CR/LF always output after you type
in a
command, so the effects of a `crlf 0' may not be immediately
obvious.
Doing `ver' should clarify matters.
**** CLS
This clears
the screen. (NB: this clears the entire screen, including
the top two and
bottom two pixel lines.)
**** DF
Report how much space is
free on all available drives. An example of
what the output's like: `A:=2k
B:=43k'. (The values will probably be
different for your card.) Only
drives which exist on the card are
reported on.
**** DIR
[filespec]
List the files in the current drive/user. If a filespec
is given, it
only shows files matching the filespec. The wildcards `*' and
`?' can
be used. If no file is found/matches, then the error `No
file'
results.
`dir' exists primarily for CP/M compatiblity,
and so that there's some
internal command to list files - see the `LS'
external command for how
to get a much better (sorted, and optionally with
file sizes)
directory listing.
**** DUMP filename
Give
a hex and ASCII dump of the specified file, pausing after every
128 bytes.
Bugs: if the file position is greater than 65535, it'll be
shown
incorrectly.
**** ERA (or RM) filespec
The CP/M-style
delete command. (ERASE and DELETE are not recognised.)
Delete all files
matching the filespec. Bugs: does not prompt when
deleting multiple files,
which it should really.
**** FORMAT d:
Format the given
drive. Cards of 256k or less are formatted as a
single A: drive. Cards
larger than that (512k and 1024k) are formatted
as two 256k logical drives
A:/B: or four drives A:/B:/C:/D:
respectively. On these larger cards, the
A: drive must formatted in
order to format and use any of the others. (The
logical drives are
formatted on an individual basis.) You can reformat one
of the logical
drives without harming any others.
So to fully
format a card of 256k or less, use `format a:'.
For a 512k card, do
`format a:' then `format b:'.
And for 1024k cards, do `format a:',
`format b:', `format c:', and
`format d:' in turn.
If the drive
is already formatted in ZCN format, you will be asked
whether to reformat
it. (It should if the drive is already formatted
in the ROM software's
format too, but I haven't tested this.)
**** GET hex_address
filename
Load a file in at the specified address (in hex). This is
useful for a
variety of things:
- Loading a COM file off one
card, then executing it with another in
the slot, e.g. `get 100 foo.com',
change cards, then `!!'.
- Patching a COM file after it's loaded.
You normally do this by
loading the COM file, then loading a small patch
over some part of it.
- Loading a previously saved screen dump, e.g.
`get f080 screen.dmp'.
This command makes it easy to crash the
machine if you don't know what
you're doing, so be careful, and check your
typing. If you miss out
the `1' in `get 100 foo.com', you'll soon know
about it. :-)
**** IFNPEEK addr val command [args]
If
byte at (hex) `addr' *does not* equal (hex) `val', run command,
otherwise
do nothing. This is primarily of use in SUB files.
See `ifpeek'
below for details.
**** IFPEEK addr val command [args]
If
byte at (hex) `addr' equals (hex) `val', run command, otherwise do
nothing.
This is primarily of use in SUB files.
Note that using a print
command (' or ") will result in all-caps text,
since ZCN didn't see
the command until after the `ifpeek' took place.
This is unfortunate, but
there's nothing I can do about it. (It also
applies to the `%'
prompt-setting command, but you're much less likely
to want to use that as
the command in an `ifpeek'.)
To abort a SUB file if some command
goes wrong, use `ifpeek ...
quitsub'. Obviously there has to be a byte in
memory which indicates
if the command worked or not!
To check
the value of 80h after the last command finished, use 3 as
the `addr'.
This is primarily intended to be used to check the exit
status of programs
compiled with Hitech C; however, there's no reason
you couldn't use it to
return an exit status from your own programs.
If you want to check if a
Hitech C command returned a non-zero exit
status - for C programs this
usually means it failed somehow - then
use ifnpeek instead, like this:
`ifnpeek 3 0 ...'.
The only command which does not have 80h copied
after it exits is
`rem'. (The same applies to a blank command-line, of
course, but
that's not really a command as such.) *ALL* other commands
and
programs have it copied when they exit, whether they change it or
not.
**** K3
Show how many K are free. :-) In other
words, show the amount of
memory available for running programs in, or the
transient program
area (TPA) as CP/M calls it. At the time of writing,
this will be 46k.
For any techies out there who may be interested,
the number given is
int((bdos_address-512)/1024). 256 of the 512
subtracted is to discount
the zero page, and the other 256 is to allow for
stack space. So it's
a realistic estimate of the maximum program
size.
**** MEMDUMP address
Show 128 bytes of memory, in
hex and ascii, from the address given.
The address should be given in
hex.
I consider this command to eliminate the need for a `peek'
command,
which you might otherwise expect as a counterpart to
`poke'.
**** MORE filename
Essentially, this is `cat' but
pausing after every ten lines. In order
to show as much at a time as
possible, you aren't prompted to press a
key to continue, as such; instead
the cursor is moved to the
bottom-right hand corner of the screen to
indicate that there is more
text waiting to be shown. There is no way of
moving back through the
file. (^C quits.)
**** NOTE
filename
This command lets you type text into a file. (Any existing
file will
be overwritten.) There's no editing, and no prompt - it's quite
crude,
but being an internal command it is at least always there. You
just
keep typing text until you're done, then type in a line
consisting
solely of a single `.' (full stop).
Mainly this is
handy for those awkward situations where you for some
reason don't have a
text editor like ZDE handy, but need to make a
quick note or something
like that.
Don't do a ^C to exit - if you do, the text isn't saved
(`note' builds
the text up in memory, and saves when you're finished). If
you should
do this, though, you could salvage the text with `save', as the
text
starts at 0100h.
**** POKE addr val
Set the
byte at address `addr' to value `val'. The address and value
must be in
hex.
I said this in the description of `get', but it applies equally
to
`poke', so I'll repeat it: This command makes it easy to crash
the
machine if you don't know what you're doing, so be careful, and
check
your typing.
Using the internal commands `get', `poke',
`memdump', and `save' is a
bearable way to patch programs and other files
if you haven't got a
better way of doing it. (And of course, Real
Programmers write all
their programs using `poke'. :-)) However, I
recommend using `wade'
for patching programs/files if at all
possible.
**** QUITSUB [command [args]]
Abort any
currently-running SUB file. This is only useful in SUB
files (of course
:-)), and usually only useful in combination with
`ifpeek' or `ifnpeek'.
If a command is specified, that command is run
afterwards.
****
REALBEEP <0 or 1>
This disables/enables a real (noisy) beep in
place of the `visual'
one. If you like having a real beep you could put
`realbeep 1' in
`autoexec.sub' to have it automatically enabled.
****
REM (or #) [any text]
This command does exactly nothing. It allows
you to put comments in
SUB files.
**** REN file1 file2
Rename
file from file1 to file2. Wildcards are not permitted.
Note that
this is *not* the way the command works in CP/M - on that,
the syntax is
rather strange, effectively `REN file2=file1' [sic].
**** REXEC
filename
This reads a uuencoded file from the serial port, decodes
it, and
writes the resulting binary file under the filename given. (It
outputs
a `.' for each line received.) The name stands for `Remote
EXECute',
as the command used to just execute the (command) file after it
was
transferred. That dates back to the time when I was running ZCN with
a
16k TPA, a 32k ramdisk, no PCMCIA card and my fingers crossed. :-)
After
ZCN stabilised a bit, I changed `rexec' to work as it does now,
which is
almost certainly more useful. (In any case, you could get the
old
behaviour if you really needed it by removing the card, doing
`rexec foo'
(it'll say "No file" but the copy in memory is fine), then
doing
`!!'.)
It's intended for getting a real serial transfer program
across, such
as QTERM (which I recommend). It won't work (will probably
crash!) if
files bigger than TPA are transferred.
**** SAVE n
filename
Save `n' pages of memory, starting from 0100h, to file
specified. A
page, in the context of this command, is 256 bytes. This
is
traditionally used to save COM files after patching, but can be
useful
for other things too.
**** SERTEST
A very simple
terminal program. It just echoes serial input, and sends
keyboard input to
the serial port. This can actually be very, very
useful if you're using
your NC100 as a terminal to a Unix box with a
suitable termcap/terminfo
entry as given earlier. You can use ^\ then
q (or ^\ then ^C) to quit; ^\
then ^\ sends a literal ^\.
**** SETBAUD [digit] (removed in ZCN
v1.2)
In versions of ZCN prior to v1.2, `setbaud' set the baud rate
the
serial port ran at, using a single digit (`4' for 2400, `5' for
4800,
`6' for 9600, etc.). It was replaced with the rather less
inscrutable
`stty', but for masochists, an emulation of the old `setbaud'
is
available in the `utils' directory, as `setbaud.sub'.
****
STAT (removed in ZCN v1.1)
In versions of ZCN prior to v1.1, `stat'
gave a few bits of useful
information, for example:
Sys upgrd
spc: 15 bytes
Max prog size: 45k
Free on drivs: A:=2k B:=43k
As
you may already realise, the second line was replaced by `k3', and
the
last line by `df'. (Most people won't miss the first line. :-))
In
case there's anyone who misses `stat', or thinks it sounds useful,
I
knocked up an external command `stat' (i.e. stat.com) which emulates
it.
(Note
for those who want to hack ZCN: `Sys upgrd spc' reported the
amount of
unused space between the ZCN system code and the ZCN static
data area
(starting at E600h) allowed for upgrading before the origin
(in main.z)
has to be moved down. You *can* still get at this number -
it's stored at
start+15 (see main.z) - but it's more tricky now. Do
`memdump 7', then do
memdump for 256 times the byte displayed there
plus 15; so e.g. for BBh,
you'd do `memdump bb0f'. The word there
(though the high byte should
always be zero) is the number you want.
It's probably easier to just use
stat.com instead... :-))
**** STTY baud_rate
Set baud
rate of serial port. The default is 2400 baud. Supported
speeds are 150,
300, 600, 1200, 2400, 4800, 9600, and 19200 baud.
Which baud rate is
best to use depends on what equipment you're using,
what you'll be doing,
etc. Assuming the `other end' is capable of
anything up to 19200 baud,
here are some guidelines:
If you want to do file transfers, you
should be able to do so without
losing any packets even at 19200 baud. (If
you get too many errors,
use 9600 baud instead - that should definitely
work. But I've never
had any problems with 19200.)
If you want
to use the `other end' interactively, i.e. if you want to
use a terminal
emulator, then you may need to use a lower speed to
avoid losing
characters.
Now, consider these facts:
- ZCN has a
768-byte serial input buffer.
- The screen driver can only write
characters at a speed of between
about 110 and 800 chars/sec, depending on line length (i.e. how
often it needs to scroll). (This is as
tested with the built-in
`sertest'
program; with an external program like QTERM there is
system call overhead, etc.)
- ZCN
uses one start bit, 8 data bits and 1 stop bit which means that
the maximum number of chars/sec you can
transfer at a given baud
rate is
baud_rate/10.
If you assume a short line length (which slows things
down because of
the more frequent scrolling required), you get these
results (I
haven't bothered with speeds lower than 1200 baud; using such
speeds
makes watching paint dry seem like a exciting spectator sport):
baud
rate chars/sec time to first lost character (sec)
1200
120 768/( 120-110) = 76.80
2400 240 768/( 240-110) = 5.91
4800 480 768/(
480-110) = 2.08
9600
960 768/( 960-110) = 0.90
19200 1920 768/(1920-110)
= 0.42
Note that the `time to
first lost character' indicates the time to the
first time the buffer is
full when a character needs to be added
(which causes a lost character)
rather than the time to when the
display catches up and the lost character
is noticeable, which may
well be rather longer.
Assuming a more
reasonable line length (about 78 chars/line) you end
up with:
baud
rate chars/sec time to first lost character (sec)
1200
120 768/( 120-800) = (never)
2400 240 768/( 240-800) = (never)
4800 480 768/(
480-800) = (never)
9600
960 768/( 960-800) = 4.80
19200 1920 768/(1920-800)
= 0.69
So, what does this all
mean? Well, it depends on how you look at it.
In my experience, 2400 is
reliable except in extreme cases (the
extreme case being long bursts of short
lines - you need about 1500
bytes of short lines continuously to start
losing chars at 2400). 4800
can usually keep up too, though it's more
prone to buffer overruns.
You can use higher speeds if you want - they'll
work, but you'll lose
characters increasingly frequently as the buffer
fills up. Personally,
I just use 19200 the whole time. It's great for file
transfers, and
the input buffer can generally handle the bursts of output
when I use
it as a terminal at that speed.
One final note: If
there's no more than a screen full of text
transmitted at a time - for
example, if you're just using an editor on
the remote host - then you can
probably get away with using any baud
rate. The reason is, assuming only
80 columns are used and 10 lines,
you get a max of 800 chars per screen
refresh (usually less due to
status line(s) etc.), and a single burst of
that size can (just
about!) be dealt with every second or two.
****
SYS d:
Add the system to a drive and make it bootable. I recommend
you only
make A: drives bootable, as booting from B:, C: or D: means
remembering
different, awkwa