2024.12.03
企業の情報漏えいで最も多いのは「中途退職者」による持ち出し 内部不正が発生しやすい3つの要素
リンクをコピー
記事をブックマーク
msyksphinz氏(以下、msyksphinz):「Rustで作るフルスクラッチQEMU型エミュレータ」と題して、発表をします。
簡単に自己紹介をさせてください。Twitterだとこういうアカウントでいろいろと活動しています。趣味で「FPGA開発日記」というブログを書いていて、RISC-V、FPGA、CPU、低レイヤプログラミングなど、興味のあるものの記事を書いています。本業はハードウェア開発エンジニアをしていて、汎用CPUの設計などの仕事をしています。
今回はRustというテーマなんですが、職場はRustの「ラ」の字も出てこないところです。こういうことを趣味でやっています。最近は、RISC-Vのことなどを雑誌に連載する機会も増えてきています。
本日は、QEMUのお話をします。私自身、どういう仕組みになっているのかを勉強する良い機会になったので、共有したいと思います。
まず簡単に、命令セットエミュレータ、シミュレータとは何かから説明します。世の中にはいろいろなターゲットのバイナリが存在していて、RISC-V、ARM、x86みたいなバイナリがあります。ただ、これらを動かしたい時に実機が存在しないことがよくあるわけですね。
そういう時にエミュレータを使うのですが、例えば私だったら、x86のデスクトップPCとかでエミュレータを動かして、RISC-Vのバイナリを動かします。こんな感じで実機が存在しなくても、別の実機を使ってその異なるバイナリの動きを模擬して、中身を見ることができるのがエミュレータの特徴です。
世の中にはいろいろなエミュレータが出てきていて、これからお話しするQEMU以外にもいろいろな命令セットシミュレータが公開されています。例えば、実機を入手するのが難しい量子コンピュータのシミュレータなどもシミュレータを使うことで、実際にどういうことが起きているのかを見ることができます。
シミュレータは、私たちのような汎用CPUの設計屋さんにとっては非常に馴染み深いもので、例えば私がCPUを設計して、動きがどうなっているんだろうと見る時に、このRTLシミュレータとは別に、この命令セットシミュレータで同じバイナリを動かして動作が一致するのかを見てデバッグを行ったりします。そんな感じで非常に馴染みの深いツールになっています。
QEMUに焦点を当てていきます。QEMUは、みなさんがご存知のとおりプロセッサのエミュレータです。さまざまなアーキテクチャをエミュレーションすることができます。上のほうでいろいろなアーキテクチャを受け入れます。これはゲストアーキテクチャといいます。それをホストアーキテクチャ、つまり私の場合はx86で変換することでエミュレーションするというツールです。
QEMUは、受け入れたバイナリを1回、Tiny Code Generator(TCG)という表現に変換して、さらにホスト命令に変換するというかたちになっています。この形式は、コンパイラだとLLVM、LLVM-IRみたいな中間表現を取るかたちによく似ていると思っていて、QEMUはエミュレータ界のLLVMだと個人的に思っています。
大きく分けて2つの方式があります。1つがインタープリタ型。ゲスト命令を1命令ずつ解釈して、その動作を何かしらのプログラミング言語で模倣することで、エミュレーションする方式です。もう1つがQEMUが取っているバイナリ変換型です。ゲスト命令をホスト命令に直接変換して実行する方式です。
どちらにも長所・短所があります。インタープリタ型は、実装が簡単です。ただしバイナリ変換型に比べると遅い。バイナリ変換型は、直接命令を変換するのでインタープリタ型と比較して非常に速度が速いという特徴があります。
次にQEMUの中身について触れていきます。QEMUは、1回バイナリを受け取るとTiny Code Generatorという表現に変換します。ここでは、RISC-Vのバイナリを受け取って、それをx86上で実行するという例を取り上げてみます。RISC-VのADDI命令、即値加算ですね。これを受け取った場合にどうするかというと、大きく4つのTCGに変換されます。
1つがRegister Readですね。x3、gpレジスタからtmp2にデータを読み出して、即値をtmp3に格納して、tmp2とtmp3を加算します。最後の計算結果tmp2をa5の汎用レジスタに格納するというTCGに変換されます。それぞれを1対1でx86の命令に置き換えていくことでエミュレーションができます。
なので、この場合はRISC-Vの1命令が3命令のx86命令に置き換わるんですが、QEMUは強力な最適化によって前後のメモリアクセス命令を除去することもできます。一番良いパターンだと、RISC-Vの1命令、ADDIがx86のaddq命令の1命令に置き換えられます。これがQEMUが非常に高速である所以になっていると思います。
TCGの仕組みを理解したところで、本当に理解できているかどうか自分でイチからQEMUらしきものをフルスクラッチで作ってみました。
言語を何にしようかと思ったんですが、Rustを私もちょくちょく使っていて、「Rustで書くと安全だ」という神話もよく聞いていました。QEMUはいろいろバグを出すと安全じゃないとかよく言われていて、「QEMUをRustで書き換えるといいよ」みたいな話も出てきたので、自分でちょっとやってみて、どんな感じになるのかを見たいと思いました。
成果物はGitHubに公開していて、RISC-Vのバイナリをx86でエミュレーションするというものをRustで作ってみました。ただ、勉強用に書いたのでほぼ実用性はないし、数ヶ月前に作って飽きてしまったので最近はあまりメンテナンスできていません。
中身の実装について紹介します。この自作QEMUは、大きく3つのコンポーネントで成り立っています。1つはゲストマシン用コンポーネント、つまりRISC-Vを模擬しているものです。メモリ、プログラムカウンタ、レジスタファイル、システムレジスタを模擬しています。もう1つがホストマシン用コンポーネント、x86側ですね。変換したx86命令をバッファリングしておくためのブロックで構成されています。
真ん中が共通コンポーネントで、これが実際にエミュレーションを行うエンジンです。大きな流れをご紹介すると、まずはフェッチします。メモリから命令を取ってきてデコードして、デコード結果に基づいてTCGを生成します。今度はTCGからx86命令の変換を行います。この段階でx86命令ブロックに格納しておいて、次に繰り返しなどで同じプログラムカウンタを踏んだ場合は、この変換処理をスキップして、直接このブロックから取りにいくということを行っています。
最後にこの変換したx86命令を実行することで、レジスタにアクセスしたり、プログラムカウンタを更新したりします。あとの説明のために、大きく分けてこの上のデコード、フェッチの辺りを制御モード、下のx86命令実行のところをエミュレーションモードと名前を付けて説明します。
これはちょっとした小話なんですが、自作QEMUを作るにあたってデバッグで非常に苦労しました。自作QEMUなので、バイナリがバイナリを作り出します。どんな命令を生成されたのかが確認できないという困った問題が起きました。
GDBとかを当てればいいんですが、DWARFのデバッグ情報とかまでは生成できず、GDBが当てられないままエミュレータを実行すると、途中でExceptionが起きて終わりみたいな、困った状態になりました。
なのでどうしたかというと、本物のQEMUで自作QEMUを動かして、そのうえでRISC-Vバイナリを動かすというちょっと再帰的なかたちを取りました。本物のQEMUは自作QEMUの動きを全部事細かにトレースして取ってくれるので、自作QEMUがどういう命令を生成して実行しようとしたのかというログを詳細を取ってくれます。
なのでそのログを見ながら、どこのオフセットが間違っている、どこのレジスタが間違っているみたいなのをデバッグしてデバッグを行っていきました。
すごくがんばって実装を行って、ある程度テストパターンが動くところまでもっていきました。とりあえず速度を測ってみたいなと思ったので、Dhrystoneという非常に一般的なベンチマークプログラムを動かしてどれだけの速度になるのかを測ってみました。
それがグラフになっていて、真ん中の赤いやつが私の実装です。この下のやつがインタープリタ型のSpikeという、わりと一般的に使われているRISC-Vのシミュレータで、一番上がQEMUです。インタープリタ型に比べると圧勝できたのですが、QEMUと比べるとぜんぜん勝てていない状態で、なんでこんなにQEMUは速いんだろうとQEMUを読み解きながら調査をしていきました。
(次回へつづく)
2024.11.26
タスクの伝え方が部下のモチベーションを左右する マッキンゼー流、メンバーが動き出す仕事の振り方
2024.11.25
仕事はできるのに、なぜか尊敬されない人が使いがちな言葉5選 老害化を防ぐために大切な心構えとは
2024.11.27
何もせず月収1,000万円超…オンラインゲームにハマって起こした事業 大学中退し4社立ち上げ・2社売却した起業家人生
2024.11.29
「明日までにお願いできますか?」ちょっとカチンとくる一言 頭がいい人に見える上品な言い方に変えるコツ
2024.11.25
論理的に「詰める」マネジメントでは本質的な解決にならない マッキンゼー流、メンバーの理解と納得を得る接し方
2024.11.28
管理職の「疲弊感」がメンバーに伝わるリスク 部下の「働きがい」を育む6つのポイント
2024.11.27
部下に残業させられず、自分の負担ばかり増える管理職 組織成長のカギを握る「ミドル層」が抱える課題
2024.11.27
仕事中の「今ちょっといいですか」が苦痛… いしかわゆき氏が語る、ADHD気質にマッチした働き方のヒント
2024.11.26
仕事の質を左右する「ムダな習慣」トップ5 忙しくなる前に棚卸ししたい“やめたほうがいいこと”とは
2024.11.28
“新規事業が生まれない組織”に足りていないもの 「PoC貧乏」に陥らず、アイデアを形にするためのヒント
長期投資の衝撃の真実!20年投資しても年率1.9%しか増えない!?
2024.10.04 - 2024.10.04
第765回 トレンド経営学『顧客に謝る基準とは?』
2022.04.18 - 2022.04.18
不機嫌な自分をやめるために!認知行動療法の専門家 中島美鈴先生新刊『脱イライラ習慣! あなたの怒り取扱説明書』発売記念【無料オンラインイベント】
2024.10.25 - 2024.10.25
ログミーBusiness リニューアル記念イベント開催
2024.11.29 - 2024.11.29
品がある人、育ちがいい人の見える 人のセリフ 3選
2022.11.30 - 2022.11.30