/*
NEC PC-9801 Emulator 'ePC-9801'
NEC PC-9801E/F/M Emulator 'ePC-9801E'
+ NEC PC-9801U Emulator 'ePC-9801U'
+ NEC PC-9801VF Emulator 'ePC-9801VF'
+ NEC PC-9801VM Emulator 'ePC-9801VM'
+ NEC PC-9801VX Emulator 'ePC-9801VX'
+ NEC PC-9801RA Emulator 'ePC-9801RA'
+ NEC PC-98XA Emulator 'ePC-98XA'
+ NEC PC-98XL Emulator 'ePC-98XL'
+ NEC PC-98RL Emulator 'ePC-98RL'
NEC PC-98DO Emulator 'ePC-98DO'
Author : Takeda.Toshiya
#include "../beep.h"
#endif
#include "../disk.h"
+#if defined(USE_HARD_DISK)
+#include "../harddisk.h"
+#endif
#include "../i8237.h"
#include "../i8251.h"
#include "../i8253.h"
#include "../i8255.h"
#include "../i8259.h"
-#if defined(HAS_I86) || defined(HAS_V30)
-#include "../i86.h"
+#if defined(HAS_I386) || defined(HAS_I486)
+#include "../i386.h"
+#elif defined(HAS_I86) || defined(HAS_V30)
+#include "../i286.h"
#else
#include "../i286.h"
#endif
#endif
//#include "../pcpr201.h"
#include "../prnfile.h"
+#if defined(SUPPORT_SASI_IF) || defined(SUPPORT_SCSI_IF)
+#include "../scsi_hdd.h"
+#include "../scsi_host.h"
+#endif
#include "../tms3631.h"
#include "../upd1990a.h"
#include "../upd7220.h"
#include "../debugger.h"
#endif
+#if defined(SUPPORT_24BIT_ADDRESS) || defined(SUPPORT_32BIT_ADDRESS)
+#include "cpureg.h"
+#endif
#include "display.h"
+#include "dmareg.h"
#include "floppy.h"
#include "fmsound.h"
#include "joystick.h"
#include "keyboard.h"
+#include "membus.h"
#include "mouse.h"
+#if defined(SUPPORT_SASI_IF)
+#include "sasi.h"
+#include "sasi_bios.h"
+#endif
+#if defined(SUPPORT_SCSI_IF)
+#include "scsi.h"
+#endif
+#if defined(SUPPORT_IDE_IF)
+#include "ide.h"
+#endif
+
+#if defined(SUPPORT_CMT_IF)
+using PC9801::CMT;
+#endif
+#if defined(SUPPORT_24BIT_ADDRESS) || defined(SUPPORT_32BIT_ADDRESS)
+using PC9801::CPUREG;
+#endif
+using PC9801::DISPLAY;
+using PC9801::DMAREG;
+using PC9801::FLOPPY;
+using PC9801::FMSOUND;
+using PC9801::JOYSTICK;
+using PC9801::KEYBOARD;
+using PC9801::MEMBUS;
+using PC9801::MOUSE;
+#if defined(SUPPORT_SASI_IF)
+using PC9801::SASI;
+using PC9801::BIOS;
+#endif
+#if defined(SUPPORT_SCSI_IF)
+using PC9801::SCSI;
+#endif
+#if defined(SUPPORT_IDE_IF)
+using PC9801::IDE;
+#endif
#if defined(SUPPORT_320KB_FDD_IF)
#include "../pc80s31k.h"
#include "../pc8801/pc88.h"
#endif
+#if defined(_PC98DO) || defined(_PC98DOPLUS)
+using PC88DEV::PC88;
+#endif
// ----------------------------------------------------------------------------
// initialize
// ----------------------------------------------------------------------------
-VM::VM(EMU* parent_emu) : emu(parent_emu)
+VM::VM(EMU* parent_emu) : VM_TEMPLATE(parent_emu)
{
// check configs
#if defined(_PC98DO) || defined(_PC98DOPLUS)
cpu_clocks = 4992030;
pit_clock_8mhz = false;
}
-#elif defined(_PC9801VM) || defined(_PC98DO)
+#elif defined(_PC9801VM) || defined(_PC98DO) || defined(_PC98DOPLUS) || defined(_PC9801VX) || defined(_PC98XL)
if(config.cpu_type != 0) {
- // 10MHz -> 8MHz
+ // 10MHz/16MHz -> 8MHz
cpu_clocks = 7987248;
pit_clock_8mhz = true;
}
+#elif defined(_PC9801RA) || defined(_PC98RL)
+ if(config.cpu_type != 0) {
+ // 20MHz -> 16MHz
+ cpu_clocks = 15974496;
+ pit_clock_8mhz = true;
+ }
#endif
int pit_clocks = pit_clock_8mhz ? 1996812 : 2457600;
pio_prn = new I8255(this, emu); // for printer
pio_prn->set_device_name(_T("8255 PIO (Printer)"));
pic = new I8259(this, emu);
-#if defined(HAS_I86) || defined(HAS_V30)
- cpu = new I86(this, emu);
+#if defined(HAS_I386) || defined(HAS_I486)
+ cpu = new I386(this, emu); // 80386, 80486
+#elif defined(HAS_I86) || defined(HAS_V30)
+ cpu = new I286(this, emu);// 8086, V30, 80286
#else
cpu = new I286(this, emu);
#endif
cpu->set_device_name(_T("CPU(i286)"));
#endif
io = new IO(this, emu);
- dmareg1 = new LS244(this, emu);
- dmareg1->set_device_name(_T("74LS244 (DMA #1)"));
- dmareg2 = new LS244(this, emu);
- dmareg2->set_device_name(_T("74LS244 (DMA #2)"));
- dmareg3 = new LS244(this, emu);
- dmareg3->set_device_name(_T("74LS244 (DMA #3)"));
- dmareg0 = new LS244(this, emu);
- dmareg0->set_device_name(_T("74LS244 (DMA #0)"));
rtcreg = new LS244(this, emu);
rtcreg->set_device_name(_T("74LS244 (RTC)"));
- memory = new MEMORY(this, emu);
+ //memory = new MEMORY(this, emu);
+ memory = new MEMBUS(this, emu);
not_busy = new NOT(this, emu);
not_busy->set_device_name(_T("NOT Gate (Printer Busy)"));
#if defined(HAS_I86) || defined(HAS_V30)
noise_seek = new NOISE(this, emu);
noise_head_down = new NOISE(this, emu);
noise_head_up = new NOISE(this, emu);
+#if defined(SUPPORT_SASI_IF)
+ sasi_host = new SCSI_HOST(this, emu);
+ sasi_hdd = new SASI_HDD(this, emu);
+ sasi_hdd->set_device_name(_T("SASI Hard Disk Drive"));
+ sasi_hdd->scsi_id = 0;
+ sasi_hdd->bytes_per_sec = 625 * 1024; // 625KB/s
+ for(int i = 0; i < USE_HARD_DISK; i++) {
+ sasi_hdd->set_disk_handler(i, new HARDDISK(emu));
+ }
+ sasi_hdd->set_context_interface(sasi_host);
+ sasi_host->set_context_target(sasi_hdd);
+#endif
+#if defined(SUPPORT_SCSI_IF)
+ scsi_host = new SCSI_HOST(this, emu);
+ for(int i = 0; i < USE_HARD_DISK; i++) {
+ scsi_hdd[i] = new SCSI_HDD(this, emu);
+ scsi_hdd[i]->set_device_name(_T("SCSI Hard Disk Drive #%d"), i + 1);
+ scsi_hdd[i]->scsi_id = i;
+ scsi_hdd[i]->set_disk_handler(0, new HARDDISK(emu));
+ scsi_hdd[i]->set_context_interface(scsi_host);
+ scsi_host->set_context_target(scsi_hdd[i]);
+ }
+#endif
gdc_chr = new UPD7220(this, emu);
gdc_chr->set_device_name(_T("uPD7220 GDC (Character)"));
gdc_gfx = new UPD7220(this, emu);
if(sound_type == 0 || sound_type == 1) {
opn = new YM2203(this, emu);
#ifdef SUPPORT_PC98_OPNA
+ opn->set_device_name(_T("YM2608 OPNA (PC-9801-86)"));
opn->is_ym2608 = true;
+#else
+ opn->set_device_name(_T("YM2203 OPN (PC-9801-26)"));
+ opn->is_ym2608 = false;
#endif
fmsound = new FMSOUND(this, emu);
joystick = new JOYSTICK(this, emu);
#if defined(SUPPORT_CMT_IF)
cmt = new CMT(this, emu);
#endif
+#if defined(SUPPORT_24BIT_ADDRESS) || defined(SUPPORT_32BIT_ADDRESS)
+ cpureg = new CPUREG(this, emu);
+#endif
display = new DISPLAY(this, emu);
+ dmareg = new DMAREG(this, emu);
floppy = new FLOPPY(this, emu);
keyboard = new KEYBOARD(this, emu);
mouse = new MOUSE(this, emu);
+#if defined(SUPPORT_SASI_IF)
+ sasi = new SASI(this, emu);
+ sasi_bios = new BIOS(this, emu);
+#endif
+#if defined(SUPPORT_SCSI_IF)
+ scsi = new SCSI(this, emu);
+#endif
+#if defined(SUPPORT_IDE_IF)
+ ide = new IDE(this, emu);
+#endif
#if defined(SUPPORT_320KB_FDD_IF)
// 320kb fdd drives
6 (INT2)
7 SLAVE PIC
8 PRINTER
- 9 (INT3)
+ 9 (INT3) PC-9801-27 (SASI), PC-9801-55 (SCSI), or IDE
10 (INT41) FDC (640KB I/F)
11 (INT42) FDC (1MB I/F)
12 (INT5) PC-9801-26(K) or PC-9801-14
// dma ch.1: memory refresh
#if defined(SUPPORT_2HD_FDD_IF)
dma->set_context_ch2(fdc_2hd);
+ dma->set_context_tc2(fdc_2hd, SIG_UPD765A_TC, 1);
#endif
#if defined(SUPPORT_2DD_FDD_IF)
dma->set_context_ch3(fdc_2dd);
+ dma->set_context_tc3(fdc_2dd, SIG_UPD765A_TC, 1);
#endif
#if defined(SUPPORT_2HD_2DD_FDD_IF)
+#if !defined(SUPPORT_HIRESO)
dma->set_context_ch2(fdc);
dma->set_context_ch3(fdc);
+ dma->set_context_tc2(fdc, SIG_UPD765A_TC, 1);
+ dma->set_context_tc3(fdc, SIG_UPD765A_TC, 1);
+#else
+ dma->set_context_ch1(fdc);
+ dma->set_context_tc1(fdc, SIG_UPD765A_TC, 1);
+#endif
#endif
// sio_rs->set_context_rxrdy(pic, SIG_I8259_CHIP0 | SIG_I8259_IR4, 1);
sio_kbd->set_context_rxrdy(pic, SIG_I8259_CHIP0 | SIG_I8259_IR1, 1);
pit->set_constant_clock(1, pit_clocks);
pit->set_constant_clock(2, pit_clocks);
pio_mouse->set_context_port_c(mouse, SIG_MOUSE_PORT_C, 0xf0, 0);
+#if defined(SUPPORT_HIRESO)
+ // sysport port.c bit7,5: sysport port.b bit4,3
+ pio_sys->set_context_port_c(pio_sys, SIG_I8255_PORT_B, 0x80, -3); // SHUT0
+ pio_sys->set_context_port_c(pio_sys, SIG_I8255_PORT_B, 0x20, -2); // SHUT1
+#endif
// sysport port.c bit6: printer strobe
#if defined(SUPPORT_OLD_BUZZER)
- pio_sys->set_context_port_c(beep, SIG_BEEP_MUTE, 8, 0);
+ pio_sys->set_context_port_c(beep, SIG_BEEP_MUTE, 0x08, 0);
#else
- pio_sys->set_context_port_c(beep, SIG_PCM1BIT_MUTE, 8, 0);
+ pio_sys->set_context_port_c(beep, SIG_PCM1BIT_MUTE, 0x08, 0);
#endif
// sysport port.c bit2: enable txrdy interrupt
// sysport port.c bit1: enable txempty interrupt
pio_prn->set_context_port_c(not_prn, SIG_NOT_INPUT, 8, 0);
not_prn->set_context_out(pic, SIG_I8259_CHIP1 | SIG_I8259_IR0, 1);
#endif
- dmareg1->set_context_output(dma, SIG_I8237_BANK1, 0x0f, 0);
- dmareg2->set_context_output(dma, SIG_I8237_BANK2, 0x0f, 0);
- dmareg3->set_context_output(dma, SIG_I8237_BANK3, 0x0f, 0);
- dmareg0->set_context_output(dma, SIG_I8237_BANK0, 0x0f, 0);
rtcreg->set_context_output(rtc, SIG_UPD1990A_CMD, 0x07, 0);
rtcreg->set_context_output(rtc, SIG_UPD1990A_DIN, 0x20, 0);
rtcreg->set_context_output(rtc, SIG_UPD1990A_STB, 0x08, 0);
pit_14->set_context_ch2(pic, SIG_I8259_CHIP1 | SIG_I8259_IR4, 1);
}
+#if defined(SUPPORT_24BIT_ADDRESS) || defined(SUPPORT_32BIT_ADDRESS)
+ cpureg->set_context_cpu(cpu);
+#endif
display->set_context_pic(pic);
display->set_context_gdc_chr(gdc_chr, gdc_chr->get_ra());
display->set_context_gdc_gfx(gdc_gfx, gdc_gfx->get_ra(), gdc_gfx->get_cs());
+ dmareg->set_context_dma(dma);
keyboard->set_context_sio(sio_kbd);
+ memory->set_context_display(display);
mouse->set_context_pic(pic);
mouse->set_context_pio(pio_mouse);
floppy->set_context_dma(dma);
floppy->set_context_pic(pic);
+#if defined(SUPPORT_SASI_IF)
+#if !defined(SUPPORT_HIRESO)
+ sasi_host->set_context_irq(pio_sys, SIG_I8255_PORT_B, 0x10);
+#endif
+ sasi_host->set_context_irq(sasi, SIG_SASI_IRQ, 1);
+ sasi_host->set_context_drq(sasi, SIG_SASI_DRQ, 1);
+#ifdef _PC98XA
+ dma->set_context_ch3(sasi_host);
+ dma->set_context_tc3(sasi, SIG_SASI_TC, 1);
+#else
+ dma->set_context_ch0(sasi_host);
+ dma->set_context_tc0(sasi, SIG_SASI_TC, 1);
+#endif
+ sasi->set_context_host(sasi_host);
+ sasi->set_context_hdd(sasi_hdd);
+ sasi->set_context_dma(dma);
+ sasi->set_context_pic(pic);
+
+ sasi_bios->set_context_sasi(sasi);
+ sasi_bios->set_context_memory(memory);
+ sasi_bios->set_context_cpu(cpu);
+ sasi_bios->set_context_pic(pic);
+ cpu->set_context_bios(sasi_bios);
+
+#endif
+#if defined(SUPPORT_SCSI_IF)
+ dma->set_context_ch0(scsi);
+ scsi->set_context_dma(dma);
+ scsi->set_context_pic(pic);
+#endif
+#if defined(SUPPORT_IDE_IF)
+ dma->set_context_ch0(ide);
+ ide->set_context_dma(dma);
+ ide->set_context_pic(pic);
+#endif
+
#if defined(SUPPORT_CMT_IF)
sio_cmt->set_context_out(cmt, SIG_CMT_OUT);
// sio_cmt->set_context_txrdy(cmt, SIG_CMT_TXRDY, 1);
#endif
#endif
- // memory bus
- memset(ram, 0, sizeof(ram));
- memset(ipl, 0xff, sizeof(ipl));
- memset(sound_bios, 0xff, sizeof(sound_bios));
-#if defined(_PC9801) || defined(_PC9801E)
- memset(fd_bios_2hd, 0xff, sizeof(fd_bios_2hd));
- memset(fd_bios_2dd, 0xff, sizeof(fd_bios_2dd));
-#endif
+ // i/o bus
+ io->set_iomap_alias_rw(0x0000, pic, 0);
+ io->set_iomap_alias_rw(0x0002, pic, 1);
+ io->set_iomap_alias_rw(0x0008, pic, 2);
+ io->set_iomap_alias_rw(0x000a, pic, 3);
- memory->read_bios(_T("IPL.ROM"), ipl, sizeof(ipl));
- if(sound_type == 0) {
- display->sound_bios_ok = (memory->read_bios(_T("SOUND.ROM"), sound_bios, sizeof(sound_bios)) != 0);
- } else if(sound_type == 2) {
- display->sound_bios_ok = (memory->read_bios(_T("MUSIC.ROM"), sound_bios, sizeof(sound_bios)) != 0);
- } else {
- display->sound_bios_ok = false;
- }
-#if defined(_PC9801) || defined(_PC9801E)
- memory->read_bios(_T("2HDIF.ROM"), fd_bios_2hd, sizeof(fd_bios_2hd));
- memory->read_bios(_T("2DDIF.ROM"), fd_bios_2dd, sizeof(fd_bios_2dd));
-#endif
-
- memory->set_memory_rw(0x00000, 0x9ffff, ram);
- // A0000h - A1FFFh: TEXT VRAM
- // A2000h - A3FFFh: ATTRIBUTE
- memory->set_memory_mapped_io_rw(0xa0000, 0xa3fff, display);
- // A8000h - BFFFFh: VRAM
- memory->set_memory_mapped_io_rw(0xa8000, 0xbffff, display);
- if(sound_type == 0 || sound_type == 2) {
- memory->set_memory_r(0xcc000, 0xcffff, sound_bios);
- }
-#if defined(_PC9801) || defined(_PC9801E)
- memory->set_memory_r(0xd6000, 0xd6fff, fd_bios_2dd);
- memory->set_memory_r(0xd7000, 0xd7fff, fd_bios_2hd);
-#endif
-#if defined(SUPPORT_16_COLORS)
- // E0000h - E7FFFh: VRAM
- memory->set_memory_mapped_io_rw(0xe0000, 0xe7fff, display);
+ io->set_iomap_alias_rw(0x0001, dma, 0x00);
+ io->set_iomap_alias_rw(0x0003, dma, 0x01);
+ io->set_iomap_alias_rw(0x0005, dma, 0x02);
+ io->set_iomap_alias_rw(0x0007, dma, 0x03);
+ io->set_iomap_alias_rw(0x0009, dma, 0x04);
+ io->set_iomap_alias_rw(0x000b, dma, 0x05);
+ io->set_iomap_alias_rw(0x000d, dma, 0x06);
+ io->set_iomap_alias_rw(0x000f, dma, 0x07);
+ io->set_iomap_alias_rw(0x0011, dma, 0x08);
+ io->set_iomap_alias_w (0x0013, dma, 0x09);
+ io->set_iomap_alias_w (0x0015, dma, 0x0a);
+ io->set_iomap_alias_w (0x0017, dma, 0x0b);
+ io->set_iomap_alias_w (0x0019, dma, 0x0c);
+ io->set_iomap_alias_rw(0x001b, dma, 0x0d);
+ io->set_iomap_alias_w (0x001d, dma, 0x0e);
+ io->set_iomap_alias_w (0x001f, dma, 0x0f);
+ io->set_iomap_single_w(0x0021, dmareg);
+ io->set_iomap_single_w(0x0023, dmareg);
+ io->set_iomap_single_w(0x0025, dmareg);
+ io->set_iomap_single_w(0x0027, dmareg);
+#if defined(SUPPORT_24BIT_ADDRESS) || defined(SUPPORT_32BIT_ADDRESS)
+ io->set_iomap_single_w(0x0029, dmareg);
+#endif
+#if defined(SUPPORT_32BIT_ADDRESS)
+ io->set_iomap_single_w(0x0e05, dmareg);
+ io->set_iomap_single_w(0x0e07, dmareg);
+ io->set_iomap_single_w(0x0e09, dmareg);
+ io->set_iomap_single_w(0x0e0b, dmareg);
#endif
- memory->set_memory_r(0xe8000, 0xfffff, ipl);
- // i/o bus
- io->set_iomap_alias_rw(0x00, pic, 0);
- io->set_iomap_alias_rw(0x02, pic, 1);
- io->set_iomap_alias_rw(0x08, pic, 2);
- io->set_iomap_alias_rw(0x0a, pic, 3);
-
- io->set_iomap_alias_rw(0x01, dma, 0x00);
- io->set_iomap_alias_rw(0x03, dma, 0x01);
- io->set_iomap_alias_rw(0x05, dma, 0x02);
- io->set_iomap_alias_rw(0x07, dma, 0x03);
- io->set_iomap_alias_rw(0x09, dma, 0x04);
- io->set_iomap_alias_rw(0x0b, dma, 0x05);
- io->set_iomap_alias_rw(0x0d, dma, 0x06);
- io->set_iomap_alias_rw(0x0f, dma, 0x07);
- io->set_iomap_alias_rw(0x11, dma, 0x08);
- io->set_iomap_alias_w(0x13, dma, 0x09);
- io->set_iomap_alias_w(0x15, dma, 0x0a);
- io->set_iomap_alias_w(0x17, dma, 0x0b);
- io->set_iomap_alias_w(0x19, dma, 0x0c);
- io->set_iomap_alias_rw(0x1b, dma, 0x0d);
- io->set_iomap_alias_w(0x1d, dma, 0x0e);
- io->set_iomap_alias_w(0x1f, dma, 0x0f);
- io->set_iomap_single_w(0x21, dmareg1);
- io->set_iomap_single_w(0x23, dmareg2);
- io->set_iomap_single_w(0x25, dmareg3);
- io->set_iomap_single_w(0x27, dmareg0);
-
- io->set_iomap_single_w(0x20, rtcreg);
-
- io->set_iomap_alias_rw(0x30, sio_rs, 0);
- io->set_iomap_alias_rw(0x32, sio_rs, 1);
-
- io->set_iomap_alias_rw(0x31, pio_sys, 0);
- io->set_iomap_alias_rw(0x33, pio_sys, 1);
- io->set_iomap_alias_rw(0x35, pio_sys, 2);
- io->set_iomap_alias_w(0x37, pio_sys, 3);
-
- io->set_iomap_alias_rw(0x40, pio_prn, 0);
- io->set_iomap_alias_rw(0x42, pio_prn, 1);
- io->set_iomap_alias_rw(0x44, pio_prn, 2);
- io->set_iomap_alias_w(0x46, pio_prn, 3);
-
- io->set_iomap_alias_rw(0x41, sio_kbd, 0);
- io->set_iomap_alias_rw(0x43, sio_kbd, 1);
-
- // 50h, 52h: NMI Flip Flop
+ io->set_iomap_single_w(0x0020, rtcreg);
+
+ io->set_iomap_alias_rw(0x0030, sio_rs, 0);
+ io->set_iomap_alias_rw(0x0032, sio_rs, 1);
+
+ io->set_iomap_alias_rw(0x0031, pio_sys, 0);
+ io->set_iomap_alias_rw(0x0033, pio_sys, 1);
+ io->set_iomap_alias_rw(0x0035, pio_sys, 2);
+ io->set_iomap_alias_w (0x0037, pio_sys, 3);
+
+ io->set_iomap_alias_rw(0x0040, pio_prn, 0);
+ io->set_iomap_alias_rw(0x0042, pio_prn, 1);
+ io->set_iomap_alias_rw(0x0044, pio_prn, 2);
+ io->set_iomap_alias_w (0x0046, pio_prn, 3);
+
+ io->set_iomap_alias_rw(0x0041, sio_kbd, 0);
+ io->set_iomap_alias_rw(0x0043, sio_kbd, 1);
+
+#if defined(SUPPORT_24BIT_ADDRESS) || defined(SUPPORT_32BIT_ADDRESS)
+ io->set_iomap_single_w(0x0050, cpureg);
+ io->set_iomap_single_w(0x0052, cpureg);
+#endif
#if defined(SUPPORT_320KB_FDD_IF)
- io->set_iomap_alias_rw(0x51, pio_fdd, 0);
- io->set_iomap_alias_rw(0x53, pio_fdd, 1);
- io->set_iomap_alias_rw(0x55, pio_fdd, 2);
- io->set_iomap_alias_w(0x57, pio_fdd, 3);
+ io->set_iomap_alias_rw(0x0051, pio_fdd, 0);
+ io->set_iomap_alias_rw(0x0053, pio_fdd, 1);
+ io->set_iomap_alias_rw(0x0055, pio_fdd, 2);
+ io->set_iomap_alias_w (0x0057, pio_fdd, 3);
#endif
- io->set_iomap_alias_rw(0x60, gdc_chr, 0);
- io->set_iomap_alias_rw(0x62, gdc_chr, 1);
+ io->set_iomap_alias_rw(0x0060, gdc_chr, 0);
+ io->set_iomap_alias_rw(0x0062, gdc_chr, 1);
io->set_iomap_single_w(0x64, display);
io->set_iomap_single_w(0x68, display);
io->set_iomap_single_w(0x76, display);
io->set_iomap_single_w(0x78, display);
io->set_iomap_single_w(0x7a, display);
-#if defined(SUPPORT_16_COLORS)
- io->set_iomap_single_w(0x7c, display);
- io->set_iomap_single_w(0x7e, display);
+#if defined(SUPPORT_GRCG)
+#if !defined(SUPPORT_HIRESO)
+ io->set_iomap_single_w(0x007c, display);
+ io->set_iomap_single_w(0x007e, display);
+#else
+ io->set_iomap_single_w(0x00a4, display);
+ io->set_iomap_single_w(0x00a6, display);
+#endif
#endif
- io->set_iomap_alias_rw(0x71, pit, 0);
- io->set_iomap_alias_rw(0x73, pit, 1);
- io->set_iomap_alias_rw(0x75, pit, 2);
- io->set_iomap_alias_w(0x77, pit, 3);
-
- // 80h, 82h: SASI
-
- io->set_iomap_single_rw(0x90, floppy);
- io->set_iomap_single_rw(0x92, floppy);
- io->set_iomap_single_rw(0x94, floppy);
-
-#if defined(SUPPORT_CMT_IF)
- io->set_iomap_alias_rw(0x91, sio_cmt, 0);
- io->set_iomap_alias_rw(0x93, sio_cmt, 1);
- io->set_iomap_single_w(0x95, cmt);
- io->set_iomap_single_w(0x97, cmt);
+#if defined(SUPPORT_SASI_IF)
+ io->set_iomap_single_rw(0x0080, sasi);
+ io->set_iomap_single_rw(0x0082, sasi);
+#endif
+#if defined(SUPPORT_SCSI_IF)
+ io->set_iomap_single_rw(0x0cc0, scsi);
+ io->set_iomap_single_rw(0x0cc2, scsi);
+ io->set_iomap_single_rw(0x0cc4, scsi);
+#endif
+#if defined(SUPPORT_IDE_IF)
+ io->set_iomap_single_rw(0x0640, ide);
+ io->set_iomap_single_rw(0x0642, ide);
+ io->set_iomap_single_rw(0x0644, ide);
+ io->set_iomap_single_rw(0x0646, ide);
+ io->set_iomap_single_rw(0x0648, ide);
+ io->set_iomap_single_rw(0x064a, ide);
+ io->set_iomap_single_rw(0x064c, ide);
+ io->set_iomap_single_rw(0x064e, ide);
+ io->set_iomap_single_rw(0x074c, ide);
+ io->set_iomap_single_rw(0x074e, ide);
#endif
- io->set_iomap_alias_rw(0xa0, gdc_gfx, 0);
- io->set_iomap_alias_rw(0xa2, gdc_gfx, 1);
+ io->set_iomap_alias_rw(0x00a0, gdc_gfx, 0);
+ io->set_iomap_alias_rw(0x00a2, gdc_gfx, 1);
-#if defined(SUPPORT_2ND_VRAM)
- io->set_iomap_single_w(0xa4, display);
- io->set_iomap_single_w(0xa6, display);
+#if defined(SUPPORT_2ND_VRAM) && !defined(SUPPORT_HIRESO)
+ io->set_iomap_single_rw(0x00a4, display);
+ io->set_iomap_single_rw(0x00a6, display);
#endif
io->set_iomap_single_rw(0xa8, display);
io->set_iomap_single_rw(0xaa, display);
io->set_iomap_single_rw(0xac, display);
io->set_iomap_single_rw(0xae, display);
- io->set_iomap_single_w(0xa1, display);
- io->set_iomap_single_w(0xa3, display);
- io->set_iomap_single_w(0xa5, display);
+// io->set_iomap_single_w(0xa1, display);
+// io->set_iomap_single_w(0xa3, display);
+// io->set_iomap_single_w(0xa5, display);
+ io->set_iomap_single_rw(0xa1, display);
+ io->set_iomap_single_rw(0xa3, display);
+ io->set_iomap_single_rw(0xa5, display);
io->set_iomap_single_rw(0xa9, display);
+#if defined(SUPPORT_EGC)
+ io->set_iomap_range_rw(0x04a0, 0x04af, display);
+#endif
+ io->set_iomap_alias_rw(0x0071, pit, 0);
+ io->set_iomap_alias_rw(0x0073, pit, 1);
+ io->set_iomap_alias_rw(0x0075, pit, 2);
+ io->set_iomap_alias_w (0x0077, pit, 3);
+
+ io->set_iomap_single_rw(0x0090, floppy);
+ io->set_iomap_single_rw(0x0092, floppy);
+ io->set_iomap_single_rw(0x0094, floppy);
+ io->set_iomap_single_rw(0x0096, floppy);
#if defined(SUPPORT_2HD_2DD_FDD_IF)
- io->set_iomap_single_rw(0xbe, floppy);
+#if !defined(SUPPORT_HIRESO)
+ io->set_iomap_single_rw(0x00be, floppy);
+#else
+//#if !defined(_PC98XA) && !defined(_PC98XL)
+ io->set_iomap_single_w (0x00be, floppy);
+//#endif
+#endif
+#endif
+#if !defined(SUPPORT_HIRESO)
+ io->set_iomap_single_rw(0x00c8, floppy);
+ io->set_iomap_single_rw(0x00ca, floppy);
+ io->set_iomap_single_rw(0x00cc, floppy);
+ io->set_iomap_single_rw(0x00ce, floppy);
+#endif
+
+#if defined(SUPPORT_CMT_IF)
+ io->set_iomap_alias_rw(0x0091, sio_cmt, 0);
+ io->set_iomap_alias_rw(0x0093, sio_cmt, 1);
+ io->set_iomap_single_w(0x0095, cmt);
+ io->set_iomap_single_w(0x0097, cmt);
+#endif
+
+#if defined(SUPPORT_24BIT_ADDRESS) || defined(SUPPORT_32BIT_ADDRESS)
+ io->set_iomap_single_rw(0x00f0, cpureg);
+ io->set_iomap_single_rw(0x00f2, cpureg);
+#endif
+#if defined(SUPPORT_32BIT_ADDRESS)
+ io->set_iomap_single_rw(0x00f6, cpureg);
#endif
- io->set_iomap_single_rw(0xc8, floppy);
- io->set_iomap_single_rw(0xca, floppy);
- io->set_iomap_single_rw(0xcc, floppy);
if(sound_type == 0 || sound_type == 1) {
- io->set_iomap_single_rw(0x188, fmsound);
- io->set_iomap_single_rw(0x18a, fmsound);
+ io->set_iomap_single_rw(0x0188, fmsound);
+ io->set_iomap_single_rw(0x018a, fmsound);
#ifdef SUPPORT_PC98_OPNA
- io->set_iomap_single_rw(0x18c, fmsound);
- io->set_iomap_single_rw(0x18e, fmsound);
+ io->set_iomap_single_rw(0x018c, fmsound);
+ io->set_iomap_single_rw(0x018e, fmsound);
io->set_iomap_single_rw(0xa460, fmsound);
#endif
} else if(sound_type == 2 || sound_type == 3) {
- io->set_iomap_alias_rw(0x88, pio_14, 0);
- io->set_iomap_alias_rw(0x8a, pio_14, 1);
- io->set_iomap_alias_rw(0x8c, pio_14, 2);
- io->set_iomap_alias_w(0x8e, pio_14, 3);
- io->set_iovalue_single_r(0x8e, 0x08);
- io->set_iomap_single_w(0x188, maskreg_14);
- io->set_iomap_single_w(0x18a, maskreg_14);
- io->set_iomap_alias_rw(0x18c, pit_14, 2);
- io->set_iomap_alias_w(0x18e, pit_14, 3);
-// io->set_iovalue_single_r(0x18e, 0x00); // INT0
-// io->set_iovalue_single_r(0x18e, 0x40); // INT41
- io->set_iovalue_single_r(0x18e, 0x80); // INT5
-// io->set_iovalue_single_r(0x18e, 0xc0); // INT6
+ io->set_iomap_alias_rw(0x0088, pio_14, 0);
+ io->set_iomap_alias_rw(0x008a, pio_14, 1);
+ io->set_iomap_alias_rw(0x008c, pio_14, 2);
+ io->set_iomap_alias_w(0x008e, pio_14, 3);
+ io->set_iovalue_single_r(0x008e, 0x08);
+ io->set_iomap_single_w(0x0188, maskreg_14);
+ io->set_iomap_single_w(0x018a, maskreg_14);
+ io->set_iomap_alias_rw(0x018c, pit_14, 2);
+ io->set_iomap_alias_w(0x018e, pit_14, 3);
+// io->set_iovalue_single_r(0x018e, 0x00); // INT0
+// io->set_iovalue_single_r(0x018e, 0x40); // INT41
+ io->set_iovalue_single_r(0x018e, 0x80); // INT5
+// io->set_iovalue_single_r(0x018e, 0xc0); // INT6
}
-#if !defined(SUPPORT_OLD_BUZZER)
+//#if !defined(SUPPORT_HIRESO)
+// io->set_iovalue_single_r(0x0431, 0x04); // bit2: 1 = Normal mode, 0 = Hireso mode
+//#else
+// io->set_iovalue_single_r(0x0431, 0x00);
+//#endif
+#if defined(SUPPORT_ITF_ROM)
+ io->set_iomap_single_w(0x043d, memory);
+#endif
+#if !defined(SUPPORT_HIRESO)
+ io->set_iomap_single_w(0x043f, memory);
+#endif
+#if defined(SUPPORT_24BIT_ADDRESS) || defined(SUPPORT_32BIT_ADDRESS)
+#if !defined(_PC98XA)
+ io->set_iomap_single_rw(0x0439, memory);
+#endif
+#if !defined(SUPPORT_HIRESO)
+ io->set_iomap_single_rw(0x0461, memory);
+ io->set_iomap_single_rw(0x0463, memory);
+#else
+ io->set_iomap_single_rw(0x0091, memory);
+ io->set_iomap_single_rw(0x0093, memory);
+#endif
+ io->set_iomap_single_r(0x0567, memory);
+#endif
+#if defined(SUPPORT_32BIT_ADDRESS)
+ io->set_iomap_single_w(0x053d, memory);
+#endif
+
+#if !(defined(_PC9801) || defined(_PC9801E) || defined(SUPPORT_HIRESO))
io->set_iomap_alias_rw(0x3fd9, pit, 0);
io->set_iomap_alias_rw(0x3fdb, pit, 1);
io->set_iomap_alias_rw(0x3fdd, pit, 2);
- io->set_iomap_alias_w(0x3fdf, pit, 3);
+ io->set_iomap_alias_w (0x3fdf, pit, 3);
#endif
+#if !defined(SUPPORT_HIRESO)
io->set_iomap_alias_rw(0x7fd9, pio_mouse, 0);
io->set_iomap_alias_rw(0x7fdb, pio_mouse, 1);
io->set_iomap_alias_rw(0x7fdd, pio_mouse, 2);
- io->set_iomap_alias_w(0x7fdf, pio_mouse, 3);
-#if !(defined(_PC9801) || defined(_PC9801E))
- io->set_iomap_single_w(0xbfdb, mouse);
+ io->set_iomap_alias_w (0x7fdf, pio_mouse, 3);
+ io->set_iomap_single_rw(0xbfdb, mouse);
+#else
+ io->set_iomap_alias_rw(0x0061, pio_mouse, 0);
+ io->set_iomap_alias_rw(0x0063, pio_mouse, 1);
+ io->set_iomap_alias_rw(0x0065, pio_mouse, 2);
+ io->set_iomap_alias_rw(0x0067, pio_mouse, 3);
#endif
#if defined(_PC98DO) || defined(_PC98DOPLUS)
pc88rtc = new UPD1990A(this, emu);
pc88rtc->set_device_name(_T("uPD1990A RTC (PC-8801)"));
pc88rtc->set_context_event_manager(pc88event);
- pc88opn = new YM2203(this, emu);
+ pc88opn1 = new YM2203(this, emu);
#ifdef SUPPORT_PC88_OPNA
- pc88opn->set_device_name(_T("YM2608 OPNA (PC-8801)"));
- pc88opn->is_ym2608 = true;
+ pc88opn1->set_device_name(_T("YM2608 OPNA (PC-8801)"));
+ pc88opn1->is_ym2608 = true;
#else
- pc88opn->set_device_name(_T("YM2203 OPN (PC-8801)"));
+ pc88opn1->set_device_name(_T("YM2203 OPN (PC-8801)"));
+ pc88opn1->is_ym2608 = false;
#endif
- pc88opn->set_context_event_manager(pc88event);
+ pc88opn1->set_context_event_manager(pc88event);
pc88cpu = new Z80(this, emu);
pc88cpu->set_device_name(_T("Z80 CPU (PC-8801)"));
pc88cpu->set_context_event_manager(pc88event);
pc88cpu_sub->set_device_name(_T("Z80 CPU (PC-8801 Sub)"));
pc88cpu_sub->set_context_event_manager(pc88event);
- pc88event->set_context_cpu(pc88cpu, (config.cpu_type != 0) ? 3993624 : 7987248);
+ pc88event->set_context_cpu(pc88cpu, (config.cpu_type == 1) ? 3993624 : 7987248);
pc88event->set_context_cpu(pc88cpu_sub, 3993624);
- pc88event->set_context_sound(pc88opn);
+ pc88event->set_context_sound(pc88opn1);
pc88event->set_context_sound(pc88pcm);
pc88event->set_context_sound(pc88noise_seek);
pc88event->set_context_sound(pc88noise_head_down);
pc88event->set_context_sound(pc88noise_head_up);
pc88->set_context_cpu(pc88cpu);
- pc88->set_context_opn(pc88opn);
+ pc88->set_context_opn1(pc88opn1);
pc88->set_context_pcm(pc88pcm);
pc88->set_context_pio(pc88pio);
pc88->set_context_prn(pc88prn);
#ifdef USE_DEBUGGER
pc88cpu->set_context_debugger(new DEBUGGER(this, emu));
#endif
- pc88opn->set_context_irq(pc88, SIG_PC88_SOUND_IRQ, 1);
+ pc88opn1->set_context_irq(pc88, SIG_PC88_OPN1_IRQ, 1);
pc88sio->set_context_rxrdy(pc88, SIG_PC88_USART_IRQ, 1);
pc88sio->set_context_out(pc88, SIG_PC88_USART_OUT);
pc88cpu_sub->set_context_debugger(new DEBUGGER(this, emu));
#endif
#endif
-
+
// initialize all devices
+#if defined(__GIT_REPO_VERSION)
+ strncpy(_git_revision, __GIT_REPO_VERSION, sizeof(_git_revision) - 1);
+#endif
for(DEVICE* device = first_device; device; device = device->next_device) {
device->initialize();
}
+
#if defined(_PC9801) || defined(_PC9801E)
fdc_2hd->get_disk_handler(0)->drive_num = 0;
fdc_2hd->get_disk_handler(1)->drive_num = 1;
fdc->get_disk_handler(0)->drive_num = 0;
fdc->get_disk_handler(1)->drive_num = 1;
#endif
+#if defined(USE_HARD_DISK)
+ for(int drv = 0; drv < USE_HARD_DISK; drv++) {
+ if(!(config.last_hard_disk_path[drv][0] != _T('\0') && FILEIO::IsFileExisting(config.last_hard_disk_path[drv]))) {
+#if defined(SUPPORT_SASI_IF)
+ create_local_path(config.last_hard_disk_path[drv], _MAX_PATH, _T("SASI%d.DAT"), drv);
+#endif
+#if defined(SUPPORT_SCSI_IF)
+ create_local_path(config.last_hard_disk_path[drv], _MAX_PATH, _T("SCSI%d.DAT"), drv);
+#endif
+#if defined(SUPPORT_IDE_IF)
+ create_local_path(config.last_hard_disk_path[drv], _MAX_PATH, _T("IDE%d.DAT"), drv);
+#endif
+ }
+ }
+#endif
}
VM::~VM()
#endif
// initial device settings
- pio_mouse->write_signal(SIG_I8255_PORT_A, 0xf0, 0xff); // clear mouse status
- pio_mouse->write_signal(SIG_I8255_PORT_B, 0x40, 0xff); // cpu high & sw3-6
- uint8_t port_c = 0x08; // normal mode & sw1-5 & sw1-6
+ uint8_t port_a, port_b, port_c;
+
+ port_a = 0xf0; // Clear mouse buttons and counters
+ port_b = 0x00;
+#if defined(_PC98XA)
+ port_b |= (uint8_t)((RAM_SIZE - 0x100000) / 0x40000);
+#else
+#if defined(SUPPORT_HIRESO)
+ port_b |= 0x80; // DIP SW 1-4, 1 = External FDD #3/#4, 0 = #1/#2
+#endif
+ port_b |= 0x40; // DIP SW 3-6, 1 = Enable internal RAM 80000h-9FFFFh
+#if defined(_PC98RL)
+ port_b |= 0x10; // DIP SW 3-3, 1 = DMA ch.0 for SASI-HDD
+#endif
+#if defined(USE_CPU_TYPE)
+ if(config.cpu_type != 0) {
+#if !defined(SUPPORT_HIRESO)
+ port_b |= 0x02; // SPDSW, 1 = 10MHz, 0 = 12MHz
+#else
+ port_b |= 0x01; // SPDSW, 1 = 8/16MHz, 0 = 10/20MHz
+#endif
+ }
+#endif
+#endif
+ port_c = 0x00;
+#if defined(SUPPORT_HIRESO)
+// port_c |= 0x08; // MODSW, 1 = Normal Mode, 0 = Hirezo Mode
+#endif
#if defined(HAS_V30) || defined(HAS_V33)
- port_c |= 0x04; // V30
+ port_c |= 0x04; // DIP SW 3-8, 1 = V30, 0 = 80x86
#endif
- pio_mouse->write_signal(SIG_I8255_PORT_C, 0x40, 0xff);
+ pio_mouse->write_signal(SIG_I8255_PORT_A, port_a, 0xff);
+ pio_mouse->write_signal(SIG_I8255_PORT_B, port_b, 0xff);
+ pio_mouse->write_signal(SIG_I8255_PORT_C, port_c, 0xff);
- pio_sys->write_signal(SIG_I8255_PORT_A, 0xe3, 0xff);
- pio_sys->write_signal(SIG_I8255_PORT_B, 0xf8, 0xff);//0xe8??
+ port_a = 0x00;
+ port_a |= 0x80; // DIP SW 2-8, 1 = GDC 2.5MHz, 0 = GDC 5MHz
+ port_a |= 0x40; // DIP SW 2-7, 1 = Do not control FD motor
+ port_a |= 0x20; // DIP SW 2-6, 1 = Enable internal HD
+// port_a |= 0x10; // DIP SW 2-5, 1 = Initialize emory switch
+// port_a |= 0x08; // DIP SW 2-4, 1 = 20 lines, 0 = 25 lines
+// port_a |= 0x04; // DIP SW 2-3, 1 = 40 columns, 0 = 80 columns
+ port_a |= 0x02; // DIP SW 2-2, 1 = BASIC mode, 0 = Terminal mode
+ port_a |= 0x01; // DIP SW 2-1, 1 = Normal mode, 0 = LT mode
+ port_b = 0x00;
+ port_b |= 0x80; // RS-232C CI#, 1 = OFF
+ port_b |= 0x40; // RS-232C CS#, 1 = OFF
+ port_b |= 0x20; // RS-232C CD#, 1 = OFF
+#if !defined(SUPPORT_HIRESO)
+// port_b |= 0x10; // INT3, 1 = Active, 0 = Inactive
+ port_b |= 0x08; // DIP SW 1-1, 1 = Hiresolution CRT, 0 = Standard CRT
+#else
+ port_b |= 0x10; // SHUT0
+ port_b |= 0x08; // SHUT1
+#endif
+// port_b |= 0x04; // IMCK, 1 = Parity error occurs in internal RAM
+// port_b |= 0x02; // EMCK, 1 = Parity error occurs in external RAM
+// port_b |= 0x01; // CDAT
+ port_c = 0x00;
+ port_c |= 0x80; // SHUT0
+ port_c |= 0x40; // PSTBM, 1 = Mask printer's PSTB#
+ port_c |= 0x20; // SHUT1
+ port_c |= 0x10; // MCHKEN, 1 = Enable parity check for RAM
+ port_c |= 0x08; // BUZ, 1 = Stop buzzer
+ port_c |= 0x04; // TXRE, 1 = Enable IRQ from RS-232C 8251A TXRDY
+ port_c |= 0x02; // TXEE, 1 = Enable IRQ from RS-232C 8251A TXEMPTY
+ port_c |= 0x01; // RXRE, 1 = Enable IRQ from RS-232C 8251A RXRDY
+ pio_sys->write_signal(SIG_I8255_PORT_A, port_a, 0xff);
+ pio_sys->write_signal(SIG_I8255_PORT_B, port_b, 0xff);
+ pio_sys->write_signal(SIG_I8255_PORT_C, port_c, 0xff);
+ port_b = 0x00;
#if defined(_PC9801)
- uint8_t prn_b = 0x00; // system type = first PC-9801
+// port_b |= 0x80; // TYP1, 0 = PC-9801 (first)
+// port_b |= 0x40; // TYP0, 0
#elif defined(_PC9801U)
- uint8_t prn_b = 0xc0; // system type = PC-9801U,PC-98LT,PC-98HA
+ port_b |= 0x80; // TYP1, 1 = PC-9801U
+ port_b |= 0x40; // TYP0, 1
#else
- uint8_t prn_b = 0x80; // system type = others
+ port_b |= 0x80; // TYP1, 1 = Other PC-9801 series
+// port_b |= 0x40; // TYP0, 0
#endif
if(pit_clock_8mhz) {
- prn_b |= 0x20; // system clock is 8MHz
+ port_b |= 0x20; // MOD, 1 = System clock 8MHz, 0 = 5/10MHz
}
- prn_b |= 0x10; // don't use LCD display
+ port_b |= 0x10; // DIP SW 1-3, 1 = Don't use LCD
#if !defined(SUPPORT_16_COLORS)
- prn_b |= 0x08; // standard graphics
+ port_b |= 0x08; // DIP SW 1-8, 1 = Standard graphic mode, 0 = Enhanced graphic mode
#endif
- prn_b |= 0x04; // printer is not busy
+ port_b |= 0x04; // Printer BUSY#, 1 = Inactive, 0 = Active (BUSY)
#if defined(HAS_V30) || defined(HAS_V33)
- prn_b |= 0x02;
+ port_b |= 0x02; // CPUT, 1 = V30/V33, 0 = 80x86
#endif
#if defined(_PC9801VF) || defined(_PC9801U)
- prn_b |= 0x01; // PC-9801VF or PC-9801U
+ port_b |= 0x01; // VF, 1 = PC-9801VF/U
#endif
- pio_prn->write_signal(SIG_I8255_PORT_B, prn_b, 0xff);
+ pio_prn->write_signal(SIG_I8255_PORT_B, port_b, 0xff);
#if defined(SUPPORT_320KB_FDD_IF)
pio_fdd->write_signal(SIG_I8255_PORT_A, 0xff, 0xff);
#endif
#if defined(_PC98DO) || defined(_PC98DOPLUS)
- pc88opn->set_reg(0x29, 3); // for Misty Blue
+ pc88opn1->set_reg(0x29, 3); // for Misty Blue
pc88pio->write_signal(SIG_I8255_PORT_C, 0, 0xff);
pc88pio_sub->write_signal(SIG_I8255_PORT_C, 0, 0xff);
#endif
beep->initialize_sound(rate, 8000);
#endif
if(sound_type == 0 || sound_type == 1) {
-#ifdef HAS_YM2608
- opn->initialize_sound(rate, 7987248, samples, 0, 0);
-#else
- opn->initialize_sound(rate, 3993624, samples, 0, 0);
-#endif
+ if(opn->is_ym2608) {
+ opn->initialize_sound(rate, 7987248, samples, 0, 0);
+ } else {
+ opn->initialize_sound(rate, 3993624, samples, 0, 0);
+ }
} else if(sound_type == 2 || sound_type == 3) {
tms3631->initialize_sound(rate, 8000);
}
pc88event->initialize_sound(rate, samples);
// init sound gen
-#ifdef HAS_YM2608
- pc88opn->initialize_sound(rate, 7987248, samples, 0, 0);
-#else
- pc88opn->initialize_sound(rate, 3993624, samples, 0, 0);
-#endif
+ if(pc88opn1->is_ym2608) {
+ pc88opn1->initialize_sound(rate, 7987248, samples, 0, 0);
+ } else {
+ pc88opn1->initialize_sound(rate, 3993624, samples, 0, 0);
+ }
pc88pcm->initialize_sound(rate, 8000);
#endif
}
beep->set_volume(0, decibel_l, decibel_r);
#if defined(_PC98DO) || defined(_PC98DOPLUS)
} else if(ch-- == 0) {
- pc88opn->set_volume(0, decibel_l, decibel_r);
+ pc88opn1->set_volume(0, decibel_l, decibel_r);
} else if(ch-- == 0) {
- pc88opn->set_volume(1, decibel_l, decibel_r);
+ pc88opn1->set_volume(1, decibel_l, decibel_r);
#if defined(SUPPORT_PC88_OPNA)
} else if(ch-- == 0) {
- pc88opn->set_volume(2, decibel_l, decibel_r);
+ pc88opn1->set_volume(2, decibel_l, decibel_r);
} else if(ch-- == 0) {
- pc88opn->set_volume(3, decibel_l, decibel_r);
+ pc88opn1->set_volume(3, decibel_l, decibel_r);
#endif
} else if(ch-- == 0) {
pc88pcm->set_volume(0, decibel_l, decibel_r);
keyboard->key_up(code);
}
+bool VM::get_caps_locked()
+{
+#if defined(_PC98DO) || defined(_PC98DOPLUS)
+ if(boot_mode != 0) {
+ return pc88->get_caps_locked();
+ } else
+#endif
+ return keyboard->get_caps_locked();
+}
+
+bool VM::get_kana_locked()
+{
+#if defined(_PC98DO) || defined(_PC98DOPLUS)
+ if(boot_mode != 0) {
+ return pc88->get_kana_locked();
+ } else
+#endif
+ return keyboard->get_kana_locked();
+}
+
// ----------------------------------------------------------------------------
// user interface
// ----------------------------------------------------------------------------
void VM::open_floppy_disk(int drv, const _TCHAR* file_path, int bank)
{
-#if defined(_PC9801) || defined(_PC9801E)
- if(drv == 0 || drv == 1) {
- fdc_2hd->open_disk(drv, file_path, bank);
- } else if(drv == 2 || drv == 3) {
- fdc_2dd->open_disk(drv - 2, file_path, bank);
- } else if(drv == 4 || drv == 5) {
- fdc_sub->open_disk(drv - 4, file_path, bank);
- }
-#elif defined(_PC9801VF) || defined(_PC9801U)
- if(drv == 0 || drv == 1) {
- fdc_2dd->open_disk(drv, file_path, bank);
- }
-#elif defined(_PC98DO) || defined(_PC98DOPLUS)
- if(drv == 0 || drv == 1) {
- fdc->open_disk(drv, file_path, bank);
- } else if(drv == 2 || drv == 3) {
- pc88fdc_sub->open_disk(drv - 2, file_path, bank);
- }
-#else
- if(drv == 0 || drv == 1) {
- fdc->open_disk(drv, file_path, bank);
+ UPD765A *controller = get_floppy_disk_controller(drv);
+
+ if(controller != NULL) {
+ controller->open_disk(drv & 1, file_path, bank);
}
-#endif
}
void VM::close_floppy_disk(int drv)
{
-#if defined(_PC9801) || defined(_PC9801E)
- if(drv == 0 || drv == 1) {
- fdc_2hd->close_disk(drv);
- } else if(drv == 2 || drv == 3) {
- fdc_2dd->close_disk(drv - 2);
- } else if(drv == 4 || drv == 5) {
- fdc_sub->close_disk(drv - 4);
- }
-#elif defined(_PC9801VF) || defined(_PC9801U)
- if(drv == 0 || drv == 1) {
- fdc_2dd->close_disk(drv);
- }
-#elif defined(_PC98DO) || defined(_PC98DOPLUS)
- if(drv == 0 || drv == 1) {
- fdc->close_disk(drv);
- } else if(drv == 2 || drv == 3) {
- pc88fdc_sub->close_disk(drv - 2);
- }
-#else
- if(drv == 0 || drv == 1) {
- fdc->close_disk(drv);
+ UPD765A *controller = get_floppy_disk_controller(drv);
+
+ if(controller != NULL) {
+ controller->close_disk(drv & 1);
}
-#endif
}
bool VM::is_floppy_disk_inserted(int drv)
{
-#if defined(_PC9801) || defined(_PC9801E)
- if(drv == 0 || drv == 1) {
- return fdc_2hd->is_disk_inserted(drv);
- } else if(drv == 2 || drv == 3) {
- return fdc_2dd->is_disk_inserted(drv - 2);
- } else if(drv == 4 || drv == 5) {
- return fdc_sub->is_disk_inserted(drv - 4);
+ DISK *handler = get_floppy_disk_handler(drv);
+
+ if(handler != NULL) {
+ return handler->inserted;
}
-#elif defined(_PC9801VF) || defined(_PC9801U)
- if(drv == 0 || drv == 1) {
- return fdc_2dd->is_disk_inserted(drv);
+ return false;
+}
+
+void VM::is_floppy_disk_protected(int drv, bool value)
+{
+ DISK *handler = get_floppy_disk_handler(drv);
+
+ if(handler != NULL) {
+ handler->write_protected = value;
}
-#elif defined(_PC98DO) || defined(_PC98DOPLUS)
- if(drv == 0 || drv == 1) {
- return fdc->is_disk_inserted(drv);
- } else if(drv == 2 || drv == 3) {
- return pc88fdc_sub->is_disk_inserted(drv - 2);
+}
+
+bool VM::is_floppy_disk_protected(int drv)
+{
+ DISK *handler = get_floppy_disk_handler(drv);
+
+ if(handler != NULL) {
+ return handler->write_protected;
+ }
+ return false;
+}
+
+uint32_t VM::is_floppy_disk_accessed()
+{
+ uint32_t status = 0;
+
+#if defined(_PC98DO) || defined(_PC98DOPLUS)
+ if(boot_mode != 0) {
+ status = pc88fdc_sub->read_signal(0) & 3;
+ } else {
+ status = fdc->read_signal(0) & 3;
}
#else
- if(drv == 0 || drv == 1) {
- return fdc->is_disk_inserted(drv);
+ for(int drv = 0; drv < USE_FLOPPY_DISK; drv += 2) {
+ UPD765A *controller = get_floppy_disk_controller(drv);
+
+ if(controller != NULL) {
+ status |= (controller->read_signal(0) & 3) << drv;
+ }
}
#endif
- return false;
+ return status;
}
-void VM::is_floppy_disk_protected(int drv, bool value)
+UPD765A *VM::get_floppy_disk_controller(int drv)
{
#if defined(_PC9801) || defined(_PC9801E)
if(drv == 0 || drv == 1) {
- fdc_2hd->is_disk_protected(drv, value);
+ return fdc_2hd;
} else if(drv == 2 || drv == 3) {
- fdc_2dd->is_disk_protected(drv - 2, value);
+ return fdc_2dd;
} else if(drv == 4 || drv == 5) {
- fdc_sub->is_disk_protected(drv - 4, value);
+ return fdc_sub;
}
#elif defined(_PC9801VF) || defined(_PC9801U)
if(drv == 0 || drv == 1) {
- fdc_2dd->is_disk_protected(drv, value);
+ return fdc_2dd;
}
#elif defined(_PC98DO) || defined(_PC98DOPLUS)
if(drv == 0 || drv == 1) {
- fdc->is_disk_protected(drv, value);
+ return fdc;
} else if(drv == 2 || drv == 3) {
- pc88fdc_sub->is_disk_protected(drv - 2, value);
+ return pc88fdc_sub;
}
#else
if(drv == 0 || drv == 1) {
- fdc->is_disk_protected(drv, value);
+ return fdc;
}
#endif
+ return NULL;
}
-bool VM::is_floppy_disk_protected(int drv)
+DISK *VM::get_floppy_disk_handler(int drv)
{
-#if defined(_PC9801) || defined(_PC9801E)
- if(drv == 0 || drv == 1) {
- return fdc_2hd->is_disk_protected(drv);
- } else if(drv == 2 || drv == 3) {
- return fdc_2dd->is_disk_protected(drv - 2);
- } else if(drv == 4 || drv == 5) {
- return fdc_sub->is_disk_protected(drv - 4);
- }
-#elif defined(_PC9801VF) || defined(_PC9801U)
- if(drv == 0 || drv == 1) {
- return fdc_2dd->is_disk_protected(drv);
+ UPD765A *controller = get_floppy_disk_controller(drv);
+
+ if(controller != NULL) {
+ return controller->get_disk_handler(drv & 1);
}
-#elif defined(_PC98DO) || defined(_PC98DOPLUS)
- if(drv == 0 || drv == 1) {
- return fdc->is_disk_protected(drv);
- } else if(drv == 2 || drv == 3) {
- return pc88fdc_sub->is_disk_protected(drv - 2);
+ return NULL;
+}
+
+#if defined(USE_HARD_DISK)
+void VM::open_hard_disk(int drv, const _TCHAR* file_path)
+{
+ if(drv < USE_HARD_DISK) {
+#if defined(SUPPORT_SASI_IF)
+ sasi_hdd->open(drv, file_path, 256);
+#endif
+#if defined(SUPPORT_SCSI_IF)
+ scsi_hdd[drv]->open(0, file_path, 512);
+#endif
+#if defined(SUPPORT_IDE_IF)
+ ide_hdd[drv]->open(0, file_path, 512);
+#endif
}
-#else
- if(drv == 0 || drv == 1) {
- return fdc->is_disk_protected(drv);
+}
+
+void VM::close_hard_disk(int drv)
+{
+ if(drv < USE_HARD_DISK) {
+#if defined(SUPPORT_SASI_IF)
+ sasi_hdd->close(drv);
+#endif
+#if defined(SUPPORT_SCSI_IF)
+ scsi_hdd[drv]->close(0);
+#endif
+#if defined(SUPPORT_IDE_IF)
+ ide_hdd[drv]->close(0);
+#endif
}
+}
+
+bool VM::is_hard_disk_inserted(int drv)
+{
+ if(drv < USE_HARD_DISK) {
+#if defined(SUPPORT_SASI_IF)
+ return sasi_hdd->mounted(drv);
#endif
+#if defined(SUPPORT_SCSI_IF)
+ return scsi_hdd[drv]->mounted(0);
+#endif
+#if defined(SUPPORT_IDE_IF)
+ return ide_hdd[drv]->mounted(0);
+#endif
+ }
return false;
}
-uint32_t VM::is_floppy_disk_accessed()
+uint32_t VM::is_hard_disk_accessed()
{
-#if defined(_PC9801) || defined(_PC9801E)
- return (fdc_2hd->read_signal(0) & 3) | ((fdc_2dd->read_signal(0) & 3) << 2) | ((fdc_sub->read_signal(0) & 3) << 4);
-#elif defined(_PC9801VF) || defined(_PC9801U)
- return fdc_2dd->read_signal(0);
-#elif defined(_PC98DO) || defined(_PC98DOPLUS)
- if(boot_mode != 0) {
- return pc88fdc_sub->read_signal(0);
- } else {
- return fdc->read_signal(0);
- }
-#else
- return fdc->read_signal(0);
+ uint32_t status = 0;
+
+ for(int drv = 0; drv < USE_HARD_DISK; drv++) {
+#if defined(SUPPORT_SASI_IF)
+ if(sasi_hdd->accessed(drv)) {
+ status |= 1 << drv;
+ }
+#endif
+#if defined(SUPPORT_SCSI_IF)
+ if(scsi_hdd[drv]->accessed(0)) {
+ status |= 1 << drv;
+ }
#endif
+#if defined(SUPPORT_IDE_IF)
+ if(ide_hdd[drv]->accessed(0)) {
+ status |= 1 << drv;
+ }
+#endif
+ }
+ return status;
}
+#endif
-#if defined(SUPPORT_CMT_IF) || defined(_PC98DO) || defined(_PC98DOPLUS)
+#if defined(USE_TAPE)
void VM::play_tape(int drv, const _TCHAR* file_path)
{
#if defined(_PC98DO) || defined(_PC98DOPLUS)
}
}
-#define STATE_VERSION 8
+#define STATE_VERSION 14
-void VM::save_state(FILEIO* state_fio)
+bool VM::process_state(FILEIO* state_fio, bool loading)
{
- state_fio->FputUint32(STATE_VERSION);
-
- for(DEVICE* device = first_device; device; device = device->next_device) {
- device->save_state(state_fio);
- }
- state_fio->Fwrite(ram, sizeof(ram), 1);
- state_fio->FputBool(pit_clock_8mhz);
-#if defined(_PC98DO) || defined(_PC98DOPLUS)
- state_fio->FputInt32(boot_mode);
-#endif
- state_fio->FputInt32(sound_type);
-}
-
-bool VM::load_state(FILEIO* state_fio)
-{
- if(state_fio->FgetUint32() != STATE_VERSION) {
- return false;
- }
- for(DEVICE* device = first_device; device; device = device->next_device) {
- if(!device->load_state(state_fio)) {
+ if(!state_fio->StateCheckUint32(STATE_VERSION)) {
+ return false;
+ }
+ for(DEVICE* device = first_device; device; device = device->next_device) {
+ // Note: typeid(foo).name is fixed by recent ABI.Not dec 6.
+ // const char *name = typeid(*device).name();
+ // But, using get_device_name() instead of typeid(foo).name() 20181008 K.O
+ const char *name = device->get_device_name();
+ int len = strlen(name);
+ if(!state_fio->StateCheckInt32(len)) {
+ if(loading) {
+ printf("Class name len Error: DEVID=%d EXPECT=%s\n", device->this_device_id, name);
+ }
return false;
}
- }
- state_fio->Fread(ram, sizeof(ram), 1);
- pit_clock_8mhz = state_fio->FgetBool();
+ if(!state_fio->StateCheckBuffer(name, len, 1)) {
+ if(loading) {
+ printf("Class name Error: DEVID=%d EXPECT=%s\n", device->this_device_id, name);
+ }
+ return false;
+ }
+ if(!device->process_state(state_fio, loading)) {
+ if(loading) {
+ printf("Data loading Error: DEVID=%d\n", device->this_device_id);
+ }
+ return false;
+ }
+ }
+ state_fio->StateValue(pit_clock_8mhz);
#if defined(_PC98DO) || defined(_PC98DOPLUS)
- boot_mode = state_fio->FgetInt32();
+ state_fio->StateValue(boot_mode);
#endif
- sound_type = state_fio->FgetInt32();
- return true;
+ state_fio->StateValue(sound_type);
+ return true;
}
-