u/Imaginary-Deer4185

▲ 4 r/Forth

If one creates global variables with VARIABLE, or one CREATE a symbol and uses COMMA to associate data with it, what then when code is moved from RAM to Flash or EEPROM?

I get the impression that Forth usually (?) lives in a single data segment ("heap") where both code and variable data are allot'ed from the same area, and that's good enough until saving to persistent and readonly memory.

I'm testing out a concept of separate data and code segments. Both exist in RAM, initially, but over time, one exports the code segment and includes it into Flash, a manual procedure with copy/paste and recompile (not that the details matter). When recompiling the code and running again, the byte that were exported now live in Flash, while the code segment part that lives in RAM is empty, ready for new code. It is all presented as a single address space (15 bits, with lower 14 bits for code and bit 15==HIGH for data segment). And a value N which identifies the offset of the first RAM byte of the code segment, below which access is readonly, from PROGMEM (Flash).

I modified the VARIABLE word into just reserving space on the data segment, forcing the programmer to create init-words that populate dynamic data. I persist the HERE value on copy to Flash, and restore it on restart, so that locations originally allot'ed for variables can be validly used, without risking overwrite etc.

Actually I could persist the data segment as well, but elected not to, as most of the data will probably be buffers and the like, and more efficient to recreate with code, than using limited Flash resources (I'm working in a pretty memory starved environment).

Another approach that would possibly cost a bit in terms of map tables would be some copy-on-write or COW for short.

reddit.com
u/Imaginary-Deer4185 — 29 days ago
▲ 11 r/Forth

I redesigned my Forth implementation, by writing a new one. This one has *no local variables*, and the return stack is not named "call stack" either. :-)

The "light" is that when writing for very limited resources, targeting the atmega328p at the moment, with 2KBytes of ram, every byte is precious, and the mindset becomes that of creating small words that do small things, and compose those together in more complex (but still small) words.

Of course I'm not really adhering much to standards, although I got the return stack. I just implemented floating point and long (4 bytes) integer values, which share a third stack which I call xStack.

I also split the address space into two parts, code segment and data segment. The dictionary and compiled words live in the code segment, while allot'ed data live in the data segment.

It's all fun and games, as in "toy language", but as before, I really intend to use it. I have created a "code.export" op which generates C code to paste into a PROGMEM array. After a recompile, the static part integrates with the code segment, so I can run code compiled Forth (bytecode) from Flash and RAM.

The code should work on other Arduino as well. I've tried it on the newer Nano Every, plus the old atmega 2560, developing on an Uno R3.

In Forth I implemented the " word (double quote), for creating strings, so I can greet you all properly.

: hello " hello world" .str ;

https://github.com/rfo909/RForth

u/Imaginary-Deer4185 — 1 month ago