フラミナル

考え方や調べたことを書き殴ります。IT技術系記事多め

CNIのCiliumについて調べてみた

f:id:lirlia:20210220201845p:plain

調査テーマ

  • Ciliumとは? / 登場背景 / 解決すること
  • Ciliumができること/他との違い
  • Ciliumが使われている事例
  • Ciliumのアーキテクチャ

今回調査したのはv1.9です。

 Ciliumとは? / 登場背景 / 解決すること

Ciliumとは?

f:id:lirlia:20210220190139p:plain

  • 読み方は「スリィアム
  • コンテナ間の通信を実現するOSS(CNIの一種/CalicoやFlannelの仲間)
  • eBPFとよばれるLinux Kernelの仕組みをベースにして通信を制御している

登場背景

ServiceMeshやマイクロサービスの登場によってPod間の通信(East-West通信)が増えた。通常アプリケーションの内部処理よりもNWのレイテンシの方が大きい。

しかも1つのリクエストを捌くために複数のNodeの複数のPodに跨って通信をするようになれば、そのレイテンシは累積することになる。


k8sのおける通信はkube-proxyにて管理されるが、その裏はデフォルトでiptablesが用いられる。iptablesはPodの数が増えるとルールが比例して増えるため、計算量がどんどん多くなる。(計算量としてO(n)として表現される)

これに対応するためk8sではkube-proxyとしてipvsを使う手段が存在している。これはPod数が増えても計算量がO(1)となるため、Podの数が問題にならないというものだ。

しかしipvsにしろUser Spaceにおけるパケット変換機構のため性能が求められる環境においては足かせになることがあるらしい。

そこでCNIの実装として、kube-proxyにそもそも頼らずOpenFlowのようなFlow型のポリシーを採用することでPodへのアクセスを実現するOVN-Kubernetesという実装も存在する。(Openshift 4.xで採用され、RedHatとしては今後こちらのCNIにしていくとのこと)

Ciliumが解決すること

CiliumはアプローチとしてKernel Spaceにてパケットフィルタの処理が行えるeBPFを使ってiptableを置き換えることで高速な通信を実現している。

f:id:lirlia:20210220201435p:plain

また豊富なモニタリング機能があるため、パケットのドロップ状況やその理由についてのトレーシングも可能。

eBPF(extend Berkeley Packet Filter)とは?

f:id:lirlia:20210220190124p:plain

eBPFは拡張(extend) BPFですが文脈によってBPFと省略されることがある。

BPF及eBPFは、User SpaceからKernel Spaceに対して任意のプログラムを挿入し、Kernel Spaceで実行させることができる機能

tcpdumpにも用いられており、パケットをわざわざUser spaceに取り出さなくても解析することができる仕組みにBPFが用いられている。

Ciliumではこれを使いKernel SpaceでNWを制御することで、高速化・認証を実現している。

XDP(eXpress DataPath)とは?

XDPはデバイスドライバ層いて、Ciliumにおいてはパケットの受信時にeBPFプログラムの実行をトリガーする用途で用いられる。

f:id:lirlia:20210220214657p:plain

Ciliumができること/他との違い

  • Nodeを跨ぐ通信の実現(CNI)
  • ロードバランシング(East-West/North-South)
  • 帯域のコントロール
  • モニタリングとトラブルシュート

Nodeを跨ぐ通信の実現(CNI)

Nodeを跨ぐ通信のために2つのNWモデルをサポートします。CNIはノード間の通信をL2/L3どちらにするのか?によって採択されるケースが多いので、使いたい方を選べるのは嬉しい。

  • Overlayモード(デフォルトはこっち)
  • Native Rountingモード
    • Linuxの通常のルーティングテーブルを利用
    • CalicoとおなじL3 NW
    • ノード間でL3接続が必要な場合は、BIRD/kube-routerなどのルーティングデーモンを動かす必要あり

ロードバランシング

通常はkube-proxyで実現されるところだが、CiliumではeBPFの中で実装されているハッシュテーブルを用いて実現している。

帯域のコントロール

CiliumではEDT-based (Earliest Departure Time) で帯域の管理を行っている。

これによりHTB (Hierarchy Token Bucket) や TBF (Token Bucket Filter)を使っているCNIよりもレイテンシが大幅に減らせたり、マルチキューNICを使う場合にロックを避けることができる。

※不明な用語が多くて理解できてない

マルチクラスタ通信

f:id:lirlia:20210220212808p:plain

前提条件として

  • PodCIDRがバッティングしていないこと(かぶっていないこと)
  • Cluster同士が通信できること(Custer間でVPNやpeeringで疎通とれるようにすること)
  • NodeがユニークなIPをもっていること

などが挙げられているので、マルチクラスタ間の通信自体を成立させるためのものではなくすでに通信が可能なクラスタ間において別クラスタのServiceの名前解決をしたり認証をするためのもの。

より詳細なトラッフィクフローやできることを知りたい場合はこちら。

モニタリングとトラブルシュート

通信が不安定になったり切断された時のためにツールが内包されている。(ほかのはついてないことが多い/tcpdumpでの解析に帰着しがち)

  • メタデータでのイベントモニタリング
    • パケットドロップ時に送受信先の情報を表示する
  • ポリシーベースのトレーシング
    • パケットドロップやリクエスト排除時になぜブロックされたのか?についてトレーシングが可能
  • Prometheus向けのメトリクスエクスポート
  • Hubble

Hubbleとは?

  • 分散化されたNWとセキュリティの可観測を行うプラットフォーム
  • Ciliumの上でeBPFを使って動く

具体的にできること

  • サービスの関連性&通信MAP
    • どのサービス(コンテナ)が通信しているのか?
    • どのサービス(コンテナ)の通信が頻繁なのかを可視化する など
  • NWモニタリング&アラート
    • どの通信が失敗しているのか?を可視化 など
  • アプリケーションモニタリング
    • HTTPレスポンスのステータス
    • 95 or 99%タイルでのHTTP通信のレイテンシ など
  • セキュリティの可観測
    • どの通信がNWポリシーでブロックされてるのか?
    • どの通信がクラスタの外からきてるのか? など

Ciliumが使われているケース(あれば)

Ciliumのアーキテクチャ

通信について

User Spaceに存在するPodやコンテナから受け取った通信を直接Kernelに挿入されたeBPFが受け取り処理を行う。


f:id:lirlia:20210220202202p:plain

より詳細には以下のサイトで解説されている(公式サイトではないので注意)

f:id:lirlia:20210220212003p:plain

※上記のサイトより引用

flannelなどではOS上に仮想スイッチを作成するアーキテクチャだが、CiliumではPodのethと対応するvethに通信がくるとそれをHookしてeBPFのプログラムが動作し、パットの制御が行われる。

Cilium利用の前提条件

変わるだろうから公式を参照。大体のLinuxOSはサポートしている。eBPFを使う関係でKernelバージョンは高い物(4.9.17以上)を要求されるので注意。

また追加機能を使う場合はより上位のKernelバージョンが要求される。

kube-proxyを使わずにCiliumを使う

簡単に流れをまとめるとこれだけ。

  • kube-proxyを入れずにk8s cluster作成
  • cilium podを起動

その他つらつら、メモ、感想

  • eBPF/XDPはdpdkにはパフォーマンスで負けているが、汎用NICで動く点は強い
  • dpdkの時はMultusが前提なのでより複雑になりがち、Ciliumは単体
  • eBPF/XDPはCPUを結構つかうとか。SmartNICという単語がちらほら
  • eBPFが目立つほどexploitの対象になりそう(ただでさえナイーブな箇所なので)

参考