D-Bus 是 Desktop Bus 缩写,是一个 inter-process communication(IPC) 和 remote procedure call (RPC) 机制,用来允许在同一台机器上进行进程间通信,它是 Linux 桌面环境中最重要的产物之一。它被越来越多地被用于应用程序间通信,也被用于应用程序和操作系统内核之间的通信。很多现代的服务进程都使用 D-Bus 取代套接字作为进程间通信机制,对外提供服务。

  • 进程间通信
  • 大部分 Linux 系统用它将系统事件(比如插入 USB 设备)通知给进程

D-Bus 作为 freedesktop.org 项目的一部分进行开发,由 Red Hat Havoc Pennington 起头,该标准被 Linux 上桌面平台 GNOME 和 KDE 采用。

D-Bus 将所有消息通过总线方式管理、分发,一般采用三层结构:

  • libdbus 库,允许应用间通信
  • 建立在 libdbus 上的消息守护进程,路由消息
  • 封装库,libdbus-glib 或者 libdbus-qt 封装使用细节

D-Bus 的重点是一个叫做 dbus-daemon 的中央槽,需要对某些事件做出反应的进程,可以到 dbus-daemon 上注册,然后就能收到想要的事件通知。进程也可以创建事件,例如,udisks-daemon 进程从 ubus 监听硬盘事件,并发送到 dbus-deamon, 而 dbus-deamon 会把这些事件再转发给那些对硬盘事件感兴趣的应用。

D-Bus 在 Linux 系统中正变的越来越重要,并且从桌面系统中突破出来,systemd 和 Upstart 也同它来通信。但是,在核心系统中加入对桌面工具的依赖,有违 Linux 的设计宗旨。所以 dbus-daemon 进程被分成两类。

  • 系统实例,开机时由 init 启动,并带有 --system 选项,这个实例通常作为 D-Bus 用户运行,配置文件是 /etc/dbus-1/system.conf 一般不用修改,进程可以通过 /var/run/dbus/system_bus_socket 的 Unix 域套接字连接该实例
  • 会话实例,和系统实例不同,会话实例只在打开桌面会话时才会运行,运行的桌面应用会连接这种实例

示例

D-Bus python 官方示例

Wiki

监视 D-Bus 消息

监视总线上的消息,监视系统实例:

dbus-monitor --system

可以看到系统实例上的消息,如果输出不多,可以尝试插入一个 USB 设备,再观察日志。

监视会话实例:

dbus-monitor --session

然后在不同的窗口点击,会看到不同的消息输出。

问题

运行在 Ubuntu 上经常遇到这样的问题

Failed to determine seats of user "1000": Too many open files)

目前找到的唯一方法就是重启。

reference