mirror of
https://git.kernel.org/pub/scm/bluetooth/bluez.git
synced 2024-11-15 00:04:29 +08:00
b22859e3cc
This adds proper decoding for UUID properties with usage of bt_uuidstr_to_str so it can print the 'friendly' name as bellow: bluetoothctl# transport.show /org/bluez/hci0/dev_94_DB_56_F7_F2_88/sep4/fd0 Transport /org/bluez/hci0/dev_94_DB_56_F7_F2_88/sep4/fd0 UUID: Audio Source (0000110a-0000-1000-8000-00805f9b34fb) ...
239 lines
5.4 KiB
C
239 lines
5.4 KiB
C
|
|
// SPDX-License-Identifier: GPL-2.0-or-later
|
|
/*
|
|
*
|
|
* BlueZ - Bluetooth protocol stack for Linux
|
|
*
|
|
* Copyright (C) 2020 Intel Corporation. All rights reserved.
|
|
*
|
|
*
|
|
*/
|
|
|
|
#ifdef HAVE_CONFIG_H
|
|
#include <config.h>
|
|
#endif
|
|
|
|
#define _GNU_SOURCE
|
|
#include <stdio.h>
|
|
#include <stdbool.h>
|
|
#include <inttypes.h>
|
|
#include <errno.h>
|
|
#include <unistd.h>
|
|
#include <stdlib.h>
|
|
#include <fcntl.h>
|
|
#include <string.h>
|
|
|
|
#include "gdbus/gdbus.h"
|
|
|
|
#include "src/shared/util.h"
|
|
#include "src/shared/shell.h"
|
|
#include "print.h"
|
|
|
|
static void print_fixed_iter(const char *label, const char *name,
|
|
DBusMessageIter *iter)
|
|
{
|
|
dbus_bool_t *valbool;
|
|
dbus_uint32_t *valu32;
|
|
dbus_uint16_t *valu16;
|
|
dbus_int16_t *vals16;
|
|
unsigned char *byte;
|
|
int len;
|
|
|
|
switch (dbus_message_iter_get_arg_type(iter)) {
|
|
case DBUS_TYPE_BOOLEAN:
|
|
dbus_message_iter_get_fixed_array(iter, &valbool, &len);
|
|
|
|
if (len <= 0)
|
|
return;
|
|
|
|
bt_shell_printf("%s%s:\n", label, name);
|
|
bt_shell_hexdump((void *)valbool, len * sizeof(*valbool));
|
|
|
|
break;
|
|
case DBUS_TYPE_UINT32:
|
|
dbus_message_iter_get_fixed_array(iter, &valu32, &len);
|
|
|
|
if (len <= 0)
|
|
return;
|
|
|
|
bt_shell_printf("%s%s:\n", label, name);
|
|
bt_shell_hexdump((void *)valu32, len * sizeof(*valu32));
|
|
|
|
break;
|
|
case DBUS_TYPE_UINT16:
|
|
dbus_message_iter_get_fixed_array(iter, &valu16, &len);
|
|
|
|
if (len <= 0)
|
|
return;
|
|
|
|
bt_shell_printf("%s%s:\n", label, name);
|
|
bt_shell_hexdump((void *)valu16, len * sizeof(*valu16));
|
|
|
|
break;
|
|
case DBUS_TYPE_INT16:
|
|
dbus_message_iter_get_fixed_array(iter, &vals16, &len);
|
|
|
|
if (len <= 0)
|
|
return;
|
|
|
|
bt_shell_printf("%s%s:\n", label, name);
|
|
bt_shell_hexdump((void *)vals16, len * sizeof(*vals16));
|
|
|
|
break;
|
|
case DBUS_TYPE_BYTE:
|
|
dbus_message_iter_get_fixed_array(iter, &byte, &len);
|
|
|
|
if (len <= 0)
|
|
return;
|
|
|
|
bt_shell_printf("%s%s:\n", label, name);
|
|
bt_shell_hexdump((void *)byte, len * sizeof(*byte));
|
|
|
|
break;
|
|
default:
|
|
return;
|
|
};
|
|
}
|
|
|
|
void print_iter(const char *label, const char *name, DBusMessageIter *iter)
|
|
{
|
|
dbus_bool_t valbool;
|
|
dbus_uint32_t valu32;
|
|
dbus_uint16_t valu16;
|
|
dbus_int16_t vals16;
|
|
unsigned char byte;
|
|
const char *valstr;
|
|
DBusMessageIter subiter;
|
|
char *entry;
|
|
|
|
if (iter == NULL) {
|
|
bt_shell_printf("%s%s is nil\n", label, name);
|
|
return;
|
|
}
|
|
|
|
switch (dbus_message_iter_get_arg_type(iter)) {
|
|
case DBUS_TYPE_INVALID:
|
|
bt_shell_printf("%s%s is invalid\n", label, name);
|
|
break;
|
|
case DBUS_TYPE_STRING:
|
|
if (!strcasecmp(name, "UUID")) {
|
|
dbus_message_iter_get_basic(iter, &valstr);
|
|
print_uuid(label, name, valstr);
|
|
break;
|
|
}
|
|
/* fall through */
|
|
case DBUS_TYPE_OBJECT_PATH:
|
|
dbus_message_iter_get_basic(iter, &valstr);
|
|
bt_shell_printf("%s%s: %s\n", label, name, valstr);
|
|
break;
|
|
case DBUS_TYPE_BOOLEAN:
|
|
dbus_message_iter_get_basic(iter, &valbool);
|
|
bt_shell_printf("%s%s: %s\n", label, name,
|
|
valbool == TRUE ? "yes" : "no");
|
|
break;
|
|
case DBUS_TYPE_UINT32:
|
|
dbus_message_iter_get_basic(iter, &valu32);
|
|
bt_shell_printf("%s%s: 0x%08x (%d)\n", label, name, valu32,
|
|
valu32);
|
|
break;
|
|
case DBUS_TYPE_UINT16:
|
|
dbus_message_iter_get_basic(iter, &valu16);
|
|
bt_shell_printf("%s%s: 0x%04x (%d)\n", label, name, valu16,
|
|
valu16);
|
|
break;
|
|
case DBUS_TYPE_INT16:
|
|
dbus_message_iter_get_basic(iter, &vals16);
|
|
bt_shell_printf("%s%s: 0x%04x (%d)\n", label, name, vals16,
|
|
vals16);
|
|
break;
|
|
case DBUS_TYPE_BYTE:
|
|
dbus_message_iter_get_basic(iter, &byte);
|
|
bt_shell_printf("%s%s: 0x%02x (%d)\n", label, name, byte, byte);
|
|
break;
|
|
case DBUS_TYPE_VARIANT:
|
|
dbus_message_iter_recurse(iter, &subiter);
|
|
print_iter(label, name, &subiter);
|
|
break;
|
|
case DBUS_TYPE_ARRAY:
|
|
dbus_message_iter_recurse(iter, &subiter);
|
|
|
|
if (dbus_type_is_fixed(
|
|
dbus_message_iter_get_arg_type(&subiter))) {
|
|
print_fixed_iter(label, name, &subiter);
|
|
break;
|
|
}
|
|
|
|
while (dbus_message_iter_get_arg_type(&subiter) !=
|
|
DBUS_TYPE_INVALID) {
|
|
print_iter(label, name, &subiter);
|
|
dbus_message_iter_next(&subiter);
|
|
}
|
|
break;
|
|
case DBUS_TYPE_DICT_ENTRY:
|
|
dbus_message_iter_recurse(iter, &subiter);
|
|
|
|
if (dbus_message_iter_get_arg_type(&subiter) ==
|
|
DBUS_TYPE_STRING) {
|
|
dbus_message_iter_get_basic(&subiter, &valstr);
|
|
entry = g_strconcat(name, ".", valstr, NULL);
|
|
} else {
|
|
entry = g_strconcat(name, ".Key", NULL);
|
|
print_iter(label, entry, &subiter);
|
|
g_free(entry);
|
|
|
|
entry = g_strconcat(name, ".Value", NULL);
|
|
}
|
|
|
|
dbus_message_iter_next(&subiter);
|
|
print_iter(label, entry, &subiter);
|
|
g_free(entry);
|
|
break;
|
|
default:
|
|
bt_shell_printf("%s%s has unsupported type\n", label, name);
|
|
break;
|
|
}
|
|
}
|
|
|
|
void print_property_with_label(GDBusProxy *proxy, const char *name,
|
|
const char *label)
|
|
{
|
|
DBusMessageIter iter;
|
|
|
|
if (g_dbus_proxy_get_property(proxy, name, &iter) == FALSE)
|
|
return;
|
|
|
|
print_iter("\t", label ? label : name, &iter);
|
|
}
|
|
|
|
void print_property(GDBusProxy *proxy, const char *name)
|
|
{
|
|
print_property_with_label(proxy, name, NULL);
|
|
}
|
|
|
|
void print_uuid(const char *label, const char *name, const char *uuid)
|
|
{
|
|
const char *text;
|
|
|
|
text = bt_uuidstr_to_str(uuid);
|
|
if (text) {
|
|
char str[26];
|
|
unsigned int n;
|
|
|
|
str[sizeof(str) - 1] = '\0';
|
|
|
|
n = snprintf(str, sizeof(str), "%s", text);
|
|
if (n > sizeof(str) - 1) {
|
|
str[sizeof(str) - 2] = '.';
|
|
str[sizeof(str) - 3] = '.';
|
|
if (str[sizeof(str) - 4] == ' ')
|
|
str[sizeof(str) - 4] = '.';
|
|
|
|
n = sizeof(str) - 1;
|
|
}
|
|
|
|
bt_shell_printf("%s%s: %s%*c(%s)\n", label, name, str, 26 - n,
|
|
' ', uuid);
|
|
} else
|
|
bt_shell_printf("%s%s: %*c(%s)\n", label, name, 26, ' ', uuid);
|
|
}
|