2 * FM-7 Main I/O [fm7_mainio.h]
4 * Author: K.Ohta <whatisthis.sowhat _at_ gmail.com>
7 * Jan 03, 2015 : Initial
12 #include "fm7_mainio.h"
14 #include "../mc6809.h"
17 #include "../datarec.h"
22 # if defined(_FM77AV20) || defined(_FM77AV40) || defined(_FM77AV20EX) || defined(_FM77AV40EX) || defined(_FM77AV40SX)
25 #include "./fm7_mainmem.h"
26 #include "./fm7_display.h"
27 #include "./fm7_keyboard.h"
28 #include "./kanjirom.h"
29 #include "./joystick.h"
30 #if defined(CAPABLE_JCOMMCARD)
31 #include "./jcommcard.h"
33 #include "../../statesub.h"
35 FM7_MAINIO::FM7_MAINIO(VM_TEMPLATE* parent_vm, EMU* parent_emu) : DEVICE(parent_vm, parent_emu)
38 for(i = 0; i < 3; i++) {
41 for(i = 0; i < 3; i++) {
43 uart_enabled[i] = false;
45 # if defined(_FM77AV20) || defined(_FM77AV40) || defined(_FM77AV20EX) || defined(_FM77AV40EX) || defined(_FM77AV40SX)
46 rs232c_enabled = false;
49 rs232c_enabled = true;
52 # if !defined(_FM77AV_VARIANTS)
78 #if defined(CAPABLE_JCOMMCARD)
83 lpt_strobe = false; // bit6
84 lpt_slctin = false; // bit7
88 cmt_indat = true; // bit7
89 cmt_invert = false; // Invert signal
93 #if defined(_FM77AV40) || defined(_FM77AV40EX) || defined(_FM77AV40SX) || \
94 defined(_FM77AV20) || defined(_FM77AV20EX) || defined(_FM77AV20SX)
95 stat_kanjirom = true; // R/W : bit5, '0' = sub, '1' = main. FM-77 Only.
96 #elif defined(_FM77_VARIANTS)
97 stat_fdmode_2hd = false; // R/W : bit6, '0' = 2HD, '1' = 2DD. FM-77 Only.
98 stat_kanjirom = true; // R/W : bit5, '0' = sub, '1' = main. FM-77 Only.
100 firq_break_key = false; // bit1, ON = '0'.
101 firq_sub_attention = false; // bit0, ON = '0'.
102 intmode_fdc = false; // bit2, '0' = normal, '1' = SFD.
104 drqstat_fdc_2hd = false;
105 irqstat_fdc_2hd = false;
112 intstat_syndet = false;
113 intstat_rxrdy = false;
114 intstat_txrdy = false;
115 irqstat_timer = false;
116 irqstat_printer = false;
117 irqstat_keyboard = false;
126 for(i = 0; i < 3; i++) {
127 opn_address[i] = 0x00;
130 opn_prescaler_type[i] = 1;
136 intstat_mouse = false;
137 mouse_enable = false;
149 irqreg_fdc = 0xff; //0b11111111;
150 irqmask_syndet = true;
151 irqmask_rxrdy = true;
152 irqmask_txrdy = true;
154 irqmask_timer = true;
155 irqmask_printer = true;
156 irqmask_keyboard = true;
160 irqreq_syndet = false;
161 irqreq_rxrdy = false;
162 irqreq_txrdy = false;
163 irqreq_printer = false;
164 irqreq_keyboard = false;
166 // FD20, FD21, FD22, FD23
167 connect_kanjiroml1 = false;
168 #if defined(_FM77AV_VARIANTS)
169 // FD2C, FD2D, FD2E, FD2F
170 connect_kanjiroml2 = false;
172 #if defined(_FM77_VARIANTS) || defined(_FM77AV_VARIANTS)
179 #if defined(_FM77_VARIANTS) || defined(_FM8)
180 bootmode = config.boot_mode & 7;
182 bootmode = config.boot_mode & 3;
184 memset(io_w_latch, 0xff, 0x100);
185 initialize_output_signals(&clock_status);
186 initialize_output_signals(&printer_reset_bus);
187 initialize_output_signals(&printer_strobe_bus);
188 initialize_output_signals(&printer_select_bus);
189 initialize_output_signals(&irq_bus);
190 initialize_output_signals(&firq_bus);
191 initialize_output_signals(&nmi_bus);
193 set_device_name(_T("MAIN I/O"));
196 FM7_MAINIO::~FM7_MAINIO()
201 void FM7_MAINIO::initialize()
204 event_beep_oneshot = -1;
206 event_fdc_motor = -1;
207 lpt_type = config.printer_type;
210 event_fdc_motor_2HD = -1;
212 #if defined(_FM77_VARIANTS) || defined(_FM77AV_VARIANTS)
214 # if defined(_FM77_VARIANTS)
215 stat_fdmode_2hd = false;
216 stat_kanjirom = true;
219 #if defined(_FM77AV_VARIANTS)
220 reg_fd12 = 0xbc; // 0b10111100
222 #if defined(_FM77_VARIANTS) || defined(_FM8)
223 bootmode = config.boot_mode & 7;
225 bootmode = config.boot_mode & 3;
234 void FM7_MAINIO::reset()
236 if(event_beep >= 0) cancel_event(this, event_beep);
238 if(event_beep_oneshot >= 0) cancel_event(this, event_beep_oneshot);
239 event_beep_oneshot = -1;
240 if(event_timerirq >= 0) cancel_event(this, event_timerirq);
243 register_event(this, EVENT_BEEP_CYCLE, (1000.0 * 1000.0) / (1200.0 * 2.0), true, &event_beep);
246 drqstat_fdc_2hd = false;
247 irqstat_fdc_2hd = false;
248 if(event_2hd_nmi >= 0) cancel_event(this, event_2hd_nmi);
251 #if defined(_FM77AV_VARIANTS)
255 #if defined(_FM77_VARIANTS)
257 #elif defined(_FM77AV_VARIANTS)
261 sub_cancel = false; // bit6 : '1' Cancel req.
262 sub_halt = false; // bit6 : '1' Cancel req.
263 sub_cancel_bak = sub_cancel; // bit6 : '1' Cancel req.
264 sub_halt_bak = sub_halt; // bit6 : '1' Cancel req.
265 req_z80run = false; // OK?
269 cmt_indat = true; // bit7
270 cmt_invert = false; // Invert signal
273 lpt_type = config.printer_type;
276 # if defined(_FM77AV20) || defined(_FM77AV40) || defined(_FM77AV20EX) || defined(_FM77AV40EX) || defined(_FM77AV40SX)
277 rs232c_enabled = false;
279 rs232c_enabled = true;
282 #if defined(_FM77AV_VARIANTS)
283 sub_monitor_type = 0x00;
285 if(config.cpu_type == 0) {
290 write_signals(&clock_status, clock_fast ? 0xffffffff : 0);
293 irqmask_syndet = true;
294 irqmask_rxrdy = true;
295 irqmask_txrdy = true;
297 irqmask_timer = true;
298 irqmask_printer = true;
299 irqmask_keyboard = true;
302 intstat_syndet = false;
303 intstat_rxrdy = false;
304 intstat_txrdy = false;
305 irqstat_timer = false;
306 irqstat_printer = false;
307 irqstat_keyboard = false;
309 irqreq_syndet = false;
310 irqreq_rxrdy = false;
311 irqreq_txrdy = false;
312 irqreq_printer = false;
313 irqreq_keyboard = false;
315 modem_irqmask_rxrdy = modem_irqmask_txrdy = true;
316 modem_syndet = modem_rxrdy = modem_txrdy = false;
317 midi_uart_irqmask = midi_syndet = midi_rxrdy = midi_txrdy = false;
320 call_write_signal(drec, SIG_DATAREC_MIC, 0x00, 0x01);
321 call_write_signal(drec, SIG_DATAREC_REMOTE, 0x00, 0x02);
327 firq_break_key = (keyboard->read_signal(SIG_FM7KEY_BREAK_KEY) != 0x00000000); // bit1, ON = '0'.
329 set_sub_attention(false);
330 #if defined(_FM77AV40) || defined(_FM77AV40EX) || defined(_FM77AV40SX) || \
331 defined(_FM77AV20) || defined(_FM77AV20EX) || defined(_FM77AV20SX)
332 stat_kanjirom = true; // R/W : bit5, '0' = sub, '1' = main. FM-77 Only.
333 #elif defined(_FM77_VARIANTS)
334 stat_fdmode_2hd = false; // R/W : bit6, '0' = 2HD, '1' = 2DD. FM-77 Only.
335 stat_kanjirom = true; // R/W : bit5, '0' = sub, '1' = main. FM-77 Only.
337 write_signals(&firq_bus, 0);
343 #if defined(_FM77AV_VARIANTS)
344 reg_fd12 = 0xbc; // 0b10111100
346 #if defined(WITH_Z80)
347 if(z80 != NULL) call_write_signal(z80, SIG_CPU_BUSREQ, 0xffffffff, 0xffffffff);
349 call_write_signal(maincpu, SIG_CPU_BUSREQ, 0, 0xffffffff);
350 call_write_signal(maincpu, SIG_CPU_HALTREQ, 0, 0xffffffff);
354 register_event(this, EVENT_TIMERIRQ_ON, 10000.0 / 4.9152, true, &event_timerirq); // TIMER IRQ
356 #if defined(_FM77_VARIANTS) || defined(_FM8)
357 bootmode = config.boot_mode & 7;
359 bootmode = config.boot_mode & 3;
361 memset(io_w_latch, 0xff, 0x100);
364 void FM7_MAINIO::reset_printer()
370 write_signals(&printer_strobe_bus, 0);
371 write_signals(&printer_select_bus, 0xffffffff);
372 write_signals(&printer_reset_bus, 0xffffffff);
373 register_event(this, EVENT_PRINTER_RESET_COMPLETED, 5.0 * 1000.0, false, NULL);
375 printer->write_signal(SIG_PRINTER_STROBE, 0x00, 0xff);
378 lpt_error_inv = true;
379 lpt_ackng_inv = true;
384 void FM7_MAINIO::set_clockmode(uint8_t flags)
387 if((flags & FM7_MAINCLOCK_SLOW) != 0) {
392 if(f != clock_fast) {
393 write_signal(FM7_MAINIO_CLOCKMODE, clock_fast ? 1 : 0, 1);
397 uint8_t FM7_MAINIO::get_clockmode(void)
399 if(!clock_fast) return FM7_MAINCLOCK_SLOW;
400 return FM7_MAINCLOCK_HIGH;
404 uint8_t FM7_MAINIO::get_port_fd00(void)
406 uint8_t ret = 0x7e; //0b01111110;
407 if(keyboard->read_data8(0x00) != 0) ret |= 0x80; // High bit.
408 if(clock_fast) ret |= 0x01; //0b00000001;
412 void FM7_MAINIO::set_port_fd00(uint8_t data)
415 call_write_signal(drec, SIG_DATAREC_MIC, data, 0x01);
416 call_write_signal(drec, SIG_DATAREC_REMOTE, data, 0x02);
418 lpt_slctin = ((data & 0x80) == 0);
419 lpt_strobe = ((data & 0x40) != 0);
420 write_signals(&printer_strobe_bus, lpt_strobe ? 0xffffffff : 0);
421 write_signals(&printer_select_bus, lpt_slctin ? 0xffffffff : 0);
422 if((lpt_type == 0) && (lpt_slctin)) {
423 printer->write_signal(SIG_PRINTER_STROBE, lpt_strobe ? 0xff : 0x00, 0xff);
427 uint8_t FM7_MAINIO::get_port_fd02(void)
430 bool ack_bak = lpt_ackng_inv;
432 ret = (cmt_indat) ? 0xff : 0x7f; // CMT
434 lpt_busy = (printer->read_signal(SIG_PRINTER_BUSY) != 0);
435 lpt_error_inv = true;
436 lpt_ackng_inv = (printer->read_signal(SIG_PRINTER_ACK) != 0);
438 } else if((lpt_type == 1) || (lpt_type == 2)) {
439 lpt_pe = (joystick->read_data8(lpt_type + 1) != 0); // check joy port;
441 lpt_error_inv = true;
442 lpt_ackng_inv = true;
445 lpt_error_inv = true;
446 lpt_ackng_inv = true;
449 ret &= (lpt_busy) ? 0xff : ~0x01;
450 ret &= (lpt_error_inv) ? 0xff : ~0x02;
451 ret &= (lpt_ackng_inv) ? 0xff : ~0x04;
452 ret &= (lpt_pe) ? 0xff : ~0x08;
453 ret &= (lpt_det1) ? 0xff : ~0x10;
454 ret &= (lpt_det2) ? 0xff : ~0x20;
455 if((lpt_ackng_inv == true) && (ack_bak == false)) set_irq_printer(true);
459 void FM7_MAINIO::set_port_fd02(uint8_t val)
463 bool syndetirq_bak = irqmask_syndet;
464 //bool rxrdyirq_bak = irqmask_rxrdy;
465 //bool txrdyirq_bak = irqmask_txrdy;
467 bool keyirq_bak = irqmask_keyboard;
468 //bool timerirq_bak = irqmask_timer;
469 //bool printerirq_bak = irqmask_printer;
470 //bool mfdirq_bak = irqmask_mfd;
472 // if((val & 0b00010000) != 0) {
473 if((val & 0x80) != 0) {
474 irqmask_syndet = false;
476 irqmask_syndet = true;
478 if(syndetirq_bak != irqmask_syndet) {
479 set_irq_txrdy(irqreq_syndet);
481 if((val & 0x40) != 0) {
482 irqmask_rxrdy = false;
484 irqmask_rxrdy = true;
486 // if(rxrdyirq_bak != irqmask_rxrdy) {
487 // set_irq_rxrdy(irqreq_rxrdy);
489 if((val & 0x20) != 0) {
490 irqmask_txrdy = false;
492 irqmask_txrdy = true;
494 // if(txrdyirq_bak != irqmask_txrdy) {
495 // set_irq_txrdy(irqreq_txrdy);
498 if((val & 0x10) != 0) {
504 if((val & 0x04) != 0) {
505 irqmask_timer = false;
507 irqmask_timer = true;
509 // if(timerirq_bak != irqmask_timer) {
510 // set_irq_timer(false);
513 if((val & 0x02) != 0) {
514 irqmask_printer = false;
516 irqmask_printer = true;
518 // if(printerirq_bak != irqmask_printer) {
519 // set_irq_printer(irqreq_printer);
522 if((val & 0x01) != 0) {
523 irqmask_keyboard = false;
525 irqmask_keyboard = true;
527 if(keyirq_bak != irqmask_keyboard) {
528 call_write_signal(display, SIG_FM7_SUB_KEY_MASK, irqmask_keyboard ? 1 : 0, 1);
529 set_irq_keyboard(irqreq_keyboard);
535 void FM7_MAINIO::set_irq_syndet(bool flag)
537 bool backup = intstat_syndet;
538 irqreq_syndet = flag;
539 if(flag && !(irqmask_syndet)) {
540 //irqstat_reg0 &= ~0x80; //~0x20;
541 intstat_syndet = true;
543 // irqstat_reg0 |= 0x80;
544 intstat_syndet = false;
546 if(backup != intstat_syndet) do_irq();
550 void FM7_MAINIO::set_irq_rxrdy(bool flag)
552 bool backup = intstat_rxrdy;
554 if(flag && !(irqmask_rxrdy)) {
555 //irqstat_reg0 &= ~0x40; //~0x20;
556 intstat_rxrdy = true;
558 //irqstat_reg0 |= 0x40;
559 intstat_rxrdy = false;
561 if(backup != intstat_rxrdy) do_irq();
566 void FM7_MAINIO::set_irq_txrdy(bool flag)
568 bool backup = intstat_txrdy;
570 if(flag && !(irqmask_txrdy)) {
571 //irqstat_reg0 &= ~0x20; //~0x20;
572 intstat_txrdy = true;
574 //irqstat_reg0 |= 0x20;
575 intstat_txrdy = false;
577 if(backup != intstat_txrdy) do_irq();
581 void FM7_MAINIO::set_irq_timer(bool flag)
584 irqstat_reg0 &= 0xfb; //~0x04;
585 irqstat_timer = true;
587 irqstat_reg0 |= 0x04;
588 irqstat_timer = false;
593 void FM7_MAINIO::set_irq_printer(bool flag)
595 irqreq_printer = flag;
596 if(flag && !(irqmask_printer)) {
597 irqstat_reg0 &= ~0x02;
598 irqstat_printer = true;
600 irqstat_reg0 |= 0x02;
601 irqstat_printer = false;
606 void FM7_MAINIO::set_irq_keyboard(bool flag)
608 //uint8_t backup = irqstat_reg0;
609 //printf("MAIN: KEYBOARD: IRQ=%d MASK=%d\n", flag ,irqmask_keyboard);
610 irqreq_keyboard = flag;
611 if(flag && !irqmask_keyboard) {
612 irqstat_reg0 &= 0xfe;
613 irqstat_keyboard = true;
615 irqstat_reg0 |= 0x01;
616 irqstat_keyboard = false;
622 void FM7_MAINIO::do_irq(void)
627 intstat = irqstat_timer | irqstat_keyboard | irqstat_printer;
628 intstat = intstat | intstat_opn | intstat_whg | intstat_thg;
629 intstat = intstat | intstat_txrdy | intstat_rxrdy | intstat_syndet;
630 intstat = intstat | intstat_mouse;
631 intstat = intstat | ((modem_irqmask_txrdy & modem_txrdy) | (modem_irqmask_rxrdy & modem_rxrdy) | modem_syndet);
632 intstat = intstat | ((!midi_uart_irqmask) & (midi_syndet | midi_txrdy | midi_rxrdy));
633 # if defined(HAS_DMA)
634 intstat = intstat | intstat_dma;
636 # if defined(HAS_2HD)
638 intstat = intstat | irqstat_fdc_2hd;
640 intstat = intstat | irqstat_fdc;
643 intstat = intstat | irqstat_fdc;
645 nval = (intstat) ? 0xffffffff : 0;
646 write_signals(&irq_bus, nval);
649 void FM7_MAINIO::do_firq(void)
653 firq_stat = firq_break_key | firq_sub_attention;
656 firq_stat = drqstat_fdc_2hd; // 20180226 BREAK KEY AND ATTENTION MUST BE MASK IF FIRQ USING FOR FDC's DRQ.Thanks to Haserin.
660 nval = (firq_stat) ? 0xffffffff : 0;
661 write_signals(&firq_bus, nval);
664 void FM7_MAINIO::do_nmi(bool flag)
666 write_signals(&nmi_bus, (flag) ? 0xffffffff : 0);
670 void FM7_MAINIO::set_break_key(bool pressed)
672 firq_break_key = pressed;
676 void FM7_MAINIO::set_sub_attention(bool flag)
678 firq_sub_attention = flag;
683 uint8_t FM7_MAINIO::get_fd04(void)
687 if(display->read_signal(SIG_DISPLAY_BUSY) != 0) val |= 0x80;
689 //f = keyboard->read_signal(SIG_FM7KEY_BREAK_KEY);
692 if(!firq_sub_attention) {
695 #if defined(_FM77_VARIANTS)
696 if(!stat_fdmode_2hd) val |= 0x40;
697 if(stat_kanjirom) val |= 0x20;
698 //if(intmode_fdc) val |= 0x04; // OK?
700 # if defined(_FM77L4)
701 val |= (display->read_signal(SIG_DISPLAY_EXTRA_MODE) & 0x18);
703 val |= 0x18; // For NON-77L4, these bit must be '1'.Thanks to Ryu Takegami.
707 // ToDo: MEMORY PARITY ERRO STATUS (if error, bit3 = '1').
708 #elif defined(_FM77AV_VARIANTS)
710 val |= 0x10; // ToDo: Hack for OS-9 for 77AV.Really need?
715 if(drqstat_fdc_2hd) {
716 drqstat_fdc_2hd = false;
717 if(!firq_sub_attention) do_firq();
720 if(firq_sub_attention) {
721 set_sub_attention(false);
722 //printf("Attention \n");
724 #if defined(_FM77AV_VARIANTS)
726 if(mainmem->read_signal(FM7_MAINIO_INITROM_ENABLED) == 0) {
727 set_break_key(false);
735 void FM7_MAINIO::set_fd04(uint8_t val)
738 #if defined(_FM77AV40) || defined(_FM77AV40EX) || defined(_FM77AV40SX)
739 call_write_signal(display, SIG_DISPLAY_EXTRA_MODE, val, 0xff);
740 stat_kanjirom = ((val & 0x20) != 0);
741 #elif defined(_FM77_VARIANTS)
742 call_write_signal(display, SIG_DISPLAY_EXTRA_MODE, val, 0xff);
743 stat_kanjirom = ((val & 0x20) != 0);
746 stat_fdmode_2hd = ((val & 0x40) == 0);
747 intmode_fdc = ((val & 0x04) == 0); // I/O port definition at Oh!FM 1985-5? is inverted status.
748 bool tmpf = intmode_fdc;
749 if(tmpf != intmode_fdc) {
756 uint8_t FM7_MAINIO::get_fd05(void)
759 if(display->read_signal(SIG_DISPLAY_BUSY) != 0) val |= 0x80;
760 if(!extdet_neg) val |= 0x01;
764 void FM7_MAINIO::set_fd05(uint8_t val)
766 sub_cancel = ((val & 0x40) != 0) ? true : false;
767 sub_halt = ((val & 0x80) != 0) ? true : false;
768 //if(sub_halt != sub_halt_bak) {
769 call_write_signal(display, SIG_DISPLAY_HALT, (sub_halt) ? 0xff : 0x00, 0xff);
771 sub_halt_bak = sub_halt;
773 //if(sub_cancel != sub_cancel_bak) {
774 call_write_signal(display, SIG_FM7_SUB_CANCEL, (sub_cancel) ? 0xff : 0x00, 0xff); // HACK
776 sub_cancel_bak = sub_cancel;
778 if((val & 0x01) != 0) {
779 call_write_signal(maincpu, SIG_CPU_HALTREQ, 1, 1);
783 if(z80 != NULL) call_write_signal(z80, SIG_CPU_BUSREQ, 1, 1);
788 void FM7_MAINIO::set_extdet(bool flag)
793 void FM7_MAINIO::write_fd0f(void)
795 call_write_signal(mainmem, FM7_MAINIO_PUSH_FD0F, 0, 0xffffffff);
798 uint8_t FM7_MAINIO::read_fd0f(void)
800 call_write_signal(mainmem, FM7_MAINIO_PUSH_FD0F, 0xffffffff, 0xffffffff);
804 bool FM7_MAINIO::get_rommode_fd0f(void)
806 return (mainmem->read_signal(FM7_MAINIO_PUSH_FD0F) == 0) ? false : true;
810 // Kanji ROM, FD20 AND FD21 (or SUBSYSTEM)
811 void FM7_MAINIO::write_kanjiaddr_hi(uint8_t addr)
813 #if defined(CAPABLE_JCOMMCARD) && !(defined(_FM77_VARIANTS) || defined(_FM77AV_VARIANTS))
814 if(jcommcard != NULL) {
815 jcommcard->write_io8(0, (uint32_t)addr);
819 if(!connect_kanjiroml1) {
822 #if defined(_FM77AV40) || defined(_FM77AV40EX) || defined(_FM77AV40SX) || \
823 defined(_FM77AV20) || defined(_FM77AV20EX) || defined(_FM77AV20SX)
824 if(!stat_kanjirom) return;
826 kanjiclass1->write_data8(KANJIROM_ADDR_HI, addr);
830 void FM7_MAINIO::write_kanjiaddr_lo(uint8_t addr)
832 #if defined(CAPABLE_JCOMMCARD) && !(defined(_FM77_VARIANTS) || defined(_FM77AV_VARIANTS))
833 if(jcommcard != NULL) {
834 jcommcard->write_io8(1, (uint32_t)addr);
838 if(!connect_kanjiroml1) {
841 #if defined(_FM77AV40) || defined(_FM77AV40EX) || defined(_FM77AV40SX) || \
842 defined(_FM77AV20) || defined(_FM77AV20EX) || defined(_FM77AV20SX)
843 if(!stat_kanjirom) return;
845 kanjiclass1->write_data8(KANJIROM_ADDR_LO, addr);
849 uint8_t FM7_MAINIO::read_kanjidata_left(void)
851 #if defined(CAPABLE_JCOMMCARD) && !(defined(_FM77_VARIANTS) || defined(_FM77AV_VARIANTS))
852 if(jcommcard != NULL) {
853 return (uint8_t)(jcommcard->read_io8(2));
856 if(!connect_kanjiroml1) {
859 #if defined(_FM77AV40) || defined(_FM77AV40EX) || defined(_FM77AV40SX) || \
860 defined(_FM77AV20) || defined(_FM77AV20EX) || defined(_FM77AV20SX)
861 if(!stat_kanjirom) return 0xff;
863 //printf("KANJI MAIN CLASS1 ADDR: %05x\n", kaddress.w.l);
865 return kanjiclass1->read_data8(KANJIROM_DATA_HI);
871 uint8_t FM7_MAINIO::read_kanjidata_right(void)
873 #if defined(CAPABLE_JCOMMCARD) && !(defined(_FM77AV_VARIANTS) || defined(_FM77_VARIANTS))
874 if(jcommcard != NULL) {
875 return (uint8_t)(jcommcard->read_io8(3));
878 if(!connect_kanjiroml1) {
881 #if defined(_FM77AV40) || defined(_FM77AV40EX) || defined(_FM77AV40SX) || \
882 defined(_FM77AV20) || defined(_FM77AV20EX) || defined(_FM77AV20SX)
883 if(!stat_kanjirom) return 0xff;
886 return kanjiclass1->read_data8(KANJIROM_DATA_LO);
892 #ifdef CAPABLE_KANJI_CLASS2
893 // Kanji ROM, FD20 AND FD21 (or SUBSYSTEM)
894 void FM7_MAINIO::write_kanjiaddr_hi_l2(uint8_t addr)
896 if(!connect_kanjiroml2) return;
897 if(!stat_kanjirom) return;
898 kanjiclass2->write_data8(KANJIROM_ADDR_HI, addr);
902 void FM7_MAINIO::write_kanjiaddr_lo_l2(uint8_t addr)
904 if(!connect_kanjiroml2) return;
905 if(!stat_kanjirom) return;
906 kanjiclass2->write_data8(KANJIROM_ADDR_LO, addr);
911 uint8_t FM7_MAINIO::read_kanjidata_left_l2(void)
913 if(!connect_kanjiroml2) return 0xff;
914 if(!stat_kanjirom) return 0xff;
917 return kanjiclass2->read_data8(KANJIROM_DATA_HI);
923 uint8_t FM7_MAINIO::read_kanjidata_right_l2(void)
925 if(!connect_kanjiroml2) return 0xff;
926 if(!stat_kanjirom) return 0xff;
929 return kanjiclass2->read_data8(KANJIROM_DATA_LO);
936 uint32_t FM7_MAINIO::read_signal(int id)
940 case FM7_MAINIO_KEYBOARDIRQ_MASK:
941 retval = (irqmask_keyboard) ? 0xffffffff : 0x00000000;
951 void FM7_MAINIO::write_signal(int id, uint32_t data, uint32_t mask)
954 val_b = ((data & mask) != 0);
957 //case SIG_FM7_SUB_HALT:
958 // mainmem->write_signal(SIG_FM7_SUB_HALT, data, mask);
960 case FM7_MAINIO_CLOCKMODE: // fd00
966 write_signals(&clock_status, clock_fast ? 0xffffffff : 0);
968 case FM7_MAINIO_CMT_RECV: // FD02
969 cmt_indat = val_b ^ cmt_invert;
971 case FM7_MAINIO_CMT_INVERT: // FD02
974 case FM7_MAINIO_TIMERIRQ: //
975 set_irq_timer(val_b);
977 case FM7_MAINIO_LPTIRQ: //
978 set_irq_printer(val_b);
980 case FM7_MAINIO_LPT_BUSY:
983 case FM7_MAINIO_LPT_ERROR:
984 lpt_error_inv = val_b;
986 case FM7_MAINIO_LPT_ACK:
988 bool f = lpt_ackng_inv;
989 lpt_ackng_inv = val_b;
990 if((lpt_ackng_inv == true) && (f == false)) set_irq_printer(true);
993 case FM7_MAINIO_LPT_PAPER_EMPTY:
996 case FM7_MAINIO_LPT_DET1:
999 case FM7_MAINIO_LPT_DET2:
1002 case FM7_MAINIO_KEYBOARDIRQ: //
1003 set_irq_keyboard(val_b);
1006 case FM7_MAINIO_PUSH_BREAK:
1007 set_break_key(val_b);
1009 #if defined(FM77AV_VARIANTS)
1010 case FM7_MAINIO_HOT_RESET:
1014 case FM7_MAINIO_SUB_ATTENTION:
1015 if(val_b) set_sub_attention(true);
1018 case FM7_MAINIO_EXTDET:
1019 extdet_neg = !val_b;
1021 case FM7_MAINIO_BEEP:
1024 case FM7_MAINIO_PSG_IRQ:
1026 #if defined(WITH_Z80)
1027 case FM7_MAINIO_RUN_Z80:
1028 if((req_z80run)/* && (val_b) */) {
1029 if(z80 != NULL) call_write_signal(z80, SIG_CPU_BUSREQ, 0, 1);
1031 //z80->reset(); // OK?
1034 case FM7_MAINIO_RUN_6809:
1035 if(!(req_z80run) /* && (val_b) */ && (z80_run)) {
1038 call_write_signal(maincpu, SIG_CPU_HALTREQ, 0, 1);
1042 case FM7_MAINIO_UART0_RXRDY:
1043 set_irq_rxrdy(val_b & rs232c_enabled);
1045 case FM7_MAINIO_UART0_TXRDY:
1046 set_irq_txrdy(val_b & rs232c_enabled);
1048 case FM7_MAINIO_UART0_SYNDET:
1049 set_irq_syndet(val_b & rs232c_enabled);
1051 case FM7_MAINIO_UART0_DCD:
1054 case FM7_MAINIO_MODEM_TXRDY:
1055 modem_txrdy = val_b;
1058 case FM7_MAINIO_MODEM_RXRDY:
1059 modem_rxrdy = val_b;
1062 case FM7_MAINIO_MODEM_SYNDET:
1063 modem_syndet = val_b;
1066 case FM7_MAINIO_MIDI_TXRDY:
1070 case FM7_MAINIO_MIDI_RXRDY:
1074 case FM7_MAINIO_MIDI_SYNDET:
1075 midi_syndet = val_b;
1079 //#if !defined(_FM8)
1080 case FM7_MAINIO_OPN_IRQ:
1081 if(!connect_opn) break;
1082 intstat_opn = val_b;
1085 case FM7_MAINIO_WHG_IRQ:
1086 if(!connect_whg) break;
1087 intstat_whg = val_b;
1090 case FM7_MAINIO_THG_IRQ:
1091 if(!connect_thg) break;
1092 intstat_thg = val_b;
1096 case FM7_MAINIO_FDC_DRQ:
1099 case FM7_MAINIO_FDC_IRQ:
1102 #if defined(HAS_2HD)
1103 case FM7_MAINIO_FDC_DRQ_2HD:
1104 set_drq_mfd_2HD(val_b);
1106 case FM7_MAINIO_FDC_IRQ_2HD:
1107 set_irq_mfd_2HD(val_b);
1110 #if defined(HAS_DMA)
1111 case FM7_MAINIO_DMA_INT:
1112 intstat_dma = val_b;
1116 #if defined(_FM77AV_VARIANTS)
1117 case SIG_DISPLAY_DISPLAY:
1124 case SIG_DISPLAY_VSYNC:
1131 case SIG_DISPLAY_MODE320:
1143 uint8_t FM7_MAINIO::get_irqstat_fd03(void)
1147 uint8_t backup = irqstat_reg0;
1149 extirq = intstat_opn | intstat_whg | intstat_thg;
1150 extirq = extirq | intstat_syndet | intstat_rxrdy | intstat_txrdy;
1151 # if defined(HAS_2HD)
1153 extirq = extirq | irqstat_fdc_2hd;
1155 extirq = extirq | irqstat_fdc;
1158 extirq = extirq | irqstat_fdc;
1160 # if defined(HAS_DMA)
1161 extirq = extirq | intstat_dma;
1164 irqstat_reg0 &= ~0x08;
1166 irqstat_reg0 |= 0x08;
1168 val = irqstat_reg0 | 0xf0;
1169 // Not call do_irq() twice. 20151221
1170 irqstat_timer = false;
1171 irqstat_printer = false;
1172 irqstat_reg0 |= 0x06;
1173 //if(backup != irqstat_reg0) do_irq();
1174 //this->out_debug_log(_T("IO: Check IRQ Status."));
1180 uint8_t FM7_MAINIO::get_extirq_fd17(void)
1183 if(intstat_opn && connect_opn) val &= ~0x08;
1184 if(intstat_mouse) val &= ~0x04;
1188 void FM7_MAINIO::set_ext_fd17(uint8_t data)
1190 if((data & 0x04) != 0) {
1191 mouse_enable = true;
1193 mouse_enable = false;
1197 #if defined(_FM77AV_VARIANTS)
1199 uint8_t FM7_MAINIO::subsystem_read_status(void)
1206 uint32_t FM7_MAINIO::read_io8(uint32_t addr)
1207 { // This is only for debug.
1208 addr = addr & 0xfff;
1210 return io_w_latch[addr];
1211 } else if(addr < 0x500) {
1212 uint32_t ofset = addr & 0xff;
1213 uint opnbank = (addr - 0x100) >> 8;
1214 return opn_regs[opnbank][ofset];
1215 } else if(addr < 0x600) {
1216 return mainmem->read_data8(addr - 0x500 + FM7_MAINIO_MMR_BANK);
1221 uint32_t FM7_MAINIO::read_dma_io8(uint32_t addr)
1223 return this->read_data8(addr & 0xff);
1226 uint32_t FM7_MAINIO::read_dma_data8(uint32_t addr)
1228 return this->read_data8(addr & 0xff);
1231 uint32_t FM7_MAINIO::read_data8(uint32_t addr)
1234 uint32_t mmr_segment;
1235 if(addr < FM7_MAINIO_IS_BASICROM) {
1238 #if defined(HAS_MMR)
1239 if((addr < 0x90) && (addr >= 0x80)) {
1240 mmr_segment = mainmem->read_data8(FM7_MAINIO_MMR_SEGMENT);
1241 # if defined(_FM77AV40) || defined(_FM77AV40SX) || defined(_FM77AV40EX) || \
1242 defined(_FM77AV20) || defined(_FM77AV20SX) || defined(_FM77AV20EX)
1243 mmr_segment &= 0x07;
1245 mmr_segment &= 0x03;
1247 return mainmem->read_data8(addr - 0x80 + FM7_MAINIO_MMR_BANK + mmr_segment * 16);
1250 // if((addr >= 0x0006) && !(addr == 0x1f) && !(addr == 0x0b)) printf("MAINIO: READ: %08x \n", addr);
1253 retval = (uint32_t) get_port_fd00();
1256 //#if !defined(_FM8)
1257 retval = keyboard->read_data8(0x01) & 0xff;
1261 retval = (uint32_t) get_port_fd02();
1264 //#if !defined(_FM8)
1265 retval = (uint32_t) get_irqstat_fd03();
1269 retval = (uint32_t) get_fd04();
1272 retval = (uint32_t) get_fd05();
1274 case 0x06: // RS-232C
1276 if(uart_enabled[0] && rs232c_enabled) {
1277 if(uart[0] != NULL) retval = uart[0]->read_io8(addr & 1);
1280 case 0x08: // Light pen
1284 #if defined(_FM77AV_VARIANTS)
1286 retval = ((config.boot_mode & 3) == 0) ? 0xfe : 0xff;
1287 #if defined(_FM77AV20) || defined(_FM77AV40) || defined(_FM77AV20EX) || defined(_FM77AV40EX) || defined(_FM77AV40SX)
1288 retval &= (uint32_t)(~0x04);
1289 if(!rs232c_dcd) retval |= 0x04;
1293 case 0x0e: // PSG DATA
1294 retval = (uint32_t) get_psg();
1295 //printf("PSG DATA READ val=%02x\n", retval);
1301 #if defined(_FM77AV_VARIANTS)
1303 retval = subsystem_read_status();
1306 //printf("OPN CMD READ \n");
1308 case 0x16: // OPN DATA
1309 retval = (uint32_t) get_opn(0);
1312 retval = (uint32_t) get_extirq_fd17();
1315 #if defined(HAS_2HD)
1316 case 0x18: // FDC: STATUS
1317 if(stat_fdmode_2hd) {
1318 retval = (uint32_t) get_fdc_stat_2HD();
1320 retval = (uint32_t) get_fdc_stat();
1323 //printf("FDC: READ STATUS %02x PC=%04x\n", retval, maincpu->get_pc());
1325 case 0x19: // FDC: Track
1326 if(stat_fdmode_2hd) {
1327 retval = (uint32_t) get_fdc_track_2HD();
1329 retval = (uint32_t) get_fdc_track();
1331 //printf("FDC: READ TRACK REG %02x\n", retval);
1333 case 0x1a: // FDC: Sector
1334 if(stat_fdmode_2hd) {
1335 retval = (uint32_t) get_fdc_sector_2HD();
1337 retval = (uint32_t) get_fdc_sector();
1339 //printf("FDC: READ SECTOR REG %02x\n", retval);
1341 case 0x1b: // FDC: Data
1342 if(stat_fdmode_2hd) {
1343 retval = (uint32_t) get_fdc_data_2HD();
1345 retval = (uint32_t) get_fdc_data();
1349 if(stat_fdmode_2hd) {
1350 retval = (uint32_t) get_fdc_fd1c_2HD();
1352 retval = (uint32_t) get_fdc_fd1c();
1354 //printf("FDC: READ HEAD REG %02x\n", retval);
1357 if(stat_fdmode_2hd) {
1358 retval = (uint32_t) get_fdc_motor_2HD();
1360 retval = (uint32_t) get_fdc_motor();
1362 //printf("FDC: READ MOTOR REG %02x\n", retval);
1365 if(stat_fdmode_2hd) {
1366 retval = (uint32_t) get_fdc_fd1e_2HD();
1368 retval = (uint32_t) get_fdc_fd1e();
1370 //printf("FDC: READ MOTOR REG %02x\n", retval);
1373 if(stat_fdmode_2hd) {
1374 retval = (uint32_t) fdc_getdrqirq_2HD();
1376 retval = (uint32_t) fdc_getdrqirq();
1380 case 0x18: // FDC: STATUS
1381 retval = (uint32_t) get_fdc_stat();
1383 //printf("FDC: READ STATUS %02x PC=%04x\n", retval, maincpu->get_pc());
1385 case 0x19: // FDC: Track
1386 retval = (uint32_t) get_fdc_track();
1387 //printf("FDC: READ TRACK REG %02x\n", retval);
1389 case 0x1a: // FDC: Sector
1390 retval = (uint32_t) get_fdc_sector();
1391 //printf("FDC: READ SECTOR REG %02x\n", retval);
1393 case 0x1b: // FDC: Data
1394 retval = (uint32_t) get_fdc_data();
1397 retval = (uint32_t) get_fdc_fd1c();
1398 //printf("FDC: READ HEAD REG %02x\n", retval);
1401 retval = (uint32_t) get_fdc_motor();
1402 //printf("FDC: READ MOTOR REG %02x\n", retval);
1405 retval = (uint32_t) get_fdc_fd1e();
1406 //printf("FDC: READ MOTOR REG %02x\n", retval);
1409 retval = (uint32_t) fdc_getdrqirq();
1412 case 0x22: // Kanji ROM
1413 retval = (uint32_t) read_kanjidata_left();
1415 case 0x23: // Kanji ROM
1416 retval = (uint32_t) read_kanjidata_right();
1418 #if defined(CAPABLE_JCOMMCARD)
1421 # if defined(_FM77_VARIANTS) || defined(_FM77AV_VARIANTS)
1425 if(jcommcard != NULL) {
1426 retval = (uint32_t)(jcommcard->read_io8(addr));
1432 #if defined(CAPABLE_KANJI_CLASS2)
1433 case 0x2e: // Kanji ROM Level2
1434 retval = (uint32_t) read_kanjidata_left_l2();
1436 case 0x2f: // Kanji ROM Level2
1437 retval = (uint32_t) read_kanjidata_right_l2();
1440 //#if !defined(_FM8)
1441 case 0x37: // Multi page
1442 //retval = (uint32_t)display->read_data8(DISPLAY_ADDR_MULTIPAGE);
1446 if(uart_enabled[1]) {
1447 if(uart[1] != NULL) retval = uart[1]->read_io8(addr & 1);
1452 case 0x45: // WHG CMD
1454 case 0x46: // WHG DATA
1455 retval = (uint32_t) get_opn(1);
1458 retval = (uint32_t) get_extirq_whg();
1460 case 0x51: // THG CMD
1462 case 0x52: // THG DATA
1463 retval = (uint32_t) get_opn(2);
1466 retval = (uint32_t) get_extirq_thg();
1469 #if defined(HAS_MMR)
1473 if(mainmem->read_signal(FM7_MAINIO_BOOTRAM_RW) != 0) retval |= 0x01;
1474 if(mainmem->read_signal(FM7_MAINIO_WINDOW_ENABLED) != 0) retval |= 0x40;
1475 if(mainmem->read_signal(FM7_MAINIO_MMR_ENABLED) != 0) retval |= 0x80;
1478 #if defined(_FM77AV40SX) || defined(_FM77AV40EX)
1481 if(mainmem->read_signal(FM7_MAINIO_FASTMMR_ENABLED) != 0) retval |= 0x08;
1482 if(mainmem->read_signal(FM7_MAINIO_EXTROM) != 0) retval |= 0x80;
1485 #if defined(HAS_DMA)
1490 retval = dmac->read_data8(dma_addr);
1495 if(uart_enabled[2]) {
1496 if(uart[2] != NULL) retval = uart[2]->read_io8(addr & 1);
1502 //#if !defined(_FM8)
1503 if((addr < 0x40) && (addr >= 0x38)) {
1504 addr = (addr - 0x38) + FM7_SUBMEM_OFFSET_DPALETTE;
1505 return (uint32_t) display->read_data8(addr);
1510 } else if(addr == FM7_MAINIO_CLOCKMODE) {
1511 return (uint32_t)get_clockmode();
1513 #if defined(_FM77AV_VARIANTS)
1514 else if(addr == FM7_MAINIO_SUBMONITOR_ROM) {
1515 retval = sub_monitor_type & 0x03;
1517 } else if(addr == FM7_MAINIO_SUBMONITOR_RAM) {
1518 #if defined(_FM77AV40) || defined(_FM77AV40SX) || defined(_FM77AV40EX) || \
1519 defined(_FM77AV20) || defined(_FM77AV20SX) || defined(_FM77AV20EX)
1520 retval = ((sub_monitor_type & 0x04) != 0) ? 0xffffffff : 0x00000000;
1527 //if((addr >= 0x0006) && (addr != 0x1f)) printf("MAINIO: READ: %08x DATA=%08x\n", addr);
1531 void FM7_MAINIO::write_dma_io8(uint32_t addr, uint32_t data)
1533 this->write_data8(addr & 0xff, data);
1536 void FM7_MAINIO::write_dma_data8(uint32_t addr, uint32_t data)
1538 this->write_data8(addr & 0xff, data);
1542 void FM7_MAINIO::write_data8(uint32_t addr, uint32_t data)
1545 uint32_t mmr_segment;
1546 if(addr < FM7_MAINIO_IS_BASICROM) {
1548 io_w_latch[addr] = data;
1549 #if defined(HAS_MMR)
1550 if((addr < 0x90) && (addr >= 0x80)) {
1551 mmr_segment = mainmem->read_data8(FM7_MAINIO_MMR_SEGMENT);
1552 # if defined(_FM77AV40) || defined(_FM77AV40SX) || defined(_FM77AV40EX) || \
1553 defined(_FM77AV20) || defined(_FM77AV20SX) || defined(_FM77AV20EX)
1554 mmr_segment &= 0x07;
1556 mmr_segment &= 0x03;
1558 mainmem->write_data8(FM7_MAINIO_MMR_BANK + mmr_segment * 16 + addr - 0x80, data);
1564 set_port_fd00((uint8_t)data);
1568 lpt_outdata = (uint8_t)data;
1570 case 0: // Write to file
1571 printer->write_signal(SIG_PRINTER_DATA, data, 0xff);
1575 joystick->write_data8(0x01, data);
1580 set_port_fd02((uint8_t)data);
1589 set_fd05((uint8_t)data);
1591 case 0x06: // RS-232C
1593 if(uart_enabled[0] && rs232c_enabled) {
1594 if(uart[0] != NULL) uart[0]->write_io8(addr & 1, data);
1597 case 0x08: // Light pen
1602 #if defined(_FM77AV20) || defined(_FM77AV40) || defined(_FM77AV20EX) || defined(_FM77AV40EX) || defined(_FM77AV40SX)
1603 if(rs232c_dtr != NULL) {
1604 if((data & 0x04) != 0) {
1605 rs232c_dtr->write_signal(SIG_AND_BIT_1, 0, 1);
1607 rs232c_dtr->write_signal(SIG_AND_BIT_1, 1, 1);
1610 rs232c_enabled = ((data & 0x01) != 0) ? true : false;
1614 //printf("PSG CMD WRITE val=%02x\n", data);
1618 //printf("PSG DATA WRITE val=%02x\n", data);
1624 #if defined(_FM77AV_VARIANTS)
1626 flag = ((data & 0x02) == 0) ? true : false;
1627 call_write_signal(mainmem, FM7_MAINIO_INITROM_ENABLED, (flag) ? 0xffffffff : 0 , 0xffffffff);
1630 call_write_signal(display, SIG_DISPLAY_MODE320, data, 0x40);
1632 reg_fd12 |= (data & 0x40);
1635 sub_monitor_type = data & 0x07;
1636 call_write_signal(display, SIG_FM7_SUB_BANK, sub_monitor_type, 0x07);
1639 case 0x15: // OPN CMD
1640 //printf("OPN CMD WRITE val=%02x\n", data);
1641 set_opn_cmd(0, data);
1643 case 0x16: // OPN DATA
1644 //printf("OPN DATA WRITE val=%02x\n", data);
1648 set_ext_fd17((uint8_t)data);
1650 #if defined(HAS_2HD)
1651 case 0x18: // FDC: COMMAND
1652 if(stat_fdmode_2hd) {
1653 set_fdc_cmd_2HD((uint8_t)data);
1655 set_fdc_cmd((uint8_t)data);
1657 //printf("FDC: WRITE CMD %02x\n", data);
1659 case 0x19: // FDC: Track
1660 if(stat_fdmode_2hd) {
1661 set_fdc_track_2HD((uint8_t)data);
1663 set_fdc_track((uint8_t)data);
1665 //printf("FDC: WRITE TRACK REG %02x\n", data);
1667 case 0x1a: // FDC: Sector
1668 if(stat_fdmode_2hd) {
1669 set_fdc_sector_2HD((uint8_t)data);
1671 set_fdc_sector((uint8_t)data);
1673 //printf("FDC: WRITE SECTOR REG %02x\n", data);
1675 case 0x1b: // FDC: Data
1676 if(stat_fdmode_2hd) {
1677 set_fdc_data_2HD((uint8_t)data);
1679 set_fdc_data((uint8_t)data);
1683 if(stat_fdmode_2hd) {
1684 set_fdc_fd1c_2HD((uint8_t)data);
1686 set_fdc_fd1c((uint8_t)data);
1688 //printf("FDC: WRITE HEAD REG %02x\n", data);
1691 if(stat_fdmode_2hd) {
1692 set_fdc_fd1d_2HD((uint8_t)data);
1694 set_fdc_fd1d((uint8_t)data);
1696 //printf("FDC: WRITE MOTOR REG %02x\n", data);
1699 if(stat_fdmode_2hd) {
1700 set_fdc_fd1e_2HD((uint8_t)data);
1702 set_fdc_fd1e((uint8_t)data);
1709 case 0x18: // FDC: COMMAND
1710 set_fdc_cmd((uint8_t)data);
1711 //printf("FDC: WRITE CMD %02x\n", data);
1713 case 0x19: // FDC: Track
1714 set_fdc_track((uint8_t)data);
1715 //printf("FDC: WRITE TRACK REG %02x\n", data);
1717 case 0x1a: // FDC: Sector
1718 set_fdc_sector((uint8_t)data);
1719 //printf("FDC: WRITE SECTOR REG %02x\n", data);
1721 case 0x1b: // FDC: Data
1722 set_fdc_data((uint8_t)data);
1725 set_fdc_fd1c((uint8_t)data);
1726 //printf("FDC: WRITE HEAD REG %02x\n", data);
1729 set_fdc_fd1d((uint8_t)data);
1730 //printf("FDC: WRITE MOTOR REG %02x\n", data);
1733 set_fdc_fd1e((uint8_t)data);
1739 case 0x20: // Kanji ROM
1740 write_kanjiaddr_hi((uint8_t)data);
1743 case 0x21: // Kanji ROM
1744 write_kanjiaddr_lo((uint8_t)data);
1746 #if defined(CAPABLE_JCOMMCARD)
1747 # if defined(_FM77_VARIANTS) || defined(_FM77AV_VARIANTS)
1753 if(jcommcard != NULL) jcommcard->write_io8(addr, data);
1756 case 0x2c: // Kanji ROM(DUP)
1757 #if defined(CAPABLE_KANJI_CLASS2)
1758 write_kanjiaddr_hi_l2((uint8_t)data);
1760 //write_kanjiaddr_hi((uint8_t)data);
1763 case 0x2d: // Kanji ROM(DUP)
1764 #if defined(CAPABLE_KANJI_CLASS2)
1765 write_kanjiaddr_lo_l2((uint8_t)data);
1767 //write_kanjiaddr_lo((uint8_t)data);
1770 #if defined(CAPABLE_DICTROM)
1772 call_write_signal(mainmem, FM7_MAINIO_EXTBANK, data, 0xff);
1775 #if defined(_FM77AV_VARIANTS)
1777 display->write_data8(FM7_SUBMEM_OFFSET_APALETTE_HI, data);
1780 display->write_data8(FM7_SUBMEM_OFFSET_APALETTE_LO, data);
1783 display->write_data8(FM7_SUBMEM_OFFSET_APALETTE_B, data);
1786 display->write_data8(FM7_SUBMEM_OFFSET_APALETTE_R, data);
1789 display->write_data8(FM7_SUBMEM_OFFSET_APALETTE_G, data);
1792 //#if !defined(_FM8)
1793 case 0x37: // Multi page
1794 call_write_signal(display, SIG_DISPLAY_MULTIPAGE, data, 0x00ff);
1798 if(uart_enabled[1]) {
1799 if(uart[1] != NULL) uart[1]->write_io8(addr & 1, data);
1803 modem_irqmask_txrdy = ((data & 0x20) != 0);
1804 modem_irqmask_rxrdy = ((data & 0x40) != 0);
1808 case 0x45: // WHG CMD
1809 set_opn_cmd(1, data);
1811 case 0x46: // WHG DATA
1816 case 0x51: // THG CMD
1817 set_opn_cmd(2, data);
1819 case 0x52: // THG DATA
1825 #if defined(HAS_MMR)
1827 #if defined(_FM77AV40) || defined(_FM77AV40SX) || defined(_FM77AV40EX) || \
1828 defined(_FM77AV20) || defined(_FM77AV20SX) || defined(_FM77AV20EX)
1829 mmr_segment = data & 7;
1831 // printf("MMR SEGMENT: %02x\n", data & 3);
1832 mmr_segment = data & 3;
1834 mainmem->write_data8(FM7_MAINIO_MMR_SEGMENT, (uint32_t)mmr_segment);
1837 mainmem->write_data8(FM7_MAINIO_WINDOW_OFFSET, (uint32_t)(data & 0x00ff));
1840 call_write_signal(mainmem, FM7_MAINIO_BOOTRAM_RW, data, 0x01);
1841 call_write_signal(mainmem, FM7_MAINIO_WINDOW_ENABLED, data , 0x40);
1842 //this->write_signal(FM7_MAINIO_CLOCKMODE, clock_fast ? 1 : 0, 1);
1843 //mainmem->write_signal(FM7_MAINIO_CLOCKMODE, clock_fast ? 1 : 0, 1);
1844 call_write_signal(mainmem, FM7_MAINIO_MMR_ENABLED, data, 0x80);
1848 #if defined(_FM77AV40) || defined(_FM77AV40SX) || defined(_FM77AV40EX) || \
1849 defined(_FM77AV20) || defined(_FM77AV20SX) || defined(_FM77AV20EX)
1851 call_write_signal(mainmem, FM7_MAINIO_MMR_EXTENDED, data, 0x80);
1852 call_write_signal(mainmem, FM7_MAINIO_MEM_REFRESH_FAST, data, 0x04);
1853 call_write_signal(mainmem, FM7_MAINIO_WINDOW_FAST , data, 0x01);
1856 # if defined(_FM77AV40SX) || defined(_FM77AV40EX)
1858 call_write_signal(mainmem, FM7_MAINIO_FASTMMR_ENABLED, data, 0x08);
1859 call_write_signal(mainmem, FM7_MAINIO_EXTROM, data , 0x80);
1863 #if defined(HAS_DMA)
1865 dma_addr = data & 0x1f;
1868 dmac->write_data8(dma_addr, data);
1869 //this->out_debug_log(_T("IO: Wrote DMA %02x to reg %02x\n"), data, dma_addr);
1875 if(uart_enabled[2]) {
1876 if(uart[2] != NULL) uart[2]->write_io8(addr & 1, data);
1880 //printf("MAIN: Write I/O Addr=%08x DATA=%02x\n", addr, data);
1883 if((addr < 0x40) && (addr >= 0x38)) {
1884 addr = (addr - 0x38) | FM7_SUBMEM_OFFSET_DPALETTE;
1885 display->write_data8(addr, (uint8_t)data);
1889 } else if(addr == FM7_MAINIO_CLOCKMODE) {
1890 set_clockmode((uint8_t)data);
1893 //if((addr >= 0x0006) && !(addr == 0x1f)) printf("MAINIO: WRITE: %08x DATA=%08x\n", addr, data);
1896 void FM7_MAINIO::event_callback(int event_id, int err)
1898 // printf("MAIN EVENT id=%d\n", event_id);
1900 case EVENT_BEEP_OFF:
1903 case EVENT_BEEP_CYCLE:
1906 case EVENT_UP_BREAK:
1907 call_write_signal(keyboard, SIG_FM7KEY_OVERRIDE_PRESS_BREAK, 0, 0xffffffff);
1908 set_break_key(false);
1910 //#if !defined(_FM8)
1911 case EVENT_TIMERIRQ_ON:
1912 //if(!irqmask_timer) set_irq_timer(true);
1913 set_irq_timer(!irqmask_timer);
1916 case EVENT_FD_MOTOR_ON:
1917 set_fdc_motor(true);
1918 event_fdc_motor = -1;
1920 case EVENT_FD_MOTOR_OFF:
1921 set_fdc_motor(false);
1922 event_fdc_motor = -1;
1924 #if defined(HAS_2HD)
1925 case EVENT_FD_MOTOR_ON_2HD:
1926 set_fdc_motor_2HD(true);
1927 event_fdc_motor_2HD = -1;
1929 case EVENT_FD_MOTOR_OFF_2HD:
1930 set_fdc_motor_2HD(false);
1931 event_fdc_motor_2HD = -1;
1933 case EVENT_FD_NMI_2HD:
1938 case EVENT_PRINTER_RESET_COMPLETED:
1939 write_signals(&printer_reset_bus, 0x00);
1947 void FM7_MAINIO::update_config()
1949 switch(config.cpu_type){
1957 write_signals(&clock_status, clock_fast ? 0xffffffff : 0);
1960 void FM7_MAINIO::event_vline(int v, int clock)
1965 #define STATE_VERSION 16
1966 #include "../../statesub.h"
1968 void FM7_MAINIO::decl_state(void)
1970 enter_decl_state(STATE_VERSION);
1972 DECL_STATE_ENTRY_MULTI(void, io_w_latch, sizeof(io_w_latch));
1974 DECL_STATE_ENTRY_BOOL(clock_fast);
1975 DECL_STATE_ENTRY_BOOL(lpt_strobe);
1976 DECL_STATE_ENTRY_BOOL(lpt_slctin);
1977 DECL_STATE_ENTRY_BOOL(beep_flag);
1978 DECL_STATE_ENTRY_BOOL(beep_snd);
1981 DECL_STATE_ENTRY_UINT8(lpt_outdata);
1983 DECL_STATE_ENTRY_BOOL(cmt_indat);
1984 DECL_STATE_ENTRY_BOOL(cmt_invert);
1985 DECL_STATE_ENTRY_BOOL(lpt_det2);
1986 DECL_STATE_ENTRY_BOOL(lpt_det1);
1987 DECL_STATE_ENTRY_BOOL(lpt_pe);
1988 DECL_STATE_ENTRY_BOOL(lpt_ackng_inv);
1989 DECL_STATE_ENTRY_BOOL(lpt_error_inv);
1990 DECL_STATE_ENTRY_UINT8(irqmask_reg0);
1992 DECL_STATE_ENTRY_BOOL(irqmask_syndet);
1993 DECL_STATE_ENTRY_BOOL(irqmask_rxrdy);
1994 DECL_STATE_ENTRY_BOOL(irqmask_txrdy);
1995 DECL_STATE_ENTRY_BOOL(irqmask_mfd);
1996 DECL_STATE_ENTRY_BOOL(irqmask_timer);
1997 DECL_STATE_ENTRY_BOOL(irqmask_printer);
1998 DECL_STATE_ENTRY_BOOL(irqmask_keyboard);
2000 DECL_STATE_ENTRY_BOOL(irqreq_syndet);
2001 DECL_STATE_ENTRY_BOOL(irqreq_rxrdy);
2002 DECL_STATE_ENTRY_BOOL(irqreq_txrdy);
2003 DECL_STATE_ENTRY_BOOL(irqreq_printer);
2004 DECL_STATE_ENTRY_BOOL(irqreq_keyboard);
2005 DECL_STATE_ENTRY_UINT8(irqstat_reg0);
2007 DECL_STATE_ENTRY_BOOL(irqstat_timer);
2008 DECL_STATE_ENTRY_BOOL(irqstat_printer);
2009 DECL_STATE_ENTRY_BOOL(irqstat_keyboard);
2012 #if defined(_FM77_VARIANTS)
2013 DECL_STATE_ENTRY_BOOL(stat_fdmode_2hd);
2014 DECL_STATE_ENTRY_BOOL(stat_kanjirom);
2015 #elif defined(_FM77AV40) || defined(_FM77AV40EX) || defined(_FM77AV40SX) || \
2016 defined(_FM77AV20) || defined(_FM77AV20EX) || defined(_FM77AV20SX)
2017 DECL_STATE_ENTRY_BOOL(stat_kanjirom);
2019 DECL_STATE_ENTRY_BOOL(firq_break_key);
2020 DECL_STATE_ENTRY_BOOL(firq_sub_attention);
2022 DECL_STATE_ENTRY_BOOL(intmode_fdc);
2024 DECL_STATE_ENTRY_BOOL(extdet_neg);
2025 DECL_STATE_ENTRY_BOOL(sub_halt);
2026 DECL_STATE_ENTRY_BOOL(sub_cancel);
2028 DECL_STATE_ENTRY_BOOL(intstat_syndet);
2029 DECL_STATE_ENTRY_BOOL(intstat_rxrdy);
2030 DECL_STATE_ENTRY_BOOL(intstat_txrdy);
2033 DECL_STATE_ENTRY_BOOL(intstat_opn);
2034 DECL_STATE_ENTRY_BOOL(intstat_mouse);
2035 DECL_STATE_ENTRY_BOOL(mouse_enable);
2037 DECL_STATE_ENTRY_BOOL(intstat_whg);
2038 DECL_STATE_ENTRY_BOOL(intstat_thg);
2041 DECL_STATE_ENTRY_BOOL(connect_fdc);
2042 DECL_STATE_ENTRY_UINT8(fdc_statreg);
2043 DECL_STATE_ENTRY_UINT8(fdc_cmdreg);
2044 DECL_STATE_ENTRY_UINT8(fdc_trackreg);
2045 DECL_STATE_ENTRY_UINT8(fdc_sectreg);
2046 DECL_STATE_ENTRY_UINT8(fdc_datareg);
2047 DECL_STATE_ENTRY_UINT8(fdc_headreg);
2048 DECL_STATE_ENTRY_UINT8(fdc_drvsel);
2049 DECL_STATE_ENTRY_UINT8(irqreg_fdc);
2050 DECL_STATE_ENTRY_BOOL(fdc_motor);
2051 DECL_STATE_ENTRY_BOOL(irqstat_fdc);
2053 DECL_STATE_ENTRY_BOOL(connect_kanjiroml1);
2054 #if defined(_FM77AV_VARIANTS)
2055 DECL_STATE_ENTRY_BOOL(connect_kanjiroml2);
2057 DECL_STATE_ENTRY_BOOL(boot_ram);
2058 DECL_STATE_ENTRY_BOOL(hotreset);
2060 DECL_STATE_ENTRY_UINT8(sub_monitor_type);
2065 DECL_STATE_ENTRY_INT(event_beep);
2066 DECL_STATE_ENTRY_INT(event_beep_oneshot);
2067 DECL_STATE_ENTRY_INT(event_timerirq);
2070 DECL_STATE_ENTRY_INT(event_fdc_motor);
2071 #if defined(_FM77AV40) || defined(_FM77AV40EX) || defined(_FM77AV40SX)|| \
2072 defined(_FM77AV20) || defined(_FM77AV20SX) || defined(_FM77AV20EX)
2073 DECL_STATE_ENTRY_UINT8_ARRAY(fdc_drive_table, 4);
2074 DECL_STATE_ENTRY_UINT8(fdc_reg_fd1e);
2076 #if defined(HAS_DMA)
2077 DECL_STATE_ENTRY_BOOL(intstat_dma);
2078 DECL_STATE_ENTRY_UINT8(dma_addr);
2080 #if defined(_FM77AV_VARIANTS)
2081 DECL_STATE_ENTRY_UINT8(reg_fd12);
2085 DECL_STATE_ENTRY_BOOL(req_z80run);
2086 DECL_STATE_ENTRY_BOOL(z80_run);
2089 DECL_STATE_ENTRY_BOOL(rs232c_enabled);
2090 DECL_STATE_ENTRY_BOOL(rs232c_dcd);
2091 DECL_STATE_ENTRY_BOOL_ARRAY(uart_enabled, 3);
2093 DECL_STATE_ENTRY_BOOL(modem_irqmask_rxrdy);
2094 DECL_STATE_ENTRY_BOOL(modem_irqmask_txrdy);
2095 DECL_STATE_ENTRY_BOOL(modem_syndet);
2096 DECL_STATE_ENTRY_BOOL(modem_rxrdy);
2097 DECL_STATE_ENTRY_BOOL(modem_txrdy);
2099 DECL_STATE_ENTRY_BOOL(midi_uart_irqmask);
2100 DECL_STATE_ENTRY_BOOL(midi_syndet);
2101 DECL_STATE_ENTRY_BOOL(midi_rxrdy);
2102 DECL_STATE_ENTRY_BOOL(midi_txrdy);
2103 #if defined(HAS_2HD)
2104 DECL_STATE_ENTRY_INT(event_fdc_motor_2HD);
2105 DECL_STATE_ENTRY_BOOL(connect_fdc_2HD);
2106 DECL_STATE_ENTRY_UINT8(fdc_2HD_statreg);
2107 DECL_STATE_ENTRY_UINT8(fdc_2HD_cmdreg);
2108 DECL_STATE_ENTRY_UINT8(fdc_2HD_trackreg);
2109 DECL_STATE_ENTRY_UINT8(fdc_2HD_sectreg);
2110 DECL_STATE_ENTRY_UINT8(fdc_2HD_datareg);
2111 DECL_STATE_ENTRY_UINT8(fdc_2HD_headreg);
2112 DECL_STATE_ENTRY_UINT8(fdc_2HD_drvsel);
2113 DECL_STATE_ENTRY_UINT8(irqreg_fdc_2HD);
2114 DECL_STATE_ENTRY_BOOL(fdc_2HD_motor);
2115 //state_fio->FputBool(irqstat_fdc);
2116 DECL_STATE_ENTRY_INT(event_2hd_nmi);
2117 DECL_STATE_ENTRY_UINT32(nmi_delay);
2118 DECL_STATE_ENTRY_BOOL(irqstat_fdc_2hd);
2119 DECL_STATE_ENTRY_BOOL(drqstat_fdc_2hd);
2126 void FM7_MAINIO::save_state(FILEIO *state_fio)
2128 if(state_entry != NULL) state_entry->save_state(state_fio);
2131 for(int i = 0; i < 3; i++) {
2132 out_debug_log("OPN#%d registers (to Save)", i);
2133 out_debug_log("ADDR: +0 +1 +2 +3 +4 +5 +6 +7 +8 +9 +a +b +c +d +e +f");
2134 for(int ladr = 0; ladr < 0x100; ladr += 0x10) {
2135 out_debug_log("+%02x: %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x",
2137 opn_regs[i][ladr + 0], opn_regs[i][ladr + 1], opn_regs[i][ladr + 2], opn_regs[i][ladr + 3],
2138 opn_regs[i][ladr + 4], opn_regs[i][ladr + 5], opn_regs[i][ladr + 6], opn_regs[i][ladr + 7],
2139 opn_regs[i][ladr + 8], opn_regs[i][ladr + 9], opn_regs[i][ladr + 10], opn_regs[i][ladr + 11],
2140 opn_regs[i][ladr + 12], opn_regs[i][ladr + 13], opn_regs[i][ladr + 14], opn_regs[i][ladr + 15]);
2146 bool FM7_MAINIO::load_state(FILEIO *state_fio)
2150 //bool stat = false;
2153 if(state_entry != NULL) {
2154 mb = state_entry->load_state(state_fio);
2156 #if defined(HAS_DMA)
2157 dma_addr = dma_addr & 0x1f;
2162 for(int i = 0; i < 3; i++) {
2163 out_debug_log("OPN#%d registers (Loaded)", i);
2164 out_debug_log("ADDR: +0 +1 +2 +3 +4 +5 +6 +7 +8 +9 +a +b +c +d +e +f");
2165 for(int ladr = 0; ladr < 0x100; ladr += 0x10) {
2166 out_debug_log("+%02x: %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x",
2168 opn_regs[i][ladr + 0], opn_regs[i][ladr + 1], opn_regs[i][ladr + 2], opn_regs[i][ladr + 3],
2169 opn_regs[i][ladr + 4], opn_regs[i][ladr + 5], opn_regs[i][ladr + 6], opn_regs[i][ladr + 7],
2170 opn_regs[i][ladr + 8], opn_regs[i][ladr + 9], opn_regs[i][ladr + 10], opn_regs[i][ladr + 11],
2171 opn_regs[i][ladr + 12], opn_regs[i][ladr + 13], opn_regs[i][ladr + 14], opn_regs[i][ladr + 15]);
2175 this->out_debug_log(_T("Load State: MAINIO: id=%d stat=%s\n"), this_device_id, (mb) ? _T("OK") : _T("NG"));