1
0
mirror of https://git.FreeBSD.org/src.git synced 2024-12-15 10:17:20 +00:00

Merge a bunch of changes that where done in tty_pty.c after tty_pts.c was

forked from it, but missed from some reason.
This commit is contained in:
Olivier Houchard 2006-01-27 15:13:40 +00:00
parent b258da0fa9
commit 23c15e6437
Notes: svn2git 2020-12-20 02:59:44 +00:00
svn path=/head/; revision=154911

View File

@ -153,11 +153,8 @@ static LIST_HEAD(,pt_desc) pt_free_list;
#define PF_PKT 0x008 /* packet mode */
#define PF_STOPPED 0x010 /* user told stopped */
#define PF_REMOTE 0x020 /* remote and flow controlled input */
#define PF_NOSTOP 0x040
#define PF_UCNTL 0x080 /* user control mode */
#define PF_COPEN 0x100 /* control half open */
#define PF_SOPEN 0x200 /* slave half open */
static unsigned int next_avail_nb;
@ -265,14 +262,9 @@ ptsopen(struct cdev *dev, int flag, int devtype, struct thread *td)
pt = dev->si_drv1;
tp = dev->si_tty;
if ((tp->t_state & TS_ISOPEN) == 0) {
ttychars(tp); /* Set up default chars */
tp->t_iflag = TTYDEF_IFLAG;
tp->t_oflag = TTYDEF_OFLAG;
tp->t_lflag = TTYDEF_LFLAG;
tp->t_cflag = TTYDEF_CFLAG;
tp->t_ispeed = tp->t_ospeed = TTYDEF_SPEED;
} else if (tp->t_state & TS_XCLUDE && suser(td)) {
if ((tp->t_state & TS_ISOPEN) == 0)
ttyinitmode(tp, 1, 0);
else if (tp->t_state & TS_XCLUDE && suser(td)) {
return (EBUSY);
} else if (pt->pt_prison != td->td_ucred->cr_prison) {
return (EBUSY);
@ -314,57 +306,11 @@ ptsclose(struct cdev *dev, int flag, int mode, struct thread *td)
static int
ptsread(struct cdev *dev, struct uio *uio, int flag)
{
struct thread *td = curthread;
struct proc *p = td->td_proc;
struct tty *tp = dev->si_tty;
struct pt_desc *pt = dev->si_drv1;
struct pgrp *pg;
int error = 0;
again:
if (pt->pt_flags & PF_REMOTE) {
while (isbackground(p, tp)) {
sx_slock(&proctree_lock);
PROC_LOCK(p);
if (SIGISMEMBER(p->p_sigacts->ps_sigignore, SIGTTIN) ||
SIGISMEMBER(td->td_sigmask, SIGTTIN) ||
p->p_pgrp->pg_jobc == 0 || p->p_flag & P_PPWAIT) {
PROC_UNLOCK(p);
sx_sunlock(&proctree_lock);
return (EIO);
}
pg = p->p_pgrp;
PROC_UNLOCK(p);
PGRP_LOCK(pg);
sx_sunlock(&proctree_lock);
pgsignal(pg, SIGTTIN, 1);
PGRP_UNLOCK(pg);
error = ttysleep(tp, &lbolt, TTIPRI | PCATCH, "ptsbg",
0);
if (error)
return (error);
}
if (tp->t_canq.c_cc == 0) {
if (flag & IO_NDELAY)
return (EWOULDBLOCK);
error = ttysleep(tp, TSA_PTS_READ(tp), TTIPRI | PCATCH,
"ptsin", 0);
if (error)
return (error);
goto again;
}
while (tp->t_canq.c_cc > 1 && uio->uio_resid > 0)
if (ureadc(getc(&tp->t_canq), uio) < 0) {
error = EFAULT;
break;
}
if (tp->t_canq.c_cc == 1)
(void) getc(&tp->t_canq);
if (tp->t_canq.c_cc)
return (error);
} else
if (tp->t_oproc)
ttyld_read(tp, uio, flag);
if (tp->t_oproc)
error = ttyld_read(tp, uio, flag);
ptcwakeup(tp, FWRITE);
return (error);
}
@ -539,7 +485,7 @@ ptcread(struct cdev *dev, struct uio *uio, int flag)
}
if ((tp->t_state & TS_CONNECTED) == 0)
return (0); /* EOF */
if (flag & IO_NDELAY)
if (flag & O_NONBLOCK)
return (EWOULDBLOCK);
error = tsleep(TSA_PTC_READ(tp), TTIPRI | PCATCH, "ptcin", 0);
if (error)
@ -605,9 +551,7 @@ ptcpoll(struct cdev *dev, int events, struct thread *td)
if (events & (POLLOUT | POLLWRNORM))
if (tp->t_state & TS_ISOPEN &&
((pt->pt_flags & PF_REMOTE) ?
(tp->t_canq.c_cc == 0) :
((tp->t_rawq.c_cc + tp->t_canq.c_cc < TTYHOG - 2) ||
(((tp->t_rawq.c_cc + tp->t_canq.c_cc < TTYHOG - 2) ||
(tp->t_canq.c_cc == 0 && (tp->t_lflag & ICANON)))))
revents |= events & (POLLOUT | POLLWRNORM);
@ -635,52 +579,11 @@ ptcwrite(struct cdev *dev, struct uio *uio, int flag)
int cc = 0;
u_char locbuf[BUFSIZ];
int cnt = 0;
struct pt_desc *pt = dev->si_drv1;
int error = 0;
again:
if ((tp->t_state&TS_ISOPEN) == 0)
goto block;
if (pt->pt_flags & PF_REMOTE) {
if (tp->t_canq.c_cc)
goto block;
while ((uio->uio_resid > 0 || cc > 0) &&
tp->t_canq.c_cc < TTYHOG - 1) {
if (cc == 0) {
cc = min(uio->uio_resid, BUFSIZ);
cc = min(cc, TTYHOG - 1 - tp->t_canq.c_cc);
cp = locbuf;
error = uiomove(cp, cc, uio);
if (error)
return (error);
/* check again for safety */
if ((tp->t_state & TS_ISOPEN) == 0) {
/* adjust as usual */
uio->uio_resid += cc;
return (EIO);
}
}
if (cc > 0) {
cc = b_to_q((char *)cp, cc, &tp->t_canq);
/*
* XXX we don't guarantee that the canq size
* is >= TTYHOG, so the above b_to_q() may
* leave some bytes uncopied. However, space
* is guaranteed for the null terminator if
* we don't fail here since (TTYHOG - 1) is
* not a multiple of CBSIZE.
*/
if (cc > 0)
break;
}
}
/* adjust for data copied in but not written */
uio->uio_resid += cc;
(void) putc(0, &tp->t_canq);
ttwakeup(tp);
wakeup(TSA_PTS_READ(tp));
return (0);
}
while (uio->uio_resid > 0 || cc > 0) {
if (cc == 0) {
cc = min(uio->uio_resid, BUFSIZ);