15
15
# include <libutil.h>
16
16
#elif defined(__OpenBSD__) || defined(__NetBSD__) || defined(__APPLE__)
17
17
# include <util.h>
18
-
#elif !defined(__sun)
18
+
#elif defined(__sun)
19
+
# include <sys/stream.h>
20
+
# include <sys/syscall.h>
21
+
# include <fcntl.h>
22
+
# include <unistd.h>
23
+
# include <signal.h>
24
+
#else
19
25
# include <pty.h>
20
26
#endif
21
27
38
44
# include "os/pty_process_unix.c.generated.h"
39
45
#endif
40
46
47
+
#if defined(__sun) && !defined(HAVE_FORKPTY)
48
+
49
+
// this header defines STR, just as nvim.h, but it is defined as ('S'<<8),
50
+
// to avoid #undef STR, #undef STR, #define STR ('S'<<8) just delay the
51
+
// inclusion of the header even though it gets include out of order.
52
+
#include <sys/stropts.h>
53
+
54
+
static int openpty(int *amaster, int *aslave, char *name,
55
+
struct termios *termp, struct winsize *winp)
56
+
{
57
+
int slave = -1;
58
+
int master = open("/dev/ptmx", O_RDWR);
59
+
if (master == -1) {
60
+
goto error;
61
+
}
62
+
63
+
// grantpt will invoke a setuid program to change permissions
64
+
// and might fail if SIGCHLD handler is set, temporarily reset
65
+
// while running
66
+
void(*sig_saved)(int) = signal(SIGCHLD, SIG_DFL);
67
+
int res = grantpt(master);
68
+
signal(SIGCHLD, sig_saved);
69
+
70
+
if (res == -1 || unlockpt(master) == -1) {
71
+
goto error;
72
+
}
73
+
74
+
char *slave_name = ptsname(master);
75
+
if (slave_name == NULL) {
76
+
goto error;
77
+
}
78
+
79
+
slave = open(slave_name, O_RDWR|O_NOCTTY);
80
+
if (slave == -1) {
81
+
goto error;
82
+
}
83
+
84
+
// ptem emulates a terminal when used on a pseudo terminal driver,
85
+
// must be pushed before ldterm
86
+
ioctl(slave, I_PUSH, "ptem");
87
+
// ldterm provides most of the termio terminal interface
88
+
ioctl(slave, I_PUSH, "ldterm");
89
+
// ttcompat compatability with older terminal ioctls
90
+
ioctl(slave, I_PUSH, "ttcompat");
91
+
92
+
if (termp) {
93
+
tcsetattr(slave, TCSAFLUSH, termp);
94
+
}
95
+
if (winp) {
96
+
ioctl(slave, TIOCSWINSZ, winp);
97
+
}
98
+
99
+
*amaster = master;
100
+
*aslave = slave;
101
+
// ignoring name, not passed and size is unknown in the API
102
+
103
+
return 0;
104
+
105
+
error:
106
+
if (slave != -1) {
107
+
close(slave);
108
+
}
109
+
if (master != -1) {
110
+
close(master);
111
+
}
112
+
return -1;
113
+
}
114
+
115
+
static int login_tty(int fd)
116
+
{
117
+
setsid();
118
+
if (ioctl(fd, TIOCSCTTY, NULL) == -1) {
119
+
return -1;
120
+
}
121
+
122
+
dup2(fd, STDIN_FILENO);
123
+
dup2(fd, STDOUT_FILENO);
124
+
dup2(fd, STDERR_FILENO);
125
+
if (fd > STDERR_FILENO) {
126
+
close(fd);
127
+
}
128
+
129
+
return 0;
130
+
}
131
+
132
+
static pid_t forkpty(int *amaster, char *name,
133
+
struct termios *termp, struct winsize *winp)
134
+
{
135
+
int master, slave;
136
+
if (openpty(&master, &slave, name, termp, winp) == -1) {
137
+
return -1;
138
+
}
139
+
140
+
pid_t pid = fork();
141
+
switch (pid) {
142
+
case -1:
143
+
close(master);
144
+
close(slave);
145
+
return -1;
146
+
case 0:
147
+
close(master);
148
+
login_tty(slave);
149
+
return 0;
150
+
default:
151
+
close(slave);
152
+
*amaster = master;
153
+
return pid;
154
+
}
155
+
}
156
+
157
+
#endif
158
+
41
159
/// termios saved at startup (for TUI) or initialized by pty_process_spawn().
42
160
static struct termios termios_default;
43
161
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4