Re: 構造体のメンバの記憶域の順
Fujii Hironori <fujii@chi.its.hiroshima-cu.ac.jp> writes:
> MAEDA Atusi wrote:
> > どっちも「structの先頭で同じ宣言の仕方をすれば,同じようにメンバが割り
> > 付けられる」と仮定しないと動かないでしょう.
>
> 共用体のなかの構造体だけは特別に保証されるそうです。
>
> 構造体の先頭に詰め物がされないことになっているので、
> 以下のような継承もできそうです。
ほんとだ.ちゃんと規格にありますね(ISO/IEC 9899:1999の,それぞれ
6.5.2.3 #5と.6.7.2.1 #13).
えーと,
共用体のメンバーの複数の構造体が「共通の先頭部分」を持っているとき,
共用体の完全な定義が可視である場所ならば,(今どの構造体が入っている
か不明でも)先頭部分に触って良い(6.5.2.3 #5;大意)
どの構造体へのポインタも同じ形式で,alignment requirementsも同じであ
る(6.2.5 #26)
共用体へのポインタは(適切に変換すれば)各メンバを指す.逆もまた真.
(6.7.2.1 #14)
であるわけですから,例えば共通の先頭部分を持つ構造体
struct s1 { int common; ... };
struct s2 { int common; ... };
があるとき,てきとーな共用体
union u {
struct s1 s1;
struct s2 s2;
};
が「可視である場所ならば」,
struct s1 *p1;
から
struct s2 *p2 = (struct s2 *)((union u *)p1);
と変換して s2->common を読み書きするのはかまわないわけですね.
で,上のunion uの定義なしで
struct s2 *p2 = (struct s2 *)p1;
とやってs2->commonを読み書きするのは規格ではなんと「ダメ」なようです
(6.5.2.3 EXAMPLE 3).
しかし,union uの定義のあるなしでstruct s1やs2のメンバのオフセットが変
わるなんてあり得ないと思うけどなあ… union uの定義が見えるファイルでも,
見えないファイルでも,同じstruct s1が使えるんだから.
実質(union u *)なしでも同じでしょう.ようするに,sockaddr_inやXEventで
やってることはOKと.
# いや,誰も「ダメ」と言った人はいないと思うんですが...
前田敦司
Fnews-brouse 1.9(20180406) -- by Mizuno, MWE <mwe@ccsf.jp>
GnuPG Key ID = ECC8A735
GnuPG Key fingerprint = 9BE6 B9E9 55A5 A499 CD51 946E 9BDC 7870 ECC8 A735