Commit | Line | Data |
---|---|---|
48f88489 AT |
1 | @ (c) 2020 Aaron Taylor <ataylor at subgeniuskitty dot com> |
2 | @ See LICENSE.txt file for copyright and license details. | |
3 | ||
8bed3ccd AT |
4 | #ifndef VVS_STDLIB_STDIO |
5 | #define VVS_STDLIB_STDIO | |
6 | ||
7 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
bb21580a | 8 | @ Name: |
b8b65c17 | 9 | @ printstackstring (1000100) |
8bed3ccd | 10 | @ Description: |
bb21580a | 11 | @ Prints a null-terminated string from the stack. |
8bed3ccd AT |
12 | @ Call Stack: |
13 | @ null-terminator (ASCII '\0') | |
14 | @ char n | |
15 | @ ... | |
16 | @ char 2 | |
17 | @ char 1 <-- TOS | |
18 | @ Return Stack: | |
19 | @ <empty> | |
20 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
b8b65c17 | 21 | NSSVTSSSTSSN | Mark: 1000100 (print string from stack) |
32c440bf | 22 | SNS | DUP |
b8b65c17 | 23 | NTSSTSSSTSSSSSSSSSTN | BRZ > 01000100 00000001 |
32c440bf | 24 | TNSS | Print character |
b8b65c17 AT |
25 | NSNTSSSTSSN | JMP > 1000100 |
26 | NSSVSTSSSTSSSSSSSSSTN | Mark: 01000100 00000001 | |
32c440bf AT |
27 | SNN | DROP |
28 | NTN | RTS | |
29 | ||
8bed3ccd | 30 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ |
bb21580a | 31 | @ Name: |
b8b65c17 | 32 | @ printheapstring (1000101) |
8bed3ccd | 33 | @ Description: |
bb21580a | 34 | @ Prints a null-terminated string from the heap. |
8bed3ccd AT |
35 | @ Call Stack: |
36 | @ pointer to first character <-- TOS | |
37 | @ Return Stack: | |
38 | @ <empty> | |
39 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
b8b65c17 | 40 | NSSVTSSSTSTN | Mark: 1000101 (print string from heap) |
32c440bf AT |
41 | SNS | DUP |
42 | TTT | LOAD | |
43 | SNS | DUP | |
b8b65c17 | 44 | NTSSTSSSTSTSSSSSSSTN | BRZ > 01000101 00000001 |
32c440bf AT |
45 | TNSS | Print character |
46 | SSSTN | Push +1 | |
47 | TSSS | ADD | |
b8b65c17 AT |
48 | NSNTSSSTSTN | JMP > 1000101 |
49 | NSSVSTSSSTSTSSSSSSSTN | Mark: 01000101 00000001 | |
32c440bf AT |
50 | SNN | DROP |
51 | SNN | DROP | |
52 | NTN | RTS | |
8bed3ccd | 53 | |
3625ff3a | 54 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ |
bb21580a | 55 | @ Name: |
23d17247 | 56 | @ printstacknumber (1001) |
3625ff3a | 57 | @ Description: |
bb21580a | 58 | @ Prints 'number' from the stack in sign-magnitude format. |
3625ff3a AT |
59 | @ Leading zeros are suppressed. |
60 | @ Call Stack: | |
bb21580a | 61 | @ number <-- TOS |
3625ff3a AT |
62 | @ Return Stack: |
63 | @ <empty> | |
64 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
23d17247 | 65 | NSSVTSSTN | Mark: 1001 (print number from stack) |
3625ff3a | 66 | SNS | DUP |
149f16fd AT |
67 | NSTTSSSSTSN | JSR > 1000010 (printstacknumbersign) |
68 | NSTTSSSSTTN | JSR > 1000011 (printstacknumbermagnitude) | |
3625ff3a AT |
69 | NTN | RTS |
70 | ||
71 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
bb21580a | 72 | @ Name: |
ae1f85a1 | 73 | @ printstacknumbersign (1000010) |
3625ff3a | 74 | @ Description: |
bb21580a | 75 | @ Prints the sign of 'number' from the stack. |
3625ff3a | 76 | @ Call Stack: |
bb21580a | 77 | @ number <-- TOS |
3625ff3a AT |
78 | @ Return Stack: |
79 | @ <empty> | |
80 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
ae1f85a1 AT |
81 | NSSVTSSSSTSN | Mark: 1000010 (print sign of number from stack) |
82 | NTTSTSSSSTSSSSSSSSTN | BMI > 01000010 00000001 | |
3625ff3a | 83 | SSSTSTSTTN | PUSH ASCII '+' |
ae1f85a1 AT |
84 | NSNSTSSSSTSSSSSSSTSN | JMP > 01000010 00000010 |
85 | NSSVSTSSSSTSSSSSSSSTN | Mark: 01000010 00000001 | |
3625ff3a | 86 | SSSTSTTSTN | PUSH ASCII '-' |
ae1f85a1 | 87 | NSSVSTSSSSTSSSSSSSTSN | Mark: 01000010 00000010 |
3625ff3a AT |
88 | TNSS | PUTC |
89 | NTN | RTS | |
90 | ||
91 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
bb21580a | 92 | @ Name: |
ae1f85a1 | 93 | @ printstacknumbermagnitude (1000011) |
3625ff3a | 94 | @ Description: |
bb21580a | 95 | @ Prints the magnitude of 'number' from the stack. |
3625ff3a | 96 | @ Call Stack: |
bb21580a | 97 | @ number <-- TOS |
3625ff3a AT |
98 | @ Return Stack: |
99 | @ <empty> | |
100 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
bb21580a | 101 | #include <math.pvvs> |
ae1f85a1 | 102 | NSSVTSSSSTTN | Mark: 1000011 (print magnitude of number from stack) |
3625ff3a | 103 | |
acd78c53 AT |
104 | @ Catch -(2^63) as a special case since its absolute value will overflow |
105 | @ a twos-complement 64-bit word. | |
106 | SNS | DUP | |
107 | SSTTSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSSN | -(2^63) | |
108 | TSST | SUBTRACT | |
109 | NTSSTSSSSTTSSSSSSTSN | BRZ > 01000011 00000010 | |
110 | ||
111 | @ No special case applies. Prepare for computation by converting the number | |
112 | @ to absolute value and preparing a string on the stack. | |
113 | NSTTSSSTN | JSR > 10001 (absolute value) | |
3625ff3a AT |
114 | SSSSN | PUSH ASCII '\0' |
115 | SNT | SWAP | |
116 | ||
117 | @ Pick off one digit on each pass through this loop. | |
ae1f85a1 | 118 | NSSVSTSSSSTTSSSSSSSSN | Mark: 01000011 00000000 |
3625ff3a AT |
119 | SNS | DUP |
120 | ||
121 | @ Mod-off a digit, convert to ASCII, store on stack as part of the string. | |
122 | SSSTSTSN | PUSH +10 | |
123 | TSTT | MODULO | |
124 | SSSTTSSSSN | PUSH ASCII '0' | |
125 | TSSS | ADD | |
126 | SNT | SWAP | |
127 | ||
128 | @ Divide down to next digit and keep looping if number != 0 yet. | |
129 | SSSTSTSN | PUSH +10 | |
130 | TSTS | DIVIDE | |
131 | SNS | DUP | |
ae1f85a1 AT |
132 | NTSSTSSSSTTSSSSSSSTN | BRZ > 01000011 00000001 |
133 | NSNSTSSSSTTSSSSSSSSN | JMP > 01000011 00000000 | |
3625ff3a AT |
134 | |
135 | @ Print the string we have built on the stack. | |
ae1f85a1 | 136 | NSSVSTSSSSTTSSSSSSSTN | Mark: 01000011 00000001 |
3625ff3a | 137 | SNN | DROP |
45abb94e | 138 | NSTTSSSTSSN | JSR > 1000100 (print string from stack) |
3625ff3a AT |
139 | NTN | RTS |
140 | ||
acd78c53 AT |
141 | @ Replace the number on the stack with its decimal ASCII representation. |
142 | NSSVSTSSSSTTSSSSSSTSN | BRZ > 01000011 00000010 | |
143 | SNN | DROP | |
144 | A"-9223372036854775808" | |
145 | NSNSTSSSSTTSSSSSSSTN | JMP > 01000011 00000001 | |
146 | ||
23d17247 AT |
147 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ |
148 | @ Name: | |
149 | @ printf | |
150 | @ Description: | |
151 | @ If printing a static string (i.e. no substitutions), pass | |
152 | @ 'number of substitutions' as 0, immediately followed by 'string word 1'. | |
153 | @ If printing a string from the heap instead of stack, pass an empty string | |
154 | @ on the stack followed by a pointer to the first word of the | |
155 | @ null-terminated string on the heap. | |
156 | @ For example: | |
157 | @ pointer | |
158 | @ ASCII '\0' | |
159 | @ substitution n | |
160 | @ <remainder of call stack is unchanged> | |
6cb31a3e AT |
161 | @ Maximum substitutions determined by upper heap limit in stackrotate and |
162 | @ stackrotatereverse subroutines. | |
23d17247 AT |
163 | @ Call Stack: |
164 | @ ACSII '\0' | |
165 | @ string word n | |
166 | @ ... | |
167 | @ string word 1 | |
168 | @ substitution n | |
169 | @ ... | |
170 | @ substitution 1 | |
171 | @ number of substitutions <-- TOS | |
172 | @ Return Stack: | |
173 | @ <empty> | |
174 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
149f16fd | 175 | #include <stack.pvvs> |
23d17247 AT |
176 | NSSVTSSSN | Mark: 1000 (printf) |
177 | ||
23d17247 AT |
178 | @ If the stack contains an empty string (i.e. just an ASCII '\0'), the next |
179 | @ word is a pointer we must use to load the string from the heap. | |
6cb31a3e | 180 | @ This will leave the stack looking exactly like the example call stack above. |
23d17247 AT |
181 | @ Do the test this way so we can keep the code inline. |
182 | SNS | DUP | |
6cb31a3e AT |
183 | SSSTSN | PUSH 2 |
184 | TSSS | ADD | |
185 | NSTTTSSN | JSR > 1100 (deepdup) | |
23d17247 AT |
186 | SSTTN | PUSH -1 |
187 | TSSN | MULTIPLY | |
188 | NTTSSSSTSSSSSSSSSSTN | BMI > 00001000 00000001 | |
6cb31a3e AT |
189 | SNS | DUP |
190 | SSSTSN | PUSH 2 | |
191 | TSSS | ADD | |
192 | NSTTSTTN | JSR > 1011 (stackrotatereverse) | |
23d17247 AT |
193 | SNN | DROP |
194 | SNS | DUP | |
6cb31a3e AT |
195 | SSSTSN | PUSH 2 |
196 | TSSS | ADD | |
197 | NSTTSTTN | JSR > 1011 (stackrotatereverse) | |
198 | NSTSSSSTSSSTSSSTTSSN | JSR > 00001000 10001100 (printf_deepslurp) | |
23d17247 AT |
199 | |
200 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
201 | @ The rest of printf parses a string according to the following information. | |
202 | @ ASCII '\ ': | |
203 | @ ASCII '\ ': putchar '\ ' | |
204 | @ ASCII '%': putchar '%' | |
205 | @ ASCII 'n': putchar '\n' | |
206 | @ ASCII 't': putchar '\t' | |
207 | @ ASCII '%': | |
208 | @ ASCII 'c': (print character) | |
209 | @ ASCII 's': (print string) | |
210 | @ ASCII 'd': (print decimal digit) | |
211 | @ ASCII 'u': (print abs(integer), w/o sign) | |
212 | @ ASCII 'i': (print integer w/sign) | |
213 | @ ASCII '\0': | |
214 | @ cleanup and exit | |
215 | @ default: | |
216 | @ putchar | |
217 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
218 | ||
219 | @@@@@@@@@@@@@@@@@@@@ | |
6cb31a3e | 220 | @ The next block tests the char against all possible level 1 branches (see above). |
23d17247 AT |
221 | @ If there is a match, execution jumps to the appropriate level 2 branch label. |
222 | @ If no match is found, print the character and move on. | |
223 | @@@@@@@@@@@@@@@@@@@@ | |
224 | NSSVSSSSTSSSSSSSSSSTN | Mark: 00001000 00000001 | |
6cb31a3e AT |
225 | @ Move the next character of the string to TOS. |
226 | NSTSSSSTSSSTSSSTSTTN | JSR > 00001000 10001011 (next char to TOS) | |
23d17247 AT |
227 | @ TOS is an ASCII '\ '. Jump to process the possible level 2 branches. |
228 | SNS | DUP | |
229 | SSSTSTTTSSN | PUSH ASCII slash | |
230 | TSST | SUBTRACT | |
231 | NTSSSSSTSSSSSSSSSTSN | BRZ > 00001000 00000010 | |
232 | @ TOS is an ASCII '%'. Jump to process the possible level 2 branches. | |
233 | SNS | DUP | |
234 | SSSTSSTSTN | PUSH ASCII '%' | |
235 | TSST | SUBTRACT | |
236 | NTSSSSSTSSSSSSSSSTTN | BRZ > 00001000 00000011 | |
237 | @ TOS is an ASCII "\0". Jump to clean-up-and-exit. | |
238 | SNS | DUP | |
239 | NTSSSSSTSSSSSSSSSSSN | BRZ > 00001000 00000000 | |
240 | @ TOS is a normal character. Print it and loop again. | |
241 | TNSS | PUTC | |
242 | NSNSSSSTSSSSSSSSSSTN | JMP > 00001000 00000001 | |
243 | ||
244 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
245 | @ Level 2 - ASCII '\ ' - Escapes | |
246 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
247 | ||
248 | @@@@@@@@@@@@@@@@@@@@ | |
249 | @ The level 1 match was an ASCII '\ '. | |
250 | @ Now look for level 2 matches that trigger a character substitution (n -> newline, etc). | |
251 | @ If no matches are found, print the character directly (e.g. "\%" -> '%') | |
252 | @ When finished, loop back to testing level 1 branches. | |
253 | @@@@@@@@@@@@@@@@@@@@ | |
254 | NSSVSSSSTSSSSSSSSSTSN | Mark: 00001000 00000010 | |
255 | SNN | DROP | |
6cb31a3e AT |
256 | @ Move the next character of the string to TOS. |
257 | NSTSSSSTSSSTSSSTSTTN | JSR > 00001000 10001011 (next char to TOS) | |
23d17247 AT |
258 | @ Check for ASCII '\n' |
259 | SNS | DUP | |
260 | SSSTTSTTTSN | PUSH ASCII 'n' | |
261 | TSST | SUBTRACT | |
262 | NTSSSSSTSSSSSSSSTSSN | BRZ > 00001000 00000100 | |
263 | @ Check for ASCII '\t' | |
264 | SNS | DUP | |
08a3a286 | 265 | SSSTTTSTSSN | PUSH ASCII 't' |
23d17247 AT |
266 | TSST | SUBTRACT |
267 | NTSSSSSTSSSSSSSSTSTN | BRZ > 00001000 00000101 | |
268 | @ No substitution necessary. Print literally. | |
269 | TNSS | PUTC | |
270 | NSNSSSSTSSSSSSSSSSTN | JMP > 00001000 00000001 | |
271 | ||
272 | @@@@@@@@@@@@@@@@@@@@ | |
273 | @ These are utility labels to output the appropriate non-printable ASCII character. | |
274 | @ After output, they loop back to testing level 1 branches. | |
275 | @@@@@@@@@@@@@@@@@@@@ | |
276 | ||
277 | @ Print a newline and loop for the next character. | |
278 | NSSVSSSSTSSSSSSSSTSSN | Mark: 00001000 00000100 | |
279 | SNN | DROP | |
280 | SSSTSTSN | PUSH ASCII '\n' | |
281 | TNSS | PUTC | |
282 | NSNSSSSTSSSSSSSSSSTN | JMP > 00001000 00000001 | |
283 | ||
284 | @ Print a horizontal tab and loop for the next character. | |
285 | NSSVSSSSTSSSSSSSSTSTN | Mark: 00001000 00000101 | |
286 | SNN | DROP | |
287 | SSSTSSTN | PUSH ASCII '\t' | |
288 | TNSS | PUTC | |
289 | NSNSSSSTSSSSSSSSSSTN | JMP > 00001000 00000001 | |
290 | ||
291 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
292 | @ Level 2 - ASCII '%' - Substitutions | |
293 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
294 | ||
295 | @@@@@@@@@@@@@@@@@@@@ | |
296 | @ The level 1 match was an ASCII '%'. | |
297 | @ Now look for level 2 matches that trigger a substitution. | |
298 | @ When finished, loop back to testing level 1 branches. | |
299 | @@@@@@@@@@@@@@@@@@@@ | |
300 | NSSVSSSSTSSSSSSSSSTTN | Mark: 00001000 00000011 | |
301 | SNN | DROP | |
6cb31a3e AT |
302 | @ Move the next character of the string to TOS. |
303 | NSTSSSSTSSSTSSSTSTTN | JSR > 00001000 10001011 (next char to TOS) | |
23d17247 AT |
304 | @ Check for ASCII 'c' - Print character |
305 | SNS | DUP | |
306 | SSSTTSSSTTN | PUSH ASCII 'c' | |
307 | TSST | SUBTRACT | |
308 | NTSSSSSTSSSSSSSSTTSN | BRZ > 00001000 00000110 | |
309 | @ Check for ASCII 's' - Print string | |
310 | SNS | DUP | |
311 | SSSTTTSSTTN | PUSH ASCII 's' | |
312 | TSST | SUBTRACT | |
313 | NTSSSSSTSSSSSSSSTTTN | BRZ > 00001000 00000111 | |
314 | @ Check for ASCII 'd' - Print decimal digit | |
315 | SNS | DUP | |
316 | SSSTTSSTSSN | PUSH ASCII 'd' | |
317 | TSST | SUBTRACT | |
318 | NTSSSSSTSSSSSSSTSSSN | BRZ > 00001000 00001000 | |
319 | @ Check for ASCII 'u' - Print unsigned number | |
320 | SNS | DUP | |
321 | SSSTTTSTSTN | PUSH ASCII 'u' | |
322 | TSST | SUBTRACT | |
323 | NTSSSSSTSSSSSSSTSSTN | BRZ > 00001000 00001001 | |
324 | @ Check for ASCII 'i' - Print signed number | |
325 | SNS | DUP | |
326 | SSSTTSTSSTN | PUSH ASCII 'i' | |
327 | TSST | SUBTRACT | |
328 | NTSSSSSTSSSSSSSTSTSN | BRZ > 00001000 00001010 | |
329 | @ Unrecognized substitution specifier. | |
330 | @ For now, silently consume it and continue. | |
331 | @ Do not increment the substitution counter. | |
332 | @ TODO: Is this really what I want to do here? | |
333 | SNN | DROP | |
334 | NSNSSSSTSSSSSSSSSSTN | JMP > 00001000 00000001 | |
335 | ||
336 | ||
337 | @@@@@@@@@@@@@@@@@@@@ | |
338 | @ These are utility labels to call the appropriate type of output subroutine. | |
6cb31a3e AT |
339 | @ After output, they decrement the substition counter and loop back to testing |
340 | @ level 1 branches. | |
23d17247 AT |
341 | @@@@@@@@@@@@@@@@@@@@ |
342 | ||
343 | @ Print a character | |
344 | NSSVSSSSTSSSSSSSSTTSN | Mark: 00001000 00000110 | |
345 | SNN | DROP | |
6cb31a3e | 346 | SNT | SWAP |
23d17247 | 347 | TNSS | PUTC |
6cb31a3e AT |
348 | SSSTN | PUSH 1 |
349 | TSST | SUBTRACT | |
23d17247 AT |
350 | NSNSSSSTSSSSSSSSSSTN | JMP > 00001000 00000001 |
351 | @ Print a string | |
352 | NSSVSSSSTSSSSSSSSTTTN | Mark: 00001000 00000111 | |
353 | SNN | DROP | |
6cb31a3e | 354 | SNT | SWAP |
23d17247 | 355 | NSTTSSSTSTN | JSR > 1000101 (print string from heap) |
6cb31a3e AT |
356 | SSSTN | PUSH 1 |
357 | TSST | SUBTRACT | |
23d17247 AT |
358 | NSNSSSSTSSSSSSSSSSTN | JMP > 00001000 00000001 |
359 | @ Print a decimal digit | |
360 | NSSVSSSSTSSSSSSSTSSSN | Mark: 00001000 00001000 | |
361 | SNN | DROP | |
6cb31a3e | 362 | SNT | SWAP |
23d17247 | 363 | TNST | PUTDIGIT |
6cb31a3e AT |
364 | SSSTN | PUSH 1 |
365 | TSST | SUBTRACT | |
23d17247 AT |
366 | NSNSSSSTSSSSSSSSSSTN | JMP > 00001000 00000001 |
367 | @ Print an unsigned integer | |
368 | NSSVSSSSTSSSSSSSTSSTN | Mark: 00001000 00001001 | |
369 | SNN | DROP | |
6cb31a3e | 370 | SNT | SWAP |
23d17247 | 371 | NSTTSSSSTTN | JSR > 1000011 (print magnitude of number from stack) |
6cb31a3e AT |
372 | SSSTN | PUSH 1 |
373 | TSST | SUBTRACT | |
23d17247 AT |
374 | NSNSSSSTSSSSSSSSSSTN | JMP > 00001000 00000001 |
375 | @ Print a signed integer | |
376 | NSSVSSSSTSSSSSSSTSTSN | Mark: 00001000 00001010 | |
377 | SNN | DROP | |
6cb31a3e | 378 | SNT | SWAP |
23d17247 | 379 | NSTTSSTN | JSR > 1001 (print number from stack) |
6cb31a3e AT |
380 | SSSTN | PUSH 1 |
381 | TSST | SUBTRACT | |
23d17247 AT |
382 | NSNSSSSTSSSSSSSSSSTN | JMP > 00001000 00000001 |
383 | ||
384 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
385 | @ These are misc labels associated with the printf function. | |
386 | @@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@@ | |
387 | ||
6cb31a3e AT |
388 | @ Found an ASCII "\0" when processing the format string. Clean up and exit. |
389 | NSSVSSSSTSSSSSSSSSSSN | Mark: 00001000 00000000 | |
390 | SNN | DROP | |
2da74194 | 391 | SNN | DROP |
6cb31a3e AT |
392 | NTN | RTS |
393 | ||
394 | @ Move the next string character to TOS. | |
395 | @ Stack should look like the printf call stack, with num-of-subs at TOS. | |
396 | NSSVSSSSTSSSTSSSTSTTN | Mark: 00001000 10001011 (next char to TOS) | |
397 | SNS | DUP | |
398 | SSSTSN | PUSH 2 | |
23d17247 | 399 | TSSS | ADD |
6cb31a3e | 400 | NSTTSTTN | JSR > 1011 (stackrotatereverse) |
23d17247 AT |
401 | NTN | RTS |
402 | ||
6cb31a3e AT |
403 | @ Slurps a string from the heap to the stack, storing it behind the substitutions. |
404 | @ Call Stack: | |
405 | @ substitution n | |
406 | @ ... | |
407 | @ substitution 1 | |
408 | @ number of substitutions <-- TOS | |
409 | @ pointer to string | |
410 | @ Return Stack: | |
411 | @ ACSII '\0' | |
412 | @ string word n | |
413 | @ ... | |
414 | @ string word 1 | |
415 | @ substitution n | |
416 | @ ... | |
417 | @ substitution 1 | |
418 | @ number of substitutions <-- TOS | |
419 | @ TODO: This, along with a deepspew, should probably be stdlib routines. | |
420 | NSSVSSSSTSSSTSSSTTSSN | Mark: 00001000 10001100 (printf_deepslurp) | |
421 | SNS | DUP | |
422 | @ Advance a duplicate copy of the pointer until it points to the null-terminator. | |
423 | NSSVSSSSTSSSTSSSTTSTN | Mark: 00001000 10001101 | |
424 | SNS | DUP | |
425 | TTT | LOAD | |
426 | NTSSSSSTSSSTSSSTTTSN | BRZ > 00001000 10001110 | |
427 | SSSTN | PUSH 1 | |
428 | TSSS | ADD | |
429 | NSNSSSSTSSSTSSSTTSTN | JMP > 00001000 10001101 | |
430 | @ Load a character to the stack on each pass through this loop. | |
431 | NSSVSSSSTSSSTSSSTTTSN | Mark: 00001000 10001110 | |
432 | SNS | DUP | |
433 | TTT | LOAD | |
434 | SSSTSSN | PUSH 4 | |
435 | NSTTTSSN | JSR > 1100 (deepdup) | |
436 | SSSTSSN | PUSH 4 | |
437 | TSSS | ADD | |
438 | NSTTSTSN | JSR > 1010 (stackrotate) | |
439 | @ Test for end of loop. | |
440 | SNS | DUP | |
441 | SSSTTN | PUSH 3 | |
442 | NSTTTSSN | JSR > 1100 (deepdup) | |
443 | TSST | SUBTRACT | |
444 | NTSSSSSTSSSTSSSTTTTN | BRZ > 00001000 10001111 | |
445 | @ Decrement pointer to end of string, loop again. | |
446 | SSSTN | PUSH 1 | |
447 | TSST | SUBTRACT | |
448 | NSNSSSSTSSSTSSSTTTSN | JMP > 00001000 10001110 | |
449 | @ Clean up and return. | |
450 | NSSVSSSSTSSSTSSSTTTTN | Mark: 00001000 10001111 | |
451 | SNN | DROP | |
23d17247 AT |
452 | SNN | DROP |
453 | NTN | RTS | |
454 | ||
8bed3ccd | 455 | #endif |