forkpty-sunos.c (2109B)
1 /* 2 * Copyright (c) 2008 Nicholas Marriott <nicm@users.sourceforge.net> 3 * 4 * Permission to use, copy, modify, and distribute this software for any 5 * purpose with or without fee is hereby granted, provided that the above 6 * copyright notice and this permission notice appear in all copies. 7 * 8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 9 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 10 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 11 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 12 * WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER 13 * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING 14 * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 15 */ 16 17 #include <sys/types.h> 18 #include <sys/ioctl.h> 19 #include <fcntl.h> 20 #include <stdlib.h> 21 #include <strings.h> 22 #include <stropts.h> 23 #include <unistd.h> 24 25 #ifndef TTY_NAME_MAX 26 #define TTY_NAME_MAX TTYNAME_MAX 27 #endif 28 29 pid_t forkpty(int *master, char *name, struct termios *tio, struct winsize *ws) 30 { 31 int slave; 32 char *path; 33 pid_t pid; 34 35 if ((*master = open("/dev/ptmx", O_RDWR|O_NOCTTY)) == -1) 36 return -1; 37 if (grantpt(*master) != 0) 38 goto out; 39 if (unlockpt(*master) != 0) 40 goto out; 41 42 if ((path = ptsname(*master)) == NULL) 43 goto out; 44 if (name != NULL) 45 strlcpy(name, path, TTY_NAME_MAX); 46 if ((slave = open(path, O_RDWR|O_NOCTTY)) == -1) 47 goto out; 48 49 switch (pid = fork()) { 50 case -1: 51 goto out; 52 case 0: 53 close(*master); 54 55 setsid(); 56 #ifdef TIOCSCTTY 57 if (ioctl(slave, TIOCSCTTY, NULL) == -1) 58 return -1; 59 #endif 60 61 if (ioctl(slave, I_PUSH, "ptem") == -1) 62 return -1; 63 if (ioctl(slave, I_PUSH, "ldterm") == -1) 64 return -1; 65 66 if (tio != NULL && tcsetattr(slave, TCSAFLUSH, tio) == -1) 67 return -1; 68 if (ioctl(slave, TIOCSWINSZ, ws) == -1) 69 return -1; 70 71 dup2(slave, 0); 72 dup2(slave, 1); 73 dup2(slave, 2); 74 if (slave > 2) 75 close(slave); 76 return 0; 77 } 78 79 close(slave); 80 return pid; 81 82 out: 83 if (*master != -1) 84 close(*master); 85 if (slave != -1) 86 close(slave); 87 return -1; 88 }