improved zero page address addresses for floating point support mode

This commit is contained in:
Irmen de Jong 2019-02-09 17:29:59 +01:00
parent 9f8ae485c3
commit ee497d2ffb
2 changed files with 65 additions and 34 deletions

View File

@ -29,8 +29,8 @@ class C64Zeropage(options: CompilationOptions) : Zeropage(options) {
const val SCRATCH_B1 = 0x02
const val SCRATCH_REG = 0x03 // temp storage for a register
const val SCRATCH_REG_X = 0xfa // temp storage for register X (the evaluation stack pointer)
const val SCRATCH_W1 = 0xfb // $fb/$fc
const val SCRATCH_W2 = 0xfd // $fd/$fe
const val SCRATCH_W1 = 0xfb // $fb+$fc
const val SCRATCH_W2 = 0xfd // $fd+$fe
}
override val exitProgramStrategy: ExitProgramStrategy = when(options.zeropage) {
@ -49,19 +49,36 @@ class C64Zeropage(options: CompilationOptions) : Zeropage(options) {
free.removeAll(listOf(SCRATCH_B1, SCRATCH_REG, SCRATCH_REG_X, SCRATCH_W1, SCRATCH_W1+1, SCRATCH_W2, SCRATCH_W2+1))
free.removeAll(listOf(0xa0, 0xa1, 0xa2, 0x91, 0xc0, 0xc5, 0xcb, 0xf5, 0xf6)) // these are updated by IRQ
} else {
if(options.zeropage == ZeropageType.KERNALSAFE) {
// add the Zp addresses that are just used by BASIC routines to the free list
free.addAll(listOf(0x09, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11,
if(options.zeropage == ZeropageType.KERNALSAFE || options.zeropage == ZeropageType.FLOATSAFE) {
free.addAll(listOf(0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11,
0x14, 0x15, 0x16, 0x17, 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, 0x20, 0x21,
0x22, 0x23, 0x24, 0x25,
0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46,
0x47, 0x48, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f, 0x51, 0x52, 0x53, 0x6f, 0x70))
0x47, 0x48, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f, 0x51, 0x52, 0x53,
0x57, 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f, 0x60,
0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68,
0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f, 0x70, 0x71, 0x72,
0x73, 0x74, 0x75, 0x76, 0x77, 0x78, 0x79, 0x7a, 0x7b, 0x7c,
0x7d, 0x7e, 0x7f, 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, 0x88, 0x89, 0x8a,
0x8b, 0x8c, 0x8d, 0x8e, 0x8f, 0xff
// 0x90-0xfa is 'kernel work storage area'
))
}
else if(options.zeropage == ZeropageType.FLOATSAFE) {
TODO("reserve float zp locations")
if(options.zeropage == ZeropageType.FLOATSAFE) {
// remove the zero page locations used for floating point operations from the free list
free.removeAll(listOf(
0x12, 0x26, 0x27, 0x28, 0x29, 0x2a,
0x57, 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f, 0x60,
0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, 0x68,
0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f, 0x70, 0x71, 0x72,
0x8b, 0x8c, 0x8d, 0x8e, 0x8f, 0xf
))
}
// add the other free Zp addresses
// these are valid for the C-64 (when no RS232 I/O is performed):
free.addAll(listOf(0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0d, 0x0e,
// add the other free Zp addresses,
// these are valid for the C-64 (when no RS232 I/O is performed) but to keep BASIC running fully:
free.addAll(listOf(0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0d, 0x0e,
0x94, 0x95, 0xa7, 0xa8, 0xa9, 0xaa,
0xb5, 0xb6, 0xf7, 0xf8, 0xf9))
}

View File

@ -138,23 +138,41 @@ class TestZeropage {
assertFailsWith<CompilerException> {
zp.allocate("", DataType.FLOAT, null)
}
val zp2 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FULL, emptyList(), true))
val zp2 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FLOATSAFE, emptyList(), true))
zp2.allocate("", DataType.FLOAT, null)
}
@Test
fun testZpModesWithFloats() {
C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FULL, emptyList(), false))
C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.KERNALSAFE, emptyList(), false))
C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.BASICSAFE, emptyList(), false))
C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FLOATSAFE, emptyList(), false))
C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.BASICSAFE, emptyList(), true))
C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FLOATSAFE, emptyList(), true))
assertFailsWith<CompilerException> {
C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FULL, emptyList(), true))
}
assertFailsWith<CompilerException> {
C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.KERNALSAFE, emptyList(), true))
}
}
@Test
fun testFreeSpaces() {
val zp1 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.BASICSAFE, emptyList(), true))
assertEquals(19, zp1.available())
val zp2 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.KERNALSAFE, emptyList(), true))
assertEquals(67, zp2.available())
val zp3 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FULL, emptyList(), true))
assertEquals(238, zp3.available())
assertEquals(20, zp1.available())
val zp2 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FLOATSAFE, emptyList(), false))
assertEquals(95, zp2.available())
val zp3 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.KERNALSAFE, emptyList(), false))
assertEquals(129, zp3.available())
val zp4 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FULL, emptyList(), false))
assertEquals(238, zp4.available())
}
@Test
fun testReservedSpace() {
val zp1 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FULL, emptyList(), true))
val zp1 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FULL, emptyList(), false))
assertEquals(238, zp1.available())
assertTrue(50 in zp1.free)
assertTrue(100 in zp1.free)
@ -163,8 +181,7 @@ class TestZeropage {
assertTrue(200 in zp1.free)
assertTrue(255 in zp1.free)
assertTrue(199 in zp1.free)
val zp2 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FULL,
listOf(50 .. 100, 200..255), true))
val zp2 = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FULL, listOf(50 .. 100, 200..255), false))
assertEquals(139, zp2.available())
assertFalse(50 in zp2.free)
assertFalse(100 in zp2.free)
@ -178,7 +195,7 @@ class TestZeropage {
@Test
fun testBasicsafeAllocation() {
val zp = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.BASICSAFE, emptyList(), true))
assertEquals(19, zp.available())
assertEquals(20, zp.available())
zp.allocate("", DataType.FLOAT, null)
assertFailsWith<ZeropageDepletedError> {
@ -201,32 +218,28 @@ class TestZeropage {
@Test
fun testFullAllocation() {
val zp = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FULL, emptyList(), true))
val zp = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.FULL, emptyList(), false))
assertEquals(238, zp.available())
val loc = zp.allocate("", DataType.FLOAT, null)
val loc = zp.allocate("", DataType.UWORD, null)
assertTrue(loc > 3)
assertFalse(loc in zp.free)
val num = zp.available() / 5
val rest = zp.available() % 5
val num = zp.available() / 2
for(i in 0..num-4) {
zp.allocate("", DataType.FLOAT, null)
zp.allocate("", DataType.UWORD, null)
}
assertEquals(18,zp.available())
assertEquals(6,zp.available())
assertFailsWith<ZeropageDepletedError> {
// can't allocate because no more sequential bytes, only fragmented
zp.allocate("", DataType.FLOAT, null)
zp.allocate("", DataType.UWORD, null)
}
for(i in 0..13) {
for(i in 0..5) {
zp.allocate("", DataType.UBYTE, null)
}
zp.allocate("", DataType.UWORD, null)
assertEquals(2, zp.available())
zp.allocate("", DataType.UBYTE, null)
zp.allocate("", DataType.UBYTE, null)
assertEquals(0, zp.available())
assertFailsWith<ZeropageDepletedError> {
// no more space
zp.allocate("", DataType.UBYTE, null)
@ -236,7 +249,7 @@ class TestZeropage {
@Test
fun testEfficientAllocation() {
val zp = C64Zeropage(CompilationOptions(OutputType.RAW, LauncherType.NONE, ZeropageType.BASICSAFE, emptyList(), true))
assertEquals(19, zp.available())
assertEquals(20, zp.available())
assertEquals(0x04, zp.allocate("", DataType.FLOAT, null))
assertEquals(0x09, zp.allocate("", DataType.UBYTE, null))
assertEquals(0x0d, zp.allocate("", DataType.UWORD, null))
@ -245,6 +258,7 @@ class TestZeropage {
assertEquals(0xa9, zp.allocate("", DataType.UWORD, null))
assertEquals(0xb5, zp.allocate("", DataType.UWORD, null))
assertEquals(0xf7, zp.allocate("", DataType.UWORD, null))
assertEquals(0x0a, zp.allocate("", DataType.UBYTE, null))
assertEquals(0xf9, zp.allocate("", DataType.UBYTE, null))
assertEquals(0, zp.available())
}