linux 环境编程学习笔记 第九、十天 IO与文件映射,IO锁


寒假学习 第九、十天 (linux 高级编程)

一、IO与文件映射

1.IO的共享与效率

read与write其中数据缓冲的大小
读取数据的缓冲:getpagesize。

 

2.定位与定位读取(随机读取)

  read与write在操作时,自动移动读取位置

(1)用lseek 可以 改变读取位置

 

lseek的函数说明:		
	off_t   lseek(
			int fd,//定位文件描述符号
			off_t off,//定位位置
			int whence//定位参照点:文件开始位置/文件结束位置/文件当前位置
					   //SEEK_SET    SEEK_END  SEEK_CUR
			);
				
	返回:
		返回当前读取位置在文件中的绝对位置.

(2)pread/pwrite

 

    相当与  lseek+write=pwrite
   lseek+read =pread

 

列子:读取/proc/${pid}/mem 文件(mem是文件程序的虚拟内存文件,程序空间都是虚拟映射到这个文件中)

 

#include <stdio.h>
#include <unistd.h>
#include <fcntl.h>
#include <stdlib.h>

int a=222;

int main(int argc, const char *argv[])
{
    char filename[100];
    int data;
    sprintf(filename,"/proc/%d/mem",getpid());
    int fd=open(filename,O_RDONLY);
    if(fd==-1) printf("Open ERROR:%m"),exit(-1);

    /*
     pread(fd,&data,4,(int)&a);//这行等同于下面两行
    */
    lseek(fd,(int)&a,SEEK_SET);
    read(fd,&data,sizeof(data));

    printf("%d\n",data);

    lseek(fd,(int)&a,SEEK_SET);
    write(fd,&data,4); //虽然执行不会出错,但是a的值是不会改变的

    printf("%d\n",data);


    return 0;
}


mem只能读取,无法改变

 

(3)文件的其他操作

fstat获取文件状态

ftruncate改变文件大小

列子见下面的

(4)文件映射,内存方式写入数据

虚拟地址映射到内存,也可以映射到文件。映射到文件,我们就可以用内存方式访问文件.
 
列子:

 

#include <stdio.h>
#include <sys/mman.h>
#include <unistd.h>
#include <fcntl.h>
#include <stdlib.h>
struct stu
{
    char name[20];
    int age;
    float score;
};
int main(int argc, const char *argv[])
{
    int fd;
    struct stat st;
    struct stu *s;
    memset(&st,0,sizeof(st));
    int count;
    fd=open("map.dat",O_RDWR|O_CREAT|O_EXCL,0666);
    if(fd==-1){
        fd=open("map.dat",O_RDWR);
        if(fd==-1) printf("Open ERROR:%m"),exit(-1);
    }

    fstat(fd,&st);                    //读取文件信息
    count = st.st_size/sizeof(struct stu);

    ftruncate(fd,st.st_size+sizeof(struct stu));    //扩大文件

    s=mmap(0,st.st_size+sizeof(struct stu),                   //0表示友系统自动指定开始
            PROT_READ|PROT_WRITE,MAP_SHARED,fd,0);//原来映射到内存时要MAP_ANONYMOUS建立匿名映射,现在不用了。
    printf("input name:");
    scanf("%s",s[count].name);
    printf("input age:");
    scanf("%d",&s[count].age);
    printf("input score:");
    scanf("%f",&s[count].score);
    int i;
    printf("already in dat:\n");
    for(i=0;i<count+1;++i){
        printf("%s\t%d\t%.2f\n",s[i].name,s[i].age,s[i].score);
    }

    munmap(s,sizeof(st.st_size+sizeof(struct stu)));
    close(fd);
    

    return 0;
}

输入student的数据,并且输出

 

 

二.文件描述符号的操作(IO锁)

1.dup dup2

dup拷贝文件符号,返回系统指定的整数
dup2拷贝文件描述符号,返回用户指定的整数

2.fcntl对文件描述的属性的修改

             以后的学习会学到,到时候在详细的写。

 

  • hutao

    评论: bucuo

    2015-09-01 13:16:18          回复