Annotation of embedaddon/sudo/compat/closefrom.c, revision 1.1.1.1

1.1       misho       1: /*
                      2:  * Copyright (c) 2004-2005, 2007, 2010
                      3:  *     Todd C. Miller <Todd.Miller@courtesan.com>
                      4:  *
                      5:  * Permission to use, copy, modify, and distribute this software for any
                      6:  * purpose with or without fee is hereby granted, provided that the above
                      7:  * copyright notice and this permission notice appear in all copies.
                      8:  *
                      9:  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
                     10:  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
                     11:  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
                     12:  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
                     13:  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
                     14:  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
                     15:  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
                     16:  */
                     17: 
                     18: #include <config.h>
                     19: 
                     20: #include <sys/types.h>
                     21: #include <sys/param.h>
                     22: #include <unistd.h>
                     23: #include <stdio.h>
                     24: #ifdef STDC_HEADERS
                     25: # include <stdlib.h>
                     26: # include <stddef.h>
                     27: #else
                     28: # ifdef HAVE_STDLIB_H
                     29: #  include <stdlib.h>
                     30: # endif
                     31: #endif /* STDC_HEADERS */
                     32: #include <fcntl.h>
                     33: #ifdef HAVE_DIRENT_H
                     34: # include <dirent.h>
                     35: # define NAMLEN(dirent) strlen((dirent)->d_name)
                     36: #else
                     37: # define dirent direct
                     38: # define NAMLEN(dirent) (dirent)->d_namlen
                     39: # ifdef HAVE_SYS_NDIR_H
                     40: #  include <sys/ndir.h>
                     41: # endif
                     42: # ifdef HAVE_SYS_DIR_H
                     43: #  include <sys/dir.h>
                     44: # endif
                     45: # ifdef HAVE_NDIR_H
                     46: #  include <ndir.h>
                     47: # endif
                     48: #endif
                     49: 
                     50: #include "missing.h"
                     51: 
                     52: #ifndef HAVE_FCNTL_CLOSEM
                     53: # ifndef HAVE_DIRFD
                     54: #   define closefrom_fallback  closefrom
                     55: # endif
                     56: #endif
                     57: 
                     58: /*
                     59:  * Close all file descriptors greater than or equal to lowfd.
                     60:  * This is the expensive (ballback) method.
                     61:  */
                     62: void
                     63: closefrom_fallback(int lowfd)
                     64: {
                     65:     long fd, maxfd;
                     66: 
                     67:     /*
                     68:      * Fall back on sysconf() or getdtablesize().  We avoid checking
                     69:      * resource limits since it is possible to open a file descriptor
                     70:      * and then drop the rlimit such that it is below the open fd.
                     71:      */
                     72: #ifdef HAVE_SYSCONF
                     73:     maxfd = sysconf(_SC_OPEN_MAX);
                     74: #else
                     75:     maxfd = getdtablesize();
                     76: #endif /* HAVE_SYSCONF */
                     77:     if (maxfd < 0)
                     78:        maxfd = OPEN_MAX;
                     79: 
                     80:     for (fd = lowfd; fd < maxfd; fd++)
                     81:        (void) close((int) fd);
                     82: }
                     83: 
                     84: /*
                     85:  * Close all file descriptors greater than or equal to lowfd.
                     86:  * We try the fast way first, falling back on the slow method.
                     87:  */
                     88: #ifdef HAVE_FCNTL_CLOSEM
                     89: void
                     90: closefrom(int lowfd)
                     91: {
                     92:     if (fcntl(lowfd, F_CLOSEM, 0) == -1)
                     93:        closefrom_fallback(lowfd);
                     94: }
                     95: #else
                     96: # ifdef HAVE_DIRFD
                     97: void
                     98: closefrom(int lowfd)
                     99: {
                    100:     struct dirent *dent;
                    101:     DIR *dirp;
                    102:     char *endp;
                    103:     long fd;
                    104: 
                    105:     /* Use /proc/self/fd directory if it exists. */
                    106:     if ((dirp = opendir("/proc/self/fd")) != NULL) {
                    107:        while ((dent = readdir(dirp)) != NULL) {
                    108:            fd = strtol(dent->d_name, &endp, 10);
                    109:            if (dent->d_name != endp && *endp == '\0' &&
                    110:                fd >= 0 && fd < INT_MAX && fd >= lowfd && fd != dirfd(dirp))
                    111:                (void) close((int) fd);
                    112:        }
                    113:        (void) closedir(dirp);
                    114:     } else
                    115:        closefrom_fallback(lowfd);
                    116: }
                    117: #endif /* HAVE_DIRFD */
                    118: #endif /* HAVE_FCNTL_CLOSEM */

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>