BIG or little endian

S

sinbad

hi,
How to find whether a given integer word is in BIG-ENDIAN or little-
endian order ... Basically there is a function fun()
which takes integer x as input parameter , without changing the
contents of 'x' , we should find if it is BIG or small endian.

thanks
sinbad

-----------------------------------

void func(int x)
{
/* do something on 'x' and find if it is BIG or little endian */
}


-----------------------------------
 
U

user923005

hi,
How to find whether a given integer word is in BIG-ENDIAN or little-
endian order ... Basically there is a function fun()
which takes integer x as input parameter , without changing the
contents of 'x' , we should find if it is BIG or small endian.

thanks
sinbad

-----------------------------------

void func(int x)
{
/* do something on 'x' and find if it is BIG or little endian */

}

-----------------------------------

Did you read the C-FAQ?
 
G

Gordon Burditt

How to find whether a given integer word is in BIG-ENDIAN or little-
endian order ... Basically there is a function fun()
which takes integer x as input parameter , without changing the
contents of 'x' , we should find if it is BIG or small endian.

No, you can't tell by looking at the bits what order they are in,
unless you've got something else known about the integer, like
it's known to be in the range of 0 .. 255.
void func(int x)
{
/* do something on 'x' and find if it is BIG or little endian */
}

Remember that there can be integers that are neither big nor little
endian. A 4-byte integer has 24 possible byte-orders.
 
T

Thomas Lumley

sinbad said:
How to find whether a given integer word is in BIG-ENDIAN or little-
endian order ... Basically there is a function fun()
which takes integer x as input parameter , without changing the
contents of 'x' , we should find if it is BIG or small endian.

This question doesn't really make sense.

You probably want to ask either

- How do I tell whether my implementation is big-endian or little-
endian (or something else)?

- How do I tell if data I get from a file or across a network has the
same endianness as my implementation?

The first question is answered in the C FAQ.

For the second, you need to know the actual intended value and then
compare it to the coded value. For example, Unicode UCS-32 files
often start with the number 0xFFFE, so if you try to read the first
two bytes and get 0xFEFF you know the endianness is wrong.

If you get to choose the file format then you can either decide in
advance on the endianness, or if you have to support both, include an
explicit field in the data telling you which way around to read the
data.

If someone else chose the data format they either did something
sensible like this (in which case, find out what) or they didn't. If
they didn't, you may have to decode the data in multiple ways and hope
that all decodings except one give clearly invalid data. This sort of
problem doesn't happen so often with numerical data and endianness any
more -- it's being replaced by the problem of guessing the encoding of
character data in non-US languages.

-thomas
 
C

cr88192

sinbad said:
hi,
How to find whether a given integer word is in BIG-ENDIAN or little-
endian order ... Basically there is a function fun()
which takes integer x as input parameter , without changing the
contents of 'x' , we should find if it is BIG or small endian.

well, assuming the value is not partly or fully symetric, here is a
possibility:
((*(char *)(&x))==(x&255))

now, some people can debate on whether this is truely valid as per the C
standard/portable code, but at least on most sane archs (say, those with 8
bit bytes...) this should work ok.

now, here is a symmetry test (assumes 32 bit integers):
!((x^(x>>24))&255)
 
K

Keith Thompson

cr88192 said:
well, assuming the value is not partly or fully symetric, here is a
possibility:
((*(char *)(&x))==(x&255))

And if I call the function with an argument of 0x12121212?

It doesn't make much sense to ask whether an integer *value* is in
big-endian or little-endian form.
 
C

Charlie Gordon

cr88192 said:
well, assuming the value is not partly or fully symetric, here is a
possibility:
((*(char *)(&x))==(x&255))

Potentially incorrect if (x & 255) > 127 and char is signed by default.
You must use (unsigned char) in the above expression.

A more reliable method relies on explicit macros from platform specific
headers, or specific code such as:

int x = 1;
if (sizeof(int) == 1) {
/* endianness does not apply */
} else
if (*(unsigned char*)&x == 1) {
/* probably little endian platform */
} else
if (*(unsigned char*)&x == 0) {
/* probably big endian platform */
} else {
/* Amazing! where did you get this actual DS9K ? */
}
now, some people can debate on whether this is truely valid as per the C
standard/portable code, but at least on most sane archs (say, those with 8
bit bytes...) this should work ok.

now, here is a symmetry test (assumes 32 bit integers):
!((x^(x>>24))&255)

Assuming 8 bit bytes and x unsigned too.
 
J

jaysome

hi,
How to find whether a given integer word is in BIG-ENDIAN or little-
endian order ... Basically there is a function fun()
which takes integer x as input parameter , without changing the
contents of 'x' , we should find if it is BIG or small endian.

If you really need to know, then you should use preprocessor defines.
Following is an example that I use that tests against preprocessor
defines that are defined by specific implementations to determine
Endianness. I have valid reasons for using this type of code because I
need to know whether I'm compiling with VC++ targeted for an x86
versus compiling with gcc targeted for a PowerPC. Such usage is
confined to a single solitary translation unit of mine, out of a total
of hundreds of translation units in my program.

#include <stdio.h>

#if defined(__LITTLEENDIAN__) && defined(__BIGENDIAN__)
#error ENDIAN multiply defined
#elif !defined(__LITTLEENDIAN__) && !defined(__BIGENDIAN__)
#error ENDIAN not defined
#endif

int main(void)
{
#ifdef __LITTLEENDIAN__
printf("Little Endian\n");
#else
printf("Big Endian\n");
#endif
return 0;
}

Best regards
 
C

cr88192

Keith Thompson said:
And if I call the function with an argument of 0x12121212?

well, that value is symetric, so it will likely fail...
It doesn't make much sense to ask whether an integer *value* is in
big-endian or little-endian form.

yes, afaik, itanium is about the only arch I know of with variable
endianess...
 
C

cr88192

Charlie Gordon said:
Potentially incorrect if (x & 255) > 127 and char is signed by default.
You must use (unsigned char) in the above expression.

yes, an obvious error.
 
K

Keith Thompson

cr88192 said:
yes, afaik, itanium is about the only arch I know of with variable
endianess...

I think there are others, but I don't think the endianness can vary
within the execution of a program.

Values don't have endianness. Types have endianness.
 
J

Joachim Schmitz

cr88192 said:
well, that value is symetric, so it will likely fail...


yes, afaik, itanium is about the only arch I know of with variable
endianess...
AFAIK MIPS is too

Bye, Jojo
 
S

slebetman

yes, afaik, itanium is about the only arch I know of with variable
endianess...

Well, afaik ix86 is about the only commonly available arch that
doesn't implement variable endianness. Families that I know supports
both big and little endian:

- PowerPC
- MIPS
- Alpha (OK, this is no longer commonly available)
- ARM (This is probably far more common than x86 since there are way
more handphones sold than PCs).

PowerPC's endianness is especially nice since you can run both big and
little endian programs on the same OS (a trick used by VirtualPC to
speed up running Windows).
 
S

slebetman

well, that value is symetric, so it will likely fail...


yes, afaik, itanium is about the only arch I know of with variable
endianess...

Well, afaik ix86 is about the only commonly available arch that
doesn't implement variable endianness. Families that I know supports
both big and little endian:

- PowerPC
- MIPS
- Alpha (OK, this is no longer commonly available)
- ARM (This is probably far more common than x86 since there are way
more handphones sold than PCs).

PowerPC's endianness is especially nice since you can run both big and
little endian programs on the same OS (a trick used by VirtualPC to
speed up running Windows).
 
P

pete

Keith said:
Types have representations. Endianness is part of that
representation.

Having representation
is an insufficient condition for having endianness.
That's a reason why "Values don't have endianness".

You can tell from the representation of (-1),
whether your C implementation uses two's complement
or something else,
but you can't tell the endianness from the representation of (-1).
 
K

Keith Thompson

pete said:
Having representation is an insufficient condition for having
endianness. That's a reason why "Values don't have endianness".

You can tell from the representation of (-1), whether your C
implementation uses two's complement or something else, but you
can't tell the endianness from the representation of (-1).

I see that the word "representation" is ambiguous. I was referring to
the representation of a type (e.g., "32 bits, big-endian,
2's-complement, bit N means [...]") as opposed to the representation
of a particular value of a type (e.g., "11001001").
 
E

Eric Sosman

Keith said:
Types have representations. Endianness is part of that
representation.

In

int i = 42;
register int r = i;

.... it is obvious that `i' and `r' have the same type.
Does it follow that they have the same endianness? If
you answer "Yes," explain how to test the endianness
of `r'.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,769
Messages
2,569,582
Members
45,065
Latest member
OrderGreenAcreCBD

Latest Threads

Top