6
Help us understand the problem. What are the problem?

More than 5 years have passed since last update.

posted at

updated at

UNIX/32VによるVAX事始め

PDP-11用のUNIX V7VAXに移植したのがUNIX/32Vです。UNIX/32Vを足掛かりにVAXの世界に踏み出してみます。

この記事には続編があります。

この記事には姉妹編があります。

今回は逆アセンブルを目的とします。UNIX/32VのSIMHへのインストールは扱いませんが、以下の記事を参照してください。

SIMH V3.9-0ではうまく動きません(参照)。V3.8-1を推奨します。

クロスコンパイラ

VAXの機械語を扱うため、VAXをターゲットにしたクロスコンパイラが必要です。以下の手順を参考にvax-netbsdelf-gccをビルドしてください。

テスト

先の記事と同じテストをしてみます。

add.c
int add(int a, int b) {
    return a + b;
}

コンパイルします。

$ vax-netbsdelf-gcc -nostdlib -g -O add.c
/usr/lib/gcc/../../vax-netbsdelf/bin/ld: 警告: エントリシンボル _start が見つかりません。デフォルトとして 0000000000010054 を使用します

※ 警告は無視します。

出力されたバイナリ(a.out)を逆アセンブルして、どんな機械語が出力されているかを確認します。

$ vax-netbsdelf-objdump -S a.out

a.out:     ファイル形式 elf32-vax


セクション .text の逆アセンブル:

00010054 <add>:
int add(int a, int b) {
   10054:       00 00           .word 0x0000 # Entry mask: < >
   10056:       c2 04 5e        subl2 $0x4,sp
    return a + b;
}
   10059:       c1 ac 04 ac     addl3 0x4(ap),0x8(ap),r0
   1005d:       08 50
   1005f:       04              ret

引数が0x4(ap)0x8(ap)で渡されて、戻り値はr0で返される様子が読み取れます。

apというのは引数(argument)を指すレジスタです。VAXではEntry maskに基づいてレジスタの退避が行われますが、その際にspがどれだけ動いたのか分かりにくいため、apという専用のレジスタで引数を指すようになっています。

UNIX/32V

以下の2つのファイルをダウンロードします。

  1. http://minnie.tuhs.org/Archive/VAX/Distributions/32V/file2.tar.gz
  2. http://minnie.tuhs.org/Archive/VAX/Distributions/32V/32v_usr.tar.gz

ディレクトリを作って展開します。直接展開すると散らばります。

$ mkdir 32v_root
$ tar xvf file2.tar.gz -C 32v_root
$ tar xvf 32v_usr.tar.gz -C 32v_root

※ 展開時にエラーが出ても無視します。

サンプル探し

ファイルサイズ順にソートして小さめなコマンドを探します。

$ ls -lS 32v_root/bin
(中略)
-rw-r--r-- 1 xxxx xxxx 3.8K 3月  27  1979 df
-rw-r--r-- 1 xxxx xxxx 1.9K 3月  27  1979 echo
-rw-r--r-- 1 xxxx xxxx    7 3月  27  1979 false

種類を推定してみます。

$ file 32v_root/bin/df 32v_root/bin/echo 32v_root/bin/false
32v_root/bin/df:    a.out little-endian 32-bit pure executable
32v_root/bin/echo:  a.out little-endian 32-bit pure executable
32v_root/bin/false: ASCII text

falseはシェルスクリプトなので、バイナリとして小さいのはechoのようです。

ファイルの分析

echoの先頭をダンプしてみます。

$ hexdump -C 32v_root/bin/echo | head
00000000  08 01 00 00 bc 05 00 00  64 01 00 00 04 04 00 00  |........d.......|
00000010  00 00 00 00 00 00 00 00  00 00 00 00 00 00 00 00  |................|
00000020  00 00 c2 08 5e d0 ae 08  6e 9e ae 0c 50 d0 50 ae  |....^...n...P.P.|
00000030  04 d5 80 12 fc d1 50 be  04 19 02 d5 70 d0 50 ae  |......P.....p.P.|
00000040  08 d0 50 ef d8 05 00 00  fb 03 ef 0d 00 00 00 dd  |..P.............|
00000050  50 fb 01 ef 80 02 00 00  bc 01 00 00 00 0c c2 00  |P...............|
00000060  5e d4 5a d1 ac 04 01 15  25 d0 ac 08 50 d0 a0 04  |^.Z.....%...P...|
00000070  50 91 60 2d 12 18 d0 ac  08 50 d0 a0 04 50 91 a0  |P.`-.....P...P..|
00000080  01 8f 6e 12 09 d6 5a d7  ac 04 c0 04 ac 08 d0 01  |..n...Z.........|
00000090  5b 11 3b df cf 9d 05 dd  4b bc 08 fb 02 cf 64 00  |[.;.....K.....d.|

どうやら先頭の0x20バイト(00000000-0000001F)がヘッダのようです。

VAXは32bitなので、ヘッダの各項目は4バイトのリトルエンディアンのようです。0番地はマジックナンバー、4番地はtextのサイズ(0x5bc)、8番地はdataのサイズ(0x164)のようです。

ヘッダに示されたセグメントサイズの合計がファイルサイズ(0x740)に一致します。

  • 0x20 + 0x5bc + 0x164 = 0x740

逆アセンブル

先ほどビルドしたvax-netbsdelf-objdumpではこの古いa.out形式は認識できません。

手動でtextを抽出します。(0x5bc = 1468)

$ dd if=32v_root/bin/echo of=echo.text bs=1 skip=32 count=1468
1468+0 レコード入力
1468+0 レコード出力
1468 バイト (1.5 kB) コピーされました、 0.0178435 秒、 82.3 kB/秒

抽出したtextを生バイナリとしてファイル全体を逆アセンブルします。

$ vax-netbsdelf-objdump -b binary -m vax -D echo.text

echo.text:     ファイル形式 binary


セクション .data の逆アセンブル:

00000000 <.data>:
   0:   00              halt
   1:   00              halt
   2:   c2 08 5e        subl2 $0x8,sp
   5:   d0 ae 08 6e     movl 0x8(sp),(sp)
   9:   9e ae 0c 50     movab 0xc(sp),r0
   d:   d0 50 ae 04     movl r0,0x4(sp)
(略)

※ 先頭のhalt×2はエントリーマスクですが、シンボル情報がないため判別できません。

UNIX/32Vのファイルが逆アセンブルできました。これでようやくスタート地点に立てました。

リンク

浜田直樹氏(@xylnao11)によるVAXやUNIX/32Vのスライドや記事です。

Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away
Sign upLogin
6
Help us understand the problem. What are the problem?