文件描述符
内核利用文件描述符来访问文件。文件描述符是非负整数。打开现存文件或新建文件时,内核会返回一个文件描述符。读写文件也需要使用文件描述符来指定待读写的文件。
POSIX 定义了 STDIN_FILENO、STDOUT_FILENO 和 STDERR_FILENO 来代替 0、1、2。这三个符号常量的定义位于头文件 unistd.h。 当然,这三个常量只是文件描述符的一部分。
文件描述符的有效范围是 0 到 OPEN_MAX。一般来说,每个进程最多可以打开 64 个文件(0 — 63)。对于 FreeBSD 5.2.1、Mac OS X 10.3 和 Solaris 9 来说,每个进程最多可以打开文件的多少取决于系统内存的大小,int 的大小,以及系统管理员设定的限制。Linux 2.4.22 强制规定最多不能超过 1,048,576 。
文件描述符是由无符号整数表示的句柄,进程使用它来标识打开的文件。文件描述符与包括相关信息(如文件的打开模式、文件的位置类型、文件的初始类型等)的文件对象相关联,这些信息被称作文件的上下文。
进程获取文件描述符最常见的方法是通过本机子例程open或create获取或者通过从父进程继承。后一种方法允许子进程同样能够访问由父进程使用的文
件。文件描述符对于每个进程一般是唯一的。当用fork子例程创建某个子进程时,该子进程会获得其父进程所有文件描述符的副本,这些文件描述符在执行
fork时打开。在由fcntl、dup和dup2子例程复制或拷贝某个进程时,会发生同样的复制过程。
文件描述符的好处主要有两个:
1. 基于文件描述符的I/O操作兼容POSIX标准。在UNIX、Linux的系统调用中,大量的系统调用都是依赖于文件描述符。
2. 在Linux系列的操作系统上,由于Linux的设计思想便是把一切设备都视作文件。因此,文件描述符为在该系列平台上进行设备相关的编程实际上提供了一个统一的方法。
那么,如何在不同平台上定义文件描述符的数量呢?
1.Linux
管理用户可以在etc/security/limits.conf配置文件中设置他们的文件描述符极限,如下例所示。
softnofile1024
hardnofile4096
系统级文件描述符极限还可以通过将以下三行添加到/etc/rc.d/rc.local启动脚本中来设置:
echo4096>/proc/sys/fs/file-max
echo16384>/proc/sys/fs/inode-max
2.Windows
在Windows操作系统上,文件描述符被称作文件句柄。在Windows2000服务器上,打开文件的句柄极限设置为16,384。此数量可以在任务管理器的性能摘要中监视。
在Linux中,以下函数与文件描述符有关:
文件描述符的生成
open(), open64(),
creat(), creat64(),
socket(),socketpair(),pipe()
与单一文件描述符相关的操作
read(), write()
recv(), send()
recvmsg(), sendmsg()
sendfile()
lseek(), lseek64()
fstat(), fstat64()
fchmod()
fchown()
与复数文件描述符相关的操作
select(), pselect()
poll()
与文件描述符表相关的操作
close()
dup()
dup2()
fcntl (F_DUPFD)
fcntl (F_GETFD and F_SETFD)
改变进程状态的操作
fchdir()
mmap()
与文件加锁的操作
flock()
fcntl (F_GETLK, F_SETLK and F_SETLKW)
lockf()
与套接字相关的操作
connect()
bind()
listen()
accept()
getsockname()
getpeername()
getsockopt() setsockopt()
shutdown()