xref: /openbsd/bin/ksh/tty.c (revision 69b9f96b)
1 /*	$OpenBSD: tty.c,v 1.3 2004/12/18 20:55:52 millert Exp $	*/
2 
3 #include "sh.h"
4 #include <sys/stat.h>
5 #define EXTERN
6 #include "tty.h"
7 #undef EXTERN
8 
9 int
10 get_tty(fd, ts)
11 	int fd;
12 	TTY_state *ts;
13 {
14 	return tcgetattr(fd, ts);
15 }
16 
17 int
18 set_tty(fd, ts, flags)
19 	int fd;
20 	TTY_state *ts;
21 	int flags;
22 {
23 	return tcsetattr(fd, TCSADRAIN, ts);
24 }
25 
26 
27 /* Initialize tty_fd.  Used for saving/reseting tty modes upon
28  * foreground job completion and for setting up tty process group.
29  */
30 void
31 tty_init(init_ttystate)
32 	int init_ttystate;
33 {
34 	int	do_close = 1;
35 	int	tfd;
36 
37 	if (tty_fd >= 0) {
38 		close(tty_fd);
39 		tty_fd = -1;
40 	}
41 	tty_devtty = 1;
42 
43 	if ((tfd = open("/dev/tty", O_RDWR, 0)) < 0) {
44 
45 		if (tfd < 0) {
46 			tty_devtty = 0;
47 			warningf(FALSE,
48 				"No controlling tty (open /dev/tty: %s)",
49 				strerror(errno));
50 		}
51 	}
52 
53 	if (tfd < 0) {
54 		do_close = 0;
55 		if (isatty(0))
56 			tfd = 0;
57 		else if (isatty(2))
58 			tfd = 2;
59 		else {
60 			warningf(FALSE, "Can't find tty file descriptor");
61 			return;
62 		}
63 	}
64 	if ((tty_fd = fcntl(tfd, F_DUPFD, FDBASE)) < 0) {
65 		warningf(FALSE, "j_ttyinit: dup of tty fd failed: %s",
66 			strerror(errno));
67 	} else if (fd_clexec(tty_fd) < 0) {
68 		warningf(FALSE, "j_ttyinit: can't set close-on-exec flag: %s",
69 			strerror(errno));
70 		close(tty_fd);
71 		tty_fd = -1;
72 	} else if (init_ttystate)
73 		get_tty(tty_fd, &tty_state);
74 	if (do_close)
75 		close(tfd);
76 }
77 
78 void
79 tty_close()
80 {
81 	if (tty_fd >= 0) {
82 		close(tty_fd);
83 		tty_fd = -1;
84 	}
85 }
86