当前位置:首页 > > 充电吧
[导读]通信数据的设置和获取前篇主要是有讲一些相对高层的概念,比如 object,interface,method 之类的,对于这些“C 本来没有的东西”,如何在 DBus 中表现的确实很让我迷惑了一阵。但通


通信数据的设置和获取

前篇主要是有讲一些相对高层的概念,比如 object,interface,method 之类的,对于这些“C 本来没有的东西”,如何在 DBus 中表现的确实很让我迷惑了一阵。但通信数据的发送可能比前面那些名称好理解得多。因为这些概念都是很本来就是底层的,很 C 的。

DBus 提供了一个 DBusMessageIter 的类型,使用这个类型的变量,我们就可以向 DBusMessage 中很容易地加入数据,也可以很容易地从中取出数据。

DBusMessage* msg;DBusMessageIter args; // msg... dbus_message_iter_init_append(msg, &args);dbus_uint32_t my_data = 10;if(!dbus_message_iter_append_basic(&args, DBUS_TYPE_UINT32, &my_data)) {    printf("Out of memoryn");    return RES_FAILED;} dbus_connection_flush(conn);dbus_message_unref(msg);

第 2 行的代码声明了一个 DBusMessageIter 的对象 args,第 6 行的代码处,对 args 进行初始化,这可以让一个 DBusMessageIter 对象与对应的 DBusMessage 关联起来,后面再对 DBusMessageIter的时候(设置或者取得数据),就是对相应的 DBusMessage 进行处理。然后使用第8行的函数,将一个 uint32 的数据 my_data 追加到 msg 中了。如果还要追加新的参数的话,只需要继续调用该函数,并传入适当的参数就可以了。

dbus_bool_t dbus_message_iter_append_basic(DBusMessageIter * iter,                                                          inttype,                                           const void *      value                                           )

这个函数可以用来向 DBusMessageIter 中追加一些“基本类型”(basic)的数据,所谓基本类型的数据,在 DBus 中是这么定义的:

Conventional Name

Encoding

Alignment

BYTE

A single 8-bit byte.

1

BOOLEAN

As for UINT32, but only 0 and 1 are valid values.

4

INT16

16-bit signed integer in the message's byte order.

2

UINT16

16-bit unsigned integer in the message's byte order.

2

INT32

32-bit signed integer in the message's byte order.

4

UINT32

32-bit unsigned integer in the message's byte order.

4

INT64

64-bit signed integer in the message's byte order.

8

UINT64

64-bit unsigned integer in the message's byte order.

8

DOUBLE

64-bit IEEE 754 double in the message's byte order.

8

STRING

UINT32 indicating the string's length in bytes excluding its terminating nul, followed by non-nul string data of the given length, followed by a terminating nul byte.

4

(for the length)

OBJECT_PATH Exactly the same as STRING except the content must be a valid object path (see below).

4

(for the length)

(参考 DBus 的在线 API 的 Marshaling (Wire Format) 一节)

有 basic type,当然也就有更复杂的不是 basic 的类型,但这和基本概念的关系不大,在这篇文章中就不多介绍了。(请参考我其它的 DBus 博文)

到现在为止,我已经知道如何把数据入到一个 DBusMessage 中了,那么,如何从一个 DBusMessage 中取出数据呢?比如,我在 A 进程使用上面的代码把 my_data 加到 DBusMessage 中了,现在 B 进程取到了 DBusMessage,如何把数据取出来呢?

DBusMessage* msg;DBusMessageIter args; // get a DBusMessage from process A if(!dbus_message_iter_init(msg, &args)) {    printf("dbus_message_iter_init error, msg has no arguments!n");}else if (DBUS_TYPE_UINT32 != dbus_message_iter_get_arg_type(&args)){    printf("not a uint 32 type !n");}else {    dbus_uint32_t my_age = 0;    dbus_message_iter_get_basic(&args, &my_age);    printf("Got signal with value %dn", my_age);}

很简单,一样的先使用 dbus_messge_iter_init 先把 DBusMessage 对象和从 DBus 总线中取到的 msg 关联起来。这样,使用第 9 行的函数先取得第一个通信数据中第一个参数的类型,如果类型无误的话可以进而使用第 14 行的函数取得参数值本身。

这样,一个简单的数据如何入到 DBusMessage 中,又如何从 DBusMessage 中取出来就明白了。那么如何将 DBusMessage 在进程之间传递呢?

