没有缓冲的I/O
1、open函数
int open(const char *pathname, int flag, .../* mode_t mode*/)
文件打开成功返回文件描述符(非负数),失败返回-1
flag常用的选项有:
O_RDONLY 只读打开
O_WRONLY 只写打开
O_RDWR 读写打开
以上三个选项必须指定且只能指定一个
O_APPEND 写的时候追加在末尾
O_CREAT 文件不存在就创建它。此时需要用第三个参数mode指明权限
O_EXCL 测试文件是否存在,如果不存在就创建。测试和创建为原子操作
O_TRUNC 如果文件存在则将其长度截断为0
O_NOCTTY
O_NONBLOCK
O_DSYNC
O_RSYNC
O_SYNC 使每次write都等到物理I/O操作完成
2、creat函数
int creat(cosnt char *pathname, mode_t mode);
它等效于 open(pathname, O_WRNOLY | O_CREAT | O_TRUNC, mode).
3、close函数
int close(int filedes)
可以不显示的关闭文件,进程结束的时候会自动关闭
4、lseek函数
off_t lseek(int filedes, off_t offset, int wherece)
执行成功返回新的偏移量,失败返回-1.
wherece的取值有:
SEEK_SET 开始处
SEEK_CUR 当前位置
SEEK_END 末尾
偏移量offset可正可负,lseek仅将当前的文件偏移量记录在内核中,它并不引起任何I/O操作。
5、具有空洞的文件
在使用的lseek的时候,文件偏移量可以大于文件的当期的长度,这时,对文件的下一次写时,就会在中间构成一个空洞,这个空洞不在磁盘上占用存储区。如图0 那一段是空洞
as1321435 |
0000000 |
4654765887 |
6、read函数
ssize_t read(int filedes, void *buf ,size_t nbytes)
成功,返回读到的字节数,若已到文件结尾则返回0,出错返回-1
7、write函数
ssize_t write(int filedes, const void *buf, size_t nbytes)
成功:返回已写的字节数,出错返回-1
8、文件共享
内核使用三种数据结构表示打开的文件。
(1)文件描述符表,包括文件表述符标志和指向文件表项的指针
(2)文件表,包括文件状态,当前的偏移量,V节点指针。
(3)V节点表,包含文件类型和对此文件进行各种操作的函数的指针
当两个独立的进程各自打开了同一个文件的时候,每个进程都得到一个文件表项,但是V节点只有一个。
9、dup函数和dup2函数
int dup(int filedes);
int dup2(int filedes, int filedes2);
dup是复制文件描述符filedes,dup2是复制filedes,并新的文件描述符的名字改为filedes2并关闭filedes2.
成功,返回新的文件描述符,出错返回-1
10、sync ,fsync ,fdatasync
当将数据写入文件时,内核通常先将数据复制到其中一个缓冲区中,知直到缓冲区写满才把该缓冲排入输出队列,然后待其到达对首时,才进行实际的I/O操作,这种输出方式称为延迟写,但是这种延迟可能会造成文件更新内容的丢失。为了避免这种情况 unix提供了sync ,fsync ,fdatasync这三个函数。
int fsync(int filedes);
int fdatasync(int filedes);
void sync(void);
sync函数只是将所有修改过的块缓冲区排入写队列,然后就返回。它并不等待实际写磁盘操作结束。
fsync对filedes指定的单一文件起作用,并且等待写磁盘操作结束后才返回。
fdatasync除了具备fsync的功能外还会同步更新文件的属性。
11、fcntl函数
int fcntl(int filedes, int cmd , .../*int arg*/);
功能是改变已经打开的文件的性质,成功返回值依赖于cmd,出错返回-1
cmd:
F_DUPFD 复制一个现有的描述符,新文件描述符作为返回值,新描述符filedes共享同一文件表项。
F_GETFD 返回filedes的文件描述符标志。
F_SETFD对filedes设置文件描述符标志,新标志位arg
F_GETFL 返回filedes的文件状态标志。
F_SETFL 设置文件状态标志,用arg传入
F_GETOWN 取当前接受 SIGIO和SIGURG信号的进程ID或进程组ID
F_SETOWN