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