Skip to content

Commit b01a9e0

Browse files
committed
[WIP] Add some evo format docs
1 parent dd40093 commit b01a9e0

11 files changed

Lines changed: 1383 additions & 0 deletions

evo-doc/8ca2-background-image.md

Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
# `.8ca2` background images
2+
3+
Sample files: `Image1.8ca2` through `Image7.8ca2`.
4+
5+
Metadata:
6+
7+
```text
8+
metaData.type = 5
9+
metaData.version = 1
10+
metaData.flags = 1
11+
metaData.name = image token, little-endian, then 0000
12+
```
13+
14+
Observed image name tokens:
15+
16+
```text
17+
Image1 E8B0 TOK_VAR_IMAGE1
18+
Image2 E8B1 TOK_VAR_IMAGE2
19+
Image3 E8B2 TOK_VAR_IMAGE3
20+
Image4 E8B3 TOK_VAR_IMAGE4
21+
Image5 E8B4 TOK_VAR_IMAGE5
22+
Image6 E8B5 TOK_VAR_IMAGE6
23+
Image7 E8B6 TOK_VAR_IMAGE7
24+
```
25+
26+
Body fields:
27+
28+
```text
29+
version = 1
30+
size = 33601
31+
data = byte string, length 33601
32+
```
33+
34+
The image data byte string is:
35+
36+
```text
37+
data[0] image-format marker; 0x16 in the provided samples
38+
data[1..] 33600 bytes of RGB565 pixel data
39+
```
40+
41+
Pixel geometry:
42+
43+
```text
44+
width = 160
45+
height = 105
46+
bytes = 160 * 105 * 2 = 33600
47+
format = RGB565, little-endian words
48+
```
49+
50+
The converter draws the input image onto a 160 by 105 white canvas,
51+
converts RGBA8888 to RGB565, then writes rows bottom-to-top:
52+
53+
```text
54+
stored row 0 = source/display row 104
55+
stored row 1 = source/display row 103
56+
...
57+
stored row 104 = source/display row 0
58+
```
59+
60+
Within each stored row, pixels are left-to-right.
61+
62+
RGB565 word decoding:
63+
64+
```js
65+
let word = data[p] | (data[p + 1] << 8);
66+
let r5 = (word >> 11) & 0x1f;
67+
let g6 = (word >> 5) & 0x3f;
68+
let b5 = word & 0x1f;
69+
```
70+
71+
It seems `0x0b` is the first data byte made by the converter but all provided calculator files use `0x16`?

evo-doc/8xl2-list.md

