王瑞聰,韓 瓊,張明慶,張 帆
(中國航天科工集團第二研究院 七〇六所,北京 100854)
近年來,隨著虛擬化技術[1]的發(fā)展,越來越多的業(yè)務、應用被部署于虛擬機上,這樣雖然可以獲得靈活性與便捷性,提升物理資源的利用率,但也對虛擬機的高可用性提出更嚴格的要求。虛擬機依托于物理服務器,物理服務器故障是所有企業(yè)都不可避免的問題。一旦物理服務器出現(xiàn)故障,運行在其上的虛擬機將會出現(xiàn)故障,虛擬機上所有的應用服務將會中斷,給企業(yè)造成巨大的經濟損失[2]。因此,如何保障虛擬機上應用服務的連續(xù)性,即虛擬機的容錯能力成為研究熱點[3]。
在廣泛的需求推動下,市場上已經涌現(xiàn)出許多虛擬機容錯服務,主流的如Xen Remus、everRun VM、VMware FT、QEMU/KVM COLO等[4]。這些虛擬機容錯功能大都以雙機容錯實現(xiàn),即在兩臺物理服務器上,分別創(chuàng)建一個虛擬機,一個作為主虛擬機PVM(primary virtual machine)對外提供服務,另一個作為備虛擬機SVM(seco-ndary virtual machine),作為主虛擬機的有效副本,在主虛擬機宕機后,無縫接替主虛擬機繼續(xù)對外提供服務。容錯功能的實現(xiàn)是通過高速網線將主虛擬機上的內存、寄存器狀態(tài)、磁盤等信息不斷地傳輸至備份虛擬機,使備虛擬機始終同步為一個可靠可用的副本[5]。
COLO(coarse-grained lock-stepping virtual machine for non-stop service)是一種針對網絡數(shù)據(jù)包的粗粒度鎖步虛擬機方法,提供容錯功能實現(xiàn)不間斷服務[14]。當部署圖形化操作系統(tǒng)的虛擬機啟用COLO功能,通過遠程連接操作虛擬機桌面會遇到主備虛擬機界面顯示不一致的現(xiàn)象,這將導致主備虛擬機間同步次數(shù)增多、同步耗時增加等問題。本文針對上述問題,提出一種通過分發(fā)鼠標鍵盤輸入,檢查桌面窗口輸出的方法,減少界面不一致情況以降低同步時間,提高系統(tǒng)性能,優(yōu)化用戶體驗。
QEMU/KVM屬于虛擬機監(jiān)控器VMM(virtual machine monitor)的一種[6],可以運行在多個操作系統(tǒng)平臺上,對國產化平臺也有較好的支持。QEMU是一個快速的開源模擬器,而內核虛擬機KVM(kernel-based virtual machine)是一個基于Linux內核的虛擬化解決方案[7],其架構如圖1所示。QEMU和KVM相互補充,KVM負責處理虛擬機的調度和資源管理,而QEMU則負責提供虛擬設備模擬等功能,使得在Linux系統(tǒng)上能夠高效地創(chuàng)建和運行虛擬機。
圖1 QEMU/KVM整體架構
QEMU/KVM提供了熱遷移技術,允許將運行中的虛擬機從一個物理主機遷移到另一個物理主機,而無需中斷虛擬機運行,并且用戶在遷移過程中沒有明顯感知。熱遷移技術是虛擬機容錯功能的實現(xiàn)基礎,通過連續(xù)的熱遷移操作,主虛擬機的狀態(tài)信息會定期復制到備份虛擬機上,這被稱為雙機熱備[8]。在此基礎上,COLO通過時刻保持備份虛擬機是一個有效且可用的副本,實現(xiàn)了高可用性的雙機容錯功能。當主虛擬機發(fā)生故障時,備份虛擬機可以無縫接替主虛擬機的工作,確保系統(tǒng)的持續(xù)運行[9]。本文以COLO容錯機制為基礎,在國產平臺下研究解決COLO對于桌面同步表現(xiàn)不佳的問題。
使用QEMU/KVM創(chuàng)建虛擬機后,可以通過VNC遠程連接虛擬機桌面進行訪問與操作[6]。VNC(virtual network console)是一種用于遠程桌面訪問和控制的開源技術。VNC允許用戶通過網絡連接到遠程計算機,以實時查看、操作遠程計算機[10]。VNC有viewer與server端分別運行于本地計算機與遠程計算機上,viewer端將用戶在本地的輸入操作反饋給遠程計算機,同時遠程計算機的server端將屏幕圖像捕獲并傳輸?shù)娇蛻舳?。VNC基于RFB(remote frame buffer)協(xié)議進行通信,使用基于幀的圖像傳輸方式,只傳輸屏幕上發(fā)生變化的像素矩陣,從而降低了網絡帶寬的需求。
TigerVNC是一個開源的VNC實現(xiàn),它提供了高性能、可靠的遠程桌面訪問和控制功能[10]。本文依托于開源的TigerVNC,設計實現(xiàn)同時連接兩臺遠程計算機的功能,并實現(xiàn)兩臺計算機輸入一致機制。
QEMU/KVM提供了粗粒度鎖步虛擬機復制的雙機容錯功能COLO,以實現(xiàn)系統(tǒng)高可用性。COLO的核心設計思想是,對于虛擬機容錯,只要備虛擬機可以在主虛擬機出現(xiàn)故障無法繼續(xù)提供網絡服務時能夠成功接管對外網絡服務即可。也就是說,只要備虛擬機和主虛擬機對于外部網絡請求的響應是一致的,即使兩個虛擬機的其它一些狀態(tài)信息可能不一致,仍然認為備虛擬機是主虛擬機的一個有效副本[13],可以接替主虛擬機提供服務。
COLO的架構設計如圖2所示,包含兩個由高速網絡連接起來的物理服務器:主節(jié)點和備節(jié)點。主虛擬機運行在主節(jié)點上,備虛擬機運行在備節(jié)點上,主節(jié)點通過高速網線不斷地將主虛擬機的狀態(tài)信息拷貝傳輸至備節(jié)點,備節(jié)點利用這些狀態(tài)信息修改備虛擬機的狀態(tài),以此來保存一個主虛擬機的有效備份。COLO要求主備虛擬機同時運行,并響應外部網絡請求。來自外部的請求被主節(jié)點接收,然后分發(fā)給主虛擬機和備虛擬機,從而使得主備虛擬機獲得同樣的請求。COLO接收到來自主虛擬機和備虛擬機的響應,然后在將響應輸出到外部之前,先比較二者響應是否一致。只要兩個響應一致,則認為備虛擬機是主虛擬機的一個有效備份,不需要進行虛擬機同步操作。一旦兩個響應出現(xiàn)差異,則先緩存來自主虛擬機的響應,與此同時進行主備虛擬機的同步操作,待同步操作完成之后,再將響應發(fā)送出去[14]。
圖2 COLO整體架構設計
COLO Proxy是COLO容錯功能的核心模塊,其主要功能是實現(xiàn)主備虛擬機響應數(shù)據(jù)包的比較,檢測二者是否一致。COLO Proxy模塊設計如圖3所示,其中A、B、C、D、E是一些轉發(fā)數(shù)據(jù)包的子模塊。A負責接收網絡設備中的外部請求,并將請求傳輸給主虛擬機與D模塊。B接收colo compare模塊比較后的響應,并發(fā)送給網絡設備。C接收主虛擬機的響應,并將該響應發(fā)送至colo compare模塊供比較使用。D模塊接收A模塊發(fā)來的網絡請求,經過一定數(shù)據(jù)包處理,發(fā)送給備虛擬機,使備虛擬機能正確與外部請求端建立連接。同樣地,備虛擬機的響應包也需要經過處理,發(fā)送至E模塊,然后E模塊將數(shù)據(jù)包發(fā)送至colo compare模塊。colo compare接收來自主備虛擬機的響應包進行比較,一致則丟棄備虛擬機響應包,將主虛擬機響應包發(fā)送給B,不一致則暫緩輸出,觸發(fā)同步操作[15]。
圖3 COLO Proxy模塊設計
通過上述分析,可以發(fā)現(xiàn)COLO非常適用于類似ssh連接遠程虛擬機對外提供網絡服務的操作。通過引入COLO機制,可以將周期性的同步間隔由毫秒級延長至分鐘級,期間通過網絡響應包的不一致來觸發(fā)同步,有效降低主備虛擬機的同步頻率,減少虛擬機用于同步的資源開銷,提升虛擬機性能[16]。
然而,當虛擬機內運行擁有圖形界面的操作系統(tǒng),QEMU會模擬一個顯示設備,將虛擬機的圖形輸出保存到虛擬顯存中,通過VNC連接虛擬機桌面并在圖形化桌面上進行各種操作,如鼠標拖拽窗口、鍵盤鍵入字符時,備虛擬機不能實時與主虛擬機顯示一致,在COLO降低同步頻率的情況下,主備的屏幕顯示可能會有分鐘級的差異,這會造成主備虛擬機機器狀態(tài),顯存數(shù)據(jù)等的不同,這時觸發(fā)同步會增加同步傳輸?shù)臄?shù)據(jù)量,延長同步時間。除此之外,在用戶使用界面進行頻繁網絡訪問操作時,該操作的數(shù)據(jù)包發(fā)送至QEMU中的VNC server端,而不會被COLO轉發(fā)至備份虛擬機內,此時備機不會進行同樣的網絡訪問操作,主備會產生不同的網絡數(shù)據(jù)包,不斷地觸發(fā)COLO同步操作,進而導致系統(tǒng)性能大大降低。
為了解決COLO在圖形化操作系統(tǒng)的虛擬機下表現(xiàn)不佳的問題,可以借鑒COLO在網絡數(shù)據(jù)包處理方面的方法進行改進。QEMU提供了VNC服務,允許用戶通過VNC客戶端遠程連接到由QEMU創(chuàng)建的虛擬機,并通過圖形界面執(zhí)行各種操作。在這個基礎上,可以采用類似COLO將網絡請求包轉發(fā)給備用虛擬機的方式來改善性能。
具體過程如下,使用VNC連接主虛擬機時,在VNC客戶端中捕獲對主虛擬機的輸入操作(例如鍵盤和鼠標操作),然后將這些操作同步發(fā)送給備用虛擬機。通過這種方式,備用虛擬機的初始狀態(tài)與主虛擬機保持一致。隨著相同輸入操作在兩個虛擬機上執(zhí)行,主備虛擬機的桌面顯示也會保持一致。這種改進方法可以有效提升在圖形化操作系統(tǒng)的虛擬機下COLO的性能,使得用戶能夠通過VNC客戶端實現(xiàn)對主虛擬機的遠程操作,并且保持主備虛擬機之間的一致性。
VNC遠程連接虛擬機也是通過網絡傳輸數(shù)據(jù),viewer端與server端通過TCP協(xié)議傳輸數(shù)據(jù),但其數(shù)據(jù)包并不經過COLO模塊。COLO模塊轉發(fā)請求主虛擬機服務的網絡包,并且捕獲比較主備虛擬機內產生的各種網絡數(shù)據(jù)包(目前支持捕獲TCP、UDP、ICMP等),而VNC遠程連接虛擬機是由QEMU處理,QEMU實現(xiàn)了VNC Server功能,響應遠端VNC Client的連接請求,連接中傳輸?shù)臄?shù)據(jù)包不會經過COLO模塊。一種直觀的改進策略是在主節(jié)點的QEMU內將響應的VNC數(shù)據(jù)包轉發(fā)給COLO模塊,備節(jié)點也將VNC數(shù)據(jù)包發(fā)送至主節(jié)點COLO模塊進行比較。然而VNC使用基于幀的圖像傳輸方式,只傳輸屏幕上發(fā)生變化的部分,通過傳輸一個個像素矩陣進行屏幕更新[17],通過實驗驗證,相同的屏幕變化,VNC Server發(fā)送的像素矩陣的個數(shù)、大小不盡相同,同時像素矩陣的數(shù)據(jù)量過大,并且存在壓縮編碼處理,因此,將VNC響應數(shù)據(jù)包引入COLO比較模塊并不現(xiàn)實。
雖然無法對主備桌面像素數(shù)據(jù)進行對比,但可以追溯桌面像素數(shù)據(jù)產生之前的過程。圖形界面由桌面系統(tǒng)繪制,國產平臺下的桌面系統(tǒng)使用X Window System開發(fā)實現(xiàn)。X Window System,又叫X Protocol、X11,是一種開源的圖形用戶界面系統(tǒng)[11]。如圖4所示,X11采用客戶端-服務器架構,X11服務端負責管理顯示設備(如顯示器)和用戶輸入設備(如鍵盤、鼠標),接收來自客戶端的事件請求并將圖形繪制到屏幕上[12]。
圖4 X11整體架構
用戶在桌面的操作經過X11客戶端的處理返回X11事件,X11服務端根據(jù)窗口事件繪制顯示屏幕設備。因此,可以通過引入X11事件進行主備虛擬機界面的比較。常見的窗口事件包括創(chuàng)建、隱藏、關閉窗口,窗口大小更改,窗口獲取焦點。X11客戶端對于相同的輸入操作產生的X11事件是完全相同的。因此,可以在虛擬機內創(chuàng)建服務Xsync捕獲相關X11事件,并將事件封裝為數(shù)據(jù)包通過網絡發(fā)送至VNC viewer端,使X11數(shù)據(jù)包經過COLO模塊進行比較。通過比較主備虛擬機X11事件是否一致,可以保證主備虛擬機的圖形界面保持一致。
如圖5所示,基于COLO容錯機制下的遠程桌面同步實現(xiàn)主要分為兩個部分。一是修改VNC viewer端,檢測用戶對主虛擬機的鼠標鍵盤輸入并分發(fā)至備份虛擬機,使主備虛擬機的輸入一致。二是在主備虛擬機內部通過X11捕獲并對外發(fā)送相關的X11事件,使其經過COLO模塊進行比較。
圖5 主備虛擬機桌面同步組件框架
TigerVNC viewer在vncviewer.cxx的mainloop()函數(shù)中使用 Conn(vncServerName,sock)建立與TigerVNC server的TCP連接cc,其中包含有輸入流is和輸出流os用以通信。為了使備份虛擬機可以接收到主虛擬機的輸入流,首先需要使用Conn(vncServerName,sock)創(chuàng)建兩條分別與主備虛擬機相連的連接cc_primary與cc_secondary,然后在cc_primary中添加輸出流os2,將備連接cc_secondary中的輸出流os賦給備連接cc_primary的os2以達到輸入分發(fā)。CMsgWriter.cxx中包含了viewer端向server端發(fā)送各種消息的操作,根據(jù)RFB協(xié)議格式組裝數(shù)據(jù)包并通過輸出流發(fā)送出去,在writeKeyEvent()、writePointerEvent()中,通過增添輸出流os2可以將主虛擬機的鍵盤鼠標事件發(fā)送到備份虛擬機。
在虛擬機內部,使用X11的擴展庫xtestlib和recordlib獲得鍵盤鼠標控制權,捕獲用戶在界面上的操作與產生的X11事件。XRecordRange用于標識一組要記錄的事件類型,這里設置為CreateNotify到ConfigureNotify,這其中包含了窗口的創(chuàng)建、關閉以及窗口大小、位置改變的事件。然后通過socket編程對外發(fā)送基于UDP的X11事件數(shù)據(jù)包。由虛擬機內部發(fā)出的網絡數(shù)據(jù)包會進入COLO模塊,進行檢查比較。這樣就填補了COLO未檢測比較主備虛擬機桌面數(shù)據(jù)是否一致的不足。
實驗所用設備的連接拓撲如圖6所示,包括兩臺國產飛騰機架式服務器作為主備節(jié)點,一臺國產一體式計算機作為陪測PC機。其中兩臺服務器物理機操作系統(tǒng)為open-Euler,虛擬機操作系統(tǒng)為銀河麒麟系統(tǒng)(桌面版),使用QEMU創(chuàng)建虛擬機,陪測PC為銀河麒麟系統(tǒng)(桌面版),詳細配置見表1。兩臺物理服務器使用萬兆網線互聯(lián),一體機與兩臺物理機處于同一局域網中,在一體機上使用VNC viewer連接兩臺物理服務器上的虛擬機。
表1 實驗環(huán)境詳細說明
圖6 實驗設備連接關系
實驗首先觀察主備虛擬機桌面顯示是否實時一致,在主備虛擬機上執(zhí)行播放視頻操作,觀察主備虛擬機視頻播放界面是否一致。
實驗使用xdotool工具模擬鼠標鍵盤輸入,測試比較引入本文改進后與原QEMU默認開啟COLO情況下的界面同步耗時情況。對于無網絡服務情況,設定操作序列:打開WPS輸入一段字符->關閉WPS->打開終端執(zhí)行命令ls->關閉終端->打開txt文本文件輸入一段字符>關閉txt文件->打開QT->關閉QT->打開影音播放器->關閉影音播放器。在每個操作后記錄同步所用時間并計算平均值。模擬操作序列的腳本需要在陪測的一體式計算機上編寫與執(zhí)行,而不在虛擬機內執(zhí)行,因為同步操作會使主備虛擬機同時執(zhí)行相同的腳本文件。對于通過桌面操作訪問網絡的情況,實驗分別模擬每隔5 s,10 s,15 s,20 s進行一次對外網絡請求,記錄1 min內觸發(fā)同步的次數(shù)和同步耗時。
使用VNC連接訪問主備虛擬機,界面如圖7所示,在主虛擬機上進行視頻播放時,備虛擬機保持與主虛擬機界面一致。
圖7 主備虛擬機界面同步展示
在無網絡服務情況下,測試無任何操作、改進前后進行界面操作情況下的主備同步時間,分別記錄10組10 min內虛擬機的同步時間并取平均值。實驗結果如圖8所示,在不操作虛擬機時COLO默認20 s同步一次,平均每次同步耗時257 ms,改進后主備虛擬機平均同步時間由523 ms縮短為435 ms,降低了16.82%。10 min內,無操作情況下總同步時間開銷為7710 ms,改進后,會偶爾發(fā)生主備虛擬機界面不一致觸發(fā)的同步,主備虛擬機總同步時間由15 690 ms縮短至14 355 ms,降低了8.50%。
圖8 主備虛擬機同步時間對比
在虛擬機上進行對外網絡操作時,原默認情況下,只有主虛擬機發(fā)出網絡數(shù)據(jù)包,備虛擬機沒有對應的網絡操作,此時COLO便會觸發(fā)同步。改進后主備虛擬機會同時進行相同的網絡操作,避免觸發(fā)檢查點同步。進行10組實驗取平均值,結果如圖9所示,在進行高頻網絡操作時,本文方法優(yōu)化提升明顯,在每隔5 s進行一次網絡請求情況下,1 min內主備虛擬機的同步次數(shù)減少了69.1%,同步耗時減少了64.7%。
圖9 不同網絡請求間隔下的對比
本文利用QEMU中COLO的設計方法,即轉發(fā)對主虛擬機的網絡請求包至備虛擬機,使主備有相同的網絡請求輸入,比較檢查主備虛擬機的網絡響應包是否一致,不一致時觸發(fā)同步操作。針對裝有圖形化操作系統(tǒng)的虛擬機,提出通過VNC輸入分發(fā),使主備虛擬機接收相同的鼠標鍵盤輸入,比較檢查主備虛擬機的X11事件是否一致,不一致時觸發(fā)同步操作,進而保證主備虛擬機一致。實驗結果表明,本文方法保證主備虛擬機圖形界面實時一致,對于虛擬機同步次數(shù)有減少作用,并且有效降低同步時間。后續(xù)的工作將研究主備虛擬機界面顯示快慢誤差所造成的不一致情況,進一步提高虛擬機性能。