CSDN博客

img zhchch

POSIX标准文件I/O管理

发表于2008/9/28 12:45:00  2383人阅读

分类: Linux

    本文介绍Linux下的文件操作的系统调用方法,是我自学Linux编程的学习笔记。
1. 文件描述符
    任何打开的文件都将被分配一个唯一标识该打开文件的文件描述符,为一个大于等于0的整数。
系统启动后默认打开的文件流有标准输入设备(stdin),标准输出设备(stdout)和标准错误输出设备
(stderr),其文件描述符分别为0,1,2。以后打开的文件描述符分配依次增加,使用fileno()函数
可以返回一个流对应的文件描述符。
    函数和常量定义说明:
    在Linux输入命令man fileno,man给出的内容显示fileno是一个ANSI C的标准函数,定义在
<stdio.h>中,在FC6下通过试验得知,stdin,stdout,stderr三个常量必须用小写才能编译通过。
文件描述符定义如:int fd;
    打印文件描述符的例子:   
  1.     #include <stdio.h>
  2.     int main()
  3.     {
  4.         printf("stdin is:%d/n", fileno(stdin));
  5.         printf("stdout is:%d/n", fileno(stdout));
  6.         printf("stderr is:%d/n", fileno(stderr));
  7.         return 0;
  8.     }

    执行结果:
    stdin is:0
    stdout is:1
    stderr is:2

2. 打开文件
    对文件操作之前需要先打开文件,获得该文件的文件描述符,打开文件的系统调用为open函数。
    该函数定义头文件:
              #include <sys/types.h>
              #include <sys/stat.h>
              #include <fcntl.h>
    函数原型:int open(const char *pathname, int flag);
              int open(const char *pathname, int flag, mode_t mode);
    参数说明:
              pathname:要打开文件的文件名指针,即一个字串,如"/home/zcc/test.txt"
              flag    :打开文件的方式,使用man open发现一共有十几种打开方式,但是我们平时使用的只有几种
              mode    :如果要打开的文件不存在,open会创建文件,即使用O_CREAT打开文件,此时要用第三个参数
                      它规定了文件的权限,在设置权限时,可采用直接设置为八进制的方式,如0666,也可以使用
                      文件权限宏定义。只有第二个参数含有O_CREAT时这个参数才有用。
    返回值  :成功后返回打开文件的文件描述符(int型),失败返回-1。
    O_RDONLY:只读方式打开文件
    O_WRONLY:只写方式打开文件
    O_RDWR  :读写方式打开文件
    O_CREAT :若要打开的文件不存在,则自动建立该文件
    O_EXCL  :当和O_CREAT一起使用的时候,如果文件已经存在,那么会出错;如果文件不存在则建立文件
             如果要打开的文件为符号连接,则打开文件出错。O_EXCL不能打开NFS系统格式的文件。
    O_SYNC  :以I/O同步方式打开文件,如果打开文件的同时有其他进程对该文件进行写操作,则此次打开
             文件调用将被阻塞知道其他进程将数据写如物理介质(如磁盘)。
    O_APPEND:当读写文件时从文件尾开始移动,即写文件时以追加的方式。
    
    open的man页说当使用open的时候flag参数必须包含O_RDONLY,O_WRONLY,O_RDWR中的一种,我感觉不是这样啊?!
    
    创建文件时权限设置,文件权限宏可以通过man open来查看
    
3. 关闭文件
    完成对文件的操作一定要关闭文件以便将内容写入到文件中。使用close函数来关闭文件
    该函数定义的头文件: #include <unistd.h>
    函数原型: int close(int fd);
    参数说明:只有一个参数,即调用open函数打开文件时返回的文件描述符。
    返回值  :成功返回0,失败返回-1并设置errno标志位。
