Every node whose bytecode includes a HALT statement MUST define a rendering template.
Templates may be either static or dynamic.
Using placeholders, the content behind MAP calls in the current executing node may be embedded in the template.
Placeholders have the following format:
{{.symbol}}
where symbol is the corresponding argument to MAP.
Note that MAP can only be called on symbols who have a corresponding LOAD on the same level or futher up the stack.
Consider the following instruction sequence:
LOAD foo 32 MAP foo HALT
If the template contains the placeholder foo, the contents of that placeholder will be replaced by the cached result of the LOAD foo external symbol.
However:
LOAD foo 32 HALT
This will not work for the same template, because the foo symbol has not been exposed with a MAP call.
LOAD foo 32 MOVE bar # (bar bytecode follows) MAP foo HALT
If the template for the node bar contains the placeholder foo, the contents of that placeholder will be replaced by the cached result of the LOAD foo external symbol.
This works because the MAP is encountered further down the node execution stack than where the LOAD was encountered.
However:
LOAD foo 32 MOVE bar # (bar bytecode follows) MAP foo MOVE baz # (baz bytecode follows) HALT
Here, if the template for baz contains the placeholder foo, the execution will fail because the MAP in bar was invalidated by the MOVE to baz.
The pipeline starts with the loading of the template corresponding to the current execution node.
From there, three branches are possible:
MAP symbols resolves to a sink.
MSINK has been encountered.
If the resulting output from any of these branches is larger than the output size, failure ensues and execution is terminated.
As indicated above, multiple-page rendering is activated when a MAP is issued to a symbol that is loaded with 0 size. (LOAD <symbol> 0).
The result is split into rows using newline (0x0a) as separator.
Consider the following instruction sequence:
LOAD foo 8 LOAD bar 16 LOAD baz 0 MAP foo MAP bar MAP baz MOUT to_foo 0 MOUT to_bar 1 MNEXT to_next 11 MPREV to_prev 22 HALT INCMP foo 0 INCMP bar 1 INCMP > 11 INCMP < 22
... and the following template (14 bytes, without the placeholders, including line break):
This is {{.foo}} and {{.bar}}
{{.baz}}
Then consider that the symbols resolve as follows:
| symbol | returned value | rendered value | bytes |
|---|---|---|---|
foo | foobar | foobar | 6 |
bar | barbarbar | barbarbar | 9 |
baz | FOO 42 BAR 13 BAZ 666 XYZZY 1984 INKY 1 PINKY 22 BLINKY 333 CLYDE 4444 | (deferred) | (71) |
to_foo | go to foo | 0:go to foo | 11 |
to_bar | visit the bar | 1:visit the bar | 15 |
to_next | next page | 11:next page | 12 |
to_prev | go back | 22:go back | 10 |
Given an output size limit of 94, static part of the template (14 bytes). this results in the following render possibilities for the sink content:
| navigation case | bytes left for sink |
|---|---|
| no navigation | 39 |
| next | 27 |
| previous | 29 |
| next + previous | 17 |
The total sink byte count is 72, whereas the maximum available sink capacity is 39. At least one extra page is needed.
The first page (with next) has 27 bytes available, which covers the 3 first sink items (22 bytes, include line break). This results in the following output:
This is foobar and barbarbar FOO 42 BAR 13 BAZ 666 0:go to foo 1:visit the bar 11:next page
Any page that is not first page has maximum 29 bytes available. There are 49 bytes left to render from the sink. This means that more pages are needed, and therefore both next and previous are needed, leaving a capacity of 17 bytes. This is only sufficient for the next item (11 bytes, with line break), resulting in the following output:
This is foobar and barbarbar XYZZY 1984 0:go to foo 1:visit the bar 11:next page 22:go back
For the next page we again compare with the maximum of 29 bytes. There are 38 bytes left to render. Another intermediate page is required, with the two next entries (16 bytes) fitting inside the capacity (17 bytes). The page then looks like this:
This is foobar and barbarbar INKY 1 PINKY 22 0:go to foo 1:visit the bar 11:next page 22:go back
Lastly, with 22 bytes left to go, we can render within the maximum available space of 29 bytes (only using previous). Thus:
This is foobar and barbarbar BLINKY 333 CLYDE 4444 0:go to foo 1:visit the bar 22:go back