OSDN Git Service

[FM7][DISPLAY] Force SYNC submemory and mainmemory to SUBCPU.
[csp-qt/common_source_project-fm7.git] / source / src / vm / fm7 / fm7_mainio.h
1 /*
2  * FM-7 Main I/O [fm7_mainio.h]
3  *
4  * Author: K.Ohta <whatisthis.sowhat _at_ gmail.com>
5  * License: GPLv2
6  * History:
7  *   Jan 03, 2015 : Initial
8  *
9  */
10
11 #ifndef _VM_FM7_MAINIO_H_
12 #define _VM_FM7_MAINIO_H_
13
14 #include "../device.h"
15 #include "../memory.h"
16 #include "../mc6809.h"
17 #include "../z80.h"
18 #include "../mb8877.h"
19 #include "../disk.h"
20 #include "../datarec.h"
21 #include "../pcm1bit.h"
22 #include "../ym2203.h"
23
24 #include "fm7_common.h"
25
26
27 class FM7_MAINIO : public DEVICE {
28  private:
29         bool opn_psg_77av;
30         bool beep_flag;
31         bool beep_snd;
32         int event_beep;  
33         int event_timerirq;  
34  protected:
35         VM* p_vm;
36         EMU* p_emu;
37
38         int irq_count;
39         int firq_count;
40         int nmi_count;
41         /* FD00: R */
42         bool clock_fast; // bit0 : maybe dummy
43         uint8 kbd_bit8;  // bit7
44         /* FD00: W */
45         bool lpt_strobe;  // bit6 : maybe dummy entry
46         bool lpt_slctin;  // bit7 : maybe dummy entry
47
48         /* FD01 : R */
49         uint8 kbd_bit7_0;
50         /* FD01: W */
51         uint8 lpt_outdata; // maybe dummy.
52
53         /* FD02 : R */
54         bool cmt_indat; // bit7
55         bool cmt_invert; // Invert signal
56         bool lpt_det2; // bit5 : maybe dummy.
57         bool lpt_det1; // bit4 : maybe dummy.
58         bool lpt_pe;   // bit3 : maybe dummy.
59         bool lpt_ackng_inv; // bit2 : maybe dummy.
60         bool lpt_error_inv; // bit1 : maybe dummy.
61         bool lpt_busy; // bit0 : maybe dummy.
62         /* FD02 : W */
63         uint8 irqmask_reg0; // bit7-4, bit2-0 , '1' is enable.  '0' is disable.
64         // 7-4 :  RS232C / SYNDET,RXRDY,TXRDY,MFD
65         // 2 : TIMER
66         // 1 : PRINTER
67         // 0 : KEYBOARD
68         bool irqmask_mfd; // bit4: "0" = mask.
69         bool irqmask_timer; // bit2: "0" = mask.
70         bool irqmask_printer; // bit1: "0" = mask.
71         bool irqmask_keyboard; // bit0: "0" = mask.
72   
73         /* FD03: R */
74         uint8 irqstat_reg0; // bit 3-0, '0' is happened, '1' is not happened.
75         // bit3 : extended interrupt
76         // bit2-0: Same as FD02 : W .
77         /* FD03 : W , '1' = ON*/
78
79         /* FD04 : R */
80         bool stat_fdmode_2hd; //  R/W : bit6, '0' = 2HD, '1' = 2DD. FM-77 Only.
81         bool stat_kanjirom;    //  R/W : bit5, '0' = sub, '1' = main. FM-77 Only.
82         bool stat_400linecard;//  R/W : bit4, '0' = connected. FM-77 Only.
83         bool stat_400linemode; // R/W : bit3, '0' = 400line, '1' = 200line.
84         bool firq_break_key; // bit1, ON = '0'.
85         bool firq_sub_attention; // bit0, ON = '0'.
86         /* FD04 : W */
87         bool intmode_fdc; // bit2, '0' = normal, '1' = SFD.
88
89         /* FD05 : R */
90         bool sub_busy; // bit7 : '0' = READY '1' = BUSY.
91         bool extdet_neg; // bit0 : '1' = none , '0' = exists.
92         /* FD05 : W */
93         bool sub_cancel; // bit6 : '1' Cancel req.
94         bool z80_sel;    // bit0 : '1' = Z80. Maybe only FM-7/77.
95
96         /* FD06 : R/W : RS-232C */
97         /* FD07 : R/W : RS-232C */
98         bool intstat_syndet;
99         bool intstat_rxrdy;
100         bool intstat_txrdy;
101         /* FD08 : Grafic pen, not implemented */
102         /* FD09 : Grafic pen, not implemented */
103         /* FD0A : Grafic pen, not implemented */
104         /* FD0B : R */
105         bool stat_bootsw_basic; // bit0 : '0' = BASIC '1' = DOS. Only 77AV/20/40.
106         uint32 bootmode;
107         /* FD0D : W */
108         uint8 psg_cmdreg; // PSG Register, Only bit 0-1 at FM-7/77 , 3-0 at FM-77AV series. Maybe dummy.
109
110         /* FD0E : R */
111         uint8 psg_statreg; // PSG data. maybe dummy.
112         uint32 psg_address;
113         uint32 psg_data;
114         bool  psg_bus_high; // true when bus = high inpedance.
115   
116         /* FD0F : R/W */
117         bool stat_romrammode; // R(true) = ROM, W(false) = RAM.
118         
119         /* FD15 / FD46 / FD51 : W */
120         bool connect_opn; // [0]
121         bool connect_whg; // [1]
122         bool connect_thg; // [2]
123         bool psg_shared_opn;
124         uint32 opn_address[3];
125         uint32 opn_data[3];
126         uint32 opn_stat[3];
127         uint8  opn_cmdreg[3]; // OPN register, bit 3-0, maybe dummy.
128
129         /* OPN Joystick */
130         uint32 joyport_a;
131         uint32 joyport_b;
132
133         /* FD47 */
134         bool intstat_whg;   // bit3 : OPN interrupt. '0' = happened.
135         /* FD53 */
136         bool intstat_thg;   // bit3 : OPN interrupt. '0' = happened.
137
138         
139         /* FD17 : R */
140         bool intstat_opn;   // bit3 : OPN interrupt. '0' = happened.
141         bool intstat_mouse; // bit2 : Mouse interrupt (not OPN-Mouse?), '0' = happened.
142         /* FD17 : W */
143         bool mouse_enable; // bit2 : '1' = enable.
144         
145         /* FD18 : R */
146         bool connect_fdc;
147         uint8 fdc_statreg;
148         /* FD18 : W */
149         uint8 fdc_cmdreg;
150         
151         /* FD19 : R/W */
152         uint8 fdc_trackreg;
153         
154         /* FD1A : R/W */
155         uint8 fdc_sectreg;
156         
157         /* FD1B : R/W */
158         uint8 fdc_datareg;
159         
160         /* FD1C : R/W */
161         uint8 fdc_headreg; // bit0, '0' = side0, '1' = side1
162         
163         /* FD1D : R/W */
164         bool fdc_motor; // bit7 : '1' = ON, '0' = OFF
165         uint8 fdc_drvsel; // bit 1-0
166         
167         /* FD1F : R */
168         bool fdc_drq; // bit7 : '1' = ON
169         bool fdc_irq; // bit6 : '1' = ON
170         uint8 irqstat_fdc;
171         
172         /* FD20,FD21 : W */
173         bool connect_kanjiroml1;
174         uint8 kaddress_hi; // FD20 : ADDRESS OF HIGH.
175         uint8 kaddress_lo; // FD21 : ADDRESS OF LOW.
176 #ifdef _FM77AV_VARIANTS
177         bool connect_kanjiroml2;
178         uint8 kaddress_hi_l2; // FD20 : ADDRESS OF HIGH.
179         uint8 kaddress_lo_l2; // FD21 : ADDRESS OF LOW.
180 #endif  
181         /* FD20, FD21 : R */
182         
183         /* FD37 : W */
184         uint8 multipage_disp;   // bit6-4 : to display : GRB. '1' = disable, '0' = enable.
185         uint8 multipage_access; // bit2-0 : to access  : GRB. '1' = disable, '0' = enable.
186 #if defined(_FM77) || defined(_FM77L2) || defined(_FM77L4) || defined(_FM77AV_VARIANTS)
187         /* FD93: bit0 */
188         bool bootram;
189 #endif  
190         
191         void set_clockmode(uint8 flags);
192         uint8 get_clockmode(void);
193         void set_cmt_motor(uint8 flag);
194         bool get_cmt_motor(void);
195         
196         virtual uint8 get_port_fd00(void);
197         virtual void  set_port_fd00(uint8 data);
198         virtual uint32 get_keyboard(void); // FD01
199         virtual uint8 get_port_fd02(void);
200         virtual void set_port_fd02(uint8 val);
201         virtual uint8 get_irqstat_fd03(void);
202         virtual uint8 get_extirq_fd17(void);
203         virtual void set_ext_fd17(uint8 data);
204
205         virtual void set_beep(uint32 data); // fd03
206   
207         void do_irq(bool flag);
208         void set_irq_timer(bool flag);
209         void set_irq_printer(bool flag);
210         void set_irq_keyboard(bool flag);
211         void set_irq_opn(bool flag);
212         void set_irq_mfd(bool flag);
213         void set_drq_mfd(bool flag);
214         virtual void set_keyboard(uint32 data);  
215
216         // FD04
217         void do_firq(bool flag);
218         void do_nmi(bool flag);
219           
220         void set_break_key(bool pressed);
221         void set_sub_attention(bool flag);
222           
223         uint8 get_fd04(void);
224         void  set_fd04(uint8 val);
225         uint8 get_fd05(void);
226         void  set_fd05(uint8 val);
227         
228         virtual void set_extdet(bool flag);
229         // FD0D
230         void set_psg(uint8 val);
231         uint8 get_psg(void);
232         // FD0E
233         void set_psg_cmd(uint8 cmd);
234         
235         void write_fd0f(void)  {
236                 stat_romrammode = false;
237         }
238         uint8 read_fd0f(void)  {
239                 stat_romrammode = true;
240                 return 0xff;
241         }
242         bool get_rommode_fd0f(void) {
243                 return stat_romrammode;
244         }
245    
246         // OPN
247         void set_opn(int index, uint8 val);
248         uint8 get_opn(int index);
249         void set_opn_cmd(int index, uint8 cmd);
250   
251         uint8 get_extirq_whg(void);
252         uint8 get_extirq_thg(void);
253         uint32 update_joystatus(int index);
254         
255         void write_kanjiaddr_lo(uint8 addr);
256         void write_kanjiaddr_hi(uint8 addr);
257         uint8 read_kanjidata_left(void);
258         uint8 read_kanjidata_right(void);
259           
260           // FDC
261         uint8 get_fdc_fd1c(void);
262         void set_fdc_fd1c(uint8 val);
263         void set_fdc_fd1d(uint8 val);
264         
265         uint8 get_fdc_stat(void);
266         void set_fdc_cmd(uint8 val);
267         uint8 fdc_getdrqirq(void);
268
269         virtual void set_fdc_track(uint8 val);
270         virtual uint8 get_fdc_track(void);
271
272         uint8 get_fdc_motor(void);
273           
274         void set_fdc_sector(uint8 val);
275
276         uint8 get_fdc_sector(void);
277           
278         void set_fdc_data(uint8 val);
279         uint8 get_fdc_data(void);
280         /* Devices */
281         DEVICE* opn[3]; // 0=OPN 1=WHG 2=THG
282         DEVICE* psg; // FM-7/77 ONLY
283         
284         DEVICE* drec;
285         DEVICE* pcm1bit;
286         DEVICE* fdc;
287         //FM7_PRINTER *printer;
288         //FM7_RS232C *rs232c;
289         /* */
290         MEMORY *kanjiclass1;
291         MEMORY *kanjiclass2;
292         DEVICE *display;
293         MC6809 *maincpu;
294         MEMORY *mainmem;
295         MC6809 *subcpu;
296         Z80 *z80;
297  public:
298         FM7_MAINIO(VM* parent_vm, EMU* parent_emu) : DEVICE(parent_vm, parent_emu)
299         {
300                 int i;
301                 p_vm = parent_vm;
302                 p_emu = parent_emu;
303                 kanjiclass1 = NULL;
304                 kanjiclass2 = NULL;
305                 opn_psg_77av = false;
306                 nmi_count = 0;
307                 firq_count = 0;
308                 irq_count = 0;
309                 // FD00
310                 clock_fast = true;
311                 kbd_bit8 = 0;  // bit7
312                 lpt_strobe = false;
313                 lpt_slctin = false;
314                 // FD01
315                 kbd_bit7_0 = 0x00;
316                 lpt_outdata = 0x00;
317                 // FD02
318                 cmt_indat = false; // bit7
319                 cmt_invert = false; // Invert signal
320                 lpt_det2 = false;
321                 lpt_det1 = false;
322                 lpt_pe = false;
323                 lpt_ackng_inv = false;
324                 lpt_error_inv = false;
325                 lpt_busy = false;
326                 // FD04
327                 stat_fdmode_2hd = false; //  R/W : bit6, '0' = 2HD, '1' = 2DD. FM-77 Only.
328                 stat_kanjirom = true;    //  R/W : bit5, '0' = sub, '1' = main. FM-77 Only.
329                 stat_400linecard = false;//  R/W : bit4, '0' = connected. FM-77 Only.
330                 stat_400linemode = false; // R/W : bit3, '0' = 400line, '1' = 200line.
331                 firq_break_key = false; // bit1, ON = '0'.
332                 firq_sub_attention = false; // bit0, ON = '0'.
333                 intmode_fdc = false; // bit2, '0' = normal, '1' = SFD.
334                 // FD05
335                 sub_busy = false;
336                 extdet_neg = false;
337                 z80_sel = false;    // bit0 : '1' = Z80. Maybe only FM-7/77.
338                 // FD06,07
339                 intstat_syndet = false;
340                 intstat_rxrdy = false;
341                 intstat_txrdy = false;
342                 // FD0B
343                 stat_bootsw_basic = true; // bit0 : '0' = BASIC '1' = DOS. Only 77AV/20/40.
344                 bootmode = 0x00;
345                 // FD0D
346                 psg_cmdreg = 0;
347                 psg_statreg = 0x00;
348                 psg_address = 0x00;
349                 psg_data = 0x00;
350                 psg_bus_high = false;
351                 // FD0F
352                 stat_romrammode = true; // ROM ON
353                 // FD15/ FD46 / FD51
354                 connect_opn = false;
355                 connect_whg = false;
356                 connect_thg = false;
357                 psg_shared_opn = false;
358                 
359                 for(i = 0; i < 3; i++) {
360                         opn_address[i] = 0x00;
361                         opn_data[i] = 0x00;
362                         opn_cmdreg[i] = 0;
363                 }
364                 joyport_a = 0x00;
365                 joyport_b = 0x00;
366                 
367                 intstat_whg = false;
368                 intstat_thg = false;
369                 // FD17
370                 intstat_opn = false;
371                 intstat_mouse = false;
372                 mouse_enable = false;
373                 // FD18-FD1F
374                 connect_fdc = false;
375                 fdc_statreg = 0x00;
376                 fdc_cmdreg = 0x00;
377                 fdc_trackreg = 0x00;
378                 fdc_sectreg = 0x00;
379                 fdc_datareg = 0x00;
380                 fdc_headreg = 0x00;
381                 fdc_drvsel = 0x00;
382                 fdc_motor = false;
383                 fdc_drq = false;
384                 fdc_irq = false;
385                 irqstat_fdc = 0;
386                 // FD20, FD21, FD22, FD23
387                 connect_kanjiroml1 = false;
388 #if defined(_FM77AV_VARIANTS)
389                 // FD2C, FD2D, FD2E, FD2F
390                 connect_kanjiroml2 = false;
391 #endif          
392 #if defined(_FM77) || defined(_FM77L2) || defined(_FM77L4) || defined(_FM77AV_VARIANTS)
393                 bootram = false;
394 #endif          
395         }
396         ~FM7_MAINIO(){}
397         
398         void initialize(void);
399         void write_data8(uint32 addr, uint32 data);
400         uint32 read_data8(uint32 addr);
401
402         void write_signal(int id, uint32 data, uint32 mask);
403         uint32 read_signal(uint32 addr);
404         void event_callback(int event_id, int err);
405         void reset(void);
406
407         void set_context_kanjirom_class1(MEMORY *p)
408         {
409                 kanjiclass1 = p;
410                 if(p != NULL) connect_kanjiroml1 = true;
411         }
412         void set_context_kanjirom_class2(MEMORY *p)
413         {
414 #if defined(_FM77AV_VARIANTS)
415                 kanjiclass2 = p;
416                 if(p != NULL) connect_kanjiroml2 = true;
417 #endif
418         }
419         void set_context_beep(DEVICE *p)
420         {
421                 pcm1bit = p;
422         }
423         void set_context_datarec(DEVICE *p)
424         {
425                 drec = p;
426         }
427         void set_context_opn(DEVICE *p, int ch)
428         {
429                 if((ch < 0) || (ch > 2)) return;
430                 if(p != NULL) {
431                         switch(ch) {
432                                 case 0:
433                                         connect_opn = true;
434                                         break;
435                                 case 1:
436                                         connect_whg = true;
437                                         break;
438                                 case 2:
439                                         connect_thg = true;
440                                         break;
441                         }
442                 }
443                 opn[ch] = p;
444                 if(connect_opn) {
445                         extdet_neg = true;
446                 }
447                 if(connect_whg) {
448                         extdet_neg = true;
449                 }
450                 if(connect_thg) {
451                         extdet_neg = true;
452                 }
453         }
454         void set_context_psg(DEVICE *p)
455         {
456                 psg = p;
457         }
458         void set_context_fdc(DEVICE *p){
459                 if(p == NULL) {
460                         connect_fdc = false;
461                 } else {
462                         connect_fdc = true;
463                 }
464                 if(connect_fdc) {
465                         extdet_neg = true;
466                 }
467                 printf("FDC: connect=%d\n", connect_fdc);
468                 fdc = p;
469         }
470         void set_context_maincpu(MC6809 *p){
471                 maincpu = p;
472         }
473         void set_context_mainmem(MEMORY *p){
474                 mainmem = p;
475         }
476         void set_context_subcpu(MC6809 *p){
477                 subcpu = p;
478         }
479         void set_context_display(DEVICE *p){
480                 display = p;
481         }
482         void set_context_z80cpu(Z80 *p){
483                 z80 = p;
484         }
485
486 };
487 #endif