/*\r
- FUJITSU FM16pi Emulator 'eFM16pi'\r
+ FUJITSU FM7 Emulator 'eFM7'\r
\r
- Author : Takeda.Toshiya\r
- Date : 2010.12.25-\r
+ Author : K.Ohta\r
+ Date : 2015.01.01-\r
\r
[ virtual machine ]\r
*/\r
EVENT* event;\r
\r
MC6809* maincpu;\r
+ FM77_MAINMEM *mainmem;\r
+ FM7_KANJIROM *kanjiclass1;\r
+ FM7_SHAREDRAM *sharedram;\r
+ FM77_DIPSW* dipsw;\r
+\r
MB8877* fdc;\r
- MEMORY* mainmemory;\r
YM2203* opn;\r
YM2203* whg;\r
YM2203* thg;\r
FM7_LPT* printer;\r
FM7_MOUSE* mouse_opn;\r
FM7_MAINIRQ* main_interrupt;\r
- FM7_SHAREDBUS* mainsub_bus;\r
FM7_DPALET* ttl_palette;\r
- \r
- FM7_APALET* analog_palette;\r
- FM7_MMR* mmr;\r
- FM7_WINDOW *fm7_window;\r
- FM7_DMA* dma;\r
#endif \r
MC6809* subcpu;\r
- MEMORY* submemory;\r
+ FM7_SUBMEM* submem;\r
+\r
#if 0 // WILL Implement\r
FM7_DISPLAY* display;\r
FM7_KBD* keyboard;\r
FM7_SUBIRQ* sub_interrupt;\r
- \r
- FM7_RTC* rtc;\r
- FM7_ALU* alu;\r
#endif \r
\r
int machine_version; // 0 = FM8 / 1 = FM7 / 2 = FM77AV / 3 = FM77AV40, etc...\r
Uint32 bootmode; \r
Uint32 connected_opns;\r
- bool cycle_steal = true;\r
+ bool cycle_steal = false;\r
bool clock_low = false;\r
int mainfreq_type;\r
Uint32 mainfreq_low;\r
bool cmt_rec;\r
Uint32 cmt_bufptr;\r
\r
- // memory\r
- // MAIN\r
- uint8 mainram_b1[0x10000]; // 0x10000, RAM\r
- uint8 mainram_b2[0x10000]; // 0x20000, RAM\r
- uint8 mainram_b3a[0x8000]; // 0x30000, RAM\r
- uint8 basicrom[0x7c00]; // 0x38000, ROM\r
- uint8 mainram_b3b[0x7c00]; // 0x38000, RAM\r
- uint8 shadowram[0x80]; // 0x3fc00, RAM\r
- uint8 sharedram[0x80]; // 0x3fc80, Shared RAM\r
- uint8 mainio[0x100]; // 0xfd00 - 0xfdff I/O\r
- uint8 boot_bas[0x1f0]; // 0xfe00, BOOT(BAS)\r
- uint8 boot_dos[0x1f0];\r
- uint8 boot_bubl[0x1f0];\r
- uint8 boot_ram[0x1f0];\r
- uint8 main_vector[0x10]; // 0xfff0, VECTOR(main)\r
- uint8 initiate[0x2000]; // Initiate RAM.\r
-\r
- uint8 dictrom[0x40000];\r
- uint8 kanjirom1[0x20000];\r
- uint8 kanjirom2[0x20000];\r
- // SUB\r
- uint8 vram_b1[0xc000];\r
- uint8 vram_b2[0xc000];\r
- uint8 vram_b3[0xc000];\r
- uint8 subchar[0x1000];\r
- uint8 subwork[0x0380];\r
- //uint8 sharedram_sub[0x80];\r
- uint8 subio[0x400]; // Really?\r
- uint8 cgrom[0x2000];\r
- uint8 submon_a[0x2000];\r
- uint8 submon_b[0x2000];\r
- uint8 submon_c[0x2800];\r
- uint8 extsubrom[0xc000];\r
public:\r
// ----------------------------------------\r
// initialize\r
--- /dev/null
+/*
+ FUJITSU FM7 Emulator 'eFM7'
+
+ Author : K.Ohta
+ Date : 2015.01.01-
+
+ [ virtual machine ]
+*/
+
+#ifndef _FM77_H_
+#define _FM77_H_
+
+#define DEVICE_NAME "FUJITSU FM77/L2/L4"
+#define CONFIG_NAME "fm77"
+
+// device informations for virtual machine
+
+// TODO: check refresh rate
+#define FRAMES_PER_SEC 60
+#define LINES_PER_FRAME 400
+#define CPU_CLOCKS 2000000
+#define SCREEN_WIDTH 640
+#define SCREEN_HEIGHT 400
+#define MAX_DRIVE 4
+#define HAS_MC6809
+#define MB8877_MAX_CHIPS 1
+#define MEMORY_ADDR_MAX 0x10000
+#define MEMORY_BANK_SIZE 0x1000
+//#define IO_ADDR_MAX 0x10000
+
+// device informations for win32
+#define USE_FD1
+#define USE_FD2
+#define NOTIFY_KEY_DOWN
+#define NOTIFY_KEY_UP
+#define USE_ALT_F10_KEY
+#define USE_AUTO_KEY 5
+#define USE_AUTO_KEY_RELEASE 6
+#define USE_POWER_OFF
+#define USE_ACCESS_LAMP
+//#define USE_DEBUGGER
+
+#define ENABLE_OPENCL // If OpenCL renderer is enabled, define here.
+
+#include "../../common.h"
+#include "fm77_mainmem.h"
+
+class EMU;
+class DEVICE;
+class EVENT;
+
+class BEEP;
+class MC6809;
+class YM2203;
+class MB8877;
+class MEMORY;
+class FM77_MAINMEM;
+
+#if 0
+class Z80;
+#endif
+class VM
+{
+protected:
+ EMU* emu;
+
+ // devices
+ EVENT* event;
+
+ MC6809* maincpu;
+ FM77_MAINMEM* mainmem;
+ FM7_KANJIROM* kanjiclass1;
+ FM7_SHAREDRAM* sharedram;
+ FM7_DIPSW* dipsw;
+
+ MB8877* fdc;
+ YM2203* opn;
+ YM2203* whg;
+ YM2203* thg;
+ YM2203* psg; // Is right? AY-3-8910 is right device.
+ BEEP* beep;
+#if 0
+ Z80* z80cpu;
+#endif
+#if 0 // WILL Implement
+ FM7_CMT* cmt;
+ FM7_OPNJOY* joystick_opn;
+ FM7_LPT* printer;
+ FM7_MOUSE* mouse_opn;
+ FM7_MAINIRQ* main_interrupt;
+ FM7_DPALET* ttl_palette;
+
+ FM7_MMR* mmr;
+ FM7_WINDOW *fm7_window;
+#endif
+ MC6809* subcpu;
+ FM77_SUBMEM *submem;
+#if 0 // WILL Implement
+ FM7_DISPLAY* display;
+ FM7_KBD* keyboard;
+ FM7_SUBIRQ* sub_interrupt;
+#endif
+
+ int machine_version; // 0 = FM8 / 1 = FM7 / 2 = FM77AV / 3 = FM77AV40, etc...
+ Uint32 bootmode;
+ Uint32 connected_opns;
+ bool cycle_steal = true;
+ bool clock_low = false;
+ int mainfreq_type;
+ Uint32 mainfreq_low;
+ Uint32 mainfreq_high;
+
+ Uint32 fdd_type[MAX_DRIVES];
+ BOOL fdd_connect[MAX_DRIVES];
+
+ FILEIO* cmt_fileio;
+ bool cmt_enabled = true; // 77AV40SX is disabled.
+ bool cmt_play;
+ bool cmt_rec;
+ Uint32 cmt_bufptr;
+
+ // memory
+ // MAIN
+
+ // SUB
+public:
+ // ----------------------------------------
+ // initialize
+ // ----------------------------------------
+
+ VM(EMU* parent_emu);
+ ~VM();
+
+ // ----------------------------------------
+ // for emulation class
+ // ----------------------------------------
+
+ // drive virtual machine
+ void reset();
+ void notify_power_off();
+ void run();
+
+#ifdef USE_DEBUGGER
+ // debugger
+ DEVICE *get_cpu(int index);
+#endif
+
+ // draw screen
+ void draw_screen();
+ int access_lamp();
+
+ // sound generation
+ void initialize_sound(int rate, int samples);
+ uint16* create_sound(int* extra_frames);
+ int sound_buffer_ptr();
+
+ // notify key
+ void key_down(int code, bool repeat);
+ void key_up(int code);
+
+ // user interface
+ void open_disk(int drv, _TCHAR* file_path, int offset);
+ void close_disk(int drv);
+ bool disk_inserted(int drv);
+ bool now_skip();
+
+ void update_config();
+
+ // ----------------------------------------
+ // for each device
+ // ----------------------------------------
+
+ // devices
+ DEVICE* get_device(int id);
+ DEVICE* dummy;
+ DEVICE* first_device;
+ DEVICE* last_device;
+};
+
+#endif
--- /dev/null
+/*
+ *
+ */
+
+int FM77_MAINMEM::getbank(uint32 addr, uint32 *realaddr)
+{
+ if(realaddr == NULL) return -1; // Not effect.
+
+ addr = addr & 0xffff;
+ if(window != NULL) {
+ if(window->isenabled() && (addr >= 0x7c00) && (addr < 0x8000)) { // Window open
+ if(use_extram) {
+ *realaddr = ((addr + window->getwindow() * 256) & 0xffff) + 0x20000;
+ return FM77_MAINMEM_77EXTRAM; // FM77
+ }
+ mainio->wait();
+ mmr_beforeaccess = false; // Really?
+ *realaddr = 0;
+ return -1;
+ }
+ }
+ if(mmr != NULL) {
+ int mmr_page;
+ uint32 mmr_offset;
+ if(!mmr->isenabled()) goto _fm7_0;
+ mainio->wait(); // 1 wait per 3 access.
+ mmr_page = mmr->getpage(addr);
+
+ if(addr < 0xfc00) { // MMR Banked
+ mmr_offset = addr & 0x0fff;
+ if(mmr_page < 0x30) {
+ if(use_extram) {
+ *realaddr = mmr_offset + mmr_page * 0x1000;
+ return FM7_MAINMEM_77EXTRAM;
+ }
+ *realaddr = 0;
+ return -1;
+ } else if((mmr_page & 0x30) == 0x30) {
+ if(mmr_page == 0x3f) { // $3f000 - $3ffff
+ if(mmr_offset < 0x0c00) {
+ addr = mmr_offset + 0xf000;
+ goto _fm7_0;
+ }
+ if((mmr_offset < 0x0e00)) {
+ *realaddr = mmr_offset - 0x0c00;
+ if(mainio->get_rommode_fd0f() == true) {
+ return FM7_MAINMEN_77_NULLRAM;
+ }
+ return FM7_MAINMEM_77_SHADOWRAM;
+ }
+ addr = mmr_offset + 0xf000;
+ goto _fm7_0; //
+ }
+ // $30000 - $3efff
+ addr = mmr_offset + (mmr_page & 0x0f) * 0x1000;
+ goto _fm7_0;
+ }
+ *realaddr = 0;
+ return -1; // Illegal
+ }
+ goto fm7_0; // With I/O Wait.
+ }
+
+_fm7_0:
+ if((addr >= 0xfe00) && (addr < 0xfffe)) {
+ *realaddr = addr - 0xfe00;
+ if(addr < 0xffe0) mainio->wait();
+ if(mainio->get_boot_romram() != true) {
+ return FM7_MAINMEM_BOOTROM_RAM;
+ }
+ }
+ return FM7_MAINMEM::getbank(addr, realaddr);
+}
+
--- /dev/null
+/*
+ * Main memory with MMR for FM-77 [FM77_MAINMEM]
+ * Author: K.Ohta
+ * Date : 2015.01.01-
+ *
+ */
+
+#ifndef _FM77_MAINMEM_H_
+#define _FM77_MAINMEM_H_
+
+#include "fm7_mainmem.h"
+
+class FM77_MAIN_MMR;
+class FM77_MAIN_WINDOW;
+
+class FM77_MAINMEM : public FM7_MAINMEM
+{
+ private:
+ uint8 fm77_extram_192k[0x30000];
+ uint8 fm77_shadowram[0x200];
+
+ FM77_MAIN_MMR *mmr = NULL;
+ FM77_MAIN_WINDOW *window = NULL;
+ bool use_extram = false;
+
+ int getbank(uint32 addr, uint32 *realaddr);
+ public:
+ FM77_MAINMEM(VM* parent_vm, EMU* parent_emu) : FM7_MAINMEM(parent_vm, parent_emu)
+ {
+ int bank_num;
+ int i;
+
+ i = FM77_MAINMEM_77EXTRAM;
+ memset(fm77_extram_192k, 0x00, 0x30000 * sizeof(uint8));
+ read_table[FM7_MAINMEM_77EXTRAM].memory = fm77_extram_192k;
+ write_table[FM7_MAINMEM_77EXTRAM].memory = fm77_extram_192k;
+ read_table[FM7_MAINMEM_77EXTRAM].dev = NULL;
+ write_table[FM7_MAINMEM_77EXTRAM].dev = NULL;
+
+ i = FM77_MAINMEM_77SHADOWRAM;
+ memset(fm77_extram_192k, 0x00, 0x200 * sizeof(uint8));
+ read_table[FM7_MAINMEM_77EXTRAM].memory = fm77_shadowram;
+ write_table[FM7_MAINMEM_77EXTRAM].memory = fm77_shadowram;
+ read_table[FM7_MAINMEM_77EXTRAM].dev = NULL;
+ write_table[FM7_MAINMEM_77EXTRAM].dev = NULL;
+
+
+ }
+
+ ~FM7_MAINMEM(void) {
+ int i;
+ for(i = 0; i < 4; i++) {
+ if(fm7_bootroms[i] != NULL) free(fm7_bootroms[i]);
+ fm7_bootroms[i] = NULL;
+ }
+ if(read_table != NULL) free(read_table);
+ if(write_table != NULL) free(write_table);
+ write_table = NULL;
+ read_table = NULL;
+ }
+
+ uint32 read_data8(uint32 addr);
+ void write_data8(uint32 addr, uint32 data);
+ uint32 read_data16(uint32 addr);
+ void write_data16(uint32 addr, uint32 data);
+ uint32 read_data32(uint32 addr);
+ void write_data32(uint32 addr, uint32 data);
+ bool get_loadstat_basicrom(void);
+ bool get_loadstat_bootrom_bas(void);
+ bool get_loadstat_bootrom_dos(void);
+}
--- /dev/null
+/*
+ * Main memory emulation of FM77AV40.
+ * MEMORY -> FM7_MAINMEM -> FM77AV_MAINMEM -> FM77AV40_MAINMEM
+ * Author: K.Ohta <whatisthis.sowhat _at_ gmail.com>
+ * History Jan 02, 2015 : Initial.
+ */
+
+int FM77AV40_MAINMEM::getbank(uint32 addr, uint32 *realaddr)
+{
+ if(realaddr == NULL) return -1; // Not effect.
+ addr = addr & 0x0ffff;
+ if(window != NULL) {
+ if(window->isenabled() && (addr >= 0x7c00) && (addr < 0x8000)) { // Window open
+ *realaddr = (addr + window->getwindow() * 256) & 0xffff;
+ return FM77AV_MAINMEM_PAGE0; // FM77
+ }
+ }
+ if(mmr != NULL) {
+ uint32 mmr_page = mmr->getpage();
+ uint32 mmr_offset = addr & 0x0fff;;
+ if(!mmr->isenabled()) goto _fm7_1;
+ if((mmr_page & 0x30) == 0x30) { // 77AV RAM/ROM Page1
+ uint32 a;
+ a = (mmr_page & 0x0f) * 0x1000 + mmr_offset;
+ if((a < 0xfd80) && (a > 0xfd97)) { // Okay.
+ addr = a;
+ goto _fm7_1;
+ }
+ // MMR Area is illegal.
+ *realaddr = 0;
+ return -1;
+ }
+ if(mmr_page < 0x10) { // 77AV RAM PAGE0
+ *realaddr = mmr_page * 0x1000 + mmr_offset;
+ return FM7_MAINMEM_AV_PAGE0;
+ }
+ if(mmr_page < 0x20) { // 77AV VRAM
+ *realaddr = ((mmr_page & 0x0f) * 0x1000) + mmr_offset;
+ return FM7_MAINMEM_AV_SUBMEM;
+ }
+ if(mmr_page < 0x30) { // 77AV Jcard
+ if(jcard != NULL) {
+ if(jcard->isenabled()) {
+ *realaddr = ((mmr_page & 0x0f) * 0x1000) + mmr_offset;
+ return FM7_MAINMEM_AV_JCARD;
+ }
+ }
+ *realaddr = mmr_offset;
+ return -1; // Illegal
+ }
+ if(use_extram) { // EXTRAM
+ *realaddr = ((mmr_page - 0x40) * 0x1000) + mmr_offset;
+ return FM7_MAINMEM_AV_EXTRAM768K;
+ } else {
+ *realaddr = 0;
+ return -1;
+ }
+ }
+
+_fm7_1:
+ if(mainio->is_initiaterom()) { // Initiate rom enabled, force overwrite vector.
+ if(addr >= 0xfffe) {
+ mainio->wait();
+ *realaddr = addr - 0xe000;
+ return FM7_MAINMEM_AV_INITROM;
+ }
+ if((addr >= 0x6000) && (addr < 0x8000)){ // Real addr: $6000 - $7fff
+ *realaddr = addr - 0x6000;
+ return FM7_MAINMEM_AV_INITROM;
+ }
+ }
+ if((addr < 0x10000) && (addr >= 0xfe00)) {
+ if(addr < 0xffe0) mainio->wait();
+ *realaddr = addr - 0xfe00;
+ return FM7_MAINMEM_BOOTROM_RAM;
+ }
+
+ return FM7_MAINMEM::getvram(addr, realaddr);
+ // Over
+}
+
--- /dev/null
+/*
+ * Main memory emulation of FM77AV40.
+ * MEMORY -> FM7_MAINMEM -> FM77AV_MAINMEM -> FM77AV40_MAINMEM
+ * Author: K.Ohta <whatisthis.sowhat _at_ gmail.com>
+ * History Jan 02, 2015 : Initial.
+ */
+
+#ifndef _FM77AV40_MAINMEM_H_
+#odefine _FM77AV40_MAINMEM_H_
+#include "fm77av_mainmem.h"
+
+class FM77AV40_MAINMEM : public FM77AV_MAINMEM;
+{
+
+ protected:
+ uint8 mainmem_extram786k[0xc0000];
+ bool use_extram = false;
+
+ void patch_bootrom(void) {
+ uint8 *p = &mainmem_initrom[0x0b0e];
+ char *s = "401Ma.";
+
+ for(i = 0; i < 6; i++) *p++ = *s++;
+
+ /* Patch initiator_rom */
+ if(patched_bootrom_p1 != NULL) {
+ patched_bootrom_p1[0] = 0x20; // BRN->BRA
+ goto _boot_2;
+ }
+ p = mainmem_initrom;
+ for(i = 0; i < 0x0b00; i++) {
+ if((p[0] == 0x20) && (p[1] == 0xd7)) {
+ p[0] = 0x20; // BRA->BRN
+ patched_bootrom_p1 = p;
+ }
+ p++;
+ }
+ _boot_2:
+ if(patched_bootrom_p2 != NULL) {
+ patched_bootrom_p2[1] = 0x50; // fe00 -> 5000
+ patched_bootrom_p2[2] = 0x00;
+ goto _boot_3;
+ }
+ p = mainmem_initrom;
+ for(i = 0; i < 0x0b00; i++) {
+ // 7e 5000 : jmp $5000 -> jmp $fe00
+ if(p[0] == 0x7e) {
+ if((p[1] == 0xfe) && (p[2] == 0x00)) {
+ p[1] = 0x50;
+ p[2] = 0x00;
+ patched_bootrom_p2 = p;
+ }
+ }
+ p++;
+ }
+_boot_3:
+ }
+
+ int getbank(uint32 addr, uint32 *realaddr);
+ public:
+ void reset(void);
+ FM77AV40_MAINMEM(VM* parent_vm, EMU* parent_emu) : FM77AV_MAINMEM(parent_vm, parent_emu)
+ {
+ int i;
+ i = FM7_MAINMEM_AV_EXTRAM768K;
+ memset(mainmem_mainmem_extram786k, 0x00, sizeof(mainmem_extram768k));
+ read_table[i].dev = write_table[i].dev = NULL;
+ read_table[i].memory = write_table[i].memory = mainmem_extram768k;
+ }
+
+ ~FM77AV40_MAINMEM(void) {
+ }
+
+ void get_stat_extram(void) {
+ return use_extram;
+ }
+
+ void connect_extram(bool mode){
+ if(mode == false){
+ if(use_extram != false){
+ use_extram = false;
+ reset();
+ }
+ } else {
+ if(use_extram == false) {
+ use_extram = true;
+ reset();
+ }
+ }
+ }
+
+}
+
+#endif
--- /dev/null
+/*
+ * Main memory without MMR for FM-7 [FM7_MAINMEM]
+ * Author: K.Ohta
+ * Date : 2015.01.01-
+ *
+ */
+
+#include "fm7_mainmem.h"
+
+int FM77AV_MAINMEM::getbank(uint32 addr, uint32 *realaddr)
+{
+ if(realaddr == NULL) return -1; // Not effect.
+
+ addr = addr & 0xffff;
+ addr = addr & 0x0ffff;
+
+ if(window != NULL) {
+ if(window->isenabled() && (addr >= 0x7c00) && (addr < 0x8000)) { // Window open
+ *realaddr = (addr + window->getwindow() * 256) & 0xffff;
+ return FM77AV_MAINMEM_PAGE0; // FM77
+ }
+ }
+ if(mmr != NULL) {
+ uint32 mmr_page = mmr->getpage(addr);
+ uint32 mmr_offset;
+ if(!mmr->isenabled()) goto _fm7_1;
+ if((mmr_page & 0x30) == 0x30) { // 77AV RAM/ROM Page1
+ uint32 a;
+ a = (mmr_page & 0x0f) * 0x1000 + mmr_offset;
+ if((a < 0xfd80) && (a > 0xfd97)) { // Okay.
+ addr = a;
+ goto _fm7_1;
+ }
+ // MMR Area is illegal.
+ *realaddr = 0;
+ return -1;
+ }
+ if(mmr_page < 0x10) { // 77AV RAM PAGE0
+ *realaddr = mmr_page * 0x1000 + mmr_offset;
+ return FM7_MAINMEM_AV_PAGE0;
+ }
+ if(mmr_page < 0x20) { // 77AV VRAM
+ *realaddr = ((mmr_page & 0x0f) * 0x1000) + mmr_offset;
+ return FM7_MAINMEM_AV_SUBMEM;
+ }
+ if(mmr_page < 0x30) { // 77AV Jcard
+ if(jcard != NULL) {
+ if(jcard->isenabled()) {
+ *realaddr = ((mmr_page & 0x0f) * 0x1000) + mmr_offset;
+ return FM7_MAINMEM_AV_JCARD;
+ }
+ }
+ *realaddr = mmr_offset;
+ return -1; // Illegal
+ }
+// if(use_extram) { // EXTRAM
+// *realaddr = ((mmr_page - 0x40) * 0x1000) + mmr_offset;
+// return FM7_MAINMEM_AV_EXTRAM768K;
+// }
+ }
+
+_fm7_1:
+ if(mainio->is_initiaterom()) { // Initiate rom enabled, force overwrite vector.
+ if(addr >= 0xfffe) {
+ mainio->wait();
+ *realaddr = addr - 0xe000;
+ return FM7_MAINMEM_AV_INITROM;
+ }
+ if((addr >= 0x6000) && (addr < 0x8000)){ // Real addr: $6000 - $7fff
+ *realaddr = addr - 0x6000;
+ return FM7_MAINMEM_AV_INITROM;
+ }
+ }
+ if((addr < 0x10000) && (addr >= 0xfe00)) {
+ if(addr < 0xffe0) mainio->wait();
+ *realaddr = addr - 0xfe00;
+ return FM7_MAINMEM_BOOTROM_RAM;
+ }
+
+ return FM7_MAINMEM::getvram(addr, realaddr);
+ // Over
+}
+
+
+void FM77AV_MAINMEM::mem_reset(void)
+{
+ Uint32 bootmode;
+ memset(fm7_bootroms[FM7_MAINMEM_BOOTROM_RAM - FM7_MAINMEM_BOOTROM_BAS], 0x00, 0x1e0); // Clear without vectors.
+ bootmode = dipsw->getbootmode();
+
+ if((bootmode & FM7_BOOTMODE_RAM) == 0) {
+ bootmode &= 1;
+ if(bootmode == FM7_BOOTMODE_BASIC) {
+ memcpy(fm7_bootroms[FM7_MAINMEM_BOOTROM_RAM - FM7_MAINMEM_BOOTROM_BAS], &initiator_rom[0x1800], 0x1e0);
+ } else {
+ memcpy(fm7_bootroms[FM7_MAINMEM_BOOTROM_RAM - FM7_MAINMEM_BOOTROM_BAS], &initiator_rom[0x1a00], 0x1e0);
+ }
+ patch_bootrom();
+ }
+}
+
+bool FM77AV_MAINMEM::get_loadstat_initrom(void)
+{
+ return diag_load_initrom;
+}
--- /dev/null
+/*
+ * Main memory emulation of FM77AV.
+ * MEMORY -> FM7_MAINMEM -> FM77AV_MAINMEM
+ * Author: K.Ohta <whatisthis.sowhat _at_ gmail.com>
+ * History Jan 02, 2015 : Initial.
+ */
+
+#ifndef _FM77AV_MAINMEM_H_
+#odefine _FM77AV_MAINMEM_H_
+#include "fm7_mainmem.h"
+
+
+class FM77AV_MAINMEM : public FM7_MAINMEM;
+{
+
+ protected:
+ uint8 mainmem_page0[0x10000];
+ uint8 mainmem_jcard[0x20000];
+ uint8 mainmem_initrom[0x2000];
+ uint8 *patched_bootrom_p1;
+ uint8 *patched_bootrom_p2;
+ bool diag_load_initrom = false;
+
+ virtual void patch_bootrom(void) {
+ uint8 *p = &initiator_rom[0x0b0e];
+ for(i = 0; i < 6; i++) *p++ = 0xff;
+
+ /* Patch initiator_rom */
+ if(patched_bootrom_p1 != NULL) {
+ patched_bootrom_p1[0] = 0x21; // BRA->BRN
+ goto _boot_2;
+ }
+ p = initiator_rom;
+ for(i = 0; i < 0x0b00; i++) {
+ if((p[0] == 0x20) && (p[1] == 0xd7)) {
+ p[0] = 0x21; // BRA->BRN
+ patched_bootrom_p1 = p;
+ }
+ p++;
+ }
+ _boot_2:
+ if(patched_bootrom_p2 != NULL) {
+ patched_bootrom_p2[1] = 0xfe; // 5000 -> fe00
+ patched_bootrom_p2[2] = 0x00;
+ goto _boot_3;
+ }
+ p = initiator_rom;
+ for(i = 0; i < 0x0b00; i++) {
+ // 7e 5000 : jmp $5000 -> jmp $fe00
+ if(p[0] == 0x7e) {
+ if((p[1] == 0x50) && (p[2] == 0x00)) {
+ p[1] = 0xfe;
+ p[2] = 0x00;
+ patched_bootrom_p2 = p;
+ }
+ }
+ p++;
+ }
+ _boot_3:
+ }
+
+ int getbank(uint32 addr, uint32 *realaddr);
+ public:
+ FM77AV_MAINMEM(VM* parent_vm, EMU* parent_emu) : FM7_MAINMEM(parent_vm, parent_emu)
+ {
+ int i;
+ i = FM7_MAINMEM_AV_PAGE0;
+ memset(mainmem_page0, 0x00, sizeof(mainmem_page0));
+ read_table[i].dev = write_table[i].dev = NULL;
+ read_table[i].memory = write_table[i].memory = mainmem_page0;
+
+ i = FM7_MAINMEM_AV_JCARD;
+ memset(mainmem_jcard, 0x00, sizeof(mainmem_jcard));
+ read_table[i].dev = write_table[i].dev = NULL;
+ read_table[i].memory = write_table[i].memory = mainmem_jcard;
+
+ i = FM7_MAINMEM_AV_INITROM;
+ memset(mainmem_initrom, 0x00, sizeof(mainmem_initrom));
+ if(read_bios("INITIATE.ROM", mainmem_initrom, 0x2000) == 0x2000) diag_load_initrom = true;
+ read_table[i].dev = write_table[i].dev = NULL;
+ read_table[i].memory = write_table[i].memory = mainmem_initrom;
+
+ }
+
+ ~FM77AV_MAINMEM(void) {
+ }
+
+ void mem_reset();
+ bool get_loadstat_initrom(void){
+ return diag_loadstat_initrom;
+ }
+}
+
+#endif
--- /dev/null
+/*
+ * Common definition of FM-7 [FM7_COMMON]
+ * Author: K.Ohta
+ * Date : 2015.01.01-
+ *
+ */
+
+
+#ifndef _FM7_COMMON_H_
+#define _FM7_COMMON_H_
+
+enum
+{
+ FM7_MAINMEM_OMOTE = 0, // $0000-$7FFF
+ FM7_MAINMEM_URA, // $8000-$FBFF #1
+ FM7_MAINMEM_BASICROM, // $8000-$FBFF #2
+ FM7_MAINMEM_BIOSWORK, // $FC00-$FC7F
+ FM7_MAINMEM_SHAREDRAM, // $FC80-$FCFF
+ FM7_MAINMEM_MMIO, // $FD00-$FDFF
+ FM7_MAINMEM_BOOTROM_BAS, // $FE00-$FFEF #1
+ FM7_MAINMEM_BOOTROM_DOS, // $FE00-$FFEF #2
+ FM7_MAINMEM_BOOTROM_ROM3, // $FE00-$FFEF #3
+ FM7_MAINMEM_BOOTROM_RAM, // $FE00-$FFEF #4
+ FM7_MAINMEM_VECTOR, // $FFF0-$FFFD
+ FM7_MAINMEM_VECTOR_RESET, // $FFFE-$FFFF
+
+ FM7_MAINMEM_77EXTRAM, // 77AVL4, 192KB EXTRAM.
+ FM7_MAINMEM_77_NULLRAM, // 0x00
+ FM7_MAINMEM_77_SHADOWRAM, // 0x200
+
+ FM7_MAINMEM_AV_PAGE0,
+ FM7_MAINMEM_AV_SUBMEM,
+ FM7_MAINMEM_AV_JCARD,
+ FM7_MAINMEM_AV_EXTRAM786K,
+ FM7_MAINMEN_AV_INITROM,
+ FM7_MAINMEM_END
+};
+
+#define FM7_BOOTMODE_BASIC 0
+#define FM7_BOOTMODE_DOS 1
+#define FM7_BOOTMODE_ROM3 2
+#define FM7_BOOTMODE_RAM 4
+
+
+#endif // _FM7_COMMON_H_
if(realaddr == NULL) return -1; // Not effect.
addr = addr & 0xffff;
- if(window != NULL) {
- if(window->isenabled() && ((addr >= 0x7c00) && (addr < 0x8000)) { // Window open
- *realaddr = (addr + window->getwindow() * 256) & 0xffff;
- if(window->is77av()) return FM7_MAINMEM_AV_PAGE0; // 77AV
- return FM7_MAINMEM_TVRAM; // FM77
- }
- }
- if(mmr != NULL) {
- int mmr_page;
- uint32 mmr_offset;
- if(!mmr->isenabled()) goto _fm7_0;
- if(addr < 0xfc00) { // MMR Banked
- mmr_page = mmr->getpage(addr);
- mmr_offset = addr & 0x0fff;
-
- if(mmr->is77av() != true) { // FM77
- if(mmr_page < 0x30) {
- if(extram != NULL) {
- if(extram->isenabled()) { // EXTEND RAM, 192KB.
- *realaddr = mmr_offset + mmr_page * 0x1000;
- return FM7_MAINMEM_77EXTRAM;
- }
- }
- } else if((mmr_page & 0x30) == 0x30) {
- if(mmr_page == 0x3f) { // $3f000 - $3ffff
- if(mmr_offset < 0x0c00) {
- addr = mmr_offset + 0xf000;
- goto _fm7_0;
- }
- if((mmr_offset < 0x0e00)) {
- *realaddr = mmr_offset - 0x0c00;
- if(mainio->get_rommode_fd0f() == true) {
- return FM7_MAINMEN_77_NULLRAM;
- }
- return FM7_MAINMEM_77_SHADOWRAM;
- }
- addr = mmr_offset + 0xf000;
- goto _fm7_0; //
- }
- // $30000 - $3efff
- addr = mmr_offset + (mmr_page & 0x0f) * 0x1000;
- goto _fm7_0;
- }
- *realaddr = mmr_offset;
- return -1; // Illegal
- } else { // FM77AV
- if((mmr_page & 0x30) == 0x30) { // 77AV RAM/ROM Page1
- uint32 a;
- a = (mmr_page & 0x0f) * 0x1000 + mmr_offset;
- if((a < 0xfd80) && (a > 0xfd97)) { // Okay.
- addr = a;
- goto _fm7_0;
- }
- // MMR Area is illegal.
- *realaddr = 0;
- return -1;
- }
- if(mmr_page < 0x10) { // 77AV RAM PAGE0
- *realaddr = mmr_page * 0x1000 + mmr_offset;
- return FM7_MAINMEM_AV_PAGE0;
- }
- if(mmr_page < 0x20) { // 77AV VRAM
- *realaddr = ((mmr_page & 0x0f) * 0x1000) + mmr_offset;
- return FM7_MAINMEM_AV_SUBMEM;
- }
- if(mmr_page < 0x30) { // 77AV Jcard
- if(jcard != NULL) {
- if(jcard->isenabled()) {
- *realaddr = ((mmr_page & 0x0f) * 0x1000) + mmr_offset;
- return FM7_MAINMEM_AV_JCARD;
- }
- }
- *realaddr = mmr_offset;
- return -1; // Illegal
- }
- if(av_extram != NULL) {
- if(av_extram->isenabled()) {
- *realaddr = ((mmr_page - 0x40) * 0x1000) + mmr_offset;
- return FM7_MAINMEM_AV_EXTRAM768K;
- }
- }
- // Illegal Page
- *realaddr = offset;
- return -1;
- }
- }
- }
-
-_fm7_0:
- addr = addr & 0x0ffff;
- if(mainio->is_initiaterom()) { // Initiate rom enabled, force overwrite vector.
- if(addr >= 0xfffe) {
- *realaddr = addr - 0xe000;
- return FM7_MAINMEM_AV_INITROM;
- }
- if((addr >= 0x6000) && (addr < 0x8000)){ // Real addr: $6000 - $7fff
- *realaddr = addr - 0x6000;
- return FM7_MAINMEM_AV_INITROM;
- }
- }
if(addr < 0x8000) {
*realaddr = addr - 0;
return FM7_MAINMEM_SHAREDRAM;
}
if(addr < 0xfe00) {
+ mainio->wait();
*realaddr = addr - 0xfd00;
return FM7_MAINMEM_MMIO;
}
if(addr < 0xfff0) {
+ if(addr < 0xffe0) mainio->wait();
*realaddr = addr - 0xfe00;
- if(mainio->get_boot_romram() != true) return FM7_MAINMEM_BOOTROM_RAM;
+ //if(mainio->get_boot_romram() != true) return FM7_MAINMEM_BOOTROM_RAM;
switch(dipsw->get_boot_mode()) {
case FM7_BOOTMODE_BASIC:
return FM7_MAIMEM_BOOTROM_BAS;
return FM7_MAINMEM_VECTOR;
}
if(addr < 0x10000) {
+ mainio->wait();
*realaddr = addr - 0xfffe;
return FM7_MAINMEM_VECTOR_RESET;
}
#ifndef _FM7_MAINMEM_H_
#define _FM7_MAINMEM_H_
-#define MEMORY_ADDR_MAX 0x0fc00
-#define MEMORY_BANK_SIZE 0x8000
-#include "../memory.h"
-enum
-{
- FM7_MAINMEM_OMOTE = 0, // $0000-$7FFF
- FM7_MAINMEM_URA, // $8000-$FBFF #1
- FM7_MAINMEM_BASICROM, // $8000-$FBFF #2
- FM7_MAINMEM_BIOSWORK, // $FC00-$FC7F
- FM7_MAINMEM_SHAREDRAM, // $FC80-$FCFF
- FM7_MAINMEM_MMIO, // $FD00-$FDFF
- FM7_MAINMEM_BOOTROM_BAS, // $FE00-$FFEF #1
- FM7_MAINMEM_BOOTROM_DOS, // $FE00-$FFEF #2
- FM7_MAINMEM_BOOTROM_ROM3, // $FE00-$FFEF #3
- FM7_MAINMEM_BOOTROM_RAM, // $FE00-$FFEF #4
- FM7_MAINMEM_VECTOR, // $FFF0-$FFFD
- FM7_MAINMEM_VECTOR_RESET, // $FFFE-$FFFF
-
- FM7_MAINMEM_TVRAM, // TVRAM. Enabled only 77L4.
- FM7_MAINMEM_77EXTRAM, // 77AVL4, 192KB EXTRAM.
- FM7_MAINMEM_77_NULLRAM, // 0x00
- FM7_MAINMEM_77_SHADOWRAM, // 0x200
-
- FM7_MAINMEM_AV_PAGE0,
- FM7_MAINMEM_AV_SUBMEM,
- FM7_MAINMEM_AV_JCARD,
- FM7_MAINMEM_AV_EXTRAM786K,
- FM7_MAINMEN_AV_INITROM,
- FM7_MAINMEM_END
-};
+#include "fm7_common.h"
-#define FM7_BOOTMODE_BASIC 0
-#define FM7_BOOTMODE_DOS 1
-#define FM7_BOOTMODE_ROM3 2
-#define FM7_BOOTMODE_RAM 4
+#define MEMORY_BANK_SIZE 0x8000
+#define MEMORY_ADDR_MAX (FM7_MAINMEM_END * MEMORY_BANK_SIZE)
+#include "../memory.h"
class DEVICE;
class MEMORY;
class FM7_SHAREDRAM;
class FM7_MAIN_IO;
class FM7_DIPSW;
-class FM7_MAIN_MMR;
-class FM7_MAIN_WINDOW;
+
class FM7_MAINMEM : public MEMORY
{
- private:
+ protected:
uint8 fm7_mainmem_omote[0x8000];
uint8 fm7_mainmem_ura[0x7c00];
uint8 fm7_mainmem_basicrom[0x7c00];
uint8 fm7_mainmem_bootrom_vector[0x0e]; // Without
uint8 fm7_mainmem_resetvector[2] = {0xfe, 0x00}; // Reset vector. Addr = 0xfe00.
- FM7_SHAREDRAM *sharedram;
- FM7_MAIN_IO *mainio;
- FM7_DIPSW *dipsw;
- FM7_MAIN_MMR *mmr = NULL;
- FM7_MAIN_WINDOW *window = NULL;
bool diag_load_basicrom = false;
bool diag_load_bootrom_bas = false;
bool diag_load_bootrom_dos = false;
- bool have_
- int getbank(uint32 addr, uint32 *realaddr);
+
+ virtual int getbank(uint32 addr, uint32 *realaddr);
public:
FM7_MAINMEM(VM* parent_vm, EMU* parent_emu) : MEMORY(parent_vm, parent_emu)
{
- int bank_num = FM7_MAINMEM_END;
int i;
- read_table = (bank_t *)malloc(sizeof(bank_t) * bank_num);
- write_table = (bank_t *)malloc(sizeof(bank_t) * bank_num);
-
// Initialize table
// $0000-$7FFF
read_table = NULL;
}
- uint32 read_data8(uint32 addr);
- void write_data8(uint32 addr, uint32 data);
- uint32 read_data16(uint32 addr);
- void write_data16(uint32 addr, uint32 data);
- uint32 read_data32(uint32 addr);
- void write_data32(uint32 addr, uint32 data);
- bool get_loadstat_basicrom(void);
- bool get_loadstat_bootrom_bas(void);
- bool get_loadstat_bootrom_dos(void);
+ virtual uint32 read_data8(uint32 addr);
+ virtual void write_data8(uint32 addr, uint32 data);
+ virtual uint32 read_data16(uint32 addr);
+ virtual void write_data16(uint32 addr, uint32 data);
+ virtual uint32 read_data32(uint32 addr);
+ virtual void write_data32(uint32 addr, uint32 data);
+ bool get_loadstat_basicrom(void){
+ return diag_load_basicrom;
+ }
+
+ bool get_loadstat_bootrom_bas(void){
+ return diag_load_bootrom_bas;
+ }
+ bool get_loadstat_bootrom_dos(void){
+ return diag_load_bootrom_dos;
+ }
}