消息的发送和获取

消息的发送其实比较简单,当进程 A 准备申请好一个 DBusMessage对象,设置好它的“类型”(就是各种名字),放好需要通信的数据,之后,使用下面的代码就可以将数据发送到总线上:

dbus_uint32_t serial = 0; if(!dbus_connection_send(conn, msg, &serial)) {    printf("Out of memory");    return RES_FAILED;}dbus_connection_flush(conn);

这很简单,只是 dbus_connection_flush 这个函数有点突兀,它的作用是“Blocks until the outgoing message queue is empty.”,可以简单地理解为调用这个函数可以使用得发送进程一直等消息发送完了才能继续运行。

接受方的代码也很简单:

dbus_connection_read_write(conn, 0);msg = dbus_connection_pop_message(conn); if(NULL == msg) {    sleep(1);    continue;}

使用 1 和 2 行的代码就可以取出发送到本进程的消息,之后就可以使用 msg (如果 msg 不是 NULL 的话)来获取通信数据了。

 

到这里,基本概念就有了。后面,应该对 DBus 的细节再深入的探索。

 

Sample 代码:

发送方进程(my_client):

My_Client.cpp #include 

本站声明: 本文章由作者或相关机构授权发布,目的在于传递更多信息,并不代表本站赞同其观点,本站亦不保证或承诺内容真实性等。需要转载请联系该专栏作者,如若文章内容侵犯您的权益,请及时联系本站删除。
换一批
延伸阅读

LED驱动电源的输入包括高压工频交流(即市电)、低压直流、高压直流、低压高频交流(如电子变压器的输出)等。

关键字: 驱动电源

在工业自动化蓬勃发展的当下,工业电机作为核心动力设备,其驱动电源的性能直接关系到整个系统的稳定性和可靠性。其中,反电动势抑制与过流保护是驱动电源设计中至关重要的两个环节,集成化方案的设计成为提升电机驱动性能的关键。

关键字: 工业电机 驱动电源

LED 驱动电源作为 LED 照明系统的 “心脏”,其稳定性直接决定了整个照明设备的使用寿命。然而,在实际应用中,LED 驱动电源易损坏的问题却十分常见,不仅增加了维护成本,还影响了用户体验。要解决这一问题,需从设计、生...

关键字: 驱动电源 照明系统 散热

根据LED驱动电源的公式,电感内电流波动大小和电感值成反比,输出纹波和输出电容值成反比。所以加大电感值和输出电容值可以减小纹波。

关键字: LED 设计 驱动电源

电动汽车(EV)作为新能源汽车的重要代表,正逐渐成为全球汽车产业的重要发展方向。电动汽车的核心技术之一是电机驱动控制系统,而绝缘栅双极型晶体管(IGBT)作为电机驱动系统中的关键元件,其性能直接影响到电动汽车的动力性能和...

关键字: 电动汽车 新能源 驱动电源

在现代城市建设中,街道及停车场照明作为基础设施的重要组成部分,其质量和效率直接关系到城市的公共安全、居民生活质量和能源利用效率。随着科技的进步,高亮度白光发光二极管(LED)因其独特的优势逐渐取代传统光源,成为大功率区域...

关键字: 发光二极管 驱动电源 LED

LED通用照明设计工程师会遇到许多挑战,如功率密度、功率因数校正(PFC)、空间受限和可靠性等。

关键字: LED 驱动电源 功率因数校正

在LED照明技术日益普及的今天,LED驱动电源的电磁干扰(EMI)问题成为了一个不可忽视的挑战。电磁干扰不仅会影响LED灯具的正常工作,还可能对周围电子设备造成不利影响,甚至引发系统故障。因此,采取有效的硬件措施来解决L...

关键字: LED照明技术 电磁干扰 驱动电源

开关电源具有效率高的特性,而且开关电源的变压器体积比串联稳压型电源的要小得多,电源电路比较整洁,整机重量也有所下降,所以,现在的LED驱动电源

关键字: LED 驱动电源 开关电源

LED驱动电源是把电源供应转换为特定的电压电流以驱动LED发光的电压转换器,通常情况下:LED驱动电源的输入包括高压工频交流(即市电)、低压直流、高压直流、低压高频交流(如电子变压器的输出)等。

关键字: LED 隧道灯 驱动电源
关闭