當 KVM 來賓需要時,主機 CPU 不會調整頻率
觀察:
我有一台帶有 AMD 雙核 CPU (Turion II Neo N40L) 的 HP 伺服器,它可以將頻率從 800 擴展到 1500 MHz。頻率縮放在 FreeBSD 9 和帶有 Linux 核心 3.5 的 Ubuntu 12.04 下工作。但是,當我將 FreeBSD 9 置於 Ubuntu 之上的 KVM 環境中時,頻率縮放不起作用。來賓(因此是 FreeBSD)不會檢測最小和最大頻率,因此當 CPU 佔用率變高時不會縮放任何東西。在主機(因此是 Ubuntu)上,KVM 程序使用了 80% 到 140% 的 CPU 資源,但沒有發生頻率縮放,頻率保持在 800 MHz,儘管當我在同一個 Ubuntu 機器上執行任何其他程序時,按需調速器很快將頻率縮放到 1500 MHz!
關注和問題:
我不明白 CPU 是如何虛擬化的,以及是否由來賓來執行適當的縮放。是否需要向來賓公開一些 CPU 功能才能使其工作?
附錄:
下面的Red Hat 發行說明傾向於建議頻率擴展即使在虛擬化環境中也能工作(參見第 6.2.2 和 6.2.3 章),認為該說明未能說明該使用哪種虛擬化技術(kvm、xen , ETC。?)
有關資訊,
cpufreq-info
Ubuntu 上的輸出為:$ cpufreq-info cpufrequtils 007: cpufreq-info (C) Dominik Brodowski 2004-2009 Report errors and bugs to cpufreq@vger.kernel.org, please. analyzing CPU 0: driver: powernow-k8 CPUs which run at the same hardware frequency: 0 CPUs which need to have their frequency coordinated by software: 0 maximum transition latency: 8.0 us. hardware limits: 800 MHz - 1.50 GHz available frequency steps: 1.50 GHz, 1.30 GHz, 1000 MHz, 800 MHz available cpufreq governors: conservative, ondemand, userspace, powersave, performance current policy: frequency should be within 800 MHz and 1.50 GHz. The governor "ondemand" may decide which speed to use within this range. current CPU frequency is 800 MHz. cpufreq stats: 1.50 GHz:14.79%, 1.30 GHz:1.07%, 1000 MHz:0.71%, 800 MHz:83.43% (277433) analyzing CPU 1: driver: powernow-k8 CPUs which run at the same hardware frequency: 1 CPUs which need to have their frequency coordinated by software: 1 maximum transition latency: 8.0 us. hardware limits: 800 MHz - 1.50 GHz available frequency steps: 1.50 GHz, 1.30 GHz, 1000 MHz, 800 MHz available cpufreq governors: conservative, ondemand, userspace, powersave, performance current policy: frequency should be within 800 MHz and 1.50 GHz. The governor "ondemand" may decide which speed to use within this range. current CPU frequency is 800 MHz. cpufreq stats: 1.50 GHz:14.56%, 1.30 GHz:1.06%, 1000 MHz:0.79%, 800 MHz:83.59% (384089)
我想讓這個功能發揮作用的原因是:節省能源,執行更安靜(不那麼熱),以及更好地理解為什麼它不工作以及如何讓它工作的簡單好奇心。
調整按需CPU DVFS調控器
按需調節器有一組參數來控制它何時啟動動態頻率縮放(或用於動態電壓和頻率縮放的 DVFS)。這些參數位於 sysfs 樹下:
/sys/devices/system/cpu/cpufreq/ondemand/
顧名思義,其中一個參數是
up_threshold
一個門檻值(單位是 CPU 的百分比,但我還沒有發現這是每個核心還是合併的核心),在該門檻值之上,按需調控器將啟動並開始動態更改頻率。使用 sudo 將其更改為 50%(例如)很簡單:
sudo bash -c "echo 50 > /sys/devices/system/cpu/cpufreq/ondemand/up_threshold"
如果您是 root,則可以使用更簡單的命令:
echo 50 > /sys/devices/system/cpu/cpufreq/ondemand/up_threshold
注意:這些更改將在下次主機重新啟動後失去。您應該將它們添加到啟動期間讀取的配置文件中,例如
/etc/init.d/rc.local
在 Ubuntu 上。我發現我的來賓虛擬機雖然在主機上消耗了大量 CPU(80-140%),但將負載分佈在兩個核心上,所以沒有一個核心超過 95%,因此 CPU,令我惱火的是,保持在 800 MHz。現在有了上面的更新檔,CPU 可以更快地動態改變每個核心的頻率,這更適合我的需求,50% 似乎對我的客人使用來說是一個更好的門檻值,你的里程可能會有所不同。
(可選)驗證您是否使用 HPET
DVFS 可能會影響某些未正確實現計時器的應用程序。這可能是主機和/或來賓環境中的問題,儘管主機可以使用一些複雜的算法來嘗試將其最小化。但是,現代 CPU 具有更新的 TSC(時間戳計數器),它們獨立於目前 CPU/核心頻率,它們是:常量 (constant_tsc)、不變 (invariant_tsc) 或不間斷 (nonstop_tsc),請參閱這篇 Chromium 文章關於TSC 重新同步了解更多資訊。所以如果你的 CPU 配備了這種 TSC 之一,你就不需要強制 HPET。要驗證您的主機 CPU 是否支持它們,請使用類似的命令(將 grep 參數更改為相應的 CPU 功能,這裡我們測試常量 TSC):
$ grep constant_tsc /proc/cpuinfo
如果您沒有這種現代 TSC 之一,您應該:
- 主動 HPET,這在後面描述;
- 如果 VM 中有任何依賴於精確計時的應用程序,請不要使用 CPU DVFS,這是Red Hat 推薦的一種。
一個安全的解決方案是啟用 HPET 計時器(有關更多詳細資訊,請參見下文),它們的查詢速度比 TSC 慢(TSC 在 CPU 中,而 HPET 在主機板中)並且可能不精確(HPET >10MHz;TSC通常是最大 CPU 時鐘),但它們更可靠,尤其是在每個核心可能具有不同頻率的 DVFS 配置中。Linux 足夠聰明,可以使用最好的可用計時器,它將首先依賴 TSC,但如果發現太不可靠,它將使用 HPET 計時器。這在主機(裸機)系統上執行良好,但由於並非所有資訊都由管理程序正確導出,這對於來賓 VM 檢測行為不良的 TSC 來說更具挑戰性。訣竅是在來賓中強制使用 HPET,儘管您需要虛擬機管理程序才能使該時鐘源對來賓可用!
您可以在下面找到如何在 Linux 和 FreeBSD 上配置和/或啟用 HPET。
Linux HPET 配置
HPET,或高精度事件計時器,是自 2005 年以來您可以在大多數商品 PC 中找到的硬體計時器。現代作業系統可以有效地使用此計時器(Linux 核心從 2.6 開始支持它,從最新的 9.x 開始在 FreeBSD 上穩定支持但在 6.3 中引入)始終為 CPU 電源管理提供一致的時序。它還允許建構更簡單的無滴答調度器實現。
基本上,HPET 就像一個安全屏障,即使主機啟動了 DVFS,主機和訪客計時事件的影響也較小。
IBM有一篇關於啟用 HPET 的好文章,它解釋瞭如何驗證您的核心正在使用哪個硬體計時器,以及哪些是可用的。我在這裡提供一個簡短的總結:
檢查可用的硬體計時器:
cat /sys/devices/system/clocksource/clocksource0/available_clocksource
檢查目前活動計時器:
cat /sys/devices/system/clocksource/clocksource0/current_clocksource
如果您有可用的 HPET,則強制使用它的更簡單方法是修改您的引導載入程序以要求啟用它(從核心 2.6.16 開始)。此配置依賴於發行版,因此請參閱您自己的發行版文件以正確設置。您應該在核心引導行上啟用
hpet=enable
或啟用clocksource=hpet
(這又取決於核心版本或發行版,我沒有找到任何相關資訊)。這確保來賓正在使用 HPET 計時器。
注意:在我的核心 3.5 上,Linux 似乎會自動啟動 hpet 計時器。
FreeBSD 來賓 HPET 配置
在 FreeBSD 上,可以通過執行以下命令檢查哪些計時器可用:
sysctl kern.timecounter.choice
目前選擇的計時器可以通過以下方式驗證:
sysctl kern.timecounter.hardware
FreeBSD 9.1 似乎自動更喜歡 HPET 而不是其他計時器提供程序。
Todo:如何在 FreeBSD 上強制 HPET。
管理程序 HPET 導出
當主機支持時,KVM 似乎會自動導出 HPET。然而,對於 Linux 客戶機,他們會更喜歡另一個自動導出的時鐘,即 kvm-clock(主機 TSC 的半虛擬化版本)。有些人報告首選時鐘有問題,您的里程可能會有所不同。如果您想在來賓中強制使用 HPET,請參閱上面的部分。
預設情況下,VirtualBox 不會將 HPET 時鐘導出到來賓,並且在 GUI 中沒有這樣做的選項。您需要使用命令行並確保關閉 VM。命令是:
./VBoxManage modifyvm "VM NAME" --hpet on
如果客戶在上述更改後繼續選擇 HPET 以外的其他來源,請參閱上一節如何強制核心使用 HPET 時鐘作為來源。