Les entrées/sorties (E/S ou I/O) s’appliquent sur:
- Les flux standards:
- Entree standard (stdin, n°0)
- Sortie standard (stdout, n°1)
- Sortie d’erreur (stderr, n°2)
- Des fichiers en utilisant des objets appelés descripteurs de fichiers
Exemple de redirection:
ls 2> /dev/null
: permet de rediriger le flux stdout
vers /dev/null
.
Les entrées sorties peuvent se faire en utilisant soit les fonctions de haut-niveau ou bas-niveau.
Principe général
Pour faire des entrées/sorties, on va:
- Ouvrir le fichier (en lecture ou en écriture). On obtient un descripteur
- Opérations de lectures et/ou d’écritures en utilisant le descripteur de fichier.
- Fermer le descripteur de fichier
Les lectures/écritures peuvent se faire de manière formattées ou non.
Indispensable
Il est NECESSAIRE de s’assurer que le fichier est bien écrit sur son support. Sinon des données vont être perdues/corrompues.
APIs
Fonctions haut-niveau
Ces fonctions sont fournies par la bibliothèque standard libc. Elles sont indépendantes du système d’exploitation, c’est une interface accessible sur tout les systèmes courants.
Libc fourni également les descripteurs de fichiers, qui sont de type File*
Bas niveau
A ce niveau, les fonctions sont fournies par le système et sont dépendantes de chaque système mais permettent des opérations plus spécifiques. (ex. permissions, pipelines…)
Formattées vs non-formattées
Par formatté, on entend par là que les données ont été converties d’une représentation binaire en mémoire à une représentation texte dans le fichier.
Au contraire, non-formatté signifie que les données sont au format binaire.
Exemple:
La valeur 12 représentée en mémoire sur un octet sera présentée au format texte avec 2 caractères: ‘1’ et ‘2’.
On aura donc 00001100
en binaire, et 00110001 00110010
au format texte
Résumé
Formatté = texte
Non-formatté = binaire
Descripteurs de fichiers
Work in progress
En bas niveau, descripteurs de fichiers = type int
API Haut-niveau
Documentation: page de man
Au haut-niveau, on doit importer la librairie stdio
de cette façon:
stdio = standard i/o
Pour ouvrir un fichier:
Avec les arguments suivants:
- name: nom du fichier à ouvrir
- mode: Le mode de lecture
r
: lecturew
: écriturer+
: Lecture/écriturew+
: Lecture/écriture, Le fichier est tronqué. (Le fichier sera vidé)a
: écriture en ajout à la fina+
: lecture/écriture en ajout
La fonction fopen
renverra un descripteur de fichier ou la valeur NULL si il y a une erreur.
Variantes:
fdopen
freopen
Fermer un fichier
Permet de fermer le descripteur donné.
Retournera 0
en cas de succès et EOF
en cas d’échecs
Documentation sur EOF: wikipedia.org
Exemple: Ouvrir un fichier ‘toto.txt’
En lecture:
En lecture/écriture:
Par octet:
Par bloc:
Lecture (écriture) de nmemb
objets de taille size
vers mémoire pointée par ptr
depuis (vers) le descripteur Stream
Exemple
Formatées
Méthode
sprintf
à éviter
Remarques TP
Exercice 1
Consignes:
Écrire une fonction :
qui copie le contenu du fichier de descripteur entree dans le fichier de descripteur sortie. La fonction doit retourner le nombre d’octets copiés, ou -1 en cas d’erreur. La copie peut se faire par caractère avec getc() / putc() ou bien par bloc avec fread() / fwrite().
Tester cette fonction en écrivant un programme principal l’utilisant avec la copie de deux fichiers : un fichier texte (par exemple le code source du programme), et un fichier binaire (par exemple un fichier exécutable). Vous pourrez utiliser la commande cmp(1) pour vérifier que la copie est conforme à l’original.
Code:
Bas-niveau
L’interface est fournie par le système d’exploitation. Les descripteurs sont de type int
.
En particulier:
0
pour l’entrée standard (STDIN_FILE)1
pour la sorte (STDOUT_FILE)2
pour la sortie d’erreur (STDERR_FILE)
Pipelines
TODO