larsbrinkhoff / lbforth Goto Github PK
View Code? Open in Web Editor NEWSelf-hosting metacompiled Forth, bootstrapping from a few lines of C; targets Linux, Windows, ARM, RISC-V, 68000, PDP-11, asm.js.
License: GNU General Public License v3.0
Self-hosting metacompiled Forth, bootstrapping from a few lines of C; targets Linux, Windows, ARM, RISC-V, 68000, PDP-11, asm.js.
License: GNU General Public License v3.0
lbForth$ strace -e open ./b-forth
[...]
s" /this/is/a/really/really/long/path" searched
ok
include foo.fth
open("/this/is/a/realfoo.fth", O_RDONLY) = -1 ENOENT (No such file or directory)
Check why this isn't caught by tests.
Building make TARGET=x86 OS=windows
in Cygwin32 seemingly works ok, but the resulting Forth is a one-line file with the text Undefined: file-source
.
Also see #28, reported by @vigilancetech-com.
When an exception is thrown, one wordlist is dropped from the search order.
Test case:
include search.fth
also forth order \ "forth forth only"
abort
order \ "forth only"
The asm.js target.fth has two definitions for header,
, which is probably a mistake.
Also, docol,
etc compile a zero cell before the code field proper. I'm not sure that's by design or not. Is that the place for the "codeid", or the does field? I think the latter. But then the zero could probably move to header,
like in the C target.
@pipcet, do you have any comment on this?
When ReadFile
returns error, check GetLastError
for ERROR_HANDLE_EOF
.
Then change KEY
to call ABORT
instead of BYE
on errors.
Use them for bootstrapping.
I thought it would be interesting to try out lbForth. Target is Fedora Core 25 x86 64 bits and here are my notes:
-m32
in targets/c/forth.mk (see compiler log below).s" /some/dir/..." searched
to make lbForth find source files of interest. Not sure if this is correct but it did seem to work.require
subdirectories seems to be lost, so that foo
in require foo/bar.fth
is ignored?Undefined: {
.make -ftargets/c/bootstrap.mk
make[1]: Entering directory '/usr/local/src/lbForth'
make[1]: Circular kernel.c <- b-forth dependency dropped.
gcc -m32 -O2 -fomit-frame-pointer -fno-unit-at-a-time -Itargets/c targets/c/params.c -o params
In file included from /usr/include/features.h:392:0,
from /usr/include/string.h:25,
from targets/c/params.c:1:
/usr/include/gnu/stubs.h:7:27: fatal error: gnu/stubs-32.h: No such file or directory
# include <gnu/stubs-32.h>
^
compilation terminated.
targets/c/forth.mk:25: recipe for target 'params' failed
make[1]: *** [params] Error 1
make[1]: Leaving directory '/usr/local/src/lbForth'
Makefile:27: recipe for target 'b-forth' failed
make: *** [b-forth] Error 2
A fresh build with "make -j" fails.
ESP8266 and ESP32 are everywhere. Need that Xtensa target.
Remove (LOOP)
from nucleus. Replace uses of DO-LOOP with FOR-NEXT in the kernel. Provide DO-LOOP in a compatability layer.
https://www.reddit.com/r/Forth/comments/6b9lsz/alternatives_to_loop/
When entering "2dummy", the error message is "Undefined: dummy". It's even worse when base
is 36, as all letters and digits will be stripped from the error message:
36 base !
ok
abcdef-ghij
Undefined: -ghij
To reproduce:
include search.fth
cold \ or warm
This is probably because CONTEXT isn't reset in WARM, and the ONLY wordlist is still active.
Why do you use min
but not umin
in the code like the following:
: name, ( a u -- ) #name min dup c, tuck move, offset, ;
Here min
protects against too long u
, but not from negative u
(or very long positive ;).
Then COREEXT, TOOLS, STRING, EXCEPTION, SEARCHORDER, DOUBLE, etc.
Get up and running in ITS.
It's a word-adressed machine. But there are also special "byte pointers". Consider what to do about C@
and C!
etc.
SYNONYM, S", ...
Use the save-image to write a new executable with everything pre-loaded.
I have no idea how the various JS engines interface to the operating system. Or how to run this in a browser.
PRG
file format:
https://hkn.eecs.berkeley.edu/~mcmartin/ophis/manual/x51.html
I'd like to make a port to macOS, but it's not really viable to do that without access to a macOS machine.
If I could get ssh access to a machine for a month or so, that'd be really helpful.
Including a file which doesn't exist just prints "File not found".
$ make
make -ftargets/c/bootstrap.mk
make[1]: Entering directory '/home/kevin/lbForth'
make[1]: Circular kernel.c <- b-forth dependency dropped.
gcc -m32 -O2 -fomit-frame-pointer -fno-unit-at-a-time -Itargets/c targets/c/params.c -o params
targets/c/run.sh ./params -lisp > params.lisp
cp targets/c/jump.fth jump.fth
cp targets/ctc.fth threading.fth
cp targets/c/target.fth target.fth
echo ": sysdir s" src/" ;" >> target.fth
./lisp/lisp.sh '(load "lisp/meta.lisp") (compile-forth "targets/c/nucleus.fth" "src/kernel.fth")'
;; Loading file lisp/meta.lisp ...
;; Loading file params.lisp ...
;; Loaded file params.lisp
WARNING: DEFUN/DEFMACRO(EXECUTE): # is locked
Ignore the lock and proceed
WARNING: DEFUN/DEFMACRO: redefining function EXECUTE in /home/kevin/lbForth/lisp/meta.lisp, was defined in C
;; Loading file lisp/words.lisp ...
;; Loaded file lisp/words.lisp
;; Loaded file lisp/meta.lisp
gcc -m32 -O2 -fomit-frame-pointer -fno-unit-at-a-time -Itargets/c -c -o kernel.o kernel.c
gcc -m32 kernel.o -o b-forth
rm -f kernel.c kernel.o params.lisp jump.fth threading.fth target.fth
make[1]: Leaving directory '/home/kevin/lbForth'
cp b-forth forth
rm -f *-stamp
touch x86-windows-stamp
cat targets/x86/params.fth targets/x86/windows/params.fth > params.fth
cp targets/x86/jump.fth jump.fth
cp targets/itc.fth threading.fth
cat targets/x86/target.fth targets/x86/windows/target.fth > target.fth
echo ": sysdir s" /usr/local/share/lbForth/" ;" >> target.fth
echo include targets/x86/meta.fth | targets/c/run.sh ./forth | tail -n+3 > x86-forth
mv image x86-forth
mv: cannot stat 'image': No such file or directory
make: [targets/x86/forth.mk:6: x86-forth] Error 1 (ignored)
chmod a+x x86-forth
rm -f forth.exe
cp x86-forth forth
0;~/lbForth
E.g.
include foo.fth .( this part of the input may be clobbered by foo.fth )
The metacompiler is due for an overhaul.
The current implementation is closely tied to building the kernel.
Everything is written to a single memory space.
Building and saving the image is constrained by the single memory space.
See e.g. https://groups.google.com/d/msg/comp.lang.forth/YVjtNQwSIH0/YHduzDG4c9EJ
Some may believe that a threaded-code engine written in assembly language would have led to better performance than that exhibited by Gforth. However, looking at http://www.complang.tuwien.ac.at/forth/performance.html, Gforth 0.4.9 performed faster than any of the threaded-code Forth systems written in assembly language (Win32Forth, NT Forth, and eforth) on all of the benchmarks on a 486DX2/66:
The interpretive systems written in assembly language (except eforth opt) are, surprisingly, slower than Gforth. One important reason for the disappointing performance of these systems is probably that they are not written optimally for the 486 (e.g., they use the lods instruction).
There's a lot of copy-pasting between the different assemblers. Much of the assembler implementation should go into a generic library, and target-specific parts should built on top of that.
The asm.js target added some [IF] sections to the metacompiler. See #33 and f832c94. These should be fixed to use code from some target file instead.
The target also abuses cold.fth to insert special code for dumping the image. This doesn't hurt the overall structure of the metacompiler, but there is room for improvement.
you know the drill
make check
fails in Windows. There are two failing tests:
Make XT point directly at code field.
With inlining?
Go completely self-hosting by ditching the Lisp metacompiler.
Also SEE.
Is there currently a high level way to call system calls?
I look in io.fth and see you setting up the system calls but you only do them from assembly below.
For example, in FreeForth there is the word:
lib:` ( @ # <name> -- ; a n -- funEntry ) loads the dynamic-link-library
with filename starting at address "@" for "#" bytes, and defines a word
which will lookup in this library for the function matching the name
starting at address "a" for "n" bytes, and if found will return its entry,
for use with "#call" or "fun:".
If the library is not found, or if later a function is not found,
an exception is thrown with corresponding error message.
: lib:` :` #lib lit` #fun ' call, ;` ;
see also: lib: #call fun: libc k32 ff.boot
and:
#call ( argN ... arg1 N funEntry -- funResult ) calls the library function
with entry at "funEntry", which consumes "N" arguments from DATAstack and
returns a single result on top of DATAstack. The N arguments must be pushed
on DATAstack in the same order as in C, i.e. C-prototype (see Linux man or
Windows win32.hlp) rightmost argument first, leftmost last.
The assembler is done.
Should use jal
.
Reported in larsbrinkhoff/forth-mode#69
@vigilancetech-com has expressed interest in using lbForth to build commercial software.
The search order is different in interpretation state and compilation state. When interpreting, only forth
is searched, but when compiling there's an implicit also compiler-words
. This is currently done in a buggy and nongeneral way.
The solution might also consider metacompilation. Inside the metacompiler in interpretation state, the search order is host-interpreter
, meta-interpreter
, forth
. In compilation state, the search order is host-compiler
, meta-interpreter
, forth
.
When metacompiling in interpretation state, the search order is: meta-interpreter
, forth
. When metacompiling in compilation state, the search order is: meta-compiler
, then target dictionary.
A declarative, efficient, and flexible JavaScript library for building user interfaces.
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google ❤️ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.