进程要访问一个文件,必须首先获得一个文件描述符,这是通过open系统调用来完成的。文件描述符是有限的资源,所以在不用时应该及时释放。
该系统调用是用来获得欲访问文件的文件描述符,如果文件并不存在,则还可以用它来创建一个新文件。其函数为sys_open(),在fs/open.c中定义,函数如下:
asmlinkage long sys_open(const char * filename, int flags, int
mode)
{
char * tmp;
int fd, error;
#if BITS_PER_LONG != 32
flags |= O_LARGEFILE;
#endif
tmp = getname(filename);
fd = PTR_ERR(tmp);
if (!IS_ERR(tmp)) {
fd = get_unused_fd();
if (fd >= 0) {
struct file *f = filp_open(tmp, flags, mode);
error = PTR_ERR(f);
if (IS_ERR(f))
goto out_error;
fd_install(fd, f);
}
out:
putname(tmp);
}
return fd;
out_error:
put_unused_fd(fd);
fd = error;
goto out;
}
1.入口参数:
(1)filename 欲打开文件的路径
(2)flags
规定如何打开该文件,它必须取下列三个值之一:
O_RDONLY
以只读方式打开文件
O_WRONLY
以只写方式打开文件
O_RDWR
以读和写的方式打开文件
此外,还可以用或运算对下列标志值任意组合:
O_CREAT
打开文件,如果文件不存在则建立文件
O_EXCL
如果已经置O_CREAT且文件存在,则强制open()失败
O_TRUNC
将文件的长度截为0
O_APPEND
强制write()从文件尾开始
对于终端文件,这四个标志是没有任何意义的,另提供了两个新的标志:
O_NOCTTY
停止这个终端作为控制终端
O_NONBLOCK 使open()、read()、write()不被阻塞。
这些标志的符号名称在/include/asmi386/fcntl.h中定义。
(3)mode
这个参数实际上是可选的,如果用open()创建一个新文件,则要用到该参数,它用来规定对该文件的所有者、文件的用户组和系统中其他用户的访问权限位。它用或运算对下列符号常量建立所需的组合:
S_IRUSR
文件所有者的读权限位
S_IWUSR
文件所有者的写权限位
S_IXUSR
文件所有者的执行权限位
S_IRGRP
文件用户组的读权限位
S_IWGRP
文件用户组的写权限位
S_IXGRP
文件用户组的执行权限位
S_IROTH
文件其他用户的读权限位
S_IWOTH
文件其他用户的写权限位
S_IXOTH
文件其他用户的执行权限位
这些标志的符号名称在/include/linux/stat.h中定义。
2.出口参数:
返回一个文件描述符。
3.执行过程:
sys_open()主要是调用filp_open
(),这个函数也在fs/open.c中,这已在前面做过介绍。
从当前进程的files_struct结构的fd数组中找到第一个未使用项,使其指向file结构,将该项的下标作为文件描述符返回,结束;
在以上过程中,如果出错,则将分配的文件描述符、file结构收回,inode也被释放,函数返回一个负数以示出错,其中PTR_ERR()和IS_ERR()是出错处理函数,下一章将给予介绍。