是否有一种编程方法来检测您使用的是大端序还是小端序体系结构?我需要能够编写将在英特尔或PPC系统上执行的代码,并使用完全相同的代码(即,没有条件编译)。


当前回答

声明一个int变量:

int variable = 0xFF;

现在使用char*指针指向它的各个部分,并检查这些部分中有什么。

char* startPart = reinterpret_cast<char*>( &variable );
char* endPart = reinterpret_cast<char*>( &variable ) + sizeof( int ) - 1;

根据哪一个指向0xFF字节,现在您可以检测到字节顺序。这需要sizeof(int) > sizeof(char),但对于所讨论的平台绝对是正确的。

其他回答

你可以通过设置int和屏蔽位来做到这一点,但可能最简单的方法是使用内置的网络字节转换操作(因为网络字节顺序总是大端序)。

if ( htonl(47) == 47 ) {
  // Big endian
} else {
  // Little endian.
}

一点点摆弄可能会更快,但这种方法简单,直接,几乎不可能搞砸。

参见Endianness - c级代码说明。

// assuming target architecture is 32-bit = 4-Bytes
enum ENDIANNESS{ LITTLEENDIAN , BIGENDIAN , UNHANDLE };


ENDIANNESS CheckArchEndianalityV1( void )
{
    int Endian = 0x00000001; // assuming target architecture is 32-bit    

    // as Endian = 0x00000001 so MSB (Most Significant Byte) = 0x00 and LSB (Least     Significant Byte) = 0x01
    // casting down to a single byte value LSB discarding higher bytes    

    return (*(char *) &Endian == 0x01) ? LITTLEENDIAN : BIGENDIAN;
} 

我不喜欢基于类型双关的方法——它经常会被编译器警告。这正是工会存在的意义!

bool is_big_endian(void)
{
    union {
        uint32_t i;
        char c[4];
    } bint = {0x01020304};

    return bint.c[0] == 1;
}

这个原则等同于其他人建议的类型大小写,但这更清楚——并且根据C99,它保证是正确的。与直接指针强制转换相比,GCC更喜欢这种方法。

这也比在编译时修复字节序要好得多——对于支持多架构的操作系统(例如Mac OS X上的胖二进制),这对ppc/i386都适用,否则很容易把事情搞砸。

这是未经测试的,但在我看来,这应该是可行的。因为在小端序上是0x01,在大端序上是0x00。

bool runtimeIsLittleEndian(void)
{
    volatile uint16_t i=1;
    return ((uint8_t*)&i)[0]==0x01; // 0x01=little, 0x00=big
}

要了解更多细节,你可能想要查看这篇codeproject文章Endianness的基本概念:

如何在运行时动态测试Endian类型? 正如《计算机》中解释的那样 动画FAQ,可以使用 下面的函数看看你的代码 是在小端还是大端运行 系统:崩溃 定义BIG_ENDIAN 0 #定义LITTLE_ENDIAN

int TestByteOrder()
{
   short int word = 0x0001;
   char *byte = (char *) &word;
   return(byte[0] ? LITTLE_ENDIAN : BIG_ENDIAN);
}

这段代码将值0001h赋给a 16位整数。然后是char指针 第一次分配给点 的(最低有效)字节 整数值。的第一个字节 整数是0x01h,然后系统 是Little-Endian (0x01h在 最低或最不重要, 地址)。如果是0x00h,则 系统是大端的。