CEF3是一個多進程架構框架,若是有了解過chromium的進程架構的,那麼就很容易瞭解CEF3的多進程了。打開CEF3源代碼中發佈的cefclient實例,若是打開的頁面帶有flash或者其餘插件。在任務管理其中能夠看到四個進程,顯示出命令行列。能夠看到一個主進程,通常主進程是Browser進程,其餘的分別是渲染進程(Render),GPU加速進程(GPU),插件進程(NPAPI或者PPAPI)。git
Browser進程:被定義爲主進程,負責窗口管理,界面繪製和網絡交互。github
Render 進程:Blink的渲染和Js的執行被放在一個獨立的Render 進程中;除此以外,Render進程還負責Js Binding和對Dom節點的訪問。 默認的進程模型中,會爲每一個標籤頁建立一個新的Render進程。數組
NPAPI插件進程:按需建立,每種類型的插件只會有一個進程,每一個插件進程能夠被多個Render進程共享;瀏覽器
Pepper插件進程:同NPAPI插件進程,不一樣的是爲Pepper插件而建立的進程;安全
GPU進程:按需建立,最多隻有一個,當且僅當GPU硬件加速打開的時候纔會被建立,主要用於對3D加速調用的實現。網絡
多進程的好處不少,在瀏覽器中最主要的好處是當一個頁面或者插件崩潰或假死,不會給其餘頁面帶來影響。CEF3的進程之間能夠經過IPC進行通訊。Browser和Render進程能夠經過發送異步消息進行雙向通訊。甚至在Render進程能夠註冊在Browser進程響應的異步JavaScript API。在CEF3中,Browser和Render進程間能夠經過SendProcessMessage(CefProcessId target_process, CefRefPtr<CefProcessMessage> message)函數實現消息傳遞。多線程
默認狀況下,主應用程序會被屢次啓動運行各自獨立的進程。經過傳遞不一樣的命令行參數給CefExecuteProcess函數實現的。若是主應用程序很大,加載時間比較長,或者不能在非瀏覽器進程裏使用,則宿主程序可以使用獨立的可執行文件去運行這些進程。這能夠經過配置 CefSettings.browser_subprocess_path變量作到。更閉包
chromium自己支持多種進程模型,但CEF3主要是模型是兩種:單進程和爲每一個標籤建立一個進程。後一種是缺省行爲,前邊一種可設置。經過設置命令行的--single-process,CEF3就能夠支持用於調試目的的單進程運行模型。支持的平臺爲:Windows,Mac OS X 和Linux。架構
一圖解千語,下圖給出了缺省的chromium瀏覽器的進程模型。方框表明進程,鏈接線表明IPC進程間通訊。app
因爲關於cef3進程架構的講解不多,我的猜想CEF3的進程架構和chromium應該差很少,畢竟CEF3是基於chromium的框架。更多和進程相關的內容能夠網上搜索「chromium多進程架構」。
在CEF3中,每一個進程都會運行多個線程。完整的線程類型表請參照cef_thread_id_t
typedef enum { // BROWSER PROCESS THREADS -- Only available in the browser process. /// // The main thread in the browser. This will be the same as the main // application thread if CefInitialize() is called with a // CefSettings.multi_threaded_message_loop value of false. /// TID_UI, // Used to interact with the database. TID_DB, /// // Used to interact with the file system. /// TID_FILE, // Used for file system operations that block user interactions. // Responsiveness of this thread affects users. TID_FILE_USER_BLOCKING, /// // Used to launch and terminate browser processes. /// TID_PROCESS_LAUNCHER, // Used to handle slow HTTP cache operations. TID_CACHE, // Used to process IPC and network messages. TID_IO, // RENDER PROCESS THREADS -- Only available in the render process. /// // The main thread in the renderer. Used for all WebKit and V8 interaction. /// TID_RENDERER, } cef_thread_id_t;
在Browser進程中包含以下主要的線程:
因爲CEF採用多線程架構,有必要使用鎖和閉包來保證數據的線程安全語義。IMPLEMENT_LOCKING定義提供了Lock()和 Unlock()方法以及AutoLock對象來保證不一樣代碼塊同步訪問數據。CefPostTask函數組支持簡易的線程間異步消息傳遞。更多信息,請參考Posting Tasks章節。
能夠經過CefCurrentlyOn()方法判斷當前所在的線程環境,cefclient工程使用下面的定義來確保方法在指望的線程中被執行。
#define REQUIRE_UI_THREAD() ASSERT(CefCurrentlyOn(TID_UI)); #define REQUIRE_IO_THREAD() ASSERT(CefCurrentlyOn(TID_IO)); #define REQUIRE_FILE_THREAD() ASSERT(CefCurrentlyOn(TID_FILE));