【テクニカル・上級編】 WFQ(Weighted Fair Queuing)およびWRR(Weighted Round Robin)キューイング – インフラ・物理&L2/L3ネットワーク基礎実践ガイド

帯域の調律師:WFQとWRRが織りなすパケットの「公平性」と「優先度」の深淵

ネットワークエンジニアとして現場に立つと、常に直面するのが「限られた帯域をいかに効率的に捌くか」という古典的かつ永遠の課題だ。スイッチのバッファが溢れ、テールドロップによるTCPの再送嵐(Retransmission Storm)に頭を抱えた経験がある者なら、QoS(Quality of Service)のアルゴリズムこそがインフラの生命線であることを痛感しているはずだ。

本稿では、L2/L3スイッチやルーターの心臓部でパケットの運命を決定づける WFQ(Weighted Fair Queuing)と WRR(Weighted Round Robin)に焦点を当て、その内部挙動と、現代のTCP/TLS通信におけるチューニングの極意を解き明かしたい。

—

1. 概念の再定義:なぜ「公平」と「重み」が必要なのか

単純な FIFO(First-In, First-Out)は、一見公平に見えて、実際には「高帯域を占有するストリーム」が「低遅延を求める制御パケット」を押し流す、最悪のキューイングだ。これを防ぐために登場したのが、動的な重み付けによるスケジューリングである。

WRR(Weighted Round Robin):単純明快な「配分」

WRR は、各キューに重み(Weight)を割り当て、その比率に応じて順番にパケットを吐き出す。

  • 挙動: キュー1に3パケット、キュー2に1パケットという重みを設定すれば、物理回線が空いている限り、その比率でパケットを切り出す。
  • 弱点: パケット長がバラバラだと帯域占有率が不安定になる。例えば、最大長の MTU パケットばかりが重み付けされたキューに流れ込むと、小さな制御パケットが待たされる「ジッター」が発生する。

WFQ(Weighted Fair Queuing):数学的公平性の追求

WFQ は、パケットのサイズとフローの数を動的に考慮し、理論上の「仮想的な終了時間」を計算して出力順を決定する。

  • 挙動: フローごとの帯域を自動的に均等化しようとするため、設定なしで「大象(高帯域)が小鼠(VoIP等の低帯域)を殺す」事態をある程度緩和できる。

—

2. パケットレベルの最適化とチューニングの実践

現代のインフラでは、単にキューを分けるだけでは足りない。TLSハンドシェイクのRTT(Round Trip Time)を短縮し、TCPの窓サイズ(Window Size)を維持するためには、スケジューラだけでなく、ホスト側のカーネルパラメータとの協調が不可欠だ。

LinuxにおけるWFQの活用:fq_codel

Linuxカーネルの fq_codel(Fair Queuing Controlled Delay)は、WFQの思想をベースに CoDel アルゴリズムを組み合わせ、バッファブロート(Bufferbloat)を劇的に抑制する。

# eth0インターフェースにfq_codelを適用し、バッファの遅延を抑える
# target: 許容する最小の遅延時間 (5ms)
# interval: キューをドロップする判断のタイムウィンドウ (100ms)
tc qdisc add dev eth0 root fq_codel target 5ms interval 100ms

なぜこれが重要か?

TLS 1.3のハンドシェイクにおいて、初回パケットがバッファで詰まれば、その後の ClientHello / ServerHello の往復に余計な遅延が乗る。fq_codel は、小さなパケット(SYNやACK)を優先的に処理する傾向があるため、ハンドシェイクの完遂を助け、結果としてスループットの向上が期待できる。

—

3. 実践的パラメータチューニング:現場の知見

スイッチのハードウェアキューを設定する際、以下の WRR の重み付け戦略を推奨する。

| クラス | トラフィック種別 | 重み付け(例) | 根拠 |
| :— | :— | :— | :— |
| Strict Priority | VoIP, 制御系 | 0 (即時転送) | 遅延許容値が極めて低いため |
| Class 1 | TLS, API通信 | 60% | トランザクション性能の確保 |
| Class 2 | 大容量データ転送 | 30% | 帯域の最大利用 |
| Class 3 | ベストエフォート | 10% | 余剰分のみ利用 |

設定サンプル(Cisco IOS-XE等の概念)

# クラスマップの定義
class-map match-any CONTROL-TRAFFIC
 match protocol ssh
 match protocol tcp 443

# ポリシーマップでの重み付け(WRR的アプローチ)
policy-map QOS-POLICY
 class CONTROL-TRAFFIC
  bandwidth remaining percent 60
 class class-default
  bandwidth remaining percent 40

—

4. 脆弱性とパフォーマンスの相関

セキュリティ専門家として忠告したいのは、「QoS設定そのものがDoS攻撃の踏み台になり得る」という事実だ。
攻撃者が特定のフローに対して低帯域だが大量のパケットを送り続けると、WFQ はそのフローを「公平に扱うべき対象」と誤認し、正当なトラフィックの帯域を奪う可能性がある。

回避策:
1. ポリシングとシェーピングの併用: 特定のクラスに上限(police)を設け、異常なバーストを叩き落とす。
2. TCPバッファの制限: Linux側で net.ipv4.tcp_rmem 等を調整し、過剰なバッファ確保によるメモリ枯渇を防ぐ。

# 適切なバッファサイズの設定例
net.ipv4.tcp_rmem = 4096 87380 16777216
net.ipv4.tcp_wmem = 4096 65536 16777216

—

結びに:プロトコルと対話せよ

ネットワークは、決して無機質な箱の集まりではない。パケットは重力に逆らい、キューという揺り籠の中で自身の運命(転送か破棄か)を待っている。

WFQ や WRR を触ることは、単なるCLI操作ではない。それは、流れるデータ一つひとつに「優先順位」という名の意思を吹き込む作業だ。マニュアルの数値を鵜呑みにせず、パケットキャプチャで TCP ACK の間隔を観察し、自身のアーキテクチャが意図した通りの「公平性」を実現しているか、常にプロトコルの声に耳を傾けてほしい。

インフラエンジニアの真価は、トラブルが起きていないとき、いかにネットワークが「呼吸」しているかを理解できているか、その一点に集約されるのだから。

コメント

タイトルとURLをコピーしました