Hello mr Barry, I succeeded to find out what was the problem. Actually I needed to iterate on the list. This is the working code: GVariantBuilder *builder = g_variant_builder_new( G_VARIANT_TYPE("a{sv}") ); GVariant *options = g_variant_new ("a{sv}", builder); g_variant_builder_unref (builder); GVariant *args = g_variant_new("(@a{sv})", options); GVariant *result = bluez_adapter_call_method_sync(rx_path.c_str(), "ReadValue", "org.bluez.GattCharacteristic1", args); if (result) { GVariant *received_data = g_variant_get_child_value(result, 0); GVariantIter i; g_variant_iter_init(&i, received_data); GVariant* dataByte; while (g_variant_iter_next(&i, "@y", &dataByte)) { cout << g_variant_get_byte(dataByte) << endl; } } Right now I'm able to send data easily, but still I am not able to read data... Question, do you know in gdbus command line if I introspect the path: /org/bluez/hci1/dev_C7_5E_38_E7_67_25/service000b/char000e (C7:5E:38:E7:67:25), if it has the UUID 6e400003-b5a3-f393-e0a9-e50e24dcca9e (the regular receive UUID) and I send the next command: gdbus call --system --dest org.bluez --object-path /org/bluez/hci1/dev_C7_5E_38_E7_67_25/service000b/char000c --method org.bluez.GattCharacteristic1.ReadValue "{}" Why is never give me proper results? If I write with call --system --dest org.bluez --object-path /org/bluez/hci1/dev_C7_5E_38_E7_67_25/service000b/char000e --method org.bluez.GattCharacteristic1.WriteValue "(['test'], {})", the send service with UUID 6e400002-b5a3-f393-e0a9-e50e24dcca9e, the data will be sent properly, and if I ReadValue from the send service gdbus call --system --dest org.bluez --object-path /org/bluez/hci1/dev_C7_5E_38_E7_67_25/service000b/char000e --method org.bluez.GattCharacteristic1.ReadValue "{}", it will echo back what it sent (string "test"). Am I doing something wrong? Shouldn't I just simply call ReadValue from the service that has proper receiving UUID, and than that's it? Do I need to call any NotifyAcquire or so? Thank you and looking forward for your reply. Cristian-Stefan Cristian-Stefan On Mon, Feb 20, 2023 at 9:14 AM Barry Byford <31baz66@xxxxxxxxx> wrote: > > Hi Cristian-Stefan, > > As I said, I'm not overly familiar with C so I'm not sure what the issue is with your code (or even if it is wrong). I can point a couple of areas that don't look as I would expect but I can't do more than that. > > The BlueZ documentation https://git.kernel.org/pub/scm/bluetooth/bluez.git/tree/doc/gatt-api.txt#n72 says that ReadValue returns array{byte} which is "ay" as a D-Bus signature. I believe that is byte[] as a C type. > > You seem to be using "g_variant_get_bytestring" on the result. "bytestrings" are a special concept in D-Bus as they must always end with a null termination. > > To simplify such use glib has helper functions like g_variant_get_bytestring() that ensures that the array is null terminated (it returns the empty string otherwise) and g_variant_new_bytestring() (creates an array of bytes including the terminating 0 from a "C string"). However, these are just a helper functions, and not something you'd use for non-bytestring byte arrays. > https://developer-old.gnome.org/glib/stable/glib-GVariant.html#g-variant-get-bytestring > > As you are getting a byte array then you need to do the conversion yourself. > > Hope that helps. > > Regards, > Barry > > > > On Sun, 19 Feb 2023 at 22:28, Neacsu Cristian <neacsu.cristianstefan@xxxxxxxxx> wrote: >> >> Hello, >> >> I am trying to develop my GATT client using DBUS >> I have the next code in order to read some data using ReadValue, but >> i'm not sure that I convert properly the results into string. >> >> If I'm using the next gdbus command: >> gdbus call --system --dest org.bluez --object-path >> /org/bluez/hci1/dev_C7_5E_38_E7_67_25/service000b/char000c --method >> org.bluez.GattCharacteristic1.ReadValue "{}" >> ([byte 0x48, 0x45, 0x4c, 0x4c, 0x4f, 0x21],) // it means HELLO! >> >> If I use my code, is giving me nothing: >> >> GVariantBuilder *builder = g_variant_builder_new( >> G_VARIANT_TYPE("a{sv}") ); >> GVariant *options = g_variant_new ("a{sv}", builder); >> g_variant_builder_unref (builder); >> >> GVariant *args = g_variant_new("(@a{sv})", options); >> >> GVariant *result = >> bluez_adapter_call_method_sync(tx_path.c_str(), "ReadValue", >> "org.bluez.GattCharacteristic1", args); >> if (result) { >> GVariant *received_data = g_variant_get_child_value(result, 0); >> cout << g_variant_get_bytestring(received_data) << endl; >> } >> >> tx_path is initialized with >> /org/bluez/hci1/dev_C7_5E_38_E7_67_25/service000b/char000c >> >> Do you have any idea what I'm doing wrong? >> Thank you in advance >> >> Cristian-Stefan