From fe6475d322663d40774d86d466003fd9b777f412 Mon Sep 17 00:00:00 2001 From: minjaesong Date: Wed, 17 Jun 2020 09:36:34 +0900 Subject: [PATCH] ^C status wont spill into the next round|memvwr --- assets/JS_INIT.js | 5 ++ assets/bios1.js | 32 +++++++- assets/tbas/basic.js | 38 +++++++--- src/net/torvald/tsvm/Memvwr.kt | 87 ++++++++++++++++++++++ src/net/torvald/tsvm/VM.kt | 20 +++-- src/net/torvald/tsvm/VMGUI.kt | 8 +- src/net/torvald/tsvm/firmware/Firmware.kt | 9 ++- src/net/torvald/tsvm/peripheral/IOSpace.kt | 2 +- 8 files changed, 177 insertions(+), 24 deletions(-) create mode 100644 src/net/torvald/tsvm/Memvwr.kt diff --git a/assets/JS_INIT.js b/assets/JS_INIT.js index b967967..be93bb3 100644 --- a/assets/JS_INIT.js +++ b/assets/JS_INIT.js @@ -39,6 +39,11 @@ con.hiteof = function() { // ^D sys.poke(-40, 1); return (sys.peek(-41) == 32 && (sys.peek(-42) == 129 || sys.peek(-42) == 130)); }; +con.resetkeybuf = function() { + sys.poke(-40, 0); + sys.poke(-41, 0); sys.poke(-42, 0); sys.poke(-43, 0); sys.poke(-44, 0); + sys.poke(-45, 0); sys.poke(-46, 0); sys.poke(-47, 0); sys.poke(-48, 0); +}; con.color_fore = function(n) { // 0..7; -1 for transparent if (n < 0) print(String.fromCharCode(27,91)+"38;5;255m"); diff --git a/assets/bios1.js b/assets/bios1.js index 065d2ff..ead0024 100644 --- a/assets/bios1.js +++ b/assets/bios1.js @@ -1 +1,31 @@ -con.move(1,1); \ No newline at end of file +println("TERRAN Megatrends inc."); +//println("Main RAM:"+(system.maxmem() >> 10)+" KBytes"); + +var memptr = 0; +var memtestptn = [0xAA,0x55,0xAA,0x55 , 0x00,0xFF,0x00,0xFF , 0x01,0x02,0x04,0x08 , 0x10,0x20,0x40,0x80]; + +try { + while (memptr < (8 << 20)) { + // just print a number + con.move(2,1); + print(memptr >> 10); + + // perform memory test + memtestptn.forEach(function(v,i,arr) { + sys.poke(memptr + i, v); + if (v != sys.peek(memptr + i)) throw "Memory Error"; + }); + + memptr += memtestptn.length; + } +} +catch (e) { + if (e == "Memory Error") { + println(" Memory Error"); + } + else { + println(" KB OK"); + } +} + +con.move(4,1); \ No newline at end of file diff --git a/assets/tbas/basic.js b/assets/tbas/basic.js index 8456324..3d1c465 100644 --- a/assets/tbas/basic.js +++ b/assets/tbas/basic.js @@ -18,14 +18,14 @@ var prompt = "Ok"; var lang = {}; lang.badNumberFormat = "Illegal number format"; -lang.badOperatorFormat = "Illegal number format"; +lang.badOperatorFormat = "Illegal operator format"; lang.badFunctionCallFormat = "Illegal function call"; lang.unmatchedBrackets = "Unmatched brackets"; lang.syntaxfehler = function(line, reason) { - return "Syntax error" + ((line !== undefined) ? (" in "+line) : "") + (reason !== undefined) ? (": "+reason) : ""; + return "Syntax error" + ((line !== undefined) ? (" in "+line) : "") + ((reason !== undefined) ? (": "+reason) : ""); }; -lang.illegalType = function(line) { return "Type mismatch" + (line !== undefined) ? (" in "+line) : ""; }; -lang.refError = function(line) { return "Unresolved reference" + (line !== undefined) ? (" in "+line) : ""; }; +lang.illegalType = function(line) { return "Type mismatch" + ((line !== undefined) ? (" in "+line) : ""); }; +lang.refError = function(line) { return "Unresolved reference" + ((line !== undefined) ? (" in "+line) : ""); }; Object.freeze(lang); function getUsedMemSize() { @@ -145,6 +145,16 @@ basicInterpreterStatus.builtin = { basicInterpreterStatus.variables[parsed.name] = new BasicVar(rh, (parsed.type === undefined) ? "float" : parsed.type); }, +"==" : function(lnum, args) { + if (args.length != 2) throw lang.syntaxfehler(lnum); + + var lh = resolve(args[0]); + var rh = resolve(args[1]); + + if (lh === undefined || rh === undefined) throw lang.refError(lnum); + + return (lh == rh); +}, "UNARYMINUS" : function(lnum, args) { if (args.length != 1) throw lang.syntaxfehler(lnum); @@ -1074,13 +1084,18 @@ basicFunctions._executeSyntaxTree = function(lnum, syntaxTree, recDepth) { serial.println(recWedge+"fn call args: "+(args.map(function(it) { return it.type+" "+it.value; })).join(", ")); } - var funcCallResult = func(lnum, args); + try { + var funcCallResult = func(lnum, args); - return new SyntaxTreeReturnObj( - JStoBASICtype(funcCallResult), - funcCallResult, - (basicFunctions._gotoCmds[funcName] !== undefined) ? funcCallResult : lnum + 1 - ); + return new SyntaxTreeReturnObj( + JStoBASICtype(funcCallResult), + funcCallResult, + (basicFunctions._gotoCmds[funcName] !== undefined) ? funcCallResult : lnum + 1 + ); + } + catch (_) { + throw lang.syntaxfehler(lnum, funcName + " is not defined"); + } } else if (syntaxTree.type == "number") { if (_debugExec) serial.println(recWedge+"number"); @@ -1205,6 +1220,7 @@ basicFunctions.run = function(args) { // RUN function break; } } while (linenumber < cmdbuf.length) + con.resetkeybuf(); }; Object.freeze(basicFunctions); while (!tbasexit) { @@ -1229,4 +1245,4 @@ while (!tbasexit) { } println(prompt); } -} +} \ No newline at end of file diff --git a/src/net/torvald/tsvm/Memvwr.kt b/src/net/torvald/tsvm/Memvwr.kt new file mode 100644 index 0000000..7473014 --- /dev/null +++ b/src/net/torvald/tsvm/Memvwr.kt @@ -0,0 +1,87 @@ +package net.torvald.tsvm + +import net.torvald.terrarum.modulecomputers.virtualcomputer.tvd.toUint +import net.torvald.tsvm.peripheral.IOSpace +import java.awt.BorderLayout +import java.awt.Dimension +import java.awt.Font +import javax.swing.JFrame +import javax.swing.JTextArea +import javax.swing.WindowConstants + +class Memvwr(val vm: VM) : JFrame() { + + val memArea = JTextArea() + + fun composeVwrText() { + val sb = StringBuilder() + val io = vm.peripheralTable[0].peripheral as IOSpace + + sb.append("== MMIO ==\n") + + sb.append("Keyboard buffer: ") + for (i in 0L..31L) { + sb.append(io.peek(i)!!.toUByte().toString(16).padStart(2, '0').toUpperCase()) + sb.append(' ') + } + sb.append('\n') + + sb.append("Keyboard/Mouse input latched: ") + sb.append(io.peek(39L) != 0.toByte()) + sb.append('\n') + sb.append("Mouse pos: ") + sb.append((io.peek(32L)!!.toUint() or (io.peek(33L)!!.toUint() shl 8)).toShort()) + sb.append(", ") + sb.append((io.peek(34L)!!.toUint() or (io.peek(35L)!!.toUint() shl 8)).toShort()) + sb.append(" (mouse down: ") + sb.append(io.peek(36L) != 0.toByte()) + sb.append(")\n") + sb.append("Keys pressed: ") + for (i in 40L..47L) { + sb.append(io.peek(i)!!.toUByte().toString(16).padStart(2, '0').toUpperCase()) + sb.append(' ') + } + sb.append('\n') + + sb.append("TTY Keyboard read: ") + sb.append(io.peek(38L) != 0.toByte()) + sb.append('\n') + + sb.append("Counter latched: ") + sb.append(io.peek(68L)!!.toString(2).padStart(8, '0')) + sb.append('\n') + + sb.append("\nBlock transfer status:\n") + for (port in 0..3) { + val status = io.peek(4084L + 2 * port)!!.toUint() or (io.peek(4085L + 2 * port)!!.toUint() shl 8) + + sb.append("== Port ${port + 1}\n") + sb.append(" hasNext: ${(status and 0x8000) != 0}\n") + sb.append(" size of the block: ${if (status and 0xFFF == 0) 4096 else status and 0xFFF}\n") + } + + sb.append("\nBlock transfer control:\n") + for (port in 0..3) { + val status = io.peek(4092L + port)!! + + sb.append("== Port ${port + 1}: ${status.toString(2).padStart(8, '0')}\n") + } + + memArea.text = sb.toString() + } + + fun update() { + composeVwrText() + } + + init { + memArea.font = Font("Monospaced", Font.PLAIN, 12) + memArea.highlighter = null + + this.layout = BorderLayout() + this.isVisible = true + this.add(javax.swing.JScrollPane(memArea), BorderLayout.CENTER) + this.defaultCloseOperation = WindowConstants.EXIT_ON_CLOSE + this.size = Dimension(800, 960) + } +} \ No newline at end of file diff --git a/src/net/torvald/tsvm/VM.kt b/src/net/torvald/tsvm/VM.kt index d53437a..9f705dc 100644 --- a/src/net/torvald/tsvm/VM.kt +++ b/src/net/torvald/tsvm/VM.kt @@ -89,7 +89,7 @@ class VM( 64 ) - println("[VM] Creating new VM with ID of $id, memesize $memsize") + println("[VM] Creating new VM with ID of $id, memsize $memsize") startTime = System.nanoTime() } @@ -146,9 +146,13 @@ class VM( internal fun poke(addr: Long, value: Byte) { val (memspace, offset) = translateAddr(addr) if (memspace == null) - Firmware.errorIllegalAccess(addr) - else if (memspace is UnsafePtr) - memspace.set(offset, value) + throw Firmware.ErrorIllegalAccess(addr) + else if (memspace is UnsafePtr) { + if (addr >= memspace.size) + throw Firmware.ErrorIllegalAccess(addr) + else + memspace.set(offset, value) + } else (memspace as PeriBase).poke(offset, value) } @@ -157,8 +161,12 @@ class VM( val (memspace, offset) = translateAddr(addr) return if (memspace == null) null - else if (memspace is UnsafePtr) - memspace.get(offset) + else if (memspace is UnsafePtr) { + if (addr >= memspace.size) + throw Firmware.ErrorIllegalAccess(addr) + else + memspace.get(offset) + } else (memspace as PeriBase).peek(offset) } diff --git a/src/net/torvald/tsvm/VMGUI.kt b/src/net/torvald/tsvm/VMGUI.kt index 13d68f5..a9473ee 100644 --- a/src/net/torvald/tsvm/VMGUI.kt +++ b/src/net/torvald/tsvm/VMGUI.kt @@ -26,10 +26,12 @@ class VMGUI(val appConfig: LwjglApplicationConfiguration) : ApplicationAdapter() lateinit var coroutineJob: Job + lateinit var memvwr: Memvwr + override fun create() { super.create() - gpu = GraphicsAdapter(vm, lcdMode = true) + gpu = GraphicsAdapter(vm, lcdMode = false) vm.peripheralTable[1] = PeripheralEntry( VM.PERITYPE_TERM, @@ -50,6 +52,8 @@ class VMGUI(val appConfig: LwjglApplicationConfiguration) : ApplicationAdapter() vm.getErrorStream = { gpu.getErrorStream() } vm.getInputStream = { gpu.getInputStream() } + memvwr = Memvwr(vm) + // TEST PRG //val fr = FileReader("./assets/tvdos/command.js") //val fr = FileReader("./assets/jscon.js") @@ -81,6 +85,8 @@ class VMGUI(val appConfig: LwjglApplicationConfiguration) : ApplicationAdapter() override fun render() { Gdx.graphics.setTitle("${AppLoader.appTitle} $EMDASH F: ${Gdx.graphics.framesPerSecond}") + memvwr.update() + super.render() val dt = Gdx.graphics.rawDeltaTime diff --git a/src/net/torvald/tsvm/firmware/Firmware.kt b/src/net/torvald/tsvm/firmware/Firmware.kt index d92fd7d..1dac192 100644 --- a/src/net/torvald/tsvm/firmware/Firmware.kt +++ b/src/net/torvald/tsvm/firmware/Firmware.kt @@ -7,14 +7,15 @@ import org.luaj.vm2.LuaValue import org.luaj.vm2.lib.OneArgFunction import org.luaj.vm2.lib.TwoArgFunction import org.luaj.vm2.lib.ZeroArgFunction +import java.lang.RuntimeException internal class Firmware(val vm: VM) : TwoArgFunction() { + class ErrorIllegalAccess(val addr: Long) : RuntimeException() { + + } + companion object { - fun errorIllegalAccess(addr: Long) { - - } - internal fun translateAddr(vm : VM, addr: LuaValue): Pair { val addr = addr.checklong() return when (addr) { diff --git a/src/net/torvald/tsvm/peripheral/IOSpace.kt b/src/net/torvald/tsvm/peripheral/IOSpace.kt index d6c2eb3..d59ac95 100644 --- a/src/net/torvald/tsvm/peripheral/IOSpace.kt +++ b/src/net/torvald/tsvm/peripheral/IOSpace.kt @@ -94,7 +94,7 @@ class IOSpace(val vm: VM) : PeriBase, InputProcessor { 4088L -> (blockTransferPorts[2].yourBlockSize().toByte()) 4089L -> (blockTransferPorts[2].doYouHaveNext().toInt().shl(7) or blockTransferPorts[2].yourBlockSize().ushr(8).and(15)).toByte() 4090L -> (blockTransferPorts[3].yourBlockSize().toByte()) - 4091L -> (blockTransferPorts[4].doYouHaveNext().toInt().shl(7) or blockTransferPorts[3].yourBlockSize().ushr(8).and(15)).toByte() + 4091L -> (blockTransferPorts[3].doYouHaveNext().toInt().shl(7) or blockTransferPorts[3].yourBlockSize().ushr(8).and(15)).toByte() in 4092..4095 -> composeBlockTransferStatus(adi - 4092).toByte()