エンディアン


Rev.3を表示中。最新版はこちら

エンディアンとは、CPUに依存する複数バイトデータによるメモリー上の配置の事をいい、ビッグエンディアンとリトルエンディアン(ミドルエンディアンというのもあるらしいです。)とがあります。X86はリトルエンディアンです。例えば0x1234は、アドレス0からメモリ上に配置すると、ビッグエンディアンではアドレス0に0x12,アドレス1には0x34となりますが、リトルエンディアンでは、アドレス0に 0x34、アドレス1に0x12と逆転します。

どっちがどっちとよくこんがらがるので、私自身の解釈で、アドレスの大きい方で終わる方をビッグエンディアンで、アドレスの小さい方で終わるのをリトルビッグエンディアンと理解しています。(命名そのまままですが。)

この違いは、同じシステム下で動作するなら問題ないのですが、異種間に渡って共通するデータなら問題となります。そこでは個々にエンディアンを統一することで、OSレベルでその違いを吸収する事で解決しちます。
ext2/3ではリトルエンディアンとしているようです。(通信ではビッグエンディアンのようです。ネットからの情報ですが。)

ext2_next_entry関数は、ext2ファイルシステムのディレクトリー内の、引数で指定するエントリーext2_dirent *pの、次のエントリーを求めるものです。エントリーはstruct ext2_dir_entry_2のフォーマットで順に配置されています。すなわち次のエントリーは、そのエントリーにそのサイズrec_lenを加算したものが次のエントリーになるわけです。
static inline ext2_dirent *ext2_next_entry(ext2_dirent *p)
{
       return (ext2_dirent *)((char *)p +
                       ext2_rec_len_from_disk(p->rec_len));
}

typedef struct ext2_dir_entry_2 ext2_dirent;
struct ext2_dir_entry_2 {
       __le32  inode;                  /* Inode number */
       __le16  rec_len;                /* Directory entry length */
       __u8    name_len;               /* Name length */
       __u8    file_type;
       char    name[EXT2_NAME_LEN];    /* File name */
};
ここで問題となるのは、struct ext2_dir_entry_2は、実デバイスから取得するものです。これはリトルエンディアンです。ビッグエンディアンの処理系では問題です。そこでp->rec_lenを直接加算するのでなく、ext2_rec_len_from_disk関数を呼ぶことでその違いを吸収しています。
static inline unsigned ext2_rec_len_from_disk(__le16 dlen)
{
       unsigned len = le16_to_cpu(dlen);

       if (len == EXT2_MAX_REC_LEN)
               return 1 << 16;
       return len;
}
ext2_rec_len_from_disk関数ではle16_to_cpuマクロをコールします。le16_to_cpuマクロは、リトルエンディアンなら、何にもせず引数の値を返し、ビッグエンディアンなら、bswap_16/32をコールする事で、バイト並びを変換して返す事で、エンディアンの違いを吸収しています。
#if BYTE_ORDER == LITTLE_ENDIAN
#define le16_to_cpu(val) (val)
#define le32_to_cpu(val) (val)
#endif
#if BYTE_ORDER == BIG_ENDIAN
#define le16_to_cpu(val) bswap_16(val)
#define le32_to_cpu(val) bswap_32(val)
#endif
ここでは、ファイルシステムのメタ情報について見ましたが、ext2/3ではデータそのものもエンディアンの処理をする必要があるわけです。


最終更新 2011/12/27 16:55:45 - north
(2011/12/27 16:49:01 作成)


検索

アクセス数
3586028
最近のコメント
コアダンプファイル - sakaia
list_head構造体 - yocto_no_yomikata
勧告ロックと強制ロック - wataash
LKMからのファイル出力 - 重松 宏昌
kprobe - ななし
ksetの実装 - スーパーコピー
カーネルスレッドとは - ノース
カーネルスレッドとは - nbyst
asmlinkageってなに? - ノース
asmlinkageってなに? - よろしく
Adsense
広告情報が設定されていません。