SEL32: Do general code cleanup to remove unused code.

SEL32: Update Ping and ICMP support code to use correct packet size.
SEL32: Update SetupNet script to support latest Fedora release.
SEL32: Improve disk write speed.
SEL32: Add .tap file reassignent support in sel32_mt.c.
This commit is contained in:
Jim Bevier 2023-09-08 16:15:18 -07:00 committed by Paul Koning
parent 8b9613ae81
commit 25b79339fd
18 changed files with 840 additions and 809 deletions

View file

@ -80,9 +80,7 @@
uint32 channels = MAX_CHAN; /* maximum number of channels */ uint32 channels = MAX_CHAN; /* maximum number of channels */
int subchannels = SUB_CHANS; /* maximum number of subchannel devices */ int subchannels = SUB_CHANS; /* maximum number of subchannel devices */
//int irq_pend = 0; /* pending interrupt flag */
//extern uint32 *M; /* cpu/ipu main memory */
extern uint32 SPAD[]; /* cpu SPAD memory */ extern uint32 SPAD[]; /* cpu SPAD memory */
extern uint32 CPUSTATUS; /* CPU status word */ extern uint32 CPUSTATUS; /* CPU status word */
extern uint32 INTS[]; /* Interrupt status flags */ extern uint32 INTS[]; /* Interrupt status flags */
@ -518,6 +516,7 @@ int32 load_ccw(CHANP *chp, int32 tic_ok)
sim_debug(DEBUG_XIO, &cpu_dev, sim_debug(DEBUG_XIO, &cpu_dev,
"load_ccw @%06x entry chan_status[%02x]=%04x\n", "load_ccw @%06x entry chan_status[%02x]=%04x\n",
chp->chan_caw, chan, chp->chan_status); chp->chan_caw, chan, chp->chan_status);
#ifdef TEST_FOR_IOCL_CHANGE #ifdef TEST_FOR_IOCL_CHANGE
/* see if iocla or iocd has changed since start */ /* see if iocla or iocd has changed since start */
if (!loading && (chp->chan_info & INFO_SIOCD)) { /* see if 1st IOCD in channel prog */ if (!loading && (chp->chan_info & INFO_SIOCD)) { /* see if 1st IOCD in channel prog */
@ -1401,9 +1400,6 @@ missing:
} }
#endif #endif
/* 05122021 cpu halts in diag if this code is enabled */
/* disabling this code allows TE to be echoed at debugger prompt */
#ifndef TEST_FOR_HSDP_PUT_BACK_05122021
/* channel not busy and ready to go, check for any status ready */ /* channel not busy and ready to go, check for any status ready */
/* see if any status ready to post */ /* see if any status ready to post */
if (FIFO_Num(chsa&0x7f00)) { if (FIFO_Num(chsa&0x7f00)) {
@ -1439,7 +1435,6 @@ missing:
sim_debug(DEBUG_IRQ, &cpu_dev, sim_debug(DEBUG_IRQ, &cpu_dev,
"SIOT chsa %04x Nothing to post FIFO #%1x irq %02x inch %06x chan_icba %06x icb+20 %08x\n", "SIOT chsa %04x Nothing to post FIFO #%1x irq %02x inch %06x chan_icba %06x icb+20 %08x\n",
chsa, FIFO_Num(chsa), inta, incha, chan_icb, RMW(chan_icb+20)); chsa, FIFO_Num(chsa), inta, incha, chan_icb, RMW(chan_icb+20));
#endif
/* check for a Command or data chain operation in progresss */ /* check for a Command or data chain operation in progresss */
if ((chp->chan_byte & BUFF_BUSY) && (chp->chan_byte != BUFF_POST)) { if ((chp->chan_byte & BUFF_BUSY) && (chp->chan_byte != BUFF_POST)) {
@ -1602,7 +1597,8 @@ missing:
/* we have an error or user requested interrupt, return status */ /* we have an error or user requested interrupt, return status */
sim_debug(DEBUG_EXP, &cpu_dev, "startxio store csw CC2 chan %04x status %08x\n", sim_debug(DEBUG_EXP, &cpu_dev, "startxio store csw CC2 chan %04x status %08x\n",
chan, chp->chan_status); chan, chp->chan_status);
/*NOTE*//* if we have an error, we would loop forever if the CC bit was set */ /* NOTE */
/* if we have an error, we would loop forever if the CC bit was set */
/* the only way to stop was to do a kill */ /* the only way to stop was to do a kill */
chp->ccw_flags &= ~(FLAG_DC|FLAG_CC); /* reset chaining bits */ chp->ccw_flags &= ~(FLAG_DC|FLAG_CC); /* reset chaining bits */
/* DIAG's want CC1 with memory access error */ /* DIAG's want CC1 with memory access error */
@ -2067,7 +2063,7 @@ missing:
} }
sim_debug(DEBUG_XIO, &cpu_dev, "RSCHNL return CC1 lchsa %02x chan %02x inta %04x\n", sim_debug(DEBUG_XIO, &cpu_dev, "RSCHNL return CC1 lchsa %02x chan %02x inta %04x\n",
lchsa, chan, inta); lchsa, chan, inta);
*status = CC1BIT; /* request accepted, no status, so CC1 TRY THIS */ *status = CC1BIT; /* request accepted, no status, so CC1 */
return SCPE_OK; /* All OK */ return SCPE_OK; /* All OK */
} }
@ -2136,7 +2132,8 @@ missing:
if ((dptr->flags & DEV_DIS) || ((uptr->flags & UNIT_DIS) && if ((dptr->flags & DEV_DIS) || ((uptr->flags & UNIT_DIS) &&
((uptr->flags & UNIT_SUBCHAN) == 0))) { ((uptr->flags & UNIT_SUBCHAN) == 0))) {
sim_debug(DEBUG_EXP, &cpu_dev, sim_debug(DEBUG_EXP, &cpu_dev,
"HIO chsa %04x device/unit disabled, CC3 returned flags %08x\n", chsa, uptr->flags); "HIO chsa %04x device/unit disabled, CC3 returned flags %08x\n",
chsa, uptr->flags);
*status = CC3BIT; /* not attached, so error CC3 */ *status = CC3BIT; /* not attached, so error CC3 */
return SCPE_OK; /* not found, CC3 */ return SCPE_OK; /* not found, CC3 */
} }
@ -2218,7 +2215,7 @@ missing:
"HIO END3 chsa %04x cmd %02x ccw_flags %04x status %04x\n", "HIO END3 chsa %04x cmd %02x ccw_flags %04x status %04x\n",
chsa, chp->ccw_cmd, chp->ccw_flags, *status); chsa, chp->ccw_cmd, chp->ccw_flags, *status);
#ifndef GIVE_INT_ON_NOT_BUSY_121420_03082021 /* GIVE_INT_ON_NOT_BUSY */
chp->chan_byte = BUFF_DONE; /* we are done */ chp->chan_byte = BUFF_DONE; /* we are done */
sim_debug(DEBUG_EXP, &cpu_dev, sim_debug(DEBUG_EXP, &cpu_dev,
"HIO BUFF_DONE2 chp %p chan_byte %04x\n", chp, chp->chan_byte); "HIO BUFF_DONE2 chp %p chan_byte %04x\n", chp, chp->chan_byte);
@ -2235,7 +2232,6 @@ missing:
chp->chan_status = 0; /* no status anymore */ chp->chan_status = 0; /* no status anymore */
chp->ccw_cmd = 0; /* no command anymore */ chp->ccw_cmd = 0; /* no command anymore */
irq_pend = 1; /* flag to test for int condition */ irq_pend = 1; /* flag to test for int condition */
#endif
return SCPE_OK; /* No CC's all OK */ return SCPE_OK; /* No CC's all OK */
} }
@ -2356,7 +2352,8 @@ missing:
if ((dptr->flags & DEV_DIS) || ((uptr->flags & UNIT_DIS) && if ((dptr->flags & DEV_DIS) || ((uptr->flags & UNIT_DIS) &&
((uptr->flags & UNIT_SUBCHAN) == 0))) { ((uptr->flags & UNIT_SUBCHAN) == 0))) {
sim_debug(DEBUG_EXP, &cpu_dev, sim_debug(DEBUG_EXP, &cpu_dev,
"GRIO chsa %04x device/unit disabled, CC3 returned flags %08x\n", chsa, uptr->flags); "GRIO chsa %04x device/unit disabled, CC3 returned flags %08x\n",
chsa, uptr->flags);
*status = CC3BIT; /* not attached, so error CC3 */ *status = CC3BIT; /* not attached, so error CC3 */
return SCPE_OK; /* not found, CC3 */ return SCPE_OK; /* not found, CC3 */
} }
@ -2370,7 +2367,6 @@ missing:
return SCPE_OK; /* CC4 all OK */ return SCPE_OK; /* CC4 all OK */
} }
// NOW ON 05142021 */
/* device does not have stop_io entry, so stop the I/O */ /* device does not have stop_io entry, so stop the I/O */
/* check for a Command or data chain operation in progresss */ /* check for a Command or data chain operation in progresss */
/* set the return to CC3BIT & CC4BIT causes infinite loop in MPX1X */ /* set the return to CC3BIT & CC4BIT causes infinite loop in MPX1X */
@ -2416,8 +2412,6 @@ missing:
/* If this is console, debugger wants CC3 & CC4 = 0 */ /* If this is console, debugger wants CC3 & CC4 = 0 */
if (chan == 0x7e) { if (chan == 0x7e) {
/* returning No CC's causes MPX1X to loop forever */
/* so restore returning CC1 */
*status = 0; /* return no CC's */ *status = 0; /* return no CC's */
} else { } else {
/* diags want unsupported transaction for disk */ /* diags want unsupported transaction for disk */
@ -2531,7 +2525,8 @@ t_stat chan_boot(uint16 chsa, DEVICE *dptr) {
UNIT *uptr = find_unit_ptr(chsa); /* find pointer to unit on channel */ UNIT *uptr = find_unit_ptr(chsa); /* find pointer to unit on channel */
CHANP *chp = 0; CHANP *chp = 0;
sim_debug(DEBUG_EXP, &cpu_dev, "Channel Boot chan/device addr %04x SNS %08x\n", chsa, uptr->u5); sim_debug(DEBUG_EXP, &cpu_dev,
"Channel Boot chan/device addr %04x SNS %08x\n", chsa, uptr->u5);
fflush(sim_deb); fflush(sim_deb);
if (dibp == 0) /* if no channel or device, error */ if (dibp == 0) /* if no channel or device, error */
@ -2626,8 +2621,9 @@ uint32 cont_chan(uint16 chsa)
/* we have an error or user requested interrupt, return status */ /* we have an error or user requested interrupt, return status */
sim_debug(DEBUG_EXP, &cpu_dev, "cont_chan error, store csw chsa %04x status %08x\n", sim_debug(DEBUG_EXP, &cpu_dev, "cont_chan error, store csw chsa %04x status %08x\n",
chsa, chp->chan_status); chsa, chp->chan_status);
/*NOTE*/ /* if we have an error, we would loop forever if the CC bit was set */ /* NOTE */
/* the only way to stop was to do a kill */ /* if we have an error, we would loop forever if the CC bit was set */
/* the only way to stop was to do a kill of sel32 */
chp->ccw_flags &= ~(FLAG_DC|FLAG_CC); /* reset chaining bits */ chp->ccw_flags &= ~(FLAG_DC|FLAG_CC); /* reset chaining bits */
/* DIAG's want CC1 with memory access error */ /* DIAG's want CC1 with memory access error */
if (chp->chan_status & STATUS_PCHK) { if (chp->chan_status & STATUS_PCHK) {

View file

@ -62,7 +62,6 @@ int32 rtc_lvl = 0x18; /* rtc interrupt level */
/* clock can be enabled / disabled */ /* clock can be enabled / disabled */
/* default to 60 HZ RTC */ /* default to 60 HZ RTC */
//718UNIT rtc_unit = { UDATA (&rtc_srv, UNIT_IDLE, 0), 16666, UNIT_ADDR(0x7F06)};
UNIT rtc_unit = { UDATA (&rtc_srv, UNIT_CLK, 0), 16666, UNIT_ADDR(0x7F06)}; UNIT rtc_unit = { UDATA (&rtc_srv, UNIT_CLK, 0), 16666, UNIT_ADDR(0x7F06)};
REG rtc_reg[] = { REG rtc_reg[] = {
@ -111,10 +110,6 @@ t_stat rtc_srv (UNIT *uptr)
#endif #endif
/* if clock disabled, do not do interrupts */ /* if clock disabled, do not do interrupts */
if (((rtc_dev.flags & DEV_DIS) == 0) && rtc_pie) { if (((rtc_dev.flags & DEV_DIS) == 0) && rtc_pie) {
int lev = rtc_lvl;
sim_debug(DEBUG_CMD, &rtc_dev,
"RT Clock mfp INTS[%02x] %08x SPAD[%02x] %08x\n",
lev, INTS[lev], lev+0x80, SPAD[lev+0x80]);
sim_debug(DEBUG_CMD, &rtc_dev, sim_debug(DEBUG_CMD, &rtc_dev,
"RT Clock int INTS[%02x] %08x SPAD[%02x] %08x\n", "RT Clock int INTS[%02x] %08x SPAD[%02x] %08x\n",
rtc_lvl, INTS[rtc_lvl], rtc_lvl+0x80, SPAD[rtc_lvl+0x80]); rtc_lvl, INTS[rtc_lvl], rtc_lvl+0x80, SPAD[rtc_lvl+0x80]);
@ -142,7 +137,6 @@ t_stat rtc_srv (UNIT *uptr)
"RT Clock int INTS[%02x] %08x SPAD[%02x] %08x\n", "RT Clock int INTS[%02x] %08x SPAD[%02x] %08x\n",
rtc_lvl, INTS[rtc_lvl], rtc_lvl+0x80, SPAD[rtc_lvl+0x80]); rtc_lvl, INTS[rtc_lvl], rtc_lvl+0x80, SPAD[rtc_lvl+0x80]);
} }
// temp = sim_rtcn_calb(rtc_tps, TMR_RTC); /* timer 0 for RTC */
sim_rtcn_calb(rtc_tps, TMR_RTC); /* timer 0 for RTC */ sim_rtcn_calb(rtc_tps, TMR_RTC); /* timer 0 for RTC */
sim_activate_after(uptr, 1000000/rtc_tps); /* reactivate 16666 tics / sec */ sim_activate_after(uptr, 1000000/rtc_tps); /* reactivate 16666 tics / sec */
return SCPE_OK; return SCPE_OK;
@ -161,7 +155,7 @@ void rtc_setup(uint32 ss, uint32 level)
if (ss == 1) { /* starting? */ if (ss == 1) { /* starting? */
INTS[level] |= INTS_ENAB; /* make sure enabled */ INTS[level] |= INTS_ENAB; /* make sure enabled */
SPAD[level+0x80] |= SINT_ENAB; /* in spad too */ SPAD[level+0x80] |= SINT_ENAB; /* in spad too */
sim_activate(&rtc_unit, 20); /* start us off */ sim_activate(&rtc_unit, 20); /* start us off, will be ignored if active */
sim_debug(DEBUG_CMD, &rtc_dev, sim_debug(DEBUG_CMD, &rtc_dev,
"RT Clock setup enable int %02x rtc_pie %01x ss %01x\n", "RT Clock setup enable int %02x rtc_pie %01x ss %01x\n",
rtc_lvl, rtc_pie, ss); rtc_lvl, rtc_pie, ss);
@ -182,7 +176,8 @@ t_stat rtc_reset(DEVICE *dptr)
{ {
rtc_pie = 0; /* disable pulse */ rtc_pie = 0; /* disable pulse */
/* initialize clock calibration */ /* initialize clock calibration */
sim_activate (&rtc_unit, rtc_unit.wait); /* activate unit */ sim_rtcn_init_unit(&rtc_unit, rtc_unit.wait, TMR_RTC);
sim_activate(&rtc_unit, rtc_unit.wait); /* activate unit, ignored for second reset */
return SCPE_OK; return SCPE_OK;
} }
@ -282,7 +277,6 @@ DEVICE itm_dev = {
NULL, NULL, &itm_reset, /* examine, deposit, reset */ NULL, NULL, &itm_reset, /* examine, deposit, reset */
NULL, NULL, NULL, /* boot, attach, detach */ NULL, NULL, NULL, /* boot, attach, detach */
/* dib, dev flags, debug flags, debug */ /* dib, dev flags, debug flags, debug */
// NULL, DEV_DEBUG|DEV_DIS|DEV_DISABLE, 0, dev_debug,
NULL, DEV_DEBUG, 0, dev_debug, /* dib, dev flags, debug flags, debug */ NULL, DEV_DEBUG, 0, dev_debug, /* dib, dev flags, debug flags, debug */
NULL, NULL, &itm_help, /* ?, ?, help */ NULL, NULL, &itm_help, /* ?, ?, help */
NULL, NULL, &itm_desc, /* ?, ?, description */ NULL, NULL, &itm_desc, /* ?, ?, description */
@ -299,10 +293,9 @@ DEVICE itm_dev = {
t_stat itm_srv (UNIT *uptr) t_stat itm_srv (UNIT *uptr)
{ {
if (itm_pie) { /* interrupt enabled? */ if (itm_pie) { /* interrupt enabled? */
time_t result = time(NULL);
sim_debug(DEBUG_CMD, &itm_dev, sim_debug(DEBUG_CMD, &itm_dev,
"Intv Timer expired status %08x lev %02x cnt %x @ time %08x\n", "Intv Timer expired status %08x lev %02x cnt %x\n",
INTS[itm_lvl], itm_lvl, itm_cnt, (uint32)result); INTS[itm_lvl], itm_lvl, itm_cnt);
if (((INTS[itm_lvl] & INTS_ENAB) || /* make sure enabled */ if (((INTS[itm_lvl] & INTS_ENAB) || /* make sure enabled */
(SPAD[itm_lvl+0x80] & SINT_ENAB)) && /* in spad too */ (SPAD[itm_lvl+0x80] & SINT_ENAB)) && /* in spad too */
(((INTS[itm_lvl] & INTS_ACT) == 0) || /* and not active */ (((INTS[itm_lvl] & INTS_ACT) == 0) || /* and not active */
@ -421,17 +414,7 @@ int32 itm_rdwr(uint32 cmd, int32 cnt, uint32 level)
sim_activate_after_abs_d(&itm_unit, ((double)cnt*1000000)/rtc_tps); sim_activate_after_abs_d(&itm_unit, ((double)cnt*1000000)/rtc_tps);
else { else {
/* use interval timer freq */ /* use interval timer freq */
#ifdef MAYBE_CHANGE_FOR_MPX3X
/* tsm does not run if fake time cnt is used */
/// if (cnt == 0)
/// cnt = 0x52f0;
/* this fixes an extra interrupt being generated on context switch */
/* the value is load for the new task anyway */
/* need to verify that UTX likes it too */
/*4MPX3X*/ sim_activate_after_abs_d(&itm_unit, ((double)(cnt+1)*itm_tick_size_x_100)/100.0);
#else
sim_activate_after_abs_d(&itm_unit, ((double)cnt*itm_tick_size_x_100)/100.0); sim_activate_after_abs_d(&itm_unit, ((double)cnt*itm_tick_size_x_100)/100.0);
#endif
} }
itm_run = 1; /* set timer running */ itm_run = 1; /* set timer running */
} }
@ -607,7 +590,6 @@ int32 itm_rdwr(uint32 cmd, int32 cnt, uint32 level)
/* get simulated negative start time in counts */ /* get simulated negative start time in counts */
temp = temp - itm_strt; /* make into a negative number */ temp = temp - itm_strt; /* make into a negative number */
} }
//extra sim_cancel (&itm_unit); /* cancel timer */
} }
sim_debug(DEBUG_CMD, &itm_dev, sim_debug(DEBUG_CMD, &itm_dev,
"Intv 0x%02x temp value %08x (%08d)\n", cmd, temp, temp); "Intv 0x%02x temp value %08x (%08d)\n", cmd, temp, temp);
@ -657,18 +639,10 @@ void itm_setup(uint32 ss, uint32 level)
itm_cnt = 0; /* no count reset value */ itm_cnt = 0; /* no count reset value */
sim_cancel (&itm_unit); /* not running yet */ sim_cancel (&itm_unit); /* not running yet */
if (ss == 1) { /* starting? */ if (ss == 1) { /* starting? */
#ifdef NOT_HERE_112422
INTS[level] |= INTS_ENAB; /* make sure enabled */
SPAD[level+0x80] |= SINT_ENAB; /* in spad too */
#endif
sim_debug(DEBUG_CMD, &itm_dev, sim_debug(DEBUG_CMD, &itm_dev,
"Intv Timer setup enable int %02x value %08x itm_pie %01x ss %01x\n", "Intv Timer setup enable int %02x value %08x itm_pie %01x ss %01x\n",
itm_lvl, itm_cnt, itm_pie, ss); itm_lvl, itm_cnt, itm_pie, ss);
} else { } else {
#ifdef NOT_HERE_112422
INTS[level] &= ~INTS_ENAB; /* make sure disabled */
SPAD[level+0x80] &= ~SINT_ENAB; /* in spad too */
#endif
sim_debug(DEBUG_CMD, &itm_dev, sim_debug(DEBUG_CMD, &itm_dev,
"Intv Timer setup disable int %02x value %08x itm_pie %01x ss %01x\n", "Intv Timer setup disable int %02x value %08x itm_pie %01x ss %01x\n",
itm_lvl, itm_cnt, itm_pie, ss); itm_lvl, itm_cnt, itm_pie, ss);

View file

@ -31,13 +31,7 @@
/* Constants */ /* Constants */
#define COM_LINES 8 /* lines defined */ #define COM_LINES 8 /* lines defined */
//Change from 500 to 5000 12/02/2021
//Change from 5000 to 4000 12/02/2021
//#define COML_WAIT 500
#define COML_WAIT 4000 #define COML_WAIT 4000
//Change from 1000 to 5000 12/02/2021
//#define COM_WAIT 5000
//#define COM_WAIT 1000
#define COM_WAIT 5000 #define COM_WAIT 5000
#define COM_NUMLIN com_desc.lines /* curr # lines */ #define COM_NUMLIN com_desc.lines /* curr # lines */
@ -302,7 +296,7 @@ DEVICE com_dev = {
&tmxr_ex, &tmxr_dep, &com_reset, NULL, &com_attach, &com_detach, &tmxr_ex, &tmxr_dep, &com_reset, NULL, &com_attach, &com_detach,
/* ctxt is the DIB pointer */ /* ctxt is the DIB pointer */
&com_dib, DEV_MUX|DEV_DISABLE|DEV_DEBUG, 0, dev_debug, &com_dib, DEV_MUX|DEV_DISABLE|DEV_DEBUG, 0, dev_debug,
NULL, NULL, NULL, NULL, NULL, &com_description NULL, NULL, NULL, NULL, NULL, &com_description,
}; };
/* COML data structures /* COML data structures
@ -312,11 +306,8 @@ DEVICE com_dev = {
coml_mod COM modifiers list coml_mod COM modifiers list
*/ */
/*#define UNIT_COML UNIT_ATTABLE|UNIT_DISABLE|UNIT_IDLE */ //#define UNIT_COML UNIT_IDLE|UNIT_DISABLE|TT_MODE_7B
//#define UNIT_COML UNIT_IDLE|UNIT_DISABLE|TT_MODE_UC #define UNIT_COML UNIT_DISABLE|TT_MODE_7B
//#define UNIT_COML UNIT_IDLE|UNIT_DISABLE|TT_MODE_7P
//#define UNIT_COML UNIT_IDLE|UNIT_DISABLE|TT_MODE_8B
#define UNIT_COML UNIT_IDLE|UNIT_DISABLE|TT_MODE_7B
/* channel program information */ /* channel program information */
CHANP coml_chp[COM_LINES*2] = {0}; CHANP coml_chp[COM_LINES*2] = {0};
@ -468,7 +459,6 @@ t_stat coml_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
{ {
DEVICE *dptr = get_dev(uptr); DEVICE *dptr = get_dev(uptr);
int unit = (uptr - dptr->units); int unit = (uptr - dptr->units);
// int unit = (uptr - dptr->units) & 0x7; /* make 0-7 */
UNIT *ruptr = &dptr->units[unit&7]; /* read uptr */ UNIT *ruptr = &dptr->units[unit&7]; /* read uptr */
UNIT *wuptr = &dptr->units[(unit&7)+8]; /* write uptr */ UNIT *wuptr = &dptr->units[(unit&7)+8]; /* write uptr */
uint16 chsa = (((uptr->CMD & LMASK) >> 16) | (chan << 8)); uint16 chsa = (((uptr->CMD & LMASK) >> 16) | (chan << 8));
@ -503,7 +493,6 @@ t_stat coml_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
/* see if DSR is set, if not give unit check error */ /* see if DSR is set, if not give unit check error */
if (((ruptr->SNS & SNS_DSRS) == 0) || ((ruptr->SNS & SNS_CONN) == 0)) { if (((ruptr->SNS & SNS_DSRS) == 0) || ((ruptr->SNS & SNS_CONN) == 0)) {
//YY if ((com_ldsc[unit&7].conn == 0) ||
ruptr->SNS &= ~SNS_RDY; /* status is not ready */ ruptr->SNS &= ~SNS_RDY; /* status is not ready */
wuptr->SNS &= ~SNS_RDY; /* status is not ready */ wuptr->SNS &= ~SNS_RDY; /* status is not ready */
ruptr->SNS |= SNS_CMDREJ; /* command reject */ ruptr->SNS |= SNS_CMDREJ; /* command reject */
@ -537,7 +526,6 @@ t_stat coml_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
/* see if DSR is set, if not give unit check error */ /* see if DSR is set, if not give unit check error */
if (((ruptr->SNS & SNS_DSRS) == 0) || ((ruptr->SNS & SNS_CONN) == 0)) { if (((ruptr->SNS & SNS_DSRS) == 0) || ((ruptr->SNS & SNS_CONN) == 0)) {
//XX if (com_ldsc[unit&7].conn == 0) {
ruptr->SNS &= ~SNS_RDY; /* status is not ready */ ruptr->SNS &= ~SNS_RDY; /* status is not ready */
wuptr->SNS &= ~SNS_RDY; /* status is not ready */ wuptr->SNS &= ~SNS_RDY; /* status is not ready */
ruptr->SNS |= SNS_CMDREJ; /* command reject */ ruptr->SNS |= SNS_CMDREJ; /* command reject */
@ -583,7 +571,6 @@ t_stat coml_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
unit &= 0x7; /* make unit 0-7 */ unit &= 0x7; /* make unit 0-7 */
/* status is in SNS (u5) */ /* status is in SNS (u5) */
/* ACE is in ACE (u4) */ /* ACE is in ACE (u4) */
///*MPX*/ uptr->SNS = 0x03813401;
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"coml_startcmd SENSE chsa %04x: unit %02x Cmd Sense SNS %08x ACE %08x\n", "coml_startcmd SENSE chsa %04x: unit %02x Cmd Sense SNS %08x ACE %08x\n",
@ -622,10 +609,7 @@ t_stat coml_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
/* byte 7 ACE parameters (Revision Level 0x4?) */ /* byte 7 ACE parameters (Revision Level 0x4?) */
// Firmware 0x44 supports RTS flow control */ // Firmware 0x44 supports RTS flow control */
// Firmware 0x45 supports DCD modem control */ // Firmware 0x45 supports DCD modem control */
// ch = 0x44; /* ACE firmware byte 1 */
// ch = 0x45; /* ACE firmware byte 1 */
ch = 0x43; /* ACE firmware byte 1 */ ch = 0x43; /* ACE firmware byte 1 */
// ch = 0x40; /* ACE firmware byte 1 */
chan_write_byte(chsa, &ch); /* write status */ chan_write_byte(chsa, &ch); /* write status */
ruptr->SNS &= ~SNS_RING; /* reset ring attention status */ ruptr->SNS &= ~SNS_RING; /* reset ring attention status */
@ -640,7 +624,6 @@ t_stat coml_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
wuptr->SNS &= ~SNS_MRING; /* reset ring attention status */ wuptr->SNS &= ~SNS_MRING; /* reset ring attention status */
wuptr->SNS &= ~SNS_ASCIICD; /* reset ASCII attention status */ wuptr->SNS &= ~SNS_ASCIICD; /* reset ASCII attention status */
wuptr->SNS &= ~SNS_DELDSR; /* reset attention status */ wuptr->SNS &= ~SNS_DELDSR; /* reset attention status */
//1X wuptr->SNS &= ~SNS_RLSDS; /* reset rec'd line signal detect */
wuptr->SNS &= ~SNS_CMDREJ; /* command reject */ wuptr->SNS &= ~SNS_CMDREJ; /* command reject */
/*MPX*/ wuptr->SNS &= ~SNS_DELTA; /* reset attention status */ /*MPX*/ wuptr->SNS &= ~SNS_DELTA; /* reset attention status */
@ -818,7 +801,6 @@ t_stat comc_srv(UNIT *uptr)
uint8 ch; uint8 ch;
DEVICE *dptr = get_dev(uptr); DEVICE *dptr = get_dev(uptr);
int32 newln, ln, c; int32 newln, ln, c;
// int cmd = uptr->CMD & 0xff;
uint16 chsa = GET_UADDR(coml_unit[0].CMD); /* get channel/sub-addr */ uint16 chsa = GET_UADDR(coml_unit[0].CMD); /* get channel/sub-addr */
/* see if comc attached */ /* see if comc attached */
@ -875,7 +857,7 @@ t_stat comc_srv(UNIT *uptr)
uint16 chsa = GET_UADDR(nuptr->CMD); /* get channel/sub-addr */ uint16 chsa = GET_UADDR(nuptr->CMD); /* get channel/sub-addr */
if (com_ldsc[ln].conn) /* connected? */ if (com_ldsc[ln].conn) /* connected? */
sim_debug(DEBUG_CMD, &com_dev, sim_debug(DEBUG_DETAIL, &com_dev,
"comc_srv conn poll input chsa %04x line %02x SNS %08x ACE %08x\n", "comc_srv conn poll input chsa %04x line %02x SNS %08x ACE %08x\n",
chsa, ln, nuptr->SNS, nuptr->ACE); chsa, ln, nuptr->SNS, nuptr->ACE);
@ -950,12 +932,7 @@ t_stat comc_srv(UNIT *uptr)
sim_debug(DEBUG_DETAIL, &com_dev, sim_debug(DEBUG_DETAIL, &com_dev,
"comc_srv POLL DONE on chsa %04x\n", chsa); "comc_srv POLL DONE on chsa %04x\n", chsa);
/* this says to use 200, but simh really uses 50000 for cnt */
/* changed 12/02/2021 from 200 to 5000 */
// return sim_clock_coschedule(uptr, 200); /* continue poll */
return sim_clock_coschedule(uptr, 5000); /* continue poll */ return sim_clock_coschedule(uptr, 5000); /* continue poll */
// return sim_activate(uptr, 10000); /* continue poll */
// return sim_activate(uptr, 5000); /* continue poll */
} }
/* Unit service - input transfers */ /* Unit service - input transfers */
@ -983,6 +960,8 @@ t_stat comi_srv(UNIT *uptr)
if (uptr->CNT != com_data[ln].incnt) { /* input available */ if (uptr->CNT != com_data[ln].incnt) { /* input available */
/* process any characters */ /* process any characters */
if (ch == 0x7f) /* if rub out, make backspace */
ch = 0x08;
/* this fixes mpx1x time entry on startup */ /* this fixes mpx1x time entry on startup */
if (uptr->CMD & COM_EKO) { /* ECHO requested */ if (uptr->CMD & COM_EKO) { /* ECHO requested */
/* echo the char out */ /* echo the char out */
@ -991,9 +970,11 @@ t_stat comi_srv(UNIT *uptr)
"comi_srv echo char %02x on chsa %04x line %02x cmd %02x ACE %08x\n", "comi_srv echo char %02x on chsa %04x line %02x cmd %02x ACE %08x\n",
ch, chsa, ln, cmd, uptr->ACE); ch, chsa, ln, cmd, uptr->ACE);
// cc = sim_tt_outcvt(c, TT_GET_MODE(coml_unit[ln].flags)); // cc = sim_tt_outcvt(c, TT_GET_MODE(coml_unit[ln].flags));
if (ch != 0x08 && ch != 0x7f) {
tmxr_putc_ln(&com_ldsc[ln], ch); /* output char */ tmxr_putc_ln(&com_ldsc[ln], ch); /* output char */
tmxr_poll_tx(&com_desc); /* poll xmt to send */ tmxr_poll_tx(&com_desc); /* poll xmt to send */
} }
}
if (chan_write_byte(chsa, &ch)) { /* write byte to memory */ if (chan_write_byte(chsa, &ch)) { /* write byte to memory */
/* write error */ /* write error */
cmd = 0; /* no cmd now */ cmd = 0; /* no cmd now */
@ -1019,7 +1000,6 @@ t_stat comi_srv(UNIT *uptr)
cc = ch & 0x7f; /* clear parity bit */ cc = ch & 0x7f; /* clear parity bit */
/* Special char detected? (7 bit read only) */ /* Special char detected? (7 bit read only) */
if (cc == ((uptr->ACE >> 8) & 0xff)) { /* is it spec char */ if (cc == ((uptr->ACE >> 8) & 0xff)) { /* is it spec char */
// uptr->CMD |= COM_SCD; /* set special char detected */
uptr->SNS |= SNS_SPCLCD; /* set special char detected */ uptr->SNS |= SNS_SPCLCD; /* set special char detected */
sim_debug(DEBUG_CMD, &com_dev, sim_debug(DEBUG_CMD, &com_dev,
"comi_srv user ACE %02x wakeup on chsa %04x line %02x cmd %02x ACE %08x\n", "comi_srv user ACE %02x wakeup on chsa %04x line %02x cmd %02x ACE %08x\n",
@ -1056,8 +1036,7 @@ t_stat comi_srv(UNIT *uptr)
if (uptr->CNT == com_data[ln].incnt) { /* input empty */ if (uptr->CNT == com_data[ln].incnt) { /* input empty */
uptr->CMD &= ~COM_INPUT; /* no input available */ uptr->CMD &= ~COM_INPUT; /* no input available */
} }
/* change 02DEC21*/ sim_activate(uptr, uptr->wait); /* wait */ sim_activate(uptr, uptr->wait); /* wait */
// change 02DEC21*/ sim_clock_coschedule(uptr, 1000); /* continue poll */
return SCPE_OK; return SCPE_OK;
} }
/* command is completed */ /* command is completed */
@ -1071,8 +1050,7 @@ t_stat comi_srv(UNIT *uptr)
chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* we done */ chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* we done */
} }
} }
// change 02DEC21 sim_activate(uptr, uptr->wait); /* wait */ sim_clock_coschedule(uptr, 1000); /* continue poll */
/* change 02DEC21*/ sim_clock_coschedule(uptr, 1000); /* continue poll */
return SCPE_OK; return SCPE_OK;
} }
/* not connected, so dump chars on ground */ /* not connected, so dump chars on ground */
@ -1115,7 +1093,6 @@ t_stat como_srv(UNIT *uptr)
uptr->CMD &= LMASK; /* nothing left, command complete */ uptr->CMD &= LMASK; /* nothing left, command complete */
ruptr->SNS &= SNS_DSRS; /* reset DSR */ ruptr->SNS &= SNS_DSRS; /* reset DSR */
ruptr->SNS |= SNS_DELDSR; /* give change status */ ruptr->SNS |= SNS_DELDSR; /* give change status */
// chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* done */
chan_end(chsa, SNS_CHNEND|SNS_DEVEND|SNS_UNITCHK); /* error return */ chan_end(chsa, SNS_CHNEND|SNS_DEVEND|SNS_UNITCHK); /* error return */
return SCPE_OK; /* return */ return SCPE_OK; /* return */
} }
@ -1212,7 +1189,6 @@ t_stat coml_haltio(UNIT *uptr) {
uptr->CNT = 0; /* no I/O yet */ uptr->CNT = 0; /* no I/O yet */
com_data[unit].incnt = 0; /* no input data */ com_data[unit].incnt = 0; /* no input data */
sim_cancel(uptr); /* stop timer */ sim_cancel(uptr); /* stop timer */
// uptr->SNS |= (SNS_RDY|SNS_CONN); /* status is online & ready */
sim_debug(DEBUG_CMD, &coml_dev, sim_debug(DEBUG_CMD, &coml_dev,
"coml_haltio HIO I/O stop chsa %04x cmd = %02x\n", chsa, cmd); "coml_haltio HIO I/O stop chsa %04x cmd = %02x\n", chsa, cmd);
chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* force end */ chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* force end */
@ -1221,7 +1197,6 @@ t_stat coml_haltio(UNIT *uptr) {
uptr->CNT = 0; /* no I/O yet */ uptr->CNT = 0; /* no I/O yet */
com_data[unit].incnt = 0; /* no input data */ com_data[unit].incnt = 0; /* no input data */
uptr->CMD &= LMASK; /* make non-busy */ uptr->CMD &= LMASK; /* make non-busy */
// uptr->SNS |= (SNS_RDY|SNS_CONN); /* status is online & ready */
return SCPE_OK; /* not busy */ return SCPE_OK; /* not busy */
} }

View file

@ -37,7 +37,7 @@
extern uint32 CPUSTATUS; extern uint32 CPUSTATUS;
extern uint32 attention_trap; extern uint32 attention_trap;
#define UNIT_CON UNIT_IDLE | UNIT_DISABLE #define UNIT_CON UNIT_DISABLE
#define CON_WAIT 1000 #define CON_WAIT 1000
#define CMD u3 #define CMD u3
/* Held in u3 is the device command and status */ /* Held in u3 is the device command and status */
@ -116,7 +116,7 @@ MTAB con_mod[] = {
}; };
UNIT con_unit[] = { UNIT con_unit[] = {
{UDATA(&con_srvi, UNIT_CON, 0), CON_WAIT, UNIT_ADDR(0x7EFC)}, /* 0 Input */ {UDATA(&con_srvi, UNIT_CON|UNIT_IDLE, 0), CON_WAIT, UNIT_ADDR(0x7EFC)}, /* 0 Input */
{UDATA(&con_srvo, UNIT_CON, 0), CON_WAIT, UNIT_ADDR(0x7EFD)}, /* 1 Output */ {UDATA(&con_srvo, UNIT_CON, 0), CON_WAIT, UNIT_ADDR(0x7EFD)}, /* 1 Output */
}; };
@ -144,6 +144,7 @@ DIB con_dib = {
DEVICE con_dev = { DEVICE con_dev = {
"CON", con_unit, NULL, con_mod, "CON", con_unit, NULL, con_mod,
NUM_UNITS_CON, 8, 15, 1, 8, 8, NUM_UNITS_CON, 8, 15, 1, 8, 8,
// We must always have a consol
// NULL, NULL, &con_reset, NULL, &con_attach, &con_detach, // NULL, NULL, &con_reset, NULL, &con_attach, &con_detach,
NULL, NULL, &con_reset, NULL, NULL, NULL, NULL, NULL, &con_reset, NULL, NULL, NULL,
&con_dib, DEV_DIS|DEV_DISABLE|DEV_DEBUG, 0, dev_debug &con_dib, DEV_DIS|DEV_DISABLE|DEV_DEBUG, 0, dev_debug
@ -262,8 +263,7 @@ t_stat con_startcmd(UNIT *uptr, uint16 chan, uint8 cmd) {
uptr->CMD |= CON_READ; /* show read mode */ uptr->CMD |= CON_READ; /* show read mode */
uptr->SNS |= (SNS_RDY|SNS_ONLN); /* status is online & ready */ uptr->SNS |= (SNS_RDY|SNS_ONLN); /* status is online & ready */
/* input is polled, so no start needed */ /* input is polled, so no start needed */
sim_cancel(uptr); /* stop input poll */ sim_activate_abs(uptr, 250); /* start us off */
sim_activate(uptr, 250); /* start us off */
return SCPE_OK; /* no status change */ return SCPE_OK; /* no status change */
break; break;
@ -288,9 +288,8 @@ t_stat con_startcmd(UNIT *uptr, uint16 chan, uint8 cmd) {
/* Starting Syslog Daemon */ /* Starting Syslog Daemon */
/* ioi: sio at 801 failed, cc=2, retry=0 */ /* ioi: sio at 801 failed, cc=2, retry=0 */
/* panic: ioi: sio - bad cc */ /* panic: ioi: sio - bad cc */
sim_activate(uptr, 200); /* start us off */ //11523 sim_activate(uptr, 200); /* start us off */
//fail sim_activate(uptr, 230); /* start us off */ sim_activate_abs(uptr, 200); /* start us off */
//fail sim_activate(uptr, 250); /* start us off */
return SCPE_OK; /* no status change */ return SCPE_OK; /* no status change */
break; break;
@ -304,10 +303,10 @@ t_stat con_startcmd(UNIT *uptr, uint16 chan, uint8 cmd) {
(CPUSTATUS & ONIPU)?"IPU":"CPU", uptr->CMD, chsa, cmd); (CPUSTATUS & ONIPU)?"IPU":"CPU", uptr->CMD, chsa, cmd);
/* input is polled, so no start needed */ /* input is polled, so no start needed */
if (unit == 1) { /* doing output */ if (unit == 1) { /* doing output */
sim_activate(uptr, 250); /* start us off */ //11523 sim_activate(uptr, 250); /* start us off */
sim_activate_abs(uptr, 250); /* start us off */
} else { } else {
sim_cancel(uptr); /* stop input poll */ sim_activate_abs(uptr, 250); /* start us off */
sim_activate(uptr, 250); /* start us off */
} }
return SCPE_OK; /* no status change */ return SCPE_OK; /* no status change */
break; break;
@ -350,9 +349,7 @@ t_stat con_srvo(UNIT *uptr) {
unit, uptr->CMD, cmd, con_data[unit].incnt, uptr->u4, mema, M[mema>>2]); unit, uptr->CMD, cmd, con_data[unit].incnt, uptr->u4, mema, M[mema>>2]);
/* now call set_inch() function to write and test inch buffer addresses */ /* now call set_inch() function to write and test inch buffer addresses */
/* 1-256 wd buffer is provided for 128 status dbl words */ tstart = set_inch(uptr, mema, 1); /* new address & 1 entry */
//TRY tstart = set_inch(uptr, mema, 128); /* new address & 128 entries */
tstart = set_inch(uptr, mema, 1); /* new address & 128 entries */
if ((tstart == SCPE_MEM) || (tstart == SCPE_ARG)) { /* any error */ if ((tstart == SCPE_MEM) || (tstart == SCPE_ARG)) { /* any error */
/* we have error, bail out */ /* we have error, bail out */
uptr->SNS |= SNS_CMDREJ; uptr->SNS |= SNS_CMDREJ;
@ -363,13 +360,13 @@ t_stat con_srvo(UNIT *uptr) {
break; break;
} }
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"con_srvo INCH CMD %08x chsa %04x len %02x inch %06x in2 %06x\n", uptr->CMD, chsa, len, mema, M[mema>>2]); "con_srvo INCH CMD %08x chsa %04x len %02x inch %06x in2 %06x\n",
uptr->CMD, chsa, len, mema, M[mema>>2]);
/* WARNING, if SNS_DEVEND is not set, diags fail by looping in CON diag */ /* WARNING, if SNS_DEVEND is not set, diags fail by looping in CON diag */
chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* return OK */ chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* return OK */
break; break;
case CON_NOP: /* 0x03 */ /* NOP has do nothing */ case CON_NOP: /* 0x03 */ /* NOP has do nothing */
//ZZ uptr->CMD &= ~CON_MSK; /* remove old CMD */
uptr->CMD &= LMASK; /* nothing left, command complete */ uptr->CMD &= LMASK; /* nothing left, command complete */
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"con_srvo NOP CMD %08x chsa %04x cmd = %02x\n", uptr->CMD, chsa, cmd); "con_srvo NOP CMD %08x chsa %04x cmd = %02x\n", uptr->CMD, chsa, cmd);
@ -433,8 +430,7 @@ t_stat con_srvi(UNIT *uptr) {
unit, uptr->CMD, cmd, con_data[unit].incnt, uptr->u4, mema, M[mema>>2]); unit, uptr->CMD, cmd, con_data[unit].incnt, uptr->u4, mema, M[mema>>2]);
/* now call set_inch() function to write and test inch buffer addresses */ /* now call set_inch() function to write and test inch buffer addresses */
//TRY tstart = set_inch(uptr, mema, 128); /* new address & 128 entries */ tstart = set_inch(uptr, mema, 1); /* new address & 1 entry */
tstart = set_inch(uptr, mema, 1); /* new address & 128 entries */
if ((tstart == SCPE_MEM) || (tstart == SCPE_ARG)) { /* any error */ if ((tstart == SCPE_MEM) || (tstart == SCPE_ARG)) { /* any error */
/* we have error, bail out */ /* we have error, bail out */
uptr->SNS |= SNS_CMDREJ; uptr->SNS |= SNS_CMDREJ;
@ -447,14 +443,14 @@ t_stat con_srvi(UNIT *uptr) {
con_data[unit].incnt = 0; /* buffer empty */ con_data[unit].incnt = 0; /* buffer empty */
uptr->u4 = 0; /* no I/O yet */ uptr->u4 = 0; /* no I/O yet */
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"con_srvi INCH CMD %08x chsa %04x len %02x inch %06x in2 %06x\n", uptr->CMD, chsa, len, mema, M[mema>>2]); "con_srvi INCH CMD %08x chsa %04x len %02x inch %06x in2 %06x\n",
uptr->CMD, chsa, len, mema, M[mema>>2]);
/* WARNING, if SNS_DEVEND is not set, diags fail by looping in CON diag */ /* WARNING, if SNS_DEVEND is not set, diags fail by looping in CON diag */
chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* return OK */ chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* return OK */
/* drop through to poll input */ /* drop through to poll input */
break; break;
case CON_NOP: /* 0x03 */ /* NOP has do nothing */ case CON_NOP: /* 0x03 */ /* NOP has do nothing */
//ZZ uptr->CMD &= ~CON_MSK; /* remove old CMD */
uptr->CMD &= LMASK; /* nothing left, command complete */ uptr->CMD &= LMASK; /* nothing left, command complete */
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"con_srvi NOP CMD %08x chsa %04x cmd = %02x\n", uptr->CMD, chsa, cmd); "con_srvi NOP CMD %08x chsa %04x cmd = %02x\n", uptr->CMD, chsa, cmd);
@ -552,10 +548,8 @@ t_stat con_srvi(UNIT *uptr) {
atbuf = (ch)<<8; /* start anew */ atbuf = (ch)<<8; /* start anew */
uptr->CMD |= CON_ATAT; /* show getting @ */ uptr->CMD |= CON_ATAT; /* show getting @ */
} }
#ifndef TEST4MPX
if (ch == '\n') /* convert newline */ if (ch == '\n') /* convert newline */
ch = '\r'; /* make newline into carriage return */ ch = '\r'; /* make newline into carriage return */
#endif
if (isprint(ch)) if (isprint(ch))
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"con_srvi handle readch unit %02x: CMD %08x read %02x [%c] u4 %02x incnt %02x r %x\n", "con_srvi handle readch unit %02x: CMD %08x read %02x [%c] u4 %02x incnt %02x r %x\n",
@ -581,12 +575,8 @@ t_stat con_srvi(UNIT *uptr) {
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"con_srvi readch unit %02x: CMD %08x read %02x u4 %02x incnt %02x\n", "con_srvi readch unit %02x: CMD %08x read %02x u4 %02x incnt %02x\n",
unit, uptr->CMD, ch, uptr->u4, con_data[unit].incnt); unit, uptr->CMD, ch, uptr->u4, con_data[unit].incnt);
//JB sim_clock_coschedule(uptr, 1000);
//JB sim_activate(uptr, 30); /* do this again */
//?? sim_activate(uptr, 300); /* do this again */
sim_activate(uptr, 500); /* do this again */ sim_activate(uptr, 500); /* do this again */
//01172021 sim_activate(uptr, 400); /* do this again */
// sim_activate(uptr, 800); /* do this again */
return SCPE_OK; return SCPE_OK;
} }
/* not looking for input, look for attn or wakeup */ /* not looking for input, look for attn or wakeup */
@ -614,11 +604,7 @@ t_stat con_srvi(UNIT *uptr) {
uptr->u4 = 0; /* no input count */ uptr->u4 = 0; /* no input count */
con_data[unit].incnt = 0; /* no input data */ con_data[unit].incnt = 0; /* no input data */
} }
// sim_activate(uptr, wait_time); /* do this again */
//?? sim_activate(uptr, 400); /* do this again */
sim_activate(uptr, 500); /* do this again */ sim_activate(uptr, 500); /* do this again */
//JB sim_clock_coschedule(uptr, 1000);
// sim_activate(uptr, 4000); /* do this again */
return SCPE_OK; return SCPE_OK;
} }
/* char not for us, so keep looking */ /* char not for us, so keep looking */
@ -649,9 +635,7 @@ t_stat con_srvi(UNIT *uptr) {
"con_srvi readch2 unit %02x: CMD %08x read %02x u4 %02x incnt %02x r %x\n", "con_srvi readch2 unit %02x: CMD %08x read %02x u4 %02x incnt %02x r %x\n",
unit, uptr->CMD, ch, uptr->u4, con_data[unit].incnt, r); unit, uptr->CMD, ch, uptr->u4, con_data[unit].incnt, r);
} }
//X sim_activate(uptr, wait_time); /* do this again */
sim_clock_coschedule(uptr, 1000); /* continue poll */ sim_clock_coschedule(uptr, 1000); /* continue poll */
//JBsim_clock_coschedule(uptr, 1000);
return SCPE_OK; return SCPE_OK;
} }

