KA10: Fixed Chaosnet devices to work properly under ITS.

This commit is contained in:
Richard Cornwell 2023-01-18 18:01:32 -05:00
parent da6dcef801
commit cd40b302e6
2 changed files with 39 additions and 31 deletions

View file

@ -105,9 +105,10 @@ static char peer[256];
int address; int address;
static uint64 ch10_status; static uint64 ch10_status;
static int rx_count; static int rx_count;
static int rx_pos;
static int tx_count; static int tx_count;
static uint8 rx_buffer[512+100]; static uint8 rx_buffer[514+100];
static uint8 tx_buffer[512+100]; static uint8 tx_buffer[514+100];
TMLN ch10_lines[1] = { {0} }; TMLN ch10_lines[1] = { {0} };
TMXR ch10_tmxr = { 1, NULL, 0, ch10_lines}; TMXR ch10_tmxr = { 1, NULL, 0, ch10_lines};
@ -226,7 +227,7 @@ t_stat ch10_transmit ()
int i = CHUDP_HEADER + tx_count; int i = CHUDP_HEADER + tx_count;
uint16 chk; uint16 chk;
if (tx_count > (512 - CHUDP_HEADER)) { if (tx_count > (514 - CHUDP_HEADER)) {
sim_debug (DBG_PKT, &ch10_dev, "Pack size failed, %d bytes.\n", (int)tx_count); sim_debug (DBG_PKT, &ch10_dev, "Pack size failed, %d bytes.\n", (int)tx_count);
ch10_status |= PLE; ch10_status |= PLE;
return SCPE_INCOMP; return SCPE_INCOMP;
@ -243,7 +244,7 @@ t_stat ch10_transmit ()
len = CHUDP_HEADER + (size_t)tx_count; len = CHUDP_HEADER + (size_t)tx_count;
r = tmxr_put_packet_ln (&ch10_lines[0], (const uint8 *)&tx_buffer, len); r = tmxr_put_packet_ln (&ch10_lines[0], (const uint8 *)&tx_buffer, len);
if (r == SCPE_OK) { if (r == SCPE_OK) {
sim_debug (DBG_PKT, &ch10_dev, "Sent UDP packet, %d bytes.\n", (int)len); sim_debug (DBG_PKT, &ch10_dev, "Sent UDP packet, %d bytes. %04x checksum\n", (int)len, chk);
tmxr_poll_tx (&ch10_tmxr); tmxr_poll_tx (&ch10_tmxr);
} else { } else {
sim_debug (DBG_ERR, &ch10_dev, "Sending UDP failed: %d.\n", r); sim_debug (DBG_ERR, &ch10_dev, "Sending UDP failed: %d.\n", r);
@ -275,11 +276,12 @@ void ch10_receive (void)
return; return;
if ((RXD & ch10_status) == 0) { if ((RXD & ch10_status) == 0) {
count = (count + 1) & 0776; count = (count + 1) & 01776;
memcpy (rx_buffer + (512 - count), p, count);
rx_count = count; rx_count = count;
memcpy (rx_buffer, p, rx_count);
rx_pos = 0;
sim_debug (DBG_TRC, &ch10_dev, "Rx count, %d\n", rx_count); sim_debug (DBG_TRC, &ch10_dev, "Rx count, %d\n", rx_count);
ch10_validate (p + CHUDP_HEADER, count - CHUDP_HEADER); ch10_validate (rx_buffer + CHUDP_HEADER, rx_count - CHUDP_HEADER);
ch10_status |= RXD; ch10_status |= RXD;
ch10_lines[0].rcve = FALSE; ch10_lines[0].rcve = FALSE;
sim_debug (DBG_TRC, &ch10_dev, "Rx off\n"); sim_debug (DBG_TRC, &ch10_dev, "Rx off\n");
@ -296,6 +298,7 @@ void ch10_clear (void)
ch10_status = TXD; ch10_status = TXD;
rx_count = 0; rx_count = 0;
tx_count = 0; tx_count = 0;
rx_pos = 0;
tx_buffer[0] = 1; /* CHUDP header */ tx_buffer[0] = 1; /* CHUDP header */
tx_buffer[1] = 1; tx_buffer[1] = 1;
@ -349,7 +352,7 @@ t_stat ch10_devio(uint32 dev, uint64 *data)
break; break;
case DATAO: case DATAO:
ch10_status &= ~TXD; ch10_status &= ~TXD;
if (tx_count < 512) { if (tx_count < 514) {
int i = CHUDP_HEADER + tx_count; int i = CHUDP_HEADER + tx_count;
if (ch10_status & SWAP) { if (ch10_status & SWAP) {
tx_buffer[i] = (*data >> 20) & 0xff; tx_buffer[i] = (*data >> 20) & 0xff;
@ -382,22 +385,23 @@ t_stat ch10_devio(uint32 dev, uint64 *data)
*data = 0; *data = 0;
sim_debug (DBG_ERR, &ch10_dev, "Read empty buffer\n"); sim_debug (DBG_ERR, &ch10_dev, "Read empty buffer\n");
} else { } else {
int i = 512-rx_count;
ch10_status &= ~RXD; ch10_status &= ~RXD;
if (ch10_status & SWAP) { if (ch10_status & SWAP) {
*data = ((uint64)(rx_buffer[i]) & 0xff) << 20; *data = ((uint64)(rx_buffer[rx_pos]) & 0xff) << 20;
*data |= ((uint64)(rx_buffer[i+1]) & 0xff) << 28; *data |= ((uint64)(rx_buffer[rx_pos+1]) & 0xff) << 28;
*data |= ((uint64)(rx_buffer[i+2]) & 0xff) << 4; *data |= ((uint64)(rx_buffer[rx_pos+2]) & 0xff) << 4;
*data |= ((uint64)(rx_buffer[i+3]) & 0xff) << 12; *data |= ((uint64)(rx_buffer[rx_pos+3]) & 0xff) << 12;
} else { } else {
*data = ((uint64)(rx_buffer[i]) & 0xff) << 28; *data = ((uint64)(rx_buffer[rx_pos]) & 0xff) << 28;
*data |= ((uint64)(rx_buffer[i+1]) & 0xff) << 20; *data |= ((uint64)(rx_buffer[rx_pos+1]) & 0xff) << 20;
*data |= ((uint64)(rx_buffer[i+2]) & 0xff) << 12; *data |= ((uint64)(rx_buffer[rx_pos+2]) & 0xff) << 12;
*data |= ((uint64)(rx_buffer[i+3]) & 0xff) << 4; *data |= ((uint64)(rx_buffer[rx_pos+3]) & 0xff) << 4;
} }
rx_count-=4; rx_count-=4;
sim_debug (DBG_DAT, &ch10_dev, "Read buffer word %d:%02x %02x %02x %02x %012llo %012llo\n", sim_debug (DBG_DAT, &ch10_dev, "Read buffer word %d:%02x %02x %02x %02x %012llo %012llo\n",
rx_count, rx_buffer[i], rx_buffer[i+1], rx_buffer[i+2], rx_buffer[i+3], *data, ch10_status); rx_count, rx_buffer[rx_pos], rx_buffer[rx_pos+1], rx_buffer[rx_pos+2], rx_buffer[rx_pos+3],
*data, ch10_status);
rx_pos+=4;
} }
} }

View file

@ -97,9 +97,10 @@ static char peer[256];
static int address; static int address;
static uint16 ch11_csr; static uint16 ch11_csr;
static int rx_count; static int rx_count;
static int rx_pos;
static int tx_count; static int tx_count;
static uint8 rx_buffer[512+100]; static uint8 rx_buffer[514+100];
static uint8 tx_buffer[512+100]; static uint8 tx_buffer[514+100];
TMLN ch11_lines[1] = { {0} }; TMLN ch11_lines[1] = { {0} };
TMXR ch11_tmxr = { 1, NULL, 0, ch11_lines}; TMXR ch11_tmxr = { 1, NULL, 0, ch11_lines};
@ -111,6 +112,7 @@ UNIT ch11_unit[] = {
REG ch11_reg[] = { REG ch11_reg[] = {
{ ORDATA(CSR, ch11_csr, 16)}, { ORDATA(CSR, ch11_csr, 16)},
{ GRDATAD(RXCNT, rx_count, 16, 16, 0, "Receive word count"), REG_FIT|REG_RO}, { GRDATAD(RXCNT, rx_count, 16, 16, 0, "Receive word count"), REG_FIT|REG_RO},
{ GRDATAD(RXPOS, rx_pos, 16, 16, 0, "Receive Position"), REG_FIT|REG_RO},
{ GRDATAD(TXCNT, tx_count, 16, 16, 0, "Transmit word count"), REG_FIT|REG_RO}, { GRDATAD(TXCNT, tx_count, 16, 16, 0, "Transmit word count"), REG_FIT|REG_RO},
{ BRDATAD(RXBUF, rx_buffer, 16, 8, sizeof rx_buffer, "Receive packet buffer"), REG_FIT}, { BRDATAD(RXBUF, rx_buffer, 16, 8, sizeof rx_buffer, "Receive packet buffer"), REG_FIT},
{ BRDATAD(TXBUF, tx_buffer, 16, 8, sizeof tx_buffer, "Transmit packet buffer"), REG_FIT}, { BRDATAD(TXBUF, tx_buffer, 16, 8, sizeof tx_buffer, "Transmit packet buffer"), REG_FIT},
@ -179,6 +181,7 @@ ch11_write(DEVICE *dptr, t_addr addr, uint16 data, int32 access)
sim_debug (DBG_REG, &ch11_dev, "Clear RX\n"); sim_debug (DBG_REG, &ch11_dev, "Clear RX\n");
ch11_csr &= ~CSR_RDN; ch11_csr &= ~CSR_RDN;
rx_count = 0; rx_count = 0;
rx_pos = 0;
ch11_lines[0].rcve = TRUE; ch11_lines[0].rcve = TRUE;
uba_clr_irq(dibp, dibp->uba_vect); uba_clr_irq(dibp, dibp->uba_vect);
} }
@ -219,7 +222,6 @@ int
ch11_read(DEVICE *dptr, t_addr addr, uint16 *data, int32 access) ch11_read(DEVICE *dptr, t_addr addr, uint16 *data, int32 access)
{ {
struct pdp_dib *dibp = (DIB *)dptr->ctxt; struct pdp_dib *dibp = (DIB *)dptr->ctxt;
int i;
addr &= dibp->uba_mask; addr &= dibp->uba_mask;
*data = 0; *data = 0;
@ -237,19 +239,19 @@ ch11_read(DEVICE *dptr, t_addr addr, uint16 *data, int32 access)
*data = 0; *data = 0;
sim_debug (DBG_ERR, &ch11_dev, "Read empty buffer\n"); sim_debug (DBG_ERR, &ch11_dev, "Read empty buffer\n");
} else { } else {
i = 512-rx_count;
ch11_csr &= ~CSR_RDN; ch11_csr &= ~CSR_RDN;
uba_clr_irq(dibp, dibp->uba_vect); uba_clr_irq(dibp, dibp->uba_vect);
*data = ((uint64)(rx_buffer[i]) & 0xff) << 8; *data = ((uint64)(rx_buffer[rx_pos]) & 0xff) << 8;
*data |= ((uint64)(rx_buffer[i+1]) & 0xff); *data |= ((uint64)(rx_buffer[rx_pos+1]) & 0xff);
rx_count-=2;
sim_debug (DBG_DAT, &ch11_dev, "Read buffer word %d:%02x %02x %06o %06o\n", sim_debug (DBG_DAT, &ch11_dev, "Read buffer word %d:%02x %02x %06o %06o\n",
rx_count, rx_buffer[i], rx_buffer[i+1], *data, ch11_csr); rx_count, rx_buffer[rx_pos], rx_buffer[rx_pos+1], *data, ch11_csr);
rx_count-=2;
rx_pos+=2;
} }
break; break;
case 006: /* Bit count */ case 006: /* Bit count */
*data = ((512 - rx_count) - 1) & 07777; *data = ((rx_count * 8) - 1) & 07777;
break; break;
case 012: /* Start transmission */ case 012: /* Start transmission */
sim_debug (DBG_REG, &ch11_dev, "XMIT TX\n"); sim_debug (DBG_REG, &ch11_dev, "XMIT TX\n");
@ -340,7 +342,7 @@ ch11_transmit (struct pdp_dib *dibp)
len = CHUDP_HEADER + (size_t)tx_count; len = CHUDP_HEADER + (size_t)tx_count;
r = tmxr_put_packet_ln (&ch11_lines[0], (const uint8 *)&tx_buffer, len); r = tmxr_put_packet_ln (&ch11_lines[0], (const uint8 *)&tx_buffer, len);
if (r == SCPE_OK) { if (r == SCPE_OK) {
sim_debug (DBG_PKT, &ch11_dev, "Sent UDP packet, %d bytes.\n", (int)len); sim_debug (DBG_PKT, &ch11_dev, "Sent UDP packet, %d bytes. %04x checksum.\n", (int)len, chk);
tmxr_poll_tx (&ch11_tmxr); tmxr_poll_tx (&ch11_tmxr);
} else { } else {
sim_debug (DBG_ERR, &ch11_dev, "Sending UDP failed: %d.\n", r); sim_debug (DBG_ERR, &ch11_dev, "Sending UDP failed: %d.\n", r);
@ -372,9 +374,10 @@ ch11_receive (struct pdp_dib *dibp)
return; return;
if ((CSR_RDN & ch11_csr) == 0) { if ((CSR_RDN & ch11_csr) == 0) {
count = (count + 1) & 0776; count = (count + 1) & 01776;
memcpy (rx_buffer + (512 - count), p, count); memcpy (rx_buffer, p + CHUDP_HEADER, count);
rx_count = count; rx_count = count - CHUDP_HEADER;
rx_pos = 0;
sim_debug (DBG_TRC, &ch11_dev, "Rx count, %d\n", rx_count); sim_debug (DBG_TRC, &ch11_dev, "Rx count, %d\n", rx_count);
ch11_validate (p + CHUDP_HEADER, count - CHUDP_HEADER); ch11_validate (p + CHUDP_HEADER, count - CHUDP_HEADER);
ch11_csr |= CSR_RDN; ch11_csr |= CSR_RDN;
@ -397,6 +400,7 @@ ch11_clear (struct pdp_dib *dibp)
ch11_csr = CSR_TDN; ch11_csr = CSR_TDN;
rx_count = 0; rx_count = 0;
tx_count = 0; tx_count = 0;
rx_pos = 0;
tx_buffer[0] = 1; /* CHUDP header */ tx_buffer[0] = 1; /* CHUDP header */
tx_buffer[1] = 1; tx_buffer[1] = 1;