Introduce ttygone() which indicates that the hardware is detached.
Move dtrwait logic to the generic TTY level.
This commit is contained in:
parent
cd2890d712
commit
911dbd84c7
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=131981
@ -160,14 +160,11 @@ typedef struct _drv_t {
|
||||
cx_dma_mem_t dmamem;
|
||||
struct tty *tty;
|
||||
struct callout_handle dcd_timeout_handle;
|
||||
unsigned dtrwait;
|
||||
unsigned dtroff;
|
||||
unsigned callout;
|
||||
unsigned lock;
|
||||
int open_dev;
|
||||
int cd;
|
||||
int running;
|
||||
struct callout_handle dtr_timeout_handle;
|
||||
#ifdef NETGRAPH
|
||||
char nodename [NG_NODELEN+1];
|
||||
hook_p hook;
|
||||
@ -217,7 +214,6 @@ extern const u_char csigma_fw_data[];
|
||||
static void cx_oproc (struct tty *tp);
|
||||
static int cx_param (struct tty *tp, struct termios *t);
|
||||
static void cx_stop (struct tty *tp, int flag);
|
||||
static void cx_dtrwakeup (void *a);
|
||||
static void cx_receive (cx_chan_t *c, char *data, int len);
|
||||
static void cx_transmit (cx_chan_t *c, void *attachment, int len);
|
||||
static void cx_error (cx_chan_t *c, int data);
|
||||
@ -817,7 +813,6 @@ static int cx_attach (device_t dev)
|
||||
sprintf (d->name, "cx%d.%d", b->num, c->num);
|
||||
d->board = b;
|
||||
d->chan = c;
|
||||
d->dtrwait = 3 * hz; /* Default DTR off timeout is 3 seconds. */
|
||||
d->open_dev = 0;
|
||||
c->sys = d;
|
||||
|
||||
@ -940,8 +935,6 @@ static int cx_detach (device_t dev)
|
||||
if (!d || d->chan->type == T_NONE)
|
||||
continue;
|
||||
|
||||
if (d->dtr_timeout_handle.callout)
|
||||
untimeout (cx_dtrwakeup, d, d->dtr_timeout_handle);
|
||||
if (d->dcd_timeout_handle.callout)
|
||||
untimeout (cx_carrier, c, d->dcd_timeout_handle);
|
||||
}
|
||||
@ -1518,12 +1511,9 @@ static int cx_open (struct cdev *dev, int flag, int mode, struct thread *td)
|
||||
dev->si_tty = d->tty;
|
||||
d->tty->t_dev = dev;
|
||||
again:
|
||||
if (d->dtroff) {
|
||||
error = tsleep (&d->dtrwait, TTIPRI | PCATCH, "cxdtr", 0);
|
||||
if (error)
|
||||
return error;
|
||||
goto again;
|
||||
}
|
||||
error = ttydtrwaitsleep(d->tty);
|
||||
if (error)
|
||||
return error;
|
||||
|
||||
if ((d->tty->t_state & TS_ISOPEN) && (d->tty->t_state & TS_XCLUDE) &&
|
||||
#if __FreeBSD_version >= 500000
|
||||
@ -1608,11 +1598,7 @@ failed: if (! (d->tty->t_state & TS_ISOPEN)) {
|
||||
splhigh ();
|
||||
cx_set_dtr (d->chan, 0);
|
||||
cx_set_rts (d->chan, 0);
|
||||
if (d->dtrwait) {
|
||||
d->dtr_timeout_handle =
|
||||
timeout (cx_dtrwakeup, d, d->dtrwait);
|
||||
d->dtroff = 1;
|
||||
}
|
||||
ttydtrwaitstart(d->tty);
|
||||
spl0 ();
|
||||
}
|
||||
return error;
|
||||
@ -1652,11 +1638,7 @@ static int cx_close (struct cdev *dev, int flag, int mode, struct thread *td)
|
||||
if ((d->tty->t_cflag & HUPCL) || ! (d->tty->t_state & TS_ISOPEN)) {
|
||||
cx_set_dtr (d->chan, 0);
|
||||
cx_set_rts (d->chan, 0);
|
||||
if (d->dtrwait) {
|
||||
d->dtr_timeout_handle =
|
||||
timeout (cx_dtrwakeup, d, d->dtrwait);
|
||||
d->dtroff = 1;
|
||||
}
|
||||
ttydtrwaitstart(d->tty);
|
||||
}
|
||||
ttyclose (d->tty);
|
||||
splx (s);
|
||||
@ -2139,48 +2121,11 @@ static int cx_ioctl (struct cdev *dev, u_long cmd, caddr_t data, int flag, struc
|
||||
*(int*)data = cx_modem_status (d);
|
||||
return 0;
|
||||
|
||||
#ifdef TIOCMSDTRWAIT
|
||||
case TIOCMSDTRWAIT:
|
||||
CX_DEBUG2 (d, ("ioctl: tiocmsdtrwait\n"));
|
||||
/* Only for superuser! */
|
||||
#if __FreeBSD_version < 500000
|
||||
error = suser (p);
|
||||
#else /* __FreeBSD_version >= 500000 */
|
||||
error = suser (td);
|
||||
#endif /* __FreeBSD_version >= 500000 */
|
||||
if (error)
|
||||
return error;
|
||||
s = splhigh ();
|
||||
d->dtrwait = *(int*)data * hz / 100;
|
||||
splx (s);
|
||||
return 0;
|
||||
#endif
|
||||
|
||||
#ifdef TIOCMGDTRWAIT
|
||||
case TIOCMGDTRWAIT:
|
||||
CX_DEBUG2 (d, ("ioctl: tiocmgdtrwait\n"));
|
||||
s = splhigh ();
|
||||
*(int*)data = d->dtrwait * 100 / hz;
|
||||
splx (s);
|
||||
return 0;
|
||||
#endif
|
||||
}
|
||||
CX_DEBUG2 (d, ("ioctl: 0x%lx\n", cmd));
|
||||
return ENOTTY;
|
||||
}
|
||||
|
||||
/*
|
||||
* Wake up opens() waiting for DTR ready.
|
||||
*/
|
||||
static void cx_dtrwakeup (void *arg)
|
||||
{
|
||||
drv_t *d = arg;
|
||||
|
||||
d->dtroff = 0;
|
||||
wakeup (&d->dtrwait);
|
||||
}
|
||||
|
||||
|
||||
#if __FreeBSD_version < 502113
|
||||
static void
|
||||
ttyldoptim(tp)
|
||||
|
@ -117,7 +117,6 @@ __FBSDID("$FreeBSD$");
|
||||
#define p_com_addr p_cy_addr
|
||||
#define sioclose cyclose
|
||||
#define siodriver cydriver
|
||||
#define siodtrwakeup cydtrwakeup
|
||||
#define sioinput cyinput
|
||||
#define siointr1 cyintr
|
||||
#define sioioctl cyioctl
|
||||
@ -191,7 +190,6 @@ __FBSDID("$FreeBSD$");
|
||||
#define CS_ODEVREADY 0x20 /* external device h/w ready (CTS) */
|
||||
#define CS_CHECKMSR 1 /* check of MSR scheduled */
|
||||
#define CS_CTS_OFLOW 2 /* use CTS output flow control */
|
||||
#define CS_DTR_OFF 0x10 /* DTR held off */
|
||||
#define CS_ODONE 4 /* output completed */
|
||||
#define CS_RTS_IFLOW 8 /* use RTS input flow control */
|
||||
#define CSE_ODONE 1 /* output transmitted */
|
||||
@ -256,7 +254,6 @@ struct com_s {
|
||||
bool_t poll_output; /* nonzero if polling for output is required */
|
||||
#endif
|
||||
int unit; /* unit number */
|
||||
int dtr_wait; /* time to hold DTR down on close (* 1/hz) */
|
||||
#if 0
|
||||
u_int tx_fifo_size;
|
||||
#endif
|
||||
@ -332,7 +329,6 @@ static void cd1400_channel_cmd_wait(struct com_s *com);
|
||||
static void cd_etc(struct com_s *com, int etc);
|
||||
static int cd_getreg(struct com_s *com, int reg);
|
||||
static void cd_setreg(struct com_s *com, int reg, int val);
|
||||
static timeout_t siodtrwakeup;
|
||||
static void comhardclose(struct com_s *com);
|
||||
static void sioinput(struct com_s *com);
|
||||
static int commctl(struct com_s *com, int bits, int how);
|
||||
@ -515,7 +511,6 @@ cyattach_common(cy_iobase, cy_align)
|
||||
com->mcr_rts = MCR_RTS;
|
||||
com->mcr_rts_reg = CD1400_MSVR1;
|
||||
}
|
||||
com->dtr_wait = 3 * hz;
|
||||
com->obufs[0].l_head = com->obuf1;
|
||||
com->obufs[1].l_head = com->obuf2;
|
||||
|
||||
@ -614,11 +609,9 @@ sioopen(dev, flag, mode, td)
|
||||
* up any changes of the device state.
|
||||
*/
|
||||
open_top:
|
||||
while (com->state & CS_DTR_OFF) {
|
||||
error = tsleep(&com->dtr_wait, TTIPRI | PCATCH, "cydtr", 0);
|
||||
if (error != 0)
|
||||
goto out;
|
||||
}
|
||||
error = ttydtrwaitsleep(tp);
|
||||
if (error != 0)
|
||||
goto out;
|
||||
if (tp->t_state & TS_ISOPEN) {
|
||||
/*
|
||||
* The device is open, so everything has been initialized.
|
||||
@ -864,10 +857,7 @@ comhardclose(com)
|
||||
| CD1400_CCR_RCVDIS;
|
||||
cd1400_channel_cmd(com, com->channel_control);
|
||||
|
||||
if (com->dtr_wait != 0 && !(com->state & CS_DTR_OFF)) {
|
||||
timeout(siodtrwakeup, com, com->dtr_wait);
|
||||
com->state |= CS_DTR_OFF;
|
||||
}
|
||||
ttydtrwaitstart(tp);
|
||||
}
|
||||
}
|
||||
#if 0
|
||||
@ -920,17 +910,6 @@ siowrite(dev, uio, flag)
|
||||
#endif
|
||||
}
|
||||
|
||||
static void
|
||||
siodtrwakeup(chan)
|
||||
void *chan;
|
||||
{
|
||||
struct com_s *com;
|
||||
|
||||
com = (struct com_s *)chan;
|
||||
com->state &= ~CS_DTR_OFF;
|
||||
wakeup(&com->dtr_wait);
|
||||
}
|
||||
|
||||
/*
|
||||
* This function:
|
||||
* a) needs to be called with COM_LOCK() held, and
|
||||
@ -1649,18 +1628,6 @@ sioioctl(dev, cmd, data, flag, td)
|
||||
case TIOCMGET:
|
||||
*(int *)data = commctl(com, 0, DMGET);
|
||||
break;
|
||||
case TIOCMSDTRWAIT:
|
||||
/* must be root since the wait applies to following logins */
|
||||
error = suser(td);
|
||||
if (error != 0) {
|
||||
splx(s);
|
||||
return (error);
|
||||
}
|
||||
com->dtr_wait = *(int *)data * hz / 100;
|
||||
break;
|
||||
case TIOCMGDTRWAIT:
|
||||
*(int *)data = com->dtr_wait * 100 / hz;
|
||||
break;
|
||||
case TIOCTIMESTAMP:
|
||||
com->do_timestamp = TRUE;
|
||||
*(struct timeval *)data = com->timestamp;
|
||||
|
@ -603,7 +603,6 @@ digi_init(struct digi_softc *sc)
|
||||
fepcmd_w(port, SRXHWATER, (3 * port->rxbufsize) >> 2, 10);
|
||||
|
||||
bc->edelay = 100;
|
||||
port->dtr_wait = 3 * hz;
|
||||
|
||||
/*
|
||||
* We don't use all the flags from <sys/ttydefaults.h> since
|
||||
@ -738,7 +737,7 @@ digiopen(struct cdev *dev, int flag, int mode, struct thread *td)
|
||||
open_top:
|
||||
while (port->status & DIGI_DTR_OFF) {
|
||||
port->wopeners++;
|
||||
error = tsleep(&port->dtr_wait, TTIPRI | PCATCH, "digidtr", 0);
|
||||
error = tsleep(&tp->t_dtr_wait, TTIPRI | PCATCH, "digidtr", 0);
|
||||
port->wopeners--;
|
||||
if (error)
|
||||
goto out;
|
||||
@ -906,7 +905,7 @@ digidtrwakeup(void *chan)
|
||||
struct digi_p *port = chan;
|
||||
|
||||
port->status &= ~DIGI_DTR_OFF;
|
||||
wakeup(&port->dtr_wait);
|
||||
wakeup(&port->tp->t_dtr_wait);
|
||||
port->wopeners--;
|
||||
}
|
||||
|
||||
@ -929,10 +928,10 @@ digihardclose(struct digi_p *port)
|
||||
!(port->it_in.c_cflag & CLOCAL)) ||
|
||||
!(port->tp->t_state & TS_ISOPEN)) {
|
||||
digimodem(port->tp, 0, SER_DTR | SER_RTS);
|
||||
if (port->dtr_wait != 0) {
|
||||
if (port->tp->t_dtr_wait != 0) {
|
||||
/* Schedule a wakeup of any callin devices */
|
||||
port->wopeners++;
|
||||
timeout(&digidtrwakeup, port, port->dtr_wait);
|
||||
timeout(&digidtrwakeup, port, port->tp->t_dtr_wait);
|
||||
port->status |= DIGI_DTR_OFF;
|
||||
}
|
||||
}
|
||||
@ -1282,18 +1281,6 @@ digiioctl(struct cdev *dev, u_long cmd, caddr_t data, int flag, struct thread *t
|
||||
case DIGIIO_RING:
|
||||
port->send_ring = *(u_char *)data;
|
||||
break;
|
||||
case TIOCMSDTRWAIT:
|
||||
error = suser(td);
|
||||
if (error != 0) {
|
||||
splx(s);
|
||||
return (error);
|
||||
}
|
||||
port->dtr_wait = *(int *)data *hz / 100;
|
||||
|
||||
break;
|
||||
case TIOCMGDTRWAIT:
|
||||
*(int *)data = port->dtr_wait * 100 / hz;
|
||||
break;
|
||||
#ifdef DIGI_INTERRUPT
|
||||
case TIOCTIMESTAMP:
|
||||
*(struct timeval *)data = sc->intr_timestamp;
|
||||
|
@ -86,7 +86,6 @@ struct digi_p {
|
||||
u_char modem; /* Force values */
|
||||
|
||||
int active_out; /* nonzero if the callout device is open */
|
||||
int dtr_wait; /* time to hold DTR down on close (* 1/hz) */
|
||||
u_int wopeners; /* # processes waiting for DCD in open() */
|
||||
|
||||
/*
|
||||
|
@ -93,7 +93,6 @@ struct rc_chans {
|
||||
u_char rc_msvr; /* modem sig. status */
|
||||
u_char rc_cor2; /* options reg */
|
||||
u_char rc_pendcmd; /* special cmd pending */
|
||||
u_int rc_dtrwait; /* dtr timeout */
|
||||
u_int rc_dcdwaits; /* how many waits DCD in open */
|
||||
struct tty rc_tp; /* tty struct */
|
||||
u_char *rc_iptr; /* Chars input buffer */
|
||||
@ -140,18 +139,15 @@ static void rc_reinit(struct rc_softc *);
|
||||
#ifdef RCDEBUG
|
||||
static void printrcflags();
|
||||
#endif
|
||||
static void rc_dtrwakeup(void *);
|
||||
static void rc_wait0(struct rc_softc *sc, int chan, int line);
|
||||
|
||||
static d_open_t rcopen;
|
||||
static d_close_t rcclose;
|
||||
static d_ioctl_t rcioctl;
|
||||
|
||||
static struct cdevsw rc_cdevsw = {
|
||||
.d_version = D_VERSION,
|
||||
.d_open = rcopen,
|
||||
.d_close = rcclose,
|
||||
.d_ioctl = rcioctl,
|
||||
.d_name = "rc",
|
||||
.d_flags = D_TTY | D_NEEDGIANT,
|
||||
};
|
||||
@ -316,7 +312,6 @@ rc_attach(device_t dev)
|
||||
rc->rc_bufend = &rc->rc_ibuf[RC_IBUFSIZE];
|
||||
rc->rc_hiwat = &rc->rc_ibuf[RC_IHIGHWATER];
|
||||
rc->rc_optr = rc->rc_obufend = rc->rc_obuf;
|
||||
rc->rc_dtrwait = 3 * hz;
|
||||
callout_init(&rc->rc_dtrcallout, 0);
|
||||
tp = &rc->rc_tp;
|
||||
ttychars(tp);
|
||||
@ -358,7 +353,7 @@ rc_detach(device_t dev)
|
||||
{
|
||||
struct rc_softc *sc;
|
||||
struct rc_chans *rc;
|
||||
int error, i, s;
|
||||
int error, i;
|
||||
|
||||
sc = device_get_softc(dev);
|
||||
if (sc->sc_opencount > 0)
|
||||
@ -367,18 +362,11 @@ rc_detach(device_t dev)
|
||||
|
||||
rc = sc->sc_channels;
|
||||
for (i = 0; i < CD180_NCHAN; i++, rc++) {
|
||||
ttygone(&rc->rc_tp);
|
||||
destroy_dev(rc->rc_dev);
|
||||
destroy_dev(rc->rc_cdev);
|
||||
}
|
||||
|
||||
rc = sc->sc_channels;
|
||||
s = splsoftclock();
|
||||
for (i = 0; i < CD180_NCHAN; i++) {
|
||||
if ((rc->rc_flags & RC_DTR_OFF) &&
|
||||
!callout_stop(&rc->rc_dtrcallout))
|
||||
tsleep(&rc->rc_dtrwait, TTIPRI, "rcdtrdet", 0);
|
||||
}
|
||||
|
||||
error = bus_teardown_intr(dev, sc->sc_irq, sc->sc_hwicookie);
|
||||
if (error)
|
||||
device_printf(dev, "failed to deregister interrupt handler\n");
|
||||
@ -874,11 +862,9 @@ rcopen(struct cdev *dev, int flag, int mode, d_thread_t *td)
|
||||
s = spltty();
|
||||
|
||||
again:
|
||||
while (rc->rc_flags & RC_DTR_OFF) {
|
||||
error = tsleep(&(rc->rc_dtrwait), TTIPRI | PCATCH, "rcdtr", 0);
|
||||
if (error != 0)
|
||||
goto out;
|
||||
}
|
||||
error = ttydtrwaitsleep(tp);
|
||||
if (error != 0)
|
||||
goto out;
|
||||
if (tp->t_state & TS_ISOPEN) {
|
||||
if (CALLOUT(dev)) {
|
||||
if (!(rc->rc_flags & RC_ACTOUT)) {
|
||||
@ -995,11 +981,7 @@ rc_hardclose(struct rc_chans *rc)
|
||||
CCRCMD(sc, rc->rc_chan, CCR_ResetChan);
|
||||
WAITFORCCR(sc, rc->rc_chan);
|
||||
(void) rc_modem(tp, SER_RTS, 0);
|
||||
if (rc->rc_dtrwait) {
|
||||
callout_reset(&rc->rc_dtrcallout, rc->rc_dtrwait,
|
||||
rc_dtrwakeup, rc);
|
||||
rc->rc_flags |= RC_DTR_OFF;
|
||||
}
|
||||
ttydtrwaitstart(tp);
|
||||
}
|
||||
rc->rc_flags &= ~RC_ACTOUT;
|
||||
wakeup( &rc->rc_rcb); /* wake bi */
|
||||
@ -1200,44 +1182,6 @@ rc_reinit(struct rc_softc *sc)
|
||||
(void) rc_param(&rc->rc_tp, &rc->rc_tp.t_termios);
|
||||
}
|
||||
|
||||
static int
|
||||
rcioctl(struct cdev *dev, u_long cmd, caddr_t data, int flag, d_thread_t *td)
|
||||
{
|
||||
struct rc_chans *rc;
|
||||
struct tty *tp;
|
||||
int s, error;
|
||||
|
||||
rc = DEV_TO_RC(dev);
|
||||
tp = &rc->rc_tp;
|
||||
error = ttyioctl(dev, cmd, data, flag, td);
|
||||
ttyldoptim(tp);
|
||||
if (error != ENOTTY)
|
||||
return (error);
|
||||
s = spltty();
|
||||
|
||||
switch (cmd) {
|
||||
case TIOCMSDTRWAIT:
|
||||
error = suser(td);
|
||||
if (error != 0) {
|
||||
splx(s);
|
||||
return (error);
|
||||
}
|
||||
rc->rc_dtrwait = *(int *)data * hz / 100;
|
||||
break;
|
||||
|
||||
case TIOCMGDTRWAIT:
|
||||
*(int *)data = rc->rc_dtrwait * 100 / hz;
|
||||
break;
|
||||
|
||||
default:
|
||||
(void) splx(s);
|
||||
return ENOTTY;
|
||||
}
|
||||
(void) splx(s);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
/* Modem control routines */
|
||||
|
||||
static int
|
||||
@ -1477,16 +1421,6 @@ printrcflags(struct rc_chans *rc, char *comment)
|
||||
}
|
||||
#endif /* RCDEBUG */
|
||||
|
||||
static void
|
||||
rc_dtrwakeup(void *arg)
|
||||
{
|
||||
struct rc_chans *rc;
|
||||
|
||||
rc = (struct rc_chans *)arg;
|
||||
rc->rc_flags &= ~RC_DTR_OFF;
|
||||
wakeup(&rc->rc_dtrwait);
|
||||
}
|
||||
|
||||
static void
|
||||
rc_discard_output(struct rc_chans *rc)
|
||||
{
|
||||
|
@ -871,7 +871,6 @@ rp_attachcommon(CONTROLLER_T *ctlp, int num_aiops, int num_ports)
|
||||
rp->rp_tty->t_line = 0;
|
||||
/* tty->t_termios = deftermios;
|
||||
*/
|
||||
rp->dtr_wait = 3 * hz;
|
||||
rp->it_in.c_iflag = 0;
|
||||
rp->it_in.c_oflag = 0;
|
||||
rp->it_in.c_cflag = TTYDEF_CFLAG;
|
||||
@ -983,7 +982,7 @@ rpopen(dev, flag, mode, td)
|
||||
|
||||
open_top:
|
||||
while(rp->state & ~SET_DTR) {
|
||||
error = tsleep(&rp->dtr_wait, TTIPRI | PCATCH, "rpdtr", 0);
|
||||
error = tsleep(&tp->t_dtr_wait, TTIPRI | PCATCH, "rpdtr", 0);
|
||||
if(error != 0)
|
||||
goto out;
|
||||
}
|
||||
@ -1174,8 +1173,8 @@ rphardclose(struct rp_port *rp)
|
||||
if(IS_CALLOUT(tp->t_dev)) {
|
||||
sClrDTR(cp);
|
||||
}
|
||||
if(rp->dtr_wait != 0) {
|
||||
timeout(rpdtrwakeup, rp, rp->dtr_wait);
|
||||
if(tp->t_dtr_wait != 0) {
|
||||
timeout(rpdtrwakeup, rp, tp->t_dtr_wait);
|
||||
rp->state |= ~SET_DTR;
|
||||
}
|
||||
|
||||
@ -1222,7 +1221,7 @@ rpdtrwakeup(void *chan)
|
||||
|
||||
rp = (struct rp_port *)chan;
|
||||
rp->state &= SET_DTR;
|
||||
wakeup(&rp->dtr_wait);
|
||||
wakeup(&rp->rp_tty->t_dtr_wait);
|
||||
}
|
||||
|
||||
static int
|
||||
@ -1408,17 +1407,6 @@ rpioctl(dev, cmd, data, flag, td)
|
||||
|
||||
*(int *)data = result;
|
||||
break;
|
||||
case TIOCMSDTRWAIT:
|
||||
error = suser(td);
|
||||
if(error != 0) {
|
||||
splx(oldspl);
|
||||
return(error);
|
||||
}
|
||||
rp->dtr_wait = *(int *)data * hz/100;
|
||||
break;
|
||||
case TIOCMGDTRWAIT:
|
||||
*(int *)data = rp->dtr_wait * 100/hz;
|
||||
break;
|
||||
default:
|
||||
splx(oldspl);
|
||||
return ENOTTY;
|
||||
|
@ -57,7 +57,6 @@ struct rp_port {
|
||||
unsigned char state; /* state of dtr */
|
||||
|
||||
/* Time to hold DTR down on close */
|
||||
int dtr_wait;
|
||||
int wopeners; /* processes waiting for DCD */
|
||||
|
||||
int rp_port;
|
||||
|
@ -102,7 +102,6 @@ static void si_start(struct tty *);
|
||||
static void si_stop(struct tty *, int);
|
||||
static timeout_t si_lstart;
|
||||
static void sihardclose(struct si_port *pp);
|
||||
static void sidtrwakeup(void *chan);
|
||||
|
||||
#ifdef SI_DEBUG
|
||||
static char *si_mctl2str(enum si_mctl cmd);
|
||||
@ -543,7 +542,6 @@ siattach(device_t dev)
|
||||
pp->sp_tty = ttymalloc(NULL);
|
||||
pp->sp_pend = IDLE_CLOSE;
|
||||
pp->sp_state = 0; /* internal flag */
|
||||
pp->sp_dtr_wait = 3 * hz;
|
||||
pp->sp_iin.c_iflag = TTYDEF_IFLAG;
|
||||
pp->sp_iin.c_oflag = TTYDEF_OFLAG;
|
||||
pp->sp_iin.c_cflag = TTYDEF_CFLAG;
|
||||
@ -652,11 +650,9 @@ siopen(struct cdev *dev, int flag, int mode, struct thread *td)
|
||||
error = 0;
|
||||
|
||||
open_top:
|
||||
while (pp->sp_state & SS_DTR_OFF) {
|
||||
error = tsleep(&pp->sp_dtr_wait, TTIPRI|PCATCH, "sidtr", 0);
|
||||
if (error != 0)
|
||||
goto out;
|
||||
}
|
||||
error = ttydtrwaitsleep(tp);
|
||||
if (error != 0)
|
||||
goto out;
|
||||
|
||||
if (tp->t_state & TS_ISOPEN) {
|
||||
/*
|
||||
@ -837,11 +833,7 @@ sihardclose(struct si_port *pp)
|
||||
(void) si_modem(pp, BIC, TIOCM_DTR|TIOCM_RTS);
|
||||
(void) si_command(pp, FCLOSE, SI_NOWAIT);
|
||||
|
||||
if (pp->sp_dtr_wait != 0) {
|
||||
timeout(sidtrwakeup, pp, pp->sp_dtr_wait);
|
||||
pp->sp_state |= SS_DTR_OFF;
|
||||
}
|
||||
|
||||
ttydtrwaitstart(tp);
|
||||
}
|
||||
pp->sp_active_out = FALSE;
|
||||
wakeup(&pp->sp_active_out);
|
||||
@ -850,25 +842,6 @@ sihardclose(struct si_port *pp)
|
||||
splx(oldspl);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* called at splsoftclock()...
|
||||
*/
|
||||
static void
|
||||
sidtrwakeup(void *chan)
|
||||
{
|
||||
struct si_port *pp;
|
||||
int oldspl;
|
||||
|
||||
oldspl = spltty();
|
||||
|
||||
pp = (struct si_port *)chan;
|
||||
pp->sp_state &= ~SS_DTR_OFF;
|
||||
wakeup(&pp->sp_dtr_wait);
|
||||
|
||||
splx(oldspl);
|
||||
}
|
||||
|
||||
static int
|
||||
siwrite(struct cdev *dev, struct uio *uio, int flag)
|
||||
{
|
||||
@ -1056,15 +1029,6 @@ siioctl(struct cdev *dev, u_long cmd, caddr_t data, int flag, struct thread *td)
|
||||
case TIOCMGET:
|
||||
*(int *)data = si_modem(pp, GET, 0);
|
||||
break;
|
||||
case TIOCMSDTRWAIT:
|
||||
/* must be root since the wait applies to following logins */
|
||||
error = suser(td);
|
||||
if (error == 0)
|
||||
pp->sp_dtr_wait = *(int *)data * hz / 100;
|
||||
break;
|
||||
case TIOCMGDTRWAIT:
|
||||
*(int *)data = pp->sp_dtr_wait * 100 / hz;
|
||||
break;
|
||||
default:
|
||||
error = ENOTTY;
|
||||
}
|
||||
|
@ -331,7 +331,6 @@ struct si_port {
|
||||
int sp_last_hi_ip; /* cached DCD */
|
||||
int sp_state;
|
||||
int sp_active_out; /* callout is open */
|
||||
int sp_dtr_wait; /* DTR holddown in hz */
|
||||
int sp_delta_overflows;
|
||||
u_int sp_wopeners; /* # procs waiting DCD */
|
||||
/* Initial state. */
|
||||
@ -362,7 +361,6 @@ struct si_port {
|
||||
/* 0x0800 -- */
|
||||
#define SS_WAITWRITE 0x1000
|
||||
#define SS_BLOCKWRITE 0x2000
|
||||
#define SS_DTR_OFF 0x4000 /* DTR held off */
|
||||
|
||||
/*
|
||||
* Command post flags
|
||||
|
@ -150,7 +150,6 @@ __FBSDID("$FreeBSD$");
|
||||
#define CS_ODEVREADY 0x20 /* external device h/w ready (CTS) */
|
||||
#define CS_CHECKMSR 1 /* check of MSR scheduled */
|
||||
#define CS_CTS_OFLOW 2 /* use CTS output flow control */
|
||||
#define CS_DTR_OFF 0x10 /* DTR held off */
|
||||
#define CS_ODONE 4 /* output completed */
|
||||
#define CS_RTS_IFLOW 8 /* use RTS input flow control */
|
||||
#define CSE_BUSYCHECK 1 /* siobusycheck() scheduled */
|
||||
@ -201,7 +200,6 @@ struct com_s {
|
||||
bool_t poll_output; /* nonzero if polling for output is required */
|
||||
bool_t st16650a; /* nonzero if Startech 16650A compatible */
|
||||
int unit; /* unit number */
|
||||
int dtr_wait; /* time to hold DTR down on close (* 1/hz) */
|
||||
u_int flags; /* copy of device flags */
|
||||
u_int tx_fifo_size;
|
||||
u_int wopeners; /* # processes waiting for DCD in open() */
|
||||
@ -285,7 +283,6 @@ static int espattach(struct com_s *com, Port_t esp_port);
|
||||
static void combreak(struct tty *tp, int sig);
|
||||
static timeout_t siobusycheck;
|
||||
static u_int siodivisor(u_long rclk, speed_t speed);
|
||||
static timeout_t siodtrwakeup;
|
||||
static void comhardclose(struct com_s *com);
|
||||
static void sioinput(struct com_s *com);
|
||||
static void siointr1(struct com_s *com);
|
||||
@ -457,6 +454,7 @@ siodetach(dev)
|
||||
return (0);
|
||||
}
|
||||
com->gone = TRUE;
|
||||
ttygone(com->tp);
|
||||
for (i = 0 ; i < 6; i++)
|
||||
destroy_dev(com->devs[i]);
|
||||
if (com->irqres) {
|
||||
@ -961,7 +959,6 @@ sioattach(dev, xrid, rclk)
|
||||
com->bst = rman_get_bustag(port);
|
||||
com->bsh = rman_get_bushandle(port);
|
||||
com->cfcr_image = CFCR_8BITS;
|
||||
com->dtr_wait = 3 * hz;
|
||||
com->loses_outints = COM_LOSESOUTINTS(flags) != 0;
|
||||
com->no_irq = bus_get_resource(dev, SYS_RES_IRQ, 0, NULL, NULL) != 0;
|
||||
com->tx_fifo_size = 1;
|
||||
@ -1239,13 +1236,9 @@ sioopen(dev, flag, mode, td)
|
||||
* up any changes of the device state.
|
||||
*/
|
||||
open_top:
|
||||
while (com->state & CS_DTR_OFF) {
|
||||
error = tsleep(&com->dtr_wait, TTIPRI | PCATCH, "siodtr", 0);
|
||||
if (com_addr(unit) == NULL)
|
||||
return (ENXIO);
|
||||
if (error != 0 || com->gone)
|
||||
goto out;
|
||||
}
|
||||
error = ttydtrwaitsleep(tp);
|
||||
if (error != 0)
|
||||
goto out;
|
||||
if (tp->t_state & TS_ISOPEN) {
|
||||
/*
|
||||
* The device is open, so everything has been initialized.
|
||||
@ -1479,10 +1472,7 @@ comhardclose(com)
|
||||
&& !(com->it_in.c_cflag & CLOCAL))
|
||||
|| !(tp->t_state & TS_ISOPEN)) {
|
||||
(void)commodem(tp, 0, SER_DTR);
|
||||
if (com->dtr_wait != 0 && !(com->state & CS_DTR_OFF)) {
|
||||
timeout(siodtrwakeup, com, com->dtr_wait);
|
||||
com->state |= CS_DTR_OFF;
|
||||
}
|
||||
ttydtrwaitstart(tp);
|
||||
}
|
||||
}
|
||||
if (com->hasfifo) {
|
||||
@ -1610,17 +1600,6 @@ siodivisor(rclk, speed)
|
||||
return (divisor);
|
||||
}
|
||||
|
||||
static void
|
||||
siodtrwakeup(chan)
|
||||
void *chan;
|
||||
{
|
||||
struct com_s *com;
|
||||
|
||||
com = (struct com_s *)chan;
|
||||
com->state &= ~CS_DTR_OFF;
|
||||
wakeup(&com->dtr_wait);
|
||||
}
|
||||
|
||||
/*
|
||||
* Call this function with the sio_lock mutex held. It will return with the
|
||||
* lock still held.
|
||||
@ -2113,18 +2092,6 @@ sioioctl(dev, cmd, data, flag, td)
|
||||
return (error);
|
||||
s = spltty();
|
||||
switch (cmd) {
|
||||
case TIOCMSDTRWAIT:
|
||||
/* must be root since the wait applies to following logins */
|
||||
error = suser(td);
|
||||
if (error != 0) {
|
||||
splx(s);
|
||||
return (error);
|
||||
}
|
||||
com->dtr_wait = *(int *)data * hz / 100;
|
||||
break;
|
||||
case TIOCMGDTRWAIT:
|
||||
*(int *)data = com->dtr_wait * 100 / hz;
|
||||
break;
|
||||
case TIOCTIMESTAMP:
|
||||
com->do_timestamp = TRUE;
|
||||
*(struct timeval *)data = com->timestamp;
|
||||
|
@ -281,7 +281,6 @@ sxattach(
|
||||
sc->sc_ports[x].sp_chan = x;
|
||||
sc->sc_ports[x].sp_tty = tp++;
|
||||
sc->sc_ports[x].sp_state = 0; /* internal flag */
|
||||
sc->sc_ports[x].sp_dtr_wait = 3 * hz;
|
||||
sc->sc_ports[x].sp_iin.c_iflag = TTYDEF_IFLAG;
|
||||
sc->sc_ports[x].sp_iin.c_oflag = TTYDEF_OFLAG;
|
||||
sc->sc_ports[x].sp_iin.c_cflag = TTYDEF_CFLAG;
|
||||
@ -391,7 +390,7 @@ sxopen(
|
||||
* it to assert.
|
||||
*/
|
||||
while (pp->sp_state & SX_SS_DTR_OFF && SX_DTRPIN(pp)) {
|
||||
error = tsleep(&pp->sp_dtr_wait, TTIPRI|PCATCH, "sxdtr", 0);
|
||||
error = tsleep(&tp->t_dtr_wait, TTIPRI|PCATCH, "sxdtr", 0);
|
||||
if (error != 0)
|
||||
goto out;
|
||||
}
|
||||
@ -603,8 +602,8 @@ sxhardclose(
|
||||
* If we should hold DTR off for a bit and we actually have a
|
||||
* DTR pin to hold down, schedule sxdtrwakeup().
|
||||
*/
|
||||
if (pp->sp_dtr_wait != 0 && SX_DTRPIN(pp)) {
|
||||
timeout(sxdtrwakeup, pp, pp->sp_dtr_wait);
|
||||
if (tp->t_dtr_wait != 0 && SX_DTRPIN(pp)) {
|
||||
timeout(sxdtrwakeup, pp, tp->t_dtr_wait);
|
||||
pp->sp_state |= SX_SS_DTR_OFF;
|
||||
}
|
||||
|
||||
@ -630,7 +629,7 @@ sxdtrwakeup(void *chan)
|
||||
oldspl = spltty();
|
||||
pp = (struct sx_port *)chan;
|
||||
pp->sp_state &= ~SX_SS_DTR_OFF;
|
||||
wakeup(&pp->sp_dtr_wait);
|
||||
wakeup(&pp->sp_tty->t_dtr_wait);
|
||||
splx(oldspl);
|
||||
}
|
||||
|
||||
@ -884,15 +883,6 @@ sxioctl(
|
||||
DPRINT((pp, DBG_IOCTL, "sxioctl(%s) got signals 0x%x\n",
|
||||
devtoname(dev), *(int *)data));
|
||||
break;
|
||||
case TIOCMSDTRWAIT: /* Set "wait on close" delay. */
|
||||
/* must be root since the wait applies to following logins */
|
||||
error = suser(p);
|
||||
if (error == 0)
|
||||
pp->sp_dtr_wait = *(int *)data * hz / 100;
|
||||
break;
|
||||
case TIOCMGDTRWAIT: /* Get "wait on close" delay. */
|
||||
*(int *)data = pp->sp_dtr_wait * 100 / hz;
|
||||
break;
|
||||
default:
|
||||
error = ENOTTY;
|
||||
}
|
||||
|
@ -39,7 +39,6 @@ struct sx_port {
|
||||
struct tty *sp_tty;
|
||||
int sp_state;
|
||||
int sp_active_out; /* callout is open */
|
||||
int sp_dtr_wait; /* DTR holddown in hz */
|
||||
int sp_delta_overflows;
|
||||
u_int sp_wopeners; /* Processes waiting for DCD. */
|
||||
struct termios sp_iin; /* Initial state. */
|
||||
|
@ -963,6 +963,16 @@ ttioctl(struct tty *tp, u_long cmd, void *data, int flag)
|
||||
splx(s);
|
||||
break;
|
||||
#endif
|
||||
case TIOCMGDTRWAIT:
|
||||
*(int *)data = tp->t_dtr_wait * 100 / hz;
|
||||
break;
|
||||
case TIOCMSDTRWAIT:
|
||||
/* must be root since the wait applies to following logins */
|
||||
error = suser(td);
|
||||
if (error)
|
||||
return (error);
|
||||
tp->t_dtr_wait = *(int *)data * hz / 100;
|
||||
break;
|
||||
case TIOCNXCL: /* reset exclusive use of tty */
|
||||
s = spltty();
|
||||
CLR(tp->t_state, TS_XCLUDE);
|
||||
@ -2773,6 +2783,7 @@ ttymalloc(struct tty *tp)
|
||||
}
|
||||
tp = malloc(sizeof *tp, M_TTYS, M_WAITOK | M_ZERO);
|
||||
tp->t_timeout = -1;
|
||||
tp->t_dtr_wait = 3 * hz;
|
||||
mtx_init(&tp->t_mtx, "tty", NULL, MTX_DEF);
|
||||
tp->t_refcnt = 1;
|
||||
mtx_lock(&tty_list_mutex);
|
||||
@ -2894,6 +2905,7 @@ ttyioctl(struct cdev *dev, u_long cmd, caddr_t data, int flag, struct thread *td
|
||||
error = ttyld_ioctl(tp, cmd, data, flag, td);
|
||||
if (error == ENOIOCTL)
|
||||
error = ttioctl(tp, cmd, data, flag);
|
||||
ttyldoptim(tp);
|
||||
if (error != ENOIOCTL)
|
||||
return (error);
|
||||
return (ENOTTY);
|
||||
@ -2916,6 +2928,58 @@ ttyldoptim(struct tty *tp)
|
||||
tp->t_state &= ~TS_CAN_BYPASS_L_RINT;
|
||||
}
|
||||
|
||||
static void
|
||||
ttydtrwaitwakeup(void *arg)
|
||||
{
|
||||
struct tty *tp;
|
||||
|
||||
tp = arg;
|
||||
tp->t_state &= ~TS_DTR_WAIT;
|
||||
wakeup(&tp->t_dtr_wait);
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
ttydtrwaitstart(struct tty *tp)
|
||||
{
|
||||
|
||||
if (tp->t_dtr_wait == 0)
|
||||
return;
|
||||
if (tp->t_state & TS_DTR_WAIT)
|
||||
return;
|
||||
timeout(ttydtrwaitwakeup, tp, tp->t_dtr_wait);
|
||||
tp->t_state |= TS_DTR_WAIT;
|
||||
}
|
||||
|
||||
int
|
||||
ttydtrwaitsleep(struct tty *tp)
|
||||
{
|
||||
int error;
|
||||
|
||||
error = 0;
|
||||
while (error == 0) {
|
||||
if (tp->t_state & TS_GONE)
|
||||
error = ENXIO;
|
||||
else if (!(tp->t_state & TS_DTR_WAIT))
|
||||
break;
|
||||
else
|
||||
error = tsleep(&tp->t_dtr_wait, TTIPRI | PCATCH,
|
||||
"dtrwait", 0);
|
||||
}
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* This function is called when the hardware disappears. We set a flag
|
||||
* and wake up stuff so all sleeping threads will notice.
|
||||
*/
|
||||
void
|
||||
ttygone(struct tty *tp)
|
||||
{
|
||||
|
||||
tp->t_state |= TS_GONE;
|
||||
wakeup(&tp->t_dtr_wait);
|
||||
}
|
||||
|
||||
/*
|
||||
* Record the relationship between the serial ports notion of modem control
|
||||
|
@ -212,7 +212,6 @@
|
||||
#define CS_ODEVREADY 0x20 /* external device h/w ready (CTS) */
|
||||
#define CS_CHECKMSR 1 /* check of MSR scheduled */
|
||||
#define CS_CTS_OFLOW 2 /* use CTS output flow control */
|
||||
#define CS_DTR_OFF 0x10 /* DTR held off */
|
||||
#define CS_ODONE 4 /* output completed */
|
||||
#define CS_RTS_IFLOW 8 /* use RTS input flow control */
|
||||
#define CSE_BUSYCHECK 1 /* siobusycheck() scheduled */
|
||||
@ -263,7 +262,6 @@ struct com_s {
|
||||
bool_t poll_output; /* nonzero if polling for output is required */
|
||||
bool_t st16650a; /* nonzero if Startech 16650A compatible */
|
||||
int unit; /* unit number */
|
||||
int dtr_wait; /* time to hold DTR down on close (* 1/hz) */
|
||||
u_int flags; /* copy of device flags */
|
||||
u_int tx_fifo_size;
|
||||
u_int wopeners; /* # processes waiting for DCD in open() */
|
||||
@ -371,7 +369,6 @@ static int espattach(struct com_s *com, Port_t esp_port);
|
||||
static void combreak(struct tty *tp, int sig);
|
||||
static timeout_t siobusycheck;
|
||||
static u_int siodivisor(u_long rclk, speed_t speed);
|
||||
static timeout_t siodtrwakeup;
|
||||
static void comhardclose(struct com_s *com);
|
||||
static void sioinput(struct com_s *com);
|
||||
static void siointr1(struct com_s *com);
|
||||
@ -788,6 +785,7 @@ siodetach(dev)
|
||||
return (0);
|
||||
}
|
||||
com->gone = TRUE;
|
||||
ttygone(com->tp);
|
||||
for (i = 0 ; i < 6; i++)
|
||||
destroy_dev(com->devs[i]);
|
||||
if (com->irqres) {
|
||||
@ -1512,7 +1510,6 @@ sioattach(dev, xrid, rclk)
|
||||
com->bst = rman_get_bustag(port);
|
||||
com->bsh = rman_get_bushandle(port);
|
||||
com->cfcr_image = CFCR_8BITS;
|
||||
com->dtr_wait = 3 * hz;
|
||||
com->loses_outints = COM_LOSESOUTINTS(flags) != 0;
|
||||
com->no_irq = bus_get_resource(dev, SYS_RES_IRQ, 0, NULL, NULL) != 0;
|
||||
com->tx_fifo_size = 1;
|
||||
@ -1909,13 +1906,9 @@ sioopen(dev, flag, mode, td)
|
||||
* up any changes of the device state.
|
||||
*/
|
||||
open_top:
|
||||
while (com->state & CS_DTR_OFF) {
|
||||
error = tsleep(&com->dtr_wait, TTIPRI | PCATCH, "siodtr", 0);
|
||||
if (com_addr(unit) == NULL)
|
||||
return (ENXIO);
|
||||
if (error != 0 || com->gone)
|
||||
goto out;
|
||||
}
|
||||
error = ttydtrwaitsleep(tp);
|
||||
if (error)
|
||||
goto out;
|
||||
if (tp->t_state & TS_ISOPEN) {
|
||||
/*
|
||||
* The device is open, so everything has been initialized.
|
||||
@ -2229,10 +2222,7 @@ comhardclose(com)
|
||||
else
|
||||
#endif
|
||||
(void)commodem(tp, 0, SER_DTR);
|
||||
if (com->dtr_wait != 0 && !(com->state & CS_DTR_OFF)) {
|
||||
timeout(siodtrwakeup, com, com->dtr_wait);
|
||||
com->state |= CS_DTR_OFF;
|
||||
}
|
||||
ttydtrwaitstart(tp);
|
||||
}
|
||||
#ifdef PC98
|
||||
else {
|
||||
@ -2385,17 +2375,6 @@ siodivisor(rclk, speed)
|
||||
return (divisor);
|
||||
}
|
||||
|
||||
static void
|
||||
siodtrwakeup(chan)
|
||||
void *chan;
|
||||
{
|
||||
struct com_s *com;
|
||||
|
||||
com = (struct com_s *)chan;
|
||||
com->state &= ~CS_DTR_OFF;
|
||||
wakeup(&com->dtr_wait);
|
||||
}
|
||||
|
||||
/*
|
||||
* Call this function with the sio_lock mutex held. It will return with the
|
||||
* lock still held.
|
||||
@ -3088,18 +3067,6 @@ sioioctl(dev, cmd, data, flag, td)
|
||||
return (error);
|
||||
s = spltty();
|
||||
switch (cmd) {
|
||||
case TIOCMSDTRWAIT:
|
||||
/* must be root since the wait applies to following logins */
|
||||
error = suser(td);
|
||||
if (error != 0) {
|
||||
splx(s);
|
||||
return (error);
|
||||
}
|
||||
com->dtr_wait = *(int *)data * hz / 100;
|
||||
break;
|
||||
case TIOCMGDTRWAIT:
|
||||
*(int *)data = com->dtr_wait * 100 / hz;
|
||||
break;
|
||||
case TIOCTIMESTAMP:
|
||||
com->do_timestamp = TRUE;
|
||||
*(struct timeval *)data = com->timestamp;
|
||||
|
@ -212,7 +212,6 @@
|
||||
#define CS_ODEVREADY 0x20 /* external device h/w ready (CTS) */
|
||||
#define CS_CHECKMSR 1 /* check of MSR scheduled */
|
||||
#define CS_CTS_OFLOW 2 /* use CTS output flow control */
|
||||
#define CS_DTR_OFF 0x10 /* DTR held off */
|
||||
#define CS_ODONE 4 /* output completed */
|
||||
#define CS_RTS_IFLOW 8 /* use RTS input flow control */
|
||||
#define CSE_BUSYCHECK 1 /* siobusycheck() scheduled */
|
||||
@ -263,7 +262,6 @@ struct com_s {
|
||||
bool_t poll_output; /* nonzero if polling for output is required */
|
||||
bool_t st16650a; /* nonzero if Startech 16650A compatible */
|
||||
int unit; /* unit number */
|
||||
int dtr_wait; /* time to hold DTR down on close (* 1/hz) */
|
||||
u_int flags; /* copy of device flags */
|
||||
u_int tx_fifo_size;
|
||||
u_int wopeners; /* # processes waiting for DCD in open() */
|
||||
@ -371,7 +369,6 @@ static int espattach(struct com_s *com, Port_t esp_port);
|
||||
static void combreak(struct tty *tp, int sig);
|
||||
static timeout_t siobusycheck;
|
||||
static u_int siodivisor(u_long rclk, speed_t speed);
|
||||
static timeout_t siodtrwakeup;
|
||||
static void comhardclose(struct com_s *com);
|
||||
static void sioinput(struct com_s *com);
|
||||
static void siointr1(struct com_s *com);
|
||||
@ -788,6 +785,7 @@ siodetach(dev)
|
||||
return (0);
|
||||
}
|
||||
com->gone = TRUE;
|
||||
ttygone(com->tp);
|
||||
for (i = 0 ; i < 6; i++)
|
||||
destroy_dev(com->devs[i]);
|
||||
if (com->irqres) {
|
||||
@ -1512,7 +1510,6 @@ sioattach(dev, xrid, rclk)
|
||||
com->bst = rman_get_bustag(port);
|
||||
com->bsh = rman_get_bushandle(port);
|
||||
com->cfcr_image = CFCR_8BITS;
|
||||
com->dtr_wait = 3 * hz;
|
||||
com->loses_outints = COM_LOSESOUTINTS(flags) != 0;
|
||||
com->no_irq = bus_get_resource(dev, SYS_RES_IRQ, 0, NULL, NULL) != 0;
|
||||
com->tx_fifo_size = 1;
|
||||
@ -1909,13 +1906,9 @@ sioopen(dev, flag, mode, td)
|
||||
* up any changes of the device state.
|
||||
*/
|
||||
open_top:
|
||||
while (com->state & CS_DTR_OFF) {
|
||||
error = tsleep(&com->dtr_wait, TTIPRI | PCATCH, "siodtr", 0);
|
||||
if (com_addr(unit) == NULL)
|
||||
return (ENXIO);
|
||||
if (error != 0 || com->gone)
|
||||
goto out;
|
||||
}
|
||||
error = ttydtrwaitsleep(tp);
|
||||
if (error)
|
||||
goto out;
|
||||
if (tp->t_state & TS_ISOPEN) {
|
||||
/*
|
||||
* The device is open, so everything has been initialized.
|
||||
@ -2229,10 +2222,7 @@ comhardclose(com)
|
||||
else
|
||||
#endif
|
||||
(void)commodem(tp, 0, SER_DTR);
|
||||
if (com->dtr_wait != 0 && !(com->state & CS_DTR_OFF)) {
|
||||
timeout(siodtrwakeup, com, com->dtr_wait);
|
||||
com->state |= CS_DTR_OFF;
|
||||
}
|
||||
ttydtrwaitstart(tp);
|
||||
}
|
||||
#ifdef PC98
|
||||
else {
|
||||
@ -2385,17 +2375,6 @@ siodivisor(rclk, speed)
|
||||
return (divisor);
|
||||
}
|
||||
|
||||
static void
|
||||
siodtrwakeup(chan)
|
||||
void *chan;
|
||||
{
|
||||
struct com_s *com;
|
||||
|
||||
com = (struct com_s *)chan;
|
||||
com->state &= ~CS_DTR_OFF;
|
||||
wakeup(&com->dtr_wait);
|
||||
}
|
||||
|
||||
/*
|
||||
* Call this function with the sio_lock mutex held. It will return with the
|
||||
* lock still held.
|
||||
@ -3088,18 +3067,6 @@ sioioctl(dev, cmd, data, flag, td)
|
||||
return (error);
|
||||
s = spltty();
|
||||
switch (cmd) {
|
||||
case TIOCMSDTRWAIT:
|
||||
/* must be root since the wait applies to following logins */
|
||||
error = suser(td);
|
||||
if (error != 0) {
|
||||
splx(s);
|
||||
return (error);
|
||||
}
|
||||
com->dtr_wait = *(int *)data * hz / 100;
|
||||
break;
|
||||
case TIOCMGDTRWAIT:
|
||||
*(int *)data = com->dtr_wait * 100 / hz;
|
||||
break;
|
||||
case TIOCTIMESTAMP:
|
||||
com->do_timestamp = TRUE;
|
||||
*(struct timeval *)data = com->timestamp;
|
||||
|
@ -117,6 +117,7 @@ struct tty {
|
||||
struct mtx t_mtx;
|
||||
int t_refcnt;
|
||||
int t_hotchar; /* linedisc preferred hot char */
|
||||
int t_dtr_wait; /* Inter-session DTR holddown [hz] */
|
||||
|
||||
/* Driver supplied methods */
|
||||
t_oproc_t *t_oproc; /* Start output. */
|
||||
@ -224,6 +225,9 @@ struct xtty {
|
||||
#define TS_DSR_OFLOW 0x800000 /* For CDSR_OFLOW. */
|
||||
#endif
|
||||
|
||||
#define TS_DTR_WAIT 0x1000000 /* DTR hold-down between sessions */
|
||||
#define TS_GONE 0x2000000 /* Hardware detached */
|
||||
|
||||
/* Character type information. */
|
||||
#define ORDINARY 0
|
||||
#define CONTROL 1
|
||||
@ -308,7 +312,10 @@ void ttyblock(struct tty *tp);
|
||||
void ttychars(struct tty *tp);
|
||||
int ttycheckoutq(struct tty *tp, int wait);
|
||||
int ttyclose(struct tty *tp);
|
||||
int ttydtrwaitsleep(struct tty *tp);
|
||||
void ttydtrwaitstart(struct tty *tp);
|
||||
void ttyflush(struct tty *tp, int rw);
|
||||
void ttygone(struct tty *tp);
|
||||
void ttyinfo(struct tty *tp);
|
||||
int ttyinput(int c, struct tty *tp);
|
||||
int ttylclose(struct tty *tp, int flag);
|
||||
|
Loading…
Reference in New Issue
Block a user