Version 1.3 is the first one that provides all ANS Forth word sets, except
for 17 words that had to be omitted for various reasons:
?DUP
Ambiguous stack effect.
PICK ROLL
Ambiguous stack effect with respect to data types.
(
Used for stack diagrams instead of for comments.
FIND
Replaced by SEARCH-ALL, because of ambiguous stack effect and usage of
counted strings.
C" COUNT WORD
Counted strings are not supported. WORD has been replaced by PARSE-WORD.
CS-PICK CS-ROLL
Not required because StrongForth does not need a separate control-flow
stack.
RESIZE-FILE
Missing support by DOS.
UNLOOP
Not required, because loop indexes are locals.
CONVERT EXPECT FORGET QUERY SPAN
Declared obsolet by the standard.
StrongForth is not ANS compatible, because all definitions that have an
actual stack effect require an explicit stack diagram. Furthermore, the
semantics of some words had to be modified, and several words got renamed.
Renaming is mostly caused by overloading. For example, + D+ M+ and F+ share
the same name +, because the compiler and interpreter can easily select the
correct version based on the data types. As a result, only 272 different
names are required to implement ANS Forth words with 342 (359 - 17)
different names.
StrongForth 1.3 is available for download at
http://home.vrweb.de/~stephan.becher/forth.
But it should be possible to emulate. Use reposition-file to move
the file pointer to the size specified; if there's no error then truncate
at that point with AH=40h CX=0 INT21h
p.s. if your reposition-file doesn't work beyond the file's boundary
then you'll have to use the AX=4200h function instead.
Yes, very simple:
: RESIZE-FILE ( ud fileid -- iof )
DUP >R REPOSITION-FILE DUP
If R>DROP EXIT \ Error, bail out
Then
DROP 0. R> WRITE-FILE
;
--
Coos
CHForth, 16 bit DOS applications
http://home.hccnet.nl/j.j.haak/forth.html
This will only work when you want to make the file larger
(given REPOSITION-FILE works according to the standard).
To handle the shortening case, do a BINary copy with WRITE-FILE,
DELETE-FILE the original, and then RENAME-FILE the result :-)
-marcel
Wouldn't that result in the renamed copy having a different
fileid from the original (or none at all if DELETE-FILE
and/or RENAME-FILE only work on closed files), which
could break code that assumes the fileid is valid.
George Hubert
I think I stole the technique from you :)
Your code relies on:
- REPOSITION-FILE being able to extend the file,
- WRITE-FILE truncating the file when writing 0 bytes
Since both are non-standard one can't rely on it - even on
MS-DOS Forth implementations. But one can use the
corresponding MS-DOS calls instead.
My WRITE-FILE traps u=0 to prevent inadvertent truncation.
While one doesn't expect apps to write 0 bytes, it's not illegal.
It might even be convenient. Let's say I want to start/stop
output to a file. I could control it via:
( c-addr u ) OUTFLAG @ AND fid WRITE-FILE
Your version of RESIZE-FILE works fine in StrongForth:
: RESIZE ( UNSIGNED-DOUBLE FILE -- SIGNED )
TUCK REPOSITION DUP IF NIP EXIT THEN DROP
NULL CDATA -> CHARACTER 0 ROT WRITE ;
I wasn't aware of this undocumented feature of DOS function 40H. Therefore,
StrongForth's implementation of WRITE(-FILE) doen't trap when writing zero
characters. Thanks a lot for the hint.
Regards,
Stephan
"lseek" is Linux's reposition-file function, and it doesn't extend the
file. You have to use "resize" instead.
According to the ANS standard, using REPOSITION-FILE to extend a file
is an ambiguous condition.
Brad