Archive for the Linux Category --Dbus study

本文档详细介绍了Linux中的D-Bus体系,包括d-bus的封装、D-Bus 体系结构、客户端和服务器端的编写、Glib绑定接口、消息的发送和处理流程。内容涵盖d-bus的使用、接口描述、对象路径、方法和信号、接口概念以及dbus启动问题。文章旨在提供对D-Bus的深入理解和实践指导。
摘要由CSDN通过智能技术生成

Archive for the Linux Category

来自: http://www.robotercoding.com/blog/?cat=3 

d-bus系统相当庞大,源代码有100多文件,大小差不多有2M,接口很复杂,即使使用glib的绑定接口,应用程序需要编写的代码都比较多,也需要了解d-bus的一些细节。因此开发平台时,希望能够把d-bus完全封装掉,上层应用程序不用知道d-bus的概念,他们对是否采用d-bus,dcop,或者直接使用scoket都不关心。

qt4发布了一个QtDBus,用于qt的绑定,与glib的绑定基本类似,很适合qt的使用习惯。

有几个问题:
1.变参无法封装掉,c里面使用可变参数是很通常的做法,dbus提供的很多接口都是可变参数,如dbus_message_get_args,可以一次性把所有参数内容取出来,应用程序需要直接填充参数字段。但是用C++来封装似乎很麻烦,还没有找到较好的方法,但是可以不用dbus的变参接口。
2.dbus-glib做了很好的封装,对消息的发送和处理过程都封装得不错,应用可以不用知道底层的一些细节。但是dbus-glib的消息分派有自己的一套,会和将要开发的消息处理框架有冲突。相当于一套系统中有两套消息处理系统,这样会打架的,因此也不能使用dbus-glib,只能从dbus底层接口来考虑,gpe phone也是这样做的。

准备借鉴dbus-glib的封装方式,使用一个xml文件描述接口内容,再分别生成client端的发送消息接口,server端的消息接收处理接口。client的应用可以直接调用发送消息接口,server端应用可以直接处理消息结束接口,在dbus-glib中,server端是使用回调函数来处理,C++中可以使用虚函数来处理。这样的方式其实就是dbus-glib的方式,但是封装dbus底层接口的好处是可以将dbus控制到自己手中,和其他的消息处理系统一块运行。

server端的编写

在GLib中,通过dbus表现出GObject,必须写XML文件描述这个对象的方法等属性。像上一篇文章中提到的例子:

<?xml version="1.0" encoding="UTF-8" ?>
<node name="/com/example/MyObject">
<interface name="com.example.MyObject">
<method name="ManyArgs">
<arg type="u" name="x" direction="in" />
<arg type="s" name="str" direction="in" />
<arg type="d" name="trouble" direction="in" />
<arg type="d" name="d_ret" direction="out" />
<arg type="s" name="str_ret" direction="out" />
</method >
</interface >
</node >

一旦写完XML,运行dbus-binding-tool工具,如 dbus-binding-tool –mode=glib-server my-object.xml > my-object-glue.h.

然后在本地代码中include产生的头文件,调用dbus_g_object_class_install_info进行类的初始化,传递对象和对象信息进去,如 dbus_g_object_type_install_info (COM_FOO_TYPE_MY_OBJECT, &com_foo_my_object_info);每个对象类都需要这样做。

为了执行方法,需要定义一个C函数,如my_object_many_args,需要遵守的规则如下:
1.函数返回gboolean,true表示成功,false标识失败。
2.第一个参数必须是对象实例的指针。
3.跟在实例指针后面的参数是方法的输入参数。
4.输入参数后面是输出参数。
5.最后一个参数必须是GError **,如果函数返回失败,必须使用g_set_error填充该错误参数。
如下的xml文件

<method name="Increment">
<arg type="u" name="x" />
<arg type="u" direction="out" />
</method>

对应的函数定义为:
gboolean
my_object_increment (MyObject *obj, gint32 x, gint32 *ret, GError **error);

最后可以使用dbus_g_connection_register_g_object输出一个对象,如
dbus_g_connection_register_g_object (connection,”/com/foo/MyObject”, obj);

server端的声明(Annotations):
org.freedesktop.DBus.GLib.CSymbol
org.freedesktop.DBus.GLib.Async
org.freedesktop.DBus.GLib.Const
org.freedesktop.DBus.GLib.ReturnVal

client端编写

我们的程序在使用dbus的时候,首先需要连接上dbus,使用dbus_g_bus_get获得dbus连接。然后可以创建代理对象。

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值