www.jupiter-ace.co.uk
|
| Index of general Forth information > Go Forth and Multiply. |
|
|
Go Forth and Multiply from Personal Computer World.
Go Forth and Multiply From Personal Computer World December 1981, page 126.
|
|
GO
F O R T |
|
|
H |
AND
MULTIPLY |
|
Basic has done for micro-computing what Henry Ford did for the motor car that is, made it easily and cheaply available to large number of people. There comes a point in the education of many micro-users, however. where an urge is felt to branch out into other languages; this step gets more feasible by the month as compilers and interpreters become available for languages hitherto unavailable on micros. Pascal, Lisp, C, PL/T, APL, Forth, COBOL, the list
goes on.
Some users will opt for a language with more
sophisticated control structures and more readable code, such as
Pascal or COBOL others for the speed and economy of
Assembler. Standing at this fork in the road between higher and
lower level languages many people have overlooked a less
distinct third path, the language Forth,
Developed in the
middle 1960s for instrument control application, it was
initially only available on mainframe and minicomputers from Forth
Inc, a company set up by it's invent is Charles H Moore and
his early collaborators. The name came from Fourth generation
computer language; unfortunately the Third generation IBM 1130 on
which it was developed only allowed Five character
identifiers.
|
The news spread and it developed a devoted 'underground' following among groups who have propagated the language by writing and distributing Forth systems for micros among themselves. Now Forth is beginning to appear 'off the shelf' for many machines and seems destined to join the shortest of popular micro languages.
The attraction of Forth's 'middle road' for micro applications is that it combines speed and memory economy comparable to Assembler with a novel modular program structure which, once mastered, allows much more rapid program development than many high level languages, alone machine code. The price paid is that the source code is not as readable as Pascal or even Basic and that many facilities taken for granted such as strings, arrays and floating point arithmetic are not initially provided (though they can be added at will once you become
Mike Curtis explains the features
of Forth which make it an
ideal language for small systems.
|
|
|
|
|
Go Forth and Multiply From Personal Computer World December 1981, page 127. |
|
|
fluent). How this happens will
only become clear after a little discussion of Forth's unique
structure, which is so different from sequentially executed
languages like Basic and Pascal that it will provoke quite a
major mental reshuffle. In particular you will have abandon any
concept of what constitutes a 'program' derived from Basic. At the
heart of Forth is a 'dictionary' of around 100 'words' held in memory
while the system is active Fifty or so of these words define machine
code routines which are linked and executed when the word is
invoked; the remainder are defined in terms of these words.
Words have names, like ALLOT, ECHO or +. This concept of defining words
using previous definitions is crucial to the operation of Forth
and is (this is a crude simile) similar to writing a Pascal
program as a cascade of nested procedures. The Activity the
programmer in a Forth system consists of defining new words which
perform functions required in his final application. Once defined
these new words are compiled into the dictionary and become Just as
much a part of Forth as the 'core' words. They can be tested immediately
in direct mode, at the keyboard. The programmer then defines 'higher
level' words in terms of these words and so forth (ouch!) until his
final 'program' typically consists of a single word. When this
word is executed, one of Forth's interpreters looks at
its dictionary entry which contains pointers to the words by
which it was defined. These in turn contain pointers to the words by
which they are defined and so on down to the level of the machine
code 'core' words. Each word is 'executed' as it is found so that
Forth is neither interpreted nor compiled in the traditional sense, it
is both. Thus, Forth enforces the 'top-down'
development of programs beloved of structured programming
proponents The source listing of a Forth program consists of a series
of definitions of new words (all of which are independently
executable) leading up to the final application. These blocks of
code could be loaded from disk or tape during development
together with he Forth 'core', but for crucially memory
conserving applications, such as industrial control, anything not
needed in the run (which includes the compiler and unused
dictionary entries) may be stripped away leaving a minimal
necessary system for the job; this may be burned into ROM and can
typically occupy as little as 800 bytes.
A great beauty of Forth is then its extendibility or
con-tractability. The user extends the language himself in the
directions which he requires, or pares the system down to
target on a specific application. Having written a Forth program, it
is likely that many words created will go on to be used in future
programs.
Forth is more than just another programming
language, it an be an operating system, incorporating its
own compiler, interpreter, assembler, text editor and a
rudimentary file management system; in short it provides a complete
environment for the writing, testing and using of programs. Basic,
of course, also provides such an environment,
though not so comprehensive, but Forth has a number of distinct
advantages over Basic.
The speed of execution of a Forth program is very much faster
than an equivalent Basic program, of the order of ten IMPS as fast.
A 16-bit machine should execute a Forth program at virtually the same
speed as ordinary machine code, and an 8-bit machine should only
be slightly slower, A good compiled Basic may be as quick in some
applications but it a always possible to use the assembler option and
write Forth definitions directly in machine code where speed is
really important. The amount of memory required by a Forth
application s also usually much less than with other systems; as
with Basic, the entire Forth system is resident in memory the
time; on most systems, however, this only requires 6.8k, and
that includes the space for the compiled programs. A little more
space is required for disc 110 buffers, or pseudo-disk in 4
cassette-based system, but this means that a really good Forth
system can he fitted into 16k!. Compare tam with the 48k at least for
a decent Pascal system.
Forth is by the very nature modular, interactive
and structured; there is no equivalent to a GOTO statement
and it is almost impossible to think of an occasion where one
could be used, The modular and interactive nature of Forth is
particularly useful and important as it means that a program can
be developed in small sections which can be separately compiled end tested
before using them in larger modules. In practice this leads to a much
quicker program development time and fewer bugs. Experience has shown
that one should be able to at least halve this time compared to Basic.
|
The final advantage of Forth, and the one that many feel is the most
important, is that the Forth system itself is written in Forth, There
are usually only a few bytes that are outside the dictionary, so that
the programs that you write, or the words that you define are treated in
exactly the same way as the words that are already there. When Forth is
searching for a word in the dictionary it starts with the most
recent definitions, which gives you the option of redefining
any of the system words, or defining your own control structures. A
Forth program is, in effect, better thought of as an extension of the
system to provide commands and facilities suitable to your
application.
This does lead us to one of the disadvantages of Forth, it can be very
easy to crash and this is one of the penalties of having the
system so open to the user. Some of the more sophisticated
systems do have some protection built in, and It is always possible to
add your own, but a certain amount of fragility is a natural
consequence of the nature of Forth, It is usually easy enough to
recover from such a crash without too much damage being done, but if
it is bad enough to need a complete reload and you are using 300
baud cassettes...!
The other main disadvantage of Forth, at least as far as beginners
are concerned, is its extensive use of stacks and postfix
(reverse polish) notation. The difficulty that many people have
with this is usually more imagined than real; though there is no doubt
that a language like Basic is easier to learn initially, anyone who
understands the basic principles of programming should be able to master
Forth without much difficulty. Stacks
A stack is best thought of as a pile of objects, a common analogy
being that of a pile of plates or trays in a canteen. Objects can
only be added to the top of the stack, and the only object that can
(safely) be removed is the top one. The objects on the Forth
stack are 16-bit numbers and the stack provides a convenient place
for temporary storage, since the user doesn't have to concern himself with
where the numbers are stored, only with the order in which they are
stored. Placing a number on the stack is known as PUSHING and removing
it is known as PULLING - see Figure 1 for an example.
Part of the documentation for a Forth word should be its effect on
the stack, eg, + (n1 n2....sum) indicating that the Forth
word '+' expects to find two numbers n1 and n2 on the stack. n2 is on
top and the effect of that word is to pull the two numbers from the stack
and to push their sum back on.
Postfix notation fits in very naturally with stacks: it involves
writing an operator after its operands, so we write 2 3 + instead
of 2+3 in ordinary infix notation, or B C + A * instead of A*(B+C).
Each operand is pushed onto the stack as it comes, each
operator pulls its operands from the stack and pushes its result
back on.
It is now possible to have a look at some Forth: if the following
sequence is entered at the keyboard: 4 5 (return) OK (OK is the Forth
response, output on the same line before the carriage return is
echoed) will result in the two numbers 4 and 5 being pushed on the stack,
then the + pulls them off, adds them and pushes the sum back on. To
see what is on the stack we use the Forth word '.' which prints the
top number so: . (return) 9 OK.
Try this
HEX F 2 * . (return) 1E OK
(Warning: everything will be done in HEX from now on until you enter DECIMAL)
Some Forth words do nothing but manipulate items on the stack, eg. DUP (n1....n1 n1) duplicates the top item on the stack; SWAP (n1 n2....n2 n1) swaps the top two Items around; OVER (n1 n2....nl n2 n1)copies the second Item onto the top; ROT (n1 n2 n3....n2 n3 n1) rotates the third item onto the top; DROP (nl....) drops the top item. Dictionary
The major difference between Forth and languages like Basic lies in
its use of a dictionary and Indirect Threaded Code (ITC) Direct
Threaded Code (DTC) means that a program consists of a list of
addresses of pre-written routines, in ITC a program consists of a list of
addresses of addresses of routines Provided that the pre-written
routines are sensibly chosen so that every programming need can
be met by some combination of them, then both methods produce
particularly programs because
|
|
|
|
|
Go Forth and Multiply From Personal Computer World December 1981, page 128. |
|
|
the routines act like a high-level instruction set for the processor, and are themselves
written in machine code. You thus get a combination of high-level programs running at very nearly the speed machine code,
with the advantage over normal compiled languages that each
routine, no matter how complicated, reduces to a two byte address,
so the programs do not use n much memory. The advantages of ITC over
DTC are not clear, and beyond the scope of this article, but it makes
it easier to treat the programs as routines that can be included
other programs. Forth has, in fact, been implemented in DTC, but the
use of ITC is now almost universal.
A Forth dictionary entry contains the following information:
- A name field, which contains the name of the routine (here is very
little restriction on the choice of name) and a few other details,
such as the length of the name.
- A link field which contains a two-byte pointer to the preceding entry, used when the dictionary is being searched. - A code field which contains a two-byte pointer to actual machine code which could be the next part of the entry (a code definition), or to a routine that interprets the rest of the entry. - A parameter field which may contain machine code, addresses of other dictionary entries, variable values, or other information depending on the type of entry. Writing a Forth program involves the creation of a new dictionary
entry, whose parameters are the addresses of the other words that go to
make up the new word. There are a number of different ways of
doing this, the most common being the COLON definition; the Forth word
':' having been defined to create a new dictionary entry. The
word ';' is used to terminate a definition, eg, to convert
a temperature in Centigrade to Fahrenheit we must multiply by 9, divide
5 and add 32. We can define a word 'DEGC='; thus:
: DEGC= 9 * 5 / 32 + . ." DEGF" ;
Note the use of spaces; Forth uses spaces as a delimiter so there must be
at least one space between every word. The '." ' prints the character
string following up to the next " . Note also that there must be a number
on the stack before the word is executed since the '*' requires two
numbers to be on the stack. The word 'DEGC=' has now been added to
the dictionary and may be used in just the same way as any other word;
either in subsequent definitions or directly interpreted
from the terminal thus.
10 DEGC= (return) 50 DEGF OK
or 12 DEGC= (return) 53 DEGF OKfrom which you may gather that Forth uses integer (fixed point)
arithmetic. There is no standard method of dealing with floating
point numbers in Forth, though a number of routines have been published.
Many people think that this another disadvantage of Forth, but in
practice most Forth programmers don't find it much of a restriction; there
are a number of useful words available for integer arithmetic, an example
being /MOD (n1 n2....rem quot) which leaves on the stack both the remainder
and quotient after a division. Forth also has words for dealing with
double length (32-bit) numbers and, at the expense of a little more thought, these give faster, more accurate results than
floating point arithmetic.
Variables are not so widely used in Forth programs, since the stack is used for
temporary storage; any that are needed must first be defined as dictionary
entries, thus:
|
0 VARIABLE X (return) OK
which defines a word X as a, variable whose parameter field is two bytes long and
may be used to store any 16-bit value. When the word 'X' is executed its effect
is to leave the address of this parameter field on the stack, values may be
stored and retrieved using the words '!' (Pronounced store) and '@' (pronounced
fetch). X @ will place the value stored in X onto the stack. While X ! will
place the current top of the stack into X.
Other types of variable are possible, but it is up to the programmer to allot
enough space in the dictionary (using the word ALLOT) and to write the words
necessary to access their values. For example a simple one-dimensional array of
ten 16-bit numbers could be defined by:
0 VARIABLE ARRAY 18 ALLOT (18 bytes + 2 bytes assigned by VARIABLE). Execution
of the word 'ARRAY' will also place the address of the parameter field (the
first element of the array) on the stack, but the word 'ARRAY could be redefined
to access all the elements thus:
: ARRAY 1 - 2 * (to work out the byte offset)
ARRAY (uses the previous
definition to get the address)
+ ;
Now, for example, 3 ARRAY will put the address of the third element on the
stack. There are other ways of doing this with only one definition, using one of
the other methods of creating a dictionary entry, but this is perhaps the
easiest to understand.
The usual control structures are available, with the exception of a CASE
construction, though there are a number of published versions of this. The major
ones are:
IF (true clause) ELSE (false clause) ENDIF where the ELSE and the false clause
may be omitted;
DO (routine to be repeated) LOOP which is the equivalent of a FOR .... NEXT loop
in BASIC. with a variation using +LOOP for an increment which is not 1;
BEGIN (condition) WHILE (routine) AGAIN
BEGIN (routine) (condition) UNTIL which
should be self-explanatory.
Here is an example which illustrates the IF and DO..LOOP constructions, and also
shows the way in which a program may be built up in modules, Suppose our ARRAY
contains ten marks in an exam, and results must be printed out as PASS (45 per
cent or over) or FAIL. First we define a word 'GRADE' which will test the number
on top of the stack and print the appropriate message.
: GRADE 45 < (pulls the top two numbers and pushes a 1
if the second is less than the top, 0 otherwise)
IF ." FAIL"
ELSE " PASS"
ENDIF ;
This can now be tested by, for example:
62 GRADE (return) PASS OK
and it can be then incorporated in:
: GRADES 11 1 (the DO LOOP index, performed ten times,
11 is the value at which it will exit)
DO
I ARRAY @ (I pushes the index onto the stack)
DUP . (to print the mark) 5 SPACES GRADE CR (to do a carriage return) LOOP ;
To sum up, Forth is not a language for absolute beginners, but it has so many
advantages over Basic and similar languages that it should be seriously
considered by anyone else. There are now versions of Forth available for most
popular micros and a thriving user group, the Forth Interest Group (FIG),
publishes a newsletter in the UK. For more information write to: The Hon Sec,
Forth Interest Group UK, c/o 38 Worsley Road, Frimley, Camberley, Surrey, GUI 6
5AU.
A very good introductory book, which not only tells you all you need to know
about Forth, but also gives an insight into the workings of computers is
Starting Forth by Leo Brodie, available for £11.95 from Computer Solutions.
Treway House, Hanworth Lane, Chertsey, Surrey, which also supplies a lot of
the more sophisticated (and expensive) Forth material.
FIG in the States publishes a magazine Forth Dimension and distributes a lot of
material, including Assembler listings for all major microprocessors, Its
address is Forth Interest Group, PO Box 1105, San Carlos, CA 94070, USA.
|
|
|
|
|
|
![]()
![]() |
|
|
|
|