文件相关系统调用 open/read/write/close

一些文件相关的系统调用 例如open/read/write/close

open

int open(const char* filename, int flags, mode_t mode);
  • filename:文件名
  • flags:打开文件的方法
  • mode:若文件不存在,设置新文件的权限
  • 返回值:成功则返回文件描述符,否则返回-1

flags 用于指定文件的打开/创建模式,这个参数可由以下常量(定义于fcntl.h)通过逻辑位或逻辑构成。

O_RDONLY 只读模式
O_WRONLY 只写模式
O_RDWR 读写模式

打开/创建文件时,至少得使用上述三个常量中的一个。
以下常量是选用的:

O_APPEND 每次写操作都写入文件的末尾
O_CREAT 如果指定文件不存在,则创建这个文件
O_EXCL 如果要创建的文件已存在,则返回-1,并且修改errno的值
O_TRUNC 如果文件存在,并且以只写/读写方式打开,则清空文件全部内容(即将其长度截短为0)
O_NOCTTY 如果路径名指向终端设备,不要把这个设备用作控制终端。
O_NONBLOCK 如果路径名指向FIFO/块文件/字符文件,则把文件的打开和后继I/O

例如:

int fd = open("myfile", O_RDWR | O_CREAT, 0664);
if(fd < 0)
{
    perror("open");
    return -1;
}

创建文件”myfile”, 赋予权限664, 通过读写方式打开

read
size_t read(int fd, void* buf, size_t count);
  • 作用: 从fd里读取count大小的数据到buf中
  • 返回值: 如果顺利read()会返回实际读到的字节数,最好能将返回值与参数count 作比较,若返回的字节数比要求读取的字节数少,则有可能读到了文件尾、从管道(pipe)或终端机读取,或者是read()被信号中断了读取动作。当有错误发生时则返回-1,错误代码存入errno中,而文件读写位置则无法预期。

示例:


char *file = "hello,wrold\n";
char *buf[1024];
while(1)
{
    ssize_t s = read(fd, buf, strlen(file));
    printf("s = %d\n", s);
    if(s > 0)
    {
        printf("%s\n", buf);
    }
    else
        return -1;
}
write
ssize_t write(int fd, const void* buf, size_t nbyte);
  • 作用: 把buf中的nbyte大小的数据写入fd
  • 返回值: 写入文档的字节数(成功);-1(出错)
    write函数把buf中nbyte写入文件描述符handle所指的文档,成功时返回写的字节数,错误时返回-1.

示例:

const char* file = "hello,world\n";
char *msg = "world,hello\n";
ssize_t sw = write(fd, msg, strlen(file));

if(sw < 0)
{
    perror("write");
    return -1;
}
close
int close(int fd);
  • 返回值:成功返回0,出错返回-1 并设置errno

参数fd是要关闭的文件描述符。需要说明的是,当一个进程终止时,内核对该进程所有尚未关闭的文件描述符调用close关闭,所以即使用户程序不调用close,在终止时内核也会自动关闭它打开的所有文件。但是对于一个长年累月运行的程序(比如网络服务器),打开的文件描述符一定要记得关闭,否则随着打开的文件越来越多,会占用大量文件描述符和系统资源。

文件描述符

文件描述符在形式上是一个非负整数。实际上,它是一个索引值,指向内核为每一个进程所维护的该进程打开文件的记录表。当程序打开一个现有文件或者创建一个新文件时,内核向进程返回一个文件描述符。在程序设计中,一些涉及底层的程序编写往往会围绕着文件描述符展开。但是文件描述符这一概念往往只适用于UNIX、Linux这样的操作系统。
习惯上,

标准输入(standard input)的文件描述符是 0
标准输出(standard output)是 1
标准错误(standard error)是 2

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 。
文件描述符是由无符号整数表示的句柄,进程使用它来标识打开的文件。文件描述符与包括相关信息(如文件的打开模式、文件的位置类型、文件的初始类型等)的文件对象相关联,这些信息被称作文件的上下文。

FILE结构体
#ifndef _FILE_DEFINED
struct _iobuf
{
       char *_ptr; //文件输入的下一个位置 
    int _cnt; //当前缓冲区的相对位置 
    char *_base; //指基础位置(即是文件的其始位置) 
    int _flag; //文件标志 
    int _file; //文件的有效性验证 
    int _charbuf; //检查缓冲区状况,如果无缓冲区则不读取 
    int _bufsiz; //缓冲区大小 
    char *_tmpfname; //临时文件名
};
typedef struct _iobuf FILE;

上面结构体中的 _file 实际上是一个描述符,作为进入打开文件表索引的整数。
就是我们说的文件描述符

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值