×
  • Share
  • Email
  • Embed
  • Like
  • Save
  • Private Content
 

PDP-11のインタプリタを作った話

on

  • 300 views

 

Statistics

Views

Total Views
300
Views on SlideShare
285
Embed Views
15

Actions

Likes
2
Downloads
2
Comments
1

1 Embed 15

https://twitter.com 15

Accessibility

Categories

Upload Details

Uploaded via SlideShare as Microsoft PowerPoint

Usage Rights

© All Rights Reserved

Report content

Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel

11 of 1 previous next

  • P15の表記にミスがあります。
    −(R1) : R1にオペランドのアドレス、実行後にR1の内容をデクリメント
    *−(R1) : R1にオペランドへのポインタのアドレス、実行後にR1の内容を2だけデクリメント

    実行「前」です。
    Are you sure you want to
    Your message goes here
    Processing…
Post Comment
Edit your comment

    PDP-11のインタプリタを作った話 PDP-11のインタプリタを作った話 Presentation Transcript

    • PDP-11のインタプリタを 作った話 @kanorimon
    • >誰? • kano • Twitter:@kanorimon • Github:https://github.com/kanorimon/ • 低レイヤ初心者 • 文系SE 兼 情報系大学一年生 • たまにJava書く程度の能力 • パタヘネ読み始めてMIPSで詰み、偶然見つけた池袋バイナリ勉強会へ
    • >何を話すのか? • 初心者がPDP-11のインタプリタを作ってみた • 池袋バイナリ勉強会でやったカリキュラムを紹介 • バイナリを教えるときの参考になれば • PDP-11でない方が良いかもしれませんが……
    • >カリキュラム • Brainf*ckのインタプリタ作成 • PDP-11の逆アセンブラ作成 • PDP-11のインタプリタ作成 • UNIX V6のカーネルビルド
    • >Brainf*ckのインタプリタ作成 ソース 実行結果
    • >Brainf*ckのインタプリタソース byte[] mem : メモリをあらわす配列 プログラムをPC=1から順に 読込み、pcの位置にある命 令によって処理を分岐する int ptr : ポインター int pc : プログラムカウンタ
    • >Brainf*ckでわかったこと • メモリはbyte配列として表現できる • メモリを読み書きするにはポインタ(アドレス)(添え字)が必要 • 原則として、プログラムは1命令目から順に実行される • 次に実行する命令がある位置はプログラムカウンタが管理している • ジャンプ命令やループ命令はプログラムカウンタを書き換える命令
    • >PDP-11の逆アセンブラ作成 ソース
    • >PDP-11の逆アセンブラ作成 バイナリ 実行結果
    • > PDP-11の逆アセンブラソース 仮想メモリ空間をあらわす配列を作成 byte[] mem バイナリを仮想メモリ空間に読み込み
    • >PDP-11の逆アセンブラソース コンディションコードを あらわす変数を作成 boolean n boolean z boolean v boolean c レジスタをあらわす配列を作成 int reg[0]~[7]
    • >PDP-11の逆アセンブラソース int ptr : ポインター Int pc : プログラムカウンタ 命令ごとに ソース/デスティネーションのオペランドを 判定する 命令を1桁ずつ分類して ニーモニックを判定する 例)000006 : RTT , 0001xx : JMP
    • >PDP-11の逆アセンブラソース 結果を画面に出力
    • >PDP-11の逆アセンブラでわかったこと • バイナリ • 0と1のファイル • 一定のルール(仕様)をもとに解釈するとアセンブリに書き換えることができ る(この仕様のセットを命令セットと言う) • PDP-11 • レジスタは、R0~R7 • コンディションコードは、N(ネガティブ),Z(ゼロ),V(オーバーフロー),C(キャ リー) • 命令セット
    • >PDP-11の逆アセンブラ(発展)ソース アドレッシングモードの取り込み R1 : R1にオペランドがある (R1) : R1にオペランドのアドレスがある (R1)+ : R1オペランドのアドレス、実行後にR1の内容をインクリメント *(R1)+ : R1にオペランドへのポインタのアドレス、実行後にR1の内容を2だけインクリメント −(R1) : R1にオペランドのアドレス、実行後にR1の内容をデクリメント *−(R1) : R1にオペランドへのポインタのアドレス、実行後にR1の内容を2だけデクリメント 2(R1) : R1+2がオペランドのアドレス *2(R1) : R1+2がオペランドのポインタへのアドレス
    • >PDP-11のインタプリタ作成 ソース 実行結果
    • > PDP-11のインタプリタソース 仮想メモリ空間をあらわす配列を作成 byte[] mem バイナリを仮想メモリ空間に読み込み
    • >PDP-11のインタプリタソース コンディションコードを あらわす変数を作成 boolean n boolean z boolean v boolean c レジスタをあらわす配列を作成 int reg[0]~[7]
    • >PDP-11の逆アセンブラソース 命令ごとに レジスタ・メモリの操作を行う 命令を1桁ずつ分類して ニーモニックを判定する 例)000006 : RTT , 0001xx : JMP
    • >PDP-11のインタプリタソース システムコールの実装 read() write() exit() …
    • >PDP-11のインタプリタ(発展1) • PDP-11のnmを読み込んで、標準出力にオブジェクトファイル のシンボルリストを出力した • PDP-11のccを読み込んで、Cのソースをコンパイルした
    • >PDP-11のインタプリタ(発展2) • fork(),exec(),wait()の実装 • リファクタリング カーネル クラス プロセス クラス 仮想アドレス空間 クラス
    • >PDP-11のインタプリタでわかったこと • UNIX V6 • ユーザー空間とカーネル空間は異なる • プロセスごとに仮想アドレス空間を持ち、MMUがメモリの物理アドレスに変 換する • 仮想アドレス空間はテキスト/空き領域(マジックナンバ0410の場合) /データ+bss/ヒープ/空き領域/スタックとなっている • ファイルはinodeで管理されている • ファイル入出力等の基本機能はシステムコールを呼び出すことで実現して いる • 関数呼び出しをする場合は、スタックに引数と戻り先のアドレスを格納し てからジャンプする
    • >PDP-11のインタプリタでわかったこと • コンパイラ • ccは以下の順で実行する • (Cコンパイラ)/lib/c0 • (Cコンパイラ)/lib/c1 • (アセンブラ)/bin/as • (アセンブラ)/lib/as2 • (リンカ)/bin/ld
    • >UNIX V6のカーネルビルド インタプリタ CC ロード UNIX V6 カーネル UNIX V6 ソース コンパイル
    • >UNIX V6のカーネルビルド • lib1 • cd ken • java pdp11.Pdp11 -e -s cc -c -O *.c • java pdp11.Pdp11 -e -s ar r lib1 main.o trap.o sig.o sysent.o • java pdp11.Pdp11 -e -s ar r lib1 *.o • lib2 • cd dmr • java pdp11.Pdp11 -e –s cc -c -O *.c • java pdp11.Pdp11 -e -s ar r lib2 *.o
    • >UNIX V6のカーネルビルド • con/mkconf • cd conf • java pdp11.Pdp11 -e -s as m40.s • rename a.out m40.o • java pdp11.Pdp11 -e -s cc mkconf.c • rename a.out mkconf • rkunix • (echo rk& echo tm& echo tc& echo done)| java pdp11.Pdp11 -e -s mkconf • java pdp11.Pdp11 -e -s cc -c c.c • java pdp11.Pdp11 -e -s as l.s • java pdp11.Pdp11 -e -s ld -x a.out m40.o c.o lib1 lib2 • copy a.out rkunix
    • >うまく動かない… 実行ログを確認して インタプリタのソースから 実装ミスを探す ↓ 【よくあったミス】 コンディションコードの設定 システムコールの仕様
    • >UNIX V6のカーネルビルド結果 • 処理時間→1:50
    • >UNIX V6のカーネルビルド結果 • 処理時間→1:50→1:50:00
    • >UNIX V6のカーネルビルド結果 • ボトルネックは10進数の値を8進数に変換して、そのx桁の値を 取得する処理 • 例:42798→0123456→3桁目=3
    • >UNIX V6のカーネルビルド結果 • 処理時間→1:50→1:50:00→0:07:30
    • >総括 • 着手から完成まで約半年(100~200時間)程度 • 自分で手を動かしてプログラムを作ることで、楽しく調べながら勉 強を進めることができました • HACKING本読んでます • 初心者におすすめな本があれば教えてください