added the TI-74 BASIC port and the mu808asm'MU74 export support

This commit is contained in:
Luxferre
2025-04-27 16:53:48 +03:00
parent 66c5befb9b
commit 192656fef8
3 changed files with 152 additions and 2 deletions
+57 -1
View File
@@ -303,7 +303,10 @@ Reference implementations
* [Python 3](mu808asm.py): supports assembling MU8A source files into both
plain text (MU8) and binary (MU8B) machine code formats. Also supports
disassembling MU8 and MU8B files into their MU8A sources and converting
machine code between MU8 and MU8B formats.
machine code between MU8 and MU8B formats. Additionally, this assembler
implementation provides the `t74` mode to convert plaintext MU8 machine code
into the format suitable for entering into TI-74 BASIC for running on the
TI-74 port of mu808 (see below).
These lists are going to be expanded as soon as new reference implementations
appear.
@@ -331,6 +334,59 @@ keys of the standard phone keypad, the following convention is recommended:
* the `#` (pound) key actually confirms entering a single number field, and
all instructions are required to contain exactly five numbers.
Retro/minimal platform implementations
--------------------------------------
Here's the list of known/existing mu808 implementations that adhere to the
specification to most extent and run compatible machine code but cannot
provide full operating environment functionality due to the limits of the
platform itself.
### TI-74 BASIC
The [mu808.b74](mu808.b74) file contains a BASIC port of mu808 for the Texas
Instruments TI-74 portable computer (tested on the TI-74S variant). Due to
the resource constraints, the following limitations apply:
* only 149 program steps and 256 data cells supported (adjustable at line 110),
* no interactive mode (the `RUN` command directly executes the predefined
program in the VM),
* the program itself is entered into the DATA statements in the so-called
MU74 format (see below),
* no support for I/O port 2, tracing or intruction dumping,
* no boundary checks for the addresses inside the program.
Also, since the VM runs on top of a BASIC interpreter, program execution is
extremely slow most of the time. Keep in mind, this is more of a proof of
concept than a viable solution, and using the "native" TI BASIC is preferred
for any serious computing on that machine.
In order to store your programs on the device to run via this mu808 VM version,
you need to enter them in DATA statements in two-number pairs starting from
`DATA 0,0` at the BASIC line 5000. The last `DATA` line of the program must be
`DATA -1,0`. In between these two, every program instruction `lno cmd a1 a2 a3`
must be compressed into the form:
```
[5000+lno] DATA [cmd*10000 + a1], [a2 * 10000 + a3]
```
This storage format is called MU74. For example, the compound interest
calculator from the official mu808 examples will transform into:
```
5000 DATA 0,0
5001 DATA 50100,1
5002 DATA 40002,30000
5003 DATA 90002,10004
5004 DATA 50001,5
5005 DATA 70005,40005
5006 DATA 130001,50005
5007 DATA 70000,30005
5008 DATA 130000,50005
5009 DATA 30005,50000
5010 DATA -1,0
```
To make the conversion easier, the official mu808 assembler, `mu808asm.py`, now
supports the `t74` mode that accepts a plain MU8 machine code file and outputs
the same program in the MU74 format.
FAQ
---
+64
View File
@@ -0,0 +1,64 @@
100 RANDOMIZE:RAD
110 DIM PMEM(300),DMEM(256)
120 RESTORE 5000
130 I=0
140 READ PMEM(I), PMEM(I+1)
150 I=I+2
160 IF PMEM(I-2)>-1 THEN 140
170 L=1:IAT,V1,V2,V3=0
180 M=L+L:A=PMEM(M):B=PMEM(M+1)
190 IF A<0 THEN 730
200 CMD=INT(A/10000)
210 IF IAT=1 THEN 220 ELSE 230
220 X=INT(V1):Y=INT(V2):Z=INT(V3):IAT=0:GOTO 240
230 X=A-CMD*10000:Y=INT(B/10000):Z=B-Y*10000
240 V1,V2,V3=0
250 IF CMD=5 THEN DMEM(Z)=X+(Y/10000):GOTO 720
260 V1=DMEM(X):V2=DMEM(Y):V3=DMEM(Z)
270 IF CMD=1 THEN 280 ELSE 420
280 IF X=0 AND V2=0 THEN L=Z-1:GOTO 720
290 IF X=1 AND V2>0 THEN L=Z-1:GOTO 720
300 IF X=2 AND V2<0 THEN L=Z-1:GOTO 720
310 IF X=3 AND V2>=0 THEN L=Z-1:GOTO 720
320 IF X=4 AND V2<=0 THEN L=Z-1:GOTO 720
330 IF X=5 AND V2<>0 THEN L=Z-1:GOTO 720
340 IF X=6 THEN L=Z-1:GOTO 720
350 IF X=7 AND V2=0 THEN L=INT(V3)-1:GOTO 720
360 IF X=8 AND V2>0 THEN L=INT(V3)-1:GOTO 720
370 IF X=9 AND V2<0 THEN L=INT(V3)-1:GOTO 720
380 IF X=10 AND V2>=0 THEN L=INT(V3)-1:GOTO 720
390 IF X=11 AND V2<=0 THEN L=INT(V3)-1:GOTO 720
400 IF X=12 AND V2<>0 THEN L=INT(V3)-1:GOTO 720
410 IF X=13 THEN L=INT(V3)-1:GOTO 720
420 IF CMD=2 THEN IAT=1:GOTO 720
430 IF CMD=3 THEN 440 ELSE 490
440 FOR I=X TO Y
450 IF Z=0 THEN PRINT(DMEM(I)):PAUSE
460 IF Z=1 THEN 470 ELSE 480
470 IF DMEM(I)=10 THEN PAUSE ELSE PRINT(CHR$(INT(DMEM(I))));
480 NEXT I:GOTO 720
490 IF CMD=4 THEN 500 ELSE 530
500 FOR I=X TO Y
510 IF Z=0 THEN INPUT DMEM(I)
520 NEXT I:GOTO 720
530 IF CMD=6 THEN 540 ELSE 570
540 IF X=0 THEN DMEM(Z)=Y:GOTO 720
550 IF X=1 THEN DMEM(Z)=V2:GOTO 720
560 IF X>1 THEN DMEM(INT(V3))=DMEM(INT(V2)):GOTO 720
570 IF CMD=7 THEN DMEM(Z)=V1+V2*V3:GOTO 720
580 IF CMD=8 THEN DMEM(Z)=V1-V2:GOTO 720
590 IF CMD=9 THEN 600 ELSE 610
600 IF V2=0 THEN DMEM(Z)=0:GOTO 720 ELSE DMEM(Z)=V1/V2:GOTO 720
610 IF CMD=10 THEN 620 ELSE 630
620 IF V2=0 THEN DMEM(Z)=INT(V1):GOTO 720 ELSE DMEM(Z)=V1-V2*INT(V1/V2):GOTO 720
630 IF CMD=11 THEN DMEM(Z)=ABS(V2):GOTO 720
640 IF CMD=12 THEN DMEM(Z)=SQR(ABS(V2)):GOTO 720
650 IF CMD=13 THEN 660 ELSE 670
660 IF X=0 THEN DMEM(Z)=EXP(V2):GOTO 720 ELSE DMEM(Z)=LN(ABS(V2)):GOTO 720
670 IF CMD=14 THEN 680 ELSE 710
680 IF X=0 THEN DMEM(Z)=SIN(V2):GOTO 720
690 IF X=1 THEN DMEM(Z)=COS(V2):GOTO 720
700 IF X>1 THEN DMEM(Z)=ATN(V2):GOTO 720
710 IF CMD=15 THEN DMEM(Z)=INT(V1)+INT(RND*(INT(V2)-INT(V1)+1))
720 L=L+1:GOTO 180
730 END
+31 -1
View File
@@ -1,7 +1,7 @@
#!/usr/bin/env python3
# a simple assembler/disassembler for the mu808 VM
# supports both text and binary program formats
# usage: mu808asm [at|ab|dt|db|t2b|b2t] file outfile
# usage: mu808asm [at|ab|dt|db|t2b|b2t|t74] file outfile
# modes:
# at: assemble to plaintext (MU8) machine code
# ab: assemble to binary (MU8B) machine code
@@ -9,6 +9,7 @@
# db: disassemble binary (MU8B) machine code
# t2b: convert from plaintext MU8 to binary MU8B
# b2t: convert from binary MU8B to plaintext MU8
# t74: convert from plaintext MU8 to the TI-74 representation
import sys, re, struct
@@ -132,6 +133,33 @@ def totext(binrep):
out += ' '.join([str(lno), str(cmd), str(x), str(y), str(z)]) + '\n'
return out
# converts the MU8 plaintext machine code to the TI-74 DATA statements (MU74)
def ti74data(txtrep:str, baseaddr:int=5000):
instrs = [] # instruction list to store here
vreg = re.compile(r'\s+')
iindex = 0
instr = []
for instrpart in vreg.split(txtrep):
if iindex == 5:
instrs.append(instr)
instr = []
iindex = 0
if len(instrpart) > 0:
instr.append(int(instrpart))
iindex += 1
# now, instrs contains 5-number groups
out = f'{baseaddr} DATA 0,0\n'
maxlno = 0
for instr in instrs:
lno, cmd, x, y, z = instr
if lno > maxlno:
maxlno = lno
a = cmd*10000 + x
b = y*10000 + z
out += f'{baseaddr + lno} DATA {a},{b}\n'
out += f'{baseaddr + maxlno + 1} DATA -1,0\n'
return out
def main():
if len(sys.argv) < 4:
print("Usage: mu808asm [at|ab|dt|db|t2b|b2t] file outfile")
@@ -162,6 +190,8 @@ def main():
elif mode == 'db': # disassemble binary
srctext = totext(srctext)
output = disassemble(srctext)
elif mode == 't74': # convert to TI-74 DATA statements
output = ti74data(srctext)
else: # assemble
output = assemble(srctext) # default mode
if mode == 'ab':