Maison >Tutoriel système >Linux >Programmation d'E/S de fichiers sous Linux

Programmation d'E/S de fichiers sous Linux

WBOY
WBOYavant
2024-03-30 21:31:11400parcourir
(1).open() ouvre le fichier
#include <sys>
#include <sys>
#include
int open(const char *pathname, int flags);
</sys></sys>

Paramètre 1 : pathname, le chemin où se trouve le fichier
Paramètre 2 : indicateurs, autorisations de fichiers, relatifs au processus du programme
Les macros courantes sont : O_WRONLY,O_RDONLY,O_RDWR,O_EXCL,O_APPEND,O_DUMP
Paramètre 3 : mode, utilisé lors de la création d'un fichier, généralement la valeur de umask.
Valeur de retour : renvoie le descripteur de fichier avec succès, sinon renvoie -1.

(2) fermer, fermer un fichier. Le paramètre est le descripteur de fichier
#include
int close(int fd);
(3) écrire, écrire des données dans le fichier
#include
ssize_t write(int fd, const void *buf, size_t count);

fd : descripteur de fichier
buf : stocke les données à écrire
count : La longueur de l'écriture, en octets
Valeur de retour : lorsque l'écriture réussit, la longueur des caractères écrits est renvoyée, sinon -1 est renvoyée.

(4) lire, lire les données dans le fichier
#include
ssize_t read(int fd, void *buf, size_t count);

fd : descripteur de fichier
buf : stocke les données à lire
count : La longueur lue, en octets
Valeur de retour : lorsque la lecture est réussie, la longueur des caractères lus est renvoyée, sinon -1 est renvoyée.
Par exemple :
#inclure

(5) rechercher, modifier le décalage du fichier
#include <sys>
#include <unistd.h off_t lseek fd offset int whence>
<p>fd : descripteur de fichier<br>
offset : le nombre d'octets à décaler. <br>
d'où : décalé de cela, la macro est définie comme suit : <br>
SEEK_END Fin du fichier<br>
SEEK_CUR position de décalage actuelle<br>
SEEK_SET Le début du fichier<br>
Remarque : Lorsque le décalage est supérieur à la longueur du fichier, un trou est généré par le décalage défini dépassant la fin du fichier et l'écriture de certaines données, qui se situent entre la fin du fichier d'origine et la nouvelle position de décalage. . C'est le trou créé. Les trous n'occupent pas d'espace disque et peuvent être utilisés : </p>
<pre class="brush:php;toolbar:false">du filename #查看文件所占实际磁盘空间
ls filename #实际文件的大小

Par exemple :

#include
#include
#include
#include <sys>
#include <sys>
#include