View file

@ -24,8 +24,6 @@
#include "sel32_defs.h" #include "sel32_defs.h"
extern uint32 sim_idle_ms_sleep(unsigned int); /* wait 1 ms */
#ifndef CPUONLY #ifndef CPUONLY
#ifndef USE_IPU_THREAD #ifndef USE_IPU_THREAD
/* running IPU FORK on CPU, n/u in IPU thread */ /* running IPU FORK on CPU, n/u in IPU thread */
@ -35,7 +33,7 @@ extern int fork();
extern int getpid(); extern int getpid();
uint32 *M = 0; /* Memory when we have IPU fork */ uint32 *M = 0; /* Memory when we have IPU fork */
struct ipcom *IPC = 0; struct ipcom *IPC = 0;
#else #else /* USE_IPU_THREAD */
/* running IPU thread on CPU, n/u in IPU fork */ /* running IPU thread on CPU, n/u in IPU fork */
/* this is different than IPU defines */ /* this is different than IPU defines */
extern void *ipu_sim_instr(void *value); extern void *ipu_sim_instr(void *value);
@ -44,16 +42,12 @@ int PeerIndex;
pthread_t ipuThread; /* thread structure */ pthread_t ipuThread; /* thread structure */
uint32 M[MAXMEMSIZE] = { 0 }; /* Memory */ uint32 M[MAXMEMSIZE] = { 0 }; /* Memory */
struct ipcom myipc = {0}; struct ipcom myipc = {0};
//struct ipcom *IPC = &myipc; /* local structure */
struct ipcom *IPC = 0; struct ipcom *IPC = 0;
//uint32 *M = 0; /* Memory when we have thread IPU */
//extern DEVICE ipu_dev; /* IPU device structure */
uint32 cpustop = 0; /* to stop reason for IPU */ uint32 cpustop = 0; /* to stop reason for IPU */
uint32 got_ipu = 0; /* set non zero when IPU thread created */
#endif #endif
#else #else /* CPUONLY */
//uint32 *M = 0; /* Memory when we have no IPU */
uint32 M[MAXMEMSIZE] = { 0 }; /* Memory */ uint32 M[MAXMEMSIZE] = { 0 }; /* Memory */
//struct ipcom *IPC = 0;
#endif #endif
LOCAL DEVICE* my_dev = &cpu_dev; /* current DEV pointer CPU or IPU */ LOCAL DEVICE* my_dev = &cpu_dev; /* current DEV pointer CPU or IPU */
@ -167,7 +161,6 @@ LOCAL int irq_pend = 0; /* go scan for pending i
extern void rtc_setup(uint32 ss, uint32 level); /* tell rtc to start/stop */ extern void rtc_setup(uint32 ss, uint32 level); /* tell rtc to start/stop */
extern void itm_setup(uint32 ss, uint32 level); /* tell itm to start/stop */ extern void itm_setup(uint32 ss, uint32 level); /* tell itm to start/stop */
extern int32 itm_rdwr(uint32 cmd, int32 cnt, uint32 level); /* read/write the interval timer */ extern int32 itm_rdwr(uint32 cmd, int32 cnt, uint32 level); /* read/write the interval timer */
extern int16 post_csw(CHANP *chp, uint32 rstat);
extern DIB *dib_chan[MAX_CHAN]; extern DIB *dib_chan[MAX_CHAN];
/* floating point subroutines definitions */ /* floating point subroutines definitions */
@ -232,6 +225,7 @@ REG cpu_reg[] = {
{BRDATAD(MAPC, MAPC, 16, 32, 1024, "CPU map cache"), REG_FIT}, {BRDATAD(MAPC, MAPC, 16, 32, 1024, "CPU map cache"), REG_FIT},
{BRDATAD(TLB, TLB, 16, 32, 2048, "CPU Translation Lookaside Buffer"), REG_FIT}, {BRDATAD(TLB, TLB, 16, 32, 2048, "CPU Translation Lookaside Buffer"), REG_FIT},
{HRDATAD(PC, PC, 24, "Program Counter"), REG_FIT}, {HRDATAD(PC, PC, 24, "Program Counter"), REG_FIT},
{HRDATAD(TRAPME, TRAPME, 32, "Trap Error Number"), REG_FIT},
{HRDATAD(IR, IR, 32, "Last Instruction Loaded"), REG_FIT}, {HRDATAD(IR, IR, 32, "Last Instruction Loaded"), REG_FIT},
{HRDATAD(HIWM, HIWM, 32, "Max Maps Loaded"), REG_FIT}, {HRDATAD(HIWM, HIWM, 32, "Max Maps Loaded"), REG_FIT},
{HRDATAD(BPIX, BPIX, 32, "# Maps Loaded for O/S"), REG_FIT}, {HRDATAD(BPIX, BPIX, 32, "# Maps Loaded for O/S"), REG_FIT},
@ -524,6 +518,7 @@ static void DumpHist()
} }
#endif #endif
#ifndef CPUONLY
#ifdef USE_POSIX_SEM #ifdef USE_POSIX_SEM
LOCAL void set_simsem() LOCAL void set_simsem()
{ {
@ -567,6 +562,7 @@ LOCAL void unlock_mutex()
} }
} }
#endif #endif
#endif /* CPUONLY */
#ifdef NOT_USED #ifdef NOT_USED
/* this function is used to extract mode bits from PSD 1 & 2 */ /* this function is used to extract mode bits from PSD 1 & 2 */
@ -800,13 +796,11 @@ npmem:
} }
/* output O/S and User MPL entries */ /* output O/S and User MPL entries */
// sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
sim_debug(DEBUG_CMD, my_dev,
"#MEMORY %06x MPL %06x MPL[0] %08x %06x MPL[%04x] %08x %06x\n", "#MEMORY %06x MPL %06x MPL[0] %08x %06x MPL[%04x] %08x %06x\n",
MEMSIZE, mpl, RMW(mpl), RMW(mpl+4), cpix, MEMSIZE, mpl, RMW(mpl), RMW(mpl+4), cpix,
RMW(cpix+mpl), RMW(cpix+mpl+4)); RMW(cpix+mpl), RMW(cpix+mpl+4));
// sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
sim_debug(DEBUG_CMD, my_dev,
"MEMORY2 %06x BPIX %04x cpix %04x CPIX %04x CPIXPL %04x HIWM %04x\n", "MEMORY2 %06x BPIX %04x cpix %04x CPIX %04x CPIXPL %04x HIWM %04x\n",
MEMSIZE, BPIX, cpix, CPIX, CPIXPL, HIWM); MEMSIZE, BPIX, cpix, CPIX, CPIXPL, HIWM);
@ -1215,16 +1209,6 @@ LOCAL t_stat RealAddr(uint32 addr, uint32 *realaddr, uint32 *prot, uint32 access
if ((CPU_MODEL == MODEL_27) || (CPU_MODEL == MODEL_87)) if ((CPU_MODEL == MODEL_27) || (CPU_MODEL == MODEL_87))
MAXMAP = MAX256; /* only 256 2KW (8kb) maps */ MAXMAP = MAX256; /* only 256 2KW (8kb) maps */
#if 0
// FIXME trapstatus bits
if ((mpl == 0) || (RMW(mpl) == 0) || ((RMW(mpl) & MASK16) >= MAXMAP)) {
sim_debug(DEBUG_TRAP, my_dev,
"RealAddr Bad MPL Count or Memory Address for O/S MPL %06x MPL[0] %04x MPL[1] %06x\n",
mpl, RMW(mpl), RMW(mpl+4));
return MACHINECHK_TRAP; /* diags want machine check error */
}
#endif
/* did not get expected machine check trap for */ /* did not get expected machine check trap for */
/* 27, 87, 67 in test 37/0 if code removed */ /* 27, 87, 67 in test 37/0 if code removed */
/* unexpected machine check trap for 67 in test 37/0 cn.mmm */ /* unexpected machine check trap for 67 in test 37/0 cn.mmm */
@ -1258,7 +1242,6 @@ LOCAL t_stat RealAddr(uint32 addr, uint32 *realaddr, uint32 *prot, uint32 access
index = (word >> 13) & 0x7ff; /* get 11 bit page value */ index = (word >> 13) & 0x7ff; /* get 11 bit page value */
offset = word & 0x1fff; /* get 13 bit page offset */ offset = word & 0x1fff; /* get 13 bit page offset */
//FIXME 112522
if (MODES & MAPMODE) { if (MODES & MAPMODE) {
uint32 mpl = SPAD[0xf3]; /* get mpl from spad address */ uint32 mpl = SPAD[0xf3]; /* get mpl from spad address */
uint32 cpix = CPIX; /* get cpix 11 bit offset from psd wd 2 */ uint32 cpix = CPIX; /* get cpix 11 bit offset from psd wd 2 */
@ -1266,12 +1249,10 @@ LOCAL t_stat RealAddr(uint32 addr, uint32 *realaddr, uint32 *prot, uint32 access
uint32 spc = midl & MASK16; /* get 16 bit user segment description count */ uint32 spc = midl & MASK16; /* get 16 bit user segment description count */
/* output O/S and User MPL entries */ /* output O/S and User MPL entries */
sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
// sim_debug(DEBUG_TRAP, my_dev,
"+MEMORY %06x MPL %06x MPL[0] %08x %06x MPL[%04x] %08x %06x\n", "+MEMORY %06x MPL %06x MPL[0] %08x %06x MPL[%04x] %08x %06x\n",
MEMSIZE, mpl, RMW(mpl), RMW(mpl+4), cpix, MEMSIZE, mpl, RMW(mpl), RMW(mpl+4), cpix,
RMW(cpix+mpl), RMW(cpix+mpl+4)); RMW(cpix+mpl), RMW(cpix+mpl+4));
sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
// sim_debug(DEBUG_TRAP, my_dev,
"+MEMORY spc %x BPIX %04x cpix %04x CPIX %04x CPIXPL %04x HIWM %04x\n", "+MEMORY spc %x BPIX %04x cpix %04x CPIX %04x CPIXPL %04x HIWM %04x\n",
spc, BPIX, cpix, CPIX, CPIXPL, HIWM); spc, BPIX, cpix, CPIX, CPIXPL, HIWM);
} }
@ -1417,14 +1398,14 @@ LOCAL t_stat RealAddr(uint32 addr, uint32 *realaddr, uint32 *prot, uint32 access
return MAPFLT; /* map fault error on memory access */ return MAPFLT; /* map fault error on memory access */
} else } else
if (CPU_MODEL == MODEL_97) { if (CPU_MODEL == MODEL_97) {
// 32/97 wants MAPFLT for test 37/1 in CN.MMM /* 32/97 wants MAPFLT for test 37/1 in CN.MMM */
TRAPSTATUS |= BIT12; /* set bit 12 of trap status */ TRAPSTATUS |= BIT12; /* set bit 12 of trap status */
TRAPSTATUS |= (BIT7|BIT9); /* set bit 7/9 of trap status */ TRAPSTATUS |= (BIT7|BIT9); /* set bit 7/9 of trap status */
TRAPSTATUS |= BIT10; /* set bit 10 of trap status */ TRAPSTATUS |= BIT10; /* set bit 10 of trap status */
return MAPFLT; /* no, map fault error */ return MAPFLT; /* no, map fault error */
} else } else
if (CPU_MODEL == MODEL_V6) { if (CPU_MODEL == MODEL_V6) {
// V6 wants MAPFLT for test 37/1 in CN.MMM & VM.MMM */ /* V6 wants MAPFLT for test 37/1 in CN.MMM & VM.MMM */
TRAPSTATUS |= BIT28; /* set bit 28 of trap status */ TRAPSTATUS |= BIT28; /* set bit 28 of trap status */
/* OK for V6 */ /* OK for V6 */
return MAPFLT; /* map fault error */ return MAPFLT; /* map fault error */
@ -1821,7 +1802,6 @@ LOCAL void set_CCs(uint32 value, int ovr)
PSD1 |= (CC & 0x78000000); /* update the CC's in the PSD */ PSD1 |= (CC & 0x78000000); /* update the CC's in the PSD */
} }
/* retain these values across calls to sim_instr */
LOCAL uint32 skipinstr = 0; /* Skip test for interrupt on this instruction */ LOCAL uint32 skipinstr = 0; /* Skip test for interrupt on this instruction */
LOCAL uint32 drop_nop = 0; /* Set if right hw instruction is a nop */ LOCAL uint32 drop_nop = 0; /* Set if right hw instruction is a nop */
LOCAL uint32 TPSD[2]; /* Temp PSD */ LOCAL uint32 TPSD[2]; /* Temp PSD */
@ -1829,7 +1809,7 @@ LOCAL uint32 TPSD[2]; /* Temp PSD */
#define TPSD2 TPSD[1] /* word 2 of PSD */ #define TPSD2 TPSD[1] /* word 2 of PSD */
/* Opcode definitions */ /* Opcode definitions */
/* called from simulator */ /* called from simh simulator code */
t_stat sim_instr(void) { t_stat sim_instr(void) {
t_stat reason = 0; /* reason for stopping */ t_stat reason = 0; /* reason for stopping */
t_uint64 dest = 0; /* Holds destination/source register */ t_uint64 dest = 0; /* Holds destination/source register */
@ -1872,7 +1852,6 @@ t_stat sim_instr(void) {
/* loop here until time out or error found */ /* loop here until time out or error found */
wait_loop: wait_loop:
while (reason == SCPE_OK) { /* loop until halted */ while (reason == SCPE_OK) { /* loop until halted */
// i_flags = 0; /* clear flags for next instruction */
if (sim_interval <= 0) { /* event queue? */ if (sim_interval <= 0) { /* event queue? */
reason = sim_process_event(); /* process */ reason = sim_process_event(); /* process */
@ -1883,21 +1862,25 @@ wait_loop:
fflush(sim_deb); fflush(sim_deb);
#ifdef DEBUG4IPU #ifdef DEBUG4IPU
DumpHist(); DumpHist();
#else
// cpu_show_hist(sim_deb, (UNIT *)0, (int32)0, (void *)0);
// fflush(sim_deb);
#endif #endif
return reason; return reason;
break; /* process */ break; /* process */
} }
} }
#if 1
/* stop simulator if user break requested */ /* stop simulator if user break requested */
if (sim_brk_summ && sim_brk_test(PC, SWMASK('E'))) { if (sim_brk_summ && sim_brk_test(PC, SWMASK('E'))) {
reason = STOP_IBKPT; reason = STOP_IBKPT;
// reason = SCPE_STEP;
sim_debug(DEBUG_EXP, my_dev, "Process Event test reason %08x interval %08x\n", sim_debug(DEBUG_EXP, my_dev, "Process Event test reason %08x interval %08x\n",
reason, sim_interval); reason, sim_interval);
sim_interval= 0; /* count down */ sim_interval= 0; /* count down */
break; break;
} }
#endif
sim_interval--; /* count down */ sim_interval--; /* count down */
@ -1940,11 +1923,13 @@ wait_loop:
CCW |= HASIPU; /* this is BIT19 for IPU configured */ CCW |= HASIPU; /* this is BIT19 for IPU configured */
SPAD[0xf9] = CPUSTATUS; /* save the cpu status in SPAD */ SPAD[0xf9] = CPUSTATUS; /* save the cpu status in SPAD */
if (!IPU_MODEL) { /* done loading if not an IPU model */ if (!IPU_MODEL) { /* done loading if not an IPU model */
sim_debug(DEBUG_TRAP, my_dev, "Boot Non IPU PSD1 %.8x PSD2 %.8x CPUSTATUS %08x CCW %.8x\n", sim_debug(DEBUG_TRAP, my_dev,
"Boot Non IPU PSD1 %.8x PSD2 %.8x CPUSTATUS %08x CCW %.8x\n",
PSD1, PSD2, CPUSTATUS, CCW); PSD1, PSD2, CPUSTATUS, CCW);
goto loadend; /* done with cpu */ goto loadend; /* done with cpu */
} }
sim_debug(DEBUG_TRAP, my_dev, "Boot use IPU PSD1 %.8x PSD2 %.8x CPUSTATUS %08x CCW %.8x\n", sim_debug(DEBUG_TRAP, my_dev,
"Boot use IPU PSD1 %.8x PSD2 %.8x CPUSTATUS %08x CCW %.8x\n",
PSD1, PSD2, CPUSTATUS, CCW); PSD1, PSD2, CPUSTATUS, CCW);
#ifndef CPUONLY #ifndef CPUONLY
#ifndef USE_IPU_THREAD #ifndef USE_IPU_THREAD
@ -1985,12 +1970,18 @@ wait_loop:
#ifndef USE_IPU_THREAD #ifndef USE_IPU_THREAD
pid = fork(); pid = fork();
#else #else
/* if we have a thread already, do't do it again */
if (got_ipu == 0) {
rstat = pthread_create(&ipuThread, NULL, ipu_sim_instr, NULL); rstat = pthread_create(&ipuThread, NULL, ipu_sim_instr, NULL);
if (rstat) { if (rstat) {
sim_printf("IPU thread create failed rstat = %x\n", rstat); sim_printf("IPU thread create failed rstat = %x\n", rstat);
exit(1); exit(1);
} else { } else {
sim_printf("IPU thread created successfully\n"); sim_printf("IPU thread created successfully\n");
got_ipu = 1; /* we have an ipu thread */
}
} else {
cpustop = STOP_RESET; /* tell IPU to reset for reboot */
} }
#endif #endif
/* /*
@ -2042,7 +2033,7 @@ wait_loop:
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"Starting IPU WAIT in fork\n"); "Starting IPU WAIT in fork\n");
#ifdef USE_POSIX_SEM #ifdef USE_POSIX_SEM
sim_idle_ms_sleep(1); /* wait 1 ms */ sim_os_ms_sleep(10); /* wait 10 ms */
// millinap(1); /* wait 1 ms */ // millinap(1); /* wait 1 ms */
#endif #endif
goto wait_loop; /* continue waiting */ goto wait_loop; /* continue waiting */
@ -2100,9 +2091,9 @@ loadend:
sim_debug(DEBUG_TRAP, my_dev, "%s: (%d) Async TRAP %02x Index %x PeerIndex %x\n", sim_debug(DEBUG_TRAP, my_dev, "%s: (%d) Async TRAP %02x Index %x PeerIndex %x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, MyIndex, PeerIndex); (CPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, MyIndex, PeerIndex);
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: PC %08x PSD1 %08x PSD2 %08x 0x20 %x 0x80 %x\n", "%s: PC %08x PSD1 %08x PSD2 %08x 0x4c %x 0xac %x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", (CPUSTATUS & ONIPU) ? "IPU" : "CPU",
PC, PSD1, PSD2, M[0x20>2], M[0x80>>2]); PC, PSD1, PSD2, M[0x4c>>2], M[0xac>>2]);
wait4int = 0; /* wait is over for int */ wait4int = 0; /* wait is over for int */
skipinstr = 1; /* skip interrupt test */ skipinstr = 1; /* skip interrupt test */
goto newpsd; /* go process trap */ goto newpsd; /* go process trap */
@ -2118,14 +2109,14 @@ loadend:
sim_debug(DEBUG_TRAP, my_dev, "%s: (%d) Async TRAP %02x SPAD[0xf0] %08x\n", sim_debug(DEBUG_TRAP, my_dev, "%s: (%d) Async TRAP %02x SPAD[0xf0] %08x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, SPAD[0xf0]); (CPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, SPAD[0xf0]);
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: PC %08x PSD1 %08x PSD2 %08x 0x20 %x 0x80 %x\n", "%s: PC %08x PSD1 %08x PSD2 %08x 0x4c %x 0x4ac%x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", (CPUSTATUS & ONIPU) ? "IPU" : "CPU",
PC, PSD1, PSD2, M[0x20>2], M[0x80>>2]); PC, PSD1, PSD2, M[0x4c>>2], M[0xac>>2]);
skipinstr = 1; /* skip interrupt test */ skipinstr = 1; /* skip interrupt test */
goto newpsd; /* go process trap */ goto newpsd; /* go process trap */
} }
if (wait4sipu) { if (wait4sipu) {
sim_idle_ms_sleep(1); /* wait 1 ms */ sim_os_ms_sleep(10); /* wait 10 ms */
// millinap(1); /* wait 1 ms */ // millinap(1); /* wait 1 ms */
goto wait_loop; /* continue waiting */ goto wait_loop; /* continue waiting */
} }
@ -2138,12 +2129,14 @@ loadend:
TRAPME = IPC->atrap[MyIndex]; TRAPME = IPC->atrap[MyIndex];
IPC->atrap[MyIndex] = 0; IPC->atrap[MyIndex] = 0;
IPC->received[MyIndex]++; IPC->received[MyIndex]++;
sim_debug(DEBUG_TRAP, my_dev, "%s: (%d) Async TRAP %02x Index %x PeerIndex %x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, MyIndex, PeerIndex);
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: PC %08x PSD1 %08x PSD2 %08x 0x20 %x 0x80 %x\n", "%s: (%d) Async TRAP %02x Index %x PeerIndex %x rec'd %08x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, MyIndex,
PeerIndex, IPC->received[MyIndex]);
sim_debug(DEBUG_TRAP, my_dev,
"%s: PC %08x PSD1 %08x PSD2 %08x 0x4c %x 0xac %x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", (CPUSTATUS & ONIPU) ? "IPU" : "CPU",
PC, PSD1, PSD2, M[0x20>2], M[0x80>>2]); PC, PSD1, PSD2, M[0x4c>>2], M[0xac>>2]);
wait4int = 0; /* wait is over for int */ wait4int = 0; /* wait is over for int */
skipinstr = 1; /* skip interrupt test */ skipinstr = 1; /* skip interrupt test */
goto newpsd; /* go process trap */ goto newpsd; /* go process trap */
@ -2155,11 +2148,7 @@ loadend:
(IPC->atrap[MyIndex] != 0)) { (IPC->atrap[MyIndex] != 0)) {
/* we are unblocked, look for SIPU */ /* we are unblocked, look for SIPU */
/* we have a trap available, lock and get it */ /* we have a trap available, lock and get it */
#ifdef MAYBE_BAD
cond_go: cond_go:
#endif
// lock_mutex(); /* lock mutex */
cond_ok:
if (IPC && IPC->atrap[MyIndex]) { if (IPC && IPC->atrap[MyIndex]) {
lock_mutex(); /* lock mutex */ lock_mutex(); /* lock mutex */
TRAPME = IPC->atrap[MyIndex]; /* get trap number */ TRAPME = IPC->atrap[MyIndex]; /* get trap number */
@ -2167,12 +2156,12 @@ cond_ok:
unlock_mutex(); /* unlock mutex */ unlock_mutex(); /* unlock mutex */
IPC->received[MyIndex]++; /* count it received */ IPC->received[MyIndex]++; /* count it received */
wait4sipu = 0; /* wait is over for sipu */ wait4sipu = 0; /* wait is over for sipu */
sim_debug(DEBUG_TRAP, my_dev, "%s: (%d) Async TRAP %02x SPAD[0xf0] %08x\n", sim_debug(DEBUG_TRAP, my_dev, "%s: (%d) Async TRAP %02x SPAD[0xf0] %02x rec'd %08x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, SPAD[0xf0]); (CPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, SPAD[0xf0], IPC->received[MyIndex]);
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: PC %08x PSD %08x %08x 0x20 %x 0x80 %x\n", "%s: PC %08x PSD %08x %08x 0x4c %x 0xac %x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", (CPUSTATUS & ONIPU) ? "IPU" : "CPU",
PC, PSD1, PSD2, M[0x20>2], M[0x80>>2]); PC, PSD1, PSD2, M[0x4c>>2], M[0xac>>2]);
skipinstr = 1; /* skip interrupt test */ skipinstr = 1; /* skip interrupt test */
goto newpsd; /* go process trap */ goto newpsd; /* go process trap */
} }
@ -2182,10 +2171,9 @@ cond_ok:
while (IPC->atrap[MyIndex]==0) /* sleep on the condition */ while (IPC->atrap[MyIndex]==0) /* sleep on the condition */
pthread_cond_wait(&IPC->cond, &IPC->mutex); /* wait for wakeup */ pthread_cond_wait(&IPC->cond, &IPC->mutex); /* wait for wakeup */
unlock_mutex(); /* unlock mutex and continue */ unlock_mutex(); /* unlock mutex and continue */
goto cond_ok; /* go process */ goto cond_go; /* go process */
} }
/* not waiting for sipu, so continue processing */ /* not waiting for sipu, so continue processing */
// unlock_mutex(); /* unlock mutex and continue */
} }
/* we are blocked or no pending sipu, contine */ /* we are blocked or no pending sipu, contine */
/* continue processing */ /* continue processing */
@ -2327,7 +2315,7 @@ cond_ok:
/* see if in wait instruction */ /* see if in wait instruction */
if (wait4int) { /* keep waiting */ if (wait4int) { /* keep waiting */
/* tell simh we will be waiting */ /* tell simh we will be waiting */
sim_idle(TMR_RTC, 1); /* wait for clock tick */ sim_idle(TMR_RTC, 0); /* wait for clock tick */
PC = OPSD1 & 0xfffffe; /* get 24 bit addr from PSD1 */ PC = OPSD1 & 0xfffffe; /* get 24 bit addr from PSD1 */
goto wait_loop; /* continue waiting */ goto wait_loop; /* continue waiting */
} }
@ -2409,12 +2397,10 @@ skipi:
i_flags = base_mode[OP>>2]; /* set the BM instruction processing flags */ i_flags = base_mode[OP>>2]; /* set the BM instruction processing flags */
else else
i_flags = nobase_mode[OP>>2]; /* set the NBM instruction processing flags */ i_flags = nobase_mode[OP>>2]; /* set the NBM instruction processing flags */
//FIX112922 if ((i_flags & 0xf) == HLF) { /* this is left HW instruction */
if (i_flags & HLF) { /* this is left HW instruction */ if (i_flags & HLF) { /* this is left HW instruction */
if ((IR & 0xffff) == 0x0002) { /* see if rt hw is a nop */ if ((IR & 0xffff) == 0x0002) { /* see if rt hw is a nop */
/* treat this as a fw instruction */ /* treat this as a fw instruction */
drop_nop = 1; /* we need to skip nop next time */ drop_nop = 1; /* we need to skip nop next time */
// sim_debug(DEBUG_IRQ, my_dev,
sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
"CPU setting Drop NOP OPSD1 %08x PSD1 %08x PC %08x IR %08x\n", OPSD1, PSD1, PC, IR); "CPU setting Drop NOP OPSD1 %08x PSD1 %08x PC %08x IR %08x\n", OPSD1, PSD1, PC, IR);
goto exec2; goto exec2;
@ -2434,9 +2420,6 @@ exec2:
OPSD1 = PSD1; /* save the old PSD1 */ OPSD1 = PSD1; /* save the old PSD1 */
OPSD2 = PSD2; /* save the old PSD2 */ OPSD2 = PSD2; /* save the old PSD2 */
TRAPSTATUS = CPUSTATUS & 0x57; /* clear all trap status except cpu type */ TRAPSTATUS = CPUSTATUS & 0x57; /* clear all trap status except cpu type */
// bc = 0;
// EXM_EXR = 0;
// source = 0;
/* Split instruction into pieces */ /* Split instruction into pieces */
PC = PSD1 & 0xfffffe; /* get 24 bit addr from PSD1 */ PC = PSD1 & 0xfffffe; /* get 24 bit addr from PSD1 */
@ -2481,9 +2464,6 @@ exec2:
} }
if (MODES & BASEBIT) { if (MODES & BASEBIT) {
#ifdef NONOP
i_flags = base_mode[OP>>2]; /* set the instruction processing flags */
#endif
addr = IR & RMASK; /* get address offset from instruction */ addr = IR & RMASK; /* get address offset from instruction */
sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
"Base OP %04x i_flags %04x addr %08x\n", OP, i_flags, addr); "Base OP %04x i_flags %04x addr %08x\n", OP, i_flags, addr);
@ -2525,9 +2505,6 @@ exec2:
break; break;
} }
} else { } else {
#ifdef NONOP
i_flags = nobase_mode[OP>>2]; /* set the instruction processing flags */
#endif
addr = IR & 0x7ffff; /* get 19 bit address from instruction */ addr = IR & 0x7ffff; /* get 19 bit address from instruction */
if (PC >= 0x80000) { if (PC >= 0x80000) {
TRAPME = MAPFAULT_TRAP; /* Map Fault Trap */ TRAPME = MAPFAULT_TRAP; /* Map Fault Trap */
@ -2822,25 +2799,20 @@ exec2:
if (CPUSTATUS & ONIPU) { if (CPUSTATUS & ONIPU) {
/* wait for any trap, knowing there will be no interrupts */ /* wait for any trap, knowing there will be no interrupts */
if (wait4sipu == 0) { if (wait4sipu == 0) {
time_t result = time(NULL); sim_debug(DEBUG_DETAIL, my_dev,
// sim_debug(DEBUG_DETAIL, my_dev, "Starting %s HALT PSD %.8x %.8x TRAPME %02x CPUSTATUS %08x\n",
sim_debug(DEBUG_TRAP, my_dev,
"Starting %s HALT PSD %.8x %.8x TRAPME %02x CPUSTATUS %08x time %.8x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", (CPUSTATUS & ONIPU) ? "IPU" : "CPU",
PSD1, PSD2, TRAPME, CPUSTATUS, (uint32)result); PSD1, PSD2, TRAPME, CPUSTATUS);
} }
#ifdef MAYBE_BAD
else { else {
#ifdef USE_POSIX_SEM #ifdef USE_POSIX_SEM
sim_idle_ms_sleep(1); /* wait 1 ms */ sim_os_ms_sleep(10); /* wait 10 ms */
// millinap(1); /* wait 1 ms */
goto wait_loop; /* continue waiting */ goto wait_loop; /* continue waiting */
#else #else
wait4sipu = 1; /* show we are waiting for SIPU */ wait4sipu = 1; /* show we are waiting for SIPU */
goto cond_go; /* start waiting for sipu */ goto cond_go; /* start waiting for sipu */
#endif #endif
} }
#endif
wait4sipu = 1; /* show we are waiting for SIPU */ wait4sipu = 1; /* show we are waiting for SIPU */
i_flags |= BT; /* keep PC from being incremented while waiting */ i_flags |= BT; /* keep PC from being incremented while waiting */
break; /* keep going */ break; /* keep going */
@ -2886,10 +2858,11 @@ exec2:
} }
#endif #endif
#endif #endif
/*TEST DIAG*/reason = STOP_HALT; /* do halt for now */ reason = STOP_HALT; /* do halt for now */
#ifdef USE_IPU_THREAD #ifdef USE_IPU_THREAD
cpustop = reason; /* tell the IPU */ cpustop = STOP_HALT; /* tell the IPU */
#endif #endif
fflush(sim_deb);
return STOP_HALT; /* exit to simh for halt */ return STOP_HALT; /* exit to simh for halt */
break; break;
@ -2911,46 +2884,36 @@ exec2:
TRAPSTATUS |= BIT20; /* set bit 20 of trap status */ TRAPSTATUS |= BIT20; /* set bit 20 of trap status */
goto newpsd; /* System check trap */ goto newpsd; /* System check trap */
} }
#if 0
do_ipu_wait:
#endif
PC = OPSD1 & 0xfffffe; /* get 24 bit addr from PSD1 */ PC = OPSD1 & 0xfffffe; /* get 24 bit addr from PSD1 */
#ifndef CPUONLY #ifndef CPUONLY
if (IPU_MODEL && (CPUSTATUS & ONIPU)) { if (IPU_MODEL && (CPUSTATUS & ONIPU)) {
/* Hack around it when on IPU side: wait by expensive method */ /* Hack around it when on IPU side: wait by expensive method */
/* wait for any trap, knowing there will be no interrupts */ /* wait for any trap, knowing there will be no interrupts */
if (wait4sipu == 0) { if (wait4sipu == 0) {
time_t result = time(NULL); sim_debug(DEBUG_DETAIL, my_dev,
// sim_debug(DEBUG_DETAIL, my_dev, "Starting %s WAIT1 PSD1 %.8x PSD2 %.8x TRAPME %02x CPUSTATUS %08x\n",
sim_debug(DEBUG_TRAP, my_dev,
"Starting %s WAIT1 PSD1 %.8x PSD2 %.8x TRAPME %02x CPUSTATUS %08x time %.8x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", (CPUSTATUS & ONIPU) ? "IPU" : "CPU",
PSD1, PSD2, TRAPME, CPUSTATUS, (uint32)result); PSD1, PSD2, TRAPME, CPUSTATUS);
} }
#ifdef MAYBE_BAD
else { else {
#ifdef USE_POSIX_SEM #ifdef USE_POSIX_SEM
sim_idle_ms_sleep(1); /* wait 1 ms */ sim_os_ms_sleep(10); /* wait 10 ms */
// millinap(1); /* wait 1 ms */
goto wait_loop; /* continue waiting */ goto wait_loop; /* continue waiting */
#else #else
wait4sipu = 1; /* show we are waiting for SIPU */ wait4sipu = 1; /* show we are waiting for SIPU */
goto cond_go; /* start waiting for sipu */ goto cond_go; /* start waiting for sipu */
#endif /* USE_POSIX_SEM */ #endif /* USE_POSIX_SEM */
} }
#endif /* MAYBE_BAD */
wait4sipu = 1; /* show we are waiting for SIPU */ wait4sipu = 1; /* show we are waiting for SIPU */
i_flags |= BT; /* keep PC from being incremented while waiting */ i_flags |= BT; /* keep PC from being incremented while waiting */
} else } else
#endif /* CPU_ONLY */ #endif /* CPU_ONLY */
{ {
if (wait4int == 0) { if (wait4int == 0) {
time_t result = time(NULL); sim_debug(DEBUG_DETAIL, my_dev,
// sim_debug(DEBUG_DETAIL, my_dev, "Starting %s WAIT2 PSD1 %.8x PSD2 %.8x TRAPME %02x CPUSTATUS %08x\n",
sim_debug(DEBUG_TRAP, my_dev,
"Starting %s WAIT2 PSD1 %.8x PSD2 %.8x TRAPME %02x CPUSTATUS %08x time %.8x\n",
(CPUSTATUS & ONIPU) ? "IPU" : "CPU", (CPUSTATUS & ONIPU) ? "IPU" : "CPU",
PSD1, PSD2, TRAPME, CPUSTATUS, (uint32)result); PSD1, PSD2, TRAPME, CPUSTATUS);
} }
/* tell simh we will be waiting */ /* tell simh we will be waiting */
wait4int = 1; /* show we are waiting for interrupt */ wait4int = 1; /* show we are waiting for interrupt */
@ -3022,7 +2985,6 @@ do_ipu_wait:
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"IPU BEI PSD %.8x %.8x SPDF5 %.8x CPUSTATUS %08x\n", "IPU BEI PSD %.8x %.8x SPDF5 %.8x CPUSTATUS %08x\n",
PSD1, PSD2, SPAD[0xf5], CPUSTATUS); PSD1, PSD2, SPAD[0xf5], CPUSTATUS);
//112522 i_flags |= BT; /* leave PC unchanged, so we point at BEI */
goto newpsd; goto newpsd;
} }
PSD2 &= ~(SETBBIT|RETBBIT); /* clear bit 48 & 49 */ PSD2 &= ~(SETBBIT|RETBBIT); /* clear bit 48 & 49 */
@ -3084,15 +3046,14 @@ do_ipu_wait:
(CPUSTATUS & ONIPU)? "IPU": "CPU", CPUSTATUS, CCW); (CPUSTATUS & ONIPU)? "IPU": "CPU", CPUSTATUS, CCW);
//GR Give it a millisec to unblock the atrap //GR Give it a millisec to unblock the atrap
sim_idle_ms_sleep(1); /* wait 1 ms */ sim_os_ms_sleep(10); /* wait 10 ms */
// millinap(1); /* wait 1 ms */
} }
if (IPC->atrap[PeerIndex] == 0) { if (IPC->atrap[PeerIndex] == 0) {
IPC->sent[MyIndex]++; IPC->sent[MyIndex]++;
IPC->atrap[PeerIndex] = SIGNALIPU_TRAP; IPC->atrap[PeerIndex] = SIGNALIPU_TRAP;
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: Async SIPU sent CPUSTATUS %08x CCW %08x\n", "%s: Async SIPU sent CPUSTATUS %08x CCW %02x\n",
(CPUSTATUS & ONIPU)? "IPU": "CPU", CPUSTATUS, CCW); (CPUSTATUS & ONIPU)? "IPU": "CPU", CPUSTATUS, CCW);
} }
else else
@ -3102,11 +3063,10 @@ do_ipu_wait:
/* previous atrap not yet handled if not zero */ /* previous atrap not yet handled if not zero */
IPC->blocked[MyIndex]++; /* count as blocked */ IPC->blocked[MyIndex]++; /* count as blocked */
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: Async SIPU blocked IPUSTATUS %08x CCW %08x SPAD[0xf0] %08x\n", "%s: Async SIPU blocked IPUSTATUS %08x CCW %08x SPAD[0xf0] %02x block %08x\n",
(CPUSTATUS & ONIPU)? "IPU": "CPU", CPUSTATUS, CCW, SPAD[0xf0]); (CPUSTATUS & ONIPU)? "IPU": "CPU", CPUSTATUS, CCW, SPAD[0xf0], IPC->blocked[MyIndex]);
//GR Give it a millisec to unblock the atrap //GR Give it a millisec to unblock the atrap
sim_idle_ms_sleep(1); /* wait 1 ms */ sim_os_ms_sleep(10); /* wait 10 ms */
// millinap(1); /* wait 1 ms */
} }
if (IPC->atrap[PeerIndex] == 0) { if (IPC->atrap[PeerIndex] == 0) {
lock_mutex(); /* lock mutex */ lock_mutex(); /* lock mutex */
@ -3115,14 +3075,13 @@ do_ipu_wait:
unlock_mutex(); /* unlock mutex */ unlock_mutex(); /* unlock mutex */
IPC->sent[MyIndex]++; IPC->sent[MyIndex]++;
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: Async SIPU sent IPUSTATUS %08x CCW %08x SPAD[0xf0] %08x\n", "%s: Async SIPU sent IPUSTATUS %08x CCW %08x SPAD[0xf0] %02x sent %08x\n",
(CPUSTATUS & ONIPU)? "IPU": "CPU", CPUSTATUS, CCW, SPAD[0xf0]); (CPUSTATUS & ONIPU)? "IPU": "CPU", CPUSTATUS, CCW, SPAD[0xf0], IPC->sent[MyIndex]);
} else { } else {
// unlock_mutex(); /* unlock mutex */
IPC->dropped[MyIndex]++; /* count dropped SIPU */ IPC->dropped[MyIndex]++; /* count dropped SIPU */
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: Async SIPU sent IPUSTATUS %08x CCW %08x SPAD[0xf0] %08x\n", "%s: Async SIPU sent IPUSTATUS %08x CCW %08x SPAD[0xf0] %02x drop %08x\n",
(CPUSTATUS & ONIPU)? "IPU": "CPU", CPUSTATUS, CCW, SPAD[0xf0]); (CPUSTATUS & ONIPU)? "IPU": "CPU", CPUSTATUS, CCW, SPAD[0xf0], IPC->dropped[MyIndex]);
} }
#endif /* USE_POSIX_SEM */ #endif /* USE_POSIX_SEM */
} else } else
@ -3130,11 +3089,6 @@ do_ipu_wait:
{ {
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"SIPU CPUSTATUS %08x CCW %08x\n", CPUSTATUS, CCW); "SIPU CPUSTATUS %08x CCW %08x\n", CPUSTATUS, CCW);
//HANGS TRAPME = IPUUNDEFI_TRAP; /* undefined IPU instruction */
//HANGS TRAPME = SYSTEMCHK_TRAP; /* trap condition */
//HANGS TRAPME = MACHINECHK_TRAP; /* trap condition */
//HANGS TRAPME = UNDEFINSTR_TRAP; /* Undefined Instruction Trap */
//FIXME goto newpsd; /* handle trap */
} }
break; break;
case 0xB: /* RWCS */ /* RWCS ignore for now */ case 0xB: /* RWCS */ /* RWCS ignore for now */
@ -4126,8 +4080,8 @@ tbr: /* handle basemode TBR too *
t = (GPR[reg] >> 16) & 0xff; /* get SPAD address from Rd (6-8) */ t = (GPR[reg] >> 16) & 0xff; /* get SPAD address from Rd (6-8) */
temp2 = SPAD[t]; /* get old SPAD data */ temp2 = SPAD[t]; /* get old SPAD data */
SPAD[t] = GPR[sreg]; /* store Rs into SPAD */ SPAD[t] = GPR[sreg]; /* store Rs into SPAD */
// sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
// "TRSC SPAD[%04x] B4 %08x New %08x\n", t, temp2, GPR[sreg]); "TRSC SPAD[%04x] B4 %08x New %08x\n", t, temp2, GPR[sreg]);
break; break;
case 0xF: /* TSCR */ /* Transfer scratchpad to register */ case 0xF: /* TSCR */ /* Transfer scratchpad to register */
@ -4141,8 +4095,8 @@ tbr: /* handle basemode TBR too *
} }
t = (GPR[sreg] >> 16) & 0xff; /* get SPAD address from Rs (9-11) */ t = (GPR[sreg] >> 16) & 0xff; /* get SPAD address from Rs (9-11) */
temp = SPAD[t]; /* get SPAD data into Rd (6-8) */ temp = SPAD[t]; /* get SPAD data into Rd (6-8) */
// sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
// "TSCR SPAD[%04x] Val %08x\n", t, temp); "TSCR SPAD[%04x] Val %08x\n", t, temp);
break; break;
} }
GPR[reg] = temp; /* save the temp value to Rd reg */ GPR[reg] = temp; /* save the temp value to Rd reg */
@ -4162,7 +4116,6 @@ skipit:
case 0x30>>2: /* 0x30 */ /* CALM */ case 0x30>>2: /* 0x30 */ /* CALM */
/* Process CALM for 32/27 when in left hw, else invalid */ /* Process CALM for 32/27 when in left hw, else invalid */
if ((CPU_MODEL <= MODEL_87) && (CPU_MODEL != MODEL_67)) { if ((CPU_MODEL <= MODEL_87) && (CPU_MODEL != MODEL_67)) {
// uint32 oldstatus = CPUSTATUS; /* keep for retain blocking state */
/* DIAG error for 32/27 or 32/87 only */ /* DIAG error for 32/27 or 32/87 only */
if ((PSD1 & 2) != 0) /* is it lf hw instruction */ if ((PSD1 & 2) != 0) /* is it lf hw instruction */
goto inv; /* invalid instr if in rt hw */ goto inv; /* invalid instr if in rt hw */
@ -5386,6 +5339,9 @@ meoa: /* merge point for eor, and, or */
unlock_mutex(); unlock_mutex();
#endif #endif
#endif #endif
sim_debug(DEBUG_IRQ, my_dev,
"SBM @ PSD %08x %08x bit %08x addr %06x CCs %08x\r\n",
PSD1, PSD2, bc, addr, PSD1 & 0x78000000);
break; break;
case 0x9C>>2: /* 0x9C ADR - ADR */ /* ZBM */ case 0x9C>>2: /* 0x9C ADR - ADR */ /* ZBM */
@ -5448,6 +5404,9 @@ meoa: /* merge point for eor, and, or */
unlock_mutex(); unlock_mutex();
#endif #endif
#endif #endif
sim_debug(DEBUG_IRQ, my_dev,
"ZBM @ PSD %08x %08x bit %08x addr %06x CCs %08x\r\n",
PSD1, PSD2, bc, addr, PSD1 & 0x78000000);
break; break;
case 0xA0>>2: /* 0xA0 ADR - ADR */ /* ABM */ case 0xA0>>2: /* 0xA0 ADR - ADR */ /* ABM */
@ -5893,7 +5852,6 @@ doovr2:
temp2>>2, IR&0xFFF, TPSD1, TPSD2, PSD1, PSD2, SPAD[0xf5], CPUSTATUS); temp2>>2, IR&0xFFF, TPSD1, TPSD2, PSD1, PSD2, SPAD[0xf5], CPUSTATUS);
TRAPME = MACHINECHK_TRAP; /* trap condition */ TRAPME = MACHINECHK_TRAP; /* trap condition */
PSD1 = TPSD1; /* restore PSD 1 */ PSD1 = TPSD1; /* restore PSD 1 */
//FIX121222 PSD2 = TPSD2; /* restore PSD 2 */
PSD2 = PSD2; /* diag wants new PSD 2, not old?? */ PSD2 = PSD2; /* diag wants new PSD 2, not old?? */
goto newpsd; /* program error */ goto newpsd; /* program error */
} }
@ -5905,7 +5863,14 @@ doovr2:
" R0=%.8x R1=%.8x R2=%.8x R3=%.8x\n", GPR[0], GPR[1], GPR[2], GPR[3]); " R0=%.8x R1=%.8x R2=%.8x R3=%.8x\n", GPR[0], GPR[1], GPR[2], GPR[3]);
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
" R4=%.8x R5=%.8x R6=%.8x R7=%.8x\n", GPR[4], GPR[5], GPR[6], GPR[7]); " R4=%.8x R5=%.8x R6=%.8x R7=%.8x\n", GPR[4], GPR[5], GPR[6], GPR[7]);
#ifdef FOR_DEBUG_SVC
bc = 0;
addr = GPR[1] & 0xffffff;
RealAddr(addr, &t, &bc, MEM_RD);
sim_debug(DEBUG_TRAP, my_dev,
"SVC addr %x raddr %x GPR[1] %x\n", addr, t, GPR[1]);
fflush(sim_deb);
#endif
/* test for retain blocking state */ /* test for retain blocking state */
if (PSD2 & RETBBIT) { /* is it retain blocking state */ if (PSD2 & RETBBIT) { /* is it retain blocking state */
/* BIT 49 has new blocking state */ /* BIT 49 has new blocking state */
@ -5957,6 +5922,10 @@ doovr2:
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"SVCX %x,%x @ %.8x %.8x NPSD %.8x %.8x SPADF5 %x CPUSTATUS %08x\n", "SVCX %x,%x @ %.8x %.8x NPSD %.8x %.8x SPADF5 %x CPUSTATUS %08x\n",
temp2>>2, IR&0xFFF, OPSD1, OPSD2, PSD1, PSD2, SPAD[0xf5], CPUSTATUS); temp2>>2, IR&0xFFF, OPSD1, OPSD2, PSD1, PSD2, SPAD[0xf5], CPUSTATUS);
sim_debug(DEBUG_TRAP, my_dev,
" R0=%.8x R1=%.8x R2=%.8x R3=%.8x\n", GPR[0], GPR[1], GPR[2], GPR[3]);
sim_debug(DEBUG_TRAP, my_dev,
" R4=%.8x R5=%.8x R6=%.8x R7=%.8x\n", GPR[4], GPR[5], GPR[6], GPR[7]);
SPAD[0xf5] = PSD2; /* save the current PSD2 */ SPAD[0xf5] = PSD2; /* save the current PSD2 */
SPAD[0xf9] = CPUSTATUS; /* save the cpu status in SPAD */ SPAD[0xf9] = CPUSTATUS; /* save the cpu status in SPAD */
TRAPME = 0; /* not to be processed as trap */ TRAPME = 0; /* not to be processed as trap */
@ -6012,9 +5981,6 @@ dohist:
hst[hst_p].modes |= INTBLKD; /* save blocking mode bit */ hst[hst_p].modes |= INTBLKD; /* save blocking mode bit */
if (CPUSTATUS & BIT27) if (CPUSTATUS & BIT27)
hst[hst_p].modes |= IPUMODE; /* save cpu/ipu status bit */ hst[hst_p].modes |= IPUMODE; /* save cpu/ipu status bit */
//113022 hst[hst_p].modes &= ~(BIT24|BIT27); /* clear blocked and ipu bits */
//113022 hst[hst_p].modes |= (CPUSTATUS & BIT24);/* save blocking mode bit */
//113022 hst[hst_p].modes |= (CPUSTATUS & BIT27);/* save cpu/ipu status bit */
for (ix=0; ix<8; ix++) { for (ix=0; ix<8; ix++) {
hst[hst_p].reg[ix] = GPR[ix]; /* save reg */ hst[hst_p].reg[ix] = GPR[ix]; /* save reg */
hst[hst_p].reg[ix+8] = BR[ix]; /* save breg */ hst[hst_p].reg[ix+8] = BR[ix]; /* save breg */
@ -6448,8 +6414,8 @@ dohist:
i_flags |= BT; /* we branched, so no PC update */ i_flags |= BT; /* we branched, so no PC update */
if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */ if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */
PSD1 = (PSD1 & 0x87fffffe) | temp2; /* insert last indirect CCs */ PSD1 = (PSD1 & 0x87fffffe) | temp2; /* insert last indirect CCs */
/*FIX F77*/ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */
/*FIX F77*/ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */
} }
/* branch not taken, go do next instruction */ /* branch not taken, go do next instruction */
break; break;
@ -6484,8 +6450,8 @@ dohist:
i_flags |= BT; /* we branched, so no PC update */ i_flags |= BT; /* we branched, so no PC update */
if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */ if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */
PSD1 = (PSD1 & 0x87fffffe) | temp2; /* insert last indirect CCs */ PSD1 = (PSD1 & 0x87fffffe) | temp2; /* insert last indirect CCs */
/*FIX F77*/ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */
/*FIX F77*/ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */
} }
break; break;
@ -6506,8 +6472,8 @@ dohist:
if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */ if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */
PSD1 = (PSD1 & 0x87fffffe) | CC; /* insert last CCs */ PSD1 = (PSD1 & 0x87fffffe) | CC; /* insert last CCs */
i_flags |= BT; /* we branched, so no PC update */ i_flags |= BT; /* we branched, so no PC update */
/*FIX F77*/ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */
/*FIX F77*/ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */
} }
break; break;
@ -6528,8 +6494,8 @@ dohist:
else else
PSD1 = (PSD1 & 0xff000000) | (addr & 0x07fffe); /* bit 13-30 */ PSD1 = (PSD1 & 0xff000000) | (addr & 0x07fffe); /* bit 13-30 */
i_flags |= BT; /* we branched, so no PC update */ i_flags |= BT; /* we branched, so no PC update */
/*FIX F77*/ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */
/*FIX F77*/ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */
break; break;
case 0x3: /* LPSD F980 */ case 0x3: /* LPSD F980 */
@ -6656,18 +6622,13 @@ dohist:
/* see what mapping we are to do if LPSDCM */ /* see what mapping we are to do if LPSDCM */
if (OPR & 0x0200) { /* Was it LPSDCM? */ if (OPR & 0x0200) { /* Was it LPSDCM? */
if (PSD2 & MAPBIT) { if (PSD2 & MAPBIT) {
//FIXME TRYING FOR DEXP FIX?
#ifndef DEXP_TRY_FIX
/* this mod fixes MPX 1.X 1st swapr load */ /* this mod fixes MPX 1.X 1st swapr load */
/* any O/S or user maps yet? */ /* any O/S or user maps yet? */
if (((CPIX != 0) && (CPIXPL == 0)) && (PSD2 & RETMBIT)) { if (((CPIX != 0) && (CPIXPL == 0)) && (PSD2 & RETMBIT)) {
PSD2 &= ~RETMBIT; /* no, turn off retain bit in PSD2 */ PSD2 &= ~RETMBIT; /* no, turn off retain bit in PSD2 */
sim_debug(DEBUG_TRAP, my_dev, "Turn off retain bit\n"); sim_debug(DEBUG_TRAP, my_dev, "Turn off retain bit\n");
} }
#endif
//FIXME TRYING FOR DEXP FIX?
#ifndef DEXP_TRY_FIX
/* test if user count is equal to CPIXPL, if not load maps */ /* test if user count is equal to CPIXPL, if not load maps */
/* this fixes software error in MPX3X where count is changed */ /* this fixes software error in MPX3X where count is changed */
/* but the retain bit was left set, so new maps were not loaded */ /* but the retain bit was left set, so new maps were not loaded */
@ -6698,7 +6659,6 @@ dohist:
"LPSDCM FIX MAP TRAPME %02x PSD %08x %08x spc %02x BPIX %02x CPIXPL %02x retain %01x\n", "LPSDCM FIX MAP TRAPME %02x PSD %08x %08x spc %02x BPIX %02x CPIXPL %02x retain %01x\n",
TRAPME, PSD1, PSD2, spc, BPIX, CPIXPL, PSD2&RETMBIT?1:0); TRAPME, PSD1, PSD2, spc, BPIX, CPIXPL, PSD2&RETMBIT?1:0);
} }
#endif
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"LPSDCML %.6x NPSD %08x %08x OPSD %08x %08x SPADF5 %x STATUS %08x\n", "LPSDCML %.6x NPSD %08x %08x OPSD %08x %08x SPADF5 %x STATUS %08x\n",
addr, PSD1, PSD2, TPSD1, TPSD2, ix, CPUSTATUS); addr, PSD1, PSD2, TPSD1, TPSD2, ix, CPUSTATUS);
@ -6721,6 +6681,10 @@ dohist:
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"LPSDL @ %.6x NPSD %08x %08x OPSD %08x %08x SPADF5 %x STATUS %08x\n", "LPSDL @ %.6x NPSD %08x %08x OPSD %08x %08x SPADF5 %x STATUS %08x\n",
addr, PSD1, PSD2, TPSD1, TPSD2, ix, CPUSTATUS); addr, PSD1, PSD2, TPSD1, TPSD2, ix, CPUSTATUS);
sim_debug(DEBUG_TRAP, my_dev,
" R0=%.8x R1=%.8x R2=%.8x R3=%.8x\n", GPR[0], GPR[1], GPR[2], GPR[3]);
sim_debug(DEBUG_TRAP, my_dev,
" R4=%.8x R5=%.8x R6=%.8x R7=%.8x\n", GPR[4], GPR[5], GPR[6], GPR[7]);
} }
/* TRAPME can be error from LPSDCM or OK here */ /* TRAPME can be error from LPSDCM or OK here */
@ -6729,7 +6693,6 @@ dohist:
"LPSDCM BAD MAPS LOAD TRAPME %02x PSD %08x %08x CPUSTAT %08x SPAD[f9] %08x\n", "LPSDCM BAD MAPS LOAD TRAPME %02x PSD %08x %08x CPUSTAT %08x SPAD[f9] %08x\n",
TRAPME, PSD1, PSD2, CPUSTATUS, SPAD[0xf9]); TRAPME, PSD1, PSD2, CPUSTATUS, SPAD[0xf9]);
PSD1 = TPSD1; /* restore PSD1 */ PSD1 = TPSD1; /* restore PSD1 */
//NO, USE NEW PSD2 = TPSD2; /* restore PSD2 */
/* HACK HACK HACK */ /* HACK HACK HACK */
/* Diags wants the new PSD2, not the original on error??? */ /* Diags wants the new PSD2, not the original on error??? */
/* if old one was used, we fail test 21/0 in cn.mmm for 32/67 */ /* if old one was used, we fail test 21/0 in cn.mmm for 32/67 */
@ -6792,7 +6755,6 @@ dohist:
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"IPU SIO PSD %.8x %.8x SPDF5 %.8x CPUSTATUS %08x\n", "IPU SIO PSD %.8x %.8x SPDF5 %.8x CPUSTATUS %08x\n",
PSD1, PSD2, SPAD[0xf5], CPUSTATUS); PSD1, PSD2, SPAD[0xf5], CPUSTATUS);
//DIAGS FIX i_flags |= BT; /* leave PC unchanged, so no PC update */
goto newpsd; goto newpsd;
} }
if ((OPR & 0x7) != 0x07) { /* aug is 111 for XIO instruction */ if ((OPR & 0x7) != 0x07) { /* aug is 111 for XIO instruction */
@ -6943,6 +6905,7 @@ dohist:
/* t has spad entry for device */ /* t has spad entry for device */
/* get the 1's comp of interrupt address from bits 9-15 SPAD entry */ /* get the 1's comp of interrupt address from bits 9-15 SPAD entry */
ix = ((~t)>>16)&0x7f; /* get positive number for interrupt */ ix = ((~t)>>16)&0x7f; /* get positive number for interrupt */
prior = ix; /* set prior for CD instruction */
if (OPR & 0x1) { /* see if CD or TD */ if (OPR & 0x1) { /* see if CD or TD */
sim_debug(DEBUG_IRQ, my_dev, sim_debug(DEBUG_IRQ, my_dev,
"TD spad %08x INTS[%02x] %08x\n", t, prior, INTS[prior]); "TD spad %08x INTS[%02x] %08x\n", t, prior, INTS[prior]);
@ -7511,7 +7474,6 @@ newpsd:
case IPUUNDEFI_TRAP: /* 0xA8 PL0A IPU Undefined Instruction Trap */ case IPUUNDEFI_TRAP: /* 0xA8 PL0A IPU Undefined Instruction Trap */
//MOVED case CALM_TRAP: /* 0xA8 PL0A Call Monitor Instruction Trap */ //MOVED case CALM_TRAP: /* 0xA8 PL0A Call Monitor Instruction Trap */
//MOVED case SIGNALIPU_TRAP: /* 0xAC PL0B Signal IPU/CPU Trap */ //MOVED case SIGNALIPU_TRAP: /* 0xAC PL0B Signal IPU/CPU Trap */
case ADDRSPEC_TRAP: /* 0xB0 PL0C Address Specification Trap */ case ADDRSPEC_TRAP: /* 0xB0 PL0C Address Specification Trap */
//BAD HERE case CONSOLEATN_TRAP: /* 0xB4 PL0D Console Attention Trap */ //BAD HERE case CONSOLEATN_TRAP: /* 0xB4 PL0D Console Attention Trap */
case PRIVHALT_TRAP: /* 0xB8 PL0E Privlege Mode Halt Trap */ case PRIVHALT_TRAP: /* 0xB8 PL0E Privlege Mode Halt Trap */
@ -7571,10 +7533,6 @@ newpsd:
case CONSOLEATN_TRAP: /* 0xB4 PL0D Console Attention Trap */ case CONSOLEATN_TRAP: /* 0xB4 PL0D Console Attention Trap */
//112522 case IPUUNDEFI_TRAP: /* 0xA8 PL0A IPU Undefined Instruction Trap */ //112522 case IPUUNDEFI_TRAP: /* 0xA8 PL0A IPU Undefined Instruction Trap */
case SIGNALIPU_TRAP: /* 0xAC PL0B Signal IPU/CPU Trap */ case SIGNALIPU_TRAP: /* 0xAC PL0B Signal IPU/CPU Trap */
sim_debug(DEBUG_TRAP, my_dev,
"At %s TRAPME %02x PC %08x PSD1 %08x PSD2 %08x CPUSTATUS %08x tta %02x\n",
(CPUSTATUS & ONIPU)? "IPU": "CPU",
TRAPME, PC, PSD1, PSD2, CPUSTATUS, tta);
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"At %s TRAP %02x IR %08x PSD1 %08x PSD2 %08x CPUSTATUS %08x drop_nop %01x\n", "At %s TRAP %02x IR %08x PSD1 %08x PSD2 %08x CPUSTATUS %08x drop_nop %01x\n",
(CPUSTATUS & ONIPU)? "IPU": "CPU", (CPUSTATUS & ONIPU)? "IPU": "CPU",
@ -7587,8 +7545,21 @@ newpsd:
tta = tta + (TRAPME - 0x80); /* tta has mem addr of trap vector */ tta = tta + (TRAPME - 0x80); /* tta has mem addr of trap vector */
tvl = M[tta>>2] & 0xFFFFFC; /* get 24 bit trap address from trap vector loc */ tvl = M[tta>>2] & 0xFFFFFC; /* get 24 bit trap address from trap vector loc */
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"tvl %08x, tta %02x CCW %08x status %08x\n", "CPU tvl %08x, tta %02x CCW %08x status %08x\n",
tvl, tta, CCW, CPUSTATUS); tvl, tta, CCW, CPUSTATUS);
if (!MEM_ADDR_OK(tvl & MASK24)) { /* see if in memory */
sim_debug(DEBUG_TRAP, my_dev,
"CPU Bad trap PSD1 %08x PSD2 %08x TRAPME %02x\r\n", PSD1, PSD2, TRAPME);
/* bad address for trap vector, lets halt */
fprintf(stderr, "CPU Bad trap PSD1 %08x PSD2 %08x TRAPME %02x\r\n", PSD1, PSD2, TRAPME);
fprintf(stderr, "CPU Bad trap address tvl %08x, tta %02x CCW %08x status %08x\r\n",
tvl, tta, CCW, CPUSTATUS);
fflush(stderr);
fprintf(stderr, "M[tta] %08x M[tvl] %08x M[tvl+1] %08x M[tvl+2] %08x M[tvl+3]] %08x\r\n",
M[tta>>2], M[(tvl>>2)+0], M[(tvl>>2)+1], M[(tvl>>2)+2], M[(tvl>>2)+3]);
fflush(stderr);
goto doahalt;
}
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"M[tta] %08x M[tvl] %08x M[tvl+1] %08x M[tvl+2] %08x M[tvl+3]] %08x\n", "M[tta] %08x M[tvl] %08x M[tvl+1] %08x M[tvl+2] %08x M[tvl+3]] %08x\n",
M[tta>>2], M[(tvl>>2)+0], M[(tvl>>2)+1], M[(tvl>>2)+2], M[(tvl>>2)+3]); M[tta>>2], M[(tvl>>2)+0], M[(tvl>>2)+1], M[(tvl>>2)+2], M[(tvl>>2)+3]);
@ -7600,12 +7571,12 @@ newpsd:
if (((tvl == 0) || (CPUSTATUS & 0x40) == 0) || if (((tvl == 0) || (CPUSTATUS & 0x40) == 0) ||
(TRAPME == PRIVHALT_TRAP)) { /* 0xB8 PL0E Privlege Mode Halt Trap */ (TRAPME == PRIVHALT_TRAP)) { /* 0xB8 PL0E Privlege Mode Halt Trap */
#endif #endif
doahalt:
/* vector is zero or software has not enabled traps yet */ /* vector is zero or software has not enabled traps yet */
/* execute a trap halt */ /* execute a trap halt */
/* set the PSD to trap vector location */ /* set the PSD to trap vector location */
fprintf(stderr, "[][][][][][][][][][] HALT TRAP [2][][][][][][][][][]\r\n"); fprintf(stderr, "[][][][][][][][][][] HALT TRAP [2][][][][][][][][][]\r\n");
fprintf(stderr, "PSD1 %08x PSD2 %08x TRAPME %02x\r\n", PSD1, PSD2, TRAPME); fprintf(stderr, "PSD1 %08x PSD2 %08x TRAPME %02x\r\n", PSD1, PSD2, TRAPME);
//FIX PSD1 = 0x80000000 + TRAPME; /* just priv and PC to trap vector */
PSD1 = 0x80000000 + tta; /* just priv and PC to trap vector */ PSD1 = 0x80000000 + tta; /* just priv and PC to trap vector */
PSD2 = 0x00004000; /* unmapped, blocked interrupts mode */ PSD2 = 0x00004000; /* unmapped, blocked interrupts mode */
/* /*
@ -7635,6 +7606,7 @@ newpsd:
} }
} }
fprintf(stderr, "[][][][][][][][][][] HALT TRAP [2][][][][][][][][][]\r\n"); fprintf(stderr, "[][][][][][][][][][] HALT TRAP [2][][][][][][][][][]\r\n");
fflush(stderr);
if (IPU_MODEL && (CPUSTATUS & ONIPU)) { if (IPU_MODEL && (CPUSTATUS & ONIPU)) {
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: Halt TRAP CPUSTATUS %08x CCW %08x\n", "%s: Halt TRAP CPUSTATUS %08x CCW %08x\n",
@ -7651,11 +7623,12 @@ newpsd:
#endif #endif
} }
#ifndef USE_IPU_THREAD #ifndef USE_IPU_THREAD
/*TEST DIAG*/reason = STOP_HALT; /* do halt for now */ reason = STOP_HALT; /* do halt for now */
fflush(sim_deb);
return STOP_HALT; /* exit to simh for halt */ return STOP_HALT; /* exit to simh for halt */
#else #else
/*TEST DIAG*/ reason = STOP_HALT; /* do halt for now */ reason = STOP_HALT; /* do halt for now */
cpustop = reason; /* tell IPU our state */ cpustop = STOP_HALT; /* tell IPU to stop */
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"[][][][][][][][][][] Send HALT to IPU [][][][][][][][][][]\n"); "[][][][][][][][][][] Send HALT to IPU [][][][][][][][][][]\n");
fflush(sim_deb); fflush(sim_deb);
@ -7723,7 +7696,6 @@ newpsd:
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"Process %s TRAPME %02x PSD1 %08x PSD2 %08x CPUSTATUS %08x MODE %08x\n", "Process %s TRAPME %02x PSD1 %08x PSD2 %08x CPUSTATUS %08x MODE %08x\n",
(CPUSTATUS & ONIPU)? "IPU": "CPU", (CPUSTATUS & ONIPU)? "IPU": "CPU",
//FIX TRAPME, PSD1, PSD2, CPUSTATUS, MODES);
tta, PSD1, PSD2, CPUSTATUS, MODES); tta, PSD1, PSD2, CPUSTATUS, MODES);
/* TODO provide page fault data to word 6 */ /* TODO provide page fault data to word 6 */
if (TRAPME == DEMANDPG_TRAP) { /* 0xC4 Demand Page Fault Trap (V6&V9 Only) */ if (TRAPME == DEMANDPG_TRAP) { /* 0xC4 Demand Page Fault Trap (V6&V9 Only) */
@ -7800,9 +7772,6 @@ t_stat cpu_reset(DEVICE *dptr)
CPUSTATUS |= PRIVBIT; /* set privleged state bit 0 */ CPUSTATUS |= PRIVBIT; /* set privleged state bit 0 */
CPUSTATUS |= BIT24; /* set blocked mode state bit 24 */ CPUSTATUS |= BIT24; /* set blocked mode state bit 24 */
CPUSTATUS |= BIT22; /* set HS floating point unit not present bit 22 */ CPUSTATUS |= BIT22; /* set HS floating point unit not present bit 22 */
#ifdef USE_IPU_THREAD
// IPUSTATUS |= ONIPU; /* set ipu state in ipu status, BIT27 */
#endif
TRAPSTATUS = CPU_MODEL; /* clear all trap status except cpu type */ TRAPSTATUS = CPU_MODEL; /* clear all trap status except cpu type */
CMCR = 0; /* No Cache Enabled */ CMCR = 0; /* No Cache Enabled */
SMCR = 0; /* No Shared Memory Enabled */ SMCR = 0; /* No Shared Memory Enabled */
@ -7886,9 +7855,7 @@ t_stat cpu_reset(DEVICE *dptr)
#else #else
#ifndef USE_POSIX_SEM #ifndef USE_POSIX_SEM
/* intialize the pthread mutex and cond on thread IPU/CPU */ /* intialize the pthread mutex and cond on thread IPU/CPU */
// IPC->mutex = PTHREAD_MUTEX_INITIALIZER;
pthread_mutex_init(&IPC->mutex, NULL); pthread_mutex_init(&IPC->mutex, NULL);
// IPC->cond = PTHREAD_COND_INITIALIZER;
pthread_cond_init(&IPC->cond, NULL); pthread_cond_init(&IPC->cond, NULL);
#endif #endif
#endif #endif
@ -7923,7 +7890,6 @@ t_stat cpu_reset(DEVICE *dptr)
#else #else
SPAD[0xf7] = 0xecdab897; /* load the CPU key */ SPAD[0xf7] = 0xecdab897; /* load the CPU key */
#endif #endif
//120822SPAD[0xf8] = 0x0000f000; /* set DRT to class f (anything else is E) */
SPAD[0xf8] = 0x0f000000; /* set DRT to class f (anything else is E) */ SPAD[0xf8] = 0x0f000000; /* set DRT to class f (anything else is E) */
SPAD[0xf9] = CPUSTATUS; /* set default cpu type in cpu status word */ SPAD[0xf9] = CPUSTATUS; /* set default cpu type in cpu status word */
SPAD[0xff] = 0x00ffffff; /* interrupt level 7f 1's complament */ SPAD[0xff] = 0x00ffffff; /* interrupt level 7f 1's complament */
@ -7953,7 +7919,6 @@ t_stat cpu_reset(DEVICE *dptr)
} }
} else { } else {
/* I am the CPU */ /* I am the CPU */
// if (IPC != 0) {
if (IPC != 0 && !(CPUSTATUS & ONIPU) && (IPC->pid[1] != 0)) { if (IPC != 0 && !(CPUSTATUS & ONIPU) && (IPC->pid[1] != 0)) {
fprintf(stdout,"CPU IPC %p pid=%d IPU pid %d 0x80=%x\r\n", IPC, IPC->pid[0], IPC->pid[1], SPAD[0xf0]); fprintf(stdout,"CPU IPC %p pid=%d IPU pid %d 0x80=%x\r\n", IPC, IPC->pid[0], IPC->pid[1], SPAD[0xf0]);
fflush(stdout); fflush(stdout);
@ -8041,9 +8006,6 @@ t_stat cpu_set_size(UNIT *uptr, int32 sval, CONST char *cptr, void *desc)
// sim_printf("cpu_set_size sval %x cptr %s desc %s\n", sval, cptr, (char *)desc); // sim_printf("cpu_set_size sval %x cptr %s desc %s\n", sval, cptr, (char *)desc);
val >>= UNIT_V_MSIZE; /* shift index right 19 bits */ val >>= UNIT_V_MSIZE; /* shift index right 19 bits */
// fprintf(stdout, "at cpu_set_size sval %x val %x\r\n", sval, val);
// fflush (stdout);
if (val >= (int32)(sizeof(memwds)/sizeof(uint32))) /* is size valid */ if (val >= (int32)(sizeof(memwds)/sizeof(uint32))) /* is size valid */
return SCPE_ARG; /* nope, argument error */ return SCPE_ARG; /* nope, argument error */
sz = memwds[val]; /* (128KB/4) << index == memory size in KW */ sz = memwds[val]; /* (128KB/4) << index == memory size in KW */
@ -8076,7 +8038,6 @@ t_stat cpu_set_ipu(UNIT *uptr, int32 sval, CONST char *cptr, void *desc)
// sim_printf("cpu_set_ipu sval %x cptr %s desc %s\n", sval, cptr, (char *)desc); // sim_printf("cpu_set_ipu sval %x cptr %s desc %s\n", sval, cptr, (char *)desc);
#ifdef CPUONLY #ifdef CPUONLY
sim_printf("IPU not available for this version of sel32\n"); sim_printf("IPU not available for this version of sel32\n");
// return SCPE_OK; /* we done */
return SCPE_ARG; /* error, we done */ return SCPE_ARG; /* error, we done */
#endif #endif
if ((CPU_MODEL == MODEL_55) || (CPU_MODEL == MODEL_27)) { if ((CPU_MODEL == MODEL_55) || (CPU_MODEL == MODEL_27)) {
@ -8200,6 +8161,7 @@ t_stat cpu_show_hist(FILE *st, UNIT *uptr, int32 val, CONST void *desc)
} }
fprintf(st, "\n"); fprintf(st, "\n");
} /* end for */ } /* end for */
fflush(sim_deb);
return SCPE_OK; /* all is good */ return SCPE_OK; /* all is good */
} }

