%ld conversion de format pour la portabilité

J'ai une base de code qui est destiné à compiler sans les avertissements et les exécuter sans aucun problème sur plusieurs architectures, toutes x86: MS-dos, Windows 32 mode console, Windows 32 en mode graphique, Linux 32 et Linux 64.

Avant d'ajouter le support de Linux 64, c'était facile. Presque toutes les données ont été déclarées, soit comme int ou de les typedefs de type BYTE, WORD, DWORD:

typedef unsigned char   BYTE;
typedef unsigned short  WORD;
typedef unsigned long   DWORD;

Lors de l'ajout de 64 bits gcc soutien, DWORD besoin d'un peu de peaufinage de rester comme une valeur 32 bits puisqu'il représente les données stockées:

//to compile DWORDs as 32 bits on 64-bit machines:
#if __x86_64__
 typedef unsigned int    DWORD;
#else
 typedef unsigned long   DWORD;
#endif

Et cela a fonctionné à merveille sur tous les environnements:

DWORD   data;
printf ("%lu", data);

Cependant, gcc -Wall maintenant se plaint des conversions de format:

warning: format ‘%ld expects argument of type long int’, but argument
         1 has type DWORD {aka unsigned int}’ [-Wformat]

En raison de la mise en forme de ce code n'—des milliers de lignes de sortie de mise en forme, je préfère ne pas la modernisation d'un type spécifique de formateur. Une question semblable a été répondu en utilisant le z modificateur:

printf ("%zu", data);

Mais qui fait de Turbo C sur MS-dos et Win32 console de faire quelque chose de bizarre: Il montre la spécification de conversion %zu en sortie au lieu de convertir quoi que ce soit.

Est-il le moyen le plus propre pour gérer la variabilité du type d'une façon qui va de pair avec le grain de printf et des types de données?

OriginalL'auteur wallyk | 2013-06-05