MobyとRustで作るコンテナをやる
tags: containerdocker2022-08-25
ToC
何を学ぶか
Moby(Docker)をビルドしてruncとcontainerdを単体で動かしてコンテナの基礎を理解する . という記事と、 Writing a container in Rust . という記事があったのでやって感想をまとめる
昔Rustでコンテナを作ってみようとして挫折した(cgroupやnamespaceの切り方がちゃんとわからなかった...)のでリベンジしたい、というのがモチベーション 最初の記事ではDockerのアーキテクチャ(低レベルランタイム、高レベルランタイム)について学び、二つ目の記事ではコンテナ自体の仕組みと それを実現するためのRustのAPIを知りたい
完了した時にはruncとcontainerdの動かし方がわかっていて、Rustでcontainerを作成する方法も学べているはず
DockerDesktopのアーキテクチャ
moby->containerd->runcの順に降りていく感じ
- containerdは高レベルランタイムで、imageの管理やruncのような低レベルのランタイムの実行を行う
- gRPCで外からリクエストを受け付けるのもこいつ
- k8sもfargateもこれ使ってる
- runcは実際にnamespaceやcgroupを使ってコンテナを作成する役目
- runcより下は、MacやWindowsでも動かせるように「LinuxKit」としてLinuxKernelが入っていて、その下にQEMUとかHyperKitがいる
runcメモ
- runc specで仕様ファイルが生成される(config.json)
- capabilityとかnamespaceが設定されてる
- mount先のpathやprocのpathのどこを使うかとかも
- rootがどこかも書いてあって、デフォルトではrootfsになっている。なのでmkdirでcurrentにrootfs作ると動く
- argsを作ったhelloに置き換えて実行してみる(READMEではshをbusyboxで持ってくるらしい)
- helloは実行前にrootfs/binに移動しておく
- 隔離されているか確認するためにls作ったりstrace走らせたりする
containerdメモ
- 操作はctrコマンドで行う
- これはcontainerdのcli
- interfaceはだいぶdockerコマンドに近い感じ
- imageのpullとかできるよ
- nerdctlというdocker互換のコマンドがあり、これでdockerっぽい操作ができる
コンテナ作るよ
- structopt
- clapをバックエンドにしたargパーサ
- ///でコメント打つとそれがmessageになってくれるっぽい?
- #[structopt]でshortやlongのoptionを設定できる
- config引数のargvをCStringにしているのは、execveのsyscallを呼ぶ時に便利だからだそうな
- nix使ってunameやhostを取得している
- linuxのkernelのversionの検査がいるため。Macでも動くんだけど互換があるのか...?
- child processを生やすぞ
- IPC(Inter process communication)を使う
- 通信にはunix domain socketsを使う。nginxとphp-fpmを繋ぐ時に使ったりするアレです
- socket関連の関数とかもnixに生えてる
- rustフレンドリーな*nixシステム関数群だそうで
- nixのSockFlag::SOCK_CLOEXECがMacだと動かなそう(target_osに記載がないので)
メモ
- rustのmod.rsを置く方法は古いらしい
- hogeディレクトリ切ったら、hoge.rsを置いて、その中でhoge/fugaをmodすることで依存を解決するみたい
- RawFd、はファイルディスクリプ他。unixでしか使えない