単一 VM に割り当てる vCPU は、多ければ多いほど速くなるわけではありません。workload が並列化できる範囲、host の物理 core、SMT sibling、NUMA node、CPU overcommit、quota、同居 VM の負荷によって、適切な数は変わります。
この記事では、workload の同時実行数から初期値を決め、host topology と縮退時 capacity に収まるか確認し、vCPU を段階的に増減して throughput、p95 / p99 latency、CPU pressure、steal を比較する手順を示します。
書籍
CPU 仮想化支援、メモリ仮想化、割り込み、仮想デバイスなど、VM の実行モデルを低レイヤから理解する参考書籍です。価格や在庫はリンク先で確認してください。
Amazon で見るこのリンクは Amazon アソシエイトリンクです。
vCPU 数の前に workload の並列性を確認する
vCPU は、同時に実行できる仕事があって初めて効果を持ちます。single thread の処理、global lock、serial queue、同期 I/O が支配的なら、vCPU を増やしても処理量は伸びません。
| workload | 並列性を決めるもの | 最初に測るもの |
|---|---|---|
| Web / API | worker、request concurrency、connection pool | request rate、p99、run queue |
| database | query concurrency、lock、buffer、log write | transaction rate、lock wait、I/O latency |
| batch | worker 数、partition、serial section | job completion time、CPU efficiency |
| NFV / network | queue、flow、packet size、crypto | pps、drop、softirq、jitter |
| build / render | thread pool、dependency graph、memory bandwidth | completion time、CPU utilization |
application の worker 数を vCPU 数と機械的に一致させません。worker が I/O 待ちを含むのか、CPU を常時使うのか、lock で直列化されるのかを確認します。
物理 core、SMT thread、vCPU を分ける
| 単位 | 意味 | capacity の扱い |
|---|---|---|
| socket | CPU package | NUMA node と memory channel を確認する |
| 物理 core | 独立した core resource | CPU capacity の基準として扱いやすい |
| SMT thread | 同じ core の execution resource を共有する sibling | 物理 core と同じ増分を前提にしない |
| vCPU | host scheduler が実行する virtual CPU | 割り当て数と同時実行 capacity は別 |
SMT の効果は workload に依存します。同じ physical core の sibling へ 2 つの CPU-intensive vCPU を置いても、独立した 2 core と同じ性能になるとは限りません。core 数と thread 数を別々に記録します。
host topology と予約 CPU を確認する
lscpu -e=CPU,NODE,SOCKET,CORE,ONLINE
lscpu
numactl --hardware
virsh nodeinfo
virsh capabilities
cat /sys/devices/system/cpu/isolated
cat /sys/devices/system/cpu/nohz_full- socket、core、SMT sibling、NUMA node の対応
- offline CPU と isolated CPU
- host OS、QEMU、IRQ、monitoring 用に残す CPU
- 同じ core の sibling を別 VM が使用していないか
- host ごとの CPU model と migration compatibility
- 障害時に VM が集約される host の topology
online CPU thread 数から VM 用 capacity を直接計算しません。housekeeping、IRQ、storage、network、emulator thread の実行余力を先に差し引きます。
VM の maximum、active、guest-visible vCPU を分ける
libvirt では maximum vCPU、現在 active な vCPU、live / config の設定が異なる場合があります。guest agent が利用できる構成では、guest から見える CPU 数との違いも確認できます。
virsh vcpucount vm01
virsh vcpucount vm01 --active --live
virsh vcpucount vm01 --maximum --config
virsh vcpuinfo vm01 --pretty
virsh vcpupin vm01
virsh schedinfo vm01
virsh domstats vm01 --cpu-total --vcpu
virsh dumpxml vm01
virsh dumpxml vm01 --inactivevcpucount の maximum は hotplug 可能な上限、active は現在使っている数です。XML の current、個別 vCPU state、guest OS の online CPU を混同しません。
guest CPU topology は application から見える設計である
guest へ sockets、cores、threads をどう見せるかは、vCPU 総数と別の設定です。license、NUMA awareness、application の topology detection に影響するため、同じ 8 vCPU でも topology の意味が変わります。
<vcpu placement='static' current='8'>8</vcpu>
<cpu mode='host-model'>
<topology sockets='1' dies='1' cores='4' threads='2'/>
</cpu>この例は guest へ 1 socket、4 cores、2 threads を示します。host の topology をそのまま複製する必要はありませんが、topology の積が vCPU 構成と一致し、migration、license、guest NUMA の方針と矛盾しないようにします。
NUMA node 内に収めるか、guest NUMA を定義する
大きな VM が 1 つの host NUMA node の CPU または memory capacity を超えると、remote memory access と node 間 traffic が増える可能性があります。単一 node に収めることを絶対条件にせず、跨ぐ理由と guest NUMA topology を明確にします。
| 構成 | 利点 | 注意点 |
|---|---|---|
| 1 host NUMA node 内 | CPU と memory locality を読みやすい | node capacity が VM の上限になる |
| 複数 node に跨る | 大きな VM を構成できる | guest NUMA、memory policy、workload awareness が必要 |
| CPU だけ跨る | CPU 数は増やせる | memory placement が片側なら remote access が増える |
| 自動配置 | scheduler の柔軟性を使える | 負荷と migration 後の配置を再確認する |
database や大きな in-memory workload では、application が guest NUMA を認識するかも確認します。vCPU 数だけを増やし、memory と device の locality を変えないと、性能が伸びない場合があります。
単一 VM sizing と host overcommit を分ける
単一 VM の vCPU 数は、その workload が必要とする並列 capacity です。host overcommit は、複数 VM の vCPU demand を同じ physical CPU pool へ収容する設計です。両者を同じ ratio だけで決めません。
| ratio | 分子 | 分母 | 用途 |
|---|---|---|---|
| allocation ratio | 割り当てた vCPU 合計 | 利用可能な host CPU thread または core | 構成上の集約度 |
| demand ratio | peak 時に実行を求める vCPU | 実行可能な physical capacity | 実際の競合可能性 |
| single VM share | 対象 VM の demand | 共有 CPU pool | 1 VM が占める範囲 |
ratio の分母を physical core にするのか SMT thread にするのかを明記します。SMT thread 数で ratio を低く見せても、CPU-intensive workload の capacity が同じ比率で増えるとは限りません。
CPU quota、weight、pinning を確認する
vCPU 数が多くても、CPU quota で実行時間を制限されていれば、その VM は vCPU 数どおりの capacity を使えません。weight は競合時の相対配分、pinning は実行可能 CPU の範囲を決めます。
| 制御 | 決めること | 典型的な見落とし |
|---|---|---|
| vCPU count | guest の並列実行単位 | workload が並列化できない |
| quota / period | 一定期間の CPU time 上限 | CPU は空いていても throttling される |
| shares / weight | 競合時の相対優先度 | 単独時の上限と誤解する |
| vcpupin | vCPU の実行可能 CPU | 固定先の core が混雑している |
| emulatorpin | QEMU 補助 thread の CPU | vCPU と同じ CPU で競合する |
専有に近い VM と共有 VM では、同じ 8 vCPU でも意味が異なります。SLO と chargeback、capacity 管理では、vCPU count だけでなく resource model を記録します。
縮退時 capacity を先に計算する
通常時に収まる sizing でも、host maintenance や障害で VM が他 host へ集約されると overcommit と NUMA placement が変わります。N+1 構成では、最大 host 1 台停止時の demand を残存 host で満たせるか確認します。
- 通常時と host 1 台停止時の VM 配置
- 縮退時の vCPU allocation ratio と demand ratio
- NUMA node ごとの CPU と memory の空き
- CPU pinning した VM の移行先 CPU map
- 同時起動による peak と通常 workload peak の重なり
- 縮退時に優先する VM と抑制できる batch
capacity を平均 CPU 使用率だけで計算すると、同時 peak と tail latency を見落とします。縮退 test では placement だけでなく、実 workload の p99 と error rate を確認します。
少ない vCPU から段階的に増やす
| 段階 | 実施すること |
|---|---|
| 1 | 現在の workload concurrency と SLO を記録する |
| 2 | host topology、NUMA、予約 CPU、縮退 capacity を確認する |
| 3 | 小さな vCPU 構成で baseline を測定する |
| 4 | vCPU を段階的に増やし、同じ workload で再測定する |
| 5 | throughput の増分と p99、pressure、steal の変化を比較する |
| 6 | 増分が小さい、または latency が悪化する手前を候補にする |
2 → 4 → 8 のように増やす場合でも、増加幅は workload と topology に合わせます。vCPU 数以外の CPU pinning、memory、queue、worker、cache を同時に変えません。
host と guest を同じ時間窓で測る
nproc
lscpu
mpstat -P ALL 1
vmstat 1
pidstat -u -t 1
cat /proc/pressure/cpu
cat /proc/pressure/memory| 指標 | 判断 |
|---|---|
| throughput | vCPU 追加で完了量がどれだけ増えたか |
| p95 / p99 | 平均が同じでも tail latency が悪化していないか |
| run queue | 実行待ち task が増えていないか |
| steal | host scheduler に待たされた時間が増えていないか |
| CPU PSI | CPU contention で task が止まる時間が増えていないか |
| CPU efficiency | vCPU 1 個当たりの完了量が急減していないか |
host の pCPU 使用率、QEMU vCPU thread、同居 VM の demand も同じ時間帯で取得します。guest の CPU 使用率だけでは、workload の限界と host contention を区別できません。
仮想 appliance は traffic profile で検証する
virtual firewall、router、load balancer、NFV appliance の推奨 vCPU は、製品が想定した traffic profile と feature set に依存します。packet size、flow 数、TLS / IPsec、inspection、logging、queue 数が変われば必要 CPU も変わります。
- 64-byte packet と大きな packet の比率
- new connection rate と同時 session 数
- 暗号化、IDS / IPS、URL filtering の有無
- RX / TX queue、RSS、softirq の分散
- pps、throughput、drop、jitter、p99 latency
- license が vCPU 数や throughput を制限していないか
vendor sizing は初期値として使い、実際の feature と traffic で検証します。vCPU を増やしても single queue や single thread が律速なら、queue と datapath の設計を先に確認します。
よくある誤判断
| 誤判断 | 問題 | 確認方法 |
|---|---|---|
| CPU が高いから vCPU を増やす | 高 utilization でも処理量が正常な場合がある | SLO、throughput、run queue を見る |
| SMT thread を physical core と同じに数える | 共有 execution resource を二重計上する | socket、core、sibling を分ける |
| host 全体の ratio だけで決める | 単一 VM の並列性と NUMA を見落とす | VM demand と topology を確認する |
| vCPU count だけを見る | quota と pinning が capacity を制限する | schedinfo と affinity を見る |
| 通常時だけ test する | 障害集約時に contention が増える | N+1 状態で workload を測る |
| 一度に多く増やす | 性能の転換点を見失う | 段階的に増減する |
まとめ
単一 VM の vCPU sizing は、specification の数字ではなく、workload の並列 demand を host の physical capacity へ配置する設計です。物理 core、SMT、NUMA、quota、pinning、overcommit を分けて確認します。
少ない vCPU から始め、同じ workload で段階的に増やし、throughput の増分と p99、CPU pressure、steal を比較します。通常時だけでなく縮退時 capacity まで満たす構成を選ぶことが、vCPU を過不足なく決めるための要点です。

