Creating arrays

The create...does> pair can be used to define some convenient array-defining words. For an array of bytes, it is straight-forward to manually allot the memory and address it at run time.
create my-array 10 allot  ok<#,ram>
my-array 10 $ff fill  ok<#,ram>
my-array @ .  -1  ok<#,ram>
Here, my-array is first allotted 10 bytes. At run time for my-array, the address of the start of the 10 bytes is left on the stack, and we use the fill word (AppendixB) to completely fill the array of bytes with ones. Accessing the first cell (2 bytes) and printing it (to get -1 sent to the serial port) confirms that all bits are 1s. The word dump can be used to get a more complete picture. It expects the starting address and number of bytes to dump sitting on the stack.
hex  ok<$,ram>
my-array $30 dump 
f170 :ff ff ff ff ff ff ff ff ff ff 00 00 00 00 00 00 ................
f180 :00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................
f190 :00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................ ok<$,ram>
Note that dump works with blocks of 16 bytes and that the dots to the right show a character representation of the byte values. This is convenient when trying to identify strings of text.


It is also straight-forward to create an array with particular data compiled in.

create my-cell-array 100 , 340 , 5 ,  ok<#,ram>
Remember to use , (comma) to compile in every data element, not leaving off the last one. At run time, my-cell-array puts the address of the start of the associated memory on the stack and the address of the desired cell (index 2, in this case) needs to be calculated (2 cells +) before executing @ (fetch).
my-cell-array 2 cells + @ . 5  ok<#,ram>
This address calculation code can be added into the defining word with does> such that the subsequently defined my-cells array will have the snippet of code (swap cells +) executed at run time to convert from a cell index to an address.
\ A defining word for creating arrays.
: mk-cell-array ( u --) 
  create cells allot 
  does> swap cells + ;  ok<#,ram>
The swap is used to get the index as TOS with the array address as NOS, cells scales the index to the offset as a number of bytes and + adds the offset to the array address. The newly computed cell address is left as TOS for use by the words ! (store) and @ (fetch).
\ Make an array and access it.
5 mk-cell-array my-cells  ok<#,ram>
3000 0 my-cells !  ok<#,ram>
3001 1 my-cells !  ok<#,ram>
3002 2 my-cells !  ok<#,ram>
1 my-cells @ . 3001  ok<#,ram>

Peter Jacobs 2013-06-12