From 0eda7ac498bed941d9e843ff295be5208d6951c1 Mon Sep 17 00:00:00 2001 From: Irmen de Jong Date: Sun, 30 Oct 2022 16:44:13 +0100 Subject: [PATCH] vm: don't crash on empty code chunks --- compiler/test/vm/TestCompilerVirtual.kt | 40 +++++++++++++++---- virtualmachine/src/prog8/vm/VirtualMachine.kt | 28 +++++++------ 2 files changed, 49 insertions(+), 19 deletions(-) diff --git a/compiler/test/vm/TestCompilerVirtual.kt b/compiler/test/vm/TestCompilerVirtual.kt index e6af64fd8..2d170f43a 100644 --- a/compiler/test/vm/TestCompilerVirtual.kt +++ b/compiler/test/vm/TestCompilerVirtual.kt @@ -84,8 +84,37 @@ main { uword i uword k - while k <= 10 { - k++ + repeat { +mylabel0: + goto mylabel0 + } + + while cx16.r0 { +mylabel1: + goto mylabel1 + } + + do { +mylabel2: + goto mylabel2 + } until cx16.r0 + +; TODO fix this for vm codegen: + repeat cx16.r0 { +mylabel3: + goto mylabel3 + } + +; TODO fix this for vm codegen: + for cx16.r0L in 0 to 2 { +mylabel4: + goto mylabel4 + } + +; TODO fix this for vm codegen: + for cx16.r0L in cx16.r1L to cx16.r2L { +mylabel5: + goto mylabel5 } mylabel_outside: @@ -112,13 +141,10 @@ mylabel_inside: }""" val target1 = C64Target() - val result1 = compileText(target1, false, src, writeAssembly = false)!! - result1 shouldNotBe null + compileText(target1, false, src, writeAssembly = false) shouldNotBe null val target = VMTarget() - val result = compileText(target, false, src, writeAssembly = true)!! - val virtfile = result.compilationOptions.outputDir.resolve(result.program.name + ".p8ir") - VmRunner().runProgram(virtfile.readText()) + compileText(target, false, src, writeAssembly = true) shouldNotBe null } test("case sensitive symbols") { diff --git a/virtualmachine/src/prog8/vm/VirtualMachine.kt b/virtualmachine/src/prog8/vm/VirtualMachine.kt index ed1677796..7f720b99d 100644 --- a/virtualmachine/src/prog8/vm/VirtualMachine.kt +++ b/virtualmachine/src/prog8/vm/VirtualMachine.kt @@ -110,19 +110,23 @@ class VirtualMachine(irProgram: IRProgram) { } private fun stepNextChunk() { - val nextChunk = pcChunk.next - when (nextChunk) { - is IRCodeChunk -> { - pcChunk = nextChunk - pcIndex = 0 + do { + val nextChunk = pcChunk.next + when (nextChunk) { + is IRCodeChunk -> { + pcChunk = nextChunk + pcIndex = 0 + } + + null -> { + exit() // end of program reached + } + + else -> { + throw IllegalArgumentException("VM cannot run code from non-code chunk $nextChunk") + } } - null -> { - exit() // end of program reached - } - else -> { - throw IllegalArgumentException("VM cannot run code from non-code chunk $nextChunk") - } - } + } while (pcChunk.isEmpty()) } private fun nextPc() {