Cours de C portabilité, maintenabilité et réutilisabilité

Dépendances au système

● 2 types de dépendances:
– valeurs/types (séparateur de fichier / ou \)
– comportements (casse des noms de fichiers)
● pour le 1er type, la gestion par #ifdef suffit
● pour le second, pas toujours
● chaque fois que quelque chose dépend du système, il faut l’expliciter
● exemple: longueur des noms de fichiers
– mauvaise solution: constante arbitraire
– bonne solution: utiliser la constante
FILENAME_MAX (stdio.h) adaptée au système courant

Tailles des types

● anticiper les différences d’architecture
● utiliser les constantes de limits.h
● utiliser sizeof
● exemple non portable:
void** new_ptr_array(int n) { void** ptr=malloc(n*4); if (ptr==NULL) {
/* … */
}
return ptr;
}
sur une machine 64 bits, sizeof(void*) vaut 8
● si on a besoin d’un type avec une taille en octets fixe, utiliser les constantes de stdint.h
● exemple: si on veut gérer Unicode non étendu, on a besoin d’un type non signé sur 2 octets
#include <stdint.h>
typedef uint16_t unichar;

Les sauts de lignes

● Windows: \r\n
● Linux: \n
● MacOS: \r
● il ne suffit pas que le programme soit portable
● est-ce que les données doivent l’être ?
– comment lire/écrire un fichier texte multi-plateforme ?

Endianness

● x86-like: little-endian
● Motorola-like: big-endian
● il ne suffit pas que le programme soit portable
● est-ce que les données doivent l’être ?*
– comment lire/écrire un fichier binaire contenant des int d’une façon multi-plateforme ?
– exemple de solution: encodage utf8
* (toute ressemblance avec un transparent existant serait forfuite et involontaire)

Makefile

● écrire des Makefile portables avec une variable qui dépend du système
● informations concernées:
– compilateur à utiliser
– options de compilation
– répertoires (include, lib, etc)
– commandes d’installation et de nettoyage
– noms des sorties (exemple: .exe ou pas?)
– etc.
● exemple: compilation portable d’une bibliothèque test sur une variable d’environnement pour savoir si on est sous Windows (à vérifier…) définitions dépendant du système
ifeq ($(strip $(PATHEXT)),)
SYSTEM = linux-like
else
SYSTEM = windows
endif
CC = gcc CFLAGS = -fPIC OBJS = utf8.o
ifeq ($(SYSTEM),linux-like)
CLEAN = rm -f
OUTPUT = libutf8.so
else
CLEAN = del
OUTPUT = utf8.dll
endif

instructions pour Linux
instructions pour Windows

all: $(OUTPUT)
%.o: %.c
$(CC) -c $< $(CFLAGS)
ifeq ($(SYSTEM),linux-like)
$(OUTPUT): $(OBJS)
$(CC) -shared $(OBJS) -o $(OUTPUT)
else
$(OUTPUT): $(OBJS)
$(CC) -shared $(OBJS) -Wl,–export-all-symbols -o $(OUTPUT) endif
clean:
$(CLEAN) *.o
$(CLEAN) $(OUTPUT)

Maintenabilité & réutilisabilité ou introduction au génie logiciel

Référence: L’art de la programmation UNIX, Eric S. Raymond, Vuibert
« Pour être un bon développeur en biniou, il suffit d’être bon en algo et de maîtriser la syntaxe de biniou  » Proverbe étudiant
« Quand on est con, on est con »
Georges Brassens

Qu’est-ce que le GL ?

● ensemble de bonnes pratiques et de conseils à méditer
● objectifs: développer mieux et plus vite*
– mieux=moins de bugs, code réutilisable, évolutif, etc.
– plus vite=accélérer le débogage, éviter de tout casser tout le temps, etc.

● qu’est-ce qu’un code portable ?
● indépendance vis-à-vis:
– du compilateur
– du système
– de la machine
● pourquoi le faire ?
– force à coder proprement en prenant du recul
– facilite la diffusion des applications

Cours gratuitTélécharger le cours complet

Télécharger aussi :

Laisser un commentaire

Votre adresse e-mail ne sera pas publiée. Les champs obligatoires sont indiqués avec *