compat/bswap.h: Detect endianness from XL C compiler macros
PATCH 3/3 compat/bswap.h: Detect endianness from XL C compiler macros
There is no /usr/include/endian.h equivalent on z/OS, but the compiler will define macros to indicate endianness on host and target hardware. This adds a test for these macros as a last resort for determining byte order.
--- compat/bswap.h | 4 ++++ 1 file changed, 4 insertions(+)
compat/bswap.h +4 -0
@@ -122,6 +122,10 @@ static inline uint64_t git_bswap64(uint64_t x)# define GIT_BYTE_ORDER GIT_BIG_ENDIAN# elif defined(_LITTLE_ENDIAN) && !defined(_BIG_ENDIAN)# define GIT_BYTE_ORDER GIT_LITTLE_ENDIAN +# elif defined(__THW_BIG_ENDIAN__) && !defined(__THW_LITTLE_ENDIAN__) +# define GIT_BYTE_ORDER GIT_BIG_ENDIAN +# elif defined(__THW_LITTLE_ENDIAN__) && !defined(__THW_BIG_ENDIAN__) +# define GIT_BYTE_ORDER GIT_LITTLE_ENDIAN# else # error "Cannot determine endianness"# endif
Signature · 1 line
1.9.3
compat/bswap.h static inline uint64_t git_bswap64(uint64_t x) · line 128
Quoted 12 lines · David Michael
compat/bswap.h +4
-0@@ -122,6 +122,10 @@ static inline uint64_t git_bswap64(uint64_t x)# define GIT_BYTE_ORDER GIT_BIG_ENDIAN# elif defined(_LITTLE_ENDIAN) && !defined(_BIG_ENDIAN)# define GIT_BYTE_ORDER GIT_LITTLE_ENDIAN +# elif defined(__THW_BIG_ENDIAN__) && !defined(__THW_LITTLE_ENDIAN__) +# define GIT_BYTE_ORDER GIT_BIG_ENDIAN +# elif defined(__THW_LITTLE_ENDIAN__) && !defined(__THW_BIG_ENDIAN__) +# define GIT_BYTE_ORDER GIT_LITTLE_ENDIAN
Out of curiosity, is there ever a case where _both_ are defined? That is, would:
compat/bswap.h +4 -0
@@ -122,6 +122,10 @@ static inline uint64_t git_bswap64(uint64_t x)# define GIT_BYTE_ORDER GIT_BIG_ENDIAN# elif defined(_LITTLE_ENDIAN) && !defined(_BIG_ENDIAN)# define GIT_BYTE_ORDER GIT_LITTLE_ENDIAN +# elif defined(__THW_BIG_ENDIAN__) +# define GIT_BYTE_ORDER GIT_BIG_ENDIAN +# elif defined(__THW_LITTLE_ENDIAN__) +# define GIT_BYTE_ORDER GIT_LITTLE_ENDIAN# else # error "Cannot determine endianness"# endif
be enough, or is that used to mark some other special case? Even if not, there is not much downside to the more thorough conditions you put above, but as a reviewer I wondered if there is something else going on.
-Peff
Quoted 34 lines · Jeff King
compat/bswap.h static inline uint64_t git_bswap64(uint64_t x) · line 128
Quoted 12 lines · David Michael
compat/bswap.h +4
-0@@ -122,6 +122,10 @@ static inline uint64_t git_bswap64(uint64_t x)# define GIT_BYTE_ORDER GIT_BIG_ENDIAN# elif defined(_LITTLE_ENDIAN) && !defined(_BIG_ENDIAN)# define GIT_BYTE_ORDER GIT_LITTLE_ENDIAN +# elif defined(__THW_BIG_ENDIAN__) && !defined(__THW_LITTLE_ENDIAN__) +# define GIT_BYTE_ORDER GIT_BIG_ENDIAN +# elif defined(__THW_LITTLE_ENDIAN__) && !defined(__THW_BIG_ENDIAN__) +# define GIT_BYTE_ORDER GIT_LITTLE_ENDIANOut of curiosity, is there ever a case where _both_ are defined? That is, would:
compat/bswap.h +4
-0@@ -122,6 +122,10 @@ static inline uint64_t git_bswap64(uint64_t x)# define GIT_BYTE_ORDER GIT_BIG_ENDIAN# elif defined(_LITTLE_ENDIAN) && !defined(_BIG_ENDIAN)# define GIT_BYTE_ORDER GIT_LITTLE_ENDIAN +# elif defined(__THW_BIG_ENDIAN__) +# define GIT_BYTE_ORDER GIT_BIG_ENDIAN +# elif defined(__THW_LITTLE_ENDIAN__) +# define GIT_BYTE_ORDER GIT_LITTLE_ENDIAN# else # error "Cannot determine endianness"# endif
Quoted 3 lines
be enough, or is that used to mark some other special case? Even if not, there is not much downside to the more thorough conditions you put above, but as a reviewer I wondered if there is something else going on.
I'm not 100% sure if __THW_LITTLE_ENDIAN__ will ever be defined, so I'd be okay with dropping those references completely. There is a recent version of the compiler for little endian Linux distributions, but I haven't found the documentation for it. (The product documentation still seems to only refer to the big endian Linux version.) The compiler's macro may be redundant in this case anyway, since Linux systems should have <bits/endian.h> supplying that information.
I only used both macros for completeness; the __THW_BIG_ENDIAN__ macro (defined to 1 on z/OS and AIX) is what I actually needed here. z/OS doesn't seem to have any other compile-time byte order indicator, short of testing for the OS itself.
Would you prefer the two-line patch to only test for the big endian macro, or maybe just test for __MVS__ to look at the OS?
Thanks.
David
Quoted 9 lines · David Michael
I'm not 100% sure if
__THW_LITTLE_ENDIAN__will ever be defined, so I'd be okay with dropping those references completely. There is a recent version of the compiler for little endian Linux distributions, but I haven't found the documentation for it. (The product documentation still seems to only refer to the big endian Linux version.) The compiler's macro may be redundant in this case anyway, since Linux systems should have <bits/endian.h> supplying that information.
Quoted 4 lines
I only used both macros for completeness; the
__THW_BIG_ENDIAN__macro (defined to 1 on z/OS and AIX) is what I actually needed here. z/OS doesn't seem to have any other compile-time byte order indicator, short of testing for the OS itself.
Thanks for the explanation.
Quoted 2 lines
Would you prefer the two-line patch to only test for the big endian macro,
I think that's OK, as long as the #else case barfs as it does now (i.e., doesn't silently choose little-endian).
Quoted 1 line
or maybe just test for
__MVS__to look at the OS?
If the OS's you're testing on all provide a big-endian marker like __THW_BIG_ENDIAN__, that seems preferable to me to use, as it's more explicit. We can deal with similar little-endian systems if and when somebody sees one in the wild (and your explanation that it would probably hit the Linux <bits/endian.h> check first makes sense to me).
-Peff