BlueZ:通过它的mac地址获取设备名称
问题描述:
背景:我正在研究iOS设备和嵌入式Linux板之间的OOB配对(通过USB)。目前,在Linux方面,我收到了蓝牙链接密钥(未来连接需要)以及mac地址。
ps:如果你对这个主题很熟悉 - 请看this question。
BlueZ:通过它的mac地址获取设备名称
我当前实现,使用MAC地址作为设备的名称(详情 - 见链接到上面的问题),这是正在第二bluetoothd
服务重新启动之后解决。
问题:有没有办法让拥有它的Mac只中的BlueZ帮助设备的蓝牙名称?我将在C代码中使用它来访问BlueZ的DBus接口。
答
AFAIK,没有直接的前向DBus API或从MAC地址查找名称的方法。但是这可以使用设备的“org.freedesktop.DBus.Properties”界面中的“GetManagedObjects”方法完成。
下面是伪代码,如果添加了适当的错误处理和变量,它应该可以工作。 DBus XML被添加到源代码的顶部以供参考。
#if 0
dbus-send --system --dest=org.bluez --type=method_call --print-reply /org/bluez/hci0/dev_44_D8_84_02_A3_17 org.freedesktop.DBus.Introspectable.Introspect
method return sender=:1.1 -> dest=:1.7 reply_serial=2
string "<!DOCTYPE node PUBLIC "-//freedesktop//DTD D-BUS Object Introspection 1.0//EN"
"http://www.freedesktop.org/standards/dbus/1.0/introspect.dtd">
<node>
<interface name="org.freedesktop.DBus.Introspectable">
<method name="Introspect">
<arg name="xml" type="s" direction="out"/>
</method>
</interface>
<interface name="org.bluez.Device1">
<method name="Disconnect"></method>
<method name="Connect"></method>
<method name="ConnectProfile">
<arg name="UUID" type="s" direction="in"/>
</method>
<method name="DisconnectProfile">
<arg name="UUID" type="s" direction="in"/>
</method>
<method name="Pair"></method>
<method name="CancelPairing"></method>
<property name="Address" type="s" access="read"></property>
<property name="Name" type="s" access="read"></property>
<property name="Alias" type="s" access="readwrite"></property>
<property name="Class" type="u" access="read"></property>
<property name="Appearance" type="q" access="read"></property>
<property name="Icon" type="s" access="read"></property>
<property name="Paired" type="b" access="read"></property>
<property name="Trusted" type="b" access="readwrite"></property>
<property name="Blocked" type="b" access="readwrite"></property>
<property name="LegacyPairing" type="b" access="read"></property>
<property name="RSSI" type="n" access="read"></property>
<property name="Connected" type="b" access="read"></property>
<property name="UUIDs" type="as" access="read"></property>
<property name="Modalias" type="s" access="read"></property>
<property name="Adapter" type="o" access="read"></property>
</interface>
<interface name="org.freedesktop.DBus.Properties">
<method name="Get">
<arg name="interface" type="s" direction="in"/>
<arg name="name" type="s" direction="in"/>
<arg name="value" type="v" direction="out"/>
</method>
<method name="Set">
<arg name="interface" type="s" direction="in"/>
<arg name="name" type="s" direction="in"/>
<arg name="value" type="v" direction="in"/>
</method>
<method name="GetAll">
<arg name="interface" type="s" direction="in"/>
<arg name="properties" type="a{sv}" direction="out"/>
</method>
<signal name="PropertiesChanged">
<arg name="interface" type="s"/>
<arg name="changed_properties" type="a{sv}"/>
<arg name="invalidated_properties" type="as"/>
</signal>
</interface>
<node name="player0"/></node>"
#endif
#define BT_BLUEZ_NAME "org.bluez"
#define BT_MANAGER_PATH "/"
#define BT_ADAPTER_INTERFACE "org.bluez.Adapter1"
#define BT_DEVICE_IFACE "org.bluez.Device1"
#define BT_MANAGER_INTERFACE "org.freedesktop.DBus.ObjectManager"
#define BT_PROPERTIES_INTERFACE "org.freedesktop.DBus.Properties"
int main(void)
{
char *known_address = "2C:F0:A2:26:D7:F5"; /*This is your address to search */
conn = g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, &error);
proxy = g_dbus_proxy_new_sync(conn, G_DBUS_PROXY_FLAGS_NONE, NULL, BT_BLUEZ_NAME, BT_MANAGER_PATH, BT_MANAGER_INTERFACE, NULL, &err);
result = g_dbus_proxy_call_sync(proxy, "GetManagedObjects", NULL, G_DBUS_CALL_FLAGS_NONE, -1, NULL, &err);
g_variant_get(result, "(a{oa{sa{sv}}})", &iter);
char *device_path = NULL;
char device_address[18] = { 0 };
/* Parse the signature: oa{sa{sv}}} */
while (g_variant_iter_loop(iter, "{&oa{sa{sv}}}", &device_path, NULL)) {
{
char address[BT_ADDRESS_STRING_SIZE] = { 0 };
char *dev_addr;
dev_addr = strstr(device_path, "dev_");
if (dev_addr != NULL) {
char *pos = NULL;
dev_addr += 4;
g_strlcpy(address, dev_addr, sizeof(address));
while ((pos = strchr(address, '_')) != NULL) {
*pos = ':';
}
g_strlcpy(device_address, address, BT_ADDRESS_STRING_SIZE);
}
}
if (g_strcmp0(known_address, device_address) == 0) {
/* Find the name of the device */
device_property_proxy = g_dbus_proxy_new_sync(conn, G_DBUS_PROXY_FLAGS_NONE, NULL, BT_BLUEZ_NAME, &device_path, BT_PROPERTIES_INTERFACE, NULL, NULL);
result = g_dbus_proxy_call_sync(proxy, "Get", g_variant_new("(ss)", BT_DEVICE_IFACE, "Alias"), G_DBUS_CALL_FLAGS_NONE, -1, NULL, &error);
const char *local = NULL;
g_variant_get(result, "(v)", &temp);
local = g_variant_get_string(temp, NULL);
printf("Your desired name : %s\n", local);
}
}
}
谢谢!但是,这段代码假设我们在之前已经'找到'了bt设备,不是吗? – rsht
@rsht是的,从你的问题我知道你有设备的MAC地址已经可用。否则,您可能会对某些适配器API感兴趣,如“StartDiscovery”。 –
是的,我拥有它。但是我通过iOS专用协议(iAP2通过USB)从OOB配对过程中获得了它,而不是通过BlueZ的扫描。 OOB配对的要点是将两台设备进行配对,而无需进行常规的蓝牙扫描/配对程序。无论如何,感谢你的努力,并请让我知道你是否会有其他想法。 – rsht