#define BUFF 12
int main()
{
char str1[BUFF] = "jigntikai";
char str2[BUFF] = "wojisuhihawe";

int fd;
if ( (fd = open("a.txt",O_WRONLY|O_CREAT,0744)) =
{
perror("open file fail\n");
exit(EXIT_FAILURE);
}
if( write(fd,str1,BUFF) == -1 )
{
perror("write fial fail\n");
exit(EXIT_FAILURE);
}
if( lseek(fd,1024,SEEK_END) == -1 )
{
perror("lseek fail\n");
}

write(fd,str2,BUFF);

return 0;
}
</sys></sys>
(6) l'accès détermine si le fichier est lisible, inscriptible, exécutable ou existe
#include
int access(const char *pathname, int mode);

chemin d'accès : nom du fichier
Le mode peut sélectionner les macros suivantes :
F_OK Le fichier existe-t-il ? R_OK Le fichier dispose-t-il d'une autorisation de lecture ? X_OK Le fichier a-t-il des autorisations exécutables
W_OK Le fichier a-t-il une autorisation en écriture
Valeur de retour : renvoie 0 si les paramètres de mode sont remplis et exécutés correctement, sinon -1 est renvoyé.

(7) dup ou dup2, créez un descripteur de fichier qui pointe vers la même table de fichiers
#include
int dup(int oldfd);
oldfd : descripteur de fichier original
newfd : Spécifiez la nouvelle valeur du descripteur de fichier. Si la description existe déjà, fermez-la d'abord. Si oldfd est égal à newfd, ze renvoie newfd sans le fermer.

Voici une brève introduction à la structure du noyau des fichiers : Tout d'abord, il existe une table de processus dans le système informatique. Chaque entrée de la table de processus contient une table de descripteur de fichier ouverte. Il existe de nombreuses descriptions de fichiers dans la table de description de fichier ouverte. élément de table, chaque élément comprend deux parties : un indicateur de descripteur de fichier et un pointeur de fichier, où le pointeur de fichier pointe vers une table de fichiers. La table de fichiers stocke l'indicateur d'état du fichier, c'est-à-dire s'il est lisible ou inscriptible, et le décalage. du fichier actuel. Il existe également un pointeur de nœud v, qui pointe vers une table de nœuds v. La table de nœuds v stocke principalement une série d'informations telles que le propriétaire du fichier, la longueur du fichier, le périphérique du fichier et. l'emplacement du bloc de données réel du fichier sur le disque. Peut-être que cette description n'est pas claire, alors utilisons une image pour la décrire :


Programmation dE/S de fichiers sous Linux

(8) synchronisation et fsync

(对于以下会主要是针对的内核缓冲)由于io操作会首先将数据放入内核缓冲区,所以在写的时候如果出现系统故障则缓冲区的数据可能会丢失,所以为了防止这种情况发生,以上两个函数使得内核缓冲区的数据立即写入磁盘。

#include
void sync(void);将所有缓冲排入写队列,然后立即返回
int fsync(int fd);将所有缓冲排入写队列,直到该缓冲去的数据写入磁盘后才返回。
int fdatasync(int fd);几乎和fsync函数相同,只是fdatasync(int fd)函数只影响数据部分,而fsync还会同步更新文件的属性。
(九)fcntl函数,该函数可以改变已经发开文件的性质
#include
#include
int fcntl(int fd, int cmd, ... /* arg */ );

fd:文件描述符
cmd 指明该函数执行什么功能
F_DUPFD 赋值文件描述符,功能相当于dup和dup2函数。例如:

dup(fd)等价于
fcntl(fd,F_DUPFD,0)
dup2(oldfd,newfd)等价于
close(newfd);
fcntl(oldfd,F_DUPFD,newfd);
F_GETFD 的到文件描述符标志,当前之定义一个文件描述符标志,FD_CLOSEEXEC.此时第三个参数被忽视。
F_SETFD 设置文件描述符标志,设置的值是函数的第三个参数,其一般可设置为0表示关闭,1表示打开。
F_SETFL 设置文件状态标志,其值放在函数的第三个参数,和open函数第二个参数的值一样的。
F_GETFL 得到文件状态标志。此时第三个参数被忽视。
arg 可选参数,根据第二个参数填写。
返回值:出错返回-1,否则哈返达到的标志。
例如:

#include
#include
#include
#include

int main(int argc,char * argv[])
{
int fd;
int val=3;
if( (fd = open(argv[1],O_RDWR|O_APPEND)) == -1 )//测试一下是否可以同时检测出文件的读写属性
{
exit(2);
}

if( val = fcntl(fd,F_GETFL,0) == -1 )
{
exit(1);
}
printf("%d\n",val);
printf("%d %d %d\n",O_RDONLY,O_WRONLY,O_RDWR);
int n = val & O_ACCMODE;

if( n == O_RDONLY)
printf("read\n");
if(O_WRONLY & val )
printf("write\n");
if( n == O_RDWR)
printf("read and write\n");
}
(十)最后再说一下Linux缓冲的问题吧

linux中有两个级别的缓冲:IO缓冲与内核缓冲

(1)IO缓冲:对于标准IO操作,都会有一个缓冲区,当用户想要写数据时,首先将数据写入缓冲区,待缓冲区满之后才能调用系统函数写入内核缓冲区。当用户想读取数据时,首先向内核读取一定的数据放入IO缓冲区,读操作从缓冲区中读数据,当读完IO缓冲区的数据时,才能再读取数据到IO缓冲区。

目的:减少对磁盘的读写次数,提高工作效率。

(2)内核缓冲区:操作系统内核部分也有缓冲,其与IO缓冲区是不同的,其主要区别用一张图表示:

Programmation dE/S de fichiers sous Linux

 

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration:
Cet article est reproduit dans:. en cas de violation, veuillez contacter admin@php.cn Supprimer