# HG changeset patch # User Eric Blake # Date 1318893581 21600 # Node ID 27cc5b08d44289bc8ea11c51c5a3283dfdc06ade # Parent 85f5b7651b9a8ff72ff3c64ceeea25828ce8dfa2 posix_openpt: new module * modules/posix_openpt: New module. * m4/posix_openpt.m4: New file. * lib/posix_openpt.c: Likewise. * m4/stdlib_h.m4 (gl_STDLIB_H): Check for decl. (gl_STDLIB_H_DEFAULTS): Set defaults. * modules/stdlib (Makefile.am): Substitute macros. * lib/stdlib.in.h (posix_openpt): Declare. * MODULES.html.sh (systems lacking POSIX:2008): Document it. * doc/posix-functions/posix_openpt.texi (posix_openpt): Likewise. * modules/posix_openpt-tests: New test module. * tests/test-posix_openpt.c: New test. diff --git a/ChangeLog b/ChangeLog --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,18 @@ +2011-10-18 Eric Blake + + posix_openpt: new module + * modules/posix_openpt: New module. + * m4/posix_openpt.m4: New file. + * lib/posix_openpt.c: Likewise. + * m4/stdlib_h.m4 (gl_STDLIB_H): Check for decl. + (gl_STDLIB_H_DEFAULTS): Set defaults. + * modules/stdlib (Makefile.am): Substitute macros. + * lib/stdlib.in.h (posix_openpt): Declare. + * MODULES.html.sh (systems lacking POSIX:2008): Document it. + * doc/posix-functions/posix_openpt.texi (posix_openpt): Likewise. + * modules/posix_openpt-tests: New test module. + * tests/test-posix_openpt.c: New test. + 2011-10-15 Bruno Haible xstrtoll: Fix compilation failure. diff --git a/MODULES.html.sh b/MODULES.html.sh --- a/MODULES.html.sh +++ b/MODULES.html.sh @@ -2411,6 +2411,7 @@ func_module perror func_module poll func_module popen + func_module posix_openpt func_module posix_spawn func_module posix_spawnattr_destroy func_module posix_spawnattr_getflags diff --git a/doc/posix-functions/posix_openpt.texi b/doc/posix-functions/posix_openpt.texi --- a/doc/posix-functions/posix_openpt.texi +++ b/doc/posix-functions/posix_openpt.texi @@ -4,16 +4,17 @@ POSIX specification:@* @url{http://www.opengroup.org/onlinepubs/9699919799/functions/posix_openpt.html} -Gnulib module: --- +Gnulib module: posix_openpt Portability problems fixed by Gnulib: @itemize -@end itemize - -Portability problems not fixed by Gnulib: -@itemize @item This function is missing on some platforms: MacOS X 10.3, OpenBSD 3.8, Minix 3.1.8, AIX 5.1, HP-UX 11.23, IRIX 6.5, OSF/1 5.1, Solaris 9, Cygwin 1.5.x, mingw, MSVC 9, Interix 3.5, BeOS. +However, the replacement may fail with ENOSYS on some platforms. @end itemize + +Portability problems not fixed by Gnulib: +@itemize +@end itemize diff --git a/lib/posix_openpt.c b/lib/posix_openpt.c new file mode 100644 --- /dev/null +++ b/lib/posix_openpt.c @@ -0,0 +1,50 @@ +/* Open the master side of a pseudo-terminal. + Copyright (C) 2010-2011 Free Software Foundation, Inc. + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + This program 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 General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . */ + +#include + +/* Specification. */ +#include + +#include +#include + +int +posix_openpty (int flags) +{ + int master; + +#ifdef _AIX /* AIX */ + + master = open ("/dev/ptc", flags); + +#elif (defined _WIN32 || defined __WIN32__) && !defined __CYGWIN__ /* mingw */ + + /* Mingw lacks pseudo-terminals altogether. */ + master = -1; + errno = ENOSYS; + +#else /* MacOS, OpenBSD, HP-UX, IRIX, Solaris 9, Cygwin 1.5 */ + + /* Most systems that lack posix_openpt() have /dev/ptmx. */ + master = open ("/dev/ptmx", flags); + +#endif + + return master; +} + +#endif diff --git a/lib/stdlib.in.h b/lib/stdlib.in.h --- a/lib/stdlib.in.h +++ b/lib/stdlib.in.h @@ -423,6 +423,22 @@ # endif #endif +#if @GNULIB_POSIX_OPENPT@ +/* Return an FD open to the master side of a pseudo-terminal. Flags should + include O_RDWR, and may also include O_NOCTTY. */ +# if !@HAVE_POSIX_OPENPT@ +_GL_FUNCDECL_SYS (posix_openpt, int, (int flags)); +# endif +_GL_CXXALIAS_SYS (posix_openpt, int, (int flags)); +_GL_CXXALIASWARN (posix_openpt); +#elif defined GNULIB_POSIXCHECK +# undef posix_openpt +# if HAVE_RAW_DECL_POSIX_OPENPT +_GL_WARN_ON_USE (posix_openpt, "posix_openpt is not portable - " + "use gnulib module posix_openpt for portability"); +# endif +#endif + #if @GNULIB_PTSNAME@ /* Return the pathname of the pseudo-terminal slave associated with the master FD is open on, or NULL on errors. */ diff --git a/m4/posix_openpt.m4 b/m4/posix_openpt.m4 new file mode 100644 --- /dev/null +++ b/m4/posix_openpt.m4 @@ -0,0 +1,21 @@ +# posix_openpt.m4 serial 1 +dnl Copyright (C) 2011 Free Software Foundation, Inc. +dnl This file is free software; the Free Software Foundation +dnl gives unlimited permission to copy and/or distribute it, +dnl with or without modifications, as long as this notice is preserved. + +AC_DEFUN([gl_FUNC_POSIX_OPENPT], +[ + AC_REQUIRE([gl_STDLIB_H_DEFAULTS]) + + dnl Persuade Solaris to declare posix_openpt(). + AC_REQUIRE([AC_USE_SYSTEM_EXTENSIONS]) + + AC_CHECK_FUNCS_ONCE([posix_openpt]) + if test $ac_cv_have_posix_openpt != yes; then + dnl The system does not have posix_openpt. + HAVE_POSIX_OPENPT=0 + dnl Prerequisites of lib/posix_openpt.c in this case. + AC_CHECK_FUNCS([_getpty]) + fi +]) diff --git a/m4/stdlib_h.m4 b/m4/stdlib_h.m4 --- a/m4/stdlib_h.m4 +++ b/m4/stdlib_h.m4 @@ -19,10 +19,10 @@ #if HAVE_RANDOM_H # include #endif - ]], [_Exit atoll canonicalize_file_name getloadavg getsubopt grantpt mkdtemp - mkostemp mkostemps mkstemp mkstemps ptsname random_r initstat_r srandom_r - setstate_r realpath rpmatch setenv strtod strtoll strtoull unlockpt - unsetenv]) + ]], [_Exit atoll canonicalize_file_name getloadavg getsubopt grantpt + initstate_r mkdtemp mkostemp mkostemps mkstemp mkstemps posix_openpt + ptsname random_r realpath rpmatch setenv setstate_r srandom_r strtod + strtoll strtoull unlockpt unsetenv]) ]) AC_DEFUN([gl_STDLIB_MODULE_INDICATOR], @@ -50,6 +50,7 @@ GNULIB_MKOSTEMPS=0; AC_SUBST([GNULIB_MKOSTEMPS]) GNULIB_MKSTEMP=0; AC_SUBST([GNULIB_MKSTEMP]) GNULIB_MKSTEMPS=0; AC_SUBST([GNULIB_MKSTEMPS]) + GNULIB_POSIX_OPENPT=0; AC_SUBST([GNULIB_POSIX_OPENPT]) GNULIB_PTSNAME=0; AC_SUBST([GNULIB_PTSNAME]) GNULIB_PUTENV=0; AC_SUBST([GNULIB_PUTENV]) GNULIB_RANDOM_R=0; AC_SUBST([GNULIB_RANDOM_R]) @@ -76,6 +77,7 @@ HAVE_MKOSTEMPS=1; AC_SUBST([HAVE_MKOSTEMPS]) HAVE_MKSTEMP=1; AC_SUBST([HAVE_MKSTEMP]) HAVE_MKSTEMPS=1; AC_SUBST([HAVE_MKSTEMPS]) + HAVE_POSIX_OPENPT=1; AC_SUBST([HAVE_POSIX_OPENPT]) HAVE_PTSNAME=1; AC_SUBST([HAVE_PTSNAME]) HAVE_RANDOM_H=1; AC_SUBST([HAVE_RANDOM_H]) HAVE_RANDOM_R=1; AC_SUBST([HAVE_RANDOM_R]) diff --git a/modules/posix_openpt b/modules/posix_openpt new file mode 100644 --- /dev/null +++ b/modules/posix_openpt @@ -0,0 +1,28 @@ +Description: +posix_openpt() function: Open the master side of a pseudo-terminal. + +Files: +lib/posix_openpt.c +m4/posix_openpt.m4 + +Depends-on: +extensions +stdlib + +configure.ac: +gl_FUNC_POSIX_OPENPT +if test $HAVE_POSIX_OPENPT = 0; then + AC_LIBOBJ([posix_openpt]) +fi +gl_STDLIB_MODULE_INDICATOR([posix_openpt]) + +Makefile.am: + +Include: + + +License: +LGPLv2+ + +Maintainer: +Eric Blake diff --git a/modules/posix_openpt-tests b/modules/posix_openpt-tests new file mode 100644 --- /dev/null +++ b/modules/posix_openpt-tests @@ -0,0 +1,15 @@ +Files: +tests/test-posix_openpt.c +tests/signature.h +tests/macros.h + +Depends-on: +grantpt +ptsname +unlockpt + +configure.ac: + +Makefile.am: +TESTS += test-posix_openpt +check_PROGRAMS += test-posix_openpt diff --git a/modules/stdlib b/modules/stdlib --- a/modules/stdlib +++ b/modules/stdlib @@ -45,6 +45,7 @@ -e 's/@''GNULIB_MKOSTEMPS''@/$(GNULIB_MKOSTEMPS)/g' \ -e 's/@''GNULIB_MKSTEMP''@/$(GNULIB_MKSTEMP)/g' \ -e 's/@''GNULIB_MKSTEMPS''@/$(GNULIB_MKSTEMPS)/g' \ + -e 's/@''GNULIB_POSIX_OPENPT''@/$(GNULIB_POSIX_OPENPT)/g' \ -e 's/@''GNULIB_PTSNAME''@/$(GNULIB_PTSNAME)/g' \ -e 's/@''GNULIB_PUTENV''@/$(GNULIB_PUTENV)/g' \ -e 's/@''GNULIB_RANDOM_R''@/$(GNULIB_RANDOM_R)/g' \ @@ -71,6 +72,7 @@ -e 's|@''HAVE_MKOSTEMPS''@|$(HAVE_MKOSTEMPS)|g' \ -e 's|@''HAVE_MKSTEMP''@|$(HAVE_MKSTEMP)|g' \ -e 's|@''HAVE_MKSTEMPS''@|$(HAVE_MKSTEMPS)|g' \ + -e 's|@''HAVE_POSIX_OPENPT''@|$(HAVE_POSIX_OPENPT)|g' \ -e 's|@''HAVE_PTSNAME''@|$(HAVE_PTSNAME)|g' \ -e 's|@''HAVE_RANDOM_H''@|$(HAVE_RANDOM_H)|g' \ -e 's|@''HAVE_RANDOM_R''@|$(HAVE_RANDOM_R)|g' \ diff --git a/tests/test-posix_openpt.c b/tests/test-posix_openpt.c new file mode 100644 --- /dev/null +++ b/tests/test-posix_openpt.c @@ -0,0 +1,76 @@ +/* Test of posix_openpt function. + Copyright (C) 2011 Free Software Foundation, Inc. + + This program is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 3 of the License, or + (at your option) any later version. + + This program 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 General Public License for more details. + + You should have received a copy of the GNU General Public License + along with this program. If not, see . */ + +/* Written by Eric Blake , 2011. */ + +#include + +#include + +#include "signature.h" +SIGNATURE_CHECK (posix_openpt, int, (int)); + +#include +#include +#include +#include + +#if defined __sun || defined __hpux /* Solaris, HP-UX */ +# include +#endif + +#include "macros.h" + +int +main (void) +{ + int master; + int slave; + char *name; + + /* Open the master of a pseudo-terminal pair. */ + master = posix_openpt(O_RDWR | O_NOCTTY); + if (master < 0 && errno == ENOSYS) + { + fputs ("skipping: platform lacks pty support\n", stderr); + return 77; + } + + ASSERT (0 <= master); + name = ptsname (master); + ASSERT (name); + ASSERT (grantpt (master) == 0); + ASSERT (unlockpt (master) == 0); + slave = open (name, O_RDWR); + ASSERT (0 <= slave); + +#if defined __sun || defined __hpux /* Solaris, HP-UX */ + ASSERT (ioctl (slave, I_PUSH, "ptem") == 0); + ASSERT (ioctl (slave, I_PUSH, "ldterm") == 0); +# if defined __sun + ASSERT (ioctl (slave, I_PUSH, "ttcompat") == 0); +# endif +#endif + + ASSERT (isatty (slave)); + + /* Close the master side before the slave side gets closed. + This is necessary on MacOS X 10.4.11. */ + ASSERT (close (master) == 0); + ASSERT (close (slave) == 0); + + return 0; +}