1
0
mirror of https://github.com/irmen/prog8.git synced 2025-04-17 07:39:42 +00:00

added -quiet flag to suppres all compiler and assembler messages

This commit is contained in:
Irmen de Jong 2025-04-10 21:16:26 +02:00
parent e2a8bdbdfb
commit 59582f5210
26 changed files with 113 additions and 71 deletions

@ -32,6 +32,7 @@ class CompilationOptions(val output: OutputType,
var breakpointCpuInstruction: String? = null,
var ignoreFootguns: Boolean = false,
var outputDir: Path = Path(""),
var quiet: Boolean = false,
var symbolDefs: Map<String, String> = emptyMap()
) {
init {

@ -36,7 +36,7 @@ interface ICompilationTarget: IStringEncoding, IMemSizer {
fun convertFloatToBytes(num: Double): List<UByte>
fun convertBytesToFloat(bytes: List<UByte>): Double
fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path)
fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path, quiet: Boolean)
fun isIOAddress(address: UInt): Boolean
override fun encodeString(str: String, encoding: Encoding): List<UByte>

@ -49,13 +49,15 @@ class C128Target: ICompilationTarget, IStringEncoding by Encoder, IMemSizer by N
return m5.toDouble()
}
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path) {
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path, quiet: Boolean) {
if(selectedEmulator!=1) {
System.err.println("The c128 target only supports the main emulator (Vice).")
return
}
println("\nStarting C-128 emulator x128...")
if(!quiet)
println("\nStarting C-128 emulator x128...")
val viceMonlist = C64Target.viceMonListName(programNameWithPath.toString())
val cmdline = listOf("x128", "-silent", "-moncommands", viceMonlist,
"-autostartprgmode", "1", "-autostart-warp", "-autostart", "${programNameWithPath}.prg")

@ -53,14 +53,16 @@ class C64Target: ICompilationTarget, IStringEncoding by Encoder, IMemSizer by No
return m5.toDouble()
}
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path) {
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path, quiet: Boolean) {
if(selectedEmulator!=1) {
System.err.println("The c64 target only supports the main emulator (Vice).")
return
}
for(emulator in listOf("x64sc", "x64")) {
println("\nStarting C-64 emulator $emulator...")
if(!quiet)
println("\nStarting C-64 emulator $emulator...")
val viceMonlist = viceMonListName(programNameWithPath.toString())
val cmdline = listOf(emulator, "-silent", "-moncommands", viceMonlist,
"-autostartprgmode", "1", "-autostart-warp", "-autostart", "${programNameWithPath}.prg")

@ -153,7 +153,7 @@ class ConfigFileTarget(
override fun getFloatAsmBytes(num: Number) = TODO("floats")
override fun convertFloatToBytes(num: Double): List<UByte> = TODO("floats")
override fun convertBytesToFloat(bytes: List<UByte>): Double = TODO("floats")
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path) {
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path, quiet: Boolean) {
throw IllegalArgumentException("Custom compiler target cannot automatically launch an emulator. Do this manually.")
}

@ -49,7 +49,7 @@ class Cx16Target: ICompilationTarget, IStringEncoding by Encoder, IMemSizer by N
return m5.toDouble()
}
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path) {
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path, quiet: Boolean) {
val emulator: String
val extraArgs: List<String>
@ -68,7 +68,9 @@ class Cx16Target: ICompilationTarget, IStringEncoding by Encoder, IMemSizer by N
}
}
println("\nStarting Commander X16 emulator $emulator...")
if(!quiet)
println("\nStarting Commander X16 emulator $emulator...")
val cmdline = listOf(emulator, "-scale", "2", "-rtc", "-run", "-prg", "${programNameWithPath}.prg") + extraArgs
val processb = ProcessBuilder(cmdline).inheritIO()
processb.environment()["PULSE_LATENCY_MSEC"] = "10"

@ -48,13 +48,15 @@ class PETTarget: ICompilationTarget, IStringEncoding by Encoder, IMemSizer by No
return m5.toDouble()
}
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path) {
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path, quiet: Boolean) {
if(selectedEmulator!=1) {
System.err.println("The pet target only supports the main emulator (Vice).")
return
}
println("\nStarting PET emulator...")
if(!quiet)
println("\nStarting PET emulator...")
val viceMonlist = C64Target.viceMonListName(programNameWithPath.toString())
val cmdline = listOf("xpet", "-model", "4032", "-ramsize", "32", "-videosize", "40", "-silent", "-moncommands", viceMonlist,
"-autostartprgmode", "1", "-autostart-warp", "-autostart", "${programNameWithPath}.prg")

@ -64,17 +64,19 @@ class VMTarget: ICompilationTarget, IStringEncoding by Encoder, IMemSizer by Nor
return Double.fromBits(b0 or b1 or b2 or b3 or b4 or b5 or b6 or b7)
}
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path) {
println("\nStarting Virtual Machine...")
override fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path, quiet: Boolean) {
if(!quiet)
println("\nStarting Virtual Machine...")
// to not have external module dependencies in our own module, we launch the virtual machine via reflection
val vm = Class.forName("prog8.vm.VmRunner").getDeclaredConstructor().newInstance() as IVirtualMachineRunner
val filename = programNameWithPath.name
if(programNameWithPath.isReadable()) {
vm.runProgram(programNameWithPath.readText())
vm.runProgram(programNameWithPath.readText(), quiet)
} else {
val withExt = programNameWithPath.resolveSibling("$filename.p8ir")
if(withExt.isReadable())
vm.runProgram(withExt.readText())
vm.runProgram(withExt.readText(), quiet)
else
throw java.nio.file.NoSuchFileException(withExt.name, null, "not a .p8ir file")
}
@ -116,7 +118,7 @@ class VMTarget: ICompilationTarget, IStringEncoding by Encoder, IMemSizer by Nor
interface IVirtualMachineRunner {
fun runProgram(irSource: String)
fun runProgram(irSource: String, quiet: Boolean)
}
private class VirtualZeropage(options: CompilationOptions): Zeropage(options) {

@ -265,7 +265,9 @@ class AsmGen6502Internal (
assembly.clear()
loopEndLabels.clear()
println("Generating assembly code... ")
if(!options.quiet)
println("Generating assembly code... ")
programGen.generate()
if(errors.noErrors()) {

@ -2,7 +2,10 @@ package prog8.codegen.cpu6502
import prog8.code.GENERATED_LABEL_PREFIX
import prog8.code.IAssemblyProgram
import prog8.code.core.*
import prog8.code.core.CompilationOptions
import prog8.code.core.ICompilationTarget
import prog8.code.core.IErrorReporter
import prog8.code.core.OutputType
import prog8.code.target.C128Target
import prog8.code.target.C64Target
import prog8.code.target.PETTarget
@ -46,7 +49,8 @@ internal class AssemblyProgram(
command.addAll(listOf("--output", prgFile.toString(), assemblyFile.toString()))
assemblerCommand = command
println("\nCreating prg for target ${compTarget.name}.")
if(!options.quiet)
println("\nCreating prg for target ${compTarget.name}.")
}
OutputType.XEX -> {
// Atari800XL .xex generation.
@ -67,7 +71,8 @@ internal class AssemblyProgram(
command.addAll(listOf("--output", xexFile.toString(), assemblyFile.toString()))
assemblerCommand = command
println("\nCreating xex for target ${compTarget.name}.")
if(!options.quiet)
println("\nCreating xex for target ${compTarget.name}.")
}
OutputType.RAW -> {
// Neo6502/headerless raw program generation.
@ -87,7 +92,8 @@ internal class AssemblyProgram(
command.addAll(listOf("--output", binFile.toString(), assemblyFile.toString()))
assemblerCommand = command
println("\nCreating raw binary for target ${compTarget.name}.")
if(!options.quiet)
println("\nCreating raw binary for target ${compTarget.name}.")
}
OutputType.LIBRARY -> {
// CBM machines library (.bin) generation (with or without 2 byte load address header depending on the compilation target machine)
@ -107,10 +113,12 @@ internal class AssemblyProgram(
command.add("--list=$listFile")
if(compTarget.name in listOf(C64Target.NAME, C128Target.NAME, PETTarget.NAME)) {
println("\nCreating binary library file with header for target ${compTarget.name}.")
if(!options.quiet)
println("\nCreating binary library file with header for target ${compTarget.name}.")
command.add("--cbm-prg")
} else {
println("\nCreating binary library file without header for target ${compTarget.name}.")
if(!options.quiet)
println("\nCreating binary library file without header for target ${compTarget.name}.")
command.add("--nostart") // should be headerless bin, because basic has problems doing a normal LOAD"lib",8,1 - need to use BLOAD
}

@ -28,12 +28,6 @@ fun main(args: Array<String>) {
// it means that you have to run the gradle task once to generate this file.
// Do that with this command: gradle createVersionFile
println("\nProg8 compiler v${prog8.buildversion.VERSION} by Irmen de Jong (irmen@razorvine.net)")
if('-' in prog8.buildversion.VERSION) {
println("Prerelease version from git commit ${prog8.buildversion.GIT_SHA.take(8)} in branch ${prog8.buildversion.GIT_BRANCH}")
}
println("This software is licensed under the GNU GPL 3.0, see https://www.gnu.org/licenses/gpl.html\n")
val succes = compileMain(args)
if(!succes)
exitProcess(1)
@ -63,7 +57,8 @@ private fun compileMain(args: Array<String>): Boolean {
val plainText by cli.option(ArgType.Boolean, fullName = "plaintext", description = "output only plain text, no colors or fancy symbols")
val printAst1 by cli.option(ArgType.Boolean, fullName = "printast1", description = "print out the internal compiler AST")
val printAst2 by cli.option(ArgType.Boolean, fullName = "printast2", description = "print out the simplified AST that is used for code generation")
val quietAssembler by cli.option(ArgType.Boolean, fullName = "quietasm", description = "don't print assembler output results")
val quietAll by cli.option(ArgType.Boolean, fullName = "quiet", description = "don't print compiler and assembler messages")
val quietAssembler by cli.option(ArgType.Boolean, fullName = "quietasm", description = "don't print assembler messages")
val slabsGolden by cli.option(ArgType.Boolean, fullName = "slabsgolden", description = "put memory() slabs in 'golden ram' memory area instead of at the end of the program. On the cx16 target this is $0400-07ff. This is unavailable on other systems.")
val slabsHighBank by cli.option(ArgType.Int, fullName = "slabshigh", description = "put memory() slabs in high memory area instead of at the end of the program. On the cx16 target the value specifies the HiRAM bank to use, on other systems this value is ignored.")
val dontIncludeSourcelines by cli.option(ArgType.Boolean, fullName = "nosourcelines", description = "do not include original Prog8 source lines in generated asm code")
@ -84,6 +79,14 @@ private fun compileMain(args: Array<String>): Boolean {
return false
}
if(quietAll!=true) {
println("\nProg8 compiler v${prog8.buildversion.VERSION} by Irmen de Jong (irmen@razorvine.net)")
if('-' in prog8.buildversion.VERSION) {
println("Prerelease version from git commit ${prog8.buildversion.GIT_SHA.take(8)} in branch ${prog8.buildversion.GIT_BRANCH}")
}
println("This software is licensed under the GNU GPL 3.0, see https://www.gnu.org/licenses/gpl.html\n")
}
val outputPath = pathFrom(outputDir)
if(!outputPath.toFile().isDirectory) {
System.err.println("Output path doesn't exist")
@ -148,7 +151,7 @@ private fun compileMain(args: Array<String>): Boolean {
}
if(startVm==true) {
runVm(moduleFiles.first())
runVm(moduleFiles.first(), quietAll==true)
return true
}
@ -169,7 +172,8 @@ private fun compileMain(args: Array<String>): Boolean {
if(checkSource==true) false else dontOptimize != true,
if(checkSource==true) false else dontWriteAssembly != true,
warnSymbolShadowing == true,
quietAssembler == true,
quietAll == true,
quietAll == true || quietAssembler == true,
asmListfile == true,
dontIncludeSourcelines != true,
experimentalCodegen == true,
@ -252,7 +256,8 @@ private fun compileMain(args: Array<String>): Boolean {
if(checkSource==true) false else dontOptimize != true,
if(checkSource==true) false else dontWriteAssembly != true,
warnSymbolShadowing == true,
quietAssembler == true,
quietAll == true,
quietAll == true || quietAssembler == true,
asmListfile == true,
dontIncludeSourcelines != true,
experimentalCodegen == true,
@ -296,9 +301,9 @@ private fun compileMain(args: Array<String>): Boolean {
val programNameInPath = outputPath.resolve(compilationResult.compilerAst.name)
if (startEmulator1 == true)
compilationResult.compilationOptions.compTarget.launchEmulator(1, programNameInPath)
compilationResult.compilationOptions.compTarget.launchEmulator(1, programNameInPath, quietAll==true)
else if (startEmulator2 == true)
compilationResult.compilationOptions.compTarget.launchEmulator(2, programNameInPath)
compilationResult.compilationOptions.compTarget.launchEmulator(2, programNameInPath, quietAll==true)
}
}
@ -335,8 +340,8 @@ private fun processSymbolDefs(symbolDefs: List<String>): Map<String, String>? {
return result
}
fun runVm(irFilename: String) {
fun runVm(irFilename: String, quiet: Boolean) {
val irFile = Path(irFilename)
val vmdef = VMTarget()
vmdef.launchEmulator(0, irFile)
vmdef.launchEmulator(0, irFile, quiet)
}

@ -38,6 +38,7 @@ class CompilerArguments(val filepath: Path,
val optimize: Boolean,
val writeAssembly: Boolean,
val warnSymbolShadowing: Boolean,
val quietAll: Boolean,
val quietAssembler: Boolean,
val asmListfile: Boolean,
val includeSourcelines: Boolean,
@ -84,13 +85,14 @@ fun compileProgram(args: CompilerArguments): CompilationResult? {
try {
val totalTime = measureTimeMillis {
val libraryDirs = if(compTarget.libraryPath!=null) listOf(compTarget.libraryPath.toString()) else emptyList()
val (program, options, imported) = parseMainModule(args.filepath, args.errors, compTarget, args.sourceDirs, libraryDirs)
val (program, options, imported) = parseMainModule(args.filepath, args.errors, compTarget, args.sourceDirs, libraryDirs, args.quietAll)
compilationOptions = options
with(compilationOptions) {
warnSymbolShadowing = args.warnSymbolShadowing
optimize = args.optimize
asmQuiet = args.quietAssembler
quiet = args.quietAll
asmListfile = args.asmListfile
includeSourcelines = args.includeSourcelines
experimentalCodegen = args.experimentalCodegen
@ -183,8 +185,10 @@ fun compileProgram(args: CompilerArguments): CompilationResult? {
System.out.flush()
System.err.flush()
val seconds = totalTime/1000.0
println("\nTotal compilation+assemble time: ${round(seconds*100.0)/100.0} sec.")
if(!args.quietAll) {
val seconds = totalTime / 1000.0
println("\nTotal compilation+assemble time: ${round(seconds * 100.0) / 100.0} sec.")
}
return CompilationResult(resultingProgram!!, ast, compilationOptions, importedFiles)
} catch (px: ParseError) {
System.out.flush()
@ -300,12 +304,13 @@ fun parseMainModule(filepath: Path,
errors: IErrorReporter,
compTarget: ICompilationTarget,
sourceDirs: List<String>,
libraryDirs: List<String>): Triple<Program, CompilationOptions, List<Path>> {
libraryDirs: List<String>,
quiet: Boolean): Triple<Program, CompilationOptions, List<Path>> {
val bf = BuiltinFunctionsFacade(BuiltinFunctions)
val program = Program(filepath.nameWithoutExtension, bf, compTarget, compTarget)
bf.program = program
val importer = ModuleImporter(program, compTarget.name, errors, sourceDirs, libraryDirs)
val importer = ModuleImporter(program, compTarget.name, errors, sourceDirs, libraryDirs, quiet)
val importedModuleResult = importer.importMainModule(filepath)
importedModuleResult.onFailure { throw it }
errors.report()

@ -23,7 +23,8 @@ class ModuleImporter(private val program: Program,
private val compilationTargetName: String,
val errors: IErrorReporter,
sourceDirs: List<String>,
libraryDirs: List<String>) {
libraryDirs: List<String>,
val quiet: Boolean) {
private val sourcePaths: List<Path> = sourceDirs.map { Path(it).sanitize() }.toSortedSet().toList()
private val libraryPaths: List<Path> = libraryDirs.map { Path(it).sanitize() }.toSortedSet().toList()
@ -34,8 +35,10 @@ class ModuleImporter(private val program: Program,
for(path in searchIn) {
val programPath = path.resolve(normalizedFilePath)
if(programPath.exists()) {
println("Compiling program ${Path("").absolute().relativize(programPath)}")
println("Compiler target: $compilationTargetName")
if(!quiet) {
println("Compiling program ${Path("").absolute().relativize(programPath)}")
println("Compiler target: $compilationTargetName")
}
val source = ImportFileSystem.getFile(programPath, false)
return Ok(importModule(source))
}

@ -10,9 +10,9 @@ import io.kotest.matchers.collections.shouldBeIn
import io.kotest.matchers.shouldBe
import io.kotest.matchers.string.shouldContain
import prog8.ast.Program
import prog8.code.INTERNED_STRINGS_MODULENAME
import prog8.code.core.IErrorReporter
import prog8.code.source.SourceCode
import prog8.code.INTERNED_STRINGS_MODULENAME
import prog8.compiler.ModuleImporter
import prog8.parser.ParseError
import prog8tests.helpers.*
@ -29,7 +29,7 @@ class TestModuleImporter: FunSpec({
}
fun makeImporter(errors: IErrorReporter? = null, searchIn: Iterable<String>) =
ModuleImporter(program, "blah", errors ?: ErrorReporterForTests(false), searchIn.toList(), emptyList())
ModuleImporter(program, "blah", errors ?: ErrorReporterForTests(false), searchIn.toList(), emptyList(), false)
fun makeImporter(errors: IErrorReporter?, vararg searchIn: String): ModuleImporter {
return makeImporter(errors, searchIn.asList())

@ -288,7 +288,7 @@ main {
errors.infos.any { "unused" in it } shouldBe false
val virtfile = result.compilationOptions.outputDir.resolve(result.compilerAst.name + ".p8ir")
VmRunner().runProgram(virtfile.readText())
VmRunner().runProgram(virtfile.readText(), false)
}
test("also remove subroutines with names matching IR asm instruction") {

@ -34,6 +34,7 @@ private fun compileTheThing(filepath: Path, optimize: Boolean, target: ICompilat
optimize,
writeAssembly = true,
warnSymbolShadowing = false,
quietAll = true,
quietAssembler = true,
asmListfile = false,
includeSourcelines = false,

@ -26,6 +26,7 @@ class TestCompilerOptionSourcedirs: FunSpec({
optimize = false,
writeAssembly = true,
warnSymbolShadowing = false,
quietAll = true,
quietAssembler = true,
asmListfile = false,
includeSourcelines = false,

@ -7,8 +7,8 @@ import io.kotest.matchers.shouldBe
import io.kotest.matchers.shouldNotBe
import io.kotest.matchers.string.shouldContain
import io.kotest.matchers.string.shouldStartWith
import prog8.code.core.ZeropageType
import prog8.code.INTERNED_STRINGS_MODULENAME
import prog8.code.core.ZeropageType
import prog8.code.target.C64Target
import prog8.code.target.Cx16Target
import prog8.code.target.VMTarget
@ -95,7 +95,7 @@ main {
val filepath = outputDir.resolve("$filenameBase.p8")
filepath.toFile().writeText(sourceText)
val (program, options, importedfiles) = parseMainModule(filepath, errors, C64Target(), emptyList(), emptyList())
val (program, options, importedfiles) = parseMainModule(filepath, errors, C64Target(), emptyList(), emptyList(), false)
program.toplevelModule.name shouldBe filenameBase
withClue("all imports other than the test source must have been internal resources library files") {

@ -39,7 +39,7 @@ class TestLaunchEmu: FunSpec({
</BLOCK>
</PROGRAM>
""")
target.launchEmulator(0, tmpfile)
target.launchEmulator(0, tmpfile, true)
tmpfile.deleteExisting()
}
})

@ -25,6 +25,7 @@ internal fun compileFile(
optimize,
writeAssembly = writeAssembly,
warnSymbolShadowing = false,
quietAll = true,
quietAssembler = true,
asmListfile = false,
includeSourcelines = false,

@ -41,7 +41,7 @@ main {
val target = VMTarget()
val result = compileText(target, false, src, outputDir, writeAssembly = true)!!
val virtfile = result.compilationOptions.outputDir.resolve(result.compilerAst.name + ".p8ir")
VmRunner().runProgram(virtfile.readText())
VmRunner().runProgram(virtfile.readText(), false)
}
test("split words array with pointers") {
@ -61,7 +61,7 @@ main {
val target = VMTarget()
val result = compileText(target, false, src, outputDir, writeAssembly = true)!!
val virtfile = result.compilationOptions.outputDir.resolve(result.compilerAst.name + ".p8ir")
VmRunner().runProgram(virtfile.readText())
VmRunner().runProgram(virtfile.readText(), false)
}
test("taking address of split arrays works") {
@ -109,11 +109,11 @@ test {
val target = VMTarget()
var result = compileText(target, false, src, outputDir, writeAssembly = true)!!
var virtfile = result.compilationOptions.outputDir.resolve(result.compilerAst.name + ".p8ir")
VmRunner().runProgram(virtfile.readText())
VmRunner().runProgram(virtfile.readText(), false)
result = compileText(target, true, src, outputDir, writeAssembly = true)!!
virtfile = result.compilationOptions.outputDir.resolve(result.compilerAst.name + ".p8ir")
VmRunner().runProgram(virtfile.readText())
VmRunner().runProgram(virtfile.readText(), false)
}
test("compile virtual: nested labels") {
@ -273,7 +273,7 @@ main {
val result = compileText(target, false, src, outputDir, writeAssembly = true)!!
val virtfile = result.compilationOptions.outputDir.resolve(result.compilerAst.name + ".p8ir")
val exc = shouldThrow<Exception> {
VmRunner().runProgram(virtfile.readText())
VmRunner().runProgram(virtfile.readText(), false)
}
exc.message shouldContain("encountered unconverted inline assembly chunk")
}
@ -294,7 +294,7 @@ main {
val irSrc = virtfile.readText()
irSrc.shouldContain("incm.b $2000")
irSrc.shouldNotContain("</ASM>")
VmRunner().runProgram(irSrc)
VmRunner().runProgram(irSrc, false)
}
test("addresses from labels/subroutines not yet supported in VM") {
@ -316,7 +316,7 @@ mylabel:
val result = compileText(VMTarget(), false, src, outputDir, writeAssembly = true)!!
val virtfile = result.compilationOptions.outputDir.resolve(result.compilerAst.name + ".p8ir")
val exc = shouldThrow<Exception> {
VmRunner().runProgram(virtfile.readText())
VmRunner().runProgram(virtfile.readText(), false)
}
exc.message shouldContain("cannot yet load a label address as a value")
}

@ -207,8 +207,11 @@ One or more .p8 module files
Prints the "simplified AST" which is the reduced representation of the program.
This is what is used in the code generators, to generate the executable code from.
``-quiet``
Don't print compiler and assembler messages.
``-quietasm``
Don't print assembler output results.
Don't print assembler messages
``-slabsgolden``
put memory() slabs in 'golden ram' memory area instead of at the end of the program.

@ -1,8 +1,6 @@
TODO
====
make compiler quiet when running .p8ir files via -vm (also add -quiet flag to suppress output on regular operation?)
romable: check library files for routines that are not yet romable and add "TODO: Romable" comment
romable: fix as many of those issues as possible to improve romability of library code

@ -20,7 +20,9 @@ class IRFileWriter(private val irProgram: IRProgram, outfileOverride: Path?) {
private var numInstr = 0
fun write(): Path {
println("Writing intermediate representation to $outfile")
if(!irProgram.options.quiet)
println("Writing intermediate representation to $outfile")
xml.writeStartDocument("utf-8", "1.0")
xml.writeEndDocument()
xml.writeCharacters("\n")
@ -43,7 +45,8 @@ class IRFileWriter(private val irProgram: IRProgram, outfileOverride: Path?) {
val used = irProgram.registersUsed()
val numberUsed = (used.readRegs.keys + used.writeRegs.keys).size + (used.readFpRegs.keys + used.writeFpRegs.keys).size
println("($numInstr instructions in $numChunks chunks, $numberUsed registers)")
if(!irProgram.options.quiet)
println("($numInstr instructions in $numChunks chunks, $numberUsed registers)")
return outfile
}

@ -76,7 +76,7 @@ class VirtualMachine(irProgram: IRProgram) {
reset(false)
}
fun run() {
fun run(quiet: Boolean) {
try {
var before = System.nanoTime()
var numIns = 0
@ -98,7 +98,8 @@ class VirtualMachine(irProgram: IRProgram) {
}
}
} catch (hx: ProgramExitException) {
println("\nProgram exit! Statuscode=${hx.status} #steps=${stepCount}")
if(!quiet)
println("\nProgram exit! Statuscode=${hx.status} #steps=${stepCount}")
gfx_close()
}
}
@ -2613,18 +2614,18 @@ internal fun ArrayDeque<UByte>.popf(): Double {
// probably called via reflection
class VmRunner: IVirtualMachineRunner {
override fun runProgram(irSource: String) {
runAndTestProgram(irSource) { /* no tests */ }
override fun runProgram(irSource: String, quiet: Boolean) {
runAndTestProgram(irSource, quiet) { /* no tests */ }
}
fun runAndTestProgram(irSource: String, test: (VirtualMachine) -> Unit) {
fun runAndTestProgram(irSource: String, quiet: Boolean = false, test: (VirtualMachine) -> Unit) {
val irProgram = IRFileReader().read(irSource)
val vm = VirtualMachine(irProgram)
// vm.breakpointHandler = { pcChunk, pcIndex ->
// println("UNHANDLED BREAKPOINT")
// println(" IN CHUNK: $pcChunk(${pcChunk.label}) INDEX: $pcIndex = INSTR ${pcChunk.instructions[pcIndex]}")
// }
vm.run()
vm.run(quiet)
test(vm)
}
}

@ -36,7 +36,7 @@ class TestVm: FunSpec( {
vm.valueStack.shouldBeEmpty()
vm.pcIndex shouldBe 0
vm.stepCount shouldBe 0
vm.run()
vm.run(false)
vm.callStack.shouldBeEmpty()
vm.valueStack.shouldBeEmpty()
vm.pcIndex shouldBe 0
@ -63,7 +63,7 @@ class TestVm: FunSpec( {
vm.valueStack.shouldBeEmpty()
vm.pcIndex shouldBe 0
vm.stepCount shouldBe 0
vm.run()
vm.run(false)
vm.stepCount shouldBe 4
vm.memory.getUW(1000) shouldBe 12345u
vm.callStack.shouldBeEmpty()
@ -121,7 +121,7 @@ class TestVm: FunSpec( {
</BLOCK>
</PROGRAM>
"""
runner.runProgram(irSource)
runner.runProgram(irSource, false)
}
test("vm machine float bits") {