summaryrefslogtreecommitdiff
path: root/sysdeps/unix/sysv/linux/ptsname.c
diff options
context:
space:
mode:
Diffstat (limited to 'sysdeps/unix/sysv/linux/ptsname.c')
-rw-r--r--sysdeps/unix/sysv/linux/ptsname.c108
1 files changed, 108 insertions, 0 deletions
diff --git a/sysdeps/unix/sysv/linux/ptsname.c b/sysdeps/unix/sysv/linux/ptsname.c
new file mode 100644
index 0000000000..04feadd436
--- /dev/null
+++ b/sysdeps/unix/sysv/linux/ptsname.c
@@ -0,0 +1,108 @@
+/* Copyright (C) 1998 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+ Contributed by Zack Weinberg <zack@rabi.phys.columbia.edu>, 1998.
+
+ The GNU C Library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Library General Public License as
+ published by the Free Software Foundation; either version 2 of the
+ License, or (at your option) any later version.
+
+ The GNU C Library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Library General Public License for more details.
+
+ You should have received a copy of the GNU Library General Public
+ License along with the GNU C Library; see the file COPYING.LIB. If not,
+ write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+ Boston, MA 02111-1307, USA. */
+
+#include <sys/types.h>
+#include <sys/ioctl.h>
+#include <sys/stat.h>
+#include <termios.h>
+#include <string.h>
+#include <errno.h>
+#include <stdlib.h>
+
+#include "pty-internal.h"
+
+#include <stdio-common/_itoa.h>
+#include <sys/sysmacros.h>
+
+/* Given the file descriptor of a master pty, return the pathname
+ of the associated slave. */
+
+static char namebuf[PTYNAMELEN];
+extern const char __ptyname1[], __ptyname2[]; /* defined in getpt.c */
+
+char *
+ptsname (fd)
+ int fd;
+{
+ return __ptsname_r (fd, namebuf, PTYNAMELEN);
+}
+
+char *
+__ptsname_r (fd, buf, len)
+ int fd;
+ char *buf;
+ unsigned int len;
+{
+ char nbuf[PTYNAMELEN], idbuf[6];
+ int ptyno;
+ struct stat st;
+
+#ifdef TIOCGPTN
+ static int tiocgptn_works = 1;
+ if (tiocgptn_works)
+ {
+ if (!ioctl (fd, TIOCGPTN, &ptyno))
+ goto gotit;
+ else
+ {
+ if(errno != EINVAL)
+ return 0;
+ else
+ tiocgptn_works = 0;
+ }
+ }
+#endif
+ /* /dev/ptmx will make it into the kernel before 32 bit dev_t, so
+ this should be safe. */
+ if (fstat (fd, &st))
+ return 0;
+
+ ptyno = minor (st.st_rdev);
+
+#ifdef TIOCGPTN
+gotit:
+#endif
+ /* Two different possible naming schemes for pty slaves:
+ the SVr4 way. */
+
+ idbuf[5] = '\0';
+ stpcpy (stpcpy (nbuf, "/dev/pts/"),
+ _itoa_word (ptyno, &idbuf[4], 10, 0));
+ if (!stat (nbuf, &st))
+ {
+ strncpy (buf, nbuf, len);
+ return buf;
+ }
+ else
+ if (errno != ENOENT)
+ return NULL;
+
+ /* ...and the BSD way. */
+ nbuf[7] = 'y';
+ nbuf[8] = __ptyname1[ptyno / 16];
+ nbuf[9] = __ptyname2[ptyno % 16];
+ nbuf[10] = '\0';
+
+ if (stat (nbuf, &st))
+ return NULL;
+
+ strncpy (buf, nbuf, len);
+ return buf;
+}
+weak_alias (__ptsname_r, ptsname_r)