xref: /csrg-svn/usr.bin/window/wwiomux.c (revision 15872)
113923Sedward #ifndef lint
2*15872Sedward static	char *sccsid = "@(#)wwiomux.c	3.7 84/01/16";
313923Sedward #endif
413923Sedward 
513923Sedward #include "ww.h"
6*15872Sedward #include <sys/time.h>
713923Sedward 
8*15872Sedward /*
9*15872Sedward  * Multiple window IO handler.
10*15872Sedward  */
11*15872Sedward wwiomux()
1213923Sedward {
13*15872Sedward 	register struct ww *w;
14*15872Sedward 	int imask;
15*15872Sedward 	char dont_block;
16*15872Sedward 	register char *p;
17*15872Sedward 	register n;
18*15872Sedward 	char c;
19*15872Sedward 	static struct timeval tv = { 0, 0 };
2013923Sedward 
21*15872Sedward loop:
22*15872Sedward 	imask = 1;
23*15872Sedward 	dont_block = 0;
24*15872Sedward 	for (w = wwhead.ww_forw; w != &wwhead; w = w->ww_forw) {
25*15872Sedward 		if (w->ww_pty < 0)
26*15872Sedward 			continue;
27*15872Sedward 		if (w->ww_obp + w->ww_obc < w->ww_obe)
28*15872Sedward 			imask |= 1 << w->ww_pty;
29*15872Sedward 		if (w->ww_obc != 0 && !w->ww_stopped)
30*15872Sedward 			dont_block = 1;
31*15872Sedward 	}
32*15872Sedward 	if (!dont_block) {
33*15872Sedward 		wwupdate();
34*15872Sedward 		wwflush();
35*15872Sedward 	}
36*15872Sedward 	wwnselect++;
37*15872Sedward 	n = select(wwdtablesize, &imask, (int *)0, (int *)0,
38*15872Sedward 		dont_block ? &tv : (struct timeval *)0);
39*15872Sedward 	if (n < 0)
40*15872Sedward 		wwnselecte++;
41*15872Sedward 	else if (imask & 1) {
42*15872Sedward 		if (wwibc == 0)
43*15872Sedward 			p = wwibp = wwib;
44*15872Sedward 		else
45*15872Sedward 			p = wwibp + wwibc;
46*15872Sedward 		n = wwibe - p;
47*15872Sedward 		wwnread++;
48*15872Sedward 		if ((n = read(0, p, n)) > 0) {
49*15872Sedward 			wwibc += n;
50*15872Sedward 			wwnreadc += n;
51*15872Sedward 		} else if (n == 0)
52*15872Sedward 			wwnreadz++;
53*15872Sedward 		else
54*15872Sedward 			wwnreade++;
55*15872Sedward 	} else if (imask != 0 || dont_block) {
56*15872Sedward 		char first_time = 1;
57*15872Sedward 		if (n == 0)
58*15872Sedward 			wwnselectz++;
59*15872Sedward 		for (w = wwhead.ww_forw; w != &wwhead; w = w->ww_forw) {
60*15872Sedward 			if (w->ww_pty < 0)
61*15872Sedward 				continue;
62*15872Sedward 			if (imask & 1 << w->ww_pty) {
63*15872Sedward 				wwnwread++;
64*15872Sedward 				p = w->ww_obp + w->ww_obc;
65*15872Sedward 				if (p == w->ww_ob)
66*15872Sedward 					w->ww_obp++;
67*15872Sedward 				else
68*15872Sedward 					p--;
69*15872Sedward 				c = *p;
70*15872Sedward 				n = read(w->ww_pty, p, w->ww_obe - p);
71*15872Sedward 				if (n < 0) {
72*15872Sedward 					wwnwreade++;
73*15872Sedward 					(void) close(w->ww_pty);
74*15872Sedward 					w->ww_pty = -1;
75*15872Sedward 					continue;
76*15872Sedward 				} else if (n == 0) {
77*15872Sedward 					wwnwreadz++;
78*15872Sedward 				} else if (*p == TIOCPKT_DATA) {
79*15872Sedward 					wwnwreadd++;
80*15872Sedward 					wwnwreadc += n - 1;
81*15872Sedward 					w->ww_obc += n - 1;
82*15872Sedward 				} else {
83*15872Sedward 					wwnwreadp++;
84*15872Sedward 					if (*p & TIOCPKT_STOP)
85*15872Sedward 						w->ww_stopped = 1;
86*15872Sedward 					if (*p & TIOCPKT_START)
87*15872Sedward 						w->ww_stopped = 0;
88*15872Sedward 					if (*p & TIOCPKT_FLUSHWRITE) {
89*15872Sedward 						w->ww_obp = w->ww_ob;
90*15872Sedward 						w->ww_obc = 0;
91*15872Sedward 						w->ww_stopped = 0;
92*15872Sedward 					}
93*15872Sedward 				}
94*15872Sedward 				*p = c;
95*15872Sedward 			}
96*15872Sedward 			if (first_time && w->ww_obc != 0 && !w->ww_stopped) {
97*15872Sedward 				first_time = 0;
98*15872Sedward 				/* XXX */
99*15872Sedward 				n = wwwrite(w, w->ww_obp, MIN(w->ww_obc, 50));
100*15872Sedward 				if (w->ww_obc -= n)
101*15872Sedward 					w->ww_obp += n;
102*15872Sedward 				else
103*15872Sedward 					w->ww_obp = w->ww_ob;
104*15872Sedward 			}
10513923Sedward 		}
106*15872Sedward 	}
10713923Sedward }
108