4. 创建文件
    除了使用open创建文件外,还可以使用creat创建。
    头文件定义:
            #include <sys/types.h>
            #include <sys/stat.h>
            #include <fcntl.h>
    函数原型:int creat(const char *pathname, mode_t mode);
    参数说明:
              pathname:要创建的文件的路径和文件名,如"./home/root/tmp"
              mode:     文件的权限描述
    返回值  :成功返回创建的文件的文件描述符,失败返回-1,并把错误代码设置为error
    
    open,close,creat函数的例子:
   
  1.     #include <sys/types.h>
  2.     #include <sys/stat.h>
  3.     #include <fcntl.h>
  4.     #include <unistd.h>
  5.     #include <stdio.h>
  6.     
  7.     int main(int argc, char *argv[])
  8.     {
  9.         //声明三个文件描述符,分别代表打开,打开创建,创建的文件描述符
  10.         int fd_open, fd_open_create, fd_create;
  11.         
  12.         //open exit file
  13.         if(-1 == (fd_open = open("/bin/ls", O_RDONLY)))
  14.         {
  15.             printf("open file error");
  16.         }
  17.         else
  18.         {
  19.             printf("the file's descriptor is %d/n", fd_open);
  20.         }
  21.         //open file, if it is not exit, create it
  22.         if(-1 == (fd_open_create = open("./tmp", O_CREAT | O_EXCL, 0644)))
  23.         {
  24.             printf("open create file error");
  25.         }
  26.         else
  27.         {
  28.             printf("the tmp descriptor is %d/n", fd_open_create);
  29.         }
  30.         
  31.         //create file
  32.         if(-1 == (fd_create = creat("./tmp2", 0644)))
  33.         {
  34.             printf("create file error");
  35.         }
  36.         else
  37.         {
  38.             printf("the tmp2 file descriptor is %d/n", fd_create);
  39.         }
  40.         //close files
  41.         close(fd_open);
  42.         close(fd_create);
  43.         close(fd_open_create);
  44.         
  45.         return 0;
  46.     }
5. 读文件内容
    使用read方法从一个文件中读取数据。
    头文件定义:
            #include <unistd.h>
    函数原型:ssize_t read(int fd, void *buf, size_t count);
    参数说明:
              fd:要读取的文件的文件描述符
              buf:存放读取的内容
              count:读取的字数,如果为0则read()不起作用并返回0
    返回值  :返回值类型为ssize_t,即int型,返回值为读取的字数,如果返回0表示已经达到文件尾部
              或无数据可读,文件的读写位置会随读取到的字节移动。
6. 写内容到文件
    打开文件后使用write方法向文件写入数据。
    头文件定义: #include <unistd.h>
    函数原型:   ssize_t write(int fd, const void *buf, size_t count);
    参数说明:和read基本一样。
    返回值:返回值为写入的字数。
    注意:这个函数是不带缓冲的。ANSI C的写函数带缓冲功能。
    
    读写文件内容例子:    
  1.     #include <stdio.h>
  2.     #include <unistd.h>
  3.     #include <sys/types.h>
  4.     #include <sys/stat.h>
  5.     #include <fcntl.h>
  6.     
  7.     int main(int argc, char *argv[])
  8.     {
  9.         char str[] = "I am Chinese!/n";
  10.         int fd = open("./tmp", O_RDWR);
  11.         if(-1 == fd)
  12.         {
  13.             printf("opean file error/n");
  14.             return 0;
  15.         }
  16.         if(sizeof(str) != (write(fd, str, sizeof(str))
  17.         {
  18.             printf("write file error/n");
  19.             return 0;
  20.         }
  21.         close(fd);//这里关闭不关闭都可以,最后一定要关闭。
  22.         char buf[30];
  23.         open("./tmp", O_RDONLY);
  24.         ssize_t size = read(fd, buf, sizeof(buf));
  25.         close(fd);
  26.         printf("read %d from file, they are %s/n", size, buf);
  27.     }
    
7. POSIX标准提供的其他方法
    POSIX不仅提供了基本的文件操作方法,还提供了更高级的用法,比如文件控制,锁定/解锁定,文件定位。
不过这些方法对一般的应用都不不常用的,这里只列出方法名,不做详细介绍。这部分我也没有系统学习,由于
不常用,用到了查手册。
    fcntl 对打开的文件进行控制
    lockf 锁定文件
    flock 锁定解锁定文件
    lseek 文件定位  
    lseek定义在:#include <sys/types.h>  #include <unistd.h>
    函数原型:off_t lseek(int fildes, off_t offset, int whence);
    参数说明:fildes:文件描述符
              offset:根据参考位置(第三个参数)来移动读写位置的位移数
              whence:设置的读写参考位置,取值为:
              SEEK_SET 0 //文件起始位置
              SEEK_CUR 1 //当前位置
              SEEK_END 2 //文件结束位置
    返回值: 执行成功返回目前读写位置,即举例文件头部的字节数,错误返回-1
    例子:
  1.     #include <sys/types.h>
  2.     #include <unistd.h>
  3.     #include <stdio.h>
  4.     #include <sys/stat.h>
  5.     #include <fcntl.h>
  6.     
  7.     int main()
  8.     {
  9.         int fd = open("./lseek.c", O_RDONLY);
  10.         lseek(fd, 30, SEEK_SET);
  11.         char s[100];
  12.         read(fd, s, sizeof(s));
  13.         close(fd);
  14.         printf("%s", s);
  15.     }

    
    
    
    
   
0 0

相关博文

我的热门文章

img
取 消
img