# C et C++ > C > Contribuez >  Buffer E/S rapide pour fichier [Sources]

## komput

Bonjour !

  Dans certaines applications qui doivent charger, interprter, crire des fichiers, les oprations de lecture/criture prennent parfois beaucoup de temps  ::(:  si on crit caractre par caractre par exemple.
  J'ai donc progamm une bibliothque de fonctions de lecture/criture dans des fichiers, avec un buffer. Par exemple dans le cas de l'importation d'un fichier WAV avec traitement et criture  la vole, j'ai diminu le temps d'excution par 4.

Je donne les sources ici, c'est une archive 7-zip.

 ::?:  Je me demande quand mme si ce que j'ai fait n'existe pas dj dans des librairies +/- standard, c'est quand mme pratique.

J'ai cr 2 structures de donnes, une pour le buffer en lecture et une pour le buffer en criture. Principalement parce que c'est beaucoup plus facile comme a  ::oops::  plutt que de faire un unique type de buffer qui fonctionnerait en lecture et en criture, et qui aussi consommerait un peu plus de CPU. Enfin a viendra peut-tre, mais pour l'instant moi je n'en ai pas besoin...

Les fonctions disponibles sont :
- criture/lecture d'un unique caractre
- criture/lecture d'une plage entire
- positionnement  un endroit particulier dans le fichier
- rcuprer la position courante

----------


## diogene

Quelques remarques (en commentaires) aprs une lecture rapide :



```

```

idem dans  filebufr *filebuf_openr(char *nom, int size)



```

```

idem dans filebuf_popm(void *ptr, int size, filebufr *fb)

----------


## komput

Bonjour !

En effet diogene, je m'tais aperu de la perte de mmoire mais je n'avais pas internet pendant ces vacances alors je n'ai pas encore actualis le code. Je crois bien que j'ai aussi fait une ou deux retouches plus esthtiques qu'autre chose, en tout cas ce sera dans le nouveau code. Je prviendrai quand il sera disponible.

Remplacer


```
	if(fb->file == NULL) return NULL;           // perte mémoire
```

par


```
	if(fb->file == NULL) {free(fb); return NULL;}
```

Mais pour le void* moi j'aime bien parce que a vite les warnings du compilateur. Je veux dire, la fonction n'est pas faite pour crire des char* uniquement, mais n'importe quelle donne.

Si on veut crire des donnes int ou double ou n'importe quelle structure exotique on met tranquilement :


```
filebuf_addm(&ma_donnee, sizeof(ma_donnee), fb)
```

et le tour est jou...

----------


## diogene

Le passage d'un void * en paramtre est logique. C'est l'incrment du void *,qui me gne :


```
ptr+=towrite; ....
```

 Du fait que le type (donc la taille) de l'objet point est inconnu, de combien sera incrment ptr ? En bonne logique, ce devrait tre interdit.
J'ai test sur 2 compilateurs. Le premier me donne une erreur et le second un warning (ce qui est le moins qu'on puisse attendre). 
Je n'ai pas trouv de comportement clairement dfini dans la norme sur la question de l'arithmtique mettant en cause un pointeur sur void.

Pour ces raisons, j'viterais ce genre d'criture.

----------


## komput

J'ai actualis les sources avec les modifications que j'ai indiques dans mon dernier post.
Je donne les sources ici, c'est une archive 7-zip.

Pourtant, je n'ai aucune erreur ni aucun warning de compilation (avec mingw sous windows) alors je ne me suis pas proccup du tout de la manipulation du void*. Peux-tu indiquer les compilateurs que tu as utilis ?

En tout cas si on fait comme a le problme doit tre rgl :


```
ptr=(char*)ptr+towrite;
```

Je vais me documenter un peu avant de faire la modif dans le code. En tout cas il y a plusieurs endroits  modifier.

Mais quand mme, vu que l'unit lmentaire de mmoire c'est l'octet, mon void* pointe vers un certain octet, alors en incrmentant de N on va aller N octets plus loin... et comme sizeof() renvoie un nombre d'octets, tout le monde doit tre content ! en fait je ne vois pas trop comment il faut se reprsenter ce fameux void* si tu dis que a pose problme... pour moi c'est de le transtyper en char* qui n'est pas logique parce que la nature des donnes manipules on s'en moque pas mal.

Est-ce que tu peux expliquer ? et dire dire ce qui ne va pas dans mon avis ?

----------


## diogene

Un compilateur Borland (Builder 6) indiquait une erreur. Mingw mettait un warning. Ca doit dpendre des options de warnings  la compilation si le tien tait muet sur le sujet.
Pour info, l'unit de mmoire est le byte (qui correspond souvent  un octet).

La norme dit 



> A pointer to void shall have the same representation and alignment requirements as a pointer to a character type


Mais elle ne dit pas (ou du moins je ne sais pas o) que l'arithmtique des void* est celle des char*. 

Normalement, incrmenter un pointeur augmente l'adresse concerne du nombre de bytes gal  la taille de l'objet point. Dans le cas de void *, cette taille est inconnue et on ne devrait pas faire d'arithmtique sur ces pointeurs (ni les drfrencer). C'est leur diffrence par rapport  un char*.

A ta place, j'oprerais un transtypage tant que ce point est incertain.

----------


## komput

Aah bah si c'est la norme qui le dit
J'ai mis  jour le code, toujours dispo ici en archive 7-zip.

Mais quand je compile j'active TOUS les warnings pourtant (-Wall), sous MingW et rien n'apparat  ce sujet. J'ai une version plutt rcente de MingW, celle incluse dans CodeBlocks 8.02

----------


## Melem

> J'ai une version plutt rcente de MingW, celle incluse dans CodeBlocks 8.02


Et qui est la mme que celle incluse depuis C:B 1.0  ::mouarf:: .

----------


## dapounet

> Je me demande quand mme si ce que j'ai fait n'existe pas dj dans des librairies +/- standard, c'est quand mme pratique.


Il y a les fonctions setbuf() et setvbuf().

----------


## komput

> Et qui est la mme que celle incluse depuis C:B 1.0 .


moi qui pensais qu'ils suivaient un minimum, je vais regarder a




> Il y a les fonctions setbuf() et setvbuf().


Oui, mais j'ai fait l'essai sur ma machine et a marche pas. Je veux dire mon petit code est toujours 2-3 fois plus rapide quand j'cris caractre par caractre. Je ne l'ai toujours pas test sous linux, ma machine a trop de mal. Mais si vous avez des chiffres, c'est toujours bienvenu...

----------

