linux進程之dbus-daemon

一:說明

D-Bus daemon是D-Bus的非常重要的一個服務,類似於IP網絡中的路由器。

跟這個後臺服務有關的應用程序包括:

dbus-daemon: D-Bus的後臺進程,作爲D-Bus的消息中轉樞紐,可分成system和session兩種。

dbus-launch: 啓動一個dbus-daemon,後面有不同的參數。一般而言,dbus-daemon啓動後需要將其地址告訴給所有需要使用該bus的applications。

當系統啓動時,需要使用dbus-launch來啓動dbus-daemon,一般而言,

一般採用下面的命令啓動dbus daemon以及dbus application

(1) eval `dbus-launch --auto-syntax`

(2) ./yourapp

第一行代碼,採用eval來執行兩次,第一次執行dbus-lauch --auto-syntax,除了啓動dbus daemon之外,還輸出了下面的內容:

DBUS_SESSION_BUS_ADDRESS='unix:path=/tmp/dbus-6Z62FMmwf3,guid=5dbd92e4865a3f56880d2120000000d6';
export DBUS_SESSION_BUS_ADDRESS;
DBUS_SESSION_BUS_PID=998;

第二次執行時就將環境變量DBUS_SESSION_BUS_ADDRESS暴露出去了。所有的dbus application在註冊DBUS服務時,必須知道這個DBUS_SESSION_BUS_ADDRESS的數據。

在第二行執行自己的dbus application的時候,根據DBUS_SESSION_BUS_ADDRESS環境變量,能夠找到session bus進行註冊和通訊。

二:理解

dbus-daemon是一個後臺進程,負責消息的轉發。它就像個路由器。最常見的基於dbus的程序也是符合C/S結構的。 

      比如我們自己寫了兩個程序,A和B,其中A是客戶,B是服務。假設A要調用B的一個函數C,那麼實際的消息流動方向是:A告訴dbus-daemon我要調用B的C函數,然後dbus-daemon則去調用B的C函數,如果C有返回值的話,B會把返回值告訴dbus-daemon,然後dbus-daemon再把返回值告訴A。由此可以看出,dbus-daemon是很關鍵的一個後臺進程。

 

      以ubuntu爲例,通常情況下,會有兩個dbus-daemon進程,一個是屬於system的,一個是屬於session的,這兩個進程,都是在用戶登錄的時候由dbus-launch啓動的。

      大多數普通程序,都是使用session的dbus-daemon,默認情況下,A就是將消息發給了這個屬於session的dbus-daemon。

 

 

      但是在調試過程中,有時想看到一些更詳細的信息,因此可以自己再啓動一個dbus-daemon,現在就有一個問題,A的消息是流向了哪一個dbus-daemon?

 

      其實dbus-daemon是有地址的,而且有一個環境變量來表示它--DBUS_SESSION_BUS_ADDRESS,可以用命令env查看到。我們的程序,也就就是依靠這個環境變量來確認使用哪一個dbus-daemon的。

      當我們登錄進桌面環境的時候,系統啓動腳本會調用到dbus-launch來啓動一個dbus-daemon,同時會把這個dbus-daemon的地址賦予環境變量DBUS_SESSION_BUS_ADDRESS。

 

      一般情況下,我們是不需要考慮DBUS_SESSION_BUS_ADDRESS的,但是,有些時候,單獨啓動一個dbus-daemon,則有助於程序的調試。

      比如,還是假設我們寫了兩個程序,A和B,其中A是客戶,B是服務。同時還使用dbus的自啓動功能(簡要說明一下,什麼是dbus的自啓動----A要調用B的函數,如果B進程還沒有啓動,則dbus-daemon會自動的先把B進程啓動起來,這就是自啓動)。

 

      由於利用dbus-daemon自啓動機制運行的服務進程,都是後臺進程,標準輸出設備已經被重定向了,如果B進程有一些調試用的打印信息,則很難直接查看。
      這個時候,就可以單獨啓動一個dbus-daemon,讓A和B都使用我們自己啓動的這個dbus-daemon,此時,這個dbus-daemon還能把B的打印信息顯示出來。

 

 

      先在終端下啓動一個dbus-daemon,命令如下形式如下:
      DBUS_VERBOSE=1 dbus-daemon --session --print-address 

      這樣的話,該dbus-daemon會前臺執行,並且打印出它的地址,地址形式類似於unix:abstract=/tmp/dbus-YcjSNNPJHg,guid=18b385acdbd58611ffd3196b4beb69f0


      然後,在執行我們的A程序的時候,設置環境變量DBUS_SESSION_BUS_ADDRESS爲剛纔得到的地址值,例如這樣執行A程序:
      DBUS_SESSION_BUS_ADDRESS=unix:abstract=/tmp/dbus-YcjSNNPJHg,guid=18b385acdbd58611ffd3196b4beb69f0  ./A

 

      這樣的話,我們的程序A和B,就是使用我們自己啓動的這個dbus-daemon來轉發消息了。同時,剛纔啓動dbus-daemon的那個終端,還會把B的打印信息顯示出來。

 

      理解上面說的這個後,還可以做的更多。
      dbus-launch是一個用來啓動dbus-daemon的腳本,它也會打印出它啓動的那個dbus-daemon的地址。

      所有使用到dbus技術的程序,都會用到DBUS_SESSION_BUS_ADDRESS環境變量,所以,我們也可以用這個環境變量來控制dbus-monitor的行爲。

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章