Lines changed: 245 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,245 @@
1+
# `.8xl2` lists
2+
3+
Sample files: `L1.8xl2` through `L6.8xl2`, plus custom named list samples.
4+
5+
Metadata:
6+
7+
```text
8+
metaData.type = 1
9+
metaData.version = 1
10+
metaData.flags = 0
11+
metaData.name = list token, little-endian, then 0000
12+
```
13+
14+
Observed list name tokens:
15+
16+
```text
17+
L1 E830 TOK_VAR_LIST_1
18+
L2 E831 TOK_VAR_LIST_2
19+
L3 E832 TOK_VAR_LIST_3
20+
L4 E833 TOK_VAR_LIST_4
21+
L5 E834 TOK_VAR_LIST_5
22+
L6 E835 TOK_VAR_LIST_6
23+
```
24+
25+
Custom named lists use `TOK_VAR_LIST_NAME` followed by variable-letter
26+
tokens, then `0000`. The user-facing list marker `(L)` is not stored as
27+
an ordinary `L` character; it is represented by `E836`.
28+
29+
Examples:
30+
31+
```text
32+
(L)A:
33+
E836 E800 0000
34+
TOK_VAR_LIST_NAME TOK_VAR_A EOS
35+
36+
(L)B:
37+
E836 E801 0000
38+
TOK_VAR_LIST_NAME TOK_VAR_B EOS
39+
40+
(L)ABC:
41+
E836 E800 E801 E802 0000
42+
TOK_VAR_LIST_NAME TOK_VAR_A TOK_VAR_B TOK_VAR_C EOS
43+
44+
(L)XXX:
45+
E836 E817 E817 E817 0000
46+
TOK_VAR_LIST_NAME TOK_VAR_X TOK_VAR_X TOK_VAR_X EOS
47+
```
48+
49+
Body fields:
50+
51+
```text
52+
version = 1
53+
type = 0 in the samples
54+
len = displayed element count
55+
arraylen = number of 16-bit expression words, excluding trailing flags
56+
size = byte length of data, including trailing flags
57+
data = expression list payload plus one-byte element flags
58+
```
59+
60+
Empty lists (`L5.8xl2` and `L6.8xl2`) stop after `len = 0` and omit
61+
`arraylen`, `size`, and `data`.
62+
63+
## Non-empty data layout
64+
65+
For a non-empty list, `data` has two regions:
66+
67+
```text
68+
00E5 list start marker
69+
... scalar expression payloads
70+
00D9 list end marker
71+
flags[len] one byte per displayed element
72+
```
73+
74+
All words in the expression region are little-endian 16-bit values. The
75+
list elements are stored in reverse display order: the first element
76+
after `00E5` is the last element shown on the calculator.
77+
78+
The trailing flags are not counted by `arraylen`, but they are counted by
79+
`size`. The flags are in display order, not reversed payload order.
80+
Observed flag values:
81+
82+
```text
83+
00 normal real or complex value
84+
06 exact fraction
85+
```
86+
87+
## Scalar payloads observed inside lists
88+
89+
The scalar format is postfix-tagged. These tags were observed:
90+
91+
```text
92+
001F positive exact integer
93+
0020 negative exact integer
94+
0021 exact fraction
95+
0022 negative exact fraction
96+
0023 decimal / approximate real
97+
```
98+
99+
Observed exact integer encodings:
100+
101+
```text
102+
0 0000 001F
103+
1 0001 0001 001F
104+
2 0002 0001 001F
105+
3 0003 0001 001F
106+
-4 0004 0001 0020
107+
```
108+
109+
The middle `0001` appears to be a one-limb count for small non-zero
110+
integers.
111+
112+
Observed exact fraction encoding:
113+
114+
```text
115+
num/den is stored as:
116+
denominator 0001 numerator 0001 0021
117+
118+
2/3:
119+
0003 0001 0002 0001 0021
120+
121+
4/5:
122+
0005 0001 0004 0001 0021
123+
124+
-2/5:
125+
0005 0001 0002 0001 0022
126+
```
127+
128+
Decimals are six 16-bit words ending in `0023`. As in `.8xn2`, they use
129+
8 packed-BCD significand bytes, then sign byte, then signed base-10
130+
exponent byte. Examples:
131+
132+
```text
133+
4.5:
134+
bytes 00 00 00 00 00 00 00 45 01 00 23 00
135+
words 0000 0000 0000 4500 0001 0023
136+
137+
675.89:
138+
bytes 00 00 00 00 00 90 58 67 01 02 23 00
139+
words 0000 0000 9000 6758 0201 0023
140+
```
141+
142+
Complex numbers reuse the `.8xn2` complex suffixes. `L4.8xl2` shows the
143+
following payloads:
144+
145+
```text
146+
-3i:
147+
0003 0001 001F 0026 008F 007A
148+
149+
-4+2i:
150+
0004 0001 0020 0002 0001 001F 0026 008F 008B
151+
```
152+
153+
The suffixes here match the top-level number samples:
154+
155+
```text
156+
0026 008F 007A negative pure imaginary suffix
157+
0026 008F 008B rectangular real + imag*i suffix
158+
```
159+
160+
## Sample breakdown
161+
162+
`L1.8xl2` is displayed as `{1,2,3}`:
163+
164+
```text
165+
len = 3
166+
arraylen = 11
167+
size = 25
168+
data = 00E5 3 2 1 00D9, then flags 00 00 00
169+
```
170+
171+
Expression words:
172+
173+
```text
174+
00E5
175+
0003 0001 001F
176+
0002 0001 001F
177+
0001 0001 001F
178+
00D9
179+
```
180+
181+
`L2.8xl2` is displayed as `{4.5,675.89}` and stores the two decimal
182+
payloads in reverse order, followed by flags `00 00`.
183+
184+
`L3.8xl2` is displayed as `{2/3,4/5}` and stores `4/5` before `2/3`,
185+
followed by flags `06 06`.
186+
187+
`L4.8xl2` is displayed as `{-4+2i,-3i}` and stores `-3i` before
188+
`-4+2i`, followed by flags `00 00`.
189+
190+
Controlled one-element samples from `more`:
191+
192+
```text
193+
L1 = {0}:
194+
arraylen = 4
195+
data = 00E5 0000 001F 00D9, flags 00
196+
197+
L2 = {1}:
198+
arraylen = 5
199+
data = 00E5 0001 0001 001F 00D9, flags 00
200+
201+
L3 = {-1}:
202+
arraylen = 5
203+
data = 00E5 0001 0001 0020 00D9, flags 00
204+
205+
L4 = {4.5}:
206+
arraylen = 8
207+
data = 00E5 <decimal 4.5> 00D9, flags 00
208+
209+
L5 = {2i}:
210+
arraylen = 7
211+
data = 00E5 0002 0001 001F 0026 008F 00D9, flags 00
212+
213+
L6 = {1/3}:
214+
arraylen = 7
215+
data = 00E5 0003 0001 0001 0001 0021 00D9, flags 06
216+
```
217+
218+
Custom named samples:
219+
220+
```text
221+
(L)A = {1,2}:
222+
stored payload order is 2, then 1
223+
flags 00 00
224+
225+
(L)B = {1/3,4.5}:
226+
stored payload order is 4.5, then 1/3
227+
flags 06 00
228+
229+
(L)ABC = {4+2i,-3i}:
230+
stored payload order is -3i, then 4+2i
231+
flags 00 00
232+
```
233+
234+
`(L)XXX` was created as a formula list from `2L1+3L6`, but the exported
235+
file contains an ordinary cached list value only:
236+
237+
```text
238+
(L)XXX:
239+
name = E836 E817 E817 E817 0000
240+
len = 1
241+
arraylen = 5
242+
data = 00E5 0001 0001 001F 00D9, flags 00
243+
```
244+
245+
No separate formula key or token stream was present in the exported sample.

0 commit comments

Comments
 (0)