[C/C++] エンディアンに苦しめられた

| | コメント(0) | トラックバック(0)

ファイルから読み込んだバイナリデータを扱うプログラムを改造してんだけど、読み込むファイルのデータがビッグエンディアンになってて、動かす環境はx86系でリトルエンディアンなんで。

1バイトだけのデータとか文字列は別にエンディアンを考慮する必要なし。1バイトずつ見る分にはひっくりかえりようがないから。2バイト以上の整数値は変換しないといけない。

memcpy(&shNum, pFileData, sizeof(short));
memcpy(&lNum, pFileData, sizeof(long));

とかやったら、shNum、lNumは変換必要。そもそも、memcpy関数使わないで、エンディアン変換込みのメモリコピー関数を独自で作ればいいけど。

嫌だったのは、バイナリデータが構造体を表してて、それを取得するところ。構造体は、long型(4バイト)とかのメンバをめちゃくちゃ持ってた。

struct ST_TEST
{
    long    lDataA;
    long    lDataB;
    long    lDataC;
    …
    …果てなく続く(嘘)…
}

この構造体をそのまま

memcpy(&stTestData, pFileData, sizeof(ST_TEST));

ってしたら、↓こんなバイナリデータが、

00 00 00 01  00 00 00 0A  00 00 00 02 …

それぞれ4バイト区切りでひっくり返った値になって解釈されちゃう。↓こんな風に。

lDataA:0x01000000 ※本当は0x00000001というデータで欲しい
lDataB:0x0A000000
lDataC:0x02000000

というわけで、せっかく構造体として存在してるのに、わざわざメンバ一個ずつ見てエンディアン変換かけることに。めんどい。

リトルエンディアンって、よくいう「バッドノウハウ」ってやつになるのかな。

トラックバック(0)

このブログ記事を参照しているブログ一覧: [C/C++] エンディアンに苦しめられた

このブログ記事に対するトラックバックURL: http://blog.1122soft.com/mt4/mt-tb.cgi/55

コメントする

プロフィール

  • 1983年生まれ。
    C++、PHP、JavaScript、ActionScriptで何か作ってます。

技術書

Effective C++ 原著第3版 (ADDISON-WESLEY PROFESSIONAL COMPUTING SERIES)
C++ Coding Standards―101のルール、ガイドライン、ベストプラクティス (C++ in‐depth series)
JavaScript 第5版
まるごとJavaScript & Ajax ! Vol.1
CakePHPガイドブック
CakePHP ポケットリファレンス (Pocket Reference)
Powered by Movable Type 4.01

このブログ記事について

このページは、1122が2008年5月13日 22:21に書いたブログ記事です。

ひとつ前のブログ記事は「[C++] do~while (false)が好き」です。

次のブログ記事は「[C/C++] 2038年問題」です。

最近のコンテンツはインデックスページで見られます。過去に書かれたものはアーカイブのページで見られます。

2008年10月

      1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31  

リンク