Détecter l'Endianness

Je suis en train d'essayer de créer un C code source qui gère correctement les I/O quel que soit le boutisme du système cible.

J'ai sélectionné l'option "little endian", comme ma I/O de la convention, ce qui signifie que, pour big endian CPU, j'ai besoin de convertir des données lors de l'écriture ou de la lecture.

La Conversion n'est pas la question. Le problème que j'ai le visage est de détecter l'endianness, de préférence au moment de la compilation (depuis le CPU ne change pas boutisme dans le milieu de l'exécution...).

Jusqu'à maintenant, j'ai été en utilisant ce :

#if __BYTE_ORDER__ == __ORDER_LITTLE_ENDIAN__
...
#else
...
#endif

Il est connu comme un GCC pré-défini de macros et Visual semble le comprendre aussi.

Cependant, j'ai reçu le rapport que la vérification échoue pour certains big_endian systèmes (PowerPC).

Donc, je suis à la recherche d'une solution infaillible, qui assure que l'endianess est correctement détecté, quel que soit le compilateur et le système cible. eh bien, la plupart d'entre eux au moins...

[Edit] : la Plupart des solutions proposées s'appuient sur "l'exécution des tests de temps". Ces tests peuvent parfois être bien évalué par les compilateurs lors de la compilation, et donc pas de coût réel les performances d'exécution.

Cependant, la ramification avec une sorte de << if (0) { ... } else { ... } >> n'est pas suffisant. Dans le code actuel de la mise en œuvre, de variables et de fonctions déclaration dépendent big_endian de détection. On ne peut pas être changé avec une instruction if.

Bien, évidemment, il est tomber en arrière plan, qui consiste à réécrire le code...

Je préfère l'éviter, mais, eh bien, il ressemble à une diminution de l'espérance...

[Edit 2] : j'ai testé "au moment de l'exécution des tests", de profondément modifier le code. Bien qu'ils fassent leur travail correctement, ces tests ont aussi un impact sur les performances.

Je m'attendais à ce que, depuis les tests ont prévisible de sortie, le compilateur pourrait éliminer les mauvaises branches. Mais malheureusement, il ne fonctionne pas tout le temps. MSVC est bon compilateur, et réussit à éliminer les mauvaises branches, mais GCC a des résultats mitigés, selon les versions, genre de tests, et avec plus d'impact sur les systèmes 64 bits que sur 32 bits.

C'est étrange. Et cela signifie aussi que le moment de l'exécution des tests ne peut être assuré d'être traité par le compilateur.

Modifier 3 : Ces jours-ci, je suis en utilisant une constante de compilation de l'union, s'attendant à le compilateur à résoudre pour un oui clair et net/pas de signal.
Et ça marche plutôt bien :
https://godbolt.org/g/DAafKo

source d'informationauteur Cyan | 2012-01-23