Back to index

nagios-plugins  1.4.16
cloexec.c
Go to the documentation of this file.
00001 /* closexec.c - set or clear the close-on-exec descriptor flag
00002 
00003    Copyright (C) 1991, 2004-2006, 2009-2010 Free Software Foundation, Inc.
00004 
00005    This program is free software: you can redistribute it and/or modify
00006    it under the terms of the GNU General Public License as published by
00007    the Free Software Foundation; either version 3 of the License, or
00008    (at your option) any later version.
00009 
00010    This program is distributed in the hope that it will be useful,
00011    but WITHOUT ANY WARRANTY; without even the implied warranty of
00012    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00013    GNU General Public License for more details.
00014 
00015    You should have received a copy of the GNU General Public License
00016    along with this program.  If not, see <http://www.gnu.org/licenses/>.
00017 
00018    The code is taken from glibc/manual/llio.texi  */
00019 
00020 #include <config.h>
00021 
00022 #include "cloexec.h"
00023 
00024 #include <errno.h>
00025 #include <fcntl.h>
00026 #include <unistd.h>
00027 
00028 /* Set the `FD_CLOEXEC' flag of DESC if VALUE is true,
00029    or clear the flag if VALUE is false.
00030    Return 0 on success, or -1 on error with `errno' set.
00031 
00032    Note that on MingW, this function does NOT protect DESC from being
00033    inherited into spawned children.  Instead, either use dup_cloexec
00034    followed by closing the original DESC, or use interfaces such as
00035    open or pipe2 that accept flags like O_CLOEXEC to create DESC
00036    non-inheritable in the first place.  */
00037 
00038 int
00039 set_cloexec_flag (int desc, bool value)
00040 {
00041 #ifdef F_SETFD
00042 
00043   int flags = fcntl (desc, F_GETFD, 0);
00044 
00045   if (0 <= flags)
00046     {
00047       int newflags = (value ? flags | FD_CLOEXEC : flags & ~FD_CLOEXEC);
00048 
00049       if (flags == newflags
00050           || fcntl (desc, F_SETFD, newflags) != -1)
00051         return 0;
00052     }
00053 
00054   return -1;
00055 
00056 #else /* !F_SETFD */
00057 
00058   /* Use dup2 to reject invalid file descriptors; the cloexec flag
00059      will be unaffected.  */
00060   if (desc < 0)
00061     {
00062       errno = EBADF;
00063       return -1;
00064     }
00065   if (dup2 (desc, desc) < 0)
00066     /* errno is EBADF here.  */
00067     return -1;
00068 
00069   /* There is nothing we can do on this kind of platform.  Punt.  */
00070   return 0;
00071 #endif /* !F_SETFD */
00072 }
00073 
00074 
00075 /* Duplicates a file handle FD, while marking the copy to be closed
00076    prior to exec or spawn.  Returns -1 and sets errno if FD could not
00077    be duplicated.  */
00078 
00079 int
00080 dup_cloexec (int fd)
00081 {
00082   return fcntl (fd, F_DUPFD_CLOEXEC, 0);
00083 }