diff --git a/ICL1900/icl1900_cpu.c b/ICL1900/icl1900_cpu.c index fdf5624..87144e0 100644 --- a/ICL1900/icl1900_cpu.c +++ b/ICL1900/icl1900_cpu.c @@ -133,6 +133,7 @@ uint32 SR3; /* Typewriter O/P */ uint32 SR64; /* Interrupt status */ uint32 SR65; /* Interrupt status */ uint32 adrmask; /* Mask for addressing memory */ +uint32 memmask; /* Memory address range mask */ uint8 loading; /* Loading bootstrap */ @@ -335,7 +336,7 @@ uint8 Mem_test(uint32 addr) { SR64 |= B1; return 1; } - addr &= adrmask; + addr &= memmask; if (addr > MEMSIZE) { SR64 |= B1; return 1; @@ -363,7 +364,7 @@ uint8 Mem_read(uint32 addr, uint32 *data, uint8 flag) { SR64 |= B1; return 1; } - addr &= adrmask; + addr &= memmask; if (addr > MEMSIZE) { SR64 |= B1; return 1; @@ -391,7 +392,7 @@ uint8 Mem_write(uint32 addr, uint32 *data, uint8 flag) { SR64 |= B1; return 1; } - addr &= adrmask; + addr &= memmask; if (addr > MEMSIZE) { SR64 |= B1; return 1; @@ -410,6 +411,7 @@ sim_instr(void) int e1,e2; /* Temp for exponents */ int f; /* Used to hold flags */ + memmask = (CPU_TYPE < TYPE_C1) ? M15: M22; adrmask = (Mode & AM22) ? M22 : M15; reason = chan_set_devs(); @@ -471,21 +473,22 @@ intr: Mem_write(RD+9, &RA, 0); } } - RA = RC & adrmask; - if (BV) - RA |= B0; + RA = RC & memmask; if (io_flags & EXT_IO) { if (BCarry) RA |= B1; } else { + RC &= M15; if (Zero) RA |= B8; } + if (BV) + RA |= B0; Mem_write(RD+8, &RA, 0); for (n = 0; n < 8; n++) Mem_write(RD+n, &XR[n], 0); BV = BCarry = Mode = Zero = 0; - adrmask = (Mode & AM22) ? M22 : M15; + adrmask = M15; RC = 020; PIP = 0; } @@ -511,7 +514,7 @@ fetch: hst[hst_p].e = exe_mode; hst[hst_p].mode = Mode; } - RC = (RC + 1) & adrmask; + RC = (RC + 1) & ((Mode & (EJM|AM22)) ? M22: M15); goto intr; } obey: @@ -522,14 +525,10 @@ obey: if (RF >= 050 && RF < 0100) { RA = XR[RX]; RM = RB = temp & 077777; - if ((Mode & EJM) && (RF & 1) == 0) { + /* Handle PC relative addressing */ + if ((Mode & EJM) != 0 && (RF & 1) == 0) { RB = RB | ((RB & 020000) ? 017740000 : 0); /* Sign extend RB */ -//fprintf(stderr, "Rel B: %08o PC=%08o -> ", RB, RC); - RB = (RB + RC) & adrmask; -//fprintf(stderr, " %08o\n\r", RC); - } - if (PIP && ((Mode & EJM) == 0 || (RF & 1) == 0)) { - RB = (RB + RP) & adrmask; + RB = (RB + RC) & M22; } } else { RA = XR[RX]; @@ -558,7 +557,7 @@ obey: hst[hst_p].e = exe_mode; hst[hst_p].mode = Mode; } - RC = (RC + 1) & adrmask; + RC = (RC + 1) & ((Mode & (EJM|AM22)) ? M22: M15); goto intr; } if (RF & 010) { @@ -589,9 +588,9 @@ obey: hst[hst_p].mode = Mode; } - /* Advance to next location */ - if (RF != 023) - RC = (RC + 1) & adrmask; + /* Advance to next location, except on OBEY order */ + if (RF != OP_OBEY) + RC = (RC + 1) & ((Mode & (EJM|AM22)) ? M22: M15); OIP = 0; switch (RF) { @@ -1147,15 +1146,16 @@ dvd_zero: case OP_CALL: /* Call Subroutine */ case OP_CALL1: RA = RC; - if (BV) - RA |= B0; if ((Mode & (AM22|EJM)) == 0) { + RA &= adrmask; if (Zero) RA |= B8; } else { if (Zero) RA |= B1; } + if (BV) + RA |= B0; BV = 0; BCarry = 0; XR[RX] = RA; @@ -1165,22 +1165,20 @@ branch: SR64 |= B2; break; } - if ((Mode & EJM) != 0) { - if ((RF & 1) != 0) { - RB &= 037777; -//fprintf(stderr, "Rep: %08o ->", RB); - if (Mem_read(RB, &RB, 0)) { - goto intr; - } -//fprintf(stderr, " %08o \n\r", RB); - RB &= adrmask; - if (OPIP) - RB = (RB + RP) & adrmask; + /* Handle replace jump */ + if ((Mode & EJM) != 0 && (RF & 1) != 0) { + RB &= 037777; + if (Mem_read(RB, &RB, 0)) { + goto intr; } } + /* Handle SMO */ + if (OPIP) + RB = (RB + RP) & adrmask; if (hst_lnt) { /* history enabled? */ hst[hst_p].ea = RB; } + /* Don't transfer if address not valid */ if (Mem_test(RB)) goto intr; /* Monitor mode 2 -> Exec Mon */ @@ -1191,6 +1189,10 @@ branch: M[temp & adrmask] = RB; M[262] = (temp & ~ 0177) + ((temp + 1) & 0177); } + if ((Mode & (EJM|AM22)) == 0) + RB &= M15; + else + RB &= M22; RC = RB; break; @@ -1217,11 +1219,15 @@ branch: if (hst_lnt) { /* history enabled? */ hst[hst_p].ea = RA; } - if (Mem_read(RA, &temp, 0)) { /* Verify memory location accessable */ + if ((Mode & (EJM|AM22)) == 0) + RA &= M15; + else + RA &= M22; + if (Mem_test(RA)) { /* Verify memory location accessable */ goto intr; } - RC = RA & adrmask; - goto obey; + RC = RA; + break; case OP_BRN: /* Branch unconditional */ case OP_BRN1: @@ -1512,19 +1518,19 @@ norm1: RK = RB; RB = XR[(RX+1) & 07]; do { - if (Mem_read(RA, &RT, 1)) { + if (Mem_read(RA & adrmask, &RT, 1)) { goto intr; } m = (RA >> 22) & 3; RT = (RT >> (6 * (3 - m))) & 077; - if (Mem_read(RB, &RS, 1)) { + if (Mem_read(RB & adrmask, &RS, 1)) { goto intr; } m = (RB >> 22) & 3; m = 6 * (3 - m); RS &= ~(077 << m); RS |= (RT & 077) << m; - if (Mem_write(RB, &RS, 1)) { + if (Mem_write(RB & adrmask, &RS, 1)) { goto intr; } RA += 020000000; @@ -2200,7 +2206,7 @@ fexp: RG |= (RA & 07); Mode = RA & 077; } - adrmask = (Mode & AM22) ? M22 : M15; + adrmask = (Mode & (AM22)) ? M22 : M15; //fprintf(stderr, "Load C=%08o limit: %08o D:=%08o %02o\n\r", RC, RL, RD, Mode); if (RF & 1) /* Check if 172 or 173 order code */ break; @@ -2223,7 +2229,7 @@ fexp: if (RA & B3) Zero = 1; } - RC &= adrmask; + RC &= (Mode & (EJM|AM22)) ? M22 : M15; /* Restore floating point ACC from D12/D13 */ Mem_read(RD+12, &faccl, 0); /* Restore F.P.U. */ Mem_read(RD+13, &facch, 0); /* Restore F.P.U. */ @@ -2234,7 +2240,7 @@ fexp: case 0174: /* Send control character to peripheral */ if (exe_mode) { chan_send_cmd(RB, RA & 07777, &RT); -fprintf(stderr, "CMD C=%08o %04o %04o %08o\n\r", RC, RT, RB, RA); +//fprintf(stderr, "CMD C=%08o %04o %04o %08o\n\r", RC, RT, RB, RA); m = (m == 0) ? 3 : (XR[m] >> 22) & 3; m = 6 * (3 - m); RT = (RT & 077) << m; @@ -2246,12 +2252,12 @@ fprintf(stderr, "CMD C=%08o %04o %04o %08o\n\r", RC, RT, RB, RA); /* Fall through */ case 0175: /* Null operation in Executive mode */ if (exe_mode) { -fprintf(stderr, "CMD 175 C=%08o %04o %08o\n\r", RC, RB, RA); +//fprintf(stderr, "CMD 175 C=%08o %04o %08o\n\r", RC, RB, RA); break; } case 0176: if (exe_mode) { -fprintf(stderr, "CMD 176 C=%08o %04o %08o\n\r", RC, RB, RA); +//fprintf(stderr, "CMD 176 C=%08o %04o %08o\n\r", RC, RB, RA); break; } /* Fall through */ @@ -2297,7 +2303,7 @@ voluntary: Mem_write(RD+n, &XR[n], 0); Zero = Mode = 0; BCarry = BV = 0; - adrmask = (Mode & AM22) ? M22 : M15; + adrmask = M15; XR[1] = RB; XR[2] = temp; RC = 040; diff --git a/ICL1900/icl1900_eds8.c b/ICL1900/icl1900_eds8.c index 3335e86..f5a8650 100644 --- a/ICL1900/icl1900_eds8.c +++ b/ICL1900/icl1900_eds8.c @@ -354,6 +354,7 @@ t_stat eds8_svc (UNIT *uptr) break; } + sim_debug(DEBUG_DATA, &eds8_dev, "RSUP: %08o\n", word); uptr->HDSEC += 9; /* Bump sector number, if more then 8, will bump head */ uptr->HDSEC &= 0367; /* If empty buffer, fill */ @@ -425,6 +426,7 @@ t_stat eds8_svc (UNIT *uptr) } for (i = 0; i < WD_SEC; i++) { + sim_debug(DEBUG_DATA, &eds8_dev, "Data: %d <%08o\n", i, eds8_buffer[i]); if (eor = chan_input_word(dev, &eds8_buffer[i], 0)) { /* Terminate */ uptr->CMD &= ~(EDS8_RUN|EDS8_SK|EDS8_BUSY); @@ -546,6 +548,7 @@ t_stat eds8_svc (UNIT *uptr) for (i = 0; i < WD_SEC; i++) { if (eor = chan_output_word(dev, &eds8_buffer[i], 0)) break; + sim_debug(DEBUG_DATA, &eds8_dev, "Data: %d >%08o\n", i, eds8_buffer[i]); } da = ((((uptr->CYL * HD_CYL) + ((uptr->HDSEC >> 4) & 017)) * SECT_TRK) + diff --git a/ICL1900/icl1900_mt.c b/ICL1900/icl1900_mt.c index 96187f7..f648abe 100644 --- a/ICL1900/icl1900_mt.c +++ b/ICL1900/icl1900_mt.c @@ -90,6 +90,7 @@ #define ST2_ROWS 00300 /* Number of rows read */ #define ST2_BLNK 00400 /* Blank Tape */ +#define ST2_TM 00706 /* Tape Mark */ #define STQ_TERM 001 /* Operation terminated */ #define STQ_WRP 002 /* Write ring present */ @@ -155,8 +156,9 @@ void mt_cmd(int dev, uint32 cmd, uint32 *resp) { sim_debug(DEBUG_CMD, &mt_dev, "Cmd: qual unit=%d %04o\n", mt_drive, cmd); cmd = uptr->CMD & ~MT_QUAL; } else { + cmd &= 077; switch(cmd & 070) { - case 000: if (cmd > 1) + case 000: if (cmd > 0) cmd |= MT_QUAL; break; case 010: if (cmd < 016) @@ -167,14 +169,13 @@ void mt_cmd(int dev, uint32 cmd, uint32 *resp) { if (mt_busy == 0) *resp |= STQ_CTL_RDY; if ((uptr->flags & UNIT_ATT) != 0) { - if (uptr->STATUS == 0) + if ((uptr->CMD & MT_BUSY) == 0) *resp |= STQ_TPT_RDY; if (!sim_tape_wrp(uptr)) *resp |= STQ_WRP; if (uptr->STATUS & 07776 || (uptr->CMD & MT_BUSY) == 0) *resp |= STQ_P1; } - uptr->STATUS &= ~1; chan_clr_done(dev); } else if (cmd == SEND_P) { if ((uptr->flags & UNIT_ATT) != 0) { @@ -187,7 +188,7 @@ void mt_cmd(int dev, uint32 cmd, uint32 *resp) { uptr->STATUS &= 07700; } else if (cmd == SEND_P2) { if ((uptr->flags & UNIT_ATT) != 0) - *resp = (uptr->STATUS >> 6) & 037; + *resp = (uptr->STATUS >> 6) & 077; uptr->STATUS = 0; } sim_debug(DEBUG_STATUS, &mt_dev, "Status: unit:=%d %02o %02o\n", mt_drive, cmd, *resp); @@ -255,7 +256,7 @@ t_stat mt_svc (UNIT *uptr) sim_debug(DEBUG_DETAIL, dptr, " error %d\n", r); uptr->STATUS = STQ_TERM; if (r == MTSE_TMK) - uptr->STATUS |= ST1_WARN; + uptr->STATUS |= ST2_TM; else if (r == MTSE_WRP) uptr->STATUS |= ST1_ERR; else if (r == MTSE_EOM) @@ -271,6 +272,7 @@ t_stat mt_svc (UNIT *uptr) sim_debug(DEBUG_DETAIL, dptr, "Block %d chars\n", reclen); } stop = 0; + /* Grab three chars off buffer */ word = 0; for(i = 16; i >= 0; i-=8) { @@ -341,7 +343,7 @@ t_stat mt_svc (UNIT *uptr) /* If empty buffer, fill */ if (BUF_EMPTY(uptr)) { if (sim_tape_bot(uptr)) { - uptr->STATUS = ST1_WARN|STQ_TERM; + uptr->STATUS = ST1_WARN|ST1_ERR; uptr->CMD = 0; mt_busy = 0; chan_set_done(dev); @@ -353,9 +355,7 @@ t_stat mt_svc (UNIT *uptr) sim_debug(DEBUG_DETAIL, dptr, " error %d\n", r); uptr->STATUS = STQ_TERM; if (r == MTSE_TMK) - uptr->STATUS |= ST1_WARN; - else if (r == MTSE_WRP) - uptr->STATUS |= ST1_ERR; + uptr->STATUS |= ST2_TM; else if (r == MTSE_EOM) uptr->STATUS |= ST1_WARN; else @@ -369,15 +369,16 @@ t_stat mt_svc (UNIT *uptr) uptr->hwmark = reclen; sim_debug(DEBUG_DETAIL, dptr, "Block %d chars\n", reclen); } - /* Grab three chars off buffer */ - word = 0; - for(i = 0; i <= 16; i+=8) { - word |= (uint32)mt_buffer[--uptr->POS] << i; - if (uptr->POS == 0) { - stop = 1; - break; - } + + /* Grab three chars off buffer */ + word = 0; + for(i = 0; i <= 16; i+=8) { + word |= (uint32)mt_buffer[--uptr->POS] << i; + if (uptr->POS == 0) { + stop = 1; + break; } + } sim_debug(DEBUG_DATA, dptr, "unit=%d read %08o\n", unit, word); eor = chan_input_word(dev, &word, 0); if (eor || uptr->POS == 0) { @@ -405,6 +406,7 @@ t_stat mt_svc (UNIT *uptr) if (r == MTSE_TMK) { uptr->POS++; sim_debug(DEBUG_DETAIL, dptr, "MARK\n"); + uptr->STATUS = ST2_TM; sim_activate(uptr, 50); } else if (r == MTSE_EOM) { uptr->POS++; @@ -417,7 +419,6 @@ t_stat mt_svc (UNIT *uptr) break; case 2: sim_debug(DEBUG_DETAIL, dptr, "Skip rec unit=%d done\n", unit); - uptr->STATUS = (ST1_WARN & uptr->STATUS) | STQ_TERM; uptr->CMD = 0; mt_busy = 0; chan_set_done(dev); @@ -427,7 +428,7 @@ t_stat mt_svc (UNIT *uptr) case MT_WTM: if (uptr->POS == 0) { if (sim_tape_wrp(uptr)) { - uptr->STATUS = ST1_ERR|STQ_TERM; + uptr->STATUS = ST1_ERR; uptr->CMD = 0; mt_busy = 0; chan_set_done(dev); @@ -438,10 +439,9 @@ t_stat mt_svc (UNIT *uptr) } else { sim_debug(DEBUG_DETAIL, dptr, "Write Mark unit=%d\n", unit); r = sim_tape_wrtmk(uptr); - uptr->STATUS = STQ_TERM; if (r != MTSE_OK) - uptr->STATUS |= ST1_ERR; - uptr->CMD = 0; + uptr->STATUS = ST1_ERR; + uptr->CMD = 0; mt_busy = 0; chan_set_done(dev); } @@ -451,7 +451,7 @@ t_stat mt_svc (UNIT *uptr) switch (uptr->POS ) { case 0: if (sim_tape_bot(uptr)) { - uptr->STATUS = ST1_WARN|STQ_TERM; + uptr->STATUS = ST1_WARN|ST1_ERR; uptr->CMD = 0; mt_busy = 0; chan_set_done(dev); @@ -463,11 +463,12 @@ t_stat mt_svc (UNIT *uptr) case 1: sim_debug(DEBUG_DETAIL, dptr, "Backspace rec unit=%d ", unit); r = sim_tape_sprecr(uptr, &reclen); - /* We don't set EOF on BSR */ - uptr->STATUS = STQ_TERM; - if (r == MTSE_TMK || r == MTSE_BOT) { - uptr->STATUS |= ST1_WARN; - } + if (r == MTSE_TMK) + uptr->STATUS = ST2_TM; + else if (r == MTSE_BOT) + uptr->STATUS = ST1_WARN|ST1_ERR; + else + uptr->STATUS = ST1_WARN; uptr->CMD = 0; mt_busy = 0; chan_set_done(dev); @@ -478,7 +479,7 @@ t_stat mt_svc (UNIT *uptr) switch (uptr->POS ) { case 0: if (sim_tape_bot(uptr)) { - uptr->STATUS = ST1_WARN|STQ_TERM; + uptr->STATUS = ST1_WARN|ST1_ERR; uptr->CMD = 0; mt_busy = 0; chan_set_done(dev); @@ -490,9 +491,12 @@ t_stat mt_svc (UNIT *uptr) case 1: sim_debug(DEBUG_DETAIL, dptr, "Backspace rec unit=%d ", unit); r = sim_tape_sprecr(uptr, &reclen); - /* We don't set EOF on BSR */ if (r == MTSE_TMK || r == MTSE_BOT) { uptr->POS++; + if (r == MTSE_TMK) + uptr->STATUS = ST2_TM; + if (r == MTSE_BOT) + uptr->STATUS = ST1_WARN|ST1_ERR; sim_activate(uptr, 50); } else { sim_debug(DEBUG_DETAIL, dptr, "%d \n", reclen); @@ -500,7 +504,6 @@ t_stat mt_svc (UNIT *uptr) } break; case 2: - uptr->STATUS = STQ_TERM; uptr->CMD = 0; mt_busy = 0; chan_set_done(dev); @@ -515,8 +518,8 @@ t_stat mt_svc (UNIT *uptr) } else { sim_debug(DEBUG_DETAIL, dptr, "Rewind unit=%d\n", unit); r = sim_tape_rewind(uptr); - uptr->CMD = 0; - uptr->STATUS = STQ_TERM; + uptr->CMD = 0; + uptr->STATUS = 0; chan_set_done(dev); } break;