-
Notifications
You must be signed in to change notification settings - Fork 66
STM8 eForth Alias Words
Alias Words is a unique feature of TG95451/STM8EF for creating dictionary entries for existing machine code in the binary which have no dictionary entry in the binary distribution. The end result is a smaller binary distribution which still contains the machine code of words defined in forth.asm, but the dictionary information for many words has been omitted. Alias Words are the mechanism by which dictionary entries for these machine code words are added at a later date as needed.
Alias Words allow the programmer to create dictionary entries like the following:
- linked previously unlinked Forth words in Flash into the dictionary
- provide words for code positions halfway into a colon definition (instead of factoring)
- keep words accessible after redefinition
Due to a core feature, Alias Words directly return the aliased code addresses. Therefore removing Alias definitions won't break the code using them.
The feature was proposed by @RigTig in issue #26 and #27:
- create minimal Forth core binaries by leaving out all non-essential parts of the dictionary
- extract addresses from a the
forth.rst
list file in the out folder - create alias words from extracted addresses when, and compile them into RAM as needed
- compile new words using an alias word
Alias Words for unlinked STM8 eForth words are now automatically generated in the board build process. In the binary release they are in the out/<BOARD>/target
folder. After linking that folder to ./target
in the working directory, in e4thcom (and codeload.py
) such Alias Words can be used easily, e.g.:
#require ULOCKF
#require LOCKF
: !F ( n a -- )
\ write n to a in Flash memory
ULOCKF ! LOCKF
;
The words ULOCKF
and LOCKF
were removed from the standard dictionary to safe memory space (in many cases NVM
and RAM
can be used instead). The example creates aliases to make a simple Flash store word.
For programmers using a windows terminal the following procedure using the example DIGIT will allow dictionary entries to be added for any words which have been left out of the dictionary.
NVM \ if you want to create the dictionary entry in flash for use in a later session
: DIGIT [ $CC C, $88F1 , OVERT
\ this is the file DIGIT in the target sub-directory for the board you are using
\ in forth.rst you see the $88F1 address where DIGIT is referenced when the binary using forth.asm was assembled
words \ we now see Digit in the dictionary
DIGIT IRET SAVEC RESET RAM <snip>
RAM \ since the dictionary entry for DIGIT was added to NVM, we must switch to RAM to make the dictionary entry permanent
cold \ do a cold restart or power cycle
STM8eForth 2N2.21 ok
words
DIGIT IRET SAVEC RESET RAM <snip> \ we see DIGIT is still there
9 digit . 57 ok \ and it works as expected
Note: please refer to the Makefile in showcase STM8 eForth application projects (e.g. W1209 data logging thermostat) for how to manage linking to a build's target
output directory!
A definer for Alias Words may look like this:
: ALIAS ( "name" xt -- ) \ M.Mahlow's solution
: $CC C, , [compile] [ OVERT
;
Using ALIAS
creating alias words is akin to defining a constant:
\ create
' . ALIAS .. ok
56 .. 56 ok
: a 123 [ here ] . ; ok
ALIAS b ok
a 123 ok
23 b 23 ok
Please be aware that the STM8 core will always go through a reset when executing binary code from EEPROM. Since it is still possible to have dictionary entries in the EEPROM the unique STM8 eForth ALIAS
feature allows moving Forth headers from the core to the EEPROM!
The library word EEALIAS
does the following:
- find the root of the dictionary in Flash memory
- unlink an existing the EEPROM
- create and link a dictionary in the EEPROM (i.e. EEPROM MODE )
- abort if a normal compilation (non-ALIAS words) is attempted
After defining ALIAS
words, e.g. from a build's target
directory, return to RAM MODE with EECLOSE
when done.
When the dictionary entries in the EEPROM are no longer needed, EERESET
can be used to unlink the dictionary in the Flash ROM.
Here is an example:
\ EEPROM MODE Example:
\ define ALIAS words in the EEPROM,
#include EEALIAS
\ load ALIAS words
#require SPACES
#require DIGIT
#require DNEGATE
\ done: return to normal, and WIPE RAM
EECLOSE
Aliases are simply dictionary entries followed by a JMP
instruction:
stm8eForth v2.2
: .. [ OVERT $CC C, ' . , ok
4 .. 4 ok
In this example an alias ..
is created for .
"print number" (in the standard use case the address comes from the STM8EF build script). The idiom : name [ OVERT
creates an empty dictionary entry, and then leaves compile mode. The sequence $CC C,
writes a JP
(jump) STM8 opcode to code field of the new word, and ' . ,
completes the JP
with the address of the word .
. Typing 4 ..
demonstrates that the word ..
works as expected.
When the alias ..
is used, the TG9541/STM8EF implementation of NAME>
detects that the code field of ..
starts with a the opcode JP
($CC), not any other instruction. NAME>
then returns the value of the jump target not the address of the jump.
Running the code directly, of course, would do the same. The advantage is that aliases can be removed from the dictionary (e.g. defined in RAM), and compiled code in the Flash memory will continue to use the "aliased code".
The following code demonstrates that the alias feature is completely transparent to the application:
: ..test .. ; ok
: .test . ; ok
' ..test 10 dump
117 CD 8A D2 81 1 10 5 2E 74 65 73 74 CD 8A D2 81 M_R____.testM_R_ ok
' .test 10 dump
123 CD 8A D2 81 0 1 4 64 75 6D 70 74 74 0 0 0 M_R____dumptt___ ok
The code of the words ..test
(with the alias ..
), and .test
(with the original .
) is identical (CD 8A D2 81
, CALL 8AD2 RET
).
Another use case for Alias Words is safeguarding a word before overwriting it in the dictionary.
Consider this example (using e4thcom):
stm8eForth v2.2
#r ALIAS Uploading: ./lib/ALIAS
\ STM8eForth : ALIAS MM-170929
\ ------------------------------------------------------------------------------
\ ...
nvm hex ok
: a 1 ; ok
' a . 9336 ok
' a ALIAS old-a ok
: a 2 ; reDef a ok
a old-a . . 1 2 ok
ram cold
stm8eForth v2.2
hex ' old-a . 9336 ok
Look in the target folder for the binary you are using e.g. \out\W1209-FD\target for the W1209 board with full duplex. The words with no dictionary entry, but included in the binary as code, are listed here. Use the alias functionality to create dictionary entries as needed.