AltairZ80: Add Z80 Interrupt Mode register (IM.)

This commit is contained in:
Howard M. Harte 2020-12-12 20:43:21 -08:00
parent d0c009504b
commit 898d7cbdbb

View file

@ -224,6 +224,7 @@ UNIT cpu_unit = {
int32 DE1_S; /* alternate DE register */
int32 HL1_S; /* alternate HL register */
int32 IFF_S; /* Interrupt Flip Flop */
int32 IM_S; /* Interrupt Mode register */
int32 IR_S; /* Interrupt (upper) / Refresh (lower) register */
int32 AX_S; /* AX register (8086) */
int32 BX_S; /* BX register (8086) */
@ -289,8 +290,8 @@ static int32 switcherPort = SWITCHCPU_DEFAULT;
static struct idev oldSwitcherDevice = { NULL, NULL };
// CPU_INDEX_8080 is defined in altairz80_defs.h
#define CPU_INDEX_8086 26
#define CPU_INDEX_M68K 53
#define CPU_INDEX_8086 27
#define CPU_INDEX_M68K 54
REG cpu_reg[] = {
// 8080 and Z80 registers
@ -309,165 +310,168 @@ REG cpu_reg[] = {
// Z80 registers
{ HRDATAD (IX, IX_S, 16, "Z80 IX register")
}, /* 8 */
{ HRDATAD (IY, IY_S, 16, "Z80 IY register")
}, /* 9 */
{ HRDATAD (AF1, AF1_S, 16, "Z80 Alternate Accumulator Flag register")
}, /* 10 */
{ HRDATAD (BC1, BC1_S, 16, "Z80 Alternate BC register")
}, /* 11 */
{ HRDATAD (DE1, DE1_S, 16, "Z80 Alternate DE register")
}, /* 12 */
{ HRDATAD (HL1, HL1_S, 16, "Z80 Alternate HL register")
}, /* 13 */
{ GRDATAD (IFF, IFF_S, 2, 2, 0, "Z80 Interrupt Flip Flop register")
}, /* 6 */
{ HRDATAD (IR, IR_S, 16, "Z80 Interrupt (upper) / Refresh (lower) register")
{ HRDATAD (IY, IY_S, 16, "Z80 IY register")
}, /* 7 */
{ HRDATAD (AF1, AF1_S, 16, "Z80 Alternate Accumulator Flag register")
}, /* 8 */
{ HRDATAD (BC1, BC1_S, 16, "Z80 Alternate BC register")
}, /* 9 */
{ HRDATAD (DE1, DE1_S, 16, "Z80 Alternate DE register")
}, /* 10 */
{ HRDATAD (HL1, HL1_S, 16, "Z80 Alternate HL register")
}, /* 11 */
{ GRDATAD (IFF, IFF_S, 2, 2, 0, "Z80 Interrupt Flip Flop register")
}, /* 12 */
{ HRDATAD (IM, IM_S, 2, "Z80 Interrupt Mode register")
}, /* 13 */
{ HRDATAD (IR, IR_S, 16, "Z80 Interrupt (upper) / Refresh (lower) register")
}, /* 14 */
// 8086 registers
{ HRDATAD (AX, AX_S, 16, "8086 AX register")
}, /* 14 8086 */
}, /* 15 8086 */
{ GRDATAD (AL, AX_S, 16, 8, 0, "8086 low bits of AX register")
}, /* 15 8086, low 8 bits of AX */
}, /* 16 8086, low 8 bits of AX */
{ GRDATAD (AH, AX_S, 16, 8, 8, "8086 high bits of AX register")
}, /* 16 8086, high 8 bits of AX */
}, /* 17 8086, high 8 bits of AX */
{ HRDATAD (BX, BX_S, 16, "8086 BX register")
}, /* 17 8086 */
}, /* 18 8086 */
{ GRDATAD (BL, BX_S, 16, 8, 0, "8086 low bits of BX register")
}, /* 18 8086, low 8 bits of BX */
}, /* 19 8086, low 8 bits of BX */
{ GRDATAD (BH, BX_S, 16, 8, 8, "8086 high bits of BX register")
}, /* 19 8086, high 8 bits of BX */
}, /* 20 8086, high 8 bits of BX */
{ HRDATAD (CX, CX_S, 16, "8086 CX register")
}, /* 20 8086 */
}, /* 21 8086 */
{ GRDATAD (CL, CX_S, 16, 8, 0, "8086 low bits of CX register")
}, /* 21 8086, low 8 bits of CX */
}, /* 22 8086, low 8 bits of CX */
{ GRDATAD (CH, CX_S, 16, 8, 8, "8086 high bits of CX register")
}, /* 22 8086, high 8 bits of CX */
}, /* 23 8086, high 8 bits of CX */
{ HRDATAD (DX, DX_S, 16, "8086 DX register")
}, /* 23 8086 */
}, /* 24 8086 */
{ GRDATAD (DL, DX_S, 16, 8, 0, "8086 low bits of DX register")
}, /* 24 8086, low 8 bits of DX */
}, /* 25 8086, low 8 bits of DX */
{ GRDATAD (DH, DX_S, 16, 8, 8, "8086 high bits of DX register")
}, /* 25 8086, high 8 bits of DX */
}, /* 26 8086, high 8 bits of DX */
{ HRDATAD (PCX, PCX_S, 16 + MAXBANKSLOG2, "8086 Program Counter register")
}, /* 26 8086, Program Counter */
}, /* 27 8086, Program Counter */
{ HRDATAD (SPX, SPX_S, 16, "8086 Stack Pointer register")
}, /* 27 8086, Stack Pointer */
}, /* 28 8086, Stack Pointer */
{ HRDATAD (BP, BP_S, 16, "8086 Base Pointer register")
}, /* 28 8086, Base Pointer */
}, /* 29 8086, Base Pointer */
{ HRDATAD (SI, SI_S, 16, "8086 Source Index register")
}, /* 29 8086, Source Index */
}, /* 30 8086, Source Index */
{ HRDATAD (DI, DI_S, 16, "8086 Destination Index register")
}, /* 30 8086, Destination Index */
}, /* 31 8086, Destination Index */
{ HRDATAD (CS, CS_S, 16, "8086 Code Segment register")
}, /* 31 8086, Code Segment */
}, /* 32 8086, Code Segment */
{ HRDATAD (DS, DS_S, 16, "8086 Data Segment register")
}, /* 32 8086, Data Segment */
}, /* 33 8086, Data Segment */
{ HRDATAD (ES, ES_S, 16, "8086 Extra Segment register")
}, /* 33 8086, Extra Segment */
}, /* 34 8086, Extra Segment */
{ HRDATAD (SS, SS_S, 16, "8086 Stack Segment register")
}, /* 34 8086, Stack Segment */
}, /* 35 8086, Stack Segment */
{ HRDATAD (FLAGS, FLAGS_S, 16, "8086 Flag register")
}, /* 35 8086, FLAGS */
}, /* 36 8086, FLAGS */
{ HRDATAD (IP, IP_S, 16, "8086 Instruction Pointer register"),
REG_RO }, /* 36 8086, set via PC */
REG_RO }, /* 37 8086, set via PC */
// M68K registers
{ HRDATAD (M68K_D0, m68k_registers[M68K_REG_D0], 32, "M68K D0 register"),
}, /* 37 M68K, D0 */
}, /* 38 M68K, D0 */
{ HRDATAD (M68K_D1, m68k_registers[M68K_REG_D1], 32, "M68K D1 register"),
}, /* 38 M68K, D1 */
}, /* 39 M68K, D1 */
{ HRDATAD (M68K_D2, m68k_registers[M68K_REG_D2], 32, "M68K D2 register"),
}, /* 39 M68K, D2 */
}, /* 40 M68K, D2 */
{ HRDATAD (M68K_D3, m68k_registers[M68K_REG_D3], 32, "M68K D3 register"),
}, /* 40 M68K, D3 */
}, /* 41 M68K, D3 */
{ HRDATAD (M68K_D4, m68k_registers[M68K_REG_D4], 32, "M68K D4 register"),
}, /* 41 M68K, D4 */
}, /* 42 M68K, D4 */
{ HRDATAD (M68K_D5, m68k_registers[M68K_REG_D5], 32, "M68K D5 register"),
}, /* 42 M68K, D5 */
}, /* 43 M68K, D5 */
{ HRDATAD (M68K_D6, m68k_registers[M68K_REG_D6], 32, "M68K D6 register"),
}, /* 43 M68K, D6 */
}, /* 44 M68K, D6 */
{ HRDATAD (M68K_D7, m68k_registers[M68K_REG_D7], 32, "M68K D7 register"),
}, /* 44 M68K, D7 */
}, /* 45 M68K, D7 */
{ HRDATAD (M68K_A0, m68k_registers[M68K_REG_A0], 32, "M68K A0 register"),
}, /* 45 M68K, A0 */
}, /* 46 M68K, A0 */
{ HRDATAD (M68K_A1, m68k_registers[M68K_REG_A1], 32, "M68K A1 register"),
}, /* 46 M68K, A1 */
}, /* 47 M68K, A1 */
{ HRDATAD (M68K_A2, m68k_registers[M68K_REG_A2], 32, "M68K A2 register"),
}, /* 47 M68K, A2 */
}, /* 48 M68K, A2 */
{ HRDATAD (M68K_A3, m68k_registers[M68K_REG_A3], 32, "M68K A3 register"),
}, /* 48 M68K, A3 */
}, /* 49 M68K, A3 */
{ HRDATAD (M68K_A4, m68k_registers[M68K_REG_A4], 32, "M68K A4 register"),
}, /* 49 M68K, A4 */
}, /* 50 M68K, A4 */
{ HRDATAD (M68K_A5, m68k_registers[M68K_REG_A5], 32, "M68K A5 register"),
}, /* 50 M68K, A5 */
}, /* 51 M68K, A5 */
{ HRDATAD (M68K_A6, m68k_registers[M68K_REG_A6], 32, "M68K A6 register"),
}, /* 51 M68K, A6 */
}, /* 52 M68K, A6 */
{ HRDATAD (M68K_A7, m68k_registers[M68K_REG_A7], 32, "M68K A7 register"),
}, /* 52 M68K, A7 */
}, /* 53 M68K, A7 */
{ HRDATAD (M68K_PC, m68k_registers[M68K_REG_PC], 32, "M68K Program Counter register"),
}, /* 53 M68K, PC */
}, /* 54 M68K, PC */
{ HRDATAD (M68K_SR, m68k_registers[M68K_REG_SR], 32, "M68K Status Register"),
}, /* 54 M68K, SR */
}, /* 55 M68K, SR */
{ HRDATAD (M68K_SP, m68k_registers[M68K_REG_SP], 32, "M68K Stack Pointer register"),
}, /* 55 M68K, SP */
}, /* 56 M68K, SP */
{ HRDATAD (M68K_USP, m68k_registers[M68K_REG_USP], 32, "M68K User Stack Pointer register"),
}, /* 56 M68K, USP */
}, /* 57 M68K, USP */
{ HRDATAD (M68K_ISP, m68k_registers[M68K_REG_ISP], 32, "M68K Interrupt Stack Pointer register"),
}, /* 57 M68K, ISP */
}, /* 58 M68K, ISP */
{ HRDATAD (M68K_MSP, m68k_registers[M68K_REG_MSP], 32, "M68K Master Stack Pointer register"),
}, /* 58 M68K, MSP */
}, /* 59 M68K, MSP */
{ HRDATAD (M68K_SFC, m68k_registers[M68K_REG_SFC], 32, "M68K Source Function Code register"),
}, /* 59 M68K, SFC */
}, /* 60 M68K, SFC */
{ HRDATAD (M68K_DFC, m68k_registers[M68K_REG_DFC], 32, "M68K Destination Function Code register"),
}, /* 60 M68K, DFC */
}, /* 61 M68K, DFC */
{ HRDATAD (M68K_VBR, m68k_registers[M68K_REG_VBR], 32, "M68K Vector Base Register"),
}, /* 61 M68K, VBR */
}, /* 62 M68K, VBR */
{ HRDATAD (M68K_CACR, m68k_registers[M68K_REG_CACR], 32, "M68K Cache Control Register"),
}, /* 62 M68K, CACR */
}, /* 63 M68K, CACR */
{ HRDATAD (M68K_CAAR, m68k_registers[M68K_REG_CAAR], 32, "M68K Cache Address Register"),
}, /* 63 M68K, CAAR */
}, /* 64 M68K, CAAR */
{ HRDATAD (M68K_PREF_ADDR, m68k_registers[M68K_REG_PREF_ADDR], 32, "M68K Last Prefetch Address register"),
}, /* 64 M68K, PREF_ADDR */
}, /* 65 M68K, PREF_ADDR */
{ HRDATAD (M68K_PREF_DATA, m68k_registers[M68K_REG_PREF_DATA], 32, "M68K Last Prefetch Data register"),
}, /* 65 M68K, PREF_DATA */
}, /* 66 M68K, PREF_DATA */
{ HRDATAD (M68K_PPC, m68k_registers[M68K_REG_PPC], 32, "M68K Previous Proram Counter register"),
}, /* 66 M68K, PPC */
}, /* 67 M68K, PPC */
{ HRDATAD (M68K_IR, m68k_registers[M68K_REG_IR], 32, "M68K Instruction Register"),
}, /* 67 M68K, IR */
}, /* 68 M68K, IR */
{ HRDATAD (M68K_CPU_TYPE, m68k_registers[M68K_REG_CPU_TYPE], 32, "M68K CPU Type register"),
REG_RO }, /* 68 M68K, CPU_TYPE */
REG_RO }, /* 69 M68K, CPU_TYPE */
// Pseudo registers
{ FLDATAD (OPSTOP, cpu_unit.flags, UNIT_CPU_V_OPSTOP, "Stop on invalid operation pseudo register"),
REG_HRO }, /* 69 */
REG_HRO }, /* 70 */
{ HRDATAD (SR, SR, 8, "Front panel switches pseudo register"),
}, /* 70 */
{ HRDATAD (BANK, bankSelect, MAXBANKSLOG2, "Active bank pseudo register"),
}, /* 71 */
{ HRDATAD (COMMON, common, 32, "Starting address of common memory pseudo register"),
{ HRDATAD (BANK, bankSelect, MAXBANKSLOG2, "Active bank pseudo register"),
}, /* 72 */
{ HRDATAD (SWITCHERPORT, switcherPort, 8, "I/O port for CPU switcher pseudo register"),
{ HRDATAD (COMMON, common, 32, "Starting address of common memory pseudo register"),
}, /* 73 */
{ DRDATAD (CLOCK, clockFrequency, 32, "Clock frequency in kHz for 8080 / Z80 pseudo register"),
{ HRDATAD (SWITCHERPORT, switcherPort, 8, "I/O port for CPU switcher pseudo register"),
}, /* 74 */
{ DRDATAD (SLICE, sliceLength, 16, "Length of time slice for 8080 / Z80 pseudo register"),
{ DRDATAD (CLOCK, clockFrequency, 32, "Clock frequency in kHz for 8080 / Z80 pseudo register"),
}, /* 75 */
{ DRDATAD (SLICE, sliceLength, 16, "Length of time slice for 8080 / Z80 pseudo register"),
}, /* 76 */
{ DRDATAD (TSTATES, executedTStates, 32, "Executed t-states for 8080 / Z80 pseudo register"),
REG_RO }, /* 76 */
{ HRDATAD (CAPACITY,cpu_unit.capac, 32, "Size of RAM pseudo register"),
REG_RO }, /* 77 */
{ HRDATAD (PREVCAP, previousCapacity, 32, "Previous size of RAM pseudo register"),
{ HRDATAD (CAPACITY,cpu_unit.capac, 32, "Size of RAM pseudo register"),
REG_RO }, /* 78 */
{ HRDATAD (PREVCAP, previousCapacity, 32, "Previous size of RAM pseudo register"),
REG_RO }, /* 79 */
{ BRDATAD (PCQ, pcq, 16, 16, PCQ_SIZE, "Program counter circular buffer for 8080 /Z80 pseudo register"),
REG_RO + REG_CIRC }, /* 79 */
REG_RO + REG_CIRC }, /* 80 */
{ DRDATAD (PCQP, pcq_p, PCQ_SIZE_LOG2, "Circular buffer head for 8080 / Z80 pseudo register"),
REG_HRO }, /* 80 */
REG_HRO }, /* 81 */
{ HRDATAD (WRU, sim_int_char, 8, "Interrupt character pseudo register"),
}, /* 81 */
{ HRDATAD(COMMONLOW,common_low, 1, "If set, use low memory for common area"),
}, /* 82 */
{ HRDATAD(COMMONLOW,common_low, 1, "If set, use low memory for common area"),
}, /* 83 */
{ NULL }
};
@ -4787,6 +4791,7 @@ static t_stat sim_instr_mmu (void) {
break;
case 0x46: /* IM 0 */
IM_S = 0;
tStates += 8; /* interrupt mode 0 */
break;
@ -4869,6 +4874,7 @@ static t_stat sim_instr_mmu (void) {
break;
case 0x56: /* IM 1 */
IM_S = 1;
tStates += 8; /* interrupt mode 1 */
break;
@ -4908,6 +4914,7 @@ static t_stat sim_instr_mmu (void) {
break;
case 0x5e: /* IM 2 */
IM_S = 2;
tStates += 8; /* interrupt mode 2 */
break;