文章目录
用于创建文件描述符的函数
pipe函数
可用于创建一个管道,实现进程通信
#include<unistd.h>
int pipe(int fd[2]);
//通过pipe函数创建的两个文件描述符fd[0]和fd[1]构成管道的两端,向fd[1]中写数据,fd[0]中读取数据
fd[0]只能用于从管道中读出数据,fd[1]只能向管道中写入数据
不能双向使用
-
管道写端fd[1]引用计数减少至0,则读端fd[0]的**read操作将返回0,**即读取到了文件结束标记(End Of File,EOF)
-
管道读端fd[0]引用计数减少至0,则写端fd[1]的write操作失败,并引发SIGPIPE信号
-
管道内部传输的是字节流,管道本身有容量限制,规定如果应用程序不将数据从管道读走的话,该管道最多能写入多少字节的数据,默认容量是65536字节
dup函数和dup2函数
用于标准输入重定向到一个文件,或者把标准输出重定向到一个网络连接,可通过用于复制文件描述符dup和dup2函数来实现
#include<unistd.h>
int dup(int file_descriptor);
int dup2(int file_descriptor_one,int file_descriptor_two);
用于读写数据的函数
readv函数和writev函数
readv函数将数据从文件描述符督导分散的内存快中,即分散读;
writev函数将多块分散的内存数据一并写入文件描述符中,即集中写。
#include<sys/uio.h>
ssize_t readv(int fd,const struct iovec* vector,int count);
ssize_t writev(int fd,const struct iovec* vector,int count);
sendfile函数
sendfile函数在两个文件描述符之间直接传递数据(完全在内核中操作),从而避免了内核缓冲区和用户缓冲区之间的数据拷贝,效率很高,被称为零拷贝。
#include<sys/sendfile.h>
ssize_t sendfile(int out_fd,int in_fd,off_t* offset,size_t count);
//out_fd是待写入的文件描述符,必须是一个socket
//in_fd是待读出的文件描述符,必须指向真实的文件
//offset数指定从读入文件流那个位置开始读,为空则从默认起始位置
//count指在in_fd和out_fd之间传输的字节数,成功返回字节数
mmap函数和munmap函数
- mmap函数用于申请一段内存空间,可以作为进程通信的共享内存,也可以直接将文件映射到其中
- munmap函数释放mmap创建的内存空间
#include<sys/mman.h>
void* mmap(void *start,size_t length,int prot,int flags,int fd);
int munmap(void*start,size_t length);
//start参数使用特定地址作为内存的起始地址,为NULL则系统自动分配
tee函数
在两个管道文件描述符之间复制数据 (零拷贝操作),不消耗数据
#include<fcntl.h>
ssize_t tee(int fd_in,int fd_out,size_t len,unsigned int flags);
用于控制I/O行为和属性的函数
fcntl函数(file control)
提供对文件描述符的各种控制操作
#include<fcntl.h>
int fcntl(int fd,int cmd,...);
将文件描述符设置为非阻塞状态
int setnonblocking(int fd)
{
int old_option = fcntl(fd,F_FETFL);//获取旧状态标志
int new_option = old_option | O_NONBLOCK;
fcntl(fd,F_SETFL,new_option);//设置非阻塞标志
return old_option;//返回旧状态,以便日后回复该状态标志