View file

@ -38,14 +38,11 @@
/* define CPUONLY to run without IPU */ /* define CPUONLY to run without IPU */
//#define CPUONLY /* run on CPU only */ //#define CPUONLY /* run on CPU only */
/* undefine CPUONLY to run with IPU */
#undef CPUONLY /* run with cpu/ipu on system */ #undef CPUONLY /* run with cpu/ipu on system */
/* undefine CPUONLY to run with IPU */
/* define USE_IPU_THREAD to use IPU thread code instead of fork code */ /* define USE_IPU_THREAD to use IPU thread code instead of fork code */
/* define USE_POSIX_SEM for POSIX semaphores otherwise use pthread mutex */
/* forked mode IPU must only use semaphores */
#ifndef CPUONLY #ifndef CPUONLY
//#define USE_POSIX_SEM /* use POSIX semaphores, else pthread mutex */
//#undef USE_IPU_THREAD /* run IPU as a forked sel32 */ //#undef USE_IPU_THREAD /* run IPU as a forked sel32 */
#define USE_IPU_THREAD /* run IPU in sel32_ipu.c thread */ #define USE_IPU_THREAD /* run IPU in sel32_ipu.c thread */
#endif #endif
@ -55,13 +52,18 @@
#define DEFINE_IPU_MODELS /* IPU devices must be define for IPU */ #define DEFINE_IPU_MODELS /* IPU devices must be define for IPU */
#ifndef USE_IPU_THREAD #ifndef USE_IPU_THREAD
#define USE_POSIX_SEM /* forked mode IPU can only use semaphores */ #define USE_POSIX_SEM /* forked mode IPU can only use semaphores */
/* include signal.h when using fork for 2nd SIMH */
#include <signal.h>
#else
#undef USE_POSIX_SEM /* make sure no POSIX semaphores for IPU thread code */
#endif #endif
#else /* CPUONLY */ #else /* NOT CPUONLY */
#undef USE_IPU_THREAD /* make sure IPU code undefined for CPUONLY */ #undef USE_IPU_THREAD /* make sure IPU code undefined for CPUONLY */
#undef DEFINE_IPU_MODELS /* make sure IPU models undefine too */ #undef DEFINE_IPU_MODELS /* make sure IPU models undefine too */
#undef USE_POSIX_SEM /* make sure no POSIX semaphores for CPU only */
#endif /* CPU_ONLY */ #endif /* CPU_ONLY */
/* use correct variable type for thread IPU */ /* use correct variable type for IPU thread */
#ifdef USE_IPU_THREAD #ifdef USE_IPU_THREAD
#ifdef USE_IPU_CODE #ifdef USE_IPU_CODE
#define LOCAL static /* IPU in thread needs static variables */ #define LOCAL static /* IPU in thread needs static variables */
@ -118,10 +120,10 @@ struct ipcom {
#define STOP_IONRDY 1 /* I/O dev not ready */ #define STOP_IONRDY 1 /* I/O dev not ready */
#define STOP_HALT 2 /* HALT */ #define STOP_HALT 2 /* HALT */
#define STOP_IBKPT 3 /* breakpoint */ #define STOP_IBKPT 3 /* breakpoint */
#define STOP_UUO 4 /* invalid opcode */ #define STOP_RESET 4 /* cpu doing reset */
#define STOP_INVINS 5 /* invalid instr */ #define STOP_INVINS 5 /* invalid instr */
#define STOP_INVIOP 6 /* invalid I/O op */ #define STOP_INVIOP 6 /* invalid I/O op */
#define STOP_INDLIM 7 /* indirect limit */ #define STOP_WAITING 7 /* waiting for cpu to run */
#define STOP_XECLIM 8 /* XEC limit */ #define STOP_XECLIM 8 /* XEC limit */
#define STOP_IOCHECK 9 /* IOCHECK */ #define STOP_IOCHECK 9 /* IOCHECK */
#define STOP_MMTRP 10 /* mm in trap */ #define STOP_MMTRP 10 /* mm in trap */
@ -378,18 +380,6 @@ extern DIB *dib_chan[MAX_CHAN]; /* Pointer to channel mux dib */
#define DEV_BUF_NUM(x) (((x) & 07) << DEV_V_UF2) #define DEV_BUF_NUM(x) (((x) & 07) << DEV_V_UF2)
#define GET_DEV_BUF(x) (((x) >> DEV_V_UF2) & 07) #define GET_DEV_BUF(x) (((x) >> DEV_V_UF2) & 07)
#ifdef NOT_USED_NOW
//#define DEV_V_ADDR DEV_V_UF /* Pointer to device address (16) */
//#define DEV_V_DADDR (DEV_V_UF + 8) /* Device address */
//#define DEV_ADDR_MASK (0x7f << DEV_V_DADDR) /* 24 bits shift */
//#define DEV_V_UADDR (DEV_V_UF) /* Device address in Unit */
//#define DEV_UADDR (1 << DEV_V_UADDR)
//#define GET_DADDR(x) (0x7f & ((x) >> DEV_V_ADDR))
//#define DEV_ADDR(x) ((x) << DEV_V_ADDR)
//#define PROTECT_V UNIT_V_UF+15
//#define PROTECT (1 << PROTECT_V)
#endif
/* defined in rightmost 8 bits of upper 16 bits of uptr->flags */ /* defined in rightmost 8 bits of upper 16 bits of uptr->flags */
/* allow 255 type disks */ /* allow 255 type disks */
#define UNIT_SUBCHAN (1 << (UNIT_V_UF_31)) #define UNIT_SUBCHAN (1 << (UNIT_V_UF_31))

View file

@ -30,7 +30,7 @@
#if NUM_DEVS_DISK > 0 #if NUM_DEVS_DISK > 0
#define UNIT_DISK UNIT_ATTABLE | UNIT_IDLE | UNIT_DISABLE #define UNIT_DISK UNIT_ATTABLE|UNIT_DISABLE
extern uint32 SPAD[]; /* cpu SPAD memory */ extern uint32 SPAD[]; /* cpu SPAD memory */
@ -366,19 +366,11 @@ disk_type[] =
{ {
/* Class F Disc Devices */ /* Class F Disc Devices */
/* For MPX */ /* For MPX */
#ifndef NOTFORMPX1X
{"MH040", 5, 192, 20, 407, 411, 0x40}, /* 0 411 40M XXXX */ {"MH040", 5, 192, 20, 407, 411, 0x40}, /* 0 411 40M XXXX */
{"MH080", 5, 192, 20, 819, 823, 0x40}, /* 1 823 80M 8138 */ {"MH080", 5, 192, 20, 819, 823, 0x40}, /* 1 823 80M 8138 */
{"MH160", 10, 192, 20, 819, 823, 0x40}, /* 2 823 160M 8148 */ {"MH160", 10, 192, 20, 819, 823, 0x40}, /* 2 823 160M 8148 */
{"MH300", 19, 192, 20, 819, 823, 0x40}, /* 3 823 300M 8127 */ {"MH300", 19, 192, 20, 819, 823, 0x40}, /* 3 823 300M 8127 */
{"MH600", 40, 192, 20, 839, 843, 0x40}, /* 4 843 600M 8155 */ {"MH600", 40, 192, 20, 839, 843, 0x40}, /* 4 843 600M 8155 */
#else
{"MH040", 5, 192, 20, 400, 411, 0x40}, /* 0 411 40M XXXX */
{"MH080", 5, 192, 20, 800, 823, 0x40}, /* 1 823 80M 8138 */
{"MH160", 10, 192, 20, 800, 823, 0x40}, /* 2 823 160M 8148 */
{"MH300", 19, 192, 20, 800, 823, 0x40}, /* 3 823 300M 8127 */
{"MH600", 40, 192, 20, 800, 843, 0x40}, /* 4 843 600M 8155 */
#endif
/* For UTX */ /* For UTX */
{"9342", 5, 256, 16, 819, 823, 0x41}, /* 5 823 80M XXXX */ {"9342", 5, 256, 16, 819, 823, 0x41}, /* 5 823 80M XXXX */
{"8148", 10, 256, 16, 819, 823, 0x41}, /* 6 823 160M 8148 */ {"8148", 10, 256, 16, 819, 823, 0x41}, /* 6 823 160M 8148 */
@ -479,7 +471,7 @@ DEVICE dda_dev = {
NULL, NULL, &disk_reset, &disk_boot, &disk_attach, &disk_detach, NULL, NULL, &disk_reset, &disk_boot, &disk_attach, &disk_detach,
/* ctxt is the DIB pointer */ /* ctxt is the DIB pointer */
&dda_dib, DEV_DISABLE|DEV_DEBUG|DEV_DIS, 0, dev_debug, &dda_dib, DEV_DISABLE|DEV_DEBUG|DEV_DIS, 0, dev_debug,
NULL, NULL, &disk_help, NULL, NULL, &disk_description NULL, NULL, &disk_help, NULL, NULL, &disk_description,
}; };
#if NUM_DEVS_DISK > 1 #if NUM_DEVS_DISK > 1
@ -525,7 +517,7 @@ DEVICE ddb_dev = {
NULL, NULL, &disk_reset, &disk_boot, &disk_attach, &disk_detach, NULL, NULL, &disk_reset, &disk_boot, &disk_attach, &disk_detach,
/* ctxt is the DIB pointer */ /* ctxt is the DIB pointer */
&ddb_dib, DEV_DISABLE|DEV_DEBUG|DEV_DIS, 0, dev_debug, &ddb_dib, DEV_DISABLE|DEV_DEBUG|DEV_DIS, 0, dev_debug,
NULL, NULL, &disk_help, NULL, NULL, &disk_description NULL, NULL, &disk_help, NULL, NULL, &disk_description,
}; };
#endif #endif
@ -953,7 +945,7 @@ loop:
} }
/* the device processor returned OK (0), so wait for I/O to complete */ /* the device processor returned OK (0), so wait for I/O to complete */
/* nothing happening, so return */ /* nothing happening, so return */
sim_debug(DEBUG_DETAIL, dptr, sim_debug(DEBUG_CMD, dptr,
"disk_iocl @%06x return, chan %04x status %04x count %04x irq_pend %1x\n", "disk_iocl @%06x return, chan %04x status %04x count %04x irq_pend %1x\n",
chp->chan_caw, chan, chp->chan_status, chp->ccw_count, irq_pend); chp->chan_caw, chan, chp->chan_status, chp->ccw_count, irq_pend);
return 0; /* good return */ return 0; /* good return */
@ -1044,15 +1036,13 @@ t_stat disk_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
/* when value was 50, UTX would get a spontainous interrupt */ /* when value was 50, UTX would get a spontainous interrupt */
/* when value was 30, UTX would get a spontainous interrupt */ /* when value was 30, UTX would get a spontainous interrupt */
/* changed to 25 from 30 121420 */
//utx21a sim_activate(uptr, 20); /* start things off */
/* changed to 15 from 20 12/17/2021 to fix utx21a getting */ /* changed to 15 from 20 12/17/2021 to fix utx21a getting */
/* "panic: ioi: tis_busy - bad cc" during root fsck on boot */ /* "panic: ioi: tis_busy - bad cc" during root fsck on boot */
/* changed back to 20 from 15 12/18/2021 to refix utx21a getting */ /* changed back to 20 from 15 12/18/2021 to refix utx21a getting */
/* "panic: ioi: tis_busy - bad cc" during root fsck on boot */ /* "panic: ioi: tis_busy - bad cc" during root fsck on boot */
sim_activate(uptr, 20); /* start things off */ sim_activate(uptr, 30); /* start things off */
/* when using 500, UTX gets "ioi: sio at 801 failed, cc3, retry=0" */
#else #else
/* when using 500, UTX gets "ioi: sio at 801 failed, cc3, retry=0" */
sim_activate(uptr, 500); /* start things off */ sim_activate(uptr, 500); /* start things off */
#endif #endif
return SCPE_OK; /* good to go */ return SCPE_OK; /* good to go */
@ -1670,7 +1660,7 @@ iha_error:
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
sim_activate(uptr, 15); /* start us off */ sim_activate(uptr, 15); /* start us off */
#else #else
sim_activate(uptr, 400+diff); /* start us off */ sim_activate(uptr, 200+diff); /* start us off */
#endif #endif
} else { } else {
/* we are on cylinder/track/sector, so go on */ /* we are on cylinder/track/sector, so go on */
@ -1838,7 +1828,7 @@ iha_error:
"DISK READ starting CMD %08x chsa %04x buffer %06x count %04x\n", "DISK READ starting CMD %08x chsa %04x buffer %06x count %04x\n",
uptr->CMD, chsa, chp->ccw_addr, chp->ccw_count); uptr->CMD, chsa, chp->ccw_addr, chp->ccw_count);
} }
domore_read:
if (uptr->CMD & DSK_READING) { /* see if we are reading data */ if (uptr->CMD & DSK_READING) { /* see if we are reading data */
/* get file offset in sectors */ /* get file offset in sectors */
tstart = STAR2SEC(uptr->CHS, SPT(type), SPC(type)); tstart = STAR2SEC(uptr->CHS, SPT(type), SPC(type));
@ -2051,11 +2041,14 @@ if ((chp->ccw_addr == 0x3cde0) && (buf[0] == 0x4a)) {
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"DISK sector read complete, %x bytes to go from diskfile %04x/%02x/%02x\n", "DISK sector read complete, %x bytes to go from diskfile %04x/%02x/%02x\n",
chp->ccw_count, STAR2CYL(uptr->CHS), ((uptr->CHS) >> 8)&0xff, (uptr->CHS&0xff)); chp->ccw_count, STAR2CYL(uptr->CHS), ((uptr->CHS) >> 8)&0xff, (uptr->CHS&0xff));
#ifdef WRITE_ALL_AT_ONCE
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
sim_activate(uptr, 10); /* wait to read next sector */ sim_activate(uptr, 10); /* wait to read next sector */
#else #else
sim_activate(uptr, 300); /* wait to read next sector */ sim_activate(uptr, 300); /* wait to read next sector */
#endif #endif
#endif
goto domore_read; /* keep reading */
break; break;
} }
uptr->CMD &= LMASK; /* remove old status bits & cmd */ uptr->CMD &= LMASK; /* remove old status bits & cmd */
@ -2080,6 +2073,7 @@ if ((chp->ccw_addr == 0x3cde0) && (buf[0] == 0x4a)) {
} }
uptr->CMD |= DSK_WRITING; /* write to disk starting */ uptr->CMD |= DSK_WRITING; /* write to disk starting */
} }
domore_write:
if (uptr->CMD & DSK_WRITING) { /* see if we are writing data */ if (uptr->CMD & DSK_WRITING) { /* see if we are writing data */
/* get file offset in sectors */ /* get file offset in sectors */
tstart = STAR2SEC(uptr->CHS, SPT(type), SPC(type)); tstart = STAR2SEC(uptr->CHS, SPT(type), SPC(type));
@ -2264,11 +2258,14 @@ if ((chp->ccw_addr == 0x3cde0) && (buf[0] == 0x4a)) {
break; break;
} }
#ifdef WRITE_ALL_AT_ONCE
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
sim_activate(uptr, 15); /* wait to read next sector */ sim_activate(uptr, 15); /* wait to write next sector */
#else #else
sim_activate(uptr, 300); /* wait to read next sector */ sim_activate(uptr, 300); /* wait to write next sector */
#endif #endif
#endif
goto domore_write; /* keep writing */
break; break;
} }
uptr->CMD &= LMASK; /* remove old status bits & cmd */ uptr->CMD &= LMASK; /* remove old status bits & cmd */
@ -2711,7 +2708,7 @@ t_stat disk_reset(DEVICE *dptr)
{ {
int cn, unit; int cn, unit;
for(unit=0; unit < NUM_UNITS_DISK; unit++) { for (unit=0; unit < NUM_UNITS_DISK; unit++) {
for (cn=0; cn<TRK_CACHE; cn++) { for (cn=0; cn<TRK_CACHE; cn++) {
tkl_label[unit].tkl[cn].track = 0; tkl_label[unit].tkl[cn].track = 0;
tkl_label[unit].tkl[cn].age = 0; tkl_label[unit].tkl[cn].age = 0;

View file

@ -384,15 +384,6 @@ loop:
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"ec_iocl @%06x read ccw chsa %04x IOCD wd 1 %08x wd 2 %08x SNS %08x\n", "ec_iocl @%06x read ccw chsa %04x IOCD wd 1 %08x wd 2 %08x SNS %08x\n",
chp->chan_caw, chp->chan_dev, word1, word2, uptr->SNS); chp->chan_caw, chp->chan_dev, word1, word2, uptr->SNS);
//#define DYNAMIC_DEBUG
#ifdef DYNAMIC_DEBUG
if ((word1 == 0x0202f000) && (word2 == 0x0000003C) && (uptr->SNS == 0x0080003e)) {
cpu_dev.dctrl |= (DEBUG_INST|DEBUG_XIO); /* start instruction trace */
} else
if ((word1 == 0x0202f000) && (word2 == 0x00000040) && (uptr->SNS == 0x0080003e)) {
cpu_dev.dctrl &= ~(DEBUG_INST|DEBUG_XIO); /* stop instruction trace */
}
#endif
chp->chan_caw = (chp->chan_caw & 0xfffffc) + 8; /* point to next IOCD */ chp->chan_caw = (chp->chan_caw & 0xfffffc) + 8; /* point to next IOCD */
@ -691,8 +682,10 @@ t_stat ec_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
uptr->CMD |= (cmd|EC_BUSY); /* save cmd */ uptr->CMD |= (cmd|EC_BUSY); /* save cmd */
// This works most of the time & stops at test 30 with no len errors // This works most of the time & stops at test 30 with no len errors
//Was sim_activate(uptr, 5000); /* start things off */ //Was sim_activate(uptr, 5000); /* start things off */
// This works // This works most of the time
/*jb*/ sim_activate(uptr, 7500); /* start things off */ //GF sim_activate(uptr, 7500); /* start things off */
//JCB sim_activate_abs(uptr, 750); /* start things off */
sim_activate_abs(uptr, 750); /* start things off */
return 0; return 0;
case EC_INCH: /* INCH cmd 0x0 */ case EC_INCH: /* INCH cmd 0x0 */
cmd = EC_INCH2; /* set dummy INCH cmd 0xf0 */ cmd = EC_INCH2; /* set dummy INCH cmd 0xf0 */
@ -708,8 +701,9 @@ t_stat ec_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
/* Fall through */ /* Fall through */
case EC_SNS: /* Sense 0x04 */ case EC_SNS: /* Sense 0x04 */
uptr->CMD |= cmd|EC_BUSY; /* save cmd */ uptr->CMD |= cmd|EC_BUSY; /* save cmd */
//Was M sim_activate(uptr, 100); /* start things off */ //GF sim_activate(uptr, 150); /* start things off */
sim_activate(uptr, 150); /* start things off */ //JCB sim_activate_abs(uptr, 150); /* start things off */
sim_activate_abs(uptr, 750); /* start things off */
return 0; return 0;
} }
@ -732,8 +726,6 @@ t_stat ec_rec_srv(UNIT *uptr)
if (q > LOOP_MSK) if (q > LOOP_MSK)
q -= (LOOP_MSK + 1); q -= (LOOP_MSK + 1);
if (eth_read(&ec_data.etherface, &ec_data.rec_buff[ec_data.rec_ptr], NULL) > 0) { if (eth_read(&ec_data.etherface, &ec_data.rec_buff[ec_data.rec_ptr], NULL) > 0) {
//jb if (((ec_data.rec_ptr + 1) & LOOP_MSK) == ec_data.xtr_ptr) {
//jb if (q > 16) {
if (q > 716) { if (q > 716) {
ec_data.drop_cnt++; ec_data.drop_cnt++;
sim_debug(DEBUG_DETAIL, dptr, sim_debug(DEBUG_DETAIL, dptr,
@ -763,7 +755,7 @@ t_stat ec_srv(UNIT *uptr)
CHANP *chp = find_chanp_ptr(chsa); /* get channel prog pointer */ CHANP *chp = find_chanp_ptr(chsa); /* get channel prog pointer */
int cmd = uptr->CMD & EC_CMDMSK; int cmd = uptr->CMD & EC_CMDMSK;
uint32 mema; uint32 mema;
int i; int i, pktlen;
int n, len; int n, len;
int pirq, cnt, dcnt; int pirq, cnt, dcnt;
uint8 ch; uint8 ch;
@ -809,7 +801,7 @@ t_stat ec_srv(UNIT *uptr)
case EC_LIA: /* 0x07 Load individual address */ case EC_LIA: /* 0x07 Load individual address */
uptr->CMD &= LMASK; /* remove old status bits & cmd */ uptr->CMD &= LMASK; /* remove old status bits & cmd */
for(i = 0; i < sizeof (ETH_MAC); i++) { for (i = 0; i < sizeof (ETH_MAC); i++) {
if (chan_read_byte(chsa, &buf[i])) { if (chan_read_byte(chsa, &buf[i])) {
chan_end(chsa, SNS_CHNEND|SNS_DEVEND|SNS_UNITCHK); chan_end(chsa, SNS_CHNEND|SNS_DEVEND|SNS_UNITCHK);
return SCPE_OK; return SCPE_OK;
@ -846,8 +838,8 @@ t_stat ec_srv(UNIT *uptr)
uptr->CMD &= LMASK; /* remove old status bits & cmd */ uptr->CMD &= LMASK; /* remove old status bits & cmd */
ec_data.macs_n = 0; ec_data.macs_n = 0;
len = 2; len = 2;
for(n = 2; n < (int)(sizeof(ec_data.macs) / sizeof (ETH_MAC)); n++) { for (n = 2; n < (int)(sizeof(ec_data.macs) / sizeof (ETH_MAC)); n++) {
for(i = 0; i < sizeof (ETH_MAC); i++) { for (i = 0; i < sizeof (ETH_MAC); i++) {
if (chan_read_byte(chsa, &buf[i])) { if (chan_read_byte(chsa, &buf[i])) {
break; break;
} }
@ -885,6 +877,7 @@ t_stat ec_srv(UNIT *uptr)
hdr = (struct ec_eth_hdr *)(&ec_data.snd_buff.msg[0]); hdr = (struct ec_eth_hdr *)(&ec_data.snd_buff.msg[0]);
pck = (uint8 *)(&ec_data.snd_buff.msg[0]); pck = (uint8 *)(&ec_data.snd_buff.msg[0]);
uptr->SNS &= LMASK; /* remove old count */ uptr->SNS &= LMASK; /* remove old count */
pktlen = 0;
/* create packet: destination(6)/source(6)/type(2) or len(2)/ data 46-1500 */ /* create packet: destination(6)/source(6)/type(2) or len(2)/ data 46-1500 */
switch (GET_MODE(ec_master_uptr->flags)) { switch (GET_MODE(ec_master_uptr->flags)) {
@ -893,7 +886,7 @@ t_stat ec_srv(UNIT *uptr)
/* create packet: destination(6)/source(6)/type(2) or len(2)/ data 46-1500 */ /* create packet: destination(6)/source(6)/type(2) or len(2)/ data 46-1500 */
/* copy users header unchanged */ /* copy users header unchanged */
for(i = 0; i < sizeof(struct ec_eth_hdr); i++) { for (i = 0; i < sizeof(struct ec_eth_hdr); i++) {
if (chan_read_byte(chsa, &pck[i])) { if (chan_read_byte(chsa, &pck[i])) {
pirq = 1; pirq = 1;
n = i; n = i;
@ -909,17 +902,33 @@ t_stat ec_srv(UNIT *uptr)
i = sizeof(struct ec_eth_hdr); /* dest/src/len 14 bytes */ i = sizeof(struct ec_eth_hdr); /* dest/src/len 14 bytes */
while (chan_read_byte(chsa, &ch) == 0) { while (chan_read_byte(chsa, &ch) == 0) {
if (i < ETH_MAX_PACKET) { if (i < ETH_MAX_PACKET) {
if (i>6 && i<28) if (i>6 && i<28) /* only display char 7-27 */
sim_debug(DEBUG_DATA, dptr, "ec_srv data[%3x]: %06x %02x\n", sim_debug(DEBUG_DATA, dptr, "ec_srv data[%2x]: %06x %02x\n",
i, chp->ccw_addr, ch); i, chp->ccw_addr, ch);
pck[i] = ch; pck[i] = ch;
if (i == len + 2)
pktlen = pck[i] << 8; /* 1st 1/2 of user data len without ethernet header */
if (i == len + 3)
pktlen |= pck[i]; /* 2nd 1/2 of user data len without ethernet header */
} }
i++; i++;
uptr->SNS++; /* set count */ uptr->SNS++; /* set count */
/* set correct packet count or ICMP and ARP response packet */
if (((chsa & 0xff) == 6) && (i > (len+3))) {/* make sure we have pkt len read in */
if (ntohs(hdr->type) == ETHTYPE_IP) { /* make sure IP packet */
if (i >= (pktlen+len)) /* see if all of data sent */
break; /* only transfer actual data */
} else
if (ntohs(hdr->type) == ETHTYPE_ARP) { /* make sure ARP packet */
if (i >= (46+len)) /* see if 60 byte packet present */
break; /* only transfer actual data */
}
}
} }
sim_debug(DEBUG_DETAIL, dptr, sim_debug(DEBUG_DETAIL, dptr,
"ec_srv case 0 transmit bytes %d (0x%x) SNS %08x\n", "ec_srv case 0 transmit bytes %d (0x%x) SNS %08x pktlen 0x%x\n",
len, len, uptr->SNS); len, len, uptr->SNS, pktlen);
break; break;
case 1: case 1:
case 2: case 2:
@ -928,7 +937,7 @@ t_stat ec_srv(UNIT *uptr)
/* copy in user dest/type/data */ /* copy in user dest/type/data */
/* get 6 byte destination from user */ /* get 6 byte destination from user */
for(i = 0; i < sizeof(ETH_MAC); i++) { for (i = 0; i < sizeof(ETH_MAC); i++) {
if (chan_read_byte(chsa, &pck[i])) { if (chan_read_byte(chsa, &pck[i])) {
pirq = 1; pirq = 1;
n = i; n = i;
@ -940,7 +949,7 @@ t_stat ec_srv(UNIT *uptr)
memcpy(&hdr->src, ec_data.mac, sizeof(ETH_MAC)); memcpy(&hdr->src, ec_data.mac, sizeof(ETH_MAC));
/* copy two byte type/len from user buffer */ /* copy two byte type/len from user buffer */
for(i = sizeof(ETH_MAC) * 2; i < sizeof(struct ec_eth_hdr); i++) { for (i = sizeof(ETH_MAC) * 2; i < sizeof(struct ec_eth_hdr); i++) {
if (chan_read_byte(chsa, &pck[i])) { if (chan_read_byte(chsa, &pck[i])) {
pirq = 1; pirq = 1;
n = i; n = i;
@ -956,17 +965,33 @@ t_stat ec_srv(UNIT *uptr)
i = sizeof(struct ec_eth_hdr); /* dest/src/len 14 bytes */ i = sizeof(struct ec_eth_hdr); /* dest/src/len 14 bytes */
while (chan_read_byte(chsa, &ch) == 0) { while (chan_read_byte(chsa, &ch) == 0) {
if (i < ETH_MAX_PACKET) { if (i < ETH_MAX_PACKET) {
if (i>6 && i<28) if (i>6 && i<28) /* only display char 7-27 */
sim_debug(DEBUG_DATA, dptr, "ec_srv data[%3x]: %06x %02x\n", sim_debug(DEBUG_DATA, dptr, "ec_srv data[%2x]: %06x %02x\n",
i, chp->ccw_addr, ch); i, chp->ccw_addr, ch);
pck[i] = ch; pck[i] = ch;
if (i == (len+2))
pktlen = pck[i] << 8; /* 1st 1/2 of user data len without ethernet header */
if (i == (len+3))
pktlen |= pck[i]; /* 2nd 1/2 of user data len without ethernet header */
} }
i++; i++;
uptr->SNS++; /* set count */ uptr->SNS++; /* set count */
/* set correct packet count or ICMP and ARP response packet */
if (((chsa & 0xff) == 6) && (i > (len+3))) {/* make sure we have pkt len read in */
if (ntohs(hdr->type) == ETHTYPE_IP) { /* make sure IP packet */
if (i >= (pktlen+len)) /* see if all of data sent */
break; /* only transfer actual data */
} else
if (ntohs(hdr->type) == ETHTYPE_ARP) { /* make sure ARP packet */
if (i >= (46+len)) /* see if 60 byte packet present */
break; /* only transfer actual data */
}
}
} }
sim_debug(DEBUG_DETAIL, dptr, sim_debug(DEBUG_DETAIL, dptr,
"ec_srv case 1&2 transmit bytes %d (0x%x) SNS %08x i 0x%x\n", "ec_srv case 1&2 transmit bytes %d (0x%x) SNS %08x i 0x%x pktlen 0x%x\n",
len-6, len-6, uptr->SNS, i); len-6, len-6, uptr->SNS, i, pktlen);
/* This code is to simulate word transfers into memory */ /* This code is to simulate word transfers into memory */
/* from the users buffer. 1-3 extra bytes are placed */ /* from the users buffer. 1-3 extra bytes are placed */
@ -989,7 +1014,7 @@ t_stat ec_srv(UNIT *uptr)
/* create packet: destination(6)/source(6)/type(2) or len(2)/ data 46-1500 */ /* create packet: destination(6)/source(6)/type(2) or len(2)/ data 46-1500 */
/* copy destination(6) from user buffer */ /* copy destination(6) from user buffer */
for(i = 0; i < sizeof(ETH_MAC); i++) { for (i = 0; i < sizeof(ETH_MAC); i++) {
if (chan_read_byte(chsa, &pck[i])) { if (chan_read_byte(chsa, &pck[i])) {
pirq = 1; pirq = 1;
n = i; n = i;
@ -1020,12 +1045,27 @@ t_stat ec_srv(UNIT *uptr)
sim_debug(DEBUG_DATA, dptr, "ec_srv data[%3x]: %06x %02x\n", sim_debug(DEBUG_DATA, dptr, "ec_srv data[%3x]: %06x %02x\n",
i, chp->ccw_addr, ch); i, chp->ccw_addr, ch);
pck[i] = ch; pck[i] = ch;
if (i == len + 2)
pktlen = pck[i] << 8; /* 1st 1/2 of user data len without ethernet header */
if (i == len + 3)
pktlen |= pck[i]; /* 2nd 1/2 of user data len without ethernet header */
} }
i++; i++;
uptr->SNS++; /* set count */ uptr->SNS++; /* set count */
#ifndef USE_DATA_CNT #ifndef USE_DATA_CNT
cnt++; /* user data count */ cnt++; /* user data count */
#endif #endif
/* set correct packet count or ICMP and ARP response packet */
if (((chsa & 0xff) == 6) && (i > (len+3))) {/* make sure we have pkt len read in */
if (ntohs(hdr->type) == ETHTYPE_IP) { /* make sure IP packet */
if (i >= (pktlen+len)) /* see if all of data sent */
break; /* only transfer actual data */
} else
if (ntohs(hdr->type) == ETHTYPE_ARP) { /* make sure ARP packet */
if (i >= (46+len)) /* see if 60 byte packet present */
break; /* only transfer actual data */
}
}
} }
#ifndef USE_DATA_CNT #ifndef USE_DATA_CNT
@ -1035,8 +1075,8 @@ t_stat ec_srv(UNIT *uptr)
#endif #endif
sim_debug(DEBUG_DETAIL, dptr, sim_debug(DEBUG_DETAIL, dptr,
"ec_srv case 3 transmit bytes %d (0x%x) SNS %08x i 0x%x cnt %x\n", "ec_srv case 3 transmit bytes %d (0x%x) SNS %08x i 0x%x cnt %x pktlen 0x%x\n",
len-8, len-8, uptr->SNS, i, cnt); len-8, len-8, uptr->SNS, i, cnt, pktlen);
/* This code is to simulate word transfers into memory */ /* This code is to simulate word transfers into memory */
/* from the users buffer. 1-3 extra bytes are placed */ /* from the users buffer. 1-3 extra bytes are placed */
@ -1059,8 +1099,8 @@ wr_end:
ec_data.snd_buff.len = i; /* set actual count */ ec_data.snd_buff.len = i; /* set actual count */
ec_packet_debug(&ec_data, "send", &ec_data.snd_buff); ec_packet_debug(&ec_data, "send", &ec_data.snd_buff);
sim_debug(DEBUG_DETAIL, dptr, sim_debug(DEBUG_DETAIL, dptr,
"ec_srv @wr_end count 0x%x i 0x%04x SNS 0x%04x\n", "ec_srv @wr_end count 0x%x i 0x%04x SNS 0x%04x pktlen 0x%x type 0x%x\n",
chp->ccw_count, i, uptr->SNS); chp->ccw_count, i, uptr->SNS, pktlen, ntohs(hdr->type));
/* make sure packet is minimum size for mode 1,2 & 3 */ /* make sure packet is minimum size for mode 1,2 & 3 */
/* when handling non-loopback packets */ /* when handling non-loopback packets */
@ -1071,7 +1111,7 @@ wr_end:
/* this fixes test 20 for mode 3 */ /* this fixes test 20 for mode 3 */
(GET_MODE(ec_master_uptr->flags) != 3)) { (GET_MODE(ec_master_uptr->flags) != 3)) {
/* Pad the packet */ /* Pad the packet */
while(i < ETH_MIN_PACKET) { while (i < ETH_MIN_PACKET) {
ec_data.snd_buff.len++; /* increment actual count */ ec_data.snd_buff.len++; /* increment actual count */
pck[n++] = 0; pck[n++] = 0;
i++; i++;
@ -1099,8 +1139,6 @@ wr_end:
int q = (((ec_data.rec_ptr + 1) & LOOP_MSK) + LOOP_MSK + 1) - ec_data.xtr_ptr; int q = (((ec_data.rec_ptr + 1) & LOOP_MSK) + LOOP_MSK + 1) - ec_data.xtr_ptr;
if (q >LOOP_MSK) if (q >LOOP_MSK)
q -= (LOOP_MSK + 1); q -= (LOOP_MSK + 1);
//jb if (((ec_data.rec_ptr + 1) & LOOP_MSK) == ec_data.xtr_ptr) {
//jb if (q > 16) {
if (q > 716) { if (q > 716) {
ec_data.drop_cnt++; ec_data.drop_cnt++;
sim_debug(DEBUG_DETAIL, dptr, "ec_srv write packet dropped %d q %d\n", sim_debug(DEBUG_DETAIL, dptr, "ec_srv write packet dropped %d q %d\n",
@ -1116,7 +1154,6 @@ wr_end:
/* check for internal loopback */ /* check for internal loopback */
if ((ec_data.conf[0] & 0x40) == 0) { if ((ec_data.conf[0] & 0x40) == 0) {
#ifndef NEW_02052021
/* not internal loopback, user wants to write to network */ /* not internal loopback, user wants to write to network */
/* check if attached, if not give no carrier and unit exception */ /* check if attached, if not give no carrier and unit exception */
if ((ec_master_uptr->flags & UNIT_ATT) == 0) { if ((ec_master_uptr->flags & UNIT_ATT) == 0) {
@ -1127,7 +1164,6 @@ wr_end:
chan_end(chsa, SNS_CHNEND|SNS_DEVEND|STATUS_EXPT); chan_end(chsa, SNS_CHNEND|SNS_DEVEND|STATUS_EXPT);
break; break;
} }
#endif
/* no loopback, write out the packet */ /* no loopback, write out the packet */
if (eth_write(&ec_data.etherface, &ec_data.snd_buff, NULL) != SCPE_OK) { if (eth_write(&ec_data.etherface, &ec_data.snd_buff, NULL) != SCPE_OK) {
sim_debug(DEBUG_DETAIL, dptr, "ec_srv short packet %d\n", i); sim_debug(DEBUG_DETAIL, dptr, "ec_srv short packet %d\n", i);
@ -1151,12 +1187,10 @@ wr_end:
if (ec_data.xtr_ptr == ec_data.rec_ptr) { if (ec_data.xtr_ptr == ec_data.rec_ptr) {
// sim_debug(DEBUG_DETAIL, &ec_dev, "ec_srv WAIT %04x read %d %d size=%d cnt %d\n", // sim_debug(DEBUG_DETAIL, &ec_dev, "ec_srv WAIT %04x read %d %d size=%d cnt %d\n",
// chsa, ec_data.xtr_ptr, ec_data.rec_ptr, ec_data.conf[9], chp->ccw_count); // chsa, ec_data.xtr_ptr, ec_data.rec_ptr, ec_data.conf[9], chp->ccw_count);
//XX sim_clock_coschedule(uptr, 1500); /* continue poll */
//HH sim_activate(uptr, 1511); /* continue poll */
/* this is OK for mode 0, 1, 2, 3 */
//12dec21 sim_activate(uptr, 2511); /* continue poll */
/* this is really a 50000 cnt poll by simh */ /* this is really a 50000 cnt poll by simh */
sim_clock_coschedule(uptr, 1000); /* continue poll */ //GF sim_clock_coschedule(uptr, 1000); /* continue poll */
//JCB sim_activate_abs(uptr, 2000); /* continue poll */
sim_activate_abs(uptr, 6000); /* continue poll */
return SCPE_OK; return SCPE_OK;
} }
/* get queue length */ /* get queue length */
@ -1187,14 +1221,14 @@ wr_end:
len = (int)(ec_data.rec_buff[ec_data.xtr_ptr].len); len = (int)(ec_data.rec_buff[ec_data.xtr_ptr].len);
n = sizeof(struct ec_eth_hdr); n = sizeof(struct ec_eth_hdr);
cnt = len - n; /* number of data bytes */ cnt = len - n; /* number of data bytes */
sim_debug(DEBUG_DETAIL, &ec_dev, "ec_srv READ addr %06x pktlen 0x%x rdcnt 0x%x conf 0x%x\n", sim_debug(DEBUG_DETAIL, &ec_dev, "ec_srv READ addr %06x pktlen 0x%x rdcnt 0x%x conf 0x%x cnt 0x%x\n",
chp->ccw_addr, len, chp->ccw_count, ec_data.conf[9]); chp->ccw_addr, len, chp->ccw_count, ec_data.conf[9], cnt);
switch (GET_MODE(ec_master_uptr->flags)) { switch (GET_MODE(ec_master_uptr->flags)) {
case 0: case 0:
/* create output: destination(6)/source(6)/type(2) or len(2)/ data 46-1500 */ /* create output: destination(6)/source(6)/type(2) or len(2)/ data 46-1500 */
/* user buffer: destination(6)/source(6)/type(2) or len)2) */ /* user buffer: destination(6)/source(6)/type(2) or len)2) */
for(i = 0; i < sizeof(struct ec_eth_hdr); i++) { for (i = 0; i < sizeof(struct ec_eth_hdr); i++) {
if (chan_write_byte(chsa, &pck[i])) { if (chan_write_byte(chsa, &pck[i])) {
pirq = 1; pirq = 1;
break; break;
@ -1210,7 +1244,7 @@ wr_end:
/* create output: destination(6)/len(2)/source(6)/type(2) or len(2)/ data 46-1500 */ /* create output: destination(6)/len(2)/source(6)/type(2) or len(2)/ data 46-1500 */
/* destination / len / source / type or len */ /* destination / len / source / type or len */
/* copy 6 byte destination */ /* copy 6 byte destination */
for(i = 0; i < sizeof(ETH_MAC); i++) { for (i = 0; i < sizeof(ETH_MAC); i++) {
if (chan_write_byte(chsa, &pck[i])) { if (chan_write_byte(chsa, &pck[i])) {
pirq = 1; pirq = 1;
break; break;
@ -1229,7 +1263,7 @@ wr_end:
break; break;
} }
/* copy in source(6)/type(2) 6 + 2 = 8 = 14 - 6 */ /* copy in source(6)/type(2) 6 + 2 = 8 = 14 - 6 */
for(; i < sizeof(struct ec_eth_hdr); i++) { for (; i < sizeof(struct ec_eth_hdr); i++) {
if (chan_write_byte(chsa, &pck[i])) { if (chan_write_byte(chsa, &pck[i])) {
pirq = 1; pirq = 1;
break; break;
@ -1245,7 +1279,7 @@ wr_end:
case 3: case 3:
/* create output: destination(6)/len(2)/source(6)/len(2)/ data 46-1500 */ /* create output: destination(6)/len(2)/source(6)/len(2)/ data 46-1500 */
/* copy 6 byte destination */ /* copy 6 byte destination */
for(i = 0; i < sizeof(ETH_MAC); i++) { for (i = 0; i < sizeof(ETH_MAC); i++) {
if (chan_write_byte(chsa, &pck[i])) { if (chan_write_byte(chsa, &pck[i])) {
pirq = 1; pirq = 1;
break; break;
@ -1450,7 +1484,6 @@ wr_end:
"ec_startcmd CMD sense excess cnt %02x\n", chp->ccw_count); "ec_startcmd CMD sense excess cnt %02x\n", chp->ccw_count);
break; break;
} }
//020522uptr->SNS &= ~(SNS_CMDREJ|SNS_EQUCHK); /* clear old status */
uptr->SNS = 0; /* clear old status */ uptr->SNS = 0; /* clear old status */
uptr->SNS &= LMASK; /* remove old count */ uptr->SNS &= LMASK; /* remove old count */
chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* done */ chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* done */
@ -1530,7 +1563,6 @@ void ec_ini(UNIT *uptr, t_bool f)
sim_debug(DEBUG_EXP, dptr, sim_debug(DEBUG_EXP, dptr,
"EC init device %s not attached on unit EC%04X\n", "EC init device %s not attached on unit EC%04X\n",
dptr->name, GET_UADDR(uptr->CMD)); dptr->name, GET_UADDR(uptr->CMD));
//OLD uptr->SNS |= SNS_NO_CAR; /* no carrier error */
} }
} }
@ -1540,14 +1572,17 @@ t_stat ec_rsctrl(UNIT *uptr) {
uint16 chsa = GET_UADDR(uptr->CMD); uint16 chsa = GET_UADDR(uptr->CMD);
int cmd = uptr->CMD & EC_CMDMSK; int cmd = uptr->CMD & EC_CMDMSK;
/*JCB*/ uptr->CMD &= LMASK; /* remove old status bits & cmd */
/*JCB*/ uptr->SNS = 0; /* clear mode value */
/* This change causes test 17 to fail in diags, and then hang at test 18 */
//JCB memset(&ec_data.conf[0], 0, sizeof(ec_data.conf));
sim_debug(DEBUG_EXP, dptr, sim_debug(DEBUG_EXP, dptr,
"ec_rsctlr chsa %04x cmd = %02x\n", chsa, cmd); "ec_rsctlr chsa %04x cmd = %02x\n", chsa, cmd);
// memset(&ec_data.conf[0], 0, sizeof(ec_data.conf));
ec_data.tx_count = 0; ec_data.tx_count = 0;
ec_data.rx_count = 0; ec_data.rx_count = 0;
ec_data.drop_cnt = 0;
ec_data.rec_ptr = 0; /* clear queue */ ec_data.rec_ptr = 0; /* clear queue */
ec_data.xtr_ptr = 0; /* clear queue */ ec_data.xtr_ptr = 0; /* clear queue */
ec_data.drop_cnt = 0;
return SCPE_OK; return SCPE_OK;
} }
@ -1684,22 +1719,13 @@ void ec_packet_debug(struct ec_device *ec, const char *action,
action, arp_op, eth_dst, eth_src, arp_shwaddr, arp_sipaddr, arp_dhwaddr, arp_dipaddr); action, arp_op, eth_dst, eth_src, arp_shwaddr, arp_sipaddr, arp_dhwaddr, arp_dipaddr);
return; return;
} }
#ifdef OLDWAY
if (ntohs(eth->type) != ETHTYPE_IP) {
payload = (uint8 *)&packet->msg[0];
len = packet->len;
sim_data_trace(&ec_dev, ec_unit, payload, "", len, "", DEBUG_DATA);
return;
}
#else
/* always dump packet */ /* always dump packet */
payload = (uint8 *)&packet->msg[0]; payload = (uint8 *)&packet->msg[0];
len = packet->len; len = packet->len & 0xffff; /* JCB */
sim_data_trace(&ec_dev, ec_unit, payload, "", len, "", DEBUG_DATA); sim_data_trace(&ec_dev, ec_unit, payload, "", len, "", DEBUG_DATA);
if (ntohs(eth->type) != ETHTYPE_IP) { if (ntohs(eth->type) != ETHTYPE_IP) {
return; return;
} }
#endif
if (!(ec_dev.dctrl & (DEBUG_TCP|DEBUG_UDP|DEBUG_ICMP))) if (!(ec_dev.dctrl & (DEBUG_TCP|DEBUG_UDP|DEBUG_ICMP)))
return; return;
memcpy(&ipaddr, &ip->ip_src, sizeof(ipaddr)); memcpy(&ipaddr, &ip->ip_src, sizeof(ipaddr));

View file

@ -30,7 +30,7 @@
#if NUM_DEVS_HSDP > 0 #if NUM_DEVS_HSDP > 0
#define UNIT_HSDP UNIT_ATTABLE | UNIT_IDLE | UNIT_DISABLE #define UNIT_HSDP UNIT_ATTABLE|UNIT_DISABLE
extern uint32 SPAD[]; /* cpu SPAD memory */ extern uint32 SPAD[]; /* cpu SPAD memory */
@ -1126,11 +1126,9 @@ t_stat hsdp_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
uptr->SNS &= ~SNS_CMDREJ; /* not rejected yet */ uptr->SNS &= ~SNS_CMDREJ; /* not rejected yet */
uptr->CMD |= DSK_INCH2; /* use 0xF0 for inch, just need int */ uptr->CMD |= DSK_INCH2; /* use 0xF0 for inch, just need int */
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
// sim_activate(uptr, 20); /* start things off */
sim_activate(uptr, 30); /* start things off */ sim_activate(uptr, 30); /* start things off */
#else #else
sim_activate(uptr, 250); /* start things off */ sim_activate(uptr, 250); /* start things off */
// sim_activate(uptr, 500); /* start things off */
#endif #endif
return SCPE_OK; /* good to go */ return SCPE_OK; /* good to go */
break; break;
@ -1164,12 +1162,9 @@ t_stat hsdp_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
"hsdp_startcmd starting disk cmd %02x chsa %04x\n", "hsdp_startcmd starting disk cmd %02x chsa %04x\n",
cmd, chsa); cmd, chsa);
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
// sim_activate(uptr, 20); /* start things off */
// sim_activate(uptr, 30); /* start things off */
sim_activate(uptr, 25); /* start things off */ sim_activate(uptr, 25); /* start things off */
#else #else
sim_activate(uptr, 250); /* start things off */ sim_activate(uptr, 250); /* start things off */
// sim_activate(uptr, 500); /* start things off */
#endif #endif
return SCPE_OK; /* good to go */ return SCPE_OK; /* good to go */
break; break;
@ -1331,7 +1326,6 @@ t_stat hsdp_srv(UNIT *uptr)
if (((i+1)%4) == 0) { /* see if we have a word yet */ if (((i+1)%4) == 0) { /* see if we have a word yet */
#ifndef FOR_TESTING #ifndef FOR_TESTING
int dn = i/4; /* get drive number */ int dn = i/4; /* get drive number */
// UNIT *up = uptr0[dn]; /* get our unit pointer */
UNIT *uptr0 = dptr->units; /* get unit 0 pointer */ UNIT *uptr0 = dptr->units; /* get unit 0 pointer */
#endif #endif
/* drive attribute registers */ /* drive attribute registers */
@ -1447,8 +1441,6 @@ t_stat hsdp_srv(UNIT *uptr)
/* Do a fake wait to kill some time */ /* Do a fake wait to kill some time */
uptr->CMD |= DSK_WAITING; /* show waiting for NOP */ uptr->CMD |= DSK_WAITING; /* show waiting for NOP */
sim_debug(DEBUG_CMD, dptr, "hsdp_srv cmd NOP stalling for 50 cnts\n"); sim_debug(DEBUG_CMD, dptr, "hsdp_srv cmd NOP stalling for 50 cnts\n");
// sim_activate(uptr, 250); /* start waiting */
// sim_activate(uptr, 50); /* start waiting */
sim_activate(uptr, 350); /* start waiting */ sim_activate(uptr, 350); /* start waiting */
break; break;
} }
@ -1469,7 +1461,6 @@ t_stat hsdp_srv(UNIT *uptr)
trk = (uptr->CHS >> 8) & 0xff; /* get trk/head */ trk = (uptr->CHS >> 8) & 0xff; /* get trk/head */
sec = uptr->CHS & 0xff; /* set sec */ sec = uptr->CHS & 0xff; /* set sec */
// ch = ((sec * 2) % SPT(type)) & 0x3f; /* get index cnt */
ch = ((2*SPT(type))-1) & 0x3f; /* get index cnt */ ch = ((2*SPT(type))-1) & 0x3f; /* get index cnt */
uptr->SNS2 = (uptr->SNS2 & 0xc0ff) | ((((uint32)ch) & 0x3f) << 8); uptr->SNS2 = (uptr->SNS2 & 0xc0ff) | ((((uint32)ch) & 0x3f) << 8);
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
@ -1525,7 +1516,7 @@ t_stat hsdp_srv(UNIT *uptr)
"hsdp_srv IHA unit=%02x STAR %08x %04x/%02x/%02x\n", "hsdp_srv IHA unit=%02x STAR %08x %04x/%02x/%02x\n",
unit, uptr->CHS, cyl, trk, sec); unit, uptr->CHS, cyl, trk, sec);
/* get alternate track if this one is defective */ /* get alternate track if this one is defective */
//sim_debug(DEBUG_CMD, dptr, "Dpatrk1 %08x label\n", uptr->CHS); // sim_debug(DEBUG_CMD, dptr, "Dpatrk1 %08x label\n", uptr->CHS);
tempt = get_dpatrk(uptr, uptr->CHS, lbuf); tempt = get_dpatrk(uptr, uptr->CHS, lbuf);
/* file offset in bytes to std or alt track */ /* file offset in bytes to std or alt track */
tstart = STAR2SEC(tempt, SPT(type), SPC(type)) * SSB(type); tstart = STAR2SEC(tempt, SPT(type), SPC(type)) * SSB(type);
@ -1829,10 +1820,6 @@ iha_error:
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"hsdp_srv LSC0 %02x AF test/incr cyl %04x trk %02x sec %02x\n", "hsdp_srv LSC0 %02x AF test/incr cyl %04x trk %02x sec %02x\n",
uptr->LSC, (tstar>>16)&0xffff, (tstar>>8)&0xff, tstar&0xff); uptr->LSC, (tstar>>16)&0xffff, (tstar>>8)&0xff, tstar&0xff);
//#define DO_DYNAMIC_DEBUG
#ifdef DO_DYNAMIC_DEBUG
// cpu_dev.dctrl |= DEBUG_INST|DEBUG_TRAP|DEBUG_CMD|DEBUG_DETAIL; /* start instruction trace */
#endif
} }
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
@ -1905,12 +1892,8 @@ iha_error:
unit, cyl, trk, buf[3], tcyl, k); unit, cyl, trk, buf[3], tcyl, k);
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
sim_activate(uptr, 15); sim_activate(uptr, 15);
// sim_activate(uptr, 20); /* start things off */
// sim_activate(uptr, 20+k); /* start us off */
#else #else
// sim_activate(uptr, 150); /* start things off */
sim_activate(uptr, 200+k); /* start us off */ sim_activate(uptr, 200+k); /* start us off */
// sim_activate(uptr, 400+k); /* start us off */
#endif #endif
break; break;
@ -1961,8 +1944,6 @@ iha_error:
case DSK_FMT: /* 0x0B Format for no skip */ case DSK_FMT: /* 0x0B Format for no skip */
/* buffer must be on halfword boundry if not STATUS_PCHK and SNS_CMDREJ status */ /* buffer must be on halfword boundry if not STATUS_PCHK and SNS_CMDREJ status */
// chp->chan_status |= STATUS_PCHK; /* program check for invalid cmd */
// uptr->SNS |= SNS_CMDREJ; /* cmd rejected */
/* byte count can not exceed 20160 for the track */ /* byte count can not exceed 20160 for the track */
uptr->CMD &= LMASK; /* remove old status bits & cmd */ uptr->CMD &= LMASK; /* remove old status bits & cmd */
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
@ -2178,7 +2159,6 @@ iha_error:
/* see if we are done reading data */ /* see if we are done reading data */
if (test_write_byte_end(chsa)) { if (test_write_byte_end(chsa)) {
/* EOM reached, abort */
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"HSDP Read complete for read from disk @ %04x/%02x/%02x\n", "HSDP Read complete for read from disk @ %04x/%02x/%02x\n",
STAR2CYL(uptr->CHS), (uptr->CHS >> 8)&0xff, (uptr->CHS&0xff)); STAR2CYL(uptr->CHS), (uptr->CHS >> 8)&0xff, (uptr->CHS&0xff));
@ -2191,12 +2171,9 @@ iha_error:
"HSDP sector read complete, %x bytes to go from diskfile /%04x/%02x/%02x\n", "HSDP sector read complete, %x bytes to go from diskfile /%04x/%02x/%02x\n",
chp->ccw_count, STAR2CYL(uptr->CHS), ((uptr->CHS) >> 8)&0xff, (uptr->CHS&0xff)); chp->ccw_count, STAR2CYL(uptr->CHS), ((uptr->CHS) >> 8)&0xff, (uptr->CHS&0xff));
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
// sim_activate(uptr, 10); /* wait to read next sector */
sim_activate(uptr, 15); /* wait to read next sector */ sim_activate(uptr, 15); /* wait to read next sector */
// sim_activate(uptr, 20); /* wait to read next sector */
#else #else
sim_activate(uptr, 150); /* wait to read next sector */ sim_activate(uptr, 150); /* wait to read next sector */
// sim_activate(uptr, 300); /* wait to read next sector */
#endif #endif
break; break;
} }
@ -2422,11 +2399,9 @@ iha_error:
} }
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
// sim_activate(uptr, 10); /* keep writing */
sim_activate(uptr, 15); /* keep writing */ sim_activate(uptr, 15); /* keep writing */
#else #else
sim_activate(uptr, 150); /* wait to read next sector */ sim_activate(uptr, 150); /* wait to write next sector */
// sim_activate(uptr, 300); /* wait to read next sector */
#endif #endif
break; break;
} }
@ -2950,7 +2925,7 @@ t_stat hsdp_reset(DEVICE *dptr)
{ {
int cn, unit; int cn, unit;
for(unit=0; unit < NUM_UNITS_HSDP; unit++) { for (unit=0; unit < NUM_UNITS_HSDP; unit++) {
for (cn=0; cn<TRK_CACHE; cn++) { for (cn=0; cn<TRK_CACHE; cn++) {
tkl_label[unit].tkl[cn].track = 0; tkl_label[unit].tkl[cn].track = 0;
tkl_label[unit].tkl[cn].age = 0; tkl_label[unit].tkl[cn].age = 0;

View file

@ -35,7 +35,7 @@
#if NUM_DEVS_IOP > 0 #if NUM_DEVS_IOP > 0
#define UNIT_IOP UNIT_IDLE | UNIT_DISABLE #define UNIT_IOP UNIT_DISABLE
/* forward definitions */ /* forward definitions */
t_stat iop_preio(UNIT *uptr, uint16 chan); t_stat iop_preio(UNIT *uptr, uint16 chan);
@ -265,7 +265,7 @@ t_stat iop_srv(UNIT *uptr)
/* the chp->ccw_addr location contains the inch address */ /* the chp->ccw_addr location contains the inch address */
/* 1-256 wd buffer is provided for 128 status dbl words */ /* 1-256 wd buffer is provided for 128 status dbl words */
//?? tstart = set_inch(uptr, mema, 128); /* new address of 128 entries */ //?? tstart = set_inch(uptr, mema, 128); /* new address of 128 entries */
tstart = set_inch(uptr, mema, 1); /* new address of 128 entries */ tstart = set_inch(uptr, mema, 1); /* new address of 128 entry */
if ((tstart == SCPE_MEM) || (tstart == SCPE_ARG)) { /* any error */ if ((tstart == SCPE_MEM) || (tstart == SCPE_ARG)) { /* any error */
/* we have error, bail out */ /* we have error, bail out */
uptr->u5 |= SNS_CMDREJ; uptr->u5 |= SNS_CMDREJ;

View file

@ -28,7 +28,6 @@
#ifdef USE_IPU_THREAD #ifdef USE_IPU_THREAD
extern uint32 sim_idle_ms_sleep(unsigned int); /* wait 1 ms */
extern UNIT cpu_unit; /* The CPU */ extern UNIT cpu_unit; /* The CPU */
/* running IPU thread on CPU, n/u in IPU fork */ /* running IPU thread on CPU, n/u in IPU fork */
@ -37,7 +36,6 @@ static uint8 wait4sipu = 0; /* waiting for sipu in IPU if set */
static int MyIndex; static int MyIndex;
static int PeerIndex; static int PeerIndex;
extern uint32 M[]; /* Memory */ extern uint32 M[]; /* Memory */
//extern uint32 *M; /* Memory when we have IPU using threads */
extern struct ipcom *IPC; /* TRAPS & flags */ extern struct ipcom *IPC; /* TRAPS & flags */
extern pthread_t ipuThread; extern pthread_t ipuThread;
extern DEVICE cpu_dev; /* cpu device structure */ extern DEVICE cpu_dev; /* cpu device structure */
@ -123,24 +121,8 @@ LOCAL t_stat Mem_read(uint32 addr, uint32 *data);
LOCAL t_stat Mem_write(uint32 addr, uint32 *data); LOCAL t_stat Mem_write(uint32 addr, uint32 *data);
/* external definitions */ /* external definitions */
extern t_stat checkxio(uint16 addr, uint32 *status); /* XIO check in chan.c */
extern t_stat startxio(uint16 addr, uint32 *status); /* XIO start in chan.c */
extern t_stat testxio(uint16 addr, uint32 *status); /* XIO test in chan.c */
extern t_stat stopxio(uint16 addr, uint32 *status); /* XIO stop in chan.c */
extern t_stat rschnlxio(uint16 addr, uint32 *status); /* reset channel XIO */
extern t_stat haltxio(uint16 addr, uint32 *status); /* halt XIO */
extern t_stat grabxio(uint16 addr, uint32 *status); /* grab XIO n/u */
extern t_stat rsctlxio(uint16 addr, uint32 *status); /* reset controller XIO */
extern t_stat chan_set_devs(); /* set up the defined devices on the simulator */
extern uint32 scan_chan(uint32 *ilev); /* go scan for I/O int pending */
extern uint32 cont_chan(uint16 chsa); /* continue channel program */
extern uint16 loading; /* set when doing IPL */ extern uint16 loading; /* set when doing IPL */
extern int fprint_inst(FILE *of, uint32 val, int32 sw); /* instruction print function */ extern int fprint_inst(FILE *of, uint32 val, int32 sw); /* instruction print function */
extern void rtc_setup(uint32 ss, uint32 level); /* tell rtc to start/stop */
extern void itm_setup(uint32 ss, uint32 level); /* tell itm to start/stop */
extern int32 itm_rdwr(uint32 cmd, int32 cnt, uint32 level); /* read/write the interval timer */
extern int16 post_csw(CHANP *chp, uint32 rstat);
extern DIB *dib_chan[MAX_CHAN];
/* floating point subroutines definitions */ /* floating point subroutines definitions */
extern uint32 s_fixw(uint32 val, uint32 *cc); extern uint32 s_fixw(uint32 val, uint32 *cc);
@ -185,7 +167,8 @@ UNIT ipu_unit =
NULL, /* void *filebuf */ /* memory buffer */ NULL, /* void *filebuf */ /* memory buffer */
0, /* uint32 hwmark */ /* high water mark */ 0, /* uint32 hwmark */ /* high water mark */
0, /* int32 time */ /* time out */ 0, /* int32 time */ /* time out */
UNIT_IDLE|UNIT_FIX|UNIT_BINK|MODEL(MODEL_27)|MEMAMOUNT(4), /* flags */ // UNIT_IDLE|UNIT_FIX|UNIT_BINK|MODEL(MODEL_27)|MEMAMOUNT(4), /* flags */
UNIT_FIX|UNIT_BINK|MODEL(MODEL_27)|MEMAMOUNT(4), /* flags */
0, /* uint32 dynflags */ /* dynamic flags */ 0, /* uint32 dynflags */ /* dynamic flags */
0x800000, /* t_addr capac */ /* capacity */ 0x800000, /* t_addr capac */ /* capacity */
0, /* t_addr pos */ /* file position */ 0, /* t_addr pos */ /* file position */
@ -204,6 +187,7 @@ REG ipu_reg[] = {
{BRDATAD(MAPC, MAPC, 16, 32, 1024, "IPU map cache"), REG_FIT}, {BRDATAD(MAPC, MAPC, 16, 32, 1024, "IPU map cache"), REG_FIT},
{BRDATAD(TLB, TLB, 16, 32, 2048, "IPU Translation Lookaside Buffer"), REG_FIT}, {BRDATAD(TLB, TLB, 16, 32, 2048, "IPU Translation Lookaside Buffer"), REG_FIT},
{HRDATAD(PC, PC, 24, "Program Counter"), REG_FIT}, {HRDATAD(PC, PC, 24, "Program Counter"), REG_FIT},
{HRDATAD(TRAPME, TRAPME, 32, "Trap Error Number"), REG_FIT},
{HRDATAD(IR, IR, 32, "Last Instruction Loaded"), REG_FIT}, {HRDATAD(IR, IR, 32, "Last Instruction Loaded"), REG_FIT},
{HRDATAD(HIWM, HIWM, 32, "Max Maps Loaded"), REG_FIT}, {HRDATAD(HIWM, HIWM, 32, "Max Maps Loaded"), REG_FIT},
{HRDATAD(BPIX, BPIX, 32, "# Maps Loaded for O/S"), REG_FIT}, {HRDATAD(BPIX, BPIX, 32, "# Maps Loaded for O/S"), REG_FIT},
@ -265,7 +249,6 @@ MTAB ipu_mod[] = {
MEMAMOUNT(0), /* uint32 match */ /* match */ MEMAMOUNT(0), /* uint32 match */ /* match */
NULL, /* cchar *pstring */ /* print string */ NULL, /* cchar *pstring */ /* print string */
"128K", /* cchar *mstring */ /* match string */ "128K", /* cchar *mstring */ /* match string */
/// &ipu_set_size, /* t_stat (*valid) */ /* validation routine */
NULL, /* t_stat (*valid) */ /* validation routine */ NULL, /* t_stat (*valid) */ /* validation routine */
NULL, /* t_stat (*disp) */ /* display routine */ NULL, /* t_stat (*disp) */ /* display routine */
NULL, /* void *desc */ /* value desc, REG* if MTAB_VAL, int* if not */ NULL, /* void *desc */ /* value desc, REG* if MTAB_VAL, int* if not */
@ -496,10 +479,7 @@ void millinap(int msec)
msecs = msec % 1000; msecs = msec % 1000;
starttimer.tv_sec = secs; starttimer.tv_sec = secs;
// starttimer.tv_nsec = msecs * 2000000; /* 2M nanosecs = 2ms */
starttimer.tv_nsec = msecs * 1000000; /* 1M nanosecs = 1ms */ starttimer.tv_nsec = msecs * 1000000; /* 1M nanosecs = 1ms */
// starttimer.tv_nsec = msecs * 100000; /* 100K nanosecs = 100us */
// starttimer.tv_nsec = msecs * 10000; /* 10K nanosecs = 10us */
nanosleep(&starttimer, & remaining); nanosleep(&starttimer, & remaining);
} }
@ -513,7 +493,7 @@ void millinap(int msec)
} }
#endif #endif
#ifdef DEBUG4IPU #ifndef DEBUG4IPU
/* Dump instruction history */ /* Dump instruction history */
static void DumpHist() static void DumpHist()
{ {
@ -801,13 +781,11 @@ npmem:
} }
/* output O/S and User MPL entries */ /* output O/S and User MPL entries */
// sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
sim_debug(DEBUG_CMD, my_dev,
"#MEMORY %06x MPL %06x MPL[0] %08x %06x MPL[%04x] %08x %06x\n", "#MEMORY %06x MPL %06x MPL[0] %08x %06x MPL[%04x] %08x %06x\n",
MEMSIZE, mpl, RMW(mpl), RMW(mpl+4), cpix, MEMSIZE, mpl, RMW(mpl), RMW(mpl+4), cpix,
RMW(cpix+mpl), RMW(cpix+mpl+4)); RMW(cpix+mpl), RMW(cpix+mpl+4));
// sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
sim_debug(DEBUG_CMD, my_dev,
"MEMORY2 %06x BPIX %04x cpix %04x CPIX %04x CPIXPL %04x HIWM %04x\n", "MEMORY2 %06x BPIX %04x cpix %04x CPIX %04x CPIXPL %04x HIWM %04x\n",
MEMSIZE, BPIX, cpix, CPIX, CPIXPL, HIWM); MEMSIZE, BPIX, cpix, CPIX, CPIXPL, HIWM);
@ -1216,16 +1194,6 @@ LOCAL t_stat RealAddr(uint32 addr, uint32 *realaddr, uint32 *prot, uint32 access
if ((CPU_MODEL == MODEL_27) || (CPU_MODEL == MODEL_87)) if ((CPU_MODEL == MODEL_27) || (CPU_MODEL == MODEL_87))
MAXMAP = MAX256; /* only 256 2KW (8kb) maps */ MAXMAP = MAX256; /* only 256 2KW (8kb) maps */
#if 0
// FIXME trapstatus bits
if ((mpl == 0) || (RMW(mpl) == 0) || ((RMW(mpl) & MASK16) >= MAXMAP)) {
sim_debug(DEBUG_TRAP, my_dev,
"RealAddr Bad MPL Count or Memory Address for O/S MPL %06x MPL[0] %04x MPL[1] %06x\n",
mpl, RMW(mpl), RMW(mpl+4));
return MACHINECHK_TRAP; /* diags want machine check error */
}
#endif
/* did not get expected machine check trap for */ /* did not get expected machine check trap for */
/* 27, 87, 67 in test 37/0 if code removed */ /* 27, 87, 67 in test 37/0 if code removed */
/* unexpected machine check trap for 67 in test 37/0 cn.mmm */ /* unexpected machine check trap for 67 in test 37/0 cn.mmm */
@ -1259,7 +1227,6 @@ LOCAL t_stat RealAddr(uint32 addr, uint32 *realaddr, uint32 *prot, uint32 access
index = (word >> 13) & 0x7ff; /* get 11 bit page value */ index = (word >> 13) & 0x7ff; /* get 11 bit page value */
offset = word & 0x1fff; /* get 13 bit page offset */ offset = word & 0x1fff; /* get 13 bit page offset */
//FIXME 112522
if (MODES & MAPMODE) { if (MODES & MAPMODE) {
uint32 mpl = SPAD[0xf3]; /* get mpl from spad address */ uint32 mpl = SPAD[0xf3]; /* get mpl from spad address */
uint32 cpix = CPIX; /* get cpix 11 bit offset from psd wd 2 */ uint32 cpix = CPIX; /* get cpix 11 bit offset from psd wd 2 */
@ -1267,12 +1234,10 @@ LOCAL t_stat RealAddr(uint32 addr, uint32 *realaddr, uint32 *prot, uint32 access
uint32 spc = midl & MASK16; /* get 16 bit user segment description count */ uint32 spc = midl & MASK16; /* get 16 bit user segment description count */
/* output O/S and User MPL entries */ /* output O/S and User MPL entries */
sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
// sim_debug(DEBUG_TRAP, my_dev,
"+MEMORY %06x MPL %06x MPL[0] %08x %06x MPL[%04x] %08x %06x\n", "+MEMORY %06x MPL %06x MPL[0] %08x %06x MPL[%04x] %08x %06x\n",
MEMSIZE, mpl, RMW(mpl), RMW(mpl+4), cpix, MEMSIZE, mpl, RMW(mpl), RMW(mpl+4), cpix,
RMW(cpix+mpl), RMW(cpix+mpl+4)); RMW(cpix+mpl), RMW(cpix+mpl+4));
sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
// sim_debug(DEBUG_TRAP, my_dev,
"+MEMORY spc %x BPIX %04x cpix %04x CPIX %04x CPIXPL %04x HIWM %04x\n", "+MEMORY spc %x BPIX %04x cpix %04x CPIX %04x CPIXPL %04x HIWM %04x\n",
spc, BPIX, cpix, CPIX, CPIXPL, HIWM); spc, BPIX, cpix, CPIX, CPIXPL, HIWM);
} }
@ -1867,15 +1832,14 @@ void *ipu_sim_instr(void *value) {
int32 int32a; /* temp int */ int32 int32a; /* temp int */
int32 int32b; /* temp int */ int32 int32b; /* temp int */
int32 int32c; /* temp int */ int32 int32c; /* temp int */
#ifdef NOT_NEEDED
int32 counter=0; /* temp int */
#endif
/* the newly created child process in IPU */ /* the newly created child process in IPU */
/* running on IPU */ /* running on IPU */
reboot: /* cpu rebooting, so reinitialize ipu */
MyIndex = 1; MyIndex = 1;
PeerIndex = 0; PeerIndex = 0;
IPC->pid[MyIndex] = 1; IPC->pid[MyIndex] = 1;
IPC->atrap[MyIndex] = 0; /* clear trap value location */
/* we will be running with an ipu, set it up */ /* we will be running with an ipu, set it up */
/* clear I/O and interrupt entries in SPAD. */ /* clear I/O and interrupt entries in SPAD. */
@ -1925,27 +1889,25 @@ void *ipu_sim_instr(void *value) {
"Starting at ipu wait_loop 1 %p 0 %08x 4 %08x\n", (void *)M, M[0], M[1]); "Starting at ipu wait_loop 1 %p 0 %08x 4 %08x\n", (void *)M, M[0], M[1]);
fflush(sim_deb); fflush(sim_deb);
reason = SCPE_OK; reason = SCPE_OK;
cpustop = reason; /* tell IPU our state */ cpustop = reason; /* clear stop code */
/* loop here until time out or error found */ /* loop here until time out or error found */
#ifdef USE_POSIX_SEM #ifdef USE_POSIX_SEM
wait_loop: wait_loop:
#endif #endif
while (reason == SCPE_OK) { /* loop until halted */ while (reason == SCPE_OK) { /* loop until halted */
cond_go: /* merge point when waiting or halted */
i_flags = 0; /* clear flags for next instruction */ i_flags = 0; /* clear flags for next instruction */
if (cpustop != SCPE_OK) if (cpustop != SCPE_OK) {
if (cpustop == STOP_RESET)
goto reboot; /* cpu rebooting, reinit ipu */
if (cpustop == STOP_WAITING)
goto cond_ok; /* go wait for sipu */
if (cpustop == STOP_HALT)
goto cond_ok; /* go wait for sipu */
break; /* quit running */ break; /* quit running */
#ifdef NOT_NEEDED
if (counter++ > 4000) {
sim_debug(DEBUG_EXP, my_dev,
"4000 loops in IPU PeerIndex %x atrap[%x] = %x wait4sipu %x\r\n",
PeerIndex, MyIndex, IPC->atrap[MyIndex], wait4sipu);
fflush(sim_deb);
counter = 0;
} }
#endif
if (skipinstr) { /* need to skip interrupt test? */ if (skipinstr) { /* need to skip interrupt test? */
skipinstr = 0; /* skip only once */ skipinstr = 0; /* skip only once */
@ -1973,10 +1935,9 @@ wait_loop:
sim_debug(DEBUG_TRAP, my_dev, "%s: (%d) Async TRAP %02x SPAD[0xf0] %08x\n", sim_debug(DEBUG_TRAP, my_dev, "%s: (%d) Async TRAP %02x SPAD[0xf0] %08x\n",
(IPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, SPAD[0xf0]); (IPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, SPAD[0xf0]);
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: PC %08x PSD1 %08x PSD2 %08x 0x20 %x 0x80 %x\n", "%s: PC %08x PSD1 %08x PSD2 %08x 0x4c %x 0xac %x\n",
(IPUSTATUS & ONIPU) ? "IPU" : "CPU", (IPUSTATUS & ONIPU) ? "IPU" : "CPU",
PC, PSD1, PSD2, M[0x20>2], M[0x80>>2]); PC, PSD1, PSD2, M[0x4c>>2], M[0xac>>2]);
// wait4sipu = 0; /* wait is over for sipu */
wait4int = 0; /* wait is over for int */ wait4int = 0; /* wait is over for int */
goto newpsd; /* go process trap */ goto newpsd; /* go process trap */
} }
@ -1991,14 +1952,13 @@ wait_loop:
sim_debug(DEBUG_TRAP, my_dev, "%s: (%d) Async TRAP %02x SPAD[0xf0] %08x\n", sim_debug(DEBUG_TRAP, my_dev, "%s: (%d) Async TRAP %02x SPAD[0xf0] %08x\n",
(IPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, SPAD[0xf0]); (IPUSTATUS & ONIPU) ? "IPU" : "CPU", __LINE__, TRAPME, SPAD[0xf0]);
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: PC %08x PSD1 %08x PSD2 %08x 0x20 %x 0x80 %x\n", "%s: PC %08x PSD1 %08x PSD2 %08x 0x4c %x 0xac %x\n",
(IPUSTATUS & ONIPU) ? "IPU" : "CPU", (IPUSTATUS & ONIPU) ? "IPU" : "CPU",
PC, PSD1, PSD2, M[0x20>2], M[0x80>>2]); PC, PSD1, PSD2, M[0x4c>>2], M[0xac>>2]);
goto newpsd; /* go process trap */ goto newpsd; /* go process trap */
} }
if (wait4sipu) { if (wait4sipu) {
// sim_idle_ms_sleep(1); /* wait 1 ms */ sim_os_ms_sleep(10); /* wait 10 ms */
millinap(1); /* wait 1 ms */
goto wait_loop; /* continue waiting */ goto wait_loop; /* continue waiting */
} }
} }
@ -2008,8 +1968,6 @@ wait_loop:
/* wait for sipu to start us on ipu */ /* wait for sipu to start us on ipu */
/* interrupts must be unblocked on IPU to receive SIPU */ /* interrupts must be unblocked on IPU to receive SIPU */
if ((IPUSTATUS & BIT24) == 0) { if ((IPUSTATUS & BIT24) == 0) {
cond_go:
// lock_mutex(); /* lock mutex */
cond_ok: cond_ok:
if (IPC && (IPC->atrap[MyIndex] != 0)) { if (IPC && (IPC->atrap[MyIndex] != 0)) {
/* we are unblocked, look for SIPU */ /* we are unblocked, look for SIPU */
@ -2021,10 +1979,15 @@ cond_ok:
unlock_mutex(); /* unlock mutex */ unlock_mutex(); /* unlock mutex */
IPC->received[MyIndex]++; /* count it received */ IPC->received[MyIndex]++; /* count it received */
wait4sipu = 0; /* wait is over for sipu */ wait4sipu = 0; /* wait is over for sipu */
sim_debug(DEBUG_TRAP, my_dev, "IPU: (%d) Async TRAP %02x SPAD[0xf0] %08x\n", sim_debug(DEBUG_TRAP, my_dev, "IPU: (%d) Async TRAP %02x SPAD[0xf0] %02x rec'd %08x\n",
__LINE__, TRAPME, SPAD[0xf0]); __LINE__, TRAPME, SPAD[0xf0], IPC->received[MyIndex]);
sim_debug(DEBUG_TRAP, my_dev, "IPU: PC %08x PSD %08x %08x 0x20 %x\n", if (TRAPME == 0) {
PC, PSD1, PSD2, M[0x20>2]); sim_debug(DEBUG_TRAP, my_dev, "!!! IPU: (%d) Async TRAP %02x is zero, forcing to %x\n",
__LINE__, TRAPME, SIGNALIPU_TRAP);
TRAPME = SIGNALIPU_TRAP;
}
sim_debug(DEBUG_TRAP, my_dev, "IPU: PC %08x PSD %08x %08x 0x4c %x\n",
PC, PSD1, PSD2, M[0x4c>>2]);
goto newpsd; /* go process trap */ goto newpsd; /* go process trap */
} }
} }
@ -2037,7 +2000,6 @@ cond_ok:
goto cond_ok; /* continue waiting */ goto cond_ok; /* continue waiting */
} }
/* not waiting for sipu, so continue processing */ /* not waiting for sipu, so continue processing */
// unlock_mutex(); /* unlock mutex and continue */
} }
/* we are blocked, continue */ /* we are blocked, continue */
/* continue processing */ /* continue processing */
@ -2074,6 +2036,7 @@ skipi:
PSD1 &= ~BIT31; /* force off last right */ PSD1 &= ~BIT31; /* force off last right */
} }
} }
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"read_instr2 TRAPME %02x PSD %08x %08x i_flags %04x\n", "read_instr2 TRAPME %02x PSD %08x %08x i_flags %04x\n",
TRAPME, PSD1, PSD2, i_flags); TRAPME, PSD1, PSD2, i_flags);
@ -2111,14 +2074,13 @@ skipi:
i_flags = base_mode[OP>>2]; /* set the BM instruction processing flags */ i_flags = base_mode[OP>>2]; /* set the BM instruction processing flags */
else else
i_flags = nobase_mode[OP>>2]; /* set the NBM instruction processing flags */ i_flags = nobase_mode[OP>>2]; /* set the NBM instruction processing flags */
//FIX112922 if ((i_flags & 0xf) == HLF) { /* this is left HW instruction */
if (i_flags & HLF) { /* this is left HW instruction */ if (i_flags & HLF) { /* this is left HW instruction */
if ((IR & 0xffff) == 0x0002) { /* see if rt hw is a nop */ if ((IR & 0xffff) == 0x0002) { /* see if rt hw is a nop */
/* treat this as a fw instruction */ /* treat this as a fw instruction */
drop_nop = 1; /* we need to skip nop next time */ drop_nop = 1; /* we need to skip nop next time */
// sim_debug(DEBUG_IRQ, my_dev,
sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
"IPU setting Drop NOP OPSD1 %08x PSD1 %08x PC %08x IR %08x\n", OPSD1, PSD1, PC, IR); "IPU setting Drop NOP OPSD1 %08x PSD1 %08x PC %08x IR %08x\n",
OPSD1, PSD1, PC, IR);
goto exec2; goto exec2;
} }
} }
@ -2136,9 +2098,6 @@ exec2:
OPSD1 = PSD1; /* save the old PSD1 */ OPSD1 = PSD1; /* save the old PSD1 */
OPSD2 = PSD2; /* save the old PSD2 */ OPSD2 = PSD2; /* save the old PSD2 */
TRAPSTATUS = IPUSTATUS & 0x57; /* clear all trap status except ipu type */ TRAPSTATUS = IPUSTATUS & 0x57; /* clear all trap status except ipu type */
// bc = 0;
// EXM_EXR = 0;
// source = 0;
/* Split instruction into pieces */ /* Split instruction into pieces */
PC = PSD1 & 0xfffffe; /* get 24 bit addr from PSD1 */ PC = PSD1 & 0xfffffe; /* get 24 bit addr from PSD1 */
@ -2183,9 +2142,6 @@ exec2:
} }
if (MODES & BASEBIT) { if (MODES & BASEBIT) {
#ifdef NONOP
i_flags = base_mode[OP>>2]; /* set the instruction processing flags */
#endif
addr = IR & RMASK; /* get address offset from instruction */ addr = IR & RMASK; /* get address offset from instruction */
sim_debug(DEBUG_DETAIL, my_dev, sim_debug(DEBUG_DETAIL, my_dev,
"Base OP %04x i_flags %04x addr %08x\n", OP, i_flags, addr); "Base OP %04x i_flags %04x addr %08x\n", OP, i_flags, addr);
@ -2227,9 +2183,6 @@ exec2:
break; break;
} }
} else { } else {
#ifdef NONOP
i_flags = nobase_mode[OP>>2]; /* set the instruction processing flags */
#endif
addr = IR & 0x7ffff; /* get 19 bit address from instruction */ addr = IR & 0x7ffff; /* get 19 bit address from instruction */
if (PC >= 0x80000) { if (PC >= 0x80000) {
TRAPME = MAPFAULT_TRAP; /* Map Fault Trap */ TRAPME = MAPFAULT_TRAP; /* Map Fault Trap */
@ -2523,28 +2476,23 @@ exec2:
if ((IPUSTATUS & ONIPU) && (cpustop == SCPE_OK)) { if ((IPUSTATUS & ONIPU) && (cpustop == SCPE_OK)) {
/* wait for any trap, knowing there will be no interrupts */ /* wait for any trap, knowing there will be no interrupts */
if (wait4sipu == 0) { if (wait4sipu == 0) {
time_t result = time(NULL); sim_debug(DEBUG_DETAIL, my_dev,
// sim_debug(DEBUG_DETAIL, my_dev, "Starting %s HALT PSD1 %.8x PSD2 %.8x TRAPME %02x IPUSTATUS %08x\n",
sim_debug(DEBUG_TRAP, my_dev,
"Starting %s HALT PSD1 %.8x PSD2 %.8x TRAPME %02x IPUSTATUS %08x time %.8x\n",
(IPUSTATUS & ONIPU) ? "IPU" : "CPU", (IPUSTATUS & ONIPU) ? "IPU" : "CPU",
PSD1, PSD2, TRAPME, IPUSTATUS, (uint32)result); PSD1, PSD2, TRAPME, IPUSTATUS);
} }
#ifndef DO_A_HALT
else { else {
#ifdef USE_POSIX_SEM #ifdef USE_POSIX_SEM
// sim_idle_ms_sleep(1); /* wait 1 ms */ sim_os_ms_sleep(10); /* wait 10 ms */
millinap(1); /* wait 1 ms */
goto wait_loop; /* continue waiting */ goto wait_loop; /* continue waiting */
#else #else
wait4sipu = 1; /* show we are waiting for SIPU */ wait4sipu = 1; /* show we are waiting for SIPU */
goto cond_go; /* start waiting for sipu */ goto cond_go; /* start waiting for SIPU */
#endif #endif
} }
wait4sipu = 1; /* show we are waiting for SIPU */ wait4sipu = 1; /* show we are waiting for SIPU */
i_flags |= BT; /* keep PC from being incremented while waiting */ i_flags |= BT; /* keep PC from being incremented while waiting */
break; /* keep going */ break; /* keep going */
#endif
} }
#ifndef NOT_ON_IPU_FOR_NOW #ifndef NOT_ON_IPU_FOR_NOW
@ -2577,12 +2525,25 @@ exec2:
} }
fprintf(stdout, "[][][][][][][][][][] IPU HALT [1][][][][][][][][][]\r\n"); fprintf(stdout, "[][][][][][][][][][] IPU HALT [1][][][][][][][][][]\r\n");
#endif #endif
/*TEST DIAG*/reason = STOP_HALT; /* do halt for now */ #if OLD_WAY
reason = STOP_HALT; /* do halt for now */
cpustop = reason; /* tell IPU our state */ cpustop = reason; /* tell IPU our state */
fprintf(stdout, "[][][][][][][][][][] IPU HALT [1][][][][][][][][][]\r\n"); fprintf(stdout, "[][][][][][][][][][] IPU HALT [1][][][][][][][][][]\r\n");
fflush(stdout); fflush(stdout);
fflush(sim_deb); fflush(sim_deb);
pthread_exit((void *)&reason); pthread_exit((void *)&reason);
#else
if (cpustop == STOP_HALT) {
/* CPU is halting and we are halted, so wait for new command */
wait4sipu = 1; /* show we are waiting for SIPU */
cpustop = STOP_WAITING; /* tell IPU our state */
reason = SCPE_OK; /* look for sipu */
IPUSTATUS &= ~BIT24; /* clear blocked bit 24 */
MODES &= ~BLKMODE; /* reset blocked mode */
PSD2 &= ~(SETBBIT|RETBBIT); /* clear bit 48 & 49 to be unblocked */
goto cond_go; /* start waiting for SIPU */
}
#endif
break; break;
case 0x1: /* WAIT */ case 0x1: /* WAIT */
@ -2603,24 +2564,18 @@ exec2:
TRAPSTATUS |= BIT20; /* set bit 20 of trap status */ TRAPSTATUS |= BIT20; /* set bit 20 of trap status */
goto newpsd; /* System check trap */ goto newpsd; /* System check trap */
} }
#if 0
do_ipu_wait:
#endif
PC = OPSD1 & 0xfffffe; /* get 24 bit addr from PSD1 */ PC = OPSD1 & 0xfffffe; /* get 24 bit addr from PSD1 */
if (IPU_MODEL && (IPUSTATUS & ONIPU)) { if (IPU_MODEL && (IPUSTATUS & ONIPU)) {
/* Hack around it when on IPU side: wait by expensive method */ /* Hack around it when on IPU side: wait by expensive method */
/* wait for any trap, knowing there will be no interrupts */ /* wait for any trap, knowing there will be no interrupts */
if (wait4sipu == 0) { if (wait4sipu == 0) {
time_t result = time(NULL); sim_debug(DEBUG_DETAIL, my_dev,
// sim_debug(DEBUG_DETAIL, my_dev, "Starting %s WAIT1 PSD1 %.8x PSD2 %.8x TRAPME %02x IPUSTATUS %08x\n",
sim_debug(DEBUG_TRAP, my_dev,
"Starting %s WAIT1 PSD1 %.8x PSD2 %.8x TRAPME %02x IPUSTATUS %08x time %.8x\n",
(IPUSTATUS & ONIPU) ? "IPU" : "CPU", (IPUSTATUS & ONIPU) ? "IPU" : "CPU",
PSD1, PSD2, TRAPME, IPUSTATUS, (uint32)result); PSD1, PSD2, TRAPME, IPUSTATUS);
} else { } else {
#ifdef USE_POSIX_SEM #ifdef USE_POSIX_SEM
// sim_idle_ms_sleep(1); /* wait 1 ms */ sim_os_ms_sleep(10); /* wait 10 ms */
millinap(1); /* wait 1 ms */
goto wait_loop; /* continue waiting */ goto wait_loop; /* continue waiting */
#else #else
wait4sipu = 1; /* show we are waiting for SIPU */ wait4sipu = 1; /* show we are waiting for SIPU */
@ -2630,21 +2585,6 @@ do_ipu_wait:
wait4sipu = 1; /* show we are waiting for SIPU */ wait4sipu = 1; /* show we are waiting for SIPU */
i_flags |= BT; /* keep PC from being incremented while waiting */ i_flags |= BT; /* keep PC from being incremented while waiting */
} }
#ifdef ONLY_FOR_CPU_CODE
else {
if (wait4int == 0) {
time_t result = time(NULL);
// sim_debug(DEBUG_DETAIL, my_dev,
sim_debug(DEBUG_TRAP, my_dev,
"Starting %s WAIT2 PSD1 %.8x PSD2 %.8x TRAPME %02x IPUSTATUS %08x time %.8x\n",
(IPUSTATUS & ONIPU) ? "IPU" : "CPU",
PSD1, PSD2, TRAPME, IPUSTATUS, (uint32)result);
}
/* tell simh we will be waiting */
wait4int = 1; /* show we are waiting for interrupt */
i_flags |= BT; /* keep PC from being incremented while waiting */
}
#endif
break; break;
case 0x2: /* NOP */ case 0x2: /* NOP */
break; break;
@ -2711,7 +2651,6 @@ do_ipu_wait:
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"IPU BEI PSD %.8x %.8x SPDF5 %.8x IPUSTATUS %08x\n", "IPU BEI PSD %.8x %.8x SPDF5 %.8x IPUSTATUS %08x\n",
PSD1, PSD2, SPAD[0xf5], IPUSTATUS); PSD1, PSD2, SPAD[0xf5], IPUSTATUS);
//112522 i_flags |= BT; /* leave PC unchanged, so we point at BEI */
goto newpsd; goto newpsd;
} }
PSD2 &= ~(SETBBIT|RETBBIT); /* clear bit 48 & 49 */ PSD2 &= ~(SETBBIT|RETBBIT); /* clear bit 48 & 49 */
@ -2768,8 +2707,7 @@ do_ipu_wait:
(IPUSTATUS & ONIPU)? "IPU": "CPU", IPUSTATUS, CCW, SPAD[0xf0]); (IPUSTATUS & ONIPU)? "IPU": "CPU", IPUSTATUS, CCW, SPAD[0xf0]);
//GR Give it a millisec to unblock the atrap //GR Give it a millisec to unblock the atrap
// sim_idle_ms_sleep(1); /* wait 1 ms */ sim_os_ms_sleep(10); /* wait 10 ms */
millinap(1); /* wait 1 ms */
} }
if (IPC->atrap[PeerIndex] == 0) { if (IPC->atrap[PeerIndex] == 0) {
@ -2786,11 +2724,10 @@ do_ipu_wait:
/* previous atrap not yet handled if not zero */ /* previous atrap not yet handled if not zero */
IPC->blocked[MyIndex]++; /* count as blocked */ IPC->blocked[MyIndex]++; /* count as blocked */
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: Async SIPU blocked IPUSTATUS %08x CCW %08x SPAD[0xf0] %08x\n", "%s: Async SIPU blocked IPUSTATUS %08x CCW %08x SPAD[0xf0] %02x block %08x\n",
(IPUSTATUS & ONIPU)? "IPU": "CPU", IPUSTATUS, CCW, SPAD[0xf0]); (IPUSTATUS & ONIPU)? "IPU": "CPU", IPUSTATUS, CCW, SPAD[0xf0], IPC->blocked[MyIndex]);
//GR Give it a millisec to unblock the atrap //GR Give it a millisec to unblock the atrap
// sim_idle_ms_sleep(1); /* wait 1 ms */ sim_os_ms_sleep(10); /* wait 10 ms */
millinap(1); /* wait 1 ms */
} }
if (IPC->atrap[PeerIndex] == 0) { if (IPC->atrap[PeerIndex] == 0) {
lock_mutex(); /* lock mutex */ lock_mutex(); /* lock mutex */
@ -2799,25 +2736,19 @@ do_ipu_wait:
unlock_mutex(); /* unlock mutex */ unlock_mutex(); /* unlock mutex */
IPC->sent[MyIndex]++; IPC->sent[MyIndex]++;
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: Async SIPU sent IPUSTATUS %08x CCW %08x SPAD[0xf0] %08x\n", "%s: Async SIPU sent IPUSTATUS %08x CCW %08x SPAD[0xf0] %02x sent %08x\n",
(IPUSTATUS & ONIPU)? "IPU": "CPU", IPUSTATUS, CCW, SPAD[0xf0]); (IPUSTATUS & ONIPU)? "IPU": "CPU", IPUSTATUS, CCW, SPAD[0xf0], IPC->sent[MyIndex]);
} else { } else {
// unlock_mutex(); /* unlock mutex */
IPC->dropped[MyIndex]++; /* count dropped SIPU */ IPC->dropped[MyIndex]++; /* count dropped SIPU */
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"%s: Async SIPU sent IPUSTATUS %08x CCW %08x SPAD[0xf0] %08x\n", "%s: Async SIPU sent IPUSTATUS %08x CCW %08x SPAD[0xf0] %02x drop %08x\n",
(IPUSTATUS & ONIPU)? "IPU": "CPU", IPUSTATUS, CCW, SPAD[0xf0]); (IPUSTATUS & ONIPU)? "IPU": "CPU", IPUSTATUS, CCW, SPAD[0xf0], IPC->dropped[MyIndex]);
} }
#endif /* USE_POSIX_SEM */ #endif /* USE_POSIX_SEM */
} else { } else {
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"SIPU IPUSTATUS %08x CCW %08x\n", IPUSTATUS, CCW); "SIPU IPUSTATUS %08x CCW %08x\n", IPUSTATUS, CCW);
goto newpsd; /* handle trap */ goto newpsd; /* handle trap */
//HANGS TRAPME = IPUUNDEFI_TRAP; /* undefined IPU instruction */
//HANGS TRAPME = SYSTEMCHK_TRAP; /* trap condition */
//HANGS TRAPME = MACHINECHK_TRAP; /* trap condition */
//HANGS TRAPME = UNDEFINSTR_TRAP; /* Undefined Instruction Trap */
//FIXME goto newpsd; /* handle trap */
} }
break; break;
case 0xB: /* RWCS */ /* RWCS ignore for now */ case 0xB: /* RWCS */ /* RWCS ignore for now */
@ -3809,8 +3740,8 @@ tbr: /* handle basemode TBR too *
t = (GPR[reg] >> 16) & 0xff; /* get SPAD address from Rd (6-8) */ t = (GPR[reg] >> 16) & 0xff; /* get SPAD address from Rd (6-8) */
temp2 = SPAD[t]; /* get old SPAD data */ temp2 = SPAD[t]; /* get old SPAD data */
SPAD[t] = GPR[sreg]; /* store Rs into SPAD */ SPAD[t] = GPR[sreg]; /* store Rs into SPAD */
// sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
// "TRSC SPAD[%04x] B4 %08x New %08x\n", t, temp2, GPR[sreg]); "TRSC SPAD[%04x] B4 %08x New %08x\n", t, temp2, GPR[sreg]);
break; break;
case 0xF: /* TSCR */ /* Transfer scratchpad to register */ case 0xF: /* TSCR */ /* Transfer scratchpad to register */
@ -3824,8 +3755,8 @@ tbr: /* handle basemode TBR too *
} }
t = (GPR[sreg] >> 16) & 0xff; /* get SPAD address from Rs (9-11) */ t = (GPR[sreg] >> 16) & 0xff; /* get SPAD address from Rs (9-11) */
temp = SPAD[t]; /* get SPAD data into Rd (6-8) */ temp = SPAD[t]; /* get SPAD data into Rd (6-8) */
// sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
// "TSCR SPAD[%04x] Val %08x\n", t, temp); "TSCR SPAD[%04x] Val %08x\n", t, temp);
break; break;
} }
GPR[reg] = temp; /* save the temp value to Rd reg */ GPR[reg] = temp; /* save the temp value to Rd reg */
@ -3845,7 +3776,6 @@ skipit:
case 0x30>>2: /* 0x30 */ /* CALM */ case 0x30>>2: /* 0x30 */ /* CALM */
/* Process CALM for 32/27 when in left hw, else invalid */ /* Process CALM for 32/27 when in left hw, else invalid */
if ((CPU_MODEL <= MODEL_87) && (CPU_MODEL != MODEL_67)) { if ((CPU_MODEL <= MODEL_87) && (CPU_MODEL != MODEL_67)) {
// uint32 oldstatus = IPUSTATUS; /* keep for retain blocking state */
/* DIAG error for 32/27 or 32/87 only */ /* DIAG error for 32/27 or 32/87 only */
if ((PSD1 & 2) != 0) /* is it lf hw instruction */ if ((PSD1 & 2) != 0) /* is it lf hw instruction */
goto inv; /* invalid instr if in rt hw */ goto inv; /* invalid instr if in rt hw */
@ -5552,7 +5482,6 @@ doovr2:
temp2>>2, IR&0xFFF, TPSD1, TPSD2, PSD1, PSD2, SPAD[0xf5], IPUSTATUS); temp2>>2, IR&0xFFF, TPSD1, TPSD2, PSD1, PSD2, SPAD[0xf5], IPUSTATUS);
TRAPME = MACHINECHK_TRAP; /* trap condition */ TRAPME = MACHINECHK_TRAP; /* trap condition */
PSD1 = TPSD1; /* restore PSD 1 */ PSD1 = TPSD1; /* restore PSD 1 */
//FIX121222 PSD2 = TPSD2; /* restore PSD 2 */
PSD2 = PSD2; /* diag wants new PSD 2, not old?? */ PSD2 = PSD2; /* diag wants new PSD 2, not old?? */
goto newpsd; /* program error */ goto newpsd; /* program error */
} }
@ -5656,9 +5585,6 @@ dohist:
hst[hst_p].modes |= INTBLKD; /* save blocking mode bit */ hst[hst_p].modes |= INTBLKD; /* save blocking mode bit */
if (IPUSTATUS & BIT27) if (IPUSTATUS & BIT27)
hst[hst_p].modes |= IPUMODE; /* save ipu/ipu status bit */ hst[hst_p].modes |= IPUMODE; /* save ipu/ipu status bit */
//113022 hst[hst_p].modes &= ~(BIT24|BIT27); /* clear blocked and ipu bits */
//113022 hst[hst_p].modes |= (IPUSTATUS & BIT24);/* save blocking mode bit */
//113022 hst[hst_p].modes |= (IPUSTATUS & BIT27);/* save ipu/ipu status bit */
for (ix=0; ix<8; ix++) { for (ix=0; ix<8; ix++) {
hst[hst_p].reg[ix] = GPR[ix]; /* save reg */ hst[hst_p].reg[ix] = GPR[ix]; /* save reg */
hst[hst_p].reg[ix+8] = BR[ix]; /* save breg */ hst[hst_p].reg[ix+8] = BR[ix]; /* save breg */
@ -6092,8 +6018,8 @@ dohist:
i_flags |= BT; /* we branched, so no PC update */ i_flags |= BT; /* we branched, so no PC update */
if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */ if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */
PSD1 = (PSD1 & 0x87fffffe) | temp2; /* insert last indirect CCs */ PSD1 = (PSD1 & 0x87fffffe) | temp2; /* insert last indirect CCs */
/*FIX F77*/ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */
/*FIX F77*/ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */
} }
/* branch not taken, go do next instruction */ /* branch not taken, go do next instruction */
break; break;
@ -6128,8 +6054,8 @@ dohist:
i_flags |= BT; /* we branched, so no PC update */ i_flags |= BT; /* we branched, so no PC update */
if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */ if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */
PSD1 = (PSD1 & 0x87fffffe) | temp2; /* insert last indirect CCs */ PSD1 = (PSD1 & 0x87fffffe) | temp2; /* insert last indirect CCs */
/*FIX F77*/ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */
/*FIX F77*/ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */
} }
break; break;
@ -6150,8 +6076,8 @@ dohist:
if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */ if (((MODES & BASEBIT) == 0) && (IR & IND)) /* see if CCs from last indirect wanted */
PSD1 = (PSD1 & 0x87fffffe) | CC; /* insert last CCs */ PSD1 = (PSD1 & 0x87fffffe) | CC; /* insert last CCs */
i_flags |= BT; /* we branched, so no PC update */ i_flags |= BT; /* we branched, so no PC update */
/*FIX F77*/ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */
/*FIX F77*/ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */
} }
break; break;
@ -6172,8 +6098,8 @@ dohist:
else else
PSD1 = (PSD1 & 0xff000000) | (addr & 0x07fffe); /* bit 13-30 */ PSD1 = (PSD1 & 0xff000000) | (addr & 0x07fffe); /* bit 13-30 */
i_flags |= BT; /* we branched, so no PC update */ i_flags |= BT; /* we branched, so no PC update */
/*FIX F77*/ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */ if ((MODES & (BASEBIT|EXTDBIT)) == 0) /* see if basemode */
/*FIX F77*/ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */ PSD1 &= 0xff07ffff; /* only 19 bit address allowed */
break; break;
case 0x3: /* LPSD F980 */ case 0x3: /* LPSD F980 */
@ -6290,18 +6216,13 @@ dohist:
/* see what mapping we are to do if LPSDCM */ /* see what mapping we are to do if LPSDCM */
if (OPR & 0x0200) { /* Was it LPSDCM? */ if (OPR & 0x0200) { /* Was it LPSDCM? */
if (PSD2 & MAPBIT) { if (PSD2 & MAPBIT) {
//FIXME TRYING FOR DEXP FIX?
#ifndef DEXP_TRY_FIX
/* this mod fixes MPX 1.X 1st swapr load */ /* this mod fixes MPX 1.X 1st swapr load */
/* any O/S or user maps yet? */ /* any O/S or user maps yet? */
if (((CPIX != 0) && (CPIXPL == 0)) && (PSD2 & RETMBIT)) { if (((CPIX != 0) && (CPIXPL == 0)) && (PSD2 & RETMBIT)) {
PSD2 &= ~RETMBIT; /* no, turn off retain bit in PSD2 */ PSD2 &= ~RETMBIT; /* no, turn off retain bit in PSD2 */
sim_debug(DEBUG_TRAP, my_dev, "Turn off retain bit\n"); sim_debug(DEBUG_TRAP, my_dev, "Turn off retain bit\n");
} }
#endif
//FIXME TRYING FOR DEXP FIX?
#ifndef DEXP_TRY_FIX
/* test if user count is equal to CPIXPL, if not load maps */ /* test if user count is equal to CPIXPL, if not load maps */
/* this fixes software error in MPX3X where count is changed */ /* this fixes software error in MPX3X where count is changed */
/* but the retain bit was left set, so new maps were not loaded */ /* but the retain bit was left set, so new maps were not loaded */
@ -6332,7 +6253,6 @@ dohist:
"LPSDCM FIX MAP TRAPME %02x PSD %08x %08x spc %02x BPIX %02x CPIXPL %02x retain %01x\n", "LPSDCM FIX MAP TRAPME %02x PSD %08x %08x spc %02x BPIX %02x CPIXPL %02x retain %01x\n",
TRAPME, PSD1, PSD2, spc, BPIX, CPIXPL, PSD2&RETMBIT?1:0); TRAPME, PSD1, PSD2, spc, BPIX, CPIXPL, PSD2&RETMBIT?1:0);
} }
#endif
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"LPSDCML %.6x NPSD %08x %08x OPSD %08x %08x SPADF5 %x STATUS %08x\n", "LPSDCML %.6x NPSD %08x %08x OPSD %08x %08x SPADF5 %x STATUS %08x\n",
addr, PSD1, PSD2, TPSD1, TPSD2, ix, IPUSTATUS); addr, PSD1, PSD2, TPSD1, TPSD2, ix, IPUSTATUS);
@ -6363,7 +6283,6 @@ dohist:
"LPSDCM BAD MAPS LOAD TRAPME %02x PSD %08x %08x IPUSTAT %08x SPAD[f9] %08x\n", "LPSDCM BAD MAPS LOAD TRAPME %02x PSD %08x %08x IPUSTAT %08x SPAD[f9] %08x\n",
TRAPME, PSD1, PSD2, IPUSTATUS, SPAD[0xf9]); TRAPME, PSD1, PSD2, IPUSTATUS, SPAD[0xf9]);
PSD1 = TPSD1; /* restore PSD1 */ PSD1 = TPSD1; /* restore PSD1 */
//NO, USE NEW PSD2 = TPSD2; /* restore PSD2 */
/* HACK HACK HACK */ /* HACK HACK HACK */
/* Diags wants the new PSD2, not the original on error??? */ /* Diags wants the new PSD2, not the original on error??? */
/* if old one was used, we fail test 21/0 in cn.mmm for 32/67 */ /* if old one was used, we fail test 21/0 in cn.mmm for 32/67 */
@ -6425,7 +6344,6 @@ dohist:
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"IPU SIO PSD %.8x %.8x SPDF5 %.8x IPUSTATUS %08x\n", "IPU SIO PSD %.8x %.8x SPDF5 %.8x IPUSTATUS %08x\n",
PSD1, PSD2, SPAD[0xf5], IPUSTATUS); PSD1, PSD2, SPAD[0xf5], IPUSTATUS);
//DIAGS FIX i_flags |= BT; /* leave PC unchanged, so no PC update */
goto newpsd; goto newpsd;
} }
break; break;
@ -6677,11 +6595,9 @@ newpsd:
case MACHINECHK_TRAP: /* 0x9C PL07 Machine Check Trap */ case MACHINECHK_TRAP: /* 0x9C PL07 Machine Check Trap */
case SYSTEMCHK_TRAP: /* 0xA0 PL08 System Check Trap */ case SYSTEMCHK_TRAP: /* 0xA0 PL08 System Check Trap */
case MAPFAULT_TRAP: /* 0xA4 PL09 Map Fault Trap */ case MAPFAULT_TRAP: /* 0xA4 PL09 Map Fault Trap */
//MOVED case IPUUNDEFI_TRAP: /* 0xA8 PL0A IPU Undefined Instruction Trap */
case IPUUNDEFI_TRAP: /* 0xA8 PL0A IPU Undefined Instruction Trap */ case IPUUNDEFI_TRAP: /* 0xA8 PL0A IPU Undefined Instruction Trap */
//MOVED case CALM_TRAP: /* 0xA8 PL0A Call Monitor Instruction Trap */ //MOVED case CALM_TRAP: /* 0xA8 PL0A Call Monitor Instruction Trap */
//MOVED case SIGNALIPU_TRAP: /* 0xAC PL0B Signal IPU/CPU Trap */ //MOVED case SIGNALIPU_TRAP: /* 0xAC PL0B Signal IPU/CPU Trap */
case ADDRSPEC_TRAP: /* 0xB0 PL0C Address Specification Trap */ case ADDRSPEC_TRAP: /* 0xB0 PL0C Address Specification Trap */
//BAD HERE case CONSOLEATN_TRAP: /* 0xB4 PL0D Console Attention Trap */ //BAD HERE case CONSOLEATN_TRAP: /* 0xB4 PL0D Console Attention Trap */
case PRIVHALT_TRAP: /* 0xB8 PL0E Privlege Mode Halt Trap */ case PRIVHALT_TRAP: /* 0xB8 PL0E Privlege Mode Halt Trap */
@ -6739,16 +6655,7 @@ newpsd:
/* This caused the 2nd instruction of an int service routine to be skipped */ /* This caused the 2nd instruction of an int service routine to be skipped */
/* The attn trap had to be on 2nd instruction */ /* The attn trap had to be on 2nd instruction */
case CONSOLEATN_TRAP: /* 0xB4 PL0D Console Attention Trap */ case CONSOLEATN_TRAP: /* 0xB4 PL0D Console Attention Trap */
//112522 case IPUUNDEFI_TRAP: /* 0xA8 PL0A IPU Undefined Instruction Trap */
case SIGNALIPU_TRAP: /* 0xAC PL0B Signal IPU/CPU Trap */ case SIGNALIPU_TRAP: /* 0xAC PL0B Signal IPU/CPU Trap */
#ifdef TRACE_SIPU
if ((TRAPME == SIGNALIPU_TRAP) || (TRAPME == IPUUNDEFI_TRAP))
ipu_dev.dctrl |= DEBUG_INST; /* start instruction trace */
#endif
sim_debug(DEBUG_TRAP, my_dev,
"At %s TRAPME %02x PC %08x PSD1 %08x PSD2 %08x IPUSTATUS %08x tta %02x\n",
(IPUSTATUS & ONIPU)? "IPU": "CPU",
TRAPME, PC, PSD1, PSD2, IPUSTATUS, tta);
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"At %s TRAP %02x IR %08x PSD1 %08x PSD2 %08x IPUSTATUS %08x drop_nop %01x\n", "At %s TRAP %02x IR %08x PSD1 %08x PSD2 %08x IPUSTATUS %08x drop_nop %01x\n",
(IPUSTATUS & ONIPU)? "IPU": "CPU", (IPUSTATUS & ONIPU)? "IPU": "CPU",
@ -6759,10 +6666,32 @@ newpsd:
"R4=%.8x R5=%.8x R6=%.8x R7=%.8x\n", GPR[4], GPR[5], GPR[6], GPR[7]); "R4=%.8x R5=%.8x R6=%.8x R7=%.8x\n", GPR[4], GPR[5], GPR[6], GPR[7]);
tta = tta + (TRAPME - 0x80); /* tta has mem addr of trap vector */ tta = tta + (TRAPME - 0x80); /* tta has mem addr of trap vector */
if (!MEM_ADDR_OK((tta>>2) & MASK24)) { /* see if in memory */
sim_debug(DEBUG_TRAP, my_dev,
"IPU Bad trap tta %08x PSD1 %08x PSD2 %08x TRAPME %02x\n",
tta, PSD1, PSD2, TRAPME);
/* bad address for trap vector, lets halt */
fprintf(stderr, "IPU Bad trap tta %08x PSD1 %08x PSD2 %08x TRAPME %02x\r\n",
tta, PSD1, PSD2, TRAPME);
fprintf(stderr, "IPU Bad trap address tvl %08x, tta %02x CCW %08x status %08x\r\n",
tvl, tta, CCW, IPUSTATUS);
fflush(stderr);
goto doahalt;
}
tvl = M[tta>>2] & 0xFFFFFC; /* get 24 bit trap address from trap vector loc */ tvl = M[tta>>2] & 0xFFFFFC; /* get 24 bit trap address from trap vector loc */
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"tvl %08x, tta %02x CCW %08x status %08x\n", "IPU tvl %08x, tta %02x CCW %08x status %08x\n",
tvl, tta, CCW, IPUSTATUS); tvl, tta, CCW, IPUSTATUS);
if (!MEM_ADDR_OK(tvl & MASK24)) { /* see if in memory */
sim_debug(DEBUG_TRAP, my_dev,
"IPU Bad trap PSD1 %08x PSD2 %08x TRAPME %02x\r\n", PSD1, PSD2, TRAPME);
/* bad address for trap vector, lets halt */
fprintf(stderr, "IPU Bad trap PSD1 %08x PSD2 %08x TRAPME %02x\r\n", PSD1, PSD2, TRAPME);
fprintf(stderr, "IPU Bad trap address tvl %08x, tta %02x CCW %08x status %08x\r\n",
tvl, tta, CCW, IPUSTATUS);
fflush(stderr);
goto doahalt;
}
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"M[tta] %08x M[tvl] %08x M[tvl+1] %08x M[tvl+2] %08x M[tvl+3]] %08x\n", "M[tta] %08x M[tvl] %08x M[tvl+1] %08x M[tvl+2] %08x M[tvl+3]] %08x\n",
M[tta>>2], M[(tvl>>2)+0], M[(tvl>>2)+1], M[(tvl>>2)+2], M[(tvl>>2)+3]); M[tta>>2], M[(tvl>>2)+0], M[(tvl>>2)+1], M[(tvl>>2)+2], M[(tvl>>2)+3]);
@ -6774,14 +6703,12 @@ newpsd:
if (((tvl == 0) || (IPUSTATUS & 0x40) == 0) || if (((tvl == 0) || (IPUSTATUS & 0x40) == 0) ||
(TRAPME == PRIVHALT_TRAP)) { /* 0xB8 PL0E Privlege Mode Halt Trap */ (TRAPME == PRIVHALT_TRAP)) { /* 0xB8 PL0E Privlege Mode Halt Trap */
#endif #endif
doahalt:
/* vector is zero or software has not enabled traps yet */ /* vector is zero or software has not enabled traps yet */
/* execute a trap halt */ /* execute a trap halt */
/* set the PSD to trap vector location */ /* set the PSD to trap vector location */
fprintf(stderr, "[][][][][][][][][][] IPU HALT TRAP [2][][][][][][][][][]\r\n"); TPSD1 = 0x80000000 + tta; /* just priv and PC to trap vector */
fprintf(stderr, "PSD1 %08x PSD2 %08x TRAPME %02x\r\n", PSD1, PSD2, TRAPME); TPSD2 = 0x00004000; /* unmapped, blocked interrupts mode */
//FIX PSD1 = 0x80000000 + TRAPME; /* just priv and PC to trap vector */
PSD1 = 0x80000000 + tta; /* just priv and PC to trap vector */
PSD2 = 0x00004000; /* unmapped, blocked interrupts mode */
/* /*
* Some illegal traps result in automatic TRAP HALT * Some illegal traps result in automatic TRAP HALT
* as per V6 TM page 2-50 locations for saving status * as per V6 TM page 2-50 locations for saving status
@ -6789,17 +6716,35 @@ newpsd:
*/ */
if (IPUSTATUS & ONIPU) { if (IPUSTATUS & ONIPU) {
/* for IPU */ /* for IPU */
M[0x690>>2] = PSD1; /* store PSD 1 */ M[0x690>>2] = TPSD1; /* store PSD 1 */
M[0x694>>2] = PSD2; /* store PSD 2 */ M[0x694>>2] = TPSD2; /* store PSD 2 */
M[0x698>>2] = TRAPSTATUS; /* store trap status */ M[0x698>>2] = TRAPSTATUS; /* store trap status */
M[0x69C>>2] = 0; /* This will be device table entry later TODO */ M[0x69C>>2] = 0; /* This will be device table entry later TODO */
} else { } else {
/* for IPU */ /* for IPU */
M[0x680>>2] = PSD1; /* store PSD 1 */ M[0x680>>2] = TPSD1; /* store PSD 1 */
M[0x684>>2] = PSD2; /* store PSD 2 */ M[0x684>>2] = TPSD2; /* store PSD 2 */
M[0x688>>2] = TRAPSTATUS; /* store trap status */ M[0x688>>2] = TRAPSTATUS; /* store trap status */
M[0x68C>>2] = 0; /* This will be device table entry later TODO */ M[0x68C>>2] = 0; /* This will be device table entry later TODO */
} }
if (cpustop == STOP_HALT) {
fprintf(stderr, "[][][][][][][][][][] IPU HALT TRAP [2][][][][][][][][][]\r\n");
fprintf(stderr, "PSD1 %08x PSD2 %08x TRAPME %02x cpustop %x\r\n",
PSD1, PSD2, TRAPME, cpustop);
/* CPU is halting and we are halted, so wait for new command */
IPUSTATUS &= ~BIT24; /* clear blocked bit 24 */
MODES &= ~BLKMODE; /* reset blocked mode */
PSD2 &= ~(SETBBIT|RETBBIT); /* clear bit 48 & 49 to be unblocked */
wait4sipu = 1; /* show we are waiting for SIPU */
cpustop = STOP_WAITING; /* tell IPU our state */
reason = SCPE_OK; /* look for sipu */
sim_os_ms_sleep(10); /* wait 10 ms */
goto cond_go; /* start waiting for SIPU */
}
if (cpustop != STOP_RESET) {
fprintf(stderr, "[][][][][][][][][][] IPU HALT TRAP [2][][][][][][][][][]\r\n");
fprintf(stderr, "PSD1 %08x PSD2 %08x TRAPME %02x cpustop %x\r\n",
PSD1, PSD2, TRAPME, cpustop);
for (ix=0; ix<8; ix+=2) { for (ix=0; ix<8; ix+=2) {
fprintf(stderr, "GPR[%d] %08x GPR[%d] %08x\r\n", ix, GPR[ix], ix+1, GPR[ix+1]); fprintf(stderr, "GPR[%d] %08x GPR[%d] %08x\r\n", ix, GPR[ix], ix+1, GPR[ix+1]);
} }
@ -6815,12 +6760,17 @@ newpsd:
(IPUSTATUS & ONIPU)? "IPU": "IPU", (IPUSTATUS & ONIPU)? "IPU": "IPU",
IPUSTATUS, CCW); IPUSTATUS, CCW);
} }
/*TEST DIAG*/ reason = STOP_HALT; /* do halt for now */
cpustop = reason; /* tell IPU our state */
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"[][][][][][][][][][] IPU HALT2 [2][][][][][][][][][]\n"); "[][][][][][][][][][] IPU HALT2 [2][][][][][][][][][]\n");
fflush(sim_deb); fflush(sim_deb);
fflush(stderr);
}
sim_os_ms_sleep(10); /* wait 10 ms */
#ifdef DO_NO_EXIT
reason = STOP_HALT; /* do halt for now */
cpustop = reason; /* tell IPU our state */
pthread_exit((void *)&reason); pthread_exit((void *)&reason);
#endif
} else { } else {
uint32 oldstatus = IPUSTATUS; /* keep for retain blocking state */ uint32 oldstatus = IPUSTATUS; /* keep for retain blocking state */
/* valid vector, so store the PSD, fetch new PSD */ /* valid vector, so store the PSD, fetch new PSD */
@ -6883,7 +6833,6 @@ newpsd:
sim_debug(DEBUG_TRAP, my_dev, sim_debug(DEBUG_TRAP, my_dev,
"Process %s TRAPME %02x PSD1 %08x PSD2 %08x IPUSTATUS %08x MODE %08x\n", "Process %s TRAPME %02x PSD1 %08x PSD2 %08x IPUSTATUS %08x MODE %08x\n",
(IPUSTATUS & ONIPU)? "IPU": "CPU", (IPUSTATUS & ONIPU)? "IPU": "CPU",
//FIX TRAPME, PSD1, PSD2, IPUSTATUS, MODES);
tta, PSD1, PSD2, IPUSTATUS, MODES); tta, PSD1, PSD2, IPUSTATUS, MODES);
/* TODO provide page fault data to word 6 */ /* TODO provide page fault data to word 6 */
if (TRAPME == DEMANDPG_TRAP) { /* 0xC4 Demand Page Fault Trap (V6&V9 Only) */ if (TRAPME == DEMANDPG_TRAP) { /* 0xC4 Demand Page Fault Trap (V6&V9 Only) */
@ -6923,10 +6872,10 @@ newpsd:
"[][][][][][][][][][] HALT [3][][][][][][][][][]\n"); "[][][][][][][][][][] HALT [3][][][][][][][][][]\n");
fflush(sim_deb); fflush(sim_deb);
#ifdef DEBUG4IPU #ifndef DEBUG4IPU
DumpHist(); DumpHist();
#endif #endif
fprintf(stdout, "[][][][][][][][][][] IPU HALT3 [3][][][][][][][][][]\r\n"); fprintf(stdout, "[][][][][][][][][][] IPU HALT [3][][][][][][][][][]\r\n");
fflush(stdout); fflush(stdout);
pthread_exit((void *)&reason); pthread_exit((void *)&reason);
return (0); /* dummy return for Windows */ return (0); /* dummy return for Windows */
@ -7009,7 +6958,6 @@ t_stat ipu_reset(DEVICE *dptr)
SPAD[0xf5] = PSD2; /* current PSD2 defaults to blocked */ SPAD[0xf5] = PSD2; /* current PSD2 defaults to blocked */
SPAD[0xf6] = 0; /* reserved (PSD1 ??) */ SPAD[0xf6] = 0; /* reserved (PSD1 ??) */
SPAD[0xf7] = 0x13254768; /* set SPAD key for IPU */ SPAD[0xf7] = 0x13254768; /* set SPAD key for IPU */
//120822SPAD[0xf8] = 0x0000f000; /* set DRT to class f (anything else is E) */
SPAD[0xf8] = 0x0f000000; /* set DRT to class f (anything else is E) */ SPAD[0xf8] = 0x0f000000; /* set DRT to class f (anything else is E) */
SPAD[0xf9] = IPUSTATUS; /* set default ipu type in ipu status word */ SPAD[0xf9] = IPUSTATUS; /* set default ipu type in ipu status word */
SPAD[0xff] = 0x00ffffff; /* interrupt level 7f 1's complament */ SPAD[0xff] = 0x00ffffff; /* interrupt level 7f 1's complament */
@ -7192,6 +7140,7 @@ t_stat ipu_show_hist(FILE *st, UNIT *uptr, int32 val, CONST void *desc)
} }
fprintf(st, "\n"); fprintf(st, "\n");
} /* end for */ } /* end for */
fflush(sim_deb);
return SCPE_OK; /* all is good */ return SCPE_OK; /* all is good */
} }

View file

@ -75,7 +75,7 @@ LPFCTBL EQU $
#if NUM_DEVS_LPR > 0 #if NUM_DEVS_LPR > 0
#define UNIT_LPR UNIT_ATTABLE | UNIT_IDLE | UNIT_DISABLE | UNIT_SEQ #define UNIT_LPR UNIT_ATTABLE|UNIT_DISABLE|UNIT_SEQ
#define CMD u3 #define CMD u3
/* u3 holds command and status information */ /* u3 holds command and status information */
@ -129,7 +129,6 @@ LPFCTBL EQU $
#define SNS_NU5 0x04000000 /* Not used */ #define SNS_NU5 0x04000000 /* Not used */
#define SNS_NU6 0x02000000 /* Not used */ #define SNS_NU6 0x02000000 /* Not used */
#define SNS_NU7 0x01000000 /* Not used */ #define SNS_NU7 0x01000000 /* Not used */
#define SNS_BOF 0x01000000 /* Not used, temp setting for paper at BOT */
/* Sense byte 1 */ /* Sense byte 1 */
#define SNS_DEVVFY 0x00800000 /* Device Verify Interface Cable Disconnected */ #define SNS_DEVVFY 0x00800000 /* Device Verify Interface Cable Disconnected */
/* plus SNS_OPRINTR */ /* plus SNS_OPRINTR */
@ -139,7 +138,7 @@ LPFCTBL EQU $
#define SNS_NU2 0x00080000 /* Not used */ #define SNS_NU2 0x00080000 /* Not used */
#define SNS_NU1 0x00040000 /* Not used */ #define SNS_NU1 0x00040000 /* Not used */
#define SNS_BEGOF 0x00020000 /* Beginning of form */ #define SNS_BEGOF 0x00020000 /* Beginning of form */
#define SNS_TOF 0x00010000 /* Top of form on printer */ #define SNS_BOF 0x00010000 /* Bottom of form on printer */
/* Sense byte 2-3 have remaining channel cnt of zero */ /* Sense byte 2-3 have remaining channel cnt of zero */
#define CBP u6 #define CBP u6
@ -220,7 +219,6 @@ DEVICE lpr_dev = {
NULL, NULL, NULL, NULL, &lpr_attach, &lpr_detach, NULL, NULL, NULL, NULL, &lpr_attach, &lpr_detach,
/* ctxt is the DIB pointer */ /* ctxt is the DIB pointer */
&lpr_dib, DEV_DISABLE|DEV_DEBUG, 0, dev_debug, &lpr_dib, DEV_DISABLE|DEV_DEBUG, 0, dev_debug,
// &lpr_dib, DEV_DISABLE|DEV_DEBUG|DEV_DIS, 0, dev_debug,
NULL, NULL, &lpr_help, NULL, NULL, &lpr_description, NULL, NULL, &lpr_help, NULL, NULL, &lpr_description,
}; };
@ -406,13 +404,10 @@ t_stat lpr_srv(UNIT *uptr) {
return SCPE_OK; return SCPE_OK;
} }
/* NEW_02092022 */
/* make sure we have a file attached, else give error */ /* make sure we have a file attached, else give error */
if ((uptr->flags & UNIT_ATT) == 0) { if ((uptr->flags & UNIT_ATT) == 0) {
uptr->CMD &= LMASK; /* make non-busy */ uptr->CMD &= LMASK; /* make non-busy */
// uptr->SNS |= SNS_DEVPWR; /* show powered off */
uptr->SNS |= SNS_DEVCHK; /* show device check */ uptr->SNS |= SNS_DEVCHK; /* show device check */
// uptr->SNS |= SNS_OFFLINE; /* show printer offline */
uptr->SNS |= SNS_OPRINTR; /* operator intervention required */ uptr->SNS |= SNS_OPRINTR; /* operator intervention required */
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"lpr_startcmd Cmd %02x LPR not attached SNS %08x\n", cmd, uptr->SNS); "lpr_startcmd Cmd %02x LPR not attached SNS %08x\n", cmd, uptr->SNS);
@ -444,17 +439,17 @@ t_stat lpr_srv(UNIT *uptr) {
case 4: /* <FF> (0x0c) */ case 4: /* <FF> (0x0c) */
lpr_data[u].lbuff[uptr->CBP++] = 0x0d; /* add C/R */ lpr_data[u].lbuff[uptr->CBP++] = 0x0d; /* add C/R */
lpr_data[u].lbuff[uptr->CBP++] = 0x0a; /* add L/F */ lpr_data[u].lbuff[uptr->CBP++] = 0x0a; /* add L/F */
lpr_data[u].lbuff[uptr->CBP++] = 0x0c; /* add FF */ lpr_data[u].lbuff[uptr->CBP++] = 0x0a; /* add FF */
uptr->CNT = 0; /* restart line count */ uptr->CNT = 0; /* restart line count */
/* set beginning of form and top of form */ /* set beginning of form */
uptr->SNS |= (SNS_TOF|SNS_BEGOF); uptr->SNS |= SNS_BEGOF;
break; break;
} }
} }
/* Copy next byte from users buffer */ /* Copy next byte from users buffer */
while ((uptr->CMD & LPR_FULL) == 0) { /* copy in a char if not full */ while ((uptr->CMD & LPR_FULL) == 0) { /* copy in a char if not full */
if(chan_read_byte(chsa, &lpr_data[u].lbuff[uptr->CBP])) { if (chan_read_byte(chsa, &lpr_data[u].lbuff[uptr->CBP])) {
uptr->CMD |= LPR_FULL; /* end of buffer or error */ uptr->CMD |= LPR_FULL; /* end of buffer or error */
break; /* done reading */ break; /* done reading */
} else { } else {
@ -512,10 +507,10 @@ t_stat lpr_srv(UNIT *uptr) {
case 4: /* <FF> (0x0c) */ case 4: /* <FF> (0x0c) */
lpr_data[u].lbuff[uptr->CBP++] = 0x0d; /* add C/R */ lpr_data[u].lbuff[uptr->CBP++] = 0x0d; /* add C/R */
lpr_data[u].lbuff[uptr->CBP++] = 0x0a; /* add L/F */ lpr_data[u].lbuff[uptr->CBP++] = 0x0a; /* add L/F */
lpr_data[u].lbuff[uptr->CBP++] = 0x0c; /* add FF */ lpr_data[u].lbuff[uptr->CBP++] = 0x0a; /* add FF */
uptr->CNT = 0; /* restart line count */ uptr->CNT = 0; /* restart line count */
/* set beginning of form and top of form */ /* set beginning of form */
uptr->SNS |= (SNS_TOF|SNS_BEGOF); uptr->SNS |= SNS_BEGOF;
break; break;
} }
} }
@ -527,7 +522,7 @@ t_stat lpr_srv(UNIT *uptr) {
sim_debug(DEBUG_DETAIL, dptr, "LPR %d %s\n", uptr->CNT, (char*)&lpr_data[u].lbuff); sim_debug(DEBUG_DETAIL, dptr, "LPR %d %s\n", uptr->CNT, (char*)&lpr_data[u].lbuff);
uptr->CMD &= ~(LPR_FULL|LPR_CMDMSK); /* clear old status */ uptr->CMD &= ~(LPR_FULL|LPR_CMDMSK); /* clear old status */
uptr->CBP = 0; /* start at beginning of buffer */ uptr->CBP = 0; /* start at beginning of buffer */
if ((uint32)uptr->CNT > uptr->capac) { /* see if at max lines/page */ if ((uint32)uptr->CNT >= uptr->capac) { /* see if at max lines/page */
uptr->CNT = 0; /* yes, restart count */ uptr->CNT = 0; /* yes, restart count */
uptr->SNS |= SNS_BOF; /* set BOF for SENSE */ uptr->SNS |= SNS_BOF; /* set BOF for SENSE */
sim_debug(DEBUG_CMD, dptr, "lpr_srv Got BOF\n"); sim_debug(DEBUG_CMD, dptr, "lpr_srv Got BOF\n");
@ -536,8 +531,8 @@ t_stat lpr_srv(UNIT *uptr) {
} else { } else {
uptr->SNS &= ~SNS_BOF; /* reset BOF for SENSE */ uptr->SNS &= ~SNS_BOF; /* reset BOF for SENSE */
if (uptr->CNT == 0) { if (uptr->CNT == 0) {
/* set beginning of form and top of form */ /* set beginning of form */
uptr->SNS |= (SNS_TOF|SNS_BEGOF); uptr->SNS |= SNS_BEGOF;
} }
chan_end(chsa, SNS_DEVEND|SNS_CHNEND); /* we are done */ chan_end(chsa, SNS_DEVEND|SNS_CHNEND); /* we are done */
} }
@ -593,7 +588,7 @@ t_stat lpr_setlpp(UNIT *uptr, int32 val, CONST char *cptr, void *desc)
if (uptr == NULL) if (uptr == NULL)
return SCPE_IERR; return SCPE_IERR;
i = 0; i = 0;
while(*cptr != '\0') { while (*cptr != '\0') {
if (*cptr < '0' || *cptr > '9') if (*cptr < '0' || *cptr > '9')
return SCPE_ARG; return SCPE_ARG;
i = (i * 10) + (*cptr++) - '0'; i = (i * 10) + (*cptr++) - '0';
@ -602,8 +597,8 @@ t_stat lpr_setlpp(UNIT *uptr, int32 val, CONST char *cptr, void *desc)
return SCPE_ARG; return SCPE_ARG;
uptr->capac = i; uptr->capac = i;
uptr->CNT = 0; uptr->CNT = 0;
/* set beginning of form and top of form */ /* set beginning of form */
uptr->SNS |= (SNS_TOF|SNS_BEGOF); uptr->SNS |= SNS_BEGOF;
return SCPE_OK; return SCPE_OK;
} }
@ -630,8 +625,8 @@ t_stat lpr_attach(UNIT *uptr, CONST char *file)
uptr->CMD &= ~(LPR_FULL|LPR_CMDMSK); uptr->CMD &= ~(LPR_FULL|LPR_CMDMSK);
uptr->CNT = 0; uptr->CNT = 0;
uptr->SNS = 0; uptr->SNS = 0;
/* set beginning of form and top of form */ /* set beginning of form */
uptr->SNS |= (SNS_TOF|SNS_BEGOF); uptr->SNS |= SNS_BEGOF;
uptr->capac = 66; uptr->capac = 66;
/* check for valid configured lpr */ /* check for valid configured lpr */

View file

@ -36,7 +36,7 @@
#if NUM_DEVS_MFP > 0 #if NUM_DEVS_MFP > 0
#define UNIT_MFP UNIT_IDLE | UNIT_DISABLE #define UNIT_MFP UNIT_DISABLE
/* forward definitions */ /* forward definitions */
t_stat mfp_preio(UNIT *uptr, uint16 chan); t_stat mfp_preio(UNIT *uptr, uint16 chan);
@ -102,7 +102,8 @@ UNIT mfp_unit[] = {
{UDATA(&mfp_srv, UNIT_MFP, 0), 0, UNIT_ADDR(0x7600)}, /* Channel controller */ {UDATA(&mfp_srv, UNIT_MFP, 0), 0, UNIT_ADDR(0x7600)}, /* Channel controller */
}; };
//DIB mfp_dib = {NULL, mfp_startcmd, NULL, NULL, NULL, mfp_ini, mfp_unit, mfp_chp, NUM_UNITS_MFP, 0xff, 0x7600,0,0,0}; //DIB mfp_dib = {NULL, mfp_startcmd, NULL, NULL, NULL, mfp_ini, mfp_unit,
// mfp_chp, NUM_UNITS_MFP, 0xff, 0x7600,0,0,0};
DIB mfp_dib = { DIB mfp_dib = {
mfp_preio, /* t_stat (*pre_io)(UNIT *uptr, uint16 chan)*/ /* Pre Start I/O */ mfp_preio, /* t_stat (*pre_io)(UNIT *uptr, uint16 chan)*/ /* Pre Start I/O */
mfp_startcmd, /* t_stat (*start_cmd)(UNIT *uptr, uint16 chan, uint8 cmd)*/ /* Start command */ mfp_startcmd, /* t_stat (*start_cmd)(UNIT *uptr, uint16 chan, uint8 cmd)*/ /* Start command */
@ -320,7 +321,7 @@ t_stat mfp_srv(UNIT *uptr)
/* the chp->ccw_addr location contains the inch address */ /* the chp->ccw_addr location contains the inch address */
/* 1-256 wd buffer is provided for 128 status dbl words */ /* 1-256 wd buffer is provided for 128 status dbl words */
///?? tstart = set_inch(uptr, mema, 128); /* new address of 128 entries */ ///?? tstart = set_inch(uptr, mema, 128); /* new address of 128 entries */
tstart = set_inch(uptr, mema, 1); /* new address of 1 entrie */ tstart = set_inch(uptr, mema, 1); /* new address of 1 entry */
if ((tstart == SCPE_MEM) || (tstart == SCPE_ARG)) { /* any error */ if ((tstart == SCPE_MEM) || (tstart == SCPE_ARG)) { /* any error */
/* we have error, bail out */ /* we have error, bail out */
uptr->u5 |= SNS_CMDREJ; uptr->u5 |= SNS_CMDREJ;

View file

@ -288,14 +288,14 @@ MTAB mt_mod[] = {
UNIT mta_unit[] = { UNIT mta_unit[] = {
/* Unit data layout for MT devices */ /* Unit data layout for MT devices */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1000)}, /* 0 */ {UDATA(&mt_srv, UNIT_MT, 0), 0, UNIT_ADDR(0x1000)}, /* 0 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1001)}, /* 1 */ {UDATA(&mt_srv, UNIT_MT, 0), 0, UNIT_ADDR(0x1001)}, /* 1 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1002)}, /* 2 */ {UDATA(&mt_srv, UNIT_MT, 0), 0, UNIT_ADDR(0x1002)}, /* 2 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1003)}, /* 3 */ {UDATA(&mt_srv, UNIT_MT, 0), 0, UNIT_ADDR(0x1003)}, /* 3 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1004)}, /* 4 */ {UDATA(&mt_srv, UNIT_MT, 0), 0, UNIT_ADDR(0x1004)}, /* 4 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1005)}, /* 5 */ {UDATA(&mt_srv, UNIT_MT, 0), 0, UNIT_ADDR(0x1005)}, /* 5 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1006)}, /* 6 */ {UDATA(&mt_srv, UNIT_MT, 0), 0, UNIT_ADDR(0x1006)}, /* 6 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1007)}, /* 7 */ {UDATA(&mt_srv, UNIT_MT, 0), 0, UNIT_ADDR(0x1007)}, /* 7 */
}; };
/* channel program information */ /* channel program information */
@ -337,14 +337,14 @@ DEVICE mta_dev = {
CHANP mtb_chp[NUM_UNITS_MT] = {0}; CHANP mtb_chp[NUM_UNITS_MT] = {0};
UNIT mtb_unit[] = { UNIT mtb_unit[] = {
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1800)}, /* 0 */ {UDATA(&mt_srv, UNIT_MT|0), 0, UNIT_ADDR(0x1800)}, /* 0 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1801)}, /* 1 */ {UDATA(&mt_srv, UNIT_MT|0), 0, UNIT_ADDR(0x1801)}, /* 1 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1802)}, /* 2 */ {UDATA(&mt_srv, UNIT_MT|0), 0, UNIT_ADDR(0x1802)}, /* 2 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1803)}, /* 3 */ {UDATA(&mt_srv, UNIT_MT|0), 0, UNIT_ADDR(0x1803)}, /* 3 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1804)}, /* 4 */ {UDATA(&mt_srv, UNIT_MT|0), 0, UNIT_ADDR(0x1804)}, /* 4 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1805)}, /* 5 */ {UDATA(&mt_srv, UNIT_MT|0), 0, UNIT_ADDR(0x1805)}, /* 5 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1806)}, /* 6 */ {UDATA(&mt_srv, UNIT_MT|0), 0, UNIT_ADDR(0x1806)}, /* 6 */
{UDATA(&mt_srv, UNIT_MT|UNIT_IDLE, 0), 0, UNIT_ADDR(0x1807)}, /* 7 */ {UDATA(&mt_srv, UNIT_MT|0), 0, UNIT_ADDR(0x1807)}, /* 7 */
}; };
/* device information block */ /* device information block */
@ -378,6 +378,15 @@ DEVICE mtb_dev = {
}; };
#endif #endif
/* table with filenames of attached units */
struct attfileinfo {
uint16 chsa;
char *att_file;
struct attfileinfo *next;
};
struct attfileinfo *att_files = (struct attfileinfo *) NULL;
/* load in the IOCD and process the commands */ /* load in the IOCD and process the commands */
/* return = 0 OK */ /* return = 0 OK */
/* return = 1 error, chan_status will have reason */ /* return = 1 error, chan_status will have reason */
@ -826,11 +835,22 @@ t_stat mt_srv(UNIT *uptr)
uint32 mema, m, skip; uint32 mema, m, skip;
uint16 len; uint16 len;
uint8 ch; uint8 ch;
struct attfileinfo *afi;
sim_debug(DEBUG_CMD, dptr, sim_debug(DEBUG_CMD, dptr,
"mt_srv unit %02x cmd %02x POS %x hwmark %03x\n", "mt_srv unit %02x cmd %02x POS %x hwmark %03x\n",
unit, cmd, uptr->POS, uptr->hwmark); unit, cmd, uptr->POS, uptr->hwmark);
/* reattach tapedev that has been set offline */
if ((uptr->SNS & SNS_ONLN) == 0) {
afi = att_files;
while (afi != (struct attfileinfo *) NULL && afi->chsa != chsa)
afi = afi->next;
/* only when valid entry found */
if (afi != (struct attfileinfo *) NULL && afi->att_file[0] != '\0')
mt_attach(uptr, afi->att_file);
}
switch (cmd) { switch (cmd) {
case MT_CMDMSK: /* 0x0ff for inch 0x00 */ /* INCH is for channel, nothing for us */ case MT_CMDMSK: /* 0x0ff for inch 0x00 */ /* INCH is for channel, nothing for us */
len = chp->ccw_count; /* INCH command count */ len = chp->ccw_count; /* INCH command count */
@ -1176,7 +1196,7 @@ rewrite:
case MT_BSR: /* 0x53 */ /* Backspace record */ case MT_BSR: /* 0x53 */ /* Backspace record */
sim_debug(DEBUG_CMD, dptr, "mt_srv cmd 0x53 BSR unit %02x POS %x SNS %08x\n", sim_debug(DEBUG_CMD, dptr, "mt_srv cmd 0x53 BSR unit %02x POS %x SNS %08x\n",
unit, uptr->POS, uptr->SNS); unit, uptr->POS, uptr->SNS);
switch (uptr->POS ) { switch (uptr->POS) {
case 0: case 0:
if (sim_tape_bot(uptr)) { if (sim_tape_bot(uptr)) {
uptr->CMD &= ~MT_CMDMSK; uptr->CMD &= ~MT_CMDMSK;
@ -1251,7 +1271,7 @@ rewrite:
#endif #endif
uptr->SNS &= ~(SNS_LOAD|SNS_EOT|SNS_FMRKDT); /* reset BOT, EOT, EOF */ uptr->SNS &= ~(SNS_LOAD|SNS_EOT|SNS_FMRKDT); /* reset BOT, EOT, EOF */
#ifdef NBSF #ifdef NBSF
/* using the backspace file call does not work with MPX */ /* using the backspace file call on simh does not work with MPX */
r = sim_tape_spfiler(uptr, skip, &reclen); r = sim_tape_spfiler(uptr, skip, &reclen);
uptr->POS++; uptr->POS++;
#else #else
@ -1551,6 +1571,7 @@ t_stat mt_attach(UNIT *uptr, CONST char *file)
DEVICE *dptr = get_dev(uptr); /* get device pointer */ DEVICE *dptr = get_dev(uptr); /* get device pointer */
t_stat r; t_stat r;
DIB *dibp = 0; DIB *dibp = 0;
struct attfileinfo *afi;
if (dptr->flags & DEV_DIS) { if (dptr->flags & DEV_DIS) {
fprintf(sim_deb, "ERROR===ERROR\nMT device %s disabled on system, aborting\r\n", fprintf(sim_deb, "ERROR===ERROR\nMT device %s disabled on system, aborting\r\n",
@ -1586,6 +1607,31 @@ t_stat mt_attach(UNIT *uptr, CONST char *file)
return SCPE_UNATT; /* error */ return SCPE_UNATT; /* error */
} }
set_devattn(chsa, SNS_DEVEND); /* ready int???? */ set_devattn(chsa, SNS_DEVEND); /* ready int???? */
/* store filename of attached device */
afi = att_files;
while (afi != (struct attfileinfo *) NULL && afi->chsa != chsa)
afi = afi->next;
/* only when valid entry found */
if (afi != (struct attfileinfo *) NULL) {
/* clear filename if previously stored filename differs */
if (strcmp(file, afi->att_file) != 0)
afi->att_file[0] = '\0';
} else {
/* create new entry */
afi = att_files;
att_files = malloc(sizeof(struct attfileinfo));
if (att_files != (struct attfileinfo *) NULL)
att_files->next = afi;
afi = att_files;
/* forget it if malloc failed */
if (afi != (struct attfileinfo *) NULL) {
afi->chsa = chsa;
afi->att_file = strdup(file);
}
}
return SCPE_OK; /* return good status */ return SCPE_OK; /* return good status */
} }

View file

@ -30,7 +30,7 @@
#if NUM_DEVS_SCFI > 0 #if NUM_DEVS_SCFI > 0
#define UNIT_SCFI UNIT_ATTABLE | UNIT_IDLE | UNIT_DISABLE #define UNIT_SCFI UNIT_ATTABLE|UNIT_DISABLE
extern uint32 SPAD[]; /* cpu SPAD memory */ extern uint32 SPAD[]; /* cpu SPAD memory */

View file

@ -30,7 +30,7 @@
#if NUM_DEVS_SCSI > 0 #if NUM_DEVS_SCSI > 0
#define UNIT_SCSI UNIT_ATTABLE | UNIT_IDLE | UNIT_DISABLE #define UNIT_SCSI UNIT_ATTABLE|UNIT_DISABLE
extern uint32 SPAD[]; /* cpu SPAD memory */ extern uint32 SPAD[]; /* cpu SPAD memory */
@ -200,7 +200,6 @@ bits 24-31 - FHD head count (number of heads on FHD or number head on FHD option
#define SNS_DIAGMOD 0x08000000 /* Diagnostic Mode ECC Code generation and checking */ #define SNS_DIAGMOD 0x08000000 /* Diagnostic Mode ECC Code generation and checking */
#define SNS_RSVTRK 0x04000000 /* Reserve Track mode: 1=OK to write, 0=read only */ #define SNS_RSVTRK 0x04000000 /* Reserve Track mode: 1=OK to write, 0=read only */
#define SNS_FHDOPT 0x02000000 /* FHD or FHD option = 1 */ #define SNS_FHDOPT 0x02000000 /* FHD or FHD option = 1 */
//#define SNS_RESERV 0x01000000 /* Reserved */
#define SNS_TCMD 0x01000000 /* Presessing CMD cmd chain */ #define SNS_TCMD 0x01000000 /* Presessing CMD cmd chain */
/* Sense byte 1 */ /* Sense byte 1 */
@ -307,7 +306,6 @@ t_stat scsi_help (FILE *st, DEVICE *dptr, UNIT *uptr, int32 flag, const char *c
const char *scsi_description (DEVICE *dptr); const char *scsi_description (DEVICE *dptr);
/* One buffer per unit */ /* One buffer per unit */
//#define BUFFSIZE (256)
#define BUFFSIZE (512) #define BUFFSIZE (512)
uint8 scsi_buf[NUM_DEVS_SCSI][NUM_UNITS_SCSI][BUFFSIZE]; uint8 scsi_buf[NUM_DEVS_SCSI][NUM_UNITS_SCSI][BUFFSIZE];
uint8 scsi_pcmd[NUM_DEVS_SCSI][NUM_UNITS_SCSI]; uint8 scsi_pcmd[NUM_DEVS_SCSI][NUM_UNITS_SCSI];
@ -371,7 +369,7 @@ UNIT sbb_unit[] = {
}; };
//DIB sdb_dib = {scsi_preio, scsi_startcmd, NULL, NULL, NULL, //DIB sdb_dib = {scsi_preio, scsi_startcmd, NULL, NULL, NULL,
//scsi_ini, sdb_unit, sdb_chp, NUM_UNITS_SCSI, 0x0f, 0x0c00, 0, 0, 0}; // scsi_ini, sdb_unit, sdb_chp, NUM_UNITS_SCSI, 0x0f, 0x0c00, 0, 0, 0};
DIB sbb_dib = { DIB sbb_dib = {
scsi_preio, /* t_stat (*pre_io)(UNIT *uptr, uint16 chan)*/ /* Pre Start I/O */ scsi_preio, /* t_stat (*pre_io)(UNIT *uptr, uint16 chan)*/ /* Pre Start I/O */
@ -468,7 +466,6 @@ t_stat scsi_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
/* leave the TCMD bit */ /* leave the TCMD bit */
uptr->SNS &= ~MASK24; /* clear all but old mode data */ uptr->SNS &= ~MASK24; /* clear all but old mode data */
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
//zz sim_activate(uptr, 100); /* start things off */
sim_activate(uptr, 30); /* start things off */ sim_activate(uptr, 30); /* start things off */
#else #else
sim_activate(uptr, 100); /* start things off */ sim_activate(uptr, 100); /* start things off */
@ -502,7 +499,6 @@ t_stat scsi_startcmd(UNIT *uptr, uint16 chan, uint8 cmd)
if (uptr->SNS & 0xff) /* any other cmd is error */ if (uptr->SNS & 0xff) /* any other cmd is error */
return SNS_CHNEND|SNS_DEVEND|SNS_UNITCHK; return SNS_CHNEND|SNS_DEVEND|SNS_UNITCHK;
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
//zz sim_activate(uptr, 100); /* start things off */
sim_activate(uptr, 20); /* start things off */ sim_activate(uptr, 20); /* start things off */
#else #else
sim_activate(uptr, 100); /* start things off */ sim_activate(uptr, 100); /* start things off */
@ -556,9 +552,6 @@ t_stat scsi_srv(UNIT *uptr)
"scsi_srv starting INCH cmd, chsa %04x MemBuf %06x cnt %04x\n", "scsi_srv starting INCH cmd, chsa %04x MemBuf %06x cnt %04x\n",
chsa, chp->ccw_addr, chp->ccw_count); chsa, chp->ccw_addr, chp->ccw_count);
#if 0
cpu_dev.dctrl |= DEBUG_INST; /* start instruction trace */
#endif
/* mema has IOCD word 1 contents. For the MFP (scsi processor) */ /* mema has IOCD word 1 contents. For the MFP (scsi processor) */
/* a pointer to the INCH buffer. The INCH buffer address must be */ /* a pointer to the INCH buffer. The INCH buffer address must be */
/* set for the parent channel as well as all other devices on the */ /* set for the parent channel as well as all other devices on the */
@ -569,7 +562,7 @@ t_stat scsi_srv(UNIT *uptr)
/* 1-256 wd buffer is provided for 128 status dbl words */ /* 1-256 wd buffer is provided for 128 status dbl words */
/* manual says 128 entries, but diag aborts if more than 1 */ /* manual says 128 entries, but diag aborts if more than 1 */
///?? i = set_inch(uptr, mema, 128); /* new address of 33 entries */ ///?? i = set_inch(uptr, mema, 128); /* new address of 33 entries */
i = set_inch(uptr, mema, 1); /* new address of 1 entrie */ i = set_inch(uptr, mema, 1); /* new address of 1 entry */
if ((i == SCPE_MEM) || (i == SCPE_ARG)) { /* any error */ if ((i == SCPE_MEM) || (i == SCPE_ARG)) { /* any error */
/* we have error, bail out */ /* we have error, bail out */
uptr->CMD &= LMASK; /* remove old status bits & cmd */ uptr->CMD &= LMASK; /* remove old status bits & cmd */
@ -1120,11 +1113,9 @@ doread:
"SCSI sector read complete, %x bytes to go from diskfile sector %06x\n", "SCSI sector read complete, %x bytes to go from diskfile sector %06x\n",
chp->ccw_count, uptr->CHS); chp->ccw_count, uptr->CHS);
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
//zz sim_activate(uptr, 10); /* start things off */
sim_activate(uptr, 15); /* start things off */ sim_activate(uptr, 15); /* start things off */
#else #else
sim_activate(uptr, 10); /* wait to read next sector */ sim_activate(uptr, 10); /* wait to read next sector */
//BAD4MPX sim_activate(uptr, 40); /* wait to read next sector */
#endif #endif
break; break;
} }
@ -1133,7 +1124,6 @@ doread:
case DSK_WD: /* Write Data */ case DSK_WD: /* Write Data */
if (uptr->SNS & SNS_TCMD) { if (uptr->SNS & SNS_TCMD) {
/* we need to process a write TCMD data */ /* we need to process a write TCMD data */
//? int cnt = scsi_buf[bufnum][unit][4]; /* byte count of status to read */
/* cnt has # bytes to read */ /* cnt has # bytes to read */
int cnt = chp->ccw_count; /* byte count of status to read */ int cnt = chp->ccw_count; /* byte count of status to read */
@ -1321,11 +1311,9 @@ dowrite:
break; break;
} }
#ifdef FAST_FOR_UTX #ifdef FAST_FOR_UTX
//zz sim_activate(uptr, 10); /* start things off */
sim_activate(uptr, 20); /* start things off */ sim_activate(uptr, 20); /* start things off */
#else #else
sim_activate(uptr, 10); /* keep writing */ sim_activate(uptr, 10); /* keep writing */
//BAD4MPX sim_activate(uptr, 40); /* keep writing */
#endif #endif
break; break;
} }
@ -1337,9 +1325,6 @@ dowrite:
/* wd 2 is sector size in bytes */ /* wd 2 is sector size in bytes */
/* cap has disk capacity */ /* cap has disk capacity */
read_cap: /* merge point from TCMD processing */ read_cap: /* merge point from TCMD processing */
#if 0
cpu_dev.dctrl |= DEBUG_INST; /* start instruction trace */
#endif
for (i=0; i<4; i++) { for (i=0; i<4; i++) {
/* I think they want cap-1, not cap?????????? */ /* I think they want cap-1, not cap?????????? */
/* verified that MPX wants cap-1, else J.VFMT aborts */ /* verified that MPX wants cap-1, else J.VFMT aborts */
@ -1388,9 +1373,6 @@ read_cap: /* merge point from TCMD process
"scsi_srv starting TCMD cmd, chsa %04x tcma %06x cnt %04x\n", "scsi_srv starting TCMD cmd, chsa %04x tcma %06x cnt %04x\n",
chsa, chp->ccw_addr, chp->ccw_count); chsa, chp->ccw_addr, chp->ccw_count);
#if 0
cpu_dev.dctrl |= DEBUG_INST; /* start instruction trace */
#endif
/* mema has IOCD word 1 contents. */ /* mema has IOCD word 1 contents. */
/* len has the byte count from IOCD wd2 */ /* len has the byte count from IOCD wd2 */
len = chp->ccw_count; /* TCMD command count */ len = chp->ccw_count; /* TCMD command count */
@ -1944,7 +1926,6 @@ t_stat scsi_haltio(UNIT *uptr) {
int cmd = uptr->CMD & DSK_CMDMSK; int cmd = uptr->CMD & DSK_CMDMSK;
CHANP *chp = find_chanp_ptr(chsa); /* find the chanp pointer */ CHANP *chp = find_chanp_ptr(chsa); /* find the chanp pointer */
// sim_debug(DEBUG_EXP, dptr,
sim_debug(DEBUG_DETAIL, dptr, sim_debug(DEBUG_DETAIL, dptr,
"scsi_haltio enter chsa %04x cmd = %02x\n", chsa, cmd); "scsi_haltio enter chsa %04x cmd = %02x\n", chsa, cmd);
@ -1969,7 +1950,6 @@ t_stat scsi_haltio(UNIT *uptr) {
"scsi_haltio HIO I/O stop chsa %04x cmd = %02x CHS %08x STAR %08x\n", "scsi_haltio HIO I/O stop chsa %04x cmd = %02x CHS %08x STAR %08x\n",
chsa, cmd, uptr->CHS, uptr->STAR); chsa, cmd, uptr->CHS, uptr->STAR);
chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* force end */ chan_end(chsa, SNS_CHNEND|SNS_DEVEND); /* force end */
// chan_end(chsa, SNS_CHNEND|SNS_DEVEND|SNS_UNITEXP); /* force end */
return SCPE_IOERR; return SCPE_IOERR;
} }

View file

@ -305,10 +305,10 @@ const char *sim_stop_messages[SCPE_BASE] = {
"IO device not ready", "IO device not ready",
"HALT instruction", "HALT instruction",
"Breakpoint", "Breakpoint",
"Unknown Opcode", "IPU Reset request",
"Invalid instruction", "Invalid instruction",
"Invalid I/O operation", "Invalid I/O operation",
"Nested indirects exceed limit", "Waiting for CPU to run",
"I/O Check opcode", "I/O Check opcode",
"Memory management trap during trap", "Memory management trap during trap",
}; };
@ -534,7 +534,6 @@ t_stat load_tap (FILE *fileref)
* *
*********************************************** ***********************************************
* *
* *END
* *END Defines the last record of the Initial Configuration Load file. * *END Defines the last record of the Initial Configuration Load file.
* *
*********************************************** ***********************************************
@ -640,21 +639,21 @@ t_stat load_icl(FILE *fileref)
/* read file input records until the end */ /* read file input records until the end */
while (fgets(&buf[0], 120, fileref) != 0) { while (fgets(&buf[0], 120, fileref) != 0) {
/* skip any white spaces */ /* skip any white spaces */
for(cp = &buf[0]; *cp == ' ' || *cp == '\t'; cp++); for (cp = &buf[0]; *cp == ' ' || *cp == '\t'; cp++);
if (*cp++ != '*') if (*cp++ != '*')
continue; /* if line does not start with *, ignore */ continue; /* if line does not start with *, ignore */
if(sim_strncasecmp(cp, "END", 3) == 0) { if (sim_strncasecmp(cp, "END", 3) == 0) {
return SCPE_OK; /* we are done */ return SCPE_OK; /* we are done */
} }
else else
if(sim_strncasecmp(cp, "DEV", 3) == 0) { if (sim_strncasecmp(cp, "DEV", 3) == 0) {
/* process device entry */ /* process device entry */
/* /*
|----+----+----+----+----+----+----+----| |----+----+----+----+----+----+----+----|
|Flgs|CLS |0|Int Lev|0|Phy Adr|Sub Addr | |Flgs|CLS |0|Int Lev|0|Phy Adr|Sub Addr |
|----+----+----+----+----+----+----+----| |----+----+----+----+----+----+----+----|
*/ */
for(cp += 3; *cp == ' ' || *cp == '\t'; cp++); /* skip white spaces */ for (cp += 3; *cp == ' ' || *cp == '\t'; cp++); /* skip white spaces */
if (get_2hex(cp, &dev) != SCPE_OK) /* get the device address */ if (get_2hex(cp, &dev) != SCPE_OK) /* get the device address */
return SCPE_ARG; /* unknown input, argument error */ return SCPE_ARG; /* unknown input, argument error */
if (dev > 0x7f) /* devices are 0-7f (0-127) */ if (dev > 0x7f) /* devices are 0-7f (0-127) */
@ -715,14 +714,14 @@ t_stat load_icl(FILE *fileref)
SPAD[sa] = intr; /* put the device interrupt entry into the spad */ SPAD[sa] = intr; /* put the device interrupt entry into the spad */
} }
else else
if(sim_strncasecmp(cp, "INT", 3) == 0) { if (sim_strncasecmp(cp, "INT", 3) == 0) {
/* process interrupt entry */ /* process interrupt entry */
/* /*
|----+----+----+----+----+----+----+----| |----+----+----+----+----+----+----+----|
| Flags |1RRR|SSSS| Int IVL | | Flags |1RRR|SSSS| Int IVL |
|----+----+----+----+----+----+----+----| |----+----+----+----+----+----+----+----|
*/ */
for(cp += 3; *cp == ' ' || *cp == '\t'; cp++); /* skip white spaces */ for (cp += 3; *cp == ' ' || *cp == '\t'; cp++); /* skip white spaces */
if (get_2hex(cp, &intr) != SCPE_OK) /* get the interrupt level value */ if (get_2hex(cp, &intr) != SCPE_OK) /* get the interrupt level value */
return SCPE_ARG; /* unknown input, argument error */ return SCPE_ARG; /* unknown input, argument error */
if (intr > 0x6f) /* ints are 0-6f (0-111) */ if (intr > 0x6f) /* ints are 0-6f (0-111) */
@ -1263,7 +1262,6 @@ t_stat fprint_sym (FILE *of, t_addr addr, t_value *val, UNIT *uptr, int32 sw)
int l = 4; /* default to full words */ int l = 4; /* default to full words */
int rdx = 16; /* default radex is hex */ int rdx = 16; /* default radex is hex */
uint32 num; uint32 num;
// uint32 tmp=*val; /* for debug */
if (sw & SIM_SW_STOP) { /* special processing for step */ if (sw & SIM_SW_STOP) { /* special processing for step */
if (PSD[0] & 0x02000000) { /* bit 6 is base mode */ if (PSD[0] & 0x02000000) { /* bit 6 is base mode */
@ -1306,7 +1304,7 @@ t_stat fprint_sym (FILE *of, t_addr addr, t_value *val, UNIT *uptr, int32 sw)
if (sw & SWMASK ('C')) { if (sw & SWMASK ('C')) {
fputc('\'', of); /* opening apostorphe */ fputc('\'', of); /* opening apostorphe */
for(i = 0; i < l; i++) { for (i = 0; i < l; i++) {
int ch = val[i] & 0xff; /* get the char */ int ch = val[i] & 0xff; /* get the char */
if (ch >= 0x20 && ch <= 0x7f) /* see if printable */ if (ch >= 0x20 && ch <= 0x7f) /* see if printable */
fprintf(of, "%c", ch); /* output the ascii char */ fprintf(of, "%c", ch); /* output the ascii char */
@ -1429,7 +1427,7 @@ t_stat parse_sym (CONST char *cptr, t_addr addr, UNIT *uptr, t_value *val, int32
/* process a character string */ /* process a character string */
if (sw & SWMASK ('C')) { if (sw & SWMASK ('C')) {
cptr = get_glyph_quoted(cptr, gbuf, 0); /* Get string */ cptr = get_glyph_quoted(cptr, gbuf, 0); /* Get string */
for(i = 0; gbuf[i] != 0; i++) { for (i = 0; gbuf[i] != 0; i++) {
val[i] = gbuf[i]; /* copy in the string */ val[i] = gbuf[i]; /* copy in the string */
} }
return -(i - 1); return -(i - 1);

View file

@ -27,6 +27,7 @@
# FreeBSD 12.1 # FreeBSD 12.1
# OpenBSD 6.7 # OpenBSD 6.7
# NetBSD 9.1 # NetBSD 9.1
# Linux ArmBian 5.19.17-meson64 (odroid n2+)
# CHANGE HISTORY # CHANGE HISTORY
# 2021/4/8 avoid setting PATH in scripts for root # 2021/4/8 avoid setting PATH in scripts for root
@ -34,11 +35,22 @@
# Corrected: bridge create and fwdelay done twice for NetBSD # Corrected: bridge create and fwdelay done twice for NetBSD
# FreeBSD: tapX opened by userland program not by ifconfig # FreeBSD: tapX opened by userland program not by ifconfig
# 2021/11/17 check for existance of br0 done too lousy. Done better. # 2021/11/17 check for existance of br0 done too lousy. Done better.
# 2021/12/29 Linux: when nmcli available: permanent setup using NetManager.
# 2023/4/19 Let ResetNet also remove tap2, tap3 as requested
# 2023/7/28 When nmcli is used check that br0 does not already exist
# Use $nmcli in SetupNet and in the generated scripts too
# Text changed to be more clear: we are building br0/tap0 with an external i/f
# When nmcli used: code to delete current ext i/f is same CMD construct as other
# When nmcli used and ResetNet created: let it remove orphaned connections too
# When nmcli used and ResetNet created: recreate original interface by type and name
# When nmcli used: correctly detect WiFi interfaces and ignore it for now
# 2023/7/30 User prompted for loading saved params from SnetSaved.interface file
# Entered params only saved when no SnetSaved.interface file exists.
# Removal of generated script /tmp/SNjob.pid after exec now optional.
# #
# uncomment next line if you need more than one tap = run multiple SIMHs... JOBFILE="/tmp/SNjob.$$"
#OPSMODE="expert" TMPFILE="/tmp/SNtmp.$$"
# ... by editting the saved params file followed by rerun of this script
OS=`uname -s` OS=`uname -s`
case $OS in case $OS in
@ -90,8 +102,15 @@ case $OS in
;; ;;
"Linux") "Linux")
NETMAN=`whereis -b nmcli | awk '{ if($2 != "") print 1; else print 0; }'`
# List of Utils # List of Utils
if test ${NETMAN} -eq 1
then
LOU="nmcli ip netstat"
else
LOU="ip brctl tunctl netstat" LOU="ip brctl tunctl netstat"
fi
# set $util to path of util for all in $LOU # set $util to path of util for all in $LOU
for U in $LOU for U in $LOU
@ -104,6 +123,8 @@ case $OS in
}'`" }'`"
done done
if test ${NETMAN} -eq 0
then
ERR=0 ERR=0
# check brctl to exist # check brctl to exist
if test $brctl = "void" if test $brctl = "void"
@ -124,30 +145,47 @@ case $OS in
then then
exit 1 exit 1
fi fi
fi
# make list of all interfaces ignoring lo # make list of all interfaces ignoring lo
if test ${NETMAN} -eq 0
then
AVL_IF=`$ip link show | AVL_IF=`$ip link show |
grep '^[0-9]' | grep '^[0-9]' |
awk -F: '{ print $2 }' | awk -F: '{ print $2 }' |
grep -v 'lo' | grep -v 'lo' |
sed '1,$s/^ //'` sed '1,$s/^ //'`
else
AVL_IF=`$nmcli -t con show | awk -F: '{print $4}'`
fi
# found br0 in active interfaces? # found br0 in active interfaces?
L=`echo $AVL_IF | tr ' ' '\012' | grep '^br0$' | wc -l` L=`echo $AVL_IF | tr ' ' '\012' | grep '^br0$' | wc -l`
if test $L -ne 0 if test $L -ne 0
then then
echo "$0: br0 already configured." echo "$0: br0 already configured."
if test ${NETMAN} -eq 0
then
echo "-- if you configured br0 statically don't use this script" echo "-- if you configured br0 statically don't use this script"
echo "-- otherwise if you do not want permanent settings" echo "-- otherwise if you do not want permanent settings"
echo "-- and want br0 configured differently reboot first" echo "-- and want br0 configured differently reboot first"
else
echo "-- most likely br0/tap0 are configured statically - no need to use this script"
echo "-- otherwise if you want br0 configured differently run ResetNet first"
fi
exit 1 exit 1
fi fi
# take tap0 out
AVL_IF=`echo $AVL_IF | sed 's/ tap0//'`
# take wlan out
## AVL_IF=`echo $AVL_IF | sed 's/ wlan0//'`
;; ;;
esac esac
# let user chose the interface he/she wants to use # let user chose the interface he/she wants to use
echo " Available networkinterfaces" echo " Available network interfaces to construct bridge br0"
N=0 N=0
for I in $AVL_IF for I in $AVL_IF
do do
@ -176,7 +214,7 @@ do
fi fi
# did we see wlan? alas... # did we see wlan? alas...
L=`echo $I | grep wlan | wc -l` L=`echo $I | grep 'wl[xa]' | wc -l`
if test $L -gt 0 if test $L -gt 0
then then
M="$M (wlan not supported)" M="$M (wlan not supported)"
@ -192,7 +230,13 @@ do
fi fi
done done
# take wlan out # take wlan out
AVL_IF=`echo $AVL_IF | sed 's/wlan.//'` AVL_IF=`echo $AVL_IF | sed 's/wl[xa][^ ]*//'`
if test $N -eq 0
then
echo "* No external interfaces suitable for bridge setup"
exit 1
fi
if test $N -gt 1 if test $N -gt 1
then then
@ -219,8 +263,21 @@ done
# see if there are saved params for this interface # see if there are saved params for this interface
if test -r SnetSaved.$ACT_IF if test -r SnetSaved.$ACT_IF
then then
echo 'There are saved params in 'SnetSaved.$ACT_IF
echo -n 'Do you want to load this file? (y/n)'
read ANSWER
case "x$ANSWER" in
"xy" | "xY" | "xyes" | "xYes" )
. ./SnetSaved.$ACT_IF . ./SnetSaved.$ACT_IF
echo "Saved params loaded from SnetSaved.$ACT_IF" echo "Saved params loaded from SnetSaved.$ACT_IF"
;;
"xn" | "xN" | "xno" | "xNo" )
echo "Params will be stored in SnetSaved.$ACT_IF"
;;
* )
echo 'Illegal answer: ' $ANSWER ' -- assume No'
;;
esac
fi fi
echo "" echo ""
@ -317,8 +374,18 @@ fi
if test "x${NrTaps}" = "x" if test "x${NrTaps}" = "x"
then then
NrTaps=1 NrTaps=1
echo -n "Number of taps to create.......... "
read NrTaps
case "x$NrTaps" in
"x1" | "x2" | "x3" | "x4" | "x5" | "x6" | "x7" | "x8" | "x9" )
;;
* )
echo "Assume 1 tap"
;;
esac
else
echo "Number of taps to create.......... " $NrTaps
fi fi
echo "Number of taps to create.......... " $NrTaps
# the user who needs access to the tap # the user who needs access to the tap
@ -340,14 +407,31 @@ then
fi fi
echo "User who runs SIMH on the taps.... " $SimhUser echo "User who runs SIMH on the taps.... " $SimhUser
# only save params when in expert OPSMODE if test "x${RemoveJF}" = "x"
if test "X$OPSMODE" = "Xexpert" then
RemoveJF="Yes"
echo -n "Remove /tmp-script after running.. "
read RemoveJF
case "x$RemoveJF" in
"xy" | "xY" | "xyes" | "xYes" )
RemoveJF="Yes"
;;
"xn" | "xN" | "xno" | "xNo" )
RemoveJF="No"
;;
* )
echo "Assume Yes"
;;
esac
else
echo "Remove /tmp-script after running.. " $RemoveJF
fi
if test ! -r SnetSaved.$ACT_IF
then then
if test ! -r SnetSaved.$ACT_IF
then
cat - > SnetSaved.$ACT_IF <<EOF cat - > SnetSaved.$ACT_IF <<EOF
# #
# expert users: edit your params and rerun the SetupNet script # edit your params and rerun the SetupNet script
# #
# ipnr including mask # ipnr including mask
@ -360,18 +444,17 @@ DEFRT=$DEFRT
NrTaps=$NrTaps NrTaps=$NrTaps
# username of the user running the SIMH emulators # username of the user running the SIMH emulators
SimhUser=$SimhUser SimhUser=$SimhUser
# remove generated script /tmp/SN... after running
RemoveJF=$RemoveJF
EOF EOF
echo '-- Params saved in SnetSaved.'$ACT_IF
L=`ls -l SnetSaved.$ACT_IF | grep root | wc -l`
if test $L -eq 1
then
chown $SimhUser SnetSaved.$ACT_IF
fi
fi
fi fi
JOBFILE="/tmp/SNjob.$$" L=`ls -l SnetSaved.$ACT_IF | grep root | wc -l`
TMPFILE="/tmp/SNtmp.$$" if test $L -eq 1
then
chown $SimhUser SnetSaved.$ACT_IF
fi
cat - > $JOBFILE <<\EOF cat - > $JOBFILE <<\EOF
#!/bin/sh #!/bin/sh
@ -393,18 +476,108 @@ EOF
case $OS in case $OS in
"Linux") "Linux")
if test ${NETMAN} -eq 1
then
IfList="tun0"
Nr=0
while test $Nr -lt ${NrTaps}
do
IfList="${IfList} tap${Nr}"
Nr=`expr ${Nr} + 1`
done
IfList="${IfList} br0 ${ACT_IF}"
for I in ${IfList}
do
C=`$nmcli -t con show |
awk -F\\: "{ if(\\$4 == \"\$I\") printf(\"$nmcli con del %s\", \\$2);}"`
if test ! "x$C" = "x"
then
echo 'CMD="'${C}'"' >> $JOBFILE
cat $TMPFILE >> $JOBFILE
fi
done
IfList=""
Nr=0
while test $Nr -lt ${NrTaps}
do
IfList="${IfList} tap${Nr}"
Nr=`expr ${Nr} + 1`
done
IfList="${IfList} br0 ${ACT_IF}"
cat - <<EOF > ResetNet
#!/bin/sh
nmcli=$nmcli
export nmcli
ACT_IF=$ACT_IF
export ACT_IF
EOF
cat - <<\EOF >> ResetNet
LINE=`$nmcli -t con show | grep $ACT_IF`
IFNAME=`echo $LINE | awk -F: '{ print $1 }'`
IFTYPE=`echo $LINE | awk -F: '{ print $3 }'`
EOF
cat - <<EOF >> ResetNet
for I in ${IfList}
EOF
cat - <<\EOF >> ResetNet
do
$nmcli -t con show |
awk -F\: "{ if(\$4 == \"$I\") printf(\"$nmcli con del '%s'\\n\", \$2);}" |
sh
done
# remove orphaned connections: those without associated device
$nmcli -t con show |
awk -F\: "{ if(\$4 == \"\") printf(\"$nmcli con del '%s'\\n\", \$2);}" |
sh
EOF
cat - <<\EOF >> ResetNet
# restore the base external network that we removed from the bridge br0
$nmcli con add type $IFTYPE ifname $ACT_IF con-name "$IFNAME"
EOF
chmod 755 ResetNet
fi
if test ${NETMAN} -eq 1
then
echo "CMD=\"$nmcli con add type bridge ifname br0 con-name br0\"" >> $JOBFILE
else
echo "CMD=\"$brctl addbr br0\"" >> $JOBFILE echo "CMD=\"$brctl addbr br0\"" >> $JOBFILE
fi
cat $TMPFILE >> $JOBFILE cat $TMPFILE >> $JOBFILE
if test ${NETMAN} -eq 1
then
echo "CMD=\"$nmcli con add type bridge-slave ifname ${ACT_IF} con-name ${ACT_IF} master br0\"">> $JOBFILE
cat $TMPFILE >> $JOBFILE
fi
SimhUID=`id -u ${SimhUser}`
N=0 N=0
while test $N -lt $NrTaps while test $N -lt $NrTaps
do do
if test ${NETMAN} -eq 1
then
echo "CMD=\"$nmcli con add type tun ifname tap${N} con-name tuntap${N} slave-type bridge master br0 mode tap owner ${SimhUID}\"" >> $JOBFILE
else
echo "CMD=\"$tunctl -t tap${N} -u ${SimhUser}\"" >> $JOBFILE echo "CMD=\"$tunctl -t tap${N} -u ${SimhUser}\"" >> $JOBFILE
fi
cat $TMPFILE >> $JOBFILE cat $TMPFILE >> $JOBFILE
N=`expr $N + 1` N=`expr $N + 1`
done done
if test ${NETMAN} -eq 0
then
echo "CMD=\"$brctl addif br0 ${ACT_IF}\"" >> $JOBFILE echo "CMD=\"$brctl addif br0 ${ACT_IF}\"" >> $JOBFILE
cat $TMPFILE >> $JOBFILE cat $TMPFILE >> $JOBFILE
@ -462,6 +635,8 @@ case $OS in
N=`expr $N + 1` N=`expr $N + 1`
done done
fi
BRIDGE="br0" BRIDGE="br0"
EXAMPLE="tap:tap0" EXAMPLE="tap:tap0"
@ -604,14 +779,22 @@ echo ""
echo 'Use unique IPnrs on your SIMH hosts within the' echo 'Use unique IPnrs on your SIMH hosts within the'
echo 'same network and set a default route if needed' echo 'same network and set a default route if needed'
rm -f $JOBFILE
EOF EOF
if test "X$OPSMODE" = "Xexpert" if test ${NETMAN} -eq 1
then
cat - >> $JOBFILE <<EOF
echo
echo ' ** IMPORTANT ** '
echo 'To RESET your network settings use: sudo sh ./ResetNet'
EOF
fi
if test ${RemoveJF} = "Yes"
then then
echo "" cat - >> $JOBFILE <<EOF
echo "-- To change the params above edit SnetSaved.$ACT_IF" rm -f $JOBFILE
echo "-- and rerun this script before executing the job" EOF
fi fi
L=`ls -l $JOBFILE | grep root | wc -l` L=`ls -l $JOBFILE | grep root | wc -l`