2 * Copyright (c) 2011 Bayard G. Bell. All rights reserved.
3 * Copyright 2008 Sun Microsystems, Inc. All rights reserved.
4 * Use is subject to license terms.
8 * Copyright (c) 1983 Regents of the University of California.
9 * All rights reserved. The Berkeley software License Agreement
10 * specifies the terms and conditions for redistribution.
14 * PTY - Stream "pseudo-tty" device.
15 * This is the "slave" side.
19 #include <sys/param.h>
20 #include <sys/systm.h>
21 #include <sys/filio.h>
22 #include <sys/ioccom.h>
23 #include <sys/termios.h>
24 #include <sys/termio.h>
25 #include <sys/ttold.h>
26 #include <sys/stropts.h>
27 #include <sys/stream.h>
28 #include <sys/strsun.h>
33 #include <sys/vnode.h> /* 1/0 on the vomit meter */
36 #include <sys/errno.h>
37 #include <sys/strsubr.h>
39 #include <sys/sysmacros.h>
40 #include <sys/debug.h>
41 #include <sys/procset.h>
43 #include <sys/ptyvar.h>
44 #include <sys/suntty.h>
46 #include <sys/policy.h>
50 #include <sys/sunddi.h>
52 extern void gsignal(int pid
, int sig
);
54 extern int npty
; /* number of pseudo-ttys configured in */
55 extern struct pty
*pty_softc
;
57 extern struct pollhead ptcph
; /* poll head for ptcpoll() use */
59 #define IFLAGS (CS7|CREAD|PARENB)
63 * Most of these should be "void", but the people who defined the "streams"
64 * data structure for S5 didn't understand data types.
68 * Slave side. This is a streams device.
70 static int ptslopen(queue_t
*, dev_t
*, int flag
, int, cred_t
*);
71 static int ptslclose(queue_t
*, int, cred_t
*);
72 static int ptslrserv(queue_t
*);
75 * To save instructions, since STREAMS ignores the return value
76 * from this function, it is defined as void here. Kind of icky, but...
79 static void ptslwput(queue_t
*q
, mblk_t
*mp
);
81 static struct module_info ptslm_info
= {
90 static struct qinit ptslrinit
= {
100 static struct qinit ptslwinit
= {
110 struct streamtab ptysinfo
= {
117 static void ptslreioctl(void *);
118 static void ptslioctl(struct pty
*, queue_t
*, mblk_t
*);
119 static void pt_sendstop(struct pty
*);
120 static void ptcpollwakeup(struct pty
*, int);
123 static int ptsl_info(dev_info_t
*, ddi_info_cmd_t
, void *, void **);
124 static int ptsl_attach(dev_info_t
*, ddi_attach_cmd_t
);
125 static dev_info_t
*ptsl_dip
; /* for dev-to-dip conversions */
127 DDI_DEFINE_STREAM_OPS(ptsl_ops
, nulldev
, nulldev
,
128 ptsl_attach
, nodev
, nodev
, ptsl_info
, D_MP
, &ptysinfo
,
129 ddi_quiesce_not_supported
);
131 #include <sys/types.h>
132 #include <sys/conf.h>
133 #include <sys/param.h>
134 #include <sys/systm.h>
135 #include <sys/errno.h>
136 #include <sys/modctl.h>
139 * Module linkage information for the kernel.
142 static struct modldrv modldrv
= {
143 &mod_driverops
, /* Type of module. This one is a pseudo driver */
144 "tty pseudo driver slave 'ptsl'",
145 &ptsl_ops
, /* driver ops */
148 static struct modlinkage modlinkage
= {
157 return (mod_install(&modlinkage
));
163 return (mod_remove(&modlinkage
));
167 _info(struct modinfo
*modinfop
)
169 return (mod_info(&modlinkage
, modinfop
));
172 static char *tty_banks
= PTY_BANKS
;
173 static char *tty_digits
= PTY_DIGITS
;
177 ptsl_attach(dev_info_t
*devi
, ddi_attach_cmd_t cmd
)
181 char *tty_digit
= tty_digits
;
182 char *tty_bank
= tty_banks
;
184 for (tty_num
= 0; tty_num
< npty
; tty_num
++) {
185 (void) sprintf(name
, "tty%c%c", *tty_bank
, *tty_digit
);
186 if (ddi_create_minor_node(devi
, name
, S_IFCHR
,
187 tty_num
, DDI_PSEUDO
, 0) == DDI_FAILURE
) {
188 ddi_remove_minor_node(devi
, NULL
);
191 if (*(++tty_digit
) == '\0') {
192 tty_digit
= tty_digits
;
193 if (*(++tty_bank
) == '\0')
198 return (DDI_SUCCESS
);
203 ptsl_info(dev_info_t
*dip
, ddi_info_cmd_t infocmd
, void *arg
,
209 case DDI_INFO_DEVT2DEVINFO
:
210 if (ptsl_dip
== NULL
) {
213 *result
= (void *)ptsl_dip
;
217 case DDI_INFO_DEVT2INSTANCE
:
229 * Open the slave side of a pty.
233 ptslopen(queue_t
*q
, dev_t
*devp
, int flag
, int sflag
, cred_t
*cred
)
239 unit
= getminor(dev
);
243 pty
= &pty_softc
[unit
];
245 mutex_enter(&pty
->ptc_lock
);
247 * Block waiting for controller to open, unless this is a no-delay
251 if (pty
->pt_ttycommon
.t_writeq
== NULL
) {
252 pty
->pt_ttycommon
.t_iflag
= 0;
253 pty
->pt_ttycommon
.t_cflag
= (B38400
<< IBSHIFT
)|B38400
|IFLAGS
;
254 pty
->pt_ttycommon
.t_iocpending
= NULL
;
256 pty
->pt_ttycommon
.t_size
.ws_row
= 0;
257 pty
->pt_ttycommon
.t_size
.ws_col
= 0;
258 pty
->pt_ttycommon
.t_size
.ws_xpixel
= 0;
259 pty
->pt_ttycommon
.t_size
.ws_ypixel
= 0;
260 } else if ((pty
->pt_ttycommon
.t_flags
& TS_XCLUDE
) &&
261 secpolicy_excl_open(cred
) != 0) {
262 mutex_exit(&pty
->ptc_lock
);
265 if (!(flag
& (FNONBLOCK
|FNDELAY
)) &&
266 !(pty
->pt_ttycommon
.t_cflag
& CLOCAL
)) {
267 if (!(pty
->pt_flags
& PF_CARR_ON
)) {
268 pty
->pt_flags
|= PF_WOPEN
;
269 if (!cv_wait_sig(&pty
->pt_cv_flags
, &pty
->ptc_lock
)) {
270 pty
->pt_flags
&= ~PF_WOPEN
;
271 mutex_exit(&pty
->ptc_lock
);
279 q
->q_ptr
= WR(q
)->q_ptr
= pty
;
280 pty
->pt_flags
&= ~PF_SLAVEGONE
;
281 pty
->pt_ttycommon
.t_readq
= pty
->pt_ttycommon
.t_writeq
= NULL
;
284 * Slave is ready to accept messages but master still can't send
285 * messages to the slave queue since it is not plumbed
286 * yet. So do qprocson() and finish slave initialization.
289 mutex_exit(&pty
->ptc_lock
);
294 * Now it is safe to send messages to q, so wakeup master possibly
295 * waiting for slave queue to finish open.
297 mutex_enter(&pty
->ptc_lock
);
299 * queue has already been setup with a pointer to
300 * the stream head that is being referenced
302 pty
->pt_vnode
= strq2vp(q
);
303 VN_RELE(pty
->pt_vnode
);
304 pty
->pt_ttycommon
.t_readq
= q
;
305 pty
->pt_ttycommon
.t_writeq
= WR(q
);
306 /* tell master device that slave is ready for writing */
307 if (pty
->pt_flags
& PF_CARR_ON
)
308 cv_broadcast(&pty
->pt_cv_readq
);
309 mutex_exit(&pty
->ptc_lock
);
315 ptslclose(queue_t
*q
, int flag
, cred_t
*cred
)
318 bufcall_id_t pt_wbufcid
= 0;
321 if ((pty
= (struct pty
*)q
->q_ptr
) == NULL
)
322 return (ENODEV
); /* already been closed once */
325 * Prevent the queues from being uses by master device.
326 * This should be done before qprocsoff or writer may attempt
327 * to use the slave queue after qprocsoff removed it from the stream and
328 * before entering mutex_enter().
330 mutex_enter(&pty
->ptc_lock
);
331 pty
->pt_ttycommon
.t_readq
= NULL
;
332 pty
->pt_ttycommon
.t_writeq
= NULL
;
333 while (pty
->pt_flags
& PF_IOCTL
) {
334 pty
->pt_flags
|= PF_WAIT
;
335 cv_wait(&pty
->pt_cv_flags
, &pty
->ptc_lock
);
337 pty
->pt_vnode
= NULL
;
338 mutex_exit(&pty
->ptc_lock
);
342 mutex_enter(&pty
->ptc_lock
);
344 * ptc_lock mutex is not dropped across
345 * the call to the routine ttycommon_close
347 ttycommon_close(&pty
->pt_ttycommon
);
350 * Cancel outstanding "bufcall" request.
352 if (pty
->pt_wbufcid
) {
353 pt_wbufcid
= pty
->pt_wbufcid
;
358 * Clear out all the slave-side state.
360 pty
->pt_flags
&= ~(PF_WOPEN
|PF_STOPPED
|PF_NOSTOP
);
361 if (pty
->pt_flags
& PF_CARR_ON
) {
362 pty
->pt_flags
|= PF_SLAVEGONE
; /* let the controller know */
363 ptcpollwakeup(pty
, 0); /* wake up readers/selectors */
364 ptcpollwakeup(pty
, FWRITE
); /* wake up writers/selectors */
365 cv_broadcast(&pty
->pt_cv_flags
);
368 q
->q_ptr
= WR(q
)->q_ptr
= NULL
;
369 mutex_exit(&pty
->ptc_lock
);
372 unbufcall(pt_wbufcid
);
378 * Put procedure for write queue.
379 * Respond to M_STOP, M_START, M_IOCTL, and M_FLUSH messages here;
380 * queue up M_DATA messages for processing by the controller "read"
381 * routine; discard everything else.
384 ptslwput(queue_t
*q
, mblk_t
*mp
)
389 pty
= (struct pty
*)q
->q_ptr
;
391 mutex_enter(&pty
->ptc_lock
);
393 switch (mp
->b_datap
->db_type
) {
396 if (!(pty
->pt_flags
& PF_STOPPED
)) {
397 pty
->pt_flags
|= PF_STOPPED
;
398 pty
->pt_send
|= TIOCPKT_STOP
;
399 ptcpollwakeup(pty
, 0);
405 if (pty
->pt_flags
& PF_STOPPED
) {
406 pty
->pt_flags
&= ~PF_STOPPED
;
407 pty
->pt_send
= TIOCPKT_START
;
408 ptcpollwakeup(pty
, 0);
410 ptcpollwakeup(pty
, FREAD
); /* permit controller to read */
415 ptslioctl(pty
, q
, mp
);
419 if (*mp
->b_rptr
& FLUSHW
) {
421 * Set the "flush write" flag, so that we
422 * notify the controller if they're in packet
423 * or user control mode.
425 if (!(pty
->pt_send
& TIOCPKT_FLUSHWRITE
)) {
426 pty
->pt_send
|= TIOCPKT_FLUSHWRITE
;
427 ptcpollwakeup(pty
, 0);
430 * Flush our write queue.
432 flushq(q
, FLUSHDATA
); /* XXX doesn't flush M_DELAY */
433 *mp
->b_rptr
&= ~FLUSHW
; /* it has been flushed */
435 if (*mp
->b_rptr
& FLUSHR
) {
437 * Set the "flush read" flag, so that we
438 * notify the controller if they're in packet
441 if (!(pty
->pt_send
& TIOCPKT_FLUSHREAD
)) {
442 pty
->pt_send
|= TIOCPKT_FLUSHREAD
;
443 ptcpollwakeup(pty
, 0);
445 flushq(RD(q
), FLUSHDATA
);
446 mutex_exit(&pty
->ptc_lock
);
447 qreply(q
, mp
); /* give the read queues a crack at it */
455 * Throw away any leading zero-length blocks, and queue it up
456 * for the controller to read.
458 if (pty
->pt_flags
& PF_CARR_ON
) {
460 while ((bp
->b_wptr
- bp
->b_rptr
) == 0) {
464 mutex_exit(&pty
->ptc_lock
);
465 return; /* damp squib of a message */
470 ptcpollwakeup(pty
, FREAD
); /* soup's on! */
472 freemsg(mp
); /* nobody listening */
476 if ((*(int *)mp
->b_rptr
) == MC_CANONQUERY
) {
478 * We're being asked whether we do canonicalization
479 * or not. Send a reply back up indicating whether
482 (void) putctl1(RD(q
), M_CTL
,
483 (pty
->pt_flags
& PF_REMOTE
) ?
484 MC_NOCANON
: MC_DOCANON
);
491 * "No, I don't want a subscription to Chain Store Age,
497 mutex_exit(&pty
->ptc_lock
);
501 * Retry an "ioctl", now that "bufcall" claims we may be able to allocate
502 * the buffer we need.
505 ptslreioctl(void *arg
)
507 struct pty
*pty
= arg
;
511 mutex_enter(&pty
->ptc_lock
);
513 * The bufcall is no longer pending.
515 if (pty
->pt_wbufcid
== 0) {
516 mutex_exit(&pty
->ptc_lock
);
521 if ((q
= pty
->pt_ttycommon
.t_writeq
) == NULL
) {
522 mutex_exit(&pty
->ptc_lock
);
525 if ((mp
= pty
->pt_ttycommon
.t_iocpending
) != NULL
) {
526 /* It's not pending any more. */
527 pty
->pt_ttycommon
.t_iocpending
= NULL
;
528 ptslioctl(pty
, q
, mp
);
530 mutex_exit(&pty
->ptc_lock
);
534 * Process an "ioctl" message sent down to us.
535 * Drops pty's ptc_lock mutex and then reacquire
538 ptslioctl(struct pty
*pty
, queue_t
*q
, mblk_t
*mp
)
545 ASSERT(MUTEX_HELD(&pty
->ptc_lock
));
547 iocp
= (struct iocblk
*)mp
->b_rptr
;
554 * The permission checking has already been done at the stream
555 * head, since it has to be done in the context of the process
560 error
= miocpullup(mp
, sizeof (char));
565 * Simulate typing of a character at the terminal.
567 if ((bp
= allocb(1, BPRI_MED
)) != NULL
) {
568 *bp
->b_wptr
++ = *mp
->b_cont
->b_rptr
;
569 if (!(pty
->pt_flags
& PF_REMOTE
)) {
570 if (!canput(pty
->pt_ttycommon
.t_readq
)) {
571 mutex_exit(&pty
->ptc_lock
);
572 ttycommon_qfull(&pty
->pt_ttycommon
, q
);
573 mutex_enter(&pty
->ptc_lock
);
579 pty
->pt_ttycommon
.t_readq
, bp
);
581 if (pty
->pt_flags
& PF_UCNTL
) {
583 * XXX - flow control; don't overflow
586 if (pty
->pt_stuffqfirst
!= NULL
) {
587 pty
->pt_stuffqlast
->b_next
= bp
;
588 bp
->b_prev
= pty
->pt_stuffqlast
;
590 pty
->pt_stuffqfirst
= bp
;
594 pty
->pt_stuffqlast
= bp
;
596 ptcpollwakeup(pty
, 0);
605 * Turn the ioctl message into an ioctl ACK message.
607 iocp
->ioc_count
= 0; /* no data returned */
608 mp
->b_datap
->db_type
= M_IOCACK
;
613 tty_common_t
*tc
= &pty
->pt_ttycommon
;
616 error
= miocpullup(mp
, sizeof (struct ttysize
));
621 * Set the window size, but don't send a SIGWINCH.
623 tp
= (struct ttysize
*)mp
->b_cont
->b_rptr
;
624 tc
->t_size
.ws_row
= tp
->ts_lines
;
625 tc
->t_size
.ws_col
= tp
->ts_cols
;
626 tc
->t_size
.ws_xpixel
= 0;
627 tc
->t_size
.ws_ypixel
= 0;
632 iocp
->ioc_count
= 0; /* no data returned */
633 mp
->b_datap
->db_type
= M_IOCACK
;
638 tty_common_t
*tc
= &pty
->pt_ttycommon
;
642 if ((datap
= allocb(sizeof (struct ttysize
),
644 if (pty
->pt_wbufcid
) {
645 if (pty
->pt_ttycommon
.t_iocpending
)
646 freemsg(pty
->pt_ttycommon
.t_iocpending
);
647 pty
->pt_ttycommon
.t_iocpending
= mp
;
650 pty
->pt_wbufcid
= bufcall(sizeof (struct ttysize
),
651 BPRI_HI
, ptslreioctl
, pty
);
652 if (pty
->pt_wbufcid
== 0) {
656 pty
->pt_ttycommon
.t_iocpending
= mp
;
660 * Return the current size.
662 tp
= (struct ttysize
*)datap
->b_wptr
;
663 tp
->ts_lines
= tc
->t_size
.ws_row
;
664 tp
->ts_cols
= tc
->t_size
.ws_col
;
665 datap
->b_wptr
+= sizeof (struct ttysize
);
666 iocp
->ioc_count
= sizeof (struct ttysize
);
668 if (mp
->b_cont
!= NULL
)
671 mp
->b_datap
->db_type
= M_IOCACK
;
676 * Imported from ttycommon_ioctl routine
680 tty_common_t
*tc
= &pty
->pt_ttycommon
;
683 error
= miocpullup(mp
, sizeof (struct termios
));
687 cb
= (struct termios
*)mp
->b_cont
->b_rptr
;
689 flushq(RD(q
), FLUSHDATA
);
690 mutex_exit(&pty
->ptc_lock
);
691 (void) putnextctl1(RD(q
), M_FLUSH
, FLUSHR
);
692 mutex_enter(&pty
->ptc_lock
);
693 mutex_enter(&tc
->t_excl
);
694 tc
->t_iflag
= cb
->c_iflag
;
695 tc
->t_cflag
= cb
->c_cflag
;
696 tc
->t_stopc
= cb
->c_cc
[VSTOP
];
697 tc
->t_startc
= cb
->c_cc
[VSTART
];
698 mutex_exit(&tc
->t_excl
);
701 * Turn the ioctl message into an ioctl ACK message.
703 iocp
->ioc_count
= 0; /* no data returned */
704 mp
->b_datap
->db_type
= M_IOCACK
;
709 tty_common_t
*tc
= &pty
->pt_ttycommon
;
712 error
= miocpullup(mp
, sizeof (struct termios
));
716 cb
= (struct termios
*)mp
->b_cont
->b_rptr
;
718 flushq(RD(q
), FLUSHDATA
);
719 mutex_exit(&pty
->ptc_lock
);
720 (void) putnextctl1(RD(q
), M_FLUSH
, FLUSHR
);
721 mutex_enter(&pty
->ptc_lock
);
722 mutex_enter(&tc
->t_excl
);
723 tc
->t_iflag
= (tc
->t_iflag
& 0xffff0000 | cb
->c_iflag
);
724 tc
->t_cflag
= (tc
->t_cflag
& 0xffff0000 | cb
->c_cflag
);
725 mutex_exit(&tc
->t_excl
);
728 * Turn the ioctl message into an ioctl ACK message.
730 iocp
->ioc_count
= 0; /* no data returned */
731 mp
->b_datap
->db_type
= M_IOCACK
;
736 tty_common_t
*tc
= &pty
->pt_ttycommon
;
739 error
= miocpullup(mp
, sizeof (struct winsize
));
743 ws
= (struct winsize
*)mp
->b_cont
->b_rptr
;
745 * If the window size changed, send a SIGWINCH.
747 mutex_enter(&tc
->t_excl
);
748 if (bcmp(&tc
->t_size
, ws
, sizeof (struct winsize
))) {
750 mutex_exit(&tc
->t_excl
);
751 mutex_exit(&pty
->ptc_lock
);
752 (void) putnextctl1(RD(q
), M_PCSIG
, SIGWINCH
);
753 mutex_enter(&pty
->ptc_lock
);
755 mutex_exit(&tc
->t_excl
);
758 * Turn the ioctl message into an ioctl ACK message.
760 iocp
->ioc_count
= 0; /* no data returned */
761 mp
->b_datap
->db_type
= M_IOCACK
;
766 * If they were just trying to drain output, that's OK.
767 * If they are actually trying to send a break it's an error.
770 error
= miocpullup(mp
, sizeof (int));
774 if (*(int *)mp
->b_cont
->b_rptr
!= 0) {
776 * Turn the ioctl message into an ioctl ACK message.
778 iocp
->ioc_count
= 0; /* no data returned */
779 mp
->b_datap
->db_type
= M_IOCACK
;
787 * The only way in which "ttycommon_ioctl" can fail is if the "ioctl"
788 * requires a response containing data to be returned to the user,
789 * and no mblk could be allocated for the data.
790 * No such "ioctl" alters our state. Thus, we always go ahead and
791 * do any state-changes the "ioctl" calls for. If we couldn't allocate
792 * the data, "ttycommon_ioctl" has stashed the "ioctl" away safely, so
793 * we just call "bufcall" to request that we be called back when we
794 * stand a better chance of allocating the data.
797 ttycommon_ioctl(&pty
->pt_ttycommon
, q
, mp
, &error
)) != 0) {
798 if (pty
->pt_wbufcid
) {
799 if (pty
->pt_ttycommon
.t_iocpending
)
800 freemsg(pty
->pt_ttycommon
.t_iocpending
);
801 pty
->pt_ttycommon
.t_iocpending
= mp
;
804 pty
->pt_wbufcid
= bufcall(datasize
, BPRI_HI
, ptslreioctl
, pty
);
805 if (pty
->pt_wbufcid
== 0) {
809 pty
->pt_ttycommon
.t_iocpending
= mp
;
816 * "ttycommon_ioctl" did most of the work; we just use the
824 * Set the "flush read" flag, so that we
825 * notify the controller if they're in packet
828 if (!(pty
->pt_send
& TIOCPKT_FLUSHREAD
)) {
829 pty
->pt_send
|= TIOCPKT_FLUSHREAD
;
830 ptcpollwakeup(pty
, 0);
836 cmd
= TIOCSETP
; /* map backwards to old codes */
842 cmd
= TIOCSETN
; /* map backwards to old codes */
848 if (pty
->pt_flags
& PF_43UCNTL
) {
850 if ((cmd
& ~0xff) == _IO('u', 0)) {
852 pty
->pt_ucntl
= (uchar_t
)cmd
& 0xff;
853 ptcpollwakeup(pty
, FREAD
);
861 if ((pty
->pt_flags
& PF_UCNTL
) &&
862 (cmd
& (IOC_INOUT
| 0xff00)) == (IOC_IN
|('t'<<8)) &&
864 pty
->pt_ucntl
= (uchar_t
)cmd
& 0xff;
865 ptcpollwakeup(pty
, FREAD
);
874 ((struct iocblk
*)mp
->b_rptr
)->ioc_error
= error
;
875 mp
->b_datap
->db_type
= M_IOCNAK
;
878 mutex_exit(&pty
->ptc_lock
);
880 mutex_enter(&pty
->ptc_lock
);
884 * Service routine for read queue.
885 * Just wakes the controller side up so it can write some more data
889 ptslrserv(queue_t
*q
)
891 struct pty
*pty
= (struct pty
*)q
->q_ptr
;
893 mblk_t
*head
= NULL
, *tail
= NULL
;
895 * Build up the link list of messages, then drop
896 * drop the lock and do putnext()
898 mutex_enter(&pty
->ptc_lock
);
900 while ((mp
= getq(q
)) != NULL
) {
901 if ((mp
->b_datap
->db_type
< QPCTL
) && !canputnext(q
)) {
914 if (q
->q_count
<= q
->q_lowat
)
915 ptcpollwakeup((struct pty
*)q
->q_ptr
, FWRITE
);
917 mutex_exit(&pty
->ptc_lock
);
930 pt_sendstop(struct pty
*pty
)
934 ASSERT(MUTEX_HELD(&pty
->ptc_lock
));
936 if ((pty
->pt_ttycommon
.t_cflag
&CBAUD
) == 0) {
937 if (pty
->pt_flags
& PF_CARR_ON
) {
939 * Let the controller know, then wake up
940 * readers/selectors and writers/selectors.
942 pty
->pt_flags
|= PF_SLAVEGONE
;
943 ptcpollwakeup(pty
, 0);
944 ptcpollwakeup(pty
, FWRITE
);
948 stop
= (pty
->pt_ttycommon
.t_iflag
& IXON
) &&
949 pty
->pt_ttycommon
.t_stopc
== CTRL('s') &&
950 pty
->pt_ttycommon
.t_startc
== CTRL('q');
952 if (pty
->pt_flags
& PF_NOSTOP
) {
954 pty
->pt_send
&= ~TIOCPKT_NOSTOP
;
955 pty
->pt_send
|= TIOCPKT_DOSTOP
;
956 pty
->pt_flags
&= ~PF_NOSTOP
;
957 ptcpollwakeup(pty
, 0);
961 pty
->pt_send
&= ~TIOCPKT_DOSTOP
;
962 pty
->pt_send
|= TIOCPKT_NOSTOP
;
963 pty
->pt_flags
|= PF_NOSTOP
;
964 ptcpollwakeup(pty
, 0);
970 * Wake up controller side. "flag" is 0 if a special packet or
971 * user control mode message has been queued up (this data is readable,
972 * so we also treat it as a regular data event; should we send SIGIO,
973 * though?), FREAD if regular data has been queued up, or FWRITE if
974 * the slave's read queue has drained sufficiently to allow writing.
977 ptcpollwakeup(struct pty
*pty
, int flag
)
979 ASSERT(MUTEX_HELD(&pty
->ptc_lock
));
983 * "Exceptional condition" occurred. This means that
984 * a "read" is now possible, so do a "read" wakeup.
987 pollwakeup(&ptcph
, POLLIN
| POLLRDBAND
);
988 if (pty
->pt_flags
& PF_ASYNC
)
989 gsignal(pty
->pt_pgrp
, SIGURG
);
993 * Wake up the parent process as there is regular
994 * data to read from slave's write queue
996 pollwakeup(&ptcph
, POLLIN
| POLLRDNORM
);
997 cv_broadcast(&pty
->pt_cv_writeq
);
998 if (pty
->pt_flags
& PF_ASYNC
)
999 gsignal(pty
->pt_pgrp
, SIGIO
);
1001 if (flag
& FWRITE
) {
1003 * Wake up the parent process to write
1004 * data into slave's read queue as the
1005 * read queue has drained enough
1007 pollwakeup(&ptcph
, POLLOUT
| POLLWRNORM
);
1008 cv_broadcast(&pty
->pt_cv_readq
);
1009 if (pty
->pt_flags
& PF_ASYNC
)
1010 gsignal(pty
->pt_pgrp
, SIGIO
);