Serial Multiplexer cleanup after review by Dave Bryan
- Added functionality to return the lines with attached serial ports by calling tmxr_poll_conn one time after a serial port is attached. - Added the ability to close a serial port from the sim> prompt if a device implements a SET dev DISCONNECT=line command. A serial port is closed if the -C switch is specified on the DISCONNECT command line. - Cleaned up the multiplexer status display based on Dave's recommendations.
This commit is contained in:
parent
b466bdc9c6
commit
59afee3128
2 changed files with 123 additions and 90 deletions
54
sim_tmxr.c
54
sim_tmxr.c
|
@ -255,10 +255,18 @@
|
|||
A device emulation may choose to implement a command interface to
|
||||
disconnect specific individual lines. This would usually be done via
|
||||
a Unit Modifier table entry (MTAB) which dispatches the command
|
||||
"SET dev DISCONNECT[=line]" to tmxr_detach_line.
|
||||
"SET dev DISCONNECT[=line]" to tmxr_dscln. This will cause a telnet
|
||||
connection to be closed, but a serial port will normally have DTR
|
||||
dropped for 500ms and raised again (thus hanging up a modem on that
|
||||
serial port).
|
||||
|
||||
sim> set MUX disconnect=2
|
||||
|
||||
A line which is connected to a serial port can be manually closed by
|
||||
adding the -C switch to a disconnect command.
|
||||
|
||||
sim> set -C MUX disconnect=2
|
||||
|
||||
Full Modem Control serial port support.
|
||||
|
||||
This library supports devices which wish to emulate full modem
|
||||
|
@ -717,6 +725,7 @@ mp->last_poll_time = poll_time;
|
|||
|
||||
/* Check for a pending Telnet connection */
|
||||
|
||||
if (mp->master) {
|
||||
newsock = sim_accept_conn (mp->master, &address); /* poll connect */
|
||||
|
||||
if (newsock != INVALID_SOCKET) { /* got a live one? */
|
||||
|
@ -760,6 +769,7 @@ if (newsock != INVALID_SOCKET) { /* got a live one? */
|
|||
return i;
|
||||
}
|
||||
} /* end if newsock */
|
||||
}
|
||||
|
||||
/* Look for per line listeners or outbound connecting sockets */
|
||||
for (i = 0; i < mp->lines; i++) { /* check each line in sequence */
|
||||
|
@ -781,6 +791,8 @@ for (i = 0; i < mp->lines; i++) { /* check each line in se
|
|||
|
||||
/* Check for a pending Telnet connection */
|
||||
|
||||
if (lp->master) {
|
||||
|
||||
newsock = sim_accept_conn (lp->master, &address);/* poll connect */
|
||||
|
||||
if (newsock != INVALID_SOCKET) { /* got a live one? */
|
||||
|
@ -825,6 +837,14 @@ for (i = 0; i < mp->lines; i++) { /* check each line in se
|
|||
}
|
||||
}
|
||||
|
||||
/* Check for pending serial port connection notification */
|
||||
|
||||
if (lp->ser_connect_pending) {
|
||||
lp->ser_connect_pending = FALSE;
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
return -1; /* no new connections made */
|
||||
}
|
||||
|
||||
|
@ -832,8 +852,9 @@ return -1; /* no new connections ma
|
|||
|
||||
The telnet/tcp or serial session associated with multiplexer descriptor "mp" and
|
||||
line descriptor "lp" is disconnected. An associated tcp socket is
|
||||
deallocated; a serial port is not, although for non modem control serial lines
|
||||
DTR is dropped and raised again after 500ms to signal the attached serial device.
|
||||
closed; a serial port is closed if the closeserial parameter is true, otherwise
|
||||
for non modem control serial lines DTR is dropped and raised again after 500ms
|
||||
to signal the attached serial device.
|
||||
*/
|
||||
|
||||
static t_stat tmxr_reset_ln_ex (TMLN *lp, t_bool closeserial)
|
||||
|
@ -847,6 +868,9 @@ if (lp->serport) {
|
|||
if (closeserial) {
|
||||
sim_close_serial (lp->serport);
|
||||
lp->serport = 0;
|
||||
lp->ser_connect_pending = FALSE;
|
||||
free (lp->destination);
|
||||
lp->destination = NULL;
|
||||
free (lp->serconfig);
|
||||
lp->serconfig = NULL;
|
||||
lp->cnms = 0;
|
||||
|
@ -879,6 +903,11 @@ else {
|
|||
tmxr_init_line (lp); /* initialize line state */
|
||||
lp->conn = 0; /* remove socket or connection flag */
|
||||
}
|
||||
/* Revise the unit's connect string to reflect the current attachments */
|
||||
lp->mp->uptr->filename = _mux_attach_string (lp->mp->uptr->filename, lp->mp);
|
||||
/* No connections or listeners exist, then we're equivalent to being fully detached. We should reflect that */
|
||||
if (lp->mp->uptr->filename == NULL)
|
||||
tmxr_detach (lp->mp, lp->mp->uptr);
|
||||
return SCPE_OK;
|
||||
}
|
||||
|
||||
|
@ -1572,6 +1601,7 @@ while (*tptr) {
|
|||
if (serport != INVALID_HANDLE) {
|
||||
lp->mp = mp;
|
||||
lp->serport = serport;
|
||||
lp->ser_connect_pending = TRUE;
|
||||
lp->notelnet = TRUE;
|
||||
tmxr_init_line (lp); /* init the line state */
|
||||
if (!lp->mp->modem_control) /* raise DTR and RTS for non modem control lines */
|
||||
|
@ -1677,6 +1707,7 @@ while (*tptr) {
|
|||
serport = sim_open_serial (lp->destination, lp, &r);
|
||||
if (serport != INVALID_HANDLE) {
|
||||
lp->serport = serport;
|
||||
lp->ser_connect_pending = TRUE;
|
||||
lp->notelnet = TRUE;
|
||||
tmxr_init_line (lp); /* init the line state */
|
||||
if (!lp->mp->modem_control) /* raise DTR and RTS for non modem control lines */
|
||||
|
@ -2016,12 +2047,11 @@ return SCPE_OK;
|
|||
}
|
||||
|
||||
|
||||
/* Detach unit from master socket.
|
||||
/* Detach unit from master socket and close all active network connections
|
||||
and/or serial ports.
|
||||
|
||||
Note that we return SCPE_OK, regardless of whether a listening socket was
|
||||
attached. For single-line multiplexers that may be attached either to a
|
||||
listening socket or to a serial port, call "tmxr_detach_line" first. If that
|
||||
routine returns SCPE_UNATT, then call "tmxr_detach".
|
||||
attached.
|
||||
*/
|
||||
|
||||
t_stat tmxr_detach (TMXR *mp, UNIT *uptr)
|
||||
|
@ -2119,17 +2149,19 @@ static const char *enab = "on";
|
|||
static const char *dsab = "off";
|
||||
|
||||
if (ln >= 0)
|
||||
fprintf (st, "line %d:\b", ln);
|
||||
fprintf (st, "line %d:\n", ln);
|
||||
if ((!lp->conn) && (!lp->connecting) && (!lp->serport))
|
||||
fprintf (st, "line disconnected\n");
|
||||
if (lp->rxcnt)
|
||||
else {
|
||||
if ((lp->rxcnt) || (!lp->rcve))
|
||||
fprintf (st, " input (%s) queued/total = %d/%d\n",
|
||||
(lp->rcve? enab: dsab),
|
||||
tmxr_rqln (lp), lp->rxcnt);
|
||||
if (lp->txcnt || lp->txbpi)
|
||||
if (lp->txcnt || lp->txbpi || (!lp->xmte))
|
||||
fprintf (st, " output (%s) queued/total = %d/%d\n",
|
||||
(lp->xmte? enab: dsab),
|
||||
tmxr_tqln (lp), lp->txcnt);
|
||||
}
|
||||
if (lp->txbfd)
|
||||
fprintf (st, " output buffer size = %d\n", lp->txbsz);
|
||||
if (lp->txcnt || lp->txbpi)
|
||||
|
@ -2185,7 +2217,7 @@ if (lp == NULL) /* bad line numb
|
|||
if ((lp->conn) || (lp->serport)) { /* connection active? */
|
||||
if (!lp->notelnet)
|
||||
tmxr_linemsg (lp, "\r\nOperator disconnected line\r\n\n");/* report closure */
|
||||
tmxr_reset_ln (lp); /* drop the line */
|
||||
tmxr_reset_ln_ex (lp, (sim_switches & SWMASK ('C'))); /* drop the line */
|
||||
}
|
||||
|
||||
return SCPE_OK;
|
||||
|
|
|
@ -116,6 +116,7 @@ struct tmln {
|
|||
TMXR *mp; /* back pointer to mux */
|
||||
char *serconfig; /* line config */
|
||||
SERHANDLE serport; /* serial port handle */
|
||||
t_bool ser_connect_pending; /* serial connection notice pending */
|
||||
SOCKET connecting; /* Outgoing socket while connecting */
|
||||
char *destination; /* Outgoing destination address:port */
|
||||
UNIT *uptr; /* input polling unit (default to mp->uptr) */
|
||||
|
|
Loading…
Add table
Reference in a new issue