fork: close all open sockets
POSIX does not include a sensible way to list or close a range of file descriptors.
So we have to loop over the full range (like from 3 to 1023), closing the file descriptors one at a time.
Or, if we have a /proc file system, we can read the list of open file descriptors in /proc/self/fd and close just those. This can be quicker than closing all possible file descriptors.
import osdef close_files(fd_min=3, fd_max=-1): if os.path.exists('/proc/self/fd'): close_files_with_procfs(fd_min, fd_max) else: close_files_exhaustively(fd_min, fd_max)def close_files_exhaustively(fd_min=3, fd_max=-1): import resource fd_top = resource.getrlimit(resource.RLIMIT_NOFILE)[1] - 1 if fd_max == -1 or fd_max > fd_top: fd_max = fd_top for fd in range(fd_min, fd_max+1): try: os.close(fd) except OSError: passdef close_files_with_procfs(fd_min=3, fd_max=-1): for nm in os.listdir("/proc/self/fd"): if nm.startswith('.'): continue fd = int(nm) if fd >= fd_min and (fd_max == -1 or fd < fd_max): try: os.close(fd) except OSError: passdef timereps(reps, func): from time import time start = time() for i in range(0, reps): func() end = time() return (end - start) / repsprint "close_files: %f" % timereps(100, lambda: close_files())print "close_files_exhaustively: %f" % timereps(100, lambda: close_files_exhaustively())print "close_files_with_procfs: %f" % timereps(1000, lambda: close_files_with_procfs())
On my system:
$ python ./close_fds.py close_files: 0.000094close_files_exhaustively: 0.010151close_files_with_procfs: 0.000039