概要
小ネタ。頻繁に使うわけでもないですが、知っておくと便利なことなので、メモメモ。
linux の実行ファイルは ELF (Executable and Linkable Format) というフォーマットのバイナリになります。
で、これが32ビットなのか64ビットなのかを判定したい場合、以下のようなやり方があります。
file コマンドで見る
これが一番手軽ですね。
$ file -e elf xxx
ってするだけです。
32ビットの場合は ELF 32-bit
、 64ビットの場合は ELF 64-bit
って表示されます。
od コマンド, hexdump コマンドでみる
odコマンドやhexdumpコマンドでバイナリをダンプして確認することもできます。
ELF フォーマットは、先頭5バイト目に32ビットか64ビットかの識別が設定されます。
32ビットの場合は 0x01
、64ビットの場合は 0x02
です。
試してみる
今回はクロスコンパイルが簡単ってことで、Goを使って試してみます。
以下のような helloworld を用意します。
package main import "fmt" func main() { fmt.Println("hello world") }
んで、以下のような Makefile を用意
all: \ display \ clean build: \ _build_linux_x86 \ _build_linux_x64 _build_linux_x86: GOOS=linux GOARCH=386 go build -o linux_x86 main.go _build_linux_x64: GOOS=linux GOARCH=amd64 go build -o linux_x64 main.go display: \ build \ _display_file \ _display_od \ _display_hexdump \ _display_elf_format _display_file: @echo '' @echo '[file ]----------------------------------------------------' file -e elf linux_x86 @echo '[file ]----------------------------------------------------' file -e elf linux_x64 @echo '[file ]----------------------------------------------------' @echo '' _display_od: @echo '' @echo '[od ]----------------------------------------------------' od -t x1 < linux_x86 2>/dev/null | head -n 1 @echo '[od ]----------------------------------------------------' od -t x1 < linux_x64 2>/dev/null | head -n 1 @echo '[od ]----------------------------------------------------' @echo '' _display_hexdump: @echo '' @echo '[hexdump]----------------------------------------------------' hexdump -C < linux_x86 2>/dev/null | head -n 1 @echo '[hexdump]----------------------------------------------------' hexdump -C < linux_x64 2>/dev/null | head -n 1 @echo '[hexdump]----------------------------------------------------' @echo '' _display_elf_format: @echo 'ELF形式は先頭 5バイト 目の値が 0x01 なら32bit, 0x02 なら64bit' @echo 'ref: https://en.wikipedia.org/wiki/Executable_and_Linkable_Format#File_header' clean: @$(RM) linux_*
で、実行すると以下のようになります。
$ make GOOS=linux GOARCH=386 go build -o linux_x86 main.go GOOS=linux GOARCH=amd64 go build -o linux_x64 main.go [file ]---------------------------------------------------- file -e elf linux_x86 linux_x86: ELF 32-bit LSB executable, Intel 80386, version 1 (SYSV) [file ]---------------------------------------------------- file -e elf linux_x64 linux_x64: ELF 64-bit LSB executable, x86-64, version 1 (SYSV) [file ]---------------------------------------------------- [od ]---------------------------------------------------- od -t x1 < linux_x86 2>/dev/null | head -n 1 0000000 7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00 [od ]---------------------------------------------------- od -t x1 < linux_x64 2>/dev/null | head -n 1 0000000 7f 45 4c 46 02 01 01 00 00 00 00 00 00 00 00 00 [od ]---------------------------------------------------- [hexdump]---------------------------------------------------- hexdump -C < linux_x86 2>/dev/null | head -n 1 00000000 7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00 |.ELF............| [hexdump]---------------------------------------------------- hexdump -C < linux_x64 2>/dev/null | head -n 1 00000000 7f 45 4c 46 02 01 01 00 00 00 00 00 00 00 00 00 |.ELF............| [hexdump]---------------------------------------------------- ELF形式は先頭 5バイト 目の値が 0x01 なら32bit, 0x02 なら64bit ref: https://en.wikipedia.org/wiki/Executable_and_Linkable_Format#File_header
ちゃんと、5バイト目の値が異なっていますね。
過去の記事については、以下のページからご参照下さい。
- いろいろ備忘録日記まとめ
サンプルコードは、以下の場所で公開しています。
- いろいろ備忘録日記サンプルソース置き場