mirror of
https://github.com/pevans/erc-c.git
synced 2024-11-23 23:32:45 +00:00
Finish refactor to separate bank_switch and memory_mode
There is one failing test, which I expect to fail at this point; that's because we need to write a read/write map function for the stack and zero page so that they use aux memory when BANK_ALTZP is on, and main memory when not.
This commit is contained in:
parent
ceccacfbc8
commit
c953616a71
@ -153,13 +153,10 @@ enum bank_switch {
|
|||||||
BANK_WRITE = 0x2,
|
BANK_WRITE = 0x2,
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* When on, the $Dnnn hexapage will use the first RAM bank for
|
* When this is on, we will use bank 2 RAM when accessing the $Dnnn
|
||||||
* reads and/or writes. All other RAM access in bank-switched memory
|
* range; otherwise, we use bank 1 (as you might guess).
|
||||||
* will still go to bank 1 RAM, with respect to BANK_RAM when it
|
|
||||||
* comes to reads. (The default behavior is actually to use bank 2
|
|
||||||
* RAM for the $D range.)
|
|
||||||
*/
|
*/
|
||||||
BANK_RAM1 = 0x4,
|
BANK_RAM2 = 0x4,
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* This is a weird little bit. When BANK_ALTZP is on, the zero page
|
* This is a weird little bit. When BANK_ALTZP is on, the zero page
|
||||||
@ -264,8 +261,9 @@ extern void apple2_press_key(apple2 *, vm_8bit);
|
|||||||
extern void apple2_release_key(apple2 *);
|
extern void apple2_release_key(apple2 *);
|
||||||
extern void apple2_reset(apple2 *);
|
extern void apple2_reset(apple2 *);
|
||||||
extern void apple2_run_loop(apple2 *);
|
extern void apple2_run_loop(apple2 *);
|
||||||
extern void apple2_set_color(apple2 *, int);
|
|
||||||
extern void apple2_set_bank_switch(apple2 *, vm_8bit);
|
extern void apple2_set_bank_switch(apple2 *, vm_8bit);
|
||||||
|
extern void apple2_set_color(apple2 *, int);
|
||||||
|
extern void apple2_set_memory_mode(apple2 *, vm_8bit);
|
||||||
extern void apple2_set_video(apple2 *, int);
|
extern void apple2_set_video(apple2 *, int);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
52
src/apple2.c
52
src/apple2.c
@ -154,27 +154,42 @@ apple2_create(int width, int height)
|
|||||||
void
|
void
|
||||||
apple2_set_bank_switch(apple2 *mach, vm_8bit flags)
|
apple2_set_bank_switch(apple2 *mach, vm_8bit flags)
|
||||||
{
|
{
|
||||||
int have_aux = mach->bank_switch & MEMORY_AUX;
|
// If we already have BANK_ALTZP, and the flags we're setting do
|
||||||
int flags_aux = flags & MEMORY_AUX;
|
// _not_ have BANK_ALTZP, then we need to copy aux's zero page and
|
||||||
|
// stack into main. But if we don't have BANK_ALTZP, and flags
|
||||||
if (flags_aux && !have_aux) {
|
// _does_, then we have to do the inverse: copy main's zero page and
|
||||||
// Switch to auxiliary memory.
|
// stack into aux.
|
||||||
mos6502_set_memory(mach->cpu, mach->aux, mach->aux);
|
if (mach->bank_switch & BANK_ALTZP) {
|
||||||
|
if (~flags & BANK_ALTZP) {
|
||||||
// We need to copy page 0 and 1 from main over to aux.
|
vm_segment_copy(mach->main, mach->aux, 0, 0, 0x200);
|
||||||
|
}
|
||||||
|
} else if (flags & BANK_ALTZP) {
|
||||||
vm_segment_copy(mach->aux, mach->main, 0, 0, 0x200);
|
vm_segment_copy(mach->aux, mach->main, 0, 0, 0x200);
|
||||||
} else if (!flags_aux && have_aux) {
|
|
||||||
// Switching back to main memory
|
|
||||||
mos6502_set_memory(mach->cpu, mach->main, mach->main);
|
|
||||||
|
|
||||||
// And, like above, we need to copy page 0 and 1 from aux back
|
|
||||||
// to main.
|
|
||||||
vm_segment_copy(mach->main, mach->aux, 0, 0, 0x200);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
mach->bank_switch = flags;
|
mach->bank_switch = flags;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Set the memory mode of the apple machine. This may cause us to change
|
||||||
|
* some behavior (i.e. start using or stop using auxiliary memory).
|
||||||
|
*/
|
||||||
|
void
|
||||||
|
apple2_set_memory_mode(apple2 *mach, vm_8bit flags)
|
||||||
|
{
|
||||||
|
vm_segment *rmem = NULL,
|
||||||
|
*wmem = NULL;
|
||||||
|
|
||||||
|
mach->memory_mode = flags;
|
||||||
|
|
||||||
|
// We may need to change which segments the CPU can read from or
|
||||||
|
// write to, based upon the below flags.
|
||||||
|
rmem = (flags & MEMORY_READ_AUX) ? mach->aux : mach->main;
|
||||||
|
wmem = (flags & MEMORY_WRITE_AUX) ? mach->aux : mach->main;
|
||||||
|
|
||||||
|
mos6502_set_memory(mach->cpu, rmem, wmem);
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Return true if we are in a state that the apple2 would consider
|
* Return true if we are in a state that the apple2 would consider
|
||||||
* double resolution. (In practice, this refers to horizontal screen
|
* double resolution. (In practice, this refers to horizontal screen
|
||||||
@ -248,12 +263,9 @@ apple2_reset(apple2 *mach)
|
|||||||
// Switch video mode back to 40 column text
|
// Switch video mode back to 40 column text
|
||||||
apple2_set_video(mach, VIDEO_40COL_TEXT);
|
apple2_set_video(mach, VIDEO_40COL_TEXT);
|
||||||
|
|
||||||
// Default to:
|
// Switch us back to defaults
|
||||||
// - read from ROM
|
|
||||||
// - write to RAM
|
|
||||||
// - use bank 2 for $Dxxx hexapage
|
|
||||||
apple2_set_bank_switch(mach, BANK_DEFAULT);
|
apple2_set_bank_switch(mach, BANK_DEFAULT);
|
||||||
apple2_set_memory_mode(mach, MEMORY_NOMINAL);
|
apple2_set_memory_mode(mach, MEMORY_DEFAULT);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -16,7 +16,7 @@ SEGMENT_READER(apple2_mem_read_bank)
|
|||||||
|
|
||||||
mach = (apple2 *)_mach;
|
mach = (apple2 *)_mach;
|
||||||
|
|
||||||
if (mach->bank_switch & MEMORY_ROM) {
|
if (~mach->bank_switch & BANK_RAM) {
|
||||||
// We need to account for the difference in address location
|
// We need to account for the difference in address location
|
||||||
// before we can successfully get any data from ROM.
|
// before we can successfully get any data from ROM.
|
||||||
return vm_segment_get(mach->rom, addr - APPLE2_BANK_OFFSET);
|
return vm_segment_get(mach->rom, addr - APPLE2_BANK_OFFSET);
|
||||||
@ -26,7 +26,7 @@ SEGMENT_READER(apple2_mem_read_bank)
|
|||||||
// that you can access through bank-switching in the $D000 - $DFFF
|
// that you can access through bank-switching in the $D000 - $DFFF
|
||||||
// range, which is actually held at the _end_ of memory beyond the
|
// range, which is actually held at the _end_ of memory beyond the
|
||||||
// 64k mark.
|
// 64k mark.
|
||||||
if (addr < 0xE000 && mach->bank_switch & MEMORY_RAM2) {
|
if (addr < 0xE000 && mach->bank_switch & BANK_RAM2) {
|
||||||
// The same caution holds for getting data from the
|
// The same caution holds for getting data from the
|
||||||
// second RAM bank.
|
// second RAM bank.
|
||||||
return segment->memory[addr + 0x3000];
|
return segment->memory[addr + 0x3000];
|
||||||
@ -48,7 +48,7 @@ SEGMENT_WRITER(apple2_mem_write_bank)
|
|||||||
mach = (apple2 *)_mach;
|
mach = (apple2 *)_mach;
|
||||||
|
|
||||||
// No writes are allowed... sorry!
|
// No writes are allowed... sorry!
|
||||||
if (~mach->bank_switch & MEMORY_WRITE) {
|
if (~mach->bank_switch & BANK_WRITE) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -62,7 +62,7 @@ SEGMENT_WRITER(apple2_mem_write_bank)
|
|||||||
// In this case, we need to assign the value at the 64-68k range at
|
// In this case, we need to assign the value at the 64-68k range at
|
||||||
// the end of memory; this is just a simple offset from the given
|
// the end of memory; this is just a simple offset from the given
|
||||||
// address.
|
// address.
|
||||||
if (addr < 0xE000 && mach->bank_switch & MEMORY_RAM2) {
|
if (addr < 0xE000 && mach->bank_switch & BANK_RAM2) {
|
||||||
segment->memory[addr + 0x3000] = value;
|
segment->memory[addr + 0x3000] = value;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -195,64 +195,62 @@ SEGMENT_READER(apple2_mem_read_bank_switch)
|
|||||||
// these soft switches is not actually to read anything useful,
|
// these soft switches is not actually to read anything useful,
|
||||||
// but simply to change the bank switch mode.
|
// but simply to change the bank switch mode.
|
||||||
case 0xC080:
|
case 0xC080:
|
||||||
apple2_set_bank_switch(mach, MEMORY_RAM2);
|
apple2_set_bank_switch(mach, BANK_RAM | BANK_RAM2);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0xC081:
|
case 0xC081:
|
||||||
if (last_addr == addr) {
|
if (last_addr == addr) {
|
||||||
apple2_set_bank_switch(mach,
|
apple2_set_bank_switch(mach, BANK_WRITE | BANK_RAM2);
|
||||||
MEMORY_ROM | MEMORY_WRITE | MEMORY_RAM2);
|
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
case 0xC082:
|
case 0xC082:
|
||||||
apple2_set_bank_switch(mach, MEMORY_ROM | MEMORY_RAM2);
|
apple2_set_bank_switch(mach, BANK_RAM2);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0xC083:
|
case 0xC083:
|
||||||
if (last_addr == addr) {
|
if (last_addr == addr) {
|
||||||
apple2_set_bank_switch(mach, MEMORY_WRITE | MEMORY_RAM2);
|
apple2_set_bank_switch(mach, BANK_RAM | BANK_WRITE | BANK_RAM2);
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
// Conversely, the $C088 - $C08B range control memory access
|
// Conversely, the $C088 - $C08B range control memory access
|
||||||
// while using bank 1 RAM.
|
// while using bank 1 RAM.
|
||||||
case 0xC088:
|
case 0xC088:
|
||||||
// The 0 means there are no special privileges; reads are to
|
apple2_set_bank_switch(mach, BANK_RAM);
|
||||||
// RAM, writes are disabled, and we are using bank 1 memory.
|
|
||||||
apple2_set_bank_switch(mach, 0);
|
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0xC089:
|
case 0xC089:
|
||||||
if (last_addr == addr) {
|
if (last_addr == addr) {
|
||||||
apple2_set_bank_switch(mach, MEMORY_ROM | MEMORY_WRITE);
|
apple2_set_bank_switch(mach, BANK_WRITE);
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0xC08A:
|
case 0xC08A:
|
||||||
apple2_set_bank_switch(mach, MEMORY_ROM);
|
apple2_set_bank_switch(mach, BANK_DEFAULT);
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
case 0xC08B:
|
case 0xC08B:
|
||||||
if (last_addr == addr) {
|
if (last_addr == addr) {
|
||||||
apple2_set_bank_switch(mach, MEMORY_WRITE);
|
apple2_set_bank_switch(mach, BANK_RAM | BANK_WRITE);
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
// Return high on the 7th bit if we're using bank 2 memory
|
// Return high on the 7th bit if we're using bank 2 memory
|
||||||
case 0xC011:
|
case 0xC011:
|
||||||
return mach->bank_switch & MEMORY_RAM2
|
return mach->bank_switch & BANK_RAM2
|
||||||
? 0x80
|
? 0x80
|
||||||
: 0x00;
|
: 0x00;
|
||||||
|
|
||||||
// Return high on 7th bit if we're reading RAM
|
// Return high on 7th bit if we're reading RAM
|
||||||
case 0xC012:
|
case 0xC012:
|
||||||
return ~mach->bank_switch & MEMORY_ROM
|
return mach->bank_switch & BANK_RAM
|
||||||
? 0x80
|
? 0x80
|
||||||
: 0x00;
|
: 0x00;
|
||||||
|
|
||||||
// Return high on the 7th bit if we're using aux memory
|
// Return high on the 7th bit if we are using the zero page and
|
||||||
|
// stack from aux memory.
|
||||||
case 0xC016:
|
case 0xC016:
|
||||||
return mach->bank_switch & MEMORY_AUX
|
return mach->bank_switch & BANK_ALTZP
|
||||||
? 0x80
|
? 0x80
|
||||||
: 0x00;
|
: 0x00;
|
||||||
}
|
}
|
||||||
@ -270,16 +268,16 @@ SEGMENT_WRITER(apple2_mem_write_bank_switch)
|
|||||||
apple2 *mach = (apple2 *)_mach;
|
apple2 *mach = (apple2 *)_mach;
|
||||||
|
|
||||||
switch (addr) {
|
switch (addr) {
|
||||||
// Turn on auxiliary memory
|
// Turn on auxiliary memory for zero page + stack
|
||||||
case 0xC008:
|
case 0xC008:
|
||||||
apple2_set_bank_switch(mach,
|
apple2_set_bank_switch(mach,
|
||||||
mach->bank_switch | MEMORY_AUX);
|
mach->bank_switch | BANK_ALTZP);
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// Disable auxiliary memory
|
// Disable auxiliary memory for zero page + stack
|
||||||
case 0xC009:
|
case 0xC009:
|
||||||
apple2_set_bank_switch(mach,
|
apple2_set_bank_switch(mach,
|
||||||
mach->bank_switch & ~MEMORY_AUX);
|
mach->bank_switch & ~BANK_ALTZP);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -121,29 +121,26 @@ Test(apple2, set_bank_switch)
|
|||||||
{
|
{
|
||||||
apple2_set_bank_switch(mach, 0);
|
apple2_set_bank_switch(mach, 0);
|
||||||
cr_assert_eq(mach->bank_switch, 0);
|
cr_assert_eq(mach->bank_switch, 0);
|
||||||
apple2_set_bank_switch(mach, MEMORY_ROM | MEMORY_WRITE | MEMORY_RAM2);
|
apple2_set_bank_switch(mach, BANK_WRITE | BANK_RAM2);
|
||||||
cr_assert_eq(mach->bank_switch, MEMORY_ROM | MEMORY_WRITE | MEMORY_RAM2);
|
cr_assert_eq(mach->bank_switch, BANK_WRITE | BANK_RAM2);
|
||||||
|
|
||||||
mos6502_set(mach->cpu, 0x1, 111);
|
mos6502_set(mach->cpu, 0x1, 111);
|
||||||
mos6502_set(mach->cpu, 0x101, 222);
|
mos6502_set(mach->cpu, 0x101, 222);
|
||||||
|
|
||||||
apple2_set_bank_switch(mach, MEMORY_AUX);
|
apple2_set_bank_switch(mach, BANK_ALTZP);
|
||||||
cr_assert_eq(mach->cpu->rmem, mach->aux);
|
|
||||||
cr_assert_eq(mos6502_get(mach->cpu, 0x1), 111);
|
cr_assert_eq(mos6502_get(mach->cpu, 0x1), 111);
|
||||||
cr_assert_eq(mos6502_get(mach->cpu, 0x101), 222);
|
cr_assert_eq(mos6502_get(mach->cpu, 0x101), 222);
|
||||||
|
|
||||||
mos6502_set(mach->cpu, 0x1, 222);
|
mos6502_set(mach->cpu, 0x1, 222);
|
||||||
mos6502_set(mach->cpu, 0x101, 101);
|
mos6502_set(mach->cpu, 0x101, 101);
|
||||||
|
|
||||||
apple2_set_bank_switch(mach, 0);
|
apple2_set_bank_switch(mach, BANK_DEFAULT);
|
||||||
cr_assert_eq(mach->cpu->rmem, mach->main);
|
|
||||||
cr_assert_eq(mos6502_get(mach->cpu, 0x1), 222);
|
cr_assert_eq(mos6502_get(mach->cpu, 0x1), 222);
|
||||||
cr_assert_eq(mos6502_get(mach->cpu, 0x101), 101);
|
cr_assert_eq(mos6502_get(mach->cpu, 0x101), 101);
|
||||||
}
|
}
|
||||||
|
|
||||||
Test(apple2, reset)
|
Test(apple2, reset)
|
||||||
{
|
{
|
||||||
apple2_set_bank_switch(mach, MEMORY_ROM);
|
|
||||||
vm_segment_set(mach->rom, 0x2FFC, 0x34);
|
vm_segment_set(mach->rom, 0x2FFC, 0x34);
|
||||||
vm_segment_set(mach->rom, 0x2FFD, 0x12);
|
vm_segment_set(mach->rom, 0x2FFD, 0x12);
|
||||||
apple2_reset(mach);
|
apple2_reset(mach);
|
||||||
|
@ -64,7 +64,7 @@ Test(apple2_mem, read_bank)
|
|||||||
|
|
||||||
// Test that setting a value in the rom segment is returned to us
|
// Test that setting a value in the rom segment is returned to us
|
||||||
// when addressing from main memory
|
// when addressing from main memory
|
||||||
apple2_set_bank_switch(mach, MEMORY_ROM | MEMORY_WRITE);
|
apple2_set_bank_switch(mach, BANK_WRITE);
|
||||||
val = 123;
|
val = 123;
|
||||||
vm_segment_set(mach->rom, 0x77, val);
|
vm_segment_set(mach->rom, 0x77, val);
|
||||||
val = vm_segment_get(mach->rom, 0x77);
|
val = vm_segment_get(mach->rom, 0x77);
|
||||||
@ -74,7 +74,7 @@ Test(apple2_mem, read_bank)
|
|||||||
// value in memory... but, as a twist, also check that the value is
|
// value in memory... but, as a twist, also check that the value is
|
||||||
// not set in ROM nor in RAM2.
|
// not set in ROM nor in RAM2.
|
||||||
val = 222;
|
val = 222;
|
||||||
apple2_set_bank_switch(mach, MEMORY_WRITE);
|
apple2_set_bank_switch(mach, BANK_RAM | BANK_WRITE);
|
||||||
vm_segment_set(mach->main, 0xD077, val);
|
vm_segment_set(mach->main, 0xD077, val);
|
||||||
cr_assert_eq(vm_segment_get(mach->main, 0xD077), val);
|
cr_assert_eq(vm_segment_get(mach->main, 0xD077), val);
|
||||||
cr_assert_neq(vm_segment_get(mach->rom, 0x77), val);
|
cr_assert_neq(vm_segment_get(mach->rom, 0x77), val);
|
||||||
@ -85,7 +85,7 @@ Test(apple2_mem, read_bank)
|
|||||||
// if it's there when addressing from main memory in the $Dnnn
|
// if it's there when addressing from main memory in the $Dnnn
|
||||||
// range.
|
// range.
|
||||||
val = 111;
|
val = 111;
|
||||||
apple2_set_bank_switch(mach, mach->bank_switch | MEMORY_RAM2);
|
apple2_set_bank_switch(mach, mach->bank_switch | BANK_RAM2);
|
||||||
vm_segment_set(mach->main, 0x10077, val);
|
vm_segment_set(mach->main, 0x10077, val);
|
||||||
cr_assert_eq(vm_segment_get(mach->main, 0xD077), val);
|
cr_assert_eq(vm_segment_get(mach->main, 0xD077), val);
|
||||||
}
|
}
|
||||||
@ -100,12 +100,11 @@ Test(apple2_mem, write_bank)
|
|||||||
{
|
{
|
||||||
vm_8bit right, wrong;
|
vm_8bit right, wrong;
|
||||||
|
|
||||||
// In BANK_ROM mode, we expect that updates to ROM will never be
|
// In BANK_DEFAULT mode, we expect that updates to ROM will never be
|
||||||
// successful (after all, it wouldn't be read-only memory if they
|
// successful (after all, it wouldn't be read-only memory if they
|
||||||
// were).
|
// were).
|
||||||
right = 123;
|
right = 123;
|
||||||
wrong = 222;
|
wrong = 222;
|
||||||
apple2_set_bank_switch(mach, MEMORY_ROM);
|
|
||||||
vm_segment_set(mach->rom, 0x77, right);
|
vm_segment_set(mach->rom, 0x77, right);
|
||||||
vm_segment_set(mach->main, 0xD077, wrong);
|
vm_segment_set(mach->main, 0xD077, wrong);
|
||||||
cr_assert_eq(vm_segment_get(mach->rom, 0x77), right);
|
cr_assert_eq(vm_segment_get(mach->rom, 0x77), right);
|
||||||
@ -114,7 +113,7 @@ Test(apple2_mem, write_bank)
|
|||||||
// RAM1 is the main bank; it's all 64k RAM in one chunk.
|
// RAM1 is the main bank; it's all 64k RAM in one chunk.
|
||||||
right = 111;
|
right = 111;
|
||||||
wrong = 232;
|
wrong = 232;
|
||||||
apple2_set_bank_switch(mach, MEMORY_WRITE);
|
apple2_set_bank_switch(mach, BANK_RAM | BANK_WRITE);
|
||||||
vm_segment_set(mach->main, 0xD078, right);
|
vm_segment_set(mach->main, 0xD078, right);
|
||||||
vm_segment_set(mach->main, 0x10078, wrong);
|
vm_segment_set(mach->main, 0x10078, wrong);
|
||||||
cr_assert_eq(vm_segment_get(mach->main, 0xD078), right);
|
cr_assert_eq(vm_segment_get(mach->main, 0xD078), right);
|
||||||
@ -124,7 +123,7 @@ Test(apple2_mem, write_bank)
|
|||||||
// ($D000..$DFFF) is in ram2.
|
// ($D000..$DFFF) is in ram2.
|
||||||
right = 210;
|
right = 210;
|
||||||
wrong = 132;
|
wrong = 132;
|
||||||
apple2_set_bank_switch(mach, mach->bank_switch | MEMORY_RAM2);
|
apple2_set_bank_switch(mach, mach->bank_switch | BANK_RAM2);
|
||||||
vm_segment_set(mach->main, 0x10073, wrong);
|
vm_segment_set(mach->main, 0x10073, wrong);
|
||||||
vm_segment_set(mach->main, 0xD073, right);
|
vm_segment_set(mach->main, 0xD073, right);
|
||||||
cr_assert_eq(vm_segment_get(mach->main, 0x10073), right);
|
cr_assert_eq(vm_segment_get(mach->main, 0x10073), right);
|
||||||
@ -133,65 +132,65 @@ Test(apple2_mem, write_bank)
|
|||||||
Test(apple2_mem, read_bank_switch)
|
Test(apple2_mem, read_bank_switch)
|
||||||
{
|
{
|
||||||
vm_segment_get(mach->main, 0xC080);
|
vm_segment_get(mach->main, 0xC080);
|
||||||
cr_assert_eq(mach->bank_switch, MEMORY_RAM2);
|
cr_assert_eq(mach->bank_switch, BANK_RAM | BANK_RAM2);
|
||||||
|
|
||||||
// This (and a few others) are trickier to test, as they require
|
// This (and a few others) are trickier to test, as they require
|
||||||
// consecutive reads to trigger.
|
// consecutive reads to trigger.
|
||||||
vm_segment_get(mach->main, 0xC081);
|
vm_segment_get(mach->main, 0xC081);
|
||||||
cr_assert_neq(mach->bank_switch, MEMORY_ROM | MEMORY_WRITE | MEMORY_RAM2);
|
cr_assert_neq(mach->bank_switch, BANK_WRITE | BANK_RAM2);
|
||||||
mach->cpu->last_addr = 0xC081;
|
mach->cpu->last_addr = 0xC081;
|
||||||
vm_segment_get(mach->main, 0xC081);
|
vm_segment_get(mach->main, 0xC081);
|
||||||
cr_assert_eq(mach->bank_switch, MEMORY_ROM | MEMORY_WRITE | MEMORY_RAM2);
|
cr_assert_eq(mach->bank_switch, BANK_WRITE | BANK_RAM2);
|
||||||
|
|
||||||
vm_segment_get(mach->main, 0xC082);
|
vm_segment_get(mach->main, 0xC082);
|
||||||
cr_assert_eq(mach->bank_switch, MEMORY_ROM | MEMORY_RAM2);
|
cr_assert_eq(mach->bank_switch, BANK_RAM2);
|
||||||
|
|
||||||
// Another that needs consecutives
|
// Another that needs consecutives
|
||||||
vm_segment_get(mach->main, 0xC083);
|
vm_segment_get(mach->main, 0xC083);
|
||||||
cr_assert_neq(mach->bank_switch, MEMORY_WRITE | MEMORY_RAM2);
|
cr_assert_neq(mach->bank_switch, BANK_RAM | BANK_WRITE | BANK_RAM2);
|
||||||
mach->cpu->last_addr = 0xC083;
|
mach->cpu->last_addr = 0xC083;
|
||||||
vm_segment_get(mach->main, 0xC083);
|
vm_segment_get(mach->main, 0xC083);
|
||||||
cr_assert_eq(mach->bank_switch, MEMORY_WRITE | MEMORY_RAM2);
|
cr_assert_eq(mach->bank_switch, BANK_RAM | BANK_WRITE | BANK_RAM2);
|
||||||
|
|
||||||
vm_segment_get(mach->main, 0xC088);
|
vm_segment_get(mach->main, 0xC088);
|
||||||
cr_assert_eq(mach->bank_switch, 0);
|
cr_assert_eq(mach->bank_switch, BANK_RAM);
|
||||||
|
|
||||||
// You get the idea
|
// You get the idea
|
||||||
vm_segment_get(mach->main, 0xC089);
|
vm_segment_get(mach->main, 0xC089);
|
||||||
cr_assert_neq(mach->bank_switch, MEMORY_ROM | MEMORY_WRITE);
|
cr_assert_neq(mach->bank_switch, BANK_WRITE);
|
||||||
mach->cpu->last_addr = 0xC089;
|
mach->cpu->last_addr = 0xC089;
|
||||||
vm_segment_get(mach->main, 0xC089);
|
vm_segment_get(mach->main, 0xC089);
|
||||||
cr_assert_eq(mach->bank_switch, MEMORY_ROM | MEMORY_WRITE);
|
cr_assert_eq(mach->bank_switch, BANK_WRITE);
|
||||||
|
|
||||||
vm_segment_get(mach->main, 0xC08A);
|
vm_segment_get(mach->main, 0xC08A);
|
||||||
cr_assert_eq(mach->bank_switch, MEMORY_ROM);
|
cr_assert_eq(mach->bank_switch, BANK_DEFAULT);
|
||||||
|
|
||||||
vm_segment_get(mach->main, 0xC08B);
|
vm_segment_get(mach->main, 0xC08B);
|
||||||
cr_assert_neq(mach->bank_switch, MEMORY_WRITE);
|
cr_assert_neq(mach->bank_switch, BANK_RAM | BANK_WRITE);
|
||||||
mach->cpu->last_addr = 0xC08B;
|
mach->cpu->last_addr = 0xC08B;
|
||||||
vm_segment_get(mach->main, 0xC08B);
|
vm_segment_get(mach->main, 0xC08B);
|
||||||
cr_assert_eq(mach->bank_switch, MEMORY_WRITE);
|
cr_assert_eq(mach->bank_switch, BANK_RAM | BANK_WRITE);
|
||||||
|
|
||||||
mach->bank_switch = MEMORY_RAM2;
|
mach->bank_switch = BANK_RAM | BANK_RAM2;
|
||||||
cr_assert_eq(vm_segment_get(mach->main, 0xC011), 0x80);
|
cr_assert_eq(vm_segment_get(mach->main, 0xC011), 0x80);
|
||||||
mach->bank_switch = 0;
|
mach->bank_switch = BANK_DEFAULT;
|
||||||
cr_assert_eq(vm_segment_get(mach->main, 0xC011), 0x00);
|
cr_assert_eq(vm_segment_get(mach->main, 0xC011), 0x00);
|
||||||
mach->bank_switch = 0;
|
mach->bank_switch = BANK_RAM;
|
||||||
cr_assert_eq(vm_segment_get(mach->main, 0xC012), 0x80);
|
cr_assert_eq(vm_segment_get(mach->main, 0xC012), 0x80);
|
||||||
mach->bank_switch = MEMORY_ROM;
|
mach->bank_switch = BANK_DEFAULT;
|
||||||
cr_assert_eq(vm_segment_get(mach->main, 0xC012), 0x00);
|
cr_assert_eq(vm_segment_get(mach->main, 0xC012), 0x00);
|
||||||
mach->bank_switch = MEMORY_AUX;
|
mach->bank_switch = BANK_ALTZP;
|
||||||
cr_assert_eq(vm_segment_get(mach->main, 0xC016), 0x80);
|
cr_assert_eq(vm_segment_get(mach->main, 0xC016), 0x80);
|
||||||
mach->bank_switch = 0;
|
mach->bank_switch = BANK_DEFAULT;
|
||||||
cr_assert_eq(vm_segment_get(mach->main, 0xC016), 0x00);
|
cr_assert_eq(vm_segment_get(mach->main, 0xC016), 0x00);
|
||||||
}
|
}
|
||||||
|
|
||||||
Test(apple2_mem, write_bank_switch)
|
Test(apple2_mem, write_bank_switch)
|
||||||
{
|
{
|
||||||
vm_segment_set(mach->main, 0xC008, 1);
|
vm_segment_set(mach->main, 0xC008, 1);
|
||||||
cr_assert_eq(mach->bank_switch & MEMORY_AUX, MEMORY_AUX);
|
cr_assert_eq(mach->bank_switch & BANK_ALTZP, BANK_ALTZP);
|
||||||
vm_segment_set(mach->main, 0xC009, 1);
|
vm_segment_set(mach->main, 0xC009, 1);
|
||||||
cr_assert_eq(mach->bank_switch & MEMORY_AUX, 0);
|
cr_assert_eq(mach->bank_switch & BANK_ALTZP, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
Test(apple2_mem, init_peripheral_rom)
|
Test(apple2_mem, init_peripheral_rom)
|
||||||
|
Loading…
Reference in New Issue
Block a user