endianness for bit-fields

考虑下面的一个简单的C结构体:

struct {
    unsigned char a:4;
    unsigned char b:4;
}t1;

以前一直想当然的认为,编译器会把a安排在高4位,而b在低4位。不过在小端系统上,多数编译器是将b放在高4位的;而在大端系统上比较符合我的直觉,a在高4位。不过,这种安排并非是一标准,依赖于编译器的实现,不具备可移植性。因此,如果定义的数据结构是要跨大小端系统的,可以考虑通过位操作而非bit-fields来实现。且从汇编代码中亦可以看出,编译器其实也是通过位操作来支持bit-fields的。

那么下面这个结构呢?

struct {
    unsigned short a:4;
    unsigned short b:12;
}t2;

假设t2.a = 0xa; t2.b = 0xbcd,那么在小端和大端上的内存布局通常分别为:

小端:                    大端:
+--------+--------+    +--------+--------+
| d   a  |  b  c  |    | a   b  |  c  d  |
+--------+--------+    +--------+--------+

在小端上系统上,首先是b的低4位、加a的4位,然后是b的高8位。而在大端系统上,则首先是a的4位、加b的高4位,然后是b的低8位。可以看出,如果一个结构里有跨8bits的field,如果不进行字节序的转化,是不可能保存成平台无关的数据文件的。


4 thoughts on “endianness for bit-fields

  1. 嗯,一般涉及到大小端的位域的话,会用宏分开定义吧,像这样
    struct {
    #if BIG_ENDIAN
    unsigned char a:4;
    unsigned char b:4;
    #else
    unsigned char b:4;
    unsigned char a:4;
    #endif
    };

  2. 超级感谢你的辛苦劳动。但是,有个问题,我看这个网页about的时候,里面介绍你自己和介绍关于sunpin的时候,都写的E文。 我想说的是,用sunpin的大部分都是会中文的华人和小部分学中文的外国人。。。。那些介绍没必要用英文写吧。毕竟,sunpin的用户群以认识中文的为主。。一点废话,嘿嘿~~~

    最后,再次感谢你的辛苦

  3. 您可以到sunpinyin.org上的wiki,看到更多关于SunPinyin的中文介绍,包括详细的代码分析文档等 :)

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

To submit your comment, click the image below where it asks you to...
Clickcha - The One-Click Captcha