2014-01-28 32 views
0

當使用#pragma pack(1)時,我發現Solaris和Linux之間的結構大小有所不同。在Linux上,Derv的大小爲128,但是在Solaris上它的大小爲132.有人可以告訴我爲什麼是這種情況?我如何在Solaris上將其升至128?下面是代碼:在Solaris和Linux上使用#pragma pack(1)時的結構大小差異

#include <inttypes.h> 
#include <iostream> 
#include <stddef.h> 

#pragma pack(1) 
struct Base { 
    char   m_1; 
    uint8_t  m_2; 
    uint64_t  m_3; 
    uint64_t  m_4; 
    uint16_t  m_5; 
    uint32_t  m_6; 
    uint32_t  m_7; 
    uint64_t  m_8; 
    uint64_t  m_9; 
    uint32_t  m_10; 
    char   m_11[6]; 
}; 

struct Derv : Base { 
    int   m_1; 
    char   m_2[66]; 
    int   m_3; 
}; 
#pragma pack() 

int main() 
{ 
    std::cout << sizeof(Base) << ", " << sizeof(Derv) << std::endl; 
    std::cout << offsetof(struct Derv, m_1) 
       << ", " << offsetof(struct Derv, m_2) 
       << ", " << offsetof(struct Derv, m_3) 
       << std::endl; 
} 

編譯這樣的: 在Linux上:克++ -Wno-無效-offsetof struct_test.cpp 在Solaris:CC -g0 -xarch = SSE2 -mt struct_test.cpp

版本:

$ g ++ -v

使用內置規格。 目標:x86_64-redhat-linux 配置:../configure --prefix =/usr --mandir =/usr/share/man --infodir =/usr/share/info --with-bugurl = http://bugzilla.redhat.com/bugzilla - -enable-bootstrap --enable-shared --enable-threads = posix --enable-checking = release --with-system-zlib --enable -__ cxa_atexit --disable-libunwind-exceptions --enable-gnu-unique- object --enable-languages = c,C++,objc,obj-C++,java,fortran,ada --enable-java-awt = gtk --disable -dssi --with-java-home =/usr/lib/jvm /java-1.5.0-gcj-1.5.0.0/jre --enable-libgcj-multifile --enable-java-maintainer-mode --with-ecj-jar =/usr/share/java/eclipse-ecj.jar --disable-libjava-multilib --with-ppl --with-cloog --with-tune = generic --with-arch_32 = i686 --build = x86_64-redhat-linux 線程模型:posix gcc版本4.4。 7 20120313(Red Hat 4.4.7-3)(GCC)

的Solaris編譯:

$ CC -V

CC:孫C++ 5.9 SunOS_i386補丁124864-13 2009/05/26

感謝您的時間。

回答

1

Pragma包不保證不會有空格;充其量,這意味着編譯器會盡可能多地包裝東西。我的建議是重新排序結構中的項目從最大到最小;雖然沒有任何保證(根據定義,編譯指令是依賴於實現的),但這通常會擺脫結構打包中的「漏洞」。

可能有其他編譯器標誌可以使用,但是如果您不關心結構中項目的順序,則從大到小排序通常會以更便攜的方式進行操作。

(顯然這並不總是一個選擇 - 例如,如果你想完全在越過線或被傳遞給某些API的結構,但它適用於內部存儲。)

2

Sun C++編譯器明白該編譯指示略有不同。您還需要通過選項-misalign以使其允許較小的默認對齊。

有關更多詳細信息,請參閱Sun Studio 12: C++ User's Guide

+0

-misalign:C用戶指南SPARC。 – Prashanth

0

的Oracle Solaris Studio 12.3 C編譯器版本5.12

$ > man cc 

... 
-misalign 
     (SPARC) Obsolete. You should not use this option. Use 
     the -xmemalign=1i option instead. For a complete list 
     of obsolete options and flags, see the C User's Guide. 

因此,在Oracle Solaris Studio 12上。3 C編譯器,你應該使用

-xmemalign=1i,不-misalign

而且,也見的Oracle Solaris Studio的12.3:僅支持在2.11.19的#pragma包 http://docs.oracle.com/cd/E24457_01/html/E21990/bjaby.html#indexterm-96