mirror of
https://github.com/irmen/prog8.git
synced 2024-12-23 09:32:43 +00:00
added options -bytes2float and -float2bytes to be able to do float conversions from the command line
This commit is contained in:
parent
f4b50368ba
commit
42f4b06ac8
@ -26,6 +26,9 @@ interface IMachineDefinition {
|
|||||||
fun initializeMemoryAreas(compilerOptions: CompilationOptions)
|
fun initializeMemoryAreas(compilerOptions: CompilationOptions)
|
||||||
fun getFloatAsmBytes(num: Number): String
|
fun getFloatAsmBytes(num: Number): String
|
||||||
|
|
||||||
|
fun convertFloatToBytes(num: Double): List<UByte>
|
||||||
|
fun convertBytesToFloat(bytes: List<UByte>): Double
|
||||||
|
|
||||||
fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String>
|
fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String>
|
||||||
fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path)
|
fun launchEmulator(selectedEmulator: Int, programNameWithPath: Path)
|
||||||
fun isIOAddress(address: UInt): Boolean
|
fun isIOAddress(address: UInt): Boolean
|
||||||
|
@ -19,3 +19,15 @@ class C64Target: ICompilationTarget, IStringEncoding by Encoder, IMemSizer by Cb
|
|||||||
fun viceMonListName(baseFilename: String) = "$baseFilename.vice-mon-list"
|
fun viceMonListName(baseFilename: String) = "$baseFilename.vice-mon-list"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
fun getCompilationTargetByName(name: String) = when(name.lowercase()) {
|
||||||
|
C64Target.NAME -> C64Target()
|
||||||
|
C128Target.NAME -> C128Target()
|
||||||
|
Cx16Target.NAME -> Cx16Target()
|
||||||
|
PETTarget.NAME -> PETTarget()
|
||||||
|
AtariTarget.NAME -> AtariTarget()
|
||||||
|
VMTarget.NAME -> VMTarget()
|
||||||
|
else -> throw IllegalArgumentException("invalid compilation target")
|
||||||
|
}
|
||||||
|
@ -22,6 +22,8 @@ class AtariMachineDefinition: IMachineDefinition {
|
|||||||
override lateinit var golden: GoldenRam
|
override lateinit var golden: GoldenRam
|
||||||
|
|
||||||
override fun getFloatAsmBytes(num: Number) = TODO("atari float asm bytes from number")
|
override fun getFloatAsmBytes(num: Number) = TODO("atari float asm bytes from number")
|
||||||
|
override fun convertFloatToBytes(num: Double): List<UByte> = TODO("atari float to bytes")
|
||||||
|
override fun convertBytesToFloat(bytes: List<UByte>): Double = TODO("atari bytes to float")
|
||||||
|
|
||||||
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
||||||
return if (compilerOptions.output == OutputType.XEX)
|
return if (compilerOptions.output == OutputType.XEX)
|
||||||
|
@ -25,6 +25,17 @@ class C128MachineDefinition: IMachineDefinition {
|
|||||||
|
|
||||||
override fun getFloatAsmBytes(num: Number) = Mflpt5.fromNumber(num).makeFloatFillAsm()
|
override fun getFloatAsmBytes(num: Number) = Mflpt5.fromNumber(num).makeFloatFillAsm()
|
||||||
|
|
||||||
|
override fun convertFloatToBytes(num: Double): List<UByte> {
|
||||||
|
val m5 = Mflpt5.fromNumber(num)
|
||||||
|
return listOf(m5.b0, m5.b1, m5.b2, m5.b3, m5.b4)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun convertBytesToFloat(bytes: List<UByte>): Double {
|
||||||
|
require(bytes.size==5) { "need 5 bytes" }
|
||||||
|
val m5 = Mflpt5(bytes[0], bytes[1], bytes[2], bytes[3], bytes[4])
|
||||||
|
return m5.toDouble()
|
||||||
|
}
|
||||||
|
|
||||||
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
||||||
return if (compilerOptions.launcher == CbmPrgLauncherType.BASIC || compilerOptions.output == OutputType.PRG)
|
return if (compilerOptions.launcher == CbmPrgLauncherType.BASIC || compilerOptions.output == OutputType.PRG)
|
||||||
listOf("syslib")
|
listOf("syslib")
|
||||||
|
@ -26,6 +26,17 @@ class C64MachineDefinition: IMachineDefinition {
|
|||||||
|
|
||||||
override fun getFloatAsmBytes(num: Number) = Mflpt5.fromNumber(num).makeFloatFillAsm()
|
override fun getFloatAsmBytes(num: Number) = Mflpt5.fromNumber(num).makeFloatFillAsm()
|
||||||
|
|
||||||
|
override fun convertFloatToBytes(num: Double): List<UByte> {
|
||||||
|
val m5 = Mflpt5.fromNumber(num)
|
||||||
|
return listOf(m5.b0, m5.b1, m5.b2, m5.b3, m5.b4)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun convertBytesToFloat(bytes: List<UByte>): Double {
|
||||||
|
require(bytes.size==5) { "need 5 bytes" }
|
||||||
|
val m5 = Mflpt5(bytes[0], bytes[1], bytes[2], bytes[3], bytes[4])
|
||||||
|
return m5.toDouble()
|
||||||
|
}
|
||||||
|
|
||||||
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
||||||
return if (compilerOptions.launcher == CbmPrgLauncherType.BASIC || compilerOptions.output == OutputType.PRG)
|
return if (compilerOptions.launcher == CbmPrgLauncherType.BASIC || compilerOptions.output == OutputType.PRG)
|
||||||
listOf("syslib")
|
listOf("syslib")
|
||||||
|
@ -24,6 +24,18 @@ class CX16MachineDefinition: IMachineDefinition {
|
|||||||
override lateinit var golden: GoldenRam
|
override lateinit var golden: GoldenRam
|
||||||
|
|
||||||
override fun getFloatAsmBytes(num: Number) = Mflpt5.fromNumber(num).makeFloatFillAsm()
|
override fun getFloatAsmBytes(num: Number) = Mflpt5.fromNumber(num).makeFloatFillAsm()
|
||||||
|
|
||||||
|
override fun convertFloatToBytes(num: Double): List<UByte> {
|
||||||
|
val m5 = Mflpt5.fromNumber(num)
|
||||||
|
return listOf(m5.b0, m5.b1, m5.b2, m5.b3, m5.b4)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun convertBytesToFloat(bytes: List<UByte>): Double {
|
||||||
|
require(bytes.size==5) { "need 5 bytes" }
|
||||||
|
val m5 = Mflpt5(bytes[0], bytes[1], bytes[2], bytes[3], bytes[4])
|
||||||
|
return m5.toDouble()
|
||||||
|
}
|
||||||
|
|
||||||
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
||||||
return if (compilerOptions.launcher == CbmPrgLauncherType.BASIC || compilerOptions.output == OutputType.PRG)
|
return if (compilerOptions.launcher == CbmPrgLauncherType.BASIC || compilerOptions.output == OutputType.PRG)
|
||||||
listOf("syslib")
|
listOf("syslib")
|
||||||
|
@ -25,6 +25,17 @@ class PETMachineDefinition: IMachineDefinition {
|
|||||||
|
|
||||||
override fun getFloatAsmBytes(num: Number) = Mflpt5.fromNumber(num).makeFloatFillAsm()
|
override fun getFloatAsmBytes(num: Number) = Mflpt5.fromNumber(num).makeFloatFillAsm()
|
||||||
|
|
||||||
|
override fun convertFloatToBytes(num: Double): List<UByte> {
|
||||||
|
val m5 = Mflpt5.fromNumber(num)
|
||||||
|
return listOf(m5.b0, m5.b1, m5.b2, m5.b3, m5.b4)
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun convertBytesToFloat(bytes: List<UByte>): Double {
|
||||||
|
require(bytes.size==5) { "need 5 bytes" }
|
||||||
|
val m5 = Mflpt5(bytes[0], bytes[1], bytes[2], bytes[3], bytes[4])
|
||||||
|
return m5.toDouble()
|
||||||
|
}
|
||||||
|
|
||||||
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
||||||
return if (compilerOptions.launcher == CbmPrgLauncherType.BASIC || compilerOptions.output == OutputType.PRG)
|
return if (compilerOptions.launcher == CbmPrgLauncherType.BASIC || compilerOptions.output == OutputType.PRG)
|
||||||
listOf("syslib")
|
listOf("syslib")
|
||||||
|
@ -30,6 +30,26 @@ class VirtualMachineDefinition: IMachineDefinition {
|
|||||||
return parts.joinToString(", ")
|
return parts.joinToString(", ")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
override fun convertFloatToBytes(num: Double): List<UByte> {
|
||||||
|
val bits = num.toBits().toULong()
|
||||||
|
val hexStr = bits.toString(16).padStart(16, '0')
|
||||||
|
val parts = hexStr.chunked(2).map { it.toInt(16).toUByte() }
|
||||||
|
return parts
|
||||||
|
}
|
||||||
|
|
||||||
|
override fun convertBytesToFloat(bytes: List<UByte>): Double {
|
||||||
|
require(bytes.size==8) { "need 8 bytes" }
|
||||||
|
val b0 = bytes[0].toLong() shl (8*7)
|
||||||
|
val b1 = bytes[1].toLong() shl (8*6)
|
||||||
|
val b2 = bytes[2].toLong() shl (8*5)
|
||||||
|
val b3 = bytes[3].toLong() shl (8*4)
|
||||||
|
val b4 = bytes[4].toLong() shl (8*3)
|
||||||
|
val b5 = bytes[5].toLong() shl (8*2)
|
||||||
|
val b6 = bytes[6].toLong() shl (8*1)
|
||||||
|
val b7 = bytes[7].toLong() shl (8*0)
|
||||||
|
return Double.fromBits(b0 or b1 or b2 or b3 or b4 or b5 or b6 or b7)
|
||||||
|
}
|
||||||
|
|
||||||
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
override fun importLibs(compilerOptions: CompilationOptions, compilationTargetName: String): List<String> {
|
||||||
return listOf("syslib")
|
return listOf("syslib")
|
||||||
}
|
}
|
||||||
|
@ -57,6 +57,8 @@ private fun compileMain(args: Array<String>): Boolean {
|
|||||||
val printAst2 by cli.option(ArgType.Boolean, fullName = "printast2", description = "print out the intermediate AST that is used for code generation")
|
val printAst2 by cli.option(ArgType.Boolean, fullName = "printast2", description = "print out the intermediate AST that is used for code generation")
|
||||||
val breakpointCpuInstruction by cli.option(ArgType.Choice(listOf("brk", "stp"), { it }), fullName = "breakinstr", description = "the CPU instruction to use as well for %breakpoint")
|
val breakpointCpuInstruction by cli.option(ArgType.Choice(listOf("brk", "stp"), { it }), fullName = "breakinstr", description = "the CPU instruction to use as well for %breakpoint")
|
||||||
val compilationTarget by cli.option(ArgType.String, fullName = "target", description = "target output of the compiler (one of '${C64Target.NAME}', '${C128Target.NAME}', '${Cx16Target.NAME}', '${AtariTarget.NAME}', '${PETTarget.NAME}', '${VMTarget.NAME}') (required)")
|
val compilationTarget by cli.option(ArgType.String, fullName = "target", description = "target output of the compiler (one of '${C64Target.NAME}', '${C128Target.NAME}', '${Cx16Target.NAME}', '${AtariTarget.NAME}', '${PETTarget.NAME}', '${VMTarget.NAME}') (required)")
|
||||||
|
val bytes2float by cli.option(ArgType.String, fullName = "bytes2float", description = "convert a comma separated list of bytes from the target system to a float value. NOTE: you need to supply a target option too, and also still have to supply a dummy module file name as well!")
|
||||||
|
val float2bytes by cli.option(ArgType.String, fullName = "float2bytes", description = "convert floating point number to a list of bytes for the target system. NOTE: you need to supply a target option too, and also still have to supply a dummy module file name as well!")
|
||||||
val startVm by cli.option(ArgType.Boolean, fullName = "vm", description = "load and run a .p8ir IR source file in the VM")
|
val startVm by cli.option(ArgType.Boolean, fullName = "vm", description = "load and run a .p8ir IR source file in the VM")
|
||||||
val watchMode by cli.option(ArgType.Boolean, fullName = "watch", description = "continuous compilation mode (watch for file changes)")
|
val watchMode by cli.option(ArgType.Boolean, fullName = "watch", description = "continuous compilation mode (watch for file changes)")
|
||||||
val varsGolden by cli.option(ArgType.Boolean, fullName = "varsgolden", description = "put uninitialized variables 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 varsGolden by cli.option(ArgType.Boolean, fullName = "varsgolden", description = "put uninitialized variables 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.")
|
||||||
@ -100,6 +102,11 @@ private fun compileMain(args: Array<String>): Boolean {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if(bytes2float!=null)
|
||||||
|
return convertBytesToFloat(bytes2float!!, compilationTarget!!)
|
||||||
|
if(float2bytes!=null)
|
||||||
|
return convertFloatToBytes(float2bytes!!, compilationTarget!!)
|
||||||
|
|
||||||
if(varsHighBank==0 && compilationTarget==Cx16Target.NAME) {
|
if(varsHighBank==0 && compilationTarget==Cx16Target.NAME) {
|
||||||
System.err.println("On the Commander X16, HiRAM bank 0 is used by the kernal and can't be used.")
|
System.err.println("On the Commander X16, HiRAM bank 0 is used by the kernal and can't be used.")
|
||||||
return false
|
return false
|
||||||
@ -290,6 +297,23 @@ private fun compileMain(args: Array<String>): Boolean {
|
|||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun convertFloatToBytes(number: String, target: String): Boolean {
|
||||||
|
val tgt = getCompilationTargetByName(target)
|
||||||
|
val dbl = number.toDouble()
|
||||||
|
val bytes = tgt.machine.convertFloatToBytes(dbl)
|
||||||
|
print("$dbl in bytes on '$target': ")
|
||||||
|
println(bytes.joinToString(","))
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
fun convertBytesToFloat(bytelist: String, target: String): Boolean {
|
||||||
|
val tgt = getCompilationTargetByName(target)
|
||||||
|
val bytes = bytelist.split(',').map { it.trim().toUByte() }
|
||||||
|
val number = tgt.machine.convertBytesToFloat(bytes)
|
||||||
|
println("floating point value on '$target': $number")
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
private fun processSymbolDefs(symbolDefs: List<String>): Map<String, String>? {
|
private fun processSymbolDefs(symbolDefs: List<String>): Map<String, String>? {
|
||||||
val result = mutableMapOf<String, String>()
|
val result = mutableMapOf<String, String>()
|
||||||
val defPattern = """(.+)\s*=\s*(.+)""".toRegex()
|
val defPattern = """(.+)\s*=\s*(.+)""".toRegex()
|
||||||
|
@ -14,7 +14,10 @@ import prog8.code.ast.PtProgram
|
|||||||
import prog8.code.ast.printAst
|
import prog8.code.ast.printAst
|
||||||
import prog8.code.core.*
|
import prog8.code.core.*
|
||||||
import prog8.code.optimize.optimizeIntermediateAst
|
import prog8.code.optimize.optimizeIntermediateAst
|
||||||
import prog8.code.target.*
|
import prog8.code.target.AtariTarget
|
||||||
|
import prog8.code.target.Cx16Target
|
||||||
|
import prog8.code.target.VMTarget
|
||||||
|
import prog8.code.target.getCompilationTargetByName
|
||||||
import prog8.codegen.vm.VmCodeGen
|
import prog8.codegen.vm.VmCodeGen
|
||||||
import prog8.compiler.astprocessing.*
|
import prog8.compiler.astprocessing.*
|
||||||
import prog8.optimizer.*
|
import prog8.optimizer.*
|
||||||
@ -60,17 +63,7 @@ class CompilerArguments(val filepath: Path,
|
|||||||
|
|
||||||
fun compileProgram(args: CompilerArguments): CompilationResult? {
|
fun compileProgram(args: CompilerArguments): CompilationResult? {
|
||||||
|
|
||||||
val compTarget =
|
val compTarget = getCompilationTargetByName(args.compilationTarget)
|
||||||
when(args.compilationTarget) {
|
|
||||||
C64Target.NAME -> C64Target()
|
|
||||||
C128Target.NAME -> C128Target()
|
|
||||||
Cx16Target.NAME -> Cx16Target()
|
|
||||||
PETTarget.NAME -> PETTarget()
|
|
||||||
AtariTarget.NAME -> AtariTarget()
|
|
||||||
VMTarget.NAME -> VMTarget()
|
|
||||||
else -> throw IllegalArgumentException("invalid compilation target")
|
|
||||||
}
|
|
||||||
|
|
||||||
var compilationOptions: CompilationOptions
|
var compilationOptions: CompilationOptions
|
||||||
var ast: PtProgram? = null
|
var ast: PtProgram? = null
|
||||||
var resultingProgram: Program? = null
|
var resultingProgram: Program? = null
|
||||||
|
@ -260,6 +260,13 @@ One or more .p8 module files
|
|||||||
put memory() slabs in 'golden ram' memory area instead of at the end of the program.
|
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.
|
On the cx16 target this is $0400-07ff. This is unavailable on other systems.
|
||||||
|
|
||||||
|
``-bytes2float <bytes>``
|
||||||
|
convert a comma separated list of bytes from the target system to a float value.
|
||||||
|
NOTE: you need to supply a target option too, and also still have to supply a dummy module file name as well!
|
||||||
|
|
||||||
|
``-float2bytes <number>``
|
||||||
|
convert floating point number to a list of bytes for the target system.
|
||||||
|
NOTE: you need to supply a target option too, and also still have to supply a dummy module file name as well!
|
||||||
|
|
||||||
|
|
||||||
Module source code files
|
Module source code files
|
||||||
|
@ -3,7 +3,8 @@ package prog8.intermediate
|
|||||||
import prog8.code.*
|
import prog8.code.*
|
||||||
import prog8.code.ast.PtVariable
|
import prog8.code.ast.PtVariable
|
||||||
import prog8.code.core.*
|
import prog8.code.core.*
|
||||||
import prog8.code.target.*
|
import prog8.code.target.VMTarget
|
||||||
|
import prog8.code.target.getCompilationTargetByName
|
||||||
import java.io.StringReader
|
import java.io.StringReader
|
||||||
import java.nio.file.Path
|
import java.nio.file.Path
|
||||||
import javax.xml.stream.XMLEventReader
|
import javax.xml.stream.XMLEventReader
|
||||||
@ -95,16 +96,7 @@ class IRFileReader {
|
|||||||
text.lineSequence().forEach { line ->
|
text.lineSequence().forEach { line ->
|
||||||
val (name, value) = line.split('=', limit=2)
|
val (name, value) = line.split('=', limit=2)
|
||||||
when(name) {
|
when(name) {
|
||||||
"compTarget" -> {
|
"compTarget" -> target = getCompilationTargetByName(value)
|
||||||
target = when(value) {
|
|
||||||
VMTarget.NAME -> VMTarget()
|
|
||||||
C64Target.NAME -> C64Target()
|
|
||||||
C128Target.NAME -> C128Target()
|
|
||||||
AtariTarget.NAME -> AtariTarget()
|
|
||||||
Cx16Target.NAME -> Cx16Target()
|
|
||||||
else -> throw IRParseException("invalid target $value")
|
|
||||||
}
|
|
||||||
}
|
|
||||||
"output" -> outputType = OutputType.valueOf(value)
|
"output" -> outputType = OutputType.valueOf(value)
|
||||||
"launcher" -> launcher = CbmPrgLauncherType.valueOf(value)
|
"launcher" -> launcher = CbmPrgLauncherType.valueOf(value)
|
||||||
"zeropage" -> zeropage = ZeropageType.valueOf(value)
|
"zeropage" -> zeropage = ZeropageType.valueOf(value)
|
||||||
|
Loading…
Reference in New Issue